using System; using System.Collections.Generic; using System.Configuration; using System.Data.Common; using System.Data.Entity; using System.Data.SqlClient; using System.Diagnostics; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Text; using System.Threading; using System.Threading.Tasks; using CAPI.Custom.Data; using CAPI.Custom.Entities; using CAPI.Custom.Security; namespace CAPI.Custom { public class BusinessUtils { public static ICustomPrincipal SetUser(int userId) { var principal = new CustomPrincipal(userId.ToString()) { Id = userId }; Thread.CurrentPrincipal = principal; return User; } /// /// Get User Identity from current thread /// public static ICustomPrincipal User => (Thread.CurrentPrincipal as ICustomPrincipal) ?? new CustomPrincipal(""); public static readonly DateTime SqlDateTimeMinValue = new DateTime(1900, 1, 1); public static string FormatDateToString(DateTime value) { string format = ConfigurationManager.AppSettings["DisplayDate"] ?? "dd/MM/yyyy"; return value.ToString(format); } public static decimal GetMargin(decimal? costPrice, decimal? newSellingPrice) { decimal cost = costPrice.GetValueOrDefault(), selling = newSellingPrice.GetValueOrDefault(), margin = 0m; if (selling != 0m) { margin = ((selling - cost) / selling) * 100m; } return margin; } public static decimal GetSellingPrice(decimal? costPrice, decimal? newMargin) { decimal cost = costPrice.GetValueOrDefault(), selling = 0m, margin = newMargin.GetValueOrDefault(); //selling = cost * (1 + (margin / 100)); decimal dividedBy = 1m - (margin / 100m); if (dividedBy != 0m) { selling = cost / dividedBy; } return selling; } public static TEntity Create(TEntity entity) where TEntity : class, IEntity { using (var db = new QuotesContext()) { db.Set().Attach(entity); db.Entry(entity).State = EntityState.Added; db.SaveChanges(); } return entity; } public static int Delete(TEntity entity) where TEntity : class, IEntity { int result = 0; using(var db = new QuotesContext()) { //var entityId = entity.GetPropertyValue("recId"); db.Set().Attach(entity); db.Entry(entity).State = EntityState.Deleted; //var temp = db.Set().FirstOrDefault(p => p.itemID == entity.itemID); //db.Set().Remove(temp); result = db.SaveChanges(); } return result; } public static TEntity Update(TEntity entity) where TEntity : class, IEntity { using (var db = new QuotesContext()) { db.Set().Attach(entity); db.Entry(entity).State = EntityState.Modified; db.SaveChanges(); } return entity; } public static TEntity Upsert(TEntity entity) where TEntity : class, IEntity { // new entity if (entity.recId == 0) { return Create(entity); } else { return Update(entity); } } public static string GetNextCEPNumber() { int value = 0; string result = string.Empty; using (var db = new QuotesContext()) { var surfaceField = (from s in db.Surfaces join f in db.SurfaceFields on s.recId equals f.surfaceId where s.isActive.Value && f.isActive.Value && s.name == "PartsMaster" && f.surfaceFieldName == "PartsMaster_PartsMasterDetails_PartsMasterCEPNumber" select f) .FirstOrDefault(); value = surfaceField.controlledValue.TryParseInt().GetValueOrDefault() + 1; db.Database.ExecuteSqlCommand($"UPDATE pal_SurfaceField set controlledValue = {value} WHERE recId = {surfaceField.recId}"); result = $"{surfaceField.controlPrefix}{value}"; } return result; } public static int GetNextSalesInvoiceNumber() { using (var db = new QuotesContext()) { var setup = db.Setup; int invoiceNo = db.Database.SqlQuery("sp_GetInvoiceNoSales @ItemType", new SqlParameter("@ItemType", "QT")) .FirstOrDefault(); // CVH 2016-09-14 Renamed to Next Num, updated with each transaction save, // result and NextNum should technically always be equal int saleQTENextNum = setup.saleQTENextNum.GetValueOrDefault(); if (invoiceNo < saleQTENextNum)//then use the start number invoiceNo = saleQTENextNum; return invoiceNo; } } public static int GetNextPurchaseOrderNumber() { int startAt = 201642 + 1; int created = 0; using(var db = QuotesContext.Create()) { created = db.PurchaseOrders.Count(); } return startAt + created; } /// /// Used to set QuoteItem.QuoteItems_QuoteItems_QuoteItemsSupplierSequenceNumber /// using the supplier name /// /// /// public static int GetQuoteItemSupplierSequence(string supplierName) { /* Item order logic: 1. CEP Inventory (always first) 2. Then Surplus Warehouse 3. Then remaining suppliers in Alpha Order UPDATE: CEP-120 display INVENTORY items first on the master group list (above CEP Inventory) Item order logic: 1. INVENTORY (always first) 2. CEP Inventory 3. Then Surplus Warehouse 4. Then remaining suppliers in Alpha Order */ var order = new string[] { "INVENTORY", "CEP Inventory", "SURPLUS WAREHOUSE" }; var orderIndex = Array.IndexOf(order, supplierName); if (orderIndex < 0) orderIndex = order.Length + 1; return orderIndex; //return "CEP Inventory".EqualsIgnoreCase(supplierName) ? 1 // : "SURPLUS WAREHOUSE".EqualsIgnoreCase(supplierName) ? 2 // : 3; } /// /// Get the Items of a Quote applying the correct sorting /// /// quote.itemID /// //public static IEnumerable GetQuoteItems(int quoteId) //{ // List quoteItems = new List(); // using (var db = new QuotesContext()) // { // db.QuotesItems_RemoveMatchingSurplusWarehouseQuoteItems(quoteId); // var quote = db.vQuotes.Where(p => p.itemID == quoteId) // .Select(p => new // { // IsFinalized = p.IsFinalized.HasValue ? p.IsFinalized.Value : false // }) // .SingleOrDefault(); // var sortedMasterNumbers = db.QuoteRequestItems // .GetByParentId(quoteId) // .OrderBy(p => p.QuoteRequestItems_QuoteRequestItems_QuoteRequestItemsItemSequence) // .Select(p => p.QuoteRequestItems_QuoteRequestItems_QuoteRequestItemsMasterNumber) // .ToArray(); // quoteItems = db.QuoteItems // .Where(p => p.ParentSurfaceItemId == quoteId) // .ToList(); // if (!quote.IsFinalized) // { // var needsPriceCheck = quoteItems.Any(p => !p.IsCATList.Value && !(p.PriceCheckIsChecked ?? false)); // var needsCatListCost = quoteItems.Any(p => !p.IsCATList.Value && !p.CATListCostPrice.HasValue); // if (needsPriceCheck) // { // db.QuoteItems_CheckPreviouslyQuotedPrice(quoteId); // } // if (needsCatListCost) // { // db.QuoteItems_ApplyCATListPrice(quoteId); // } // if (needsCatListCost || needsPriceCheck) // { // db.SaveChanges(); // quoteItems = db.QuoteItems // .Where(p => p.ParentSurfaceItemId == quoteId) // .ToList(); // } // } // quoteItems = quoteItems // .OrderBy(p => Array.IndexOf(sortedMasterNumbers, p.QuoteItems_QuoteItems_PartsMasterPartNumber)) // //.ThenBy(p => p.QuoteItems_QuoteItems_QuoteItemsSequenceNumber) // .ThenBy(p => p.QuoteItems_QuoteItems_PartsMasterPartNumber) // .ThenBy(p => GetQuoteItemSupplierSequence(p.QuoteItems_QuoteItems_QuoteItemsSupplier) /* p.QuoteItems_QuoteItems_QuoteItemsSupplierSequenceNumber */) // .ThenBy(p => p.QuoteItems_QuoteItems_QuoteItemsSupplier) // .ToList(); // } // return quoteItems; //} private static object _exchangeRatesLock = new object(); private static Dictionary _exchangeRates = new Dictionary(); private static string[] _zarExchangeRates = new string[] { "", "ZAR" }; /// /// Converts ammount from ZAR to other Currency /// /// ZAR ammount /// Currency to convert to /// public static decimal ApplyExchangeRate(decimal value, string currency) { if (_zarExchangeRates.Contains(currency)) { return value; } else { if (!_exchangeRates.ContainsKey(currency)) { using (var db = new QuotesContext()) { var exRateItem = db.ExchangeRates .Where(p => p.ForexCurrency == currency) .Select(p => new { Currency = p.ForexCurrency, Rate = p.BuyExchangeRate }) .FirstOrDefault(); if (exRateItem.IsNotNull()) { var rate = exRateItem.Rate.TryParseDecimal().GetValueOrDefault(); lock (_exchangeRatesLock) { _exchangeRates.Add(exRateItem.Currency, rate); } } } } var exRate = _exchangeRates[currency]; // make 123.4567 -> 123.45 var result = Math.Round((value * exRate), 2, MidpointRounding.ToEven); return result; } } #region temp private static string LogFilePath = @"c:\temp\log.log"; public static void Log(string message) { if (System.IO.File.Exists(LogFilePath)) { System.IO.File.AppendAllLines(LogFilePath, new string[] { "----------------------------------", message }); } } #endregion #region Error Handling public static int HandleException(Exception ex, string message = null, [CallerMemberName] string memberName = "", [CallerFilePath] string filePath = "", [CallerLineNumber] int lineNumber = 0) { int userId = User.Id; int frameIndex = 1; StackTrace stackTrace = new StackTrace(); StackFrame stackFrame = stackTrace.GetFrame(frameIndex); MethodBase methodBase = stackFrame.GetMethod(); string className = methodBase.ReflectedType.Name; string msg = message ?? ex.Message ?? ex.GetType().Name; string trace = ex.StackTrace ?? $"File: {filePath}, Line: {lineNumber}"; string query = $@"INSERT INTO pal_Exceptions ([ClassName], [FunctionName], [Exception], [UserID], [DateLogged]) VALUES (@className, @methodName, 'Message: ' + @message + ' | StackTrace: ' + @stacktTrace, @userId, getdate())"; int result = 0; using (var db = new QuotesContext()) { result = db.Database.ExecuteSqlCommand(query, new SqlParameter("@className", className), new SqlParameter("@methodName", memberName), new SqlParameter("@message", msg), new SqlParameter("@stacktTrace", trace), new SqlParameter("@userId", userId)); } return result; } #endregion #region Quote Processing Helpers //public static PartsMaster CreatePartsMasterFromPriceListItem(ISupplierPricelistPart priceListPart) //{ // return Create(new PartsMaster // { // AdditionalDescription = priceListPart.AdditionalDescription, // CEPNumber = GetNextCEPNumber(), // Description = priceListPart.Description, // ItemVetted = YesNo.No, // PartNumber = priceListPart.PartNumber, // MasterNumber = priceListPart.PartNumber, // WeightKG = priceListPart.WeightKG.GetValueOrDefault(), // WeightLBS = priceListPart.WeightLBS.GetValueOrDefault(), // }); //} //public static PartsAlternate CreateAlternateFromMaster(PartsMaster partsMaster) //{ // return Create(new PartsAlternate // { // CEPNumber = partsMaster.CEPNumber, // AlternateNumber = partsMaster.MasterNumber, // PartNumber = partsMaster.MasterNumber, // ParentSurfaceItemId = partsMaster.itemID // }); //} //public static PartsMaster CreatePartsMasterFromPartNumber(string partNumber) //{ // return Create(new PartsMaster // { // CEPNumber = GetNextCEPNumber(), // ItemVetted = YesNo.No, // No // MasterNumber = partNumber, // PartNumber = partNumber // }); //} #endregion } }