فهرست منبع

Cleaned out old (unused) JobMaterial and StockHolding Stores code
Added AverageCost property to Product
PurchaseOrderItemStore now updates Product.AverageCost when receiving

Frank van den Bos 2 سال پیش
والد
کامیت
f9af769a69

+ 10 - 5
prs.classes/Entities/Product/Product.cs

@@ -77,20 +77,25 @@ namespace Comal.Classes
         [CurrencyEditor(Visible = Visible.Optional, Editable = Editable.Disabled)]
         [EditorSequence("Pricing", 6)]
         public double NettCost { get; set; }
-
+        
+        [CurrencyEditor(Visible = Visible.Optional, Editable = Editable.Disabled)]
         [EditorSequence("Pricing", 7)]
+        [LoggableProperty]
+        public double AverageCost { get; set; }
+        
+        [EditorSequence("Pricing", 8)]
         public TaxCodeLink TaxCode { get; set; }
 
-        [EditorSequence("Pricing", 8)]
+        [EditorSequence("Pricing", 9)]
         public GLCodeLink PurchaseGL { get; set; }
 
-        [EditorSequence("Pricing", 9)]
+        [EditorSequence("Pricing", 10)]
         public GLCodeLink SellGL { get; set; }
 
-        [EditorSequence("Pricing", 10)]
+        [EditorSequence("Pricing", 11)]
         public CostCentreLink CostCentre { get; set; }
 
-        [EditorSequence("Pricing", 11)]
+        [EditorSequence("Pricing", 12)]
         public CostSheetSectionLink CostSheetSection { get; set; }
 
         /// <summary>

+ 58 - 0
prs.classes/Entities/PurchaseOrder/PurchaseOrder.cs

@@ -1,5 +1,6 @@
 using System;
 using System.Collections.Generic;
+using System.Linq;
 using System.Linq.Expressions;
 using InABox.Core;
 
@@ -223,5 +224,62 @@ namespace Comal.Classes
 
             Category = new PurchaseOrderCategoryLink();
         }
+        
+        public static void UpdateCosts(IEnumerable<PurchaseOrderItem> items, Guid supplierid, Action<String,object>? update)
+        {
+
+            void UpdateValue<TType>(PurchaseOrderItem item,Expression<Func<PurchaseOrderItem, TType>> property, TType value)
+            {
+                String propertyname = CoreUtils.GetFullPropertyName(property, ".");
+                if (update == null)
+                    CoreUtils.SetPropertyValue(item, propertyname , value);
+                else
+                    update?.Invoke(propertyname, value);
+            }
+            
+            var productids = items.Where(x => x.Product.ID != Guid.Empty).Select(x => x.Product.ID).ToArray();
+            MultiQuery query = new MultiQuery();
+            query.Add(
+                new Filter<SupplierProduct>(x=>x.SupplierLink.ID).IsEqualTo(supplierid).And(x=>x.ProductLink.ID).InList(productids),
+                new Columns<SupplierProduct>(x=>x.ProductLink.ID).Add(x=>x.Job.ID).Add(x=>x.CostPrice).Add(x=>x.SupplierCode).Add(x=>x.SupplierDescription)
+            );
+            query.Add(
+                new Filter<Product>(x=>x.ID).InList(productids),
+                new Columns<Product>(x=>x.ID).Add(x=>x.NettCost).Add(x=>x.Code).Add(x=>x.Name)
+            );
+            query.Query();
+                
+            foreach (var item in items)
+            {
+                CoreRow? row = query.Get<SupplierProduct>()?.Rows.FirstOrDefault(r =>
+                    (r.Get<SupplierProduct, Guid>(c => c.ProductLink.ID) == item.Product.ID)
+                    && (r.Get<SupplierProduct, Guid>(c => c.Job.ID) == item.Job.ID)
+                );
+                if (row == null)
+                    row = query.Get<SupplierProduct>()?.Rows.FirstOrDefault(r =>
+                        (r.Get<SupplierProduct, Guid>(c => c.ProductLink.ID) == item.Product.ID)
+                        && (r.Get<SupplierProduct, Guid>(c => c.Job.ID) == Guid.Empty)
+                    );
+                if (row != null)
+                {
+                    UpdateValue<String>(item, x => x.SupplierCode, row.Get<SupplierProduct, String>(c => c.SupplierCode));
+                    UpdateValue<String>(item, x => x.Description, row.Get<SupplierProduct, String>(c => c.SupplierDescription));
+                    UpdateValue<double>(item, x => x.Cost, row.Get<SupplierProduct, double>(c => c.CostPrice));
+                }
+                else
+                {
+                    row = query.Get<Product>()?.Rows.FirstOrDefault(r =>
+                        (r.Get<Product, Guid>(c => c.ID) == item.Product.ID)
+                    );
+                    if (row != null)
+                    {
+                        UpdateValue<String>(item, x => x.SupplierCode, row.Get<Product, String>(c => c.Code));
+                        UpdateValue<String>(item, x => x.Description, row.Get<Product, String>(c => c.Name));
+                        UpdateValue<double>(item, x => x.Cost, row.Get<Product, double>(c => c.NettCost));
+                    }
+                }
+
+            }
+        }
     }
 }

+ 3 - 0
prs.classes/Entities/PurchaseOrder/PurchaseOrderItem.cs

@@ -248,6 +248,9 @@ namespace Comal.Classes
             bChanging = false;
             base.DoPropertyChanged(name, before, after);
         }
+
+
+        
         
     }
 }

+ 1 - 0
prs.classes/Entities/Stock/StockMovement.cs

@@ -94,6 +94,7 @@ namespace Comal.Classes
         // Units = Received - Issued
         [Formula(typeof(StockMovementUnitsFormula))]
         [EditorSequence(4)]
+        [DoubleEditor(Visible=Visible.Optional, Editable = Editable.Hidden)]
         public double Units { get; set; }
         
         [EditorSequence(5)]

+ 35 - 0
prs.desktop/Panels/Suppliers/SupplierPurchaseOrderItemOneToMany.cs

@@ -0,0 +1,35 @@
+using System;
+using System.Collections.Generic;
+using Comal.Classes;
+using InABox.DynamicGrid;
+
+namespace PRSDesktop
+{
+    public class SupplierPurchaseOrderItemOneToMany : DynamicOneToManyGrid<PurchaseOrder,PurchaseOrderItem>
+    {
+        public SupplierPurchaseOrderItemOneToMany() : base()
+        {
+            
+        }
+
+        protected override Dictionary<string, object> EditorValueChanged(DynamicEditorForm editor, PurchaseOrderItem[] items, string name,
+            object value)
+        {
+            var results = base.EditorValueChanged(editor, items, name, value);
+            if (name.Equals("Product.ID") || name.Equals("Job.ID"))
+            {
+                PurchaseOrder.UpdateCosts(
+                    items, 
+                    Item.SupplierLink.ID,
+                    (n,v) => DynamicGridUtils.UpdateEditorValue(items, n, v, results)
+                );
+            }
+            else if (name.Equals("ProductLink.TaxCode.ID"))
+            {
+                DynamicGridUtils.UpdateEditorValue(items, "TaxCode.ID", (Guid)value, results);
+            }
+
+            return results;
+        }
+    }
+}

