diff --git a/TechTest/AnyCompany.Abstractions/AnyCompany.Abstractions.csproj b/TechTest/AnyCompany.Abstractions/AnyCompany.Abstractions.csproj new file mode 100644 index 0000000..6caf342 --- /dev/null +++ b/TechTest/AnyCompany.Abstractions/AnyCompany.Abstractions.csproj @@ -0,0 +1,55 @@ + + + + + Debug + AnyCPU + {CA267EE7-6F9B-4DE8-B8B4-9FA61B4CDAB8} + Library + Properties + AnyCompany.Abstractions + AnyCompany.Abstractions + v4.6.1 + 512 + true + + + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + + + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + + + + + + + + + + + + + + + + + {06886605-5e83-4702-a634-4fb0eec9e6de} + AnyCompany.Domain + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Abstractions/IOrderRepository.cs b/TechTest/AnyCompany.Abstractions/IOrderRepository.cs new file mode 100644 index 0000000..cad688a --- /dev/null +++ b/TechTest/AnyCompany.Abstractions/IOrderRepository.cs @@ -0,0 +1,14 @@ +using System.Collections.Generic; +using AnyCompany.Domain; + +namespace AnyCompany.Abstractions +{ + public interface IOrderRepository + { + void Save(Order order); + void Save(Customer customer); + IEnumerable GetAllOrders(); + Customer GetCustomer(int customerId); + IEnumerable GetAllCustomers(); + } +} \ No newline at end of file diff --git a/TechTest/AnyCompany.Abstractions/IOrderService.cs b/TechTest/AnyCompany.Abstractions/IOrderService.cs new file mode 100644 index 0000000..9dd44db --- /dev/null +++ b/TechTest/AnyCompany.Abstractions/IOrderService.cs @@ -0,0 +1,11 @@ +using System.Collections.Generic; +using AnyCompany.Domain; + +namespace AnyCompany.Abstractions +{ + public interface IOrderService + { + Order PlaceOrder(Order order, int customerId); + IEnumerable GetAlOrders(); + } +} \ No newline at end of file diff --git a/TechTest/AnyCompany.Abstractions/Properties/AssemblyInfo.cs b/TechTest/AnyCompany.Abstractions/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..5fce538 --- /dev/null +++ b/TechTest/AnyCompany.Abstractions/Properties/AssemblyInfo.cs @@ -0,0 +1,36 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +// General Information about an assembly is controlled through the following +// set of attributes. Change these attribute values to modify the information +// associated with an assembly. +[assembly: AssemblyTitle("AnyCompany.Abstractions")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("AnyCompany.Abstractions")] +[assembly: AssemblyCopyright("Copyright © 2019")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// Setting ComVisible to false makes the types in this assembly not visible +// to COM components. If you need to access a type in this assembly from +// COM, set the ComVisible attribute to true on that type. +[assembly: ComVisible(false)] + +// The following GUID is for the ID of the typelib if this project is exposed to COM +[assembly: Guid("ca267ee7-6f9b-4de8-b8b4-9fa61b4cdab8")] + +// Version information for an assembly consists of the following four values: +// +// Major Version +// Minor Version +// Build Number +// Revision +// +// You can specify all the values or you can default the Build and Revision Numbers +// by using the '*' as shown below: +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/TechTest/AnyCompany.Client/AnyCompany.Client.csproj b/TechTest/AnyCompany.Client/AnyCompany.Client.csproj new file mode 100644 index 0000000..bd6614d --- /dev/null +++ b/TechTest/AnyCompany.Client/AnyCompany.Client.csproj @@ -0,0 +1,95 @@ + + + + + Debug + AnyCPU + {5ADF09FE-E7DA-402D-8DA9-FDB76DE0EF10} + Exe + AnyCompany.Client + AnyCompany.Client + v4.6.1 + 512 + true + true + + + AnyCPU + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + + + AnyCPU + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + + ..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.dll + + + ..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.SqlServer.dll + + + ..\packages\EntityFramework.SqlServerCompact.6.2.0\lib\net45\EntityFramework.SqlServerCompact.dll + + + ..\packages\StructureMap.4.7.1\lib\net45\StructureMap.dll + + + + + + ..\packages\Microsoft.SqlServer.Compact.4.0.8876.1\lib\net40\System.Data.SqlServerCe.dll + + + + + + + + + + + + + + + + + + + {CA267EE7-6F9B-4DE8-B8B4-9FA61B4CDAB8} + AnyCompany.Abstractions + + + {06886605-5E83-4702-A634-4FB0EEC9E6DE} + AnyCompany.Domain + + + {9205a0a6-64cd-47b2-9927-f8e502b05c33} + AnyCompany.Repository + + + {A4D6B6B4-EC02-4ECD-8E84-472A44A48CF7} + AnyCompany.Services + + + + + + if not exist "$(TargetDir)x86" md "$(TargetDir)x86" + xcopy /s /y "$(SolutionDir)packages\Microsoft.SqlServer.Compact.4.0.8876.1\NativeBinaries\x86\*.*" "$(TargetDir)x86" + if not exist "$(TargetDir)amd64" md "$(TargetDir)amd64" + xcopy /s /y "$(SolutionDir)packages\Microsoft.SqlServer.Compact.4.0.8876.1\NativeBinaries\amd64\*.*" "$(TargetDir)amd64" + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Client/App.config b/TechTest/AnyCompany.Client/App.config new file mode 100644 index 0000000..7891dfa --- /dev/null +++ b/TechTest/AnyCompany.Client/App.config @@ -0,0 +1,27 @@ + + + + +
+ + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Client/Program.cs b/TechTest/AnyCompany.Client/Program.cs new file mode 100644 index 0000000..c4102fe --- /dev/null +++ b/TechTest/AnyCompany.Client/Program.cs @@ -0,0 +1,78 @@ +using System; +using System.Linq; +using AnyCompany.Abstractions; +using AnyCompany.Domain; +using AnyCompany.Services; +using AnyCompany.Services.Repositories; +using StructureMap; + +namespace AnyCompany.Client +{ + class Program + { + static void Main(string[] args) + { + var container = Container.For(); + + //below Save customer is not required, for testing purpose + var customer = new Customer + { + Country = "UK", + DateOfBirth = DateTime.Now.AddYears(-20), + Name = "tester2" + }; + var orderRepository = container.GetInstance(); + orderRepository.Save(customer); + + var order = new Order + { + Amount = 120.0 + }; + Console.WriteLine("Placing an order for customer id 1. "); + var orderService = container.GetInstance(); + orderService.PlaceOrder(order, 1); + + Console.WriteLine("Getting all customers and their linked orders. "); + var orders = orderService.GetAlOrders().ToList(); + var customers = orderService.GetAlCustomers().ToList(); + + foreach (var item in customers) + { + if (item.Orders == null || !item.Orders.Any()) + { + continue; + } + Console.WriteLine($"customer id: {item.CustomerId}, name: {item.Name}, total orders: {item.Orders.Count} "); + + foreach (var linkedOrder in item.Orders) + { + Console.WriteLine($"order id: {linkedOrder.OrderId}, amount: {linkedOrder.Amount}, VAT: {linkedOrder.VAT} "); + } + } + + Console.WriteLine("Listing all orders and the linked customer. "); + foreach (var item in orders) + { + if (item.Customer == null) + { + continue; + } + Console.WriteLine($"order id: {item.OrderId}, amount: {item.Amount}, VAT: {item.VAT}, customer id: {item.Customer.CustomerId}, customer name: {item.Customer.Name} "); + } + Console.ReadLine(); + } + } + + public class ClientRegistry : Registry + { + public ClientRegistry() + { + Scan(scan => + { + scan.TheCallingAssembly(); + scan.WithDefaultConventions(); + }); + For().Use(); + } + } +} diff --git a/TechTest/AnyCompany.Client/Properties/AssemblyInfo.cs b/TechTest/AnyCompany.Client/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..ba9d9cc --- /dev/null +++ b/TechTest/AnyCompany.Client/Properties/AssemblyInfo.cs @@ -0,0 +1,36 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +// General Information about an assembly is controlled through the following +// set of attributes. Change these attribute values to modify the information +// associated with an assembly. +[assembly: AssemblyTitle("AnyCompany.Client")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("AnyCompany.Client")] +[assembly: AssemblyCopyright("Copyright © 2019")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// Setting ComVisible to false makes the types in this assembly not visible +// to COM components. If you need to access a type in this assembly from +// COM, set the ComVisible attribute to true on that type. +[assembly: ComVisible(false)] + +// The following GUID is for the ID of the typelib if this project is exposed to COM +[assembly: Guid("5adf09fe-e7da-402d-8da9-fdb76de0ef10")] + +// Version information for an assembly consists of the following four values: +// +// Major Version +// Minor Version +// Build Number +// Revision +// +// You can specify all the values or you can default the Build and Revision Numbers +// by using the '*' as shown below: +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/TechTest/AnyCompany.Client/packages.config b/TechTest/AnyCompany.Client/packages.config new file mode 100644 index 0000000..855e502 --- /dev/null +++ b/TechTest/AnyCompany.Client/packages.config @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Domain/AnyCompany.Domain.csproj b/TechTest/AnyCompany.Domain/AnyCompany.Domain.csproj new file mode 100644 index 0000000..be125af --- /dev/null +++ b/TechTest/AnyCompany.Domain/AnyCompany.Domain.csproj @@ -0,0 +1,50 @@ + + + + + Debug + AnyCPU + {06886605-5E83-4702-A634-4FB0EEC9E6DE} + Library + Properties + AnyCompany.Domain + AnyCompany.Domain + v4.6.1 + 512 + true + + + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + + + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Domain/Customer.cs b/TechTest/AnyCompany.Domain/Customer.cs new file mode 100644 index 0000000..0cb5d67 --- /dev/null +++ b/TechTest/AnyCompany.Domain/Customer.cs @@ -0,0 +1,14 @@ +using System; +using System.Collections.Generic; + +namespace AnyCompany.Domain +{ + public class Customer + { + public int CustomerId { get; set; } + public string Country { get; set; } + public DateTime DateOfBirth { get; set; } + public string Name { get; set; } + public virtual ICollection Orders { get; set; } + } +} diff --git a/TechTest/AnyCompany.Domain/Order.cs b/TechTest/AnyCompany.Domain/Order.cs new file mode 100644 index 0000000..5d8b979 --- /dev/null +++ b/TechTest/AnyCompany.Domain/Order.cs @@ -0,0 +1,15 @@ +using System.ComponentModel.DataAnnotations.Schema; + +namespace AnyCompany.Domain +{ + public class Order + { + public int OrderId { get; set; } + public double Amount { get; set; } + public double VAT { get; set; } + [ForeignKey("CustomersId")] + [InverseProperty("Orders")] + public Customer Customer { get; set; } + public virtual int CustomersId { get; set; } + } +} diff --git a/TechTest/AnyCompany.Domain/Properties/AssemblyInfo.cs b/TechTest/AnyCompany.Domain/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..36efcb9 --- /dev/null +++ b/TechTest/AnyCompany.Domain/Properties/AssemblyInfo.cs @@ -0,0 +1,36 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +// General Information about an assembly is controlled through the following +// set of attributes. Change these attribute values to modify the information +// associated with an assembly. +[assembly: AssemblyTitle("AnyCompany.Domain")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("AnyCompany.Domain")] +[assembly: AssemblyCopyright("Copyright © 2019")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// Setting ComVisible to false makes the types in this assembly not visible +// to COM components. If you need to access a type in this assembly from +// COM, set the ComVisible attribute to true on that type. +[assembly: ComVisible(false)] + +// The following GUID is for the ID of the typelib if this project is exposed to COM +[assembly: Guid("06886605-5e83-4702-a634-4fb0eec9e6de")] + +// Version information for an assembly consists of the following four values: +// +// Major Version +// Minor Version +// Build Number +// Revision +// +// You can specify all the values or you can default the Build and Revision Numbers +// by using the '*' as shown below: +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/TechTest/AnyCompany.Repository/AnyCompany.Repository.csproj b/TechTest/AnyCompany.Repository/AnyCompany.Repository.csproj new file mode 100644 index 0000000..afa6209 --- /dev/null +++ b/TechTest/AnyCompany.Repository/AnyCompany.Repository.csproj @@ -0,0 +1,81 @@ + + + + + Debug + AnyCPU + {9205A0A6-64CD-47B2-9927-F8E502B05C33} + Library + Properties + AnyCompany.Repository + AnyCompany.Repository + v4.6.1 + 512 + true + + + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + + + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + + ..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.dll + + + ..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.SqlServer.dll + + + ..\packages\EntityFramework.SqlServerCompact.6.2.0\lib\net45\EntityFramework.SqlServerCompact.dll + + + ..\packages\StructureMap.4.7.1\lib\net45\StructureMap.dll + + + + + + ..\packages\Microsoft.SqlServer.Compact.4.0.8876.1\lib\net40\System.Data.SqlServerCe.dll + + + + + + + + + + + + + + + + + + + {06886605-5E83-4702-A634-4FB0EEC9E6DE} + AnyCompany.Domain + + + + + + if not exist "$(TargetDir)x86" md "$(TargetDir)x86" + xcopy /s /y "$(SolutionDir)packages\Microsoft.SqlServer.Compact.4.0.8876.1\NativeBinaries\x86\*.*" "$(TargetDir)x86" + if not exist "$(TargetDir)amd64" md "$(TargetDir)amd64" + xcopy /s /y "$(SolutionDir)packages\Microsoft.SqlServer.Compact.4.0.8876.1\NativeBinaries\amd64\*.*" "$(TargetDir)amd64" + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Repository/App.config b/TechTest/AnyCompany.Repository/App.config new file mode 100644 index 0000000..e47bd0f --- /dev/null +++ b/TechTest/AnyCompany.Repository/App.config @@ -0,0 +1,28 @@ + + + + +
+ + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Repository/OrdersDbContext.cs b/TechTest/AnyCompany.Repository/OrdersDbContext.cs new file mode 100644 index 0000000..69027b3 --- /dev/null +++ b/TechTest/AnyCompany.Repository/OrdersDbContext.cs @@ -0,0 +1,24 @@ +using System.Data.Entity; +using AnyCompany.Domain; + +namespace AnyCompany.Repository +{ + public class OrdersDbContext : DbContext + { + public OrdersDbContext() : base("name = Orders") + { + } + + public virtual DbSet Orders { get; set; } + public virtual DbSet Customers { get; set; } + + protected override void OnModelCreating(DbModelBuilder modelBuilder) + { + modelBuilder.Entity() + .HasRequired(p => p.Customer) + .WithMany() + .HasForeignKey(p => p.CustomersId) + .WillCascadeOnDelete(false); + } + } +} diff --git a/TechTest/AnyCompany.Repository/Properties/AssemblyInfo.cs b/TechTest/AnyCompany.Repository/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..399ac08 --- /dev/null +++ b/TechTest/AnyCompany.Repository/Properties/AssemblyInfo.cs @@ -0,0 +1,36 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +// General Information about an assembly is controlled through the following +// set of attributes. Change these attribute values to modify the information +// associated with an assembly. +[assembly: AssemblyTitle("AnyCompany.Repository")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("AnyCompany.Repository")] +[assembly: AssemblyCopyright("Copyright © 2019")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// Setting ComVisible to false makes the types in this assembly not visible +// to COM components. If you need to access a type in this assembly from +// COM, set the ComVisible attribute to true on that type. +[assembly: ComVisible(false)] + +// The following GUID is for the ID of the typelib if this project is exposed to COM +[assembly: Guid("9205a0a6-64cd-47b2-9927-f8e502b05c33")] + +// Version information for an assembly consists of the following four values: +// +// Major Version +// Minor Version +// Build Number +// Revision +// +// You can specify all the values or you can default the Build and Revision Numbers +// by using the '*' as shown below: +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/TechTest/AnyCompany.Repository/packages.config b/TechTest/AnyCompany.Repository/packages.config new file mode 100644 index 0000000..855e502 --- /dev/null +++ b/TechTest/AnyCompany.Repository/packages.config @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Services/AnyCompany.Services.csproj b/TechTest/AnyCompany.Services/AnyCompany.Services.csproj new file mode 100644 index 0000000..f3fd57e --- /dev/null +++ b/TechTest/AnyCompany.Services/AnyCompany.Services.csproj @@ -0,0 +1,78 @@ + + + + + Debug + AnyCPU + {A4D6B6B4-EC02-4ECD-8E84-472A44A48CF7} + Library + Properties + AnyCompany.Services + AnyCompany.Services + v4.6.1 + 512 + true + + + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + + + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + + ..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.dll + + + ..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.SqlServer.dll + + + ..\packages\StructureMap.4.7.1\lib\net45\StructureMap.dll + + + + + + + + + + + + + + + + + + + + + + + + {CA267EE7-6F9B-4DE8-B8B4-9FA61B4CDAB8} + AnyCompany.Abstractions + + + {06886605-5E83-4702-A634-4FB0EEC9E6DE} + AnyCompany.Domain + + + {9205A0A6-64CD-47B2-9927-F8E502B05C33} + AnyCompany.Repository + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Services/App.config b/TechTest/AnyCompany.Services/App.config new file mode 100644 index 0000000..2fb423e --- /dev/null +++ b/TechTest/AnyCompany.Services/App.config @@ -0,0 +1,13 @@ + + + + +
+ + + + + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.Services/OrderService.cs b/TechTest/AnyCompany.Services/OrderService.cs new file mode 100644 index 0000000..3bd6f92 --- /dev/null +++ b/TechTest/AnyCompany.Services/OrderService.cs @@ -0,0 +1,48 @@ +using System.Collections.Generic; +using AnyCompany.Abstractions; +using AnyCompany.Domain; +using AnyCompany.Services.Repositories; + +namespace AnyCompany.Services +{ + public class OrderService : IOrderService + { + private readonly IOrderRepository _orderRepository; + private int _customerId; + + public OrderService(IOrderRepository orderRepository) + { + _orderRepository = orderRepository; + } + + public Order PlaceOrder(Order order, int customerId) + { + _customerId = customerId; + + if (Customer == null || order.Amount == 0d) + { + return null; + } + + order.Customer = _orderRepository.GetCustomer(_customerId); + + order.VAT = Customer.Country.ToLower() == "uk" ? 0.2d : 0; + + _orderRepository.Save(order); + + return order; + } + + public Customer Customer => CustomerRepository.Load(_customerId); + + public IEnumerable GetAlOrders() + { + return _orderRepository.GetAllOrders(); + } + + public IEnumerable GetAlCustomers() + { + return _orderRepository.GetAllCustomers(); + } + } +} diff --git a/TechTest/AnyCompany.Services/Properties/AssemblyInfo.cs b/TechTest/AnyCompany.Services/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..b86cd48 --- /dev/null +++ b/TechTest/AnyCompany.Services/Properties/AssemblyInfo.cs @@ -0,0 +1,36 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +// General Information about an assembly is controlled through the following +// set of attributes. Change these attribute values to modify the information +// associated with an assembly. +[assembly: AssemblyTitle("AnyCompany.Services")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("AnyCompany.Services")] +[assembly: AssemblyCopyright("Copyright © 2019")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +// Setting ComVisible to false makes the types in this assembly not visible +// to COM components. If you need to access a type in this assembly from +// COM, set the ComVisible attribute to true on that type. +[assembly: ComVisible(false)] + +// The following GUID is for the ID of the typelib if this project is exposed to COM +[assembly: Guid("a4d6b6b4-ec02-4ecd-8e84-472a44a48cf7")] + +// Version information for an assembly consists of the following four values: +// +// Major Version +// Minor Version +// Build Number +// Revision +// +// You can specify all the values or you can default the Build and Revision Numbers +// by using the '*' as shown below: +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/TechTest/AnyCompany.Services/Repositories/CustomerRepository.cs b/TechTest/AnyCompany.Services/Repositories/CustomerRepository.cs new file mode 100644 index 0000000..f1d4176 --- /dev/null +++ b/TechTest/AnyCompany.Services/Repositories/CustomerRepository.cs @@ -0,0 +1,16 @@ +using System.Linq; +using AnyCompany.Domain; +using AnyCompany.Repository; + +namespace AnyCompany.Services.Repositories +{ + public static class CustomerRepository + { + private static OrdersDbContext OrdersDbContext => new OrdersDbContext(); + + public static Customer Load(int customerId) + { + return OrdersDbContext.Customers?.FirstOrDefault(x => x.CustomerId == customerId); + } + } +} diff --git a/TechTest/AnyCompany.Services/Repositories/OrderRepository.cs b/TechTest/AnyCompany.Services/Repositories/OrderRepository.cs new file mode 100644 index 0000000..ae54355 --- /dev/null +++ b/TechTest/AnyCompany.Services/Repositories/OrderRepository.cs @@ -0,0 +1,45 @@ +using System.Collections.Generic; +using System.Linq; +using AnyCompany.Abstractions; +using AnyCompany.Domain; +using AnyCompany.Repository; + +namespace AnyCompany.Services.Repositories +{ + public class OrderRepository : IOrderRepository + { + private readonly OrdersDbContext _ordersDbContext; + + public OrderRepository(OrdersDbContext ordersDbContext) + { + _ordersDbContext = ordersDbContext; + } + + public void Save(Order order) + { + _ordersDbContext.Orders.Add(order); + _ordersDbContext.SaveChanges(); + } + + public IEnumerable GetAllOrders() + { + return _ordersDbContext.Orders.OrderBy(x => x.CustomersId).ToList(); + } + + public IEnumerable GetAllCustomers() + { + return _ordersDbContext.Customers.ToList(); + } + + public void Save(Customer customer) + { + _ordersDbContext.Customers.Add(customer); + _ordersDbContext.SaveChanges(); + } + + public Customer GetCustomer(int customerId) + { + return _ordersDbContext.Customers?.FirstOrDefault(x => x.CustomerId == customerId); + } + } +} diff --git a/TechTest/AnyCompany.Services/packages.config b/TechTest/AnyCompany.Services/packages.config new file mode 100644 index 0000000..7db2e35 --- /dev/null +++ b/TechTest/AnyCompany.Services/packages.config @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.UnitTests/AnyCompany.UnitTests.csproj b/TechTest/AnyCompany.UnitTests/AnyCompany.UnitTests.csproj new file mode 100644 index 0000000..5cae420 --- /dev/null +++ b/TechTest/AnyCompany.UnitTests/AnyCompany.UnitTests.csproj @@ -0,0 +1,127 @@ + + + + + + Debug + AnyCPU + {D32443F4-AA48-4F1D-BCE4-C629A72CF92C} + Library + Properties + AnyCompany.UnitTests + AnyCompany.UnitTests + v4.6.1 + 512 + {3AC096D0-A1C2-E12C-1390-A8335801FDAB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} + 15.0 + $(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion) + $(ProgramFiles)\Common Files\microsoft shared\VSTT\$(VisualStudioVersion)\UITestExtensionPackages + False + UnitTest + + + + + true + full + false + bin\Debug\ + DEBUG;TRACE + prompt + 4 + + + pdbonly + true + bin\Release\ + TRACE + prompt + 4 + + + + ..\packages\Castle.Core.4.4.0\lib\net45\Castle.Core.dll + + + ..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.dll + + + ..\packages\EntityFramework.6.2.0\lib\net45\EntityFramework.SqlServer.dll + + + ..\packages\FluentAssertions.5.8.0\lib\net45\FluentAssertions.dll + + + ..\packages\MSTest.TestFramework.1.3.2\lib\net45\Microsoft.VisualStudio.TestPlatform.TestFramework.dll + + + ..\packages\MSTest.TestFramework.1.3.2\lib\net45\Microsoft.VisualStudio.TestPlatform.TestFramework.Extensions.dll + + + ..\packages\Moq.4.12.0\lib\net45\Moq.dll + + + + + + + ..\packages\Microsoft.SqlServer.Compact.4.0.8876.1\lib\net40\System.Data.SqlServerCe.dll + + + ..\packages\System.Runtime.CompilerServices.Unsafe.4.5.0\lib\netstandard2.0\System.Runtime.CompilerServices.Unsafe.dll + + + ..\packages\System.Threading.Tasks.Extensions.4.5.1\lib\netstandard2.0\System.Threading.Tasks.Extensions.dll + + + ..\packages\System.ValueTuple.4.4.0\lib\net461\System.ValueTuple.dll + + + + + + + + + + + + + + + + + {ca267ee7-6f9b-4de8-b8b4-9fa61b4cdab8} + AnyCompany.Abstractions + + + {06886605-5e83-4702-a634-4fb0eec9e6de} + AnyCompany.Domain + + + {9205a0a6-64cd-47b2-9927-f8e502b05c33} + AnyCompany.Repository + + + {A4D6B6B4-EC02-4ECD-8E84-472A44A48CF7} + AnyCompany.Services + + + + + + + This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}. + + + + + + + + if not exist "$(TargetDir)x86" md "$(TargetDir)x86" + xcopy /s /y "$(SolutionDir)packages\Microsoft.SqlServer.Compact.4.0.8876.1\NativeBinaries\x86\*.*" "$(TargetDir)x86" + if not exist "$(TargetDir)amd64" md "$(TargetDir)amd64" + xcopy /s /y "$(SolutionDir)packages\Microsoft.SqlServer.Compact.4.0.8876.1\NativeBinaries\amd64\*.*" "$(TargetDir)amd64" + + \ No newline at end of file diff --git a/TechTest/AnyCompany.UnitTests/App.config b/TechTest/AnyCompany.UnitTests/App.config new file mode 100644 index 0000000..936b7e1 --- /dev/null +++ b/TechTest/AnyCompany.UnitTests/App.config @@ -0,0 +1,21 @@ + + + + +
+ + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/TechTest/AnyCompany.UnitTests/CustomerRepositoryShould.cs b/TechTest/AnyCompany.UnitTests/CustomerRepositoryShould.cs new file mode 100644 index 0000000..4d7cb3c --- /dev/null +++ b/TechTest/AnyCompany.UnitTests/CustomerRepositoryShould.cs @@ -0,0 +1,21 @@ +using AnyCompany.Services.Repositories; +using FluentAssertions; +using Microsoft.VisualStudio.TestTools.UnitTesting; + +namespace AnyCompany.UnitTests +{ + /// + /// can't really test static class/method + /// + [TestClass] + public class CustomerRepositoryShould + { + [TestMethod] + public void ShouldLoadCustomerOk() + { + var customer = CustomerRepository.Load(1); + + customer.CustomerId.Should().Be(1); + } + } +} diff --git a/TechTest/AnyCompany.UnitTests/OrderRepositoryShould.cs b/TechTest/AnyCompany.UnitTests/OrderRepositoryShould.cs new file mode 100644 index 0000000..e0bb67f --- /dev/null +++ b/TechTest/AnyCompany.UnitTests/OrderRepositoryShould.cs @@ -0,0 +1,159 @@ +using System; +using System.Collections.Generic; +using System.Data.Entity; +using System.Linq; +using AnyCompany.Domain; +using AnyCompany.Repository; +using AnyCompany.Services.Repositories; +using FluentAssertions; +using Microsoft.VisualStudio.TestTools.UnitTesting; +using Moq; + +namespace AnyCompany.UnitTests +{ + [TestClass] + public class OrderRepositoryShould + { + private Order _order1; + private Order _order2; + private Customer _customer; + private IQueryable _orders; + private IQueryable _customers; + private Mock> _mockOrderDbSet; + private Mock _mockOrderDbContext; + private Mock> _mockCustomerDbSet; + + public OrderRepositoryShould() + { + AssumeOrderIsInitialised(); + AssumeDbContextIsInitialised(); + } + + [TestMethod] + public void ShouldSaveOrderOk() + { + AssumDbContextIsSetup(); + + var repository = new OrderRepository(_mockOrderDbContext.Object); + repository.Save(_order1); + + _mockOrderDbSet.Verify(m => m.Add(It.IsAny()), Times.Once()); + _mockOrderDbContext.Verify(m => m.SaveChanges(), Times.Once()); + } + + [TestMethod] + public void ShouldSaveCustomerOk() + { + AssumDbContextIsSetup(); + + var repository = new OrderRepository(_mockOrderDbContext.Object); + repository.Save(_customer); + + _mockCustomerDbSet.Verify(m => m.Add(It.IsAny()), Times.Once()); + _mockOrderDbContext.Verify(m => m.SaveChanges(), Times.Once()); + } + + [TestMethod] + public void ShouldGetAllOrders() + { + AssumeIQueryableDbSetIsSetup(); + + var reposity = new OrderRepository(_mockOrderDbContext.Object); + var orders = reposity.GetAllOrders().ToList(); + + orders.Count.Should().Be(2); + orders[0].Should().Be(_order1); + orders[1].Should().Be(_order2); + } + + [TestMethod] + public void ShouldGetCustomerOk() + { + AssumeIQueryableDbSetIsSetup(); + + var repository = new OrderRepository(_mockOrderDbContext.Object); + var customer = repository.GetCustomer(1); + + customer.Should().NotBeNull(); + customer.Should().Be(_customer); + } + + [TestMethod] + public void ShouldGetAllCustomersWithLinkedOrders() + { + AssumeIQueryableDbSetIsSetup(); + + var reposity = new OrderRepository(_mockOrderDbContext.Object); + var customers = reposity.GetAllCustomers().ToList(); + + customers.Count.Should().Be(1); + customers[0].Should().Be(_customer); + customers[0].Orders.Count.Should().Be(2); + customers[0].Orders.First().Should().Be(_order1); + customers[0].Orders.Last().Should().Be(_order2); + } + + private void AssumeIQueryableDbSetIsSetup() + { + _mockOrderDbSet.As>().Setup(m => m.Provider).Returns(_orders.Provider); + _mockOrderDbSet.As>().Setup(m => m.Expression).Returns(_orders.Expression); + _mockOrderDbSet.As>().Setup(m => m.ElementType).Returns(_orders.ElementType); + _mockOrderDbSet.As>().Setup(m => m.GetEnumerator()).Returns(_orders.GetEnumerator()); + _mockOrderDbContext.Setup(c => c.Orders).Returns(_mockOrderDbSet.Object); + + _mockCustomerDbSet.As>().Setup(m => m.Provider).Returns(_customers.Provider); + _mockCustomerDbSet.As>().Setup(m => m.Expression).Returns(_customers.Expression); + _mockCustomerDbSet.As>().Setup(m => m.ElementType).Returns(_customers.ElementType); + _mockCustomerDbSet.As>().Setup(m => m.GetEnumerator()).Returns(_customers.GetEnumerator()); + _mockOrderDbContext.Setup(c => c.Customers).Returns(_mockCustomerDbSet.Object); + } + + private void AssumeOrderIsInitialised() + { + _customer = new Customer + { + CustomerId = 1, + Country = "UK", + DateOfBirth = DateTime.Now.AddYears(-20), + Name = "tester1" + }; + + _order1 = new Order + { + OrderId = 1, + Amount = 12, + VAT = 2, + Customer = _customer + }; + + _order2 = new Order + { + OrderId = 2, + Amount = 122, + VAT = 4, + Customer = _customer + }; + + _orders = new List + { + _order1, + _order2 + }.AsQueryable(); + _customer.Orders = new List { _order1, _order2 }; + _customers = new List { _customer }.AsQueryable(); + } + + private void AssumeDbContextIsInitialised() + { + _mockOrderDbSet = new Mock>(); + _mockCustomerDbSet = new Mock>(); + _mockOrderDbContext = new Mock(); + } + + private void AssumDbContextIsSetup() + { + _mockOrderDbContext.Setup(m => m.Orders).Returns(_mockOrderDbSet.Object); + _mockOrderDbContext.Setup(m => m.Customers).Returns(_mockCustomerDbSet.Object); + } + } +} \ No newline at end of file diff --git a/TechTest/AnyCompany.UnitTests/OrderServiceShould.cs b/TechTest/AnyCompany.UnitTests/OrderServiceShould.cs new file mode 100644 index 0000000..2a3d43d --- /dev/null +++ b/TechTest/AnyCompany.UnitTests/OrderServiceShould.cs @@ -0,0 +1,147 @@ +using System; +using System.Collections.Generic; +using System.Data.Entity; +using System.Linq; +using AnyCompany.Abstractions; +using AnyCompany.Domain; +using AnyCompany.Repository; +using AnyCompany.Services; +using FluentAssertions; +using Microsoft.VisualStudio.TestTools.UnitTesting; +using Moq; + +namespace AnyCompany.UnitTests +{ + [TestClass] + public class OrderServiceShould + { + private Order _order1; + private Order _order2; + private Customer _customer; + private Mock _mockOrderRepository; + private List _orders; + private Mock> _mockOrderDbSet; + private Mock _mockOrderDbContext; + + public OrderServiceShould() + { + AssumeOrderIsInitialised(); + AssumeDbContextIsInitialised(); + AssumDbContextIsSetup(); + AssumeRepositoryIsInitialised(); + AssumRepositoryIsSetup(); + } + + [TestMethod] + public void ShouldPlaceOrderOk() + { + var service = new OrderService(_mockOrderRepository.Object); + var order = service.PlaceOrder(_order1, 1); + + _mockOrderRepository.Verify(m => m.Save(It.IsAny()), Times.Once()); + order.Customer.CustomerId.Should().Be(1); + } + + [TestMethod] + public void ShouldPlaceOrderSetCorrectVAT() + { + var service = new OrderService(_mockOrderRepository.Object); + var order = service.PlaceOrder(_order1, 1); + + _mockOrderRepository.Verify(m => m.Save(It.IsAny()), Times.Once()); + order.Customer.CustomerId.Should().Be(1); + order.VAT.Should().Be(0.2d); + } + + [TestMethod] + public void ShouldGetAllOrders() + { + var service = new OrderService(_mockOrderRepository.Object); + var orders = service.GetAlOrders().ToList(); + + orders.Count.Should().Be(2); + orders[0].Should().Be(_order1); + orders[1].Should().Be(_order2); + } + + [TestMethod] + public void ShouldReturnNullWhenOrderAmountLessThanZero() + { + _order1.Amount = 0d; + var service = new OrderService(_mockOrderRepository.Object); + var order = service.PlaceOrder(_order1, 1); + order.Should().BeNull(); + } + + [TestMethod] + public void ShouldGetAllCustomersWithLinkedOrders() + { + var service = new OrderService(_mockOrderRepository.Object); + var customers = service.GetAlCustomers().ToList(); + + customers.Count.Should().Be(1); + customers[0].Should().Be(_customer); + customers[0].Orders.Count.Should().Be(2); + customers[0].Orders.First().Should().Be(_order1); + customers[0].Orders.Last().Should().Be(_order2); + } + + private void AssumeOrderIsInitialised() + { + _customer = new Customer + { + CustomerId = 1, + Country = "UK", + DateOfBirth = DateTime.Now.AddYears(-20), + Name = "tester2" + }; + + _order1 = new Order + { + OrderId = 1, + Amount = 12, + VAT = 2, + Customer = _customer + }; + + _order2 = new Order + { + OrderId = 2, + Amount = 122, + VAT = 4, + Customer = _customer + }; + + _orders = new List + { + _order1, + _order2 + }; + _customer.Orders = _orders; + } + + private void AssumeRepositoryIsInitialised() + { + _mockOrderRepository = new Mock(); + } + + private void AssumRepositoryIsSetup() + { + _mockOrderRepository.Setup(m => m.Save(It.IsAny())); + _mockOrderRepository.Setup(m => m.GetAllOrders()).Returns(_orders); + _mockOrderRepository.Setup(m => m.GetCustomer(It.IsAny())).Returns(_customer); + _mockOrderRepository.Setup(m => m.GetAllCustomers()).Returns(new List { _customer }); + } + + private void AssumeDbContextIsInitialised() + { + _mockOrderDbSet = new Mock>(); + _mockOrderDbContext = new Mock(); + } + + private void AssumDbContextIsSetup() + { + _mockOrderDbContext.Setup(m => m.Orders).Returns(_mockOrderDbSet.Object); + } + } +} \ No newline at end of file diff --git a/TechTest/AnyCompany.UnitTests/Properties/AssemblyInfo.cs b/TechTest/AnyCompany.UnitTests/Properties/AssemblyInfo.cs new file mode 100644 index 0000000..5c0a95d --- /dev/null +++ b/TechTest/AnyCompany.UnitTests/Properties/AssemblyInfo.cs @@ -0,0 +1,20 @@ +using System.Reflection; +using System.Runtime.CompilerServices; +using System.Runtime.InteropServices; + +[assembly: AssemblyTitle("AnyCompany.UnitTests")] +[assembly: AssemblyDescription("")] +[assembly: AssemblyConfiguration("")] +[assembly: AssemblyCompany("")] +[assembly: AssemblyProduct("AnyCompany.UnitTests")] +[assembly: AssemblyCopyright("Copyright © 2019")] +[assembly: AssemblyTrademark("")] +[assembly: AssemblyCulture("")] + +[assembly: ComVisible(false)] + +[assembly: Guid("d32443f4-aa48-4f1d-bce4-c629a72cf92c")] + +// [assembly: AssemblyVersion("1.0.*")] +[assembly: AssemblyVersion("1.0.0.0")] +[assembly: AssemblyFileVersion("1.0.0.0")] diff --git a/TechTest/AnyCompany.UnitTests/packages.config b/TechTest/AnyCompany.UnitTests/packages.config new file mode 100644 index 0000000..3a23ea7 --- /dev/null +++ b/TechTest/AnyCompany.UnitTests/packages.config @@ -0,0 +1,13 @@ + + + + + + + + + + + + + \ No newline at end of file diff --git a/TechTest/SolutionSummary.txt b/TechTest/SolutionSummary.txt new file mode 100644 index 0000000..3d42aad --- /dev/null +++ b/TechTest/SolutionSummary.txt @@ -0,0 +1,12 @@ +I have done the following refactories to the AnyCompany solution: + +1. Replace the existing SqlClient code with Entity Framework 6, created seperate project for DBContext and services. +2. Created Interface for OrderRepository and OrderService and moved it to a seperate project. +3. Moved domain models to a seperate project. +4. Implemented StructionMap as Ioc framework. +5. Added console app for the client that consume the service. +6. Replaced AnyCompany.Test project with Unit test project, in which use Moq and FluentAssertions. +7. Removed AnyCompany project from solution. + +if I had more time, I could have tried to firgure out a better way to deal with the staic CustomerRepository. + \ No newline at end of file diff --git a/TechTest/TechTest.sln b/TechTest/TechTest.sln index 1c1c57a..4038f86 100644 --- a/TechTest/TechTest.sln +++ b/TechTest/TechTest.sln @@ -3,29 +3,54 @@ Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio 15 VisualStudioVersion = 15.0.27004.2005 MinimumVisualStudioVersion = 10.0.40219.1 -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AnyCompany", "AnyCompany\AnyCompany.csproj", "{C7E15594-7D8F-4C18-9DD7-14F3FBB1572D}" -EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AnyCompany.Tests", "AnyCompany.Tests\AnyCompany.Tests.csproj", "{CD5D577E-BDC9-4DFC-AC6A-B1DA474995F3}" -EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{B6D3C1BB-2A37-4E17-9EE3-DEF28286E782}" ProjectSection(SolutionItems) = preProject Instructions.txt = Instructions.txt + SolutionSummary.txt = SolutionSummary.txt EndProjectSection EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AnyCompany.Abstractions", "AnyCompany.Abstractions\AnyCompany.Abstractions.csproj", "{CA267EE7-6F9B-4DE8-B8B4-9FA61B4CDAB8}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AnyCompany.Domain", "AnyCompany.Domain\AnyCompany.Domain.csproj", "{06886605-5E83-4702-A634-4FB0EEC9E6DE}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AnyCompany.Repository", "AnyCompany.Repository\AnyCompany.Repository.csproj", "{9205A0A6-64CD-47B2-9927-F8E502B05C33}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AnyCompany.Services", "AnyCompany.Services\AnyCompany.Services.csproj", "{A4D6B6B4-EC02-4ECD-8E84-472A44A48CF7}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AnyCompany.Client", "AnyCompany.Client\AnyCompany.Client.csproj", "{5ADF09FE-E7DA-402D-8DA9-FDB76DE0EF10}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "AnyCompany.UnitTests", "AnyCompany.UnitTests\AnyCompany.UnitTests.csproj", "{D32443F4-AA48-4F1D-BCE4-C629A72CF92C}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU Release|Any CPU = Release|Any CPU EndGlobalSection GlobalSection(ProjectConfigurationPlatforms) = postSolution - {C7E15594-7D8F-4C18-9DD7-14F3FBB1572D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {C7E15594-7D8F-4C18-9DD7-14F3FBB1572D}.Debug|Any CPU.Build.0 = Debug|Any CPU - {C7E15594-7D8F-4C18-9DD7-14F3FBB1572D}.Release|Any CPU.ActiveCfg = Release|Any CPU - {C7E15594-7D8F-4C18-9DD7-14F3FBB1572D}.Release|Any CPU.Build.0 = Release|Any CPU - {CD5D577E-BDC9-4DFC-AC6A-B1DA474995F3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {CD5D577E-BDC9-4DFC-AC6A-B1DA474995F3}.Debug|Any CPU.Build.0 = Debug|Any CPU - {CD5D577E-BDC9-4DFC-AC6A-B1DA474995F3}.Release|Any CPU.ActiveCfg = Release|Any CPU - {CD5D577E-BDC9-4DFC-AC6A-B1DA474995F3}.Release|Any CPU.Build.0 = Release|Any CPU + {CA267EE7-6F9B-4DE8-B8B4-9FA61B4CDAB8}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {CA267EE7-6F9B-4DE8-B8B4-9FA61B4CDAB8}.Debug|Any CPU.Build.0 = Debug|Any CPU + {CA267EE7-6F9B-4DE8-B8B4-9FA61B4CDAB8}.Release|Any CPU.ActiveCfg = Release|Any CPU + {CA267EE7-6F9B-4DE8-B8B4-9FA61B4CDAB8}.Release|Any CPU.Build.0 = Release|Any CPU + {06886605-5E83-4702-A634-4FB0EEC9E6DE}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {06886605-5E83-4702-A634-4FB0EEC9E6DE}.Debug|Any CPU.Build.0 = Debug|Any CPU + {06886605-5E83-4702-A634-4FB0EEC9E6DE}.Release|Any CPU.ActiveCfg = Release|Any CPU + {06886605-5E83-4702-A634-4FB0EEC9E6DE}.Release|Any CPU.Build.0 = Release|Any CPU + {9205A0A6-64CD-47B2-9927-F8E502B05C33}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {9205A0A6-64CD-47B2-9927-F8E502B05C33}.Debug|Any CPU.Build.0 = Debug|Any CPU + {9205A0A6-64CD-47B2-9927-F8E502B05C33}.Release|Any CPU.ActiveCfg = Release|Any CPU + {9205A0A6-64CD-47B2-9927-F8E502B05C33}.Release|Any CPU.Build.0 = Release|Any CPU + {A4D6B6B4-EC02-4ECD-8E84-472A44A48CF7}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {A4D6B6B4-EC02-4ECD-8E84-472A44A48CF7}.Debug|Any CPU.Build.0 = Debug|Any CPU + {A4D6B6B4-EC02-4ECD-8E84-472A44A48CF7}.Release|Any CPU.ActiveCfg = Release|Any CPU + {A4D6B6B4-EC02-4ECD-8E84-472A44A48CF7}.Release|Any CPU.Build.0 = Release|Any CPU + {5ADF09FE-E7DA-402D-8DA9-FDB76DE0EF10}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {5ADF09FE-E7DA-402D-8DA9-FDB76DE0EF10}.Debug|Any CPU.Build.0 = Debug|Any CPU + {5ADF09FE-E7DA-402D-8DA9-FDB76DE0EF10}.Release|Any CPU.ActiveCfg = Release|Any CPU + {5ADF09FE-E7DA-402D-8DA9-FDB76DE0EF10}.Release|Any CPU.Build.0 = Release|Any CPU + {D32443F4-AA48-4F1D-BCE4-C629A72CF92C}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {D32443F4-AA48-4F1D-BCE4-C629A72CF92C}.Debug|Any CPU.Build.0 = Debug|Any CPU + {D32443F4-AA48-4F1D-BCE4-C629A72CF92C}.Release|Any CPU.ActiveCfg = Release|Any CPU + {D32443F4-AA48-4F1D-BCE4-C629A72CF92C}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE