diff --git a/RMData/RMData.sqlproj b/RMData/RMData.sqlproj
index 5471387..a8988d0 100644
--- a/RMData/RMData.sqlproj
+++ b/RMData/RMData.sqlproj
@@ -72,6 +72,7 @@
+
diff --git a/RMData/dbo/Stored Procedures/spProductGetAll.sql b/RMData/dbo/Stored Procedures/spProductGetAll.sql
new file mode 100644
index 0000000..d0fe2cc
--- /dev/null
+++ b/RMData/dbo/Stored Procedures/spProductGetAll.sql
@@ -0,0 +1,9 @@
+CREATE PROCEDURE [dbo].[spProductGetAll]
+AS
+BEGIN
+ SET NOCOUNT ON;
+
+ select Id, ProductName, [Description], RetailPrice, QuantityInStock
+ from [dbo].[Product]
+ order by ProductName;
+END
\ No newline at end of file
diff --git a/RMData/dbo/Tables/Product.sql b/RMData/dbo/Tables/Product.sql
index 78867e4..61dada0 100644
--- a/RMData/dbo/Tables/Product.sql
+++ b/RMData/dbo/Tables/Product.sql
@@ -4,7 +4,7 @@
[ProductName] NVARCHAR(100) NOT NULL,
[Description] NVARCHAR(MAX) NOT NULL,
[RetailPrice] MONEY NOT NULL,
+ [QuantityInStock] INT NOT NULL DEFAULT 1,
[CreatedDate] DATETIME2 NOT NULL DEFAULT getutcdate(),
- [LastModified] DATETIME2 NOT NULL DEFAULT getutcdate(),
-
+ [LastModified] DATETIME2 NOT NULL DEFAULT getutcdate()
)
diff --git a/RMDataManager/Controllers/ProductController.cs b/RMDataManager/Controllers/ProductController.cs
new file mode 100644
index 0000000..c26380c
--- /dev/null
+++ b/RMDataManager/Controllers/ProductController.cs
@@ -0,0 +1,22 @@
+using RMDataManagerLibrary.DataAcccess;
+using RMDataManagerLibrary.Models;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Net;
+using System.Net.Http;
+using System.Web.Http;
+
+namespace RMDataManager.Controllers
+{
+ [Authorize]
+ public class ProductController : ApiController
+ {
+ public List Get()
+ {
+ ProductData data = new ProductData();
+
+ return data.GetProducts();
+ }
+ }
+}
diff --git a/RMDataManager/RMDataManager.csproj b/RMDataManager/RMDataManager.csproj
index 0611b47..ca6a8ed 100644
--- a/RMDataManager/RMDataManager.csproj
+++ b/RMDataManager/RMDataManager.csproj
@@ -213,6 +213,7 @@
+
diff --git a/RMDataManagerLibrary/DataAcccess/ProductData.cs b/RMDataManagerLibrary/DataAcccess/ProductData.cs
new file mode 100644
index 0000000..db78ae4
--- /dev/null
+++ b/RMDataManagerLibrary/DataAcccess/ProductData.cs
@@ -0,0 +1,22 @@
+using RMDataManagerLibrary.Internal.DataAccess;
+using RMDataManagerLibrary.Models;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace RMDataManagerLibrary.DataAcccess
+{
+ public class ProductData
+ {
+ public List GetProducts()
+ {
+ SqlDataAccess sql = new SqlDataAccess();
+
+ var output = sql.LoadData("dbo.spProductGetAll", new { }, "RMData");
+
+ return output;
+ }
+ }
+}
diff --git a/RMDataManagerLibrary/Models/ProductModel.cs b/RMDataManagerLibrary/Models/ProductModel.cs
new file mode 100644
index 0000000..eba19f7
--- /dev/null
+++ b/RMDataManagerLibrary/Models/ProductModel.cs
@@ -0,0 +1,16 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Web;
+
+namespace RMDataManagerLibrary.Models
+{
+ public class ProductModel
+ {
+ public int Id { get; set; }
+ public string ProductName { get; set; }
+ public string Description { get; set; }
+ public decimal RetailPrice { get; set; }
+ public int QuantityInStock { get; set; }
+ }
+}
\ No newline at end of file
diff --git a/RMDataManagerLibrary/RMDataManagerLibrary.csproj b/RMDataManagerLibrary/RMDataManagerLibrary.csproj
index 897e7d5..5ee02f4 100644
--- a/RMDataManagerLibrary/RMDataManagerLibrary.csproj
+++ b/RMDataManagerLibrary/RMDataManagerLibrary.csproj
@@ -45,7 +45,9 @@
+
+
diff --git a/RMWPFInterfaceLibrary/Api/APIHelper.cs b/RMWPFInterfaceLibrary/Api/APIHelper.cs
index ef15489..1c64c51 100644
--- a/RMWPFInterfaceLibrary/Api/APIHelper.cs
+++ b/RMWPFInterfaceLibrary/Api/APIHelper.cs
@@ -13,21 +13,30 @@ namespace RMWPFInterfaceLibrary.Api
{
public class APIHelper : IAPIHelper
{
- private HttpClient apiClient;
+ private HttpClient _apiClient;
private ILoggedInUserModel _loggedInUser;
public APIHelper(ILoggedInUserModel loggedInUser)
{
InitializeClient();
_loggedInUser = loggedInUser;
}
+
+ public HttpClient ApiClient
+ {
+ get
+ {
+ return _apiClient;
+ }
+ }
+
private void InitializeClient()
{
string api = ConfigurationManager.AppSettings["api"];
- apiClient = new HttpClient();
- apiClient.BaseAddress = new Uri(api);
- apiClient.DefaultRequestHeaders.Accept.Clear();
- apiClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
+ _apiClient = new HttpClient();
+ _apiClient.BaseAddress = new Uri(api);
+ _apiClient.DefaultRequestHeaders.Accept.Clear();
+ _apiClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
}
public async Task Authenticate(string username, string password)
@@ -39,7 +48,7 @@ namespace RMWPFInterfaceLibrary.Api
new KeyValuePair("password", password),
});
- using (HttpResponseMessage response = await apiClient.PostAsync("/Token", data))
+ using (HttpResponseMessage response = await _apiClient.PostAsync("/Token", data))
{
if (response.IsSuccessStatusCode)
{
@@ -55,12 +64,12 @@ namespace RMWPFInterfaceLibrary.Api
public async Task GetLogedInUserInfo(string token)
{
- apiClient.DefaultRequestHeaders.Clear();
- apiClient.DefaultRequestHeaders.Accept.Clear();
- apiClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
- apiClient.DefaultRequestHeaders.Add("Authorization", $"Bearer {token}");
+ _apiClient.DefaultRequestHeaders.Clear();
+ _apiClient.DefaultRequestHeaders.Accept.Clear();
+ _apiClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
+ _apiClient.DefaultRequestHeaders.Add("Authorization", $"Bearer {token}");
- using (HttpResponseMessage response = await apiClient.GetAsync("api/User"))
+ using (HttpResponseMessage response = await _apiClient.GetAsync("api/User"))
{
if (response.IsSuccessStatusCode)
{
diff --git a/RMWPFInterfaceLibrary/Api/IAPIHelper.cs b/RMWPFInterfaceLibrary/Api/IAPIHelper.cs
index 73ef29a..c4c9819 100644
--- a/RMWPFInterfaceLibrary/Api/IAPIHelper.cs
+++ b/RMWPFInterfaceLibrary/Api/IAPIHelper.cs
@@ -1,10 +1,12 @@
using RMWPFUserInterface.Models;
+using System.Net.Http;
using System.Threading.Tasks;
namespace RMWPFInterfaceLibrary.Api
{
public interface IAPIHelper
{
+ HttpClient ApiClient { get; }
Task Authenticate(string username, string password);
Task GetLogedInUserInfo(string token);
}
diff --git a/RMWPFInterfaceLibrary/Api/IProductEndPoint.cs b/RMWPFInterfaceLibrary/Api/IProductEndPoint.cs
new file mode 100644
index 0000000..dfc691e
--- /dev/null
+++ b/RMWPFInterfaceLibrary/Api/IProductEndPoint.cs
@@ -0,0 +1,11 @@
+using RMWPFInterfaceLibrary.Models;
+using System.Collections.Generic;
+using System.Threading.Tasks;
+
+namespace RMWPFInterfaceLibrary.Api
+{
+ public interface IProductEndPoint
+ {
+ Task> GetAll();
+ }
+}
\ No newline at end of file
diff --git a/RMWPFInterfaceLibrary/Api/ProductEndPoint.cs b/RMWPFInterfaceLibrary/Api/ProductEndPoint.cs
new file mode 100644
index 0000000..fb6082d
--- /dev/null
+++ b/RMWPFInterfaceLibrary/Api/ProductEndPoint.cs
@@ -0,0 +1,36 @@
+using RMWPFInterfaceLibrary.Models;
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Net.Http;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace RMWPFInterfaceLibrary.Api
+{
+ public class ProductEndPoint : IProductEndPoint
+ {
+ private IAPIHelper _apiHelper;
+ public ProductEndPoint(IAPIHelper apiHelper)
+ {
+ _apiHelper = apiHelper;
+ }
+
+ public async Task> GetAll()
+ {
+ using (HttpResponseMessage response = await _apiHelper.ApiClient.GetAsync("api/Product"))
+ {
+ if (response.IsSuccessStatusCode)
+ {
+ var result = await response.Content.ReadAsAsync>();
+ return result;
+ }
+ else
+ {
+ throw new Exception(response.ReasonPhrase);
+ }
+
+ }
+ }
+ }
+}
diff --git a/RMWPFInterfaceLibrary/Models/CartItemModel.cs b/RMWPFInterfaceLibrary/Models/CartItemModel.cs
new file mode 100644
index 0000000..80292a1
--- /dev/null
+++ b/RMWPFInterfaceLibrary/Models/CartItemModel.cs
@@ -0,0 +1,22 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace RMWPFInterfaceLibrary.Models
+{
+ public class CartItemModel
+ {
+ public ProductModel Product { get; set; }
+ public int QuantityInCart { get; set; }
+
+ public string DisplayText
+ {
+ get
+ {
+ return $"{Product.ProductName} ({QuantityInCart})";
+ }
+ }
+ }
+}
diff --git a/RMWPFInterfaceLibrary/Models/ProductModel.cs b/RMWPFInterfaceLibrary/Models/ProductModel.cs
new file mode 100644
index 0000000..2c26c94
--- /dev/null
+++ b/RMWPFInterfaceLibrary/Models/ProductModel.cs
@@ -0,0 +1,17 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace RMWPFInterfaceLibrary.Models
+{
+ public class ProductModel
+ {
+ public int Id { get; set; }
+ public string ProductName { get; set; }
+ public string Description { get; set; }
+ public decimal RetailPrice { get; set; }
+ public int QuantityInStock { get; set; }
+ }
+}
diff --git a/RMWPFInterfaceLibrary/RMWPFInterfaceLibrary.csproj b/RMWPFInterfaceLibrary/RMWPFInterfaceLibrary.csproj
index 14f9cdb..b64de7e 100644
--- a/RMWPFInterfaceLibrary/RMWPFInterfaceLibrary.csproj
+++ b/RMWPFInterfaceLibrary/RMWPFInterfaceLibrary.csproj
@@ -50,9 +50,13 @@
+
+
+
+
diff --git a/RMWPFUserInterface/BootStrapper.cs b/RMWPFUserInterface/BootStrapper.cs
index b62ce16..094cecf 100644
--- a/RMWPFUserInterface/BootStrapper.cs
+++ b/RMWPFUserInterface/BootStrapper.cs
@@ -27,8 +27,9 @@ namespace RMWPFUserInterface
}
protected override void Configure()
{
- _container.Instance(_container);
-
+ _container.Instance(_container)
+ .PerRequest();
+
_container
.Singleton()
.Singleton()
diff --git a/RMWPFUserInterface/EventModels/LogOnEvent.cs b/RMWPFUserInterface/EventModels/LogOnEvent.cs
new file mode 100644
index 0000000..0ef5b7e
--- /dev/null
+++ b/RMWPFUserInterface/EventModels/LogOnEvent.cs
@@ -0,0 +1,12 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace RMWPFUserInterface.EventModels
+{
+ public class LogOnEvent
+ {
+ }
+}
diff --git a/RMWPFUserInterface/RMWPFUserInterface.csproj b/RMWPFUserInterface/RMWPFUserInterface.csproj
index bff8b6c..9f5201d 100644
--- a/RMWPFUserInterface/RMWPFUserInterface.csproj
+++ b/RMWPFUserInterface/RMWPFUserInterface.csproj
@@ -81,6 +81,7 @@
Designer
+
diff --git a/RMWPFUserInterface/ViewModels/LoginViewModel.cs b/RMWPFUserInterface/ViewModels/LoginViewModel.cs
index 121b9a2..58b6e16 100644
--- a/RMWPFUserInterface/ViewModels/LoginViewModel.cs
+++ b/RMWPFUserInterface/ViewModels/LoginViewModel.cs
@@ -1,5 +1,6 @@
using Caliburn.Micro;
using RMWPFInterfaceLibrary.Api;
+using RMWPFUserInterface.EventModels;
using RMWPFUserInterface.Helpers;
using System;
using System.Collections.Generic;
@@ -14,10 +15,12 @@ namespace RMWPFUserInterface.ViewModels
private string _userName;
private string _password;
private IAPIHelper _apiHelper;
+ private IEventAggregator _events;
- public LoginViewModel(IAPIHelper apiHelper)
+ public LoginViewModel(IAPIHelper apiHelper, IEventAggregator events)
{
_apiHelper = apiHelper;
+ _events = events;
}
public string UserName
{
@@ -96,6 +99,8 @@ namespace RMWPFUserInterface.ViewModels
// Capture more information
await _apiHelper.GetLogedInUserInfo(result.Access_Token);
+
+ await _events.PublishOnUIThreadAsync(new LogOnEvent());
}
catch (Exception ex)
{
diff --git a/RMWPFUserInterface/ViewModels/SalesViewModel.cs b/RMWPFUserInterface/ViewModels/SalesViewModel.cs
index 7ff3c91..ec14020 100644
--- a/RMWPFUserInterface/ViewModels/SalesViewModel.cs
+++ b/RMWPFUserInterface/ViewModels/SalesViewModel.cs
@@ -1,4 +1,6 @@
using Caliburn.Micro;
+using RMWPFInterfaceLibrary.Api;
+using RMWPFInterfaceLibrary.Models;
using System;
using System.Collections.Generic;
using System.ComponentModel;
@@ -10,9 +12,27 @@ namespace RMWPFUserInterface.ViewModels
{
public class SalesViewModel : Screen
{
- private BindingList _products;
+ IProductEndPoint _productEndPoint;
+ public SalesViewModel(IProductEndPoint productEndPoint)
+ {
+ _productEndPoint = productEndPoint;
+ }
- public BindingList Products
+ protected override async void OnViewLoaded(object view)
+ {
+ base.OnViewLoaded(view);
+ await LoadProducts();
+ }
+
+ private async Task LoadProducts()
+ {
+ var prods = await _productEndPoint.GetAll();
+ Products = new BindingList(prods);
+ }
+
+ private BindingList _products;
+
+ public BindingList Products
{
get { return _products; }
set
@@ -22,27 +42,42 @@ namespace RMWPFUserInterface.ViewModels
}
}
- private BindingList _cart;
+ private ProductModel _selectedProduct;
- public BindingList Cart
+ public ProductModel SelectedProduct
+ {
+ get { return _selectedProduct; }
+ set
+ {
+ _selectedProduct = value;
+ NotifyOfPropertyChange(() => SelectedProduct);
+ NotifyOfPropertyChange(() => CanAddToCart);
+ }
+ }
+
+
+ private BindingList _cart = new BindingList();
+
+ public BindingList Cart
{
get { return _cart; }
set
- {
- Cart = value;
+ {
+ _cart = value;
NotifyOfPropertyChange(() => Cart);
}
}
- private string _itemQuantity;
+ private int _itemQuantity = 1;
- public string ItemQuantity
+ public int ItemQuantity
{
get { return _itemQuantity; }
set
{
- ItemQuantity = value;
+ _itemQuantity = value;
NotifyOfPropertyChange(() => ItemQuantity);
+ NotifyOfPropertyChange(() => CanAddToCart);
}
}
@@ -50,8 +85,14 @@ namespace RMWPFUserInterface.ViewModels
{
get
{
- // replace with calulation;
- return "$0.00";
+ decimal subTotal = 0;
+
+ foreach (var item in Cart)
+ {
+ subTotal += item.Product.RetailPrice * item.QuantityInCart;
+ }
+
+ return subTotal.ToString("C");
}
}
@@ -79,14 +120,36 @@ namespace RMWPFUserInterface.ViewModels
{
bool output = false;
- // Make sure item is selected and quantity is typed in
+ if (ItemQuantity > 0 && SelectedProduct?.QuantityInStock >= ItemQuantity)
+ {
+ output = true;
+ }
return output;
}
}
public void AddToCart()
{
+ CartItemModel existingItem = Cart.FirstOrDefault(x => x.Product == SelectedProduct);
+ if (existingItem != null)
+ {
+ existingItem.QuantityInCart += ItemQuantity;
+ }
+ else
+ {
+ CartItemModel item = new CartItemModel
+ {
+ Product = SelectedProduct,
+ QuantityInCart = ItemQuantity
+ };
+
+ Cart.Add(item);
+ }
+ SelectedProduct.QuantityInStock -= ItemQuantity;
+ ItemQuantity = 1;
+ NotifyOfPropertyChange(() => SubTotal);
+ Cart.ResetBindings();
}
public bool CanRemoveFromCart
@@ -102,7 +165,7 @@ namespace RMWPFUserInterface.ViewModels
}
public void RemoveFromCart()
{
-
+ NotifyOfPropertyChange(() => SubTotal);
}
public bool CanCheckOut
diff --git a/RMWPFUserInterface/ViewModels/ShellViewModel.cs b/RMWPFUserInterface/ViewModels/ShellViewModel.cs
index a7c41a3..49d04ec 100644
--- a/RMWPFUserInterface/ViewModels/ShellViewModel.cs
+++ b/RMWPFUserInterface/ViewModels/ShellViewModel.cs
@@ -2,18 +2,35 @@
using System.Collections.Generic;
using System.Linq;
using System.Text;
+using System.Threading;
using System.Threading.Tasks;
using Caliburn.Micro;
+using RMWPFUserInterface.EventModels;
namespace RMWPFUserInterface.ViewModels
{
- public class ShellViewModel : Conductor