+ 23 - 82
prs.desktop/Panels/Suppliers/SupplierPurchaseOrderItems.cs

@@ -19,6 +19,10 @@ namespace PRSDesktop
         private readonly Button consign;
         private readonly Button receive;
         private readonly Button viewconsign;
+        
+        public Guid OrderID { get; set; }
+        public Guid SupplierID { get; set; }
+        public bool Closed { get; set; }
 
         public SupplierPurchaseOrderItems()
         {
@@ -71,8 +75,7 @@ namespace PRSDesktop
             bill.IsEnabled = false;
         }
 
-        public Guid OrderID { get; set; }
-        public bool Closed { get; set; }
+
 
         private void BuildMenu(DynamicMenuColumn column, CoreRow? row)
         {
@@ -166,67 +169,12 @@ namespace PRSDesktop
             criteria.Add(new Filter<PurchaseOrderItem>(x => x.PurchaseOrderLink.ID).IsEqualTo(OrderID));
             base.Reload(criteria, columns, ref sort, action);
         }
-
-        protected override void DoAdd()
+        
+        protected override PurchaseOrderItem CreateItem()
         {
-            if (OrderID.Equals(Guid.Empty))
-            {
-                MessageBox.Show("Please select a Purchase Order first!");
-                return;
-            }
-
-            if (Closed)
-            {
-                MessageBox.Show("Cannot Modify a Closed Purchase Order");
-                return;
-            }
-
-            var dialog = new MultiSelectDialog<Product>(
-                new Filter<Product>(x => x.Expired).IsEqualTo(DateTime.MinValue),
-                new Columns<Product>(x => x.ID)
-                    .Add(x => x.Code)
-                    .Add(x => x.Name)
-                    .Add(x => x.NettCost)
-                    .Add(x => x.Dimensions.Unit.ID)
-                    .Add(x=>x.Dimensions.Unit.Description)
-                    .Add(x=>x.Dimensions.Unit.Formula)
-                    .Add(x=>x.Dimensions.Unit.Format)
-                    .Add(x=>x.Dimensions.Unit.HasQuantity)
-                    .Add(x=>x.Dimensions.Unit.HasLength)
-                    .Add(x=>x.Dimensions.Unit.HasWidth)
-                    .Add(x=>x.Dimensions.Unit.HasLength)
-                    .Add(x=>x.Dimensions.Unit.HasWeight)
-                    .Add(x=>x.Dimensions.Quantity)
-                    .Add(x=>x.Dimensions.Length)
-                    .Add(x=>x.Dimensions.Width)
-                    .Add(x=>x.Dimensions.Height)
-                    .Add(x=>x.Dimensions.Weight)
-                    .Add(x=>x.Dimensions.Value)
-                    .Add(x=>x.Dimensions.UnitSize)
-                    .Add(x => x.TaxCode.ID)
-            );
-            if (dialog.ShowDialog())
-            {
-                Progress.Show("Adding Order Items");
-                var items = new List<PurchaseOrderItem>();
-                foreach (var row in dialog.Data().Rows)
-                {
-                    var p = row.ToObject<Product>();
-                    var item = new PurchaseOrderItem();
-                    item.PurchaseOrderLink.ID = OrderID;
-                    item.Product.ID = p.ID;
-                    item.Qty = 1;
-                    item.Dimensions.CopyFrom(p.Dimensions);
-                    item.TaxCode.ID = p.TaxCode.ID;
-                    items.Add(item);
-                }
-
-                Progress.SetMessage("Updating Items");
-                new Client<PurchaseOrderItem>().Save(items, "Added to Order");
-                Refresh(false, true);
-                Progress.Close();
-                MessageBox.Show(string.Format("{0} order items added", items.Count));
-            }
+            var result = base.CreateItem();
+            result.PurchaseOrderLink.ID = OrderID;
+            return result;
         }
 
         public override bool EditItems(PurchaseOrderItem[] items, Func<Type, CoreTable> PageDataHandler, bool PreloadPages = false)
@@ -243,31 +191,20 @@ namespace PRSDesktop
                 return false;
             }
 
-            return base.EditItems(items, PageDataHandler, PreloadPages);
+            return base.EditItems(items, PageDataHandler, true);
         }
 
         protected override Dictionary<string, object> EditorValueChanged(DynamicEditorForm editor, PurchaseOrderItem[] items, string name,
             object value)
         {
             var results = base.EditorValueChanged(editor, items, name, value);
-            if (name.Equals("ProductLink.ID") || name.Equals("Job.ID"))
+            if (name.Equals("Product.ID") || name.Equals("Job.ID"))
             {
-                var pid = name.Equals("ProductLink.ID") ? (Guid)value : items.First().Product.ID;
-                var jid = name.Equals("Job.ID") ? (Guid)value : items.First().Job.ID;
-
-                var supprods = new Client<SupplierProduct>().Query(
-                    new Filter<SupplierProduct>(x => x.ProductLink.ID).IsEqualTo(pid).And(x => x.SupplierLink.ID)
-                        .IsEqualTo(items.First().PurchaseOrderLink.SupplierLink.ID)
+                PurchaseOrder.UpdateCosts(
+                    items, 
+                    SupplierID, 
+                    (name,value) => DynamicGridUtils.UpdateEditorValue(items, name, value, results)
                 );
-                var row = supprods.Rows.FirstOrDefault(r => r.Get<SupplierProduct, Guid>(x => x.Job.ID).Equals(jid));
-                if (row == null)
-                    row = supprods.Rows.FirstOrDefault(r => !r.IsEntityLinkValid<SupplierProduct, JobLink>(x => x.Job));
-
-                var cost = row != null ? row.Get<SupplierProduct, double>(x => x.CostPrice) : 0.0F;
-                DynamicGridUtils.UpdateEditorValue(items, "Cost", cost, results);
-
-                var code = row != null ? row.Get<SupplierProduct, string>(x => x.SupplierCode) : "";
-                DynamicGridUtils.UpdateEditorValue(items, "SupplierCode", code, results);
             }
             else if (name.Equals("ProductLink.TaxCode.ID"))
             {
@@ -277,9 +214,9 @@ namespace PRSDesktop
             return results;
         }
 
-        protected override bool CanDeleteItems(CoreRow[] rows)
+        private bool CheckPOStatus(Func<bool> basefunction)
         {
-            if (OrderID.Equals(Guid.Empty))
+            if (OrderID.Equals(Guid.Empty) || (OrderID.Equals(CoreUtils.FullGuid)))
             {
                 MessageBox.Show("Please select a Purchase Order first!");
                 return false;
@@ -291,9 +228,13 @@ namespace PRSDesktop
                 return false;
             }
 
-            return base.CanDeleteItems(rows);
+            return basefunction();
         }
 
+        protected override bool CanCreateItems() => CheckPOStatus(() => base.CanCreateItems());
+
+        protected override bool CanDeleteItems(CoreRow[] rows) => CheckPOStatus(() => base.CanDeleteItems(rows));
+        
         private bool CreateConsignment(Button sender, CoreRow[] rows)
         {
             if (!rows.Any())

+ 12 - 2
prs.desktop/Panels/Suppliers/SupplierPurchaseOrderPanel.xaml.cs

@@ -23,12 +23,22 @@ namespace PRSDesktop
         public SupplierPurchaseOrderPanel()
         {
             InitializeComponent();
+            Orders.HiddenColumns.Add(x => x.SupplierLink.ID);
+            Orders.HiddenColumns.Add(x => x.PONumber);
+            Orders.HiddenColumns.Add(x => x.SupplierLink.Code);
+            Orders.HiddenColumns.Add(x => x.SupplierLink.Name);
+            Orders.HiddenColumns.Add(x => x.Notes);
+            Orders.HiddenColumns.Add(x => x.IssuedDate);
+            Orders.HiddenColumns.Add(x => x.IssuedBy.Name);
+            Orders.HiddenColumns.Add(x => x.DueDate);
+            Orders.HiddenColumns.Add(x => x.ClosedDate);
+            
             Orders.OnSelectItem += (o, e) =>
             {
                 var row = e.Rows?.FirstOrDefault();
                 Items.OrderID = row != null ? row.Get<PurchaseOrder, Guid>(x => x.ID) : CoreUtils.FullGuid;
-                Items.Closed = row != null ? !row.Get<PurchaseOrder, DateTime>(x => x.ClosedDate).IsEmpty() : true;
-                LoadOrder(row);
+                Items.SupplierID = row != null ? row.Get<PurchaseOrder, Guid>(x => x.SupplierLink.ID) : CoreUtils.FullGuid;
+                Items.Closed = row != null ? !row.Get<PurchaseOrder, DateTime>(x => x.ClosedDate).IsEmpty() : true; LoadOrder(row);
                 Items.Refresh(false, true);
             };
         }

+ 74 - 130
prs.desktop/Panels/Suppliers/SupplierPurchaseOrders.cs

@@ -9,6 +9,7 @@ using InABox.Clients;
 using InABox.Core;
 using InABox.DynamicGrid;
 using InABox.WPF;
+using sun.misc;
 
 namespace PRSDesktop
 {
@@ -25,7 +26,7 @@ namespace PRSDesktop
             );
 
             OnEditorValueChanged += SupplierPurchaseOrders_OnEditorValueChanged;
-
+            
             HiddenColumns.Add(x => x.ClosedDate);
             HiddenColumns.Add(x => x.Balance);
 
@@ -36,139 +37,84 @@ namespace PRSDesktop
         private Dictionary<string, object> SupplierPurchaseOrders_OnEditorValueChanged(object sender, string name, object value)
         {
             Dictionary<string, object> result = new Dictionary<string, object>();
-            if (name.Equals("DueDate"))
+            var form = sender as DynamicEditorForm;
+            var itemspage = form?.Pages.FirstOrDefault(x => x is DynamicOneToManyGrid<PurchaseOrder, PurchaseOrderItem>) as DynamicOneToManyGrid<PurchaseOrder, PurchaseOrderItem>;
+            if ((itemspage == null) || (itemspage.Items.Count == 0))
+                return result;
+            
+            if (name.Equals("DueDate") && (MessageBox.Show("Update Due Date on existing items?", "Alert", MessageBoxButton.YesNo) == MessageBoxResult.Yes))
             {
-                var choice = MessageBox.Show("Due Date changed - apply to all Purchase Order Items?", "Alert", MessageBoxButton.YesNo);
-                switch (choice)
-                {
-                    case MessageBoxResult.Yes:
-                        break;
-                    default:
-                        return result;
-                }
-                Progress.Show("Working");
-                var form = sender as DynamicEditorForm;
-                foreach (var page in form.Pages)
-                {
-                    if (page is DynamicOneToManyGrid<PurchaseOrder, PurchaseOrderItem> poitemgrid)
-                    {
-                        if (poitemgrid.Items.Count == 0)
-                        {
-                            Dispatcher.Invoke(() =>
-                            {
-                                poitemgrid.Load(form.Items[0], null);
-                            });
-                        }
-                        List<PurchaseOrderItem> items = new List<PurchaseOrderItem>();
-                        foreach (var item in poitemgrid.Items)
-                        {
-                            item.DueDate = Convert.ToDateTime(value);
-                        }
-                        Dispatcher.Invoke(() =>
-                        {
-                            poitemgrid.Refresh(false, true);
-                        });
-                    }
-                }
-                Progress.Close();
+                foreach (var item in itemspage.Items)
+                    item.DueDate = Convert.ToDateTime(value);
+                itemspage.Refresh(false, true);
             }
-            else if (name.Equals("SupplierLink.ID"))
+            else if (name.Equals("SupplierLink.ID") &&
+                     (MessageBox.Show("Update Supplier Pricing to existihg items?", "Alert", MessageBoxButton.YesNo) == MessageBoxResult.Yes))
             {
-                var choice = MessageBox.Show("Supplier changed - change pricing to all Purchase Order Items where Supplier Pricing is found?" +
-                    " (If not found, product base cost price will be applied", "Alert", MessageBoxButton.YesNo);
-                switch (choice)
-                {
-                    case MessageBoxResult.Yes:
-                        break;
-                    default:
-                        return result;
-                }
-                Progress.Show("Working");
-                var form = sender as DynamicEditorForm;
-                foreach (var page in form.Pages)
-                {
-                    if (page is DynamicOneToManyGrid<PurchaseOrder, PurchaseOrderItem> poitemgrid)
-                    {
-                        if (poitemgrid.Items.Count == 0)
-                        {
-                            Dispatcher.Invoke(() =>
-                            {
-                                poitemgrid.Load(form.Items[0], null);
-                            });
-                        }
-                        List<SupplierProduct> supplierProducts = GetSupplierProducts(value);
-                        Filter<Product> filter = new Filter<Product>(x => x.ID).IsEqualTo(poitemgrid.Items[0].Product.ID);
-                        foreach (var item in poitemgrid.Items)
-                        {
-                            SupplierProduct checkProduct = supplierProducts.Find(x => x.ProductLink.ID == item.Product.ID);
-                            if (checkProduct != null)
-                            {
-                                SupplierProduct checkJob = supplierProducts.Find(x => x.ProductLink.ID == item.Product.ID && x.Job.ID == item.Job.ID);
-                                if (checkJob != null)
-                                    item.Cost = checkJob.TradePrice;
-                                else
-                                    item.Cost = checkProduct.TradePrice;
-                            }
-                            else
-                            {
-                                filter = filter.Or(x => x.ID).IsEqualTo(item.Product.ID);
-                                item.Cost = 0;
-                            }
-                        }
-                        Dictionary<Guid, double> productIDCosts = new Dictionary<Guid, double>();
+                PurchaseOrder.UpdateCosts(itemspage.Items, (Guid)value, null);
+                // var productids = itemspage.Items.Where(x => x.Product.ID != Guid.Empty).Select(x => x.Product.ID).ToArray();
+                // MultiQuery query = new MultiQuery();
+                // query.Add(
+                //     new Filter<SupplierProduct>(x=>x.SupplierLink.ID).IsEqualTo(value).And(x=>x.ProductLink.ID).InList(productids),
+                //     new Columns<SupplierProduct>(x=>x.ProductLink.ID).Add(x=>x.Job.ID).Add(x=>x.CostPrice)
+                // );
+                // query.Add(
+                //     new Filter<Product>(x=>x.ID).InList(productids),
+                //     new Columns<Product>(x=>x.ID).Add(x=>x.NettCost)
+                // );
+                // query.Query();
+                //
+                // foreach (var item in itemspage.Items)
+                // {
+                //     CoreRow? row = query.Get<SupplierProduct>()?.Rows.FirstOrDefault(r =>
+                //         (r.Get<SupplierProduct, Guid>(c => c.ProductLink.ID) == item.Product.ID)
+                //         && (r.Get<SupplierProduct, Guid>(c => c.Job.ID) == item.Job.ID)
+                //     );
+                //     if (row == null)
+                //         row = query.Get<SupplierProduct>()?.Rows.FirstOrDefault(r =>
+                //             (r.Get<SupplierProduct, Guid>(c => c.ProductLink.ID) == item.Product.ID)
+                //             && (r.Get<SupplierProduct, Guid>(c => c.Job.ID) == Guid.Empty)
+                //         );
+                //     if (row != null)
+                //         item.Cost = row.Get<SupplierProduct, double>(c => c.CostPrice);
+                //     else
+                //     {
+                //         row = query.Get<Product>()?.Rows.FirstOrDefault(r =>
+                //             (r.Get<Product, Guid>(c => c.ID) == item.Product.ID)
+                //         );
+                //         if (row != null)
+                //             item.Cost = row.Get<Product, double>(c => c.NettCost);
+                //     }
+                //
+                // }
+                
+                itemspage.Refresh(false, true);
 
-                        CoreTable productsTable = new Client<Product>().Query(filter,
-                            new Columns<Product>(x => x.ID, x => x.BaseCost));
-                        if (productsTable.Rows.Any())
-                        {
-                            foreach (CoreRow row in productsTable.Rows)
-                            {
-                                List<Object> list = row.Values;
-                                if (list[1] == null) list[1] = 0;
-                                productIDCosts.Add(Guid.Parse(list[0].ToString()), double.Parse(list[1].ToString()));
-                            }
-                        }
-                        if (productIDCosts.Count != 0)
-                        {
-                            foreach (var item in poitemgrid.Items)
-                            {
-                                if (item.Cost == 0 && productIDCosts.ContainsKey(item.Product.ID))
-                                {
-                                    item.Cost = productIDCosts[item.Product.ID];
-                                }
-                            }
-                        }
-                        Dispatcher.Invoke(() =>
-                        {
-                            poitemgrid.Refresh(false, true);
-                        });
-                    }
-                }
-                Progress.Close();           
             }
             return result;
+            
         }
 
-        private List<SupplierProduct> GetSupplierProducts(object value)
-        {
-            List<SupplierProduct> supplierProducts = new List<SupplierProduct>();
-            CoreTable supplierProductstable = new Client<SupplierProduct>().Query(new Filter<SupplierProduct>(x => x.SupplierLink.ID).IsEqualTo(Guid.Parse(value.ToString())),
-            new Columns<SupplierProduct>(
-            x => x.ID,
-            x => x.SupplierLink.ID,
-            x => x.ProductLink.ID,
-            x => x.Job.ID,
-            x => x.TradePrice));
-            if (supplierProductstable.Rows.Any())
-            {
-                foreach (CoreRow row in supplierProductstable.Rows)
-                {
-                    SupplierProduct supplierProduct = row.ToObject<SupplierProduct>();
-                    supplierProducts.Add(supplierProduct);
-                }
-            }
-            return supplierProducts;
-        }
+        // private List<SupplierProduct> GetSupplierProducts(object value)
+        // {
+        //     List<SupplierProduct> supplierProducts = new List<SupplierProduct>();
+        //     CoreTable supplierProductstable = new Client<SupplierProduct>().Query(new Filter<SupplierProduct>(x => x.SupplierLink.ID).IsEqualTo(Guid.Parse(value.ToString())),
+        //     new Columns<SupplierProduct>(
+        //     x => x.ID,
+        //     x => x.SupplierLink.ID,
+        //     x => x.ProductLink.ID,
+        //     x => x.Job.ID,
+        //     x => x.TradePrice));
+        //     if (supplierProductstable.Rows.Any())
+        //     {
+        //         foreach (CoreRow row in supplierProductstable.Rows)
+        //         {
+        //             SupplierProduct supplierProduct = row.ToObject<SupplierProduct>();
+        //             supplierProducts.Add(supplierProduct);
+        //         }
+        //     }
+        //     return supplierProducts;
+        // }
 
         public bool ShowAll { get; set; }
 
@@ -183,10 +129,8 @@ namespace PRSDesktop
 
             if (SelectedCategory != CoreUtils.FullGuid)
                 criteria.Add(new Filter<PurchaseOrder>(x => x.Category.ID).IsEqualTo(SelectedCategory));
-
-            var cols = new Columns<PurchaseOrder>().Default(ColumnType.IncludeOptional, ColumnType.IncludeLinked, ColumnType.IncludeAggregates,
-                ColumnType.IncludeFormulae);
-            base.Reload(criteria, cols, ref sort, action);
+            
+            base.Reload(criteria, columns, ref sort, action);
         }
 
         protected override void SelectItems(CoreRow[] rows)

+ 0 - 142
prs.stores/BaseStore.cs

@@ -78,148 +78,6 @@ namespace Comal.Stores
                 }
             }
         }
-
-        protected void EnsureJobMaterials(ProductLink product, JobLink job, ProductStyleLink style, StockDimensions dimensions)
-        {
-            // if (product.ID == Guid.Empty || job.ID == Guid.Empty)
-            //     return;
-            //
-            // var jobmaterials = Provider.List(
-            //     new Filter<JobMaterial>(x => x.Product.ID).IsEqualTo(product.ID)
-            //         .And(x => x.Job.ID).IsEqualTo(job.ID)
-            //         .And(x => x.Style.ID).IsEqualTo(style.ID)
-            //         .And(x => x.Dimensions.Unit.ID).IsEqualTo(dimensions.Unit.ID)
-            //         .And(x => x.Dimensions.Length).IsEqualTo(dimensions.Length)
-            //         .And(x => x.Dimensions.Width).IsEqualTo(dimensions.Width)
-            //         .And(x => x.Dimensions.Height).IsEqualTo(dimensions.Height)
-            //         .And(x => x.Dimensions.Weight).IsEqualTo(dimensions.Weight)
-            //     ,
-            //     new Columns<JobMaterial>(x => x.ID)
-            // );
-            // if (!jobmaterials.Any())
-            // {
-            //     var material = new JobMaterial();
-            //     material.Product.ID = product.ID;
-            //     material.Job.ID = job.ID;
-            //     material.Style.ID = style.ID;
-            //     material.Dimensions.CopyFrom(dimensions);
-            //     Provider.Save(material);
-            // }
-        }
-        
-        protected void CleanupJobMaterials(Guid id, ProductLink Product, JobLink Job, ProductStyleLink Style, StockDimensions Dimensions, bool delete)
-        {
-            // if (Product.ID == Guid.Empty || Job.ID == Guid.Empty)
-            //     return;
-            //
-            // var hasProduct = !delete && Product.HasOriginalValue(x=>x.ID);
-            // var hasJob = !delete && Job.HasOriginalValue(x=>x.ID);
-            // var hasStyle = !delete && Style.HasOriginalValue(x=>x.ID);
-            // var hasUnit = !delete && Dimensions.HasOriginalValue(x=>x.Unit.ID);
-            // var hasLength = !delete && Dimensions.HasOriginalValue(x => x.Length);
-            // var hasWidth = !delete && Dimensions.HasOriginalValue(x => x.Width);
-            // var hasHeight = !delete && Dimensions.HasOriginalValue(x => x.Height);
-            // var hasWeight = !delete && Dimensions.HasOriginalValue(x => x.Weight);
-            // if (delete || hasProduct || hasJob || hasStyle || hasUnit || hasLength || hasWidth || hasHeight || hasWeight)
-            // {
-            //     var productid = hasProduct ? Product.GetOriginalValue(x=>x.ID) : Product.ID;
-            //     var jobid = hasJob ? Job.GetOriginalValue(x=>x.ID) : Job.ID;
-            //     var styleid = hasStyle ? Style.GetOriginalValue(x=>x.ID) : Style.ID;
-            //     var unitid = hasUnit ? Dimensions.GetOriginalValue(x=>x.Unit.ID) : Dimensions.Unit.ID;
-            //     var length = hasLength ? Dimensions.GetOriginalValue(x=>x.Length) : Dimensions.Length;
-            //     var width = hasWidth ? Dimensions.GetOriginalValue(x=>x.Width) : Dimensions.Width;
-            //     var height = hasHeight ? Dimensions.GetOriginalValue(x=>x.Height) : Dimensions.Height;
-            //     var weight = hasWeight ? Dimensions.GetOriginalValue(x=>x.Weight) : Dimensions.Weight;
-            //     
-            //     var bomtask = Task.Run(() =>
-            //     {
-            //         return Provider.List(
-            //             new Filter<JobBillOfMaterialsItem>(x => x.Product.ID).IsEqualTo(productid)
-            //                 .And(x => x.Job.ID).IsEqualTo(jobid)
-            //                 .And(x => x.Style.ID).IsEqualTo(styleid)
-            //                 .And(x => x.ID).IsNotEqualTo(id)
-            //                 .And(x => x.Dimensions.Unit.ID).IsEqualTo(unitid)
-            //                 .And(x => x.Dimensions.Length).IsEqualTo(length)
-            //                 .And(x => x.Dimensions.Width).IsEqualTo(width)
-            //                 .And(x => x.Dimensions.Height).IsEqualTo(height)
-            //                 .And(x => x.Dimensions.Weight).IsEqualTo(weight)
-            //             ,
-            //             new Columns<JobBillOfMaterialsItem>(x => x.ID)
-            //         ).Any();
-            //     });
-            //
-            //     var reqtask = Task.Run(() =>
-            //     {
-            //         return Provider.List(
-            //             new Filter<JobRequisitionItem>(x => x.Product.ID).IsEqualTo(productid)
-            //                 .And(x => x.Requisition.Job.ID).IsEqualTo(jobid)
-            //                 .And(x => x.Style.ID).IsEqualTo(styleid)
-            //                 .And(x => x.ID).IsNotEqualTo(id)
-            //                 .And(x => x.Dimensions.Unit.ID).IsEqualTo(unitid)
-            //                 .And(x => x.Dimensions.Length).IsEqualTo(length)
-            //                 .And(x => x.Dimensions.Width).IsEqualTo(width)
-            //                 .And(x => x.Dimensions.Height).IsEqualTo(height)
-            //                 .And(x => x.Dimensions.Weight).IsEqualTo(weight)
-            //             ,
-            //             new Columns<JobRequisitionItem>(x => x.ID)
-            //         ).Any();
-            //     });
-            //
-            //     var movetask = Task.Run(() =>
-            //     {
-            //         return Provider.List(
-            //             new Filter<StockMovement>(x => x.Product.ID).IsEqualTo(productid)
-            //                 .And(x => x.Job.ID).IsEqualTo(jobid)
-            //                 .And(x => x.Style.ID).IsEqualTo(styleid)
-            //                 .And(x => x.ID).IsNotEqualTo(id)
-            //                 .And(x => x.Dimensions.Unit.ID).IsEqualTo(unitid)
-            //                 .And(x => x.Dimensions.Length).IsEqualTo(length)
-            //                 .And(x => x.Dimensions.Width).IsEqualTo(width)
-            //                 .And(x => x.Dimensions.Height).IsEqualTo(height)
-            //                 .And(x => x.Dimensions.Weight).IsEqualTo(weight)
-            //             ,
-            //             new Columns<StockMovement>(x => x.ID)
-            //         ).Any();
-            //     });
-            //
-            //     var potask = Task.Run(() =>
-            //     {
-            //         return Provider.List(
-            //             new Filter<PurchaseOrderItem>(x => x.ProductLink.ID).IsEqualTo(productid)
-            //                 .And(x => x.Job.ID).IsEqualTo(jobid)
-            //                 .And(x => x.StyleLink.ID).IsEqualTo(styleid)
-            //                 .And(x => x.ID).IsNotEqualTo(id)
-            //                 .And(x => x.Dimensions.Unit.ID).IsEqualTo(unitid)
-            //                 .And(x => x.Dimensions.Length).IsEqualTo(length)
-            //                 .And(x => x.Dimensions.Width).IsEqualTo(width)
-            //                 .And(x => x.Dimensions.Height).IsEqualTo(height)
-            //                 .And(x => x.Dimensions.Weight).IsEqualTo(weight)
-            //             ,
-            //             new Columns<PurchaseOrderItem>(x => x.ID)
-            //         ).Any();
-            //     });
-            //
-            //     Task.WaitAll(bomtask, reqtask, movetask, potask);
-            //     
-            //     if (bomtask.Result || reqtask.Result || movetask.Result || potask.Result)
-            //         return;
-            //
-            //     var remove = Provider.Query(
-            //         new Filter<JobMaterial>(x => x.Product.ID).IsEqualTo(productid)
-            //             .And(x => x.Job.ID).IsEqualTo(jobid)
-            //             .And(x => x.Style.ID).IsEqualTo(styleid)
-            //             .And(x => x.Dimensions.Unit.ID).IsEqualTo(unitid)
-            //             .And(x => x.Dimensions.Length).IsEqualTo(length)
-            //             .And(x => x.Dimensions.Width).IsEqualTo(width)
-            //             .And(x => x.Dimensions.Height).IsEqualTo(height)
-            //             .And(x => x.Dimensions.Weight).IsEqualTo(weight)
-            //         ,
-            //         new Columns<JobMaterial>(x => x.ID)
-            //     ).Rows.Select(x => x.ToObject<JobMaterial>());
-            //     
-            //     Provider.Delete(remove);
-            // }
-        }
         
         protected void UnlinkTrackingKanban<TEntityKanban, TEntity, TEntityLink>(TEntity entity)
             where TEntityKanban : EntityKanban<TEntity, TEntityLink>, new()

