{"id":27082302,"url":"https://github.com/dasiths/portsandadapterspatterndemo","last_synced_at":"2025-04-06T02:40:23.349Z","repository":{"id":285771719,"uuid":"639541521","full_name":"dasiths/PortsAndAdaptersPatternDemo","owner":"dasiths","description":null,"archived":false,"fork":false,"pushed_at":"2025-04-02T15:05:01.000Z","size":19,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-04-02T16:22:51.275Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"C#","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/dasiths.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"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":"2023-05-11T17:08:02.000Z","updated_at":"2025-04-02T15:05:05.000Z","dependencies_parsed_at":"2025-04-02T16:22:58.925Z","dependency_job_id":"3c722598-9d15-4a89-9156-b616877c38ed","html_url":"https://github.com/dasiths/PortsAndAdaptersPatternDemo","commit_stats":null,"previous_names":["dasiths/portsandadapterspatterndemo"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/dasiths%2FPortsAndAdaptersPatternDemo","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/dasiths%2FPortsAndAdaptersPatternDemo/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/dasiths%2FPortsAndAdaptersPatternDemo/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/dasiths%2FPortsAndAdaptersPatternDemo/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/dasiths","download_url":"https://codeload.github.com/dasiths/PortsAndAdaptersPatternDemo/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247426987,"owners_count":20937197,"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","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":[],"created_at":"2025-04-06T02:40:22.795Z","updated_at":"2025-04-06T02:40:23.340Z","avatar_url":"https://github.com/dasiths.png","language":"C#","funding_links":[],"categories":[],"sub_categories":[],"readme":"## Project Structure\n\n### 1. API Layer\n**Project Name**: `PortsAndAdaptersPatternDemo.Api`\n\n- **Purpose**: This project handles the HTTP requests and routes them to the appropriate request processors.\n- **Dependencies**: \n  - `PortsAndAdaptersPatternDemo.Data` for database context.\n  - `PortsAndAdaptersPatternDemo.RequestProcessing` for handling requests.\n\n**Key File**: `Program.cs`\n```csharp\nusing System.Reflection;\nusing PortsAndAdaptersPatternDemo.Data;\nusing PortsAndAdaptersPatternDemo.RequestProcessing.Features.GetOrder;\nusing PortsAndAdaptersPatternDemo.RequestProcessing.Features.GetProduct;\n\nvar builder = WebApplication.CreateBuilder(args);\n\n// Add services to the container.\nbuilder.Services.AddControllers();\nbuilder.Services.AddTransient\u003cGetOrderRequestProcessor\u003e();\nbuilder.Services.AddTransient\u003cGetProductRequestProcessor\u003e();\nbuilder.Services.AddDbContext\u003cDemoDbContext\u003e();\n\nDemoDbContext.SeedData();\n\nvar app = builder.Build();\n\n// Configure the HTTP request pipeline.\nif (!app.Environment.IsDevelopment())\n{\n    app.UseExceptionHandler(\"/Error\");\n    app.UseHsts();\n}\n\napp.UseHttpsRedirection();\napp.UseStaticFiles();\napp.UseRouting();\napp.UseAuthorization();\napp.MapControllers();\napp.Run();\n```\n\n**Key File**: `OrderController.cs`\n\n```csharp\n[ApiController]\n[Route(\"api/[controller]\")]\npublic class OrderController : ControllerBase\n{\n    private readonly GetOrderRequestProcessor _getOrderRequestProcessor;\n\n    public OrderController(GetOrderRequestProcessor getOrderRequestProcessor)\n    {\n        _getOrderRequestProcessor = getOrderRequestProcessor;\n    }\n\n    [HttpGet(\"{orderId}\")]\n    public async Task\u003cIActionResult\u003e GetOrder(int orderId)\n    {\n        var result = await _getOrderRequestProcessor.HandleAsync(new GetOrderRequest { OrderId = orderId });\n        return Ok(result);\n    }\n}\n```\n\n### 2. Data Layer\n**Project Name**: `PortsAndAdaptersPatternDemo.Data`\n\n- **Purpose**: This project manages the database context, domain entity models and data access logic.\n- **Dependencies**: \n  - `Microsoft.EntityFrameworkCore` for database operations.\n\n**Key File**: `DemoDbContext.cs`\n```csharp\nusing Microsoft.EntityFrameworkCore;\n\nnamespace PortsAndAdaptersPatternDemo.Data\n{\n    public class DemoDbContext : DbContext\n    {\n        protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)\n        {\n            optionsBuilder.UseInMemoryDatabase(databaseName: \"DemoDb\");\n        }\n\n        protected override void OnModelCreating(ModelBuilder modelBuilder)\n        {\n            modelBuilder.Entity\u003cOrder\u003e()\n                .HasMany(e =\u003e e.Products)\n                .WithMany(e =\u003e e.Orders);\n        }\n\n        public static void SeedData() // only required for dev and testing\n        {\n            using var context = new DemoDbContext();\n            context.Database.EnsureCreated();\n\n            var products = Enumerable.Range(1, 10).Select(i =\u003e new Product()\n            {\n                Name = $\"Product {i}\",\n                ProductId = i\n            });\n\n            context.Products.AddRangeAsync(products);\n            context.SaveChanges();\n\n            var rnd = new Random();\n\n            var orders = Enumerable.Range(1, 10).Select(i =\u003e new Order()\n            {\n                OrderId = i,\n                Customer = $\"Customer {i}\",\n                Products = context.Products.OrderBy(_ =\u003e rnd.Next()).Take(5).ToList()\n            });\n\n            context.Orders.AddRangeAsync(orders);\n            context.SaveChanges();\n        }\n\n        public DbSet\u003cProduct\u003e Products { get; set; }\n        public DbSet\u003cOrder\u003e Orders { get; set; }\n    }\n}\n```\n\nFile `Order.cs`\n\n```csharp\npublic class Order\n{\n    [Key]\n    public int OrderId { get; set; }\n    public string Customer { get; set; }\n    public List\u003cProduct\u003e Products { get; set; }\n}\n```\n\n### 3. Request Processing Layer\n**Project Name**: `PortsAndAdaptersPatternDemo.RequestProcessing`\n\n- **Purpose**: This project implements the use cases and application services. It contains all business logic of the application, acting as the orchestrator between the API and Data layers.\n- **Dependencies**: \n  - `PortsAndAdaptersPatternDemo.Data` for accessing the database context.\n  - `PortsAndAdaptersPatternDemo.Dtos` for dto models.\n\n**Key File**: `GetOrderRequestProcessor.cs`\n```csharp\nusing Microsoft.EntityFrameworkCore;\nusing PortsAndAdaptersPatternDemo.Data;\nusing PortsAndAdaptersPatternDemo.Dtos;\n\nnamespace PortsAndAdaptersPatternDemo.RequestProcessing.Features.GetOrder\n{\n    public class GetOrderRequestProcessor\n    {\n        private readonly DemoDbContext _demoDbContext;\n\n        public GetOrderRequestProcessor(DemoDbContext demoDbContext)\n        {\n            _demoDbContext = demoDbContext;\n        }\n\n        public async Task\u003cGetOrderResponse\u003e HandleAsync(GetOrderRequest request, CancellationToken cancellationToken)\n        {\n            var result = await _demoDbContext.Orders.Include(o =\u003e o.Products).Where(o =\u003e o.OrderId == request.OrderId).Select(o =\u003e\n                new OrderDto()\n                {\n                    Customer = o.Customer,\n                    OrderId = o.OrderId,\n                    Products = o.Products.Select(p =\u003e new ProductDto()\n                    {\n                        ProductId = p.ProductId,\n                        Name = p.Name\n                    }).ToList()\n                }).FirstOrDefaultAsync(cancellationToken);\n\n            return new GetOrderResponse()\n            {\n                Result = result\n            };\n        }\n    }\n}\n```\n\n### 4. Model Layer\n**Project Name**: `PortsAndAdaptersPatternDemo.Dtos`\n\n- **Purpose**: This project contains only DTO (Data Transfer Object) type objects with minimal logic. It primarily consists of data structures used for communication between layers. These are not domain models that contain business logic.\n- **Dependencies**: None.\n\n**Key File**: `OrderDto.cs`\n```csharp\npublic class OrderDto\n{\n    public int OrderId { get; set; }\n    public string Customer { get; set; }\n    public List\u003cProduct\u003e Products { get; set; }\n}\n```\n\n## Summary of Dependencies\n- `PortsAndAdaptersPatternDemo.Api` depends on `PortsAndAdaptersPatternDemo.Data` and `PortsAndAdaptersPatternDemo.RequestProcessing`.\n- `PortsAndAdaptersPatternDemo.RequestProcessing` depends on `PortsAndAdaptersPatternDemo.Data` and `PortsAndAdaptersPatternDemo.Dtos`.\n\nThis layout ensures that each project has a clear responsibility and the dependencies are well-defined, promoting a clean and maintainable architecture.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdasiths%2Fportsandadapterspatterndemo","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fdasiths%2Fportsandadapterspatterndemo","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdasiths%2Fportsandadapterspatterndemo/lists"}