{"id":18904449,"url":"https://github.com/alexalvess/poc-tests-scopes","last_synced_at":"2026-07-09T13:31:12.094Z","repository":{"id":125407886,"uuid":"481748460","full_name":"alexalvess/poc-tests-scopes","owner":"alexalvess","description":"This project has an objective to show some Tests Scopes that we have","archived":false,"fork":false,"pushed_at":"2022-05-14T17:29:02.000Z","size":520,"stargazers_count":0,"open_issues_count":0,"forks_count":1,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-07-28T19:01:55.035Z","etag":null,"topics":["fake","integration-testing","test","test-automation","unittest"],"latest_commit_sha":null,"homepage":"","language":"C#","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/alexalvess.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2022-04-14T21:01:09.000Z","updated_at":"2022-08-18T13:45:17.000Z","dependencies_parsed_at":"2023-03-24T06:18:56.641Z","dependency_job_id":null,"html_url":"https://github.com/alexalvess/poc-tests-scopes","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/alexalvess/poc-tests-scopes","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/alexalvess%2Fpoc-tests-scopes","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/alexalvess%2Fpoc-tests-scopes/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/alexalvess%2Fpoc-tests-scopes/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/alexalvess%2Fpoc-tests-scopes/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/alexalvess","download_url":"https://codeload.github.com/alexalvess/poc-tests-scopes/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/alexalvess%2Fpoc-tests-scopes/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":281397340,"owners_count":26493908,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-10-28T02:00:06.022Z","response_time":60,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["fake","integration-testing","test","test-automation","unittest"],"created_at":"2024-11-08T09:08:31.422Z","updated_at":"2025-10-28T06:35:34.908Z","avatar_url":"https://github.com/alexalvess.png","language":"C#","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Test Scopes\n\nTo cover our application, we have many types of tests for it. So, let's analyze the test pyramid:\n\n![test pyramid](https://res.cloudinary.com/practicaldev/image/fetch/s--dcM0135C--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/i/ealtg2m79jiaur0ryb3v.png)\n\nThis simple pyramid we have three kind of tests:\n\n* End-to-End: this scope allow we to test our UI\n* Integration: this scope allow we to test the providers integrations, like APIs, Databases and Queues.\n* Unit: this scope allow we to test our business logic, the application's heart.\n\nBut, you can ask me \"Why can we not use just Unit Test? It's simple, we need just mock somethings, and go on!\"... 🤔\n\nSo, the answer it's simple too 😁 But I don't tell you a simple answer, let's think the below scenario:\n\nImagine that your application has a hundred percent of coverage, and all the tests was built on Unit Scopes: You test the providers methods, entry points and your business logical. It's simple, easy and \"fast\" to do it. But, if in a moment, you need to change a provider. A big part of your test, reference the provider changed, will fail 😕, because you don't use it in the best way...\n\nLooking for our project, how can we divide the tests to cover all application?\n\n1. For the core/domain: \n\tIf we were guided for use Domain-Driven Design, we'll have Aggregates, Entities, and Value Objects that contain our representative world: business rules, properties, and behaviors. So it's interesting we cover a hundred percent and for it we can use Unit Tests, that is low cost and fast to build.\n2. For the providers:\n\tThe service layer uses the domain and providers to do something in our application. So, to guarantee the connection for these providers, we can get some main use cases to test the connections, like message brokers, APIs, and databases. We can use some In Memory strategies or mock the connection in our dependency injection to validate our connection configuration, and for it, we can use Fixture.\n3. For complete flow:\n\tOur application has a front-end client. For it, we can use the e2e test! And to build this, we can containerize the providers, configure all our environment in a docker-compose, and run it in our pipeline.\n\nSee the next chapter for a look at how we can made all this tests in practice! 👀\n\n---\n\n## [Let's Code!] Unit Test Scope 🔥\nTo my domain I represent it like this:\n\n![domain_layer](/imgs/domain_layer.png)\n\nAnd I have my Aggregates and Value Objects that contain my business logics, properties, and behaviors:\n\n```csharp\npublic class Customer : AggregateRoot\u003clong\u003e\n{\n    public string Name { get; private set; }\n\n    public DateOnly BirthDate { get; private set; }\n\n    public Credential Credential { get; private set; }\n\n    public Contact Contact { get; private set; }\n\n    public void Register(CreateCustomerRequest request)\n    {\n        Name = request.Name;\n        BirthDate = DateOnly.FromDateTime(request.BirthDate);\n        Active = request.Active;\n\n        Credential = new Credential(request.Login, request.Password);\n        Contact = new Contact(request.Contact.Email, request.Contact.Phone);\n        \n        Validate();\n    }\n\n    public void Inactivate()\n        =\u003e Active = false;\n\n    public void Activate()\n    {\n        if (IsDeleted is true)\n            return;\n\n        Active = true;\n    }\n\n    protected override bool Validate()\n        =\u003e OnValidate\u003cCustomerValidator, Customer\u003e();\n\n\t// ...\n}\n```\n\nSo, this is my application's core! So I need to guarantee this is works very fine and for it, I need to cover a hundred percent with tests! And to do this, I can use of Unit Test scope:\n\n![unit_test_project](/imgs//unit_test_project.png)\n\nAnd I can use a behavior strategy to test all my scenario, like this:\n\n```csharp\npublic class CustomerTest\n{\n\t[Fact]\n\tpublic void Register_Customer()\n\t\t=\u003e BehaviorExtensions\n\t\t\t.Given(() =\u003e CreateDefaultFakeCustomer())\n\t\t\t.When(fakeRequest =\u003e (request: fakeRequest.Generate(), customer: new Customer()))\n\t\t\t.Then(tuple =\u003e tuple.customer.Register(tuple.request))\n\t\t\t.And(tuple =\u003e tuple.customer)\n\t\t\t.Then(customer =\u003e customer.IsValid.Should().BeTrue())\n\t\t\t.Then(customer =\u003e customer.Id.Should().Be(0));\n\n\t[Fact]\n\tpublic void Register_Customer_InvalidBirthDate()\n\t\t=\u003e BehaviorExtensions\n\t\t\t.Given(() =\u003e CreateDefaultFakeCustomer())\n\t\t\t.When(requestFake =\u003e requestFake\n\t\t\t\t.RuleFor(customer =\u003e customer.BirthDate, Faker =\u003e Faker.Date.Recent()))\n\t\t\t.When(requestFake =\u003e requestFake.Generate())\n\t\t\t.When(request =\u003e (request, customer: new Customer()))\n\t\t\t.Then(tuple =\u003e tuple.customer.Register(tuple.request))\n\t\t\t.And(tuple =\u003e tuple.customer)\n\t\t\t.Then(customer =\u003e customer.IsValid.Should().BeFalse());\n\n\t// ...\n}\n```\n\nAnd with a few lines, I can cover all my aggregate (and my value objects, consequently)!\n\n---\n\n## [Let's Code!] Integration Test Scope 🔥\n\nI need to certify that all my providers are configured correctly either. \n\nSo, I have a specific project for it:\n\n![integration_test_project](/imgs//integration_test_project.png)\n\nAnd for it, I can use the Providers In Memory strategy to verify that my configurations are correct, using Fixtures:\n\n```csharp\nclass TestScopesApiFixture : WebApplicationFactory\u003cProgram\u003e\n{\n\tprotected override IHost CreateHost(IHostBuilder builder)\n\t{\n\t\tbuilder.ConfigureServices(services =\u003e\n\t\t{\n\t\t\tservices.RemoveAll(typeof(DbContextOptions\u003cPersistenceDbContext\u003e));\n\t\t\tservices.AddScoped\u003cDbContext, PersistenceDbContext\u003e();\n\t\t\tservices.AddDbContext\u003cPersistenceDbContext\u003e(options\n\t\t\t\t=\u003e options.UseInMemoryDatabase(\"integration_test\", new InMemoryDatabaseRoot()));\n\t\t});\n\n\t\treturn base.CreateHost(builder);\n\t}\n}\n```\n\nI remake my dependency injections and inject mine in-memory providers.\n\nAnd use like below:\n\n```csharp\npublic class CustomerControllerTest\n{\n    [Fact]\n    public async Task RegisterCustomer()\n    {\n        await using var api = new TestScopesApiFixture();\n        var client = api.CreateClient();\n        var request = new Faker\u003cCreateCustomerRequest\u003e(\"pt_BR\")\n            .RuleFor(customer =\u003e customer.Name, fake =\u003e fake.Person.FullName)\n            .RuleFor(customer =\u003e customer.BirthDate, fake =\u003e fake.Person.DateOfBirth)\n            .RuleFor(customer =\u003e customer.Login, fake =\u003e fake.Person.UserName)\n            .RuleFor(customer =\u003e customer.Password, fake =\u003e fake.Internet.Password())\n            .RuleFor(customer =\u003e customer.Contact, fake\n                =\u003e new Faker\u003cCreateCustomerRequest.CreateContactRequest\u003e(\"pt_BR\")\n                .RuleFor(contact =\u003e contact.Phone, fake =\u003e fake.Person.Phone)\n                .RuleFor(contact =\u003e contact.Email, fake =\u003e fake.Person.Email)\n                .Generate())\n            .Generate();\n\n        var response = await client.PostAsJsonAsync(\"/api/Customer\", request);\n        response.IsSuccessStatusCode.Should().BeTrue();\n    }\n}\n```\n\nFor this kind of test, I just do it for main use cases like registering and updating customer. Made like it, I guarantee that providers work fine and my configurations too (the configuration are the same, for real or in-memory providers, for the same type).\n\n---\n\n## [Let's Code!] E2E Test Scope 🔥\n\nDestinate to verify the complex flows and analyze the application behaviors!\n\n![e2e_test_project](/imgs/e2e_test_project.png)\n\nFor this, I choose the main use cases and try to cover it, simulate a custmer behavior:\n\n```js\ncontext('Customers', () =\u003e {\n    beforeEach(() =\u003e {\n        cy.visit('https://localhost:7184/customer')\n    })\n\n    describe('Verify customers registered', () =\u003e {\n        it('Contains 5 customers in list', () =\u003e verifyList(5))\n    })\n\n    describe('Register customers', () =\u003e {\n        beforeEach(() =\u003e cy.get('#create_customer').click())\n\n        it('With a valid fields', () =\u003e {\n            cy.get('#login').type('joaodasilva')\n            cy.get('#password').type('12345678')\n            cy.get('#name').type('João da Silva')\n            cy.get('#birth_date').type('1990-02-01')\n            cy.get('#email').type('joao@gmail.com')\n            cy.get('#phone').type('(19) 9880-0102')\n\n            cy.get('#create_customer_modal').click()\n\n            verifyList(6)\n        })\n\n        it('With invalid name', () =\u003e {\n            cy.get('#login').type('joaodasilva')\n            cy.get('#password').type('12345678')\n            cy.get('#name').type('JP')\n            cy.get('#birth_date').type('1990-02-01')\n            cy.get('#email').type('joao@gmail.com')\n            cy.get('#phone').type('(19) 9880-0102')\n\n            cy.get('#create_customer_modal').click()\n\n            verifyList(6)\n        })\n    })\n})\n```\n\n---\n\n## On Pipeline! 🧿\n\nTo run all this steps, I can build a pipeline that contains the follow steps:\n1. Build my application\n2. Run my Unit Tests\n    * Calculate the code coverage, excluding all that not unit test scopes (providers, for example)\n3. Run my Integration Tests\n    * Calculate the code coverage, excluding all that not integration test scopes (domain, for example)\n4. And run my docker-compose and execute my E2E Tests\n\nYou can see it on [Github Actions](https://github.com/alexalvess/Tests.Scopes/actions)\n\n---\n\n## Summing up\n* Unit Tests\n\t* test just my domain\n* Integration Tests\n\t* verify the providers configuration\n\t* isolated use cases\n\t* application servicer behaviors\n\t* ex.: how many times the provider was called?\n* E2E tests:\n\t* most critical use cases\n\t* complete flow\n\t\t* ex.: since interface until storage data\n\n---\n\n# References:\n- [The Practical Test Pyramid - Martin Fowler](https://martinfowler.com/articles/practical-test-pyramid.html)\n- [E2E Testing - Code With Engineering Playbook](https://microsoft.github.io/code-with-engineering-playbook/automated-testing/e2e-testing/)\n- [Unit vs Integration vs System vs E2E Testing - Code With Engineering Playbook](https://microsoft.github.io/code-with-engineering-playbook/automated-testing/e2e-testing/testing-comparison/)\n- [Domain-Driven Design \u0026 Unit Tests](https://www.jamesmichaelhickey.com/ddd-unit-tests/)\n- [Introducing BDD - Dan North \u0026 Associates LTd](http://dannorth.net/introducing-bdd/)","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Falexalvess%2Fpoc-tests-scopes","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Falexalvess%2Fpoc-tests-scopes","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Falexalvess%2Fpoc-tests-scopes/lists"}