+ 0 - 45
prs.stores/JobBillOfMaterialsItemStore.cs

@@ -1,45 +0,0 @@
-using System;
-using System.Linq;
-using System.Reactive;
-using Comal.Classes;
-using InABox.Core;
-
-namespace Comal.Stores
-{
-    public class JobBillOfMaterialsItemStore : BaseStore<JobBillOfMaterialsItem>
-    {
-        protected override void BeforeSave(JobBillOfMaterialsItem entity)
-        {
-            base.BeforeSave(entity);
-            EnsureJobMaterials(entity.Product, entity.Job, entity.Style, entity.Dimensions);
-        }
-
-        protected override void AfterSave(JobBillOfMaterialsItem entity)
-        {
-            base.AfterSave(entity);
-            CleanupJobMaterials(entity.ID, entity.Product, entity.Job, entity.Style, entity.Dimensions, false);
-        }
-        
-        protected override void AfterDelete(JobBillOfMaterialsItem entity)
-        {
-            base.AfterDelete(entity);
-            
-            var delete = Provider.Query(
-                new Filter<JobBillOfMaterialsItem>(x => x.ID).IsEqualTo(entity.ID),
-                new Columns<JobBillOfMaterialsItem>(x => x.ID)
-                    .Add(x => x.Product.ID)
-                    .Add(x => x.Job.ID)
-                    .Add(x => x.Style.ID)
-                    .Add(x => x.Dimensions.Unit.ID)
-                    .Add(x => x.Dimensions.Length)
-                    .Add(x => x.Dimensions.Width)
-                    .Add(x => x.Dimensions.Height)
-                    .Add(x => x.Dimensions.Weight)
-            ).Rows.FirstOrDefault()?.ToObject<JobBillOfMaterialsItem>();
-            
-            if (delete != null)
-                CleanupJobMaterials(delete.ID, delete.Product, delete.Job, delete.Style, delete.Dimensions, true);
-
-        }
-    }
-}

+ 0 - 43
prs.stores/JobMaterialRequisitionItemStore.cs

@@ -1,43 +0,0 @@
-using System;
-using System.Linq;
-using Comal.Classes;
-using InABox.Core;
-
-namespace Comal.Stores
-{
-    public class JobMaterialRequisitionItemStore : BaseStore<JobRequisitionItem>
-    {
-        protected override void BeforeSave(JobRequisitionItem entity)
-        {
-            base.BeforeSave(entity);
-            EnsureJobMaterials(entity.Product, entity.Requisition.Job, entity.Style, entity.Dimensions);
-        }
-
-        protected override void AfterSave(JobRequisitionItem entity)
-        {
-            base.AfterSave(entity);
-            CleanupJobMaterials(entity.ID, entity.Product, entity.Requisition.Job, entity.Style, entity.Dimensions, false);
-        }
-
-        protected override void AfterDelete(JobRequisitionItem entity)
-        {
-            base.AfterDelete(entity);
-            
-            var delete = Provider.Query(
-                new Filter<JobRequisitionItem>(x => x.ID).IsEqualTo(entity.ID),
-                new Columns<JobRequisitionItem>(x => x.ID)
-                    .Add(x => x.Product.ID)
-                    .Add(x => x.Requisition.Job.ID)
-                    .Add(x => x.Style.ID)
-                    .Add(x => x.Dimensions.Unit.ID)
-                    .Add(x => x.Dimensions.Length)
-                    .Add(x => x.Dimensions.Width)
-                    .Add(x => x.Dimensions.Height)
-                    .Add(x => x.Dimensions.Weight)
-            ).Rows.FirstOrDefault()?.ToObject<JobRequisitionItem>();
-            
-            CleanupJobMaterials(delete.ID, delete.Product, delete.Requisition.Job, delete.Style, delete.Dimensions, true);
-
-        }
-    }
-}

+ 0 - 3
prs.stores/PRSStores.projitems

@@ -35,8 +35,6 @@
     <Compile Include="$(MSBuildThisFileDirectory)InvoiceLineStore.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)InvoiceReceiptStore.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)InvoiceStore.cs" />
-    <Compile Include="$(MSBuildThisFileDirectory)JobBillOfMaterialsItemStore.cs" />
-    <Compile Include="$(MSBuildThisFileDirectory)JobMaterialRequisitionItemStore.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)JobMaterialRequsitionStore.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)JobRequisitionStore.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)JobStageStore.cs" />
@@ -62,7 +60,6 @@
     <Compile Include="$(MSBuildThisFileDirectory)StandardLeaveStore.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)StockAreaStore.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)StockLocationStore.cs" />
-    <Compile Include="$(MSBuildThisFileDirectory)StockMovementStore.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)StockWarehouseStore.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)StoreUtils.cs" />
     <Compile Include="$(MSBuildThisFileDirectory)SupplierProductStore.cs" />

+ 38 - 45
prs.stores/PurchaseOrderItemStore.cs

@@ -61,7 +61,7 @@ namespace Comal.Stores
             });
             movementtask.Start();
 
-            var producttask = new Task<CoreRow>(() =>
+            var producttask = new Task<CoreRow?>(() =>
             {
                 return Provider.Query(
                     new Filter<Product>(x => x.ID).IsEqualTo(entity.Product.ID),
@@ -86,7 +86,9 @@ namespace Comal.Stores
                         x => x.Dimensions.Unit.Formula,
                         x => x.Dimensions.Unit.Format,
                         x => x.Dimensions.Unit.Code,
-                        x => x.Dimensions.Unit.Description
+                        x => x.Dimensions.Unit.Description,
+                        x => x.TotalStock,
+                        x => x.AverageCost
                     )
                 ).Rows.FirstOrDefault();
             });
@@ -107,6 +109,12 @@ namespace Comal.Stores
             var productrow = producttask.Result;
             var defaultlocations = locationtask.Result;
 
+            if (entity.Qty == 0)
+            {
+                Logger.Send(LogType.Information, UserID, "PurchaseOrderItem Qty is blank!");
+                return;
+            }
+
             if (productrow == null)
             {
                 Logger.Send(LogType.Information, UserID, "Cannot Find PurchaseOrderItem.Product.ID!");
@@ -118,7 +126,7 @@ namespace Comal.Stores
                 Logger.Send(LogType.Information, UserID, "PurchaseOrderItem.Product is marked as Non Stock!");
                 return;
             }
-
+            
             if (!locationValid)
             {
                 Logger.Send(LogType.Information, UserID, "PurchaseOrderItem.Location.ID is blank!");
@@ -158,8 +166,7 @@ namespace Comal.Stores
                     return;
                 }
             }
-
-
+            
             if (
                 (entity.Dimensions.Unit.ID == Guid.Empty)
                 && (entity.Dimensions.Height == 0)
@@ -173,6 +180,21 @@ namespace Comal.Stores
             }
 
             var product = productrow.ToObject<Product>();
+            
+            var poqty = entity.Qty * (Math.Abs(entity.Dimensions.Value) > 0.0001F ? entity.Dimensions.Value : 1.0F);
+            var pocost = entity.Cost * entity.Qty;
+            
+            var totalqty = product.TotalStock + poqty;
+            var totalcost = (product.TotalStock * product.AverageCost) + pocost;
+
+            var averagecost = Math.Abs(totalqty) > 0.0001F
+                ? totalcost / totalqty
+                : pocost / poqty;
+            if (Math.Abs(averagecost - product.AverageCost) > 0.0001F)
+            {
+                product.AverageCost = averagecost;
+                FindSubStore<Product>().Save(product,"Updated Average Cost");
+            }
 
             foreach (var movement in movements)
             {
@@ -189,22 +211,16 @@ namespace Comal.Stores
                 movement.Style.Description = entity.Style.Description;
                 movement.Notes = string.Format("Received on PO {0}", entity.PurchaseOrderLink.PONumber);
                 movement.Cost = entity.Cost;
-                movement.Dimensions.UnitSize = product.Dimensions.UnitSize;
-                movement.Dimensions.Unit.ID = product.Dimensions.Unit.ID;
-                movement.Dimensions.Height = product.Dimensions.Height;
-                movement.Dimensions.Length = product.Dimensions.Length;
-                movement.Dimensions.Width = product.Dimensions.Width;
-                movement.Dimensions.Weight = product.Dimensions.Weight;
-                movement.Dimensions.Quantity = product.Dimensions.Quantity;
-                movement.Dimensions.Unit.HasHeight = product.Dimensions.Unit.HasHeight;
-                movement.Dimensions.Unit.HasWidth = product.Dimensions.Unit.HasWidth;
-                movement.Dimensions.Unit.HasLength = product.Dimensions.Unit.HasLength;
-                movement.Dimensions.Unit.HasWeight = product.Dimensions.Unit.HasWeight;
-                movement.Dimensions.Unit.HasQuantity = product.Dimensions.Unit.HasQuantity;
-                movement.Dimensions.Unit.Formula = product.Dimensions.Unit.Formula;
-                movement.Dimensions.Unit.Format = product.Dimensions.Unit.Format;
-                movement.Dimensions.Unit.Code = product.Dimensions.Unit.Code;
-                movement.Dimensions.Unit.Description = product.Dimensions.Unit.Description;
+                movement.Dimensions.Unit.ID = entity.Dimensions.Unit.ID;
+                movement.Dimensions.Height = entity.Dimensions.Height;
+                movement.Dimensions.Length = entity.Dimensions.Length;
+                movement.Dimensions.Width = entity.Dimensions.Width;
+                movement.Dimensions.Weight = entity.Dimensions.Weight;
+                movement.Dimensions.Quantity = entity.Dimensions.Quantity;
+                movement.Dimensions.UnitSize = entity.Dimensions.UnitSize;
+                movement.Dimensions.Value = entity.Dimensions.Value;
+                movement.Dimensions.UnitSize = entity.Dimensions.UnitSize;
+
             }
 
             var updates = movements.Where(x => x.IsChanged());
@@ -223,12 +239,7 @@ namespace Comal.Stores
             if (movements.Any())
                 FindSubStore<StockMovement>().Delete(movements, "Purchase Order Item marked as Unreceived");
         }
-
-        protected override void BeforeSave(PurchaseOrderItem entity)
-        {
-            base.BeforeSave(entity);
-            EnsureJobMaterials(entity.Product, entity.Job, entity.Style, entity.Dimensions);
-        }
+        
 
         protected override void AfterSave(PurchaseOrderItem entity)
         {
@@ -241,10 +252,6 @@ namespace Comal.Stores
                 UpdateStockMovements(entity);
                 UpdateJobRequiItems(entity);
             }
-            //}
-
-            CleanupJobMaterials(entity.ID, entity.Product, entity.Job, entity.Style, entity.Dimensions, false);
-
         }
 
         private void UpdateJobRequiItems(PurchaseOrderItem entity)
@@ -267,20 +274,6 @@ namespace Comal.Stores
         {
             base.BeforeDelete(entity);
             DeleteStockMovements(entity);
-
-            var delete = Provider.Query(
-                new Filter<PurchaseOrderItem>(x => x.ID).IsEqualTo(entity.ID),
-                new Columns<PurchaseOrderItem>(x => x.ID)
-                    .Add(x => x.Product.ID)
-                    .Add(x => x.Job.ID)
-                    .Add(x => x.Style.ID)
-                    .Add(x => x.Dimensions.Unit.ID)
-                    .Add(x => x.Dimensions.Length)
-                    .Add(x => x.Dimensions.Width)
-                    .Add(x => x.Dimensions.Height)
-                    .Add(x => x.Dimensions.Weight)
-            ).Rows.FirstOrDefault()?.ToObject<PurchaseOrderItem>();
-            CleanupJobMaterials(delete.ID, delete.Product, delete.Job, delete.Style, delete.Dimensions, true);
         }
 
         protected override void AfterDelete(PurchaseOrderItem entity)

+ 0 - 160
prs.stores/StockMovementStore.cs

@@ -1,160 +0,0 @@
-using System;
-using System.Linq;
-using Comal.Classes;
-using InABox.Core;
-
-namespace Comal.Stores
-{
-    
-    public class StockMovementStore : BaseStore<StockMovement>
-    {
-        protected override void BeforeSave(StockMovement entity)
-        {
-            base.BeforeSave(entity);
-            EnsureHoldings(entity);
-            EnsureJobMaterials(entity.Product, entity.Job, entity.Style, entity.Dimensions);
-        }
-
-        protected override void AfterSave(StockMovement entity)
-        {
-            base.AfterSave(entity);
-            CleanupHoldings(entity, false);
-            CleanupJobMaterials(entity.ID, entity.Product, entity.Job, entity.Style, entity.Dimensions, true);
-        }
-
-        protected override void BeforeDelete(StockMovement entity)
-        {
-            base.BeforeDelete(entity);
-            var delete = Provider.Query(
-                new Filter<StockMovement>(x => x.ID).IsEqualTo(entity.ID),
-                new Columns<StockMovement>(x => x.ID)
-                    .Add(x => x.Product.ID)
-                    .Add(x => x.Location.ID)
-                    .Add(x => x.Job.ID)
-                    .Add(x => x.Style.ID)
-                    .Add(x => x.Dimensions.Unit.ID)
-                    .Add(x => x.Dimensions.Length)
-                    .Add(x => x.Dimensions.Width)
-                    .Add(x => x.Dimensions.Height)
-                    .Add(x => x.Dimensions.Weight)
-            ).Rows.FirstOrDefault()?.ToObject<StockMovement>();
-                
-            CleanupHoldings(delete, true);
-            CleanupJobMaterials(entity.ID, delete.Product, delete.Job, delete.Style, delete.Dimensions, true);
-        }
-
-        private void EnsureHoldings(StockMovement entity)
-        {
-            // var holdings = Provider.List(
-            //     new Filter<StockHolding>(x => x.Product.ID).IsEqualTo(entity.Product.ID)
-            //         .And(x => x.Location.ID).IsEqualTo(entity.Location.ID)
-            //         .And(x => x.Job.ID).IsEqualTo(entity.Job.ID)
-            //         .And(x => x.Style.ID).IsEqualTo(entity.Style.ID)
-            //         .And(x => x.Dimensions.Unit.ID).IsEqualTo(entity.Dimensions.Unit.ID)
-            //         .And(x => x.Dimensions.Length).IsEqualTo(entity.Dimensions.Length)
-            //         .And(x => x.Dimensions.Width).IsEqualTo(entity.Dimensions.Width)
-            //         .And(x => x.Dimensions.Height).IsEqualTo(entity.Dimensions.Height)
-            //         .And(x => x.Dimensions.Weight).IsEqualTo(entity.Dimensions.Weight)
-            //     ,
-            //     new Columns<StockHolding>(x => x.ID)
-            // );
-            // if (!holdings.Any())
-            // {
-            //     var holding = new StockHolding();
-            //     holding.Product.ID = entity.Product.ID;
-            //     holding.Location.ID = entity.Location.ID;
-            //     holding.Job.ID = entity.Job.ID;
-            //     holding.Style.ID = entity.Style.ID;
-            //     holding.Dimensions.CopyFrom(entity.Dimensions);
-            //     Provider.Save(holding);
-            // }
-            //
-            // var jobmaterials = Provider.List(
-            //     new Filter<JobMaterial>(x => x.Product.ID).IsEqualTo(entity.Product.ID)
-            //         .And(x => x.Job.ID).IsEqualTo(entity.Job.ID)
-            //         .And(x => x.Style.ID).IsEqualTo(entity.Style.ID)
-            //         .And(x => x.Dimensions.Unit.ID).IsEqualTo(entity.Dimensions.Unit.ID)
-            //         .And(x => x.Dimensions.Length).IsEqualTo(entity.Dimensions.Length)
-            //         .And(x => x.Dimensions.Width).IsEqualTo(entity.Dimensions.Width)
-            //         .And(x => x.Dimensions.Height).IsEqualTo(entity.Dimensions.Height)
-            //         .And(x => x.Dimensions.Weight).IsEqualTo(entity.Dimensions.Weight)
-            //     ,
-            //     new Columns<JobMaterial>(x => x.ID)
-            // );
-            // if (!jobmaterials.Any())
-            // {
-            //     var material = new JobMaterial();
-            //     material.Product.ID = entity.Product.ID;
-            //     material.Job.ID = entity.Job.ID;
-            //     material.Style.ID = entity.Style.ID;
-            //     material.Dimensions.CopyFrom(entity.Dimensions);
-            //     Provider.Save(material);
-            // }
-        }
-
-        private void CleanupHoldings(StockMovement entity, bool delete)
-        {
-            // var isNew = !delete && entity.HasOriginalValue(x => x.ID) && entity.Product.GetOriginalValue(x => x.ID) == Guid.Empty;
-            // if (isNew)
-            //     return;
-            // var hasProduct = !delete && entity.Product.HasOriginalValue(x=>x.ID);
-            // var hasLocation = !delete && entity.Location.HasOriginalValue(x=>x.ID);
-            // var hasJob = !delete && entity.Job.HasOriginalValue(x=>x.ID);
-            // var hasStyle = !delete && entity.Style.HasOriginalValue(x=>x.ID);
-            // var hasDimensionUnit = !delete && entity.Dimensions.Unit.HasOriginalValue(x=>x.ID);
-            // var hasLength = !delete && entity.Dimensions.HasOriginalValue(x=>x.Length);
-            // var hasWidth = !delete && entity.Dimensions.HasOriginalValue(x=>x.Width);
-            // var hasHeight = !delete && entity.Dimensions.HasOriginalValue(x=>x.Height);
-            // var hasWeight = !delete && entity.Dimensions.HasOriginalValue(x=>x.Weight);
-            //
-            // if (delete || hasProduct || hasLocation || hasJob || hasStyle || hasDimensionUnit || hasLength || hasWidth || hasHeight || hasWeight)
-            // {
-            //     var product = hasProduct ? entity.Product.GetOriginalValue(x=>x.ID) : entity.Product.ID;
-            //     var location = hasLocation ? entity.Location.GetOriginalValue(x=>x.ID) : entity.Location.ID;
-            //     var job = hasJob ? entity.Job.GetOriginalValue(x=>x.ID) : entity.Job.ID;
-            //     var style = hasStyle ? entity.Style.GetOriginalValue(x=>x.ID) : entity.Style.ID;
-            //     var dimensionUnit = hasDimensionUnit ? entity.Dimensions.Unit.GetOriginalValue(x=>x.ID) : entity.Dimensions.Unit.ID;
-            //     var length = hasLength ? entity.Dimensions.GetOriginalValue(x=>x.Length) : entity.Dimensions.Length;
-            //     var width = hasWidth ? entity.Dimensions.GetOriginalValue(x=>x.Width) : entity.Dimensions.Width;
-            //     var height = hasHeight ? entity.Dimensions.GetOriginalValue(x=>x.Height) : entity.Dimensions.Height;
-            //     var weight = hasWeight ? entity.Dimensions.GetOriginalValue(x=>x.Weight) : entity.Dimensions.Weight;
-            //     
-            //     var movements = Provider.Query(
-            //         new Filter<StockMovement>(X => X.ID).IsNotEqualTo(entity.ID)
-            //             .And(x => x.Product.ID).IsEqualTo(product)
-            //             .And(x=>x.Location.ID).IsEqualTo(location)
-            //             .And(x => x.Job.ID).IsEqualTo(job)
-            //             .And(x => x.Style.ID).IsEqualTo(style)
-            //             .And(x => x.Dimensions.Unit.ID).IsEqualTo(dimensionUnit)
-            //             .And(x => x.Dimensions.Length).IsEqualTo(length)
-            //             .And(x => x.Dimensions.Width).IsEqualTo(width)
-            //             .And(x => x.Dimensions.Height).IsEqualTo(height)
-            //             .And(x => x.Dimensions.Weight).IsEqualTo(weight),
-            //         new Columns<StockMovement>(x => x.Location.ID)
-            //     );
-            //     
-            //     if (!movements.Rows.Any())
-            //     {
-            //         var holdings = Provider.Query(
-            //             new Filter<StockHolding>(x => x.Product.ID).IsEqualTo(product)
-            //                 .And(x => x.Location.ID).IsEqualTo(location)
-            //                 .And(x => x.Job.ID).IsEqualTo(job)
-            //                 .And(x => x.Style.ID).IsEqualTo(style)
-            //                 .And(x => x.Dimensions.Unit.ID).IsEqualTo(dimensionUnit)
-            //                 .And(x => x.Dimensions.Length).IsEqualTo(length)
-            //                 .And(x => x.Dimensions.Width).IsEqualTo(width)
-            //                 .And(x => x.Dimensions.Height).IsEqualTo(height)
-            //                 .And(x => x.Dimensions.Weight).IsEqualTo(weight),
-            //             new Columns<StockHolding>(x => x.ID)
-            //         ).Rows.Select(r => r.ToObject<StockHolding>());
-            //
-            //         // should only ever be one, but lets clean up anyways
-            //         foreach (var holding in holdings)
-            //             Provider.Delete(holding);
-            //     }
-            //     
-            // }
-        }
-        
-    }
-}