diff --git a/src/Dynamicweb.DataIntegration.Providers.OrderProvider.csproj b/src/Dynamicweb.DataIntegration.Providers.OrderProvider.csproj index 11b9be0..9e8d796 100644 --- a/src/Dynamicweb.DataIntegration.Providers.OrderProvider.csproj +++ b/src/Dynamicweb.DataIntegration.Providers.OrderProvider.csproj @@ -1,6 +1,6 @@  - 10.8.2 + 10.8.3 1.0.0.0 Order Provider Order Provider diff --git a/src/OrderProvider.cs b/src/OrderProvider.cs index d43ea75..69c544f 100644 --- a/src/OrderProvider.cs +++ b/src/OrderProvider.cs @@ -8,7 +8,6 @@ using Dynamicweb.Extensibility.Editors; using Dynamicweb.Logging; using System; -using System.Collections; using System.Collections.Generic; using System.Data; using System.Data.SqlClient; @@ -24,9 +23,11 @@ public class OrderProvider : BaseSqlProvider, IParameterOptions, ISource, IDesti { private const string OrderCustomerAccessUserExternalId = "OrderCustomerAccessUserExternalId"; private const string OrderLineCalculatedDiscountPercentage = "OrderLineCalculatedDiscountPercentage"; + private const string OrderIntegrationOrderId = "OrderIntegrationOrderId"; private Job job = null; private Schema Schema { get; set; } private string SqlConnectionString { get; set; } + private string SourceColumnNameForDestinationOrderIntegrationOrderId = string.Empty; private string SourceColumnNameForDestinationOrderCustomerAccessUserId = string.Empty; private ColumnMapping OrderShippingMethodCodeMapping = null; private ColumnMapping OrderPaymentMethodCodeMapping = null; @@ -118,7 +119,11 @@ public override Schema GetOriginalDestinationSchema() if (table.Name == "EcomOrders") { table.AddColumn(new SqlColumn(OrderCustomerAccessUserExternalId, typeof(string), SqlDbType.NVarChar, table, -1, false, false, true)); - } + } + else if (table.Name == "EcomOrderLines") + { + table.AddColumn(new SqlColumn(OrderIntegrationOrderId, typeof(string), SqlDbType.NVarChar, table, -1, false, false, true)); + } } return result; @@ -357,11 +362,11 @@ public override bool RunJob(Job job) if (Connection.State != ConnectionState.Open) Connection.Open(); - AddMappingsToJobThatNeedsToBeThereForMoveToMainTables(job); foreach (Mapping mapping in job.Mappings) { if (mapping.Active) { + AddMappingsThatNeedsToBeThereForMoveToMainTables(mapping); Logger.Log("Starting import to temporary table for " + mapping.DestinationTable.Name + "."); using (var reader = job.Source.GetReader(mapping)) { @@ -380,11 +385,11 @@ public override bool RunJob(Job job) writers.Add(writer); } Logger.Log("Finished import to temporary table for " + mapping.DestinationTable.Name + "."); + RemoveColumnMappingsThatShouldBeSkippedInMoveToMainTables(mapping); } } sourceRow = null; - RemoveColumnMappingsFromJobThatShouldBeSkippedInMoveToMainTables(job); sqlTransaction = Connection.BeginTransaction(); foreach (OrderDestinationWriter writer in writers) { @@ -443,53 +448,87 @@ IEnumerable IParameterOptions.GetParameterOptions(string parame return result; } - private void AddMappingsToJobThatNeedsToBeThereForMoveToMainTables(Job job) + private void AddMappingsThatNeedsToBeThereForMoveToMainTables(Mapping mapping) { - Mapping mapping = job.Mappings.Find(m => m.DestinationTable.Name == "EcomOrders"); - if (mapping != null) + if (string.IsNullOrEmpty(mapping?.DestinationTable?.Name)) return; + + switch (mapping.DestinationTable.Name) { - var columnMappings = mapping.GetColumnMappings(); - if (columnMappings.Find(cm => string.Compare(cm.DestinationColumn.Name, OrderCustomerAccessUserExternalId, true) == 0) != null) + case "EcomOrders": + HandleMappingsForOrders(mapping); + break; + case "EcomOrderLines": + HandleMappingsForOrderLines(mapping); + break; + default: + break; + } + } + private void HandleMappingsForOrderLines(Mapping mapping) + { + var columnMappings = mapping.GetColumnMappings(); + if (columnMappings.Find(cm => string.Compare(cm.DestinationColumn.Name, OrderIntegrationOrderId, true) == 0) != null) + { + var orderIntegrationOrderIdMapping = columnMappings.Find(cm => string.Compare(cm.DestinationColumn.Name, "OrderLineOrderId", true) == 0); + if (orderIntegrationOrderIdMapping == null) { - var OrderCustomerAccessUserIdMapping = columnMappings.Find(cm => string.Compare(cm.DestinationColumn.Name, "OrderCustomerAccessUserId", true) == 0); - if (OrderCustomerAccessUserIdMapping == null) - { - var randomColumn = job.Source.GetSchema().GetTables().First(obj => obj.Columns.Count > 0).Columns.First(); - SourceColumnNameForDestinationOrderCustomerAccessUserId = randomColumn.Name; - mapping.AddMapping(randomColumn, job.Destination.GetSchema().GetTables().Find(t => t.Name == "EcomOrders").Columns.Find(c => string.Compare(c.Name, "OrderCustomerAccessUserId", true) == 0), true); - } - else - { - if (OrderCustomerAccessUserIdMapping.SourceColumn != null) - { - SourceColumnNameForDestinationOrderCustomerAccessUserId = OrderCustomerAccessUserIdMapping.SourceColumn.Name; - } - } + var randomColumn = mapping.SourceTable.Columns.First(); + SourceColumnNameForDestinationOrderIntegrationOrderId = randomColumn.Name; + mapping.AddMapping(randomColumn, mapping.DestinationTable.Columns.Find(c => string.Compare(c.Name, "OrderLineOrderId", true) == 0), true); } - var ordersTable = job.Destination.GetSchema().GetTables().FirstOrDefault(t => string.Equals(t.Name, "EcomOrders", StringComparison.OrdinalIgnoreCase)); - if (ordersTable is not null && - columnMappings.FirstOrDefault(cm => cm.Active && string.Equals(cm.DestinationColumn.Name, "OrderId", StringComparison.OrdinalIgnoreCase)) is not null) + else { - OrderShippingMethodCodeMapping = columnMappings.FirstOrDefault(cm => cm.Active && string.Equals(cm.DestinationColumn.Name, "OrderShippingMethodCode", StringComparison.OrdinalIgnoreCase)); - if (OrderShippingMethodCodeMapping is not null) + if (orderIntegrationOrderIdMapping.SourceColumn != null) { - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethodId", StringComparison.OrdinalIgnoreCase))); - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethod", StringComparison.OrdinalIgnoreCase))); - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethodDescription", StringComparison.OrdinalIgnoreCase))); - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethodAgentCode", StringComparison.OrdinalIgnoreCase))); - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethodAgentServiceCode", StringComparison.OrdinalIgnoreCase))); - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingProviderData", StringComparison.OrdinalIgnoreCase))); + SourceColumnNameForDestinationOrderIntegrationOrderId = orderIntegrationOrderIdMapping.SourceColumn.Name; } - OrderPaymentMethodCodeMapping = columnMappings.FirstOrDefault(cm => cm.Active && string.Equals(cm.DestinationColumn.Name, "OrderPaymentMethodCode", StringComparison.OrdinalIgnoreCase)); - if (OrderPaymentMethodCodeMapping is not null) + } + } + } + + private void HandleMappingsForOrders(Mapping mapping) + { + var columnMappings = mapping.GetColumnMappings(); + if (columnMappings.Find(cm => string.Compare(cm.DestinationColumn.Name, OrderCustomerAccessUserExternalId, true) == 0) != null) + { + var OrderCustomerAccessUserIdMapping = columnMappings.Find(cm => string.Compare(cm.DestinationColumn.Name, "OrderCustomerAccessUserId", true) == 0); + if (OrderCustomerAccessUserIdMapping == null) + { + var randomColumn = mapping.SourceTable.Columns.First(); + SourceColumnNameForDestinationOrderCustomerAccessUserId = randomColumn.Name; + mapping.AddMapping(randomColumn, mapping.DestinationTable.Columns.Find(c => string.Compare(c.Name, "OrderCustomerAccessUserId", true) == 0), true); + } + else + { + if (OrderCustomerAccessUserIdMapping.SourceColumn != null) { - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderPaymentMethodId", StringComparison.OrdinalIgnoreCase))); - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderPaymentMethod", StringComparison.OrdinalIgnoreCase))); - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderPaymentMethodDescription", StringComparison.OrdinalIgnoreCase))); - EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderPaymentMethodTermsCode", StringComparison.OrdinalIgnoreCase))); + SourceColumnNameForDestinationOrderCustomerAccessUserId = OrderCustomerAccessUserIdMapping.SourceColumn.Name; } } } + var ordersTable = mapping.DestinationTable; + if (columnMappings.FirstOrDefault(cm => cm.Active && string.Equals(cm.DestinationColumn.Name, "OrderId", StringComparison.OrdinalIgnoreCase)) is not null) + { + OrderShippingMethodCodeMapping = columnMappings.FirstOrDefault(cm => cm.Active && string.Equals(cm.DestinationColumn.Name, "OrderShippingMethodCode", StringComparison.OrdinalIgnoreCase)); + if (OrderShippingMethodCodeMapping is not null) + { + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethodId", StringComparison.OrdinalIgnoreCase))); + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethod", StringComparison.OrdinalIgnoreCase))); + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethodDescription", StringComparison.OrdinalIgnoreCase))); + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethodAgentCode", StringComparison.OrdinalIgnoreCase))); + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingMethodAgentServiceCode", StringComparison.OrdinalIgnoreCase))); + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderShippingProviderData", StringComparison.OrdinalIgnoreCase))); + } + + OrderPaymentMethodCodeMapping = columnMappings.FirstOrDefault(cm => cm.Active && string.Equals(cm.DestinationColumn.Name, "OrderPaymentMethodCode", StringComparison.OrdinalIgnoreCase)); + if (OrderPaymentMethodCodeMapping is not null) + { + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderPaymentMethodId", StringComparison.OrdinalIgnoreCase))); + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderPaymentMethod", StringComparison.OrdinalIgnoreCase))); + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderPaymentMethodDescription", StringComparison.OrdinalIgnoreCase))); + EnsureMapping(columnMappings, mapping, ordersTable.Columns.FirstOrDefault(c => string.Equals(c.Name, "OrderPaymentMethodTermsCode", StringComparison.OrdinalIgnoreCase))); + } + } } private void EnsureMapping(ColumnMappingCollection columnMappings, Mapping mapping, Column destinationColumn) @@ -503,30 +542,39 @@ private void EnsureMapping(ColumnMappingCollection columnMappings, Mapping mappi } } - private void RemoveColumnMappingsFromJobThatShouldBeSkippedInMoveToMainTables(Job job) + private static void RemoveColumnMappingsThatShouldBeSkippedInMoveToMainTables(Mapping mapping) { - Mapping cleanMapping = job.Mappings.Find(m => m.DestinationTable.Name == "EcomOrders"); - if (cleanMapping != null) + if (string.IsNullOrEmpty(mapping?.DestinationTable?.Name)) + return; + + ColumnMappingCollection columnMapping = mapping.GetColumnMappings(true); + switch (mapping.DestinationTable.Name) { - ColumnMappingCollection columnMapping = cleanMapping.GetColumnMappings(true); - columnMapping.RemoveAll(cm => cm.DestinationColumn != null && string.Compare(cm.DestinationColumn.Name, OrderCustomerAccessUserExternalId, true) == 0); + case "EcomOrders": + columnMapping.RemoveAll(cm => cm.DestinationColumn != null && string.Compare(cm.DestinationColumn.Name, OrderCustomerAccessUserExternalId, true) == 0); + break; + case "EcomOrderLines": + columnMapping.RemoveAll(cm => cm.DestinationColumn != null && string.Compare(cm.DestinationColumn.Name, OrderIntegrationOrderId, true) == 0); + break; + default: + break; } } - private Hashtable _existingUsers = null; + private Dictionary _existingUsers = null; /// /// Collection of , key value pairs /// - private Hashtable ExistingUsers + private Dictionary ExistingUsers { get { if (_existingUsers == null) { - _existingUsers = new Hashtable(); - SqlDataAdapter usersDataAdapter = new SqlDataAdapter("select AccessUserExternalID, AccessUserID from AccessUser where AccessUserExternalID is not null and AccessUserExternalID <> ''", Connection); + _existingUsers = []; + SqlDataAdapter usersDataAdapter = new("select AccessUserExternalID, AccessUserID from AccessUser where AccessUserExternalID is not null and AccessUserExternalID <> ''", Connection); new SqlCommandBuilder(usersDataAdapter); - DataSet dataSet = new DataSet(); + DataSet dataSet = new(); usersDataAdapter.Fill(dataSet); DataTable dataTable = dataSet.Tables[0]; if (dataTable != null) @@ -535,10 +583,7 @@ private Hashtable ExistingUsers foreach (DataRow row in dataTable.Rows) { key = row["AccessUserExternalID"].ToString(); - if (!_existingUsers.ContainsKey(key)) - { - _existingUsers.Add(key, row["AccessUserID"].ToString()); - } + _existingUsers.TryAdd(key, row["AccessUserID"].ToString()); } } } @@ -546,43 +591,116 @@ private Hashtable ExistingUsers } } - private void ProcessRow(Mapping mapping, ColumnMappingCollection columnMappings, Dictionary row) + private Dictionary _existingOrders = null; + /// + /// Collection of , key value pairs + /// + private Dictionary ExistingOrdersWithOrderIntegrationOrderId { - if (mapping != null && mapping.DestinationTable != null && mapping.DestinationTable.Name == "EcomOrders") + get { - if (!string.IsNullOrEmpty(SourceColumnNameForDestinationOrderCustomerAccessUserId)) + if (_existingOrders == null) { - object accessUserId = DBNull.Value; - var OrderCustomerAccessUserExternalIdMapping = columnMappings.Find(cm => string.Compare(cm.DestinationColumn.Name, OrderCustomerAccessUserExternalId, true) == 0); - if (OrderCustomerAccessUserExternalIdMapping != null && OrderCustomerAccessUserExternalIdMapping.SourceColumn != null) + _existingOrders = []; + SqlDataAdapter ordersDataAdapter = new("SELECT OrderId, OrderIntegrationOrderId FROM EcomOrders WHERE OrderIntegrationOrderId IS NOT NULL AND OrderIntegrationOrderId <> ''", Connection); + _ = new SqlCommandBuilder(ordersDataAdapter); + DataSet dataSet = new(); + ordersDataAdapter.Fill(dataSet); + DataTable dataTable = dataSet.Tables[0]; + if (dataTable != null) { - if (row.ContainsKey(OrderCustomerAccessUserExternalIdMapping.SourceColumn.Name)) + string key; + foreach (DataRow row in dataTable.Rows) { - string externalID = Convert.ToString(row[OrderCustomerAccessUserExternalIdMapping.SourceColumn.Name]); - if (!string.IsNullOrEmpty(externalID) && ExistingUsers.ContainsKey(externalID)) - { - accessUserId = ExistingUsers[externalID]; - } + key = row["OrderIntegrationOrderId"].ToString(); + _existingOrders.TryAdd(key, row["OrderId"].ToString()); } } - if (!row.ContainsKey(SourceColumnNameForDestinationOrderCustomerAccessUserId)) + } + return _existingOrders; + } + } + + private void ProcessRow(Mapping mapping, ColumnMappingCollection columnMappings, Dictionary row) + { + if (mapping == null || mapping.DestinationTable == null) + return; + + switch (mapping.DestinationTable.Name) + { + case "EcomOrders": + ProcessOrderRow(mapping, columnMappings, row); + break; + case "EcomOrderLines": + ProcessOrderLineRow(columnMappings, row); + break; + default: + break; + } + } + + private void ProcessOrderLineRow(ColumnMappingCollection columnMappings, Dictionary row) + { + if (!string.IsNullOrEmpty(SourceColumnNameForDestinationOrderIntegrationOrderId)) + { + object orderId = DBNull.Value; + var orderIntegrationOrderIdMapping = columnMappings.Find(cm => string.Compare(cm.DestinationColumn.Name, OrderIntegrationOrderId, true) == 0); + if (orderIntegrationOrderIdMapping != null && orderIntegrationOrderIdMapping.SourceColumn != null) + { + if (row.TryGetValue(orderIntegrationOrderIdMapping.SourceColumn.Name, out object value)) { - row.Add(SourceColumnNameForDestinationOrderCustomerAccessUserId, accessUserId); + string integrationOrderId = Convert.ToString(value); + if (!string.IsNullOrEmpty(integrationOrderId)) + { + orderId = ExistingOrdersWithOrderIntegrationOrderId.ContainsKey(integrationOrderId) ? ExistingOrdersWithOrderIntegrationOrderId[integrationOrderId] : integrationOrderId; + } } - else + } + if (!row.ContainsKey(SourceColumnNameForDestinationOrderIntegrationOrderId)) + { + row.Add(SourceColumnNameForDestinationOrderIntegrationOrderId, orderId); + } + else + { + row[SourceColumnNameForDestinationOrderIntegrationOrderId] = orderId; + } + } + } + + private void ProcessOrderRow(Mapping mapping, ColumnMappingCollection columnMappings, Dictionary row) + { + if (!string.IsNullOrEmpty(SourceColumnNameForDestinationOrderCustomerAccessUserId)) + { + object accessUserId = DBNull.Value; + var OrderCustomerAccessUserExternalIdMapping = columnMappings.Find(cm => string.Compare(cm.DestinationColumn.Name, OrderCustomerAccessUserExternalId, true) == 0); + if (OrderCustomerAccessUserExternalIdMapping != null && OrderCustomerAccessUserExternalIdMapping.SourceColumn != null) + { + if (row.ContainsKey(OrderCustomerAccessUserExternalIdMapping.SourceColumn.Name)) { - row[SourceColumnNameForDestinationOrderCustomerAccessUserId] = accessUserId; + string externalID = Convert.ToString(row[OrderCustomerAccessUserExternalIdMapping.SourceColumn.Name]); + if (!string.IsNullOrEmpty(externalID) && ExistingUsers.ContainsKey(externalID)) + { + accessUserId = ExistingUsers[externalID]; + } } } - if (OrderShippingMethodCodeMapping is not null) + if (!row.ContainsKey(SourceColumnNameForDestinationOrderCustomerAccessUserId)) { - ProcessShipping(mapping, columnMappings, row); + row.Add(SourceColumnNameForDestinationOrderCustomerAccessUserId, accessUserId); } - if (OrderPaymentMethodCodeMapping is not null) + else { - ProcessPayment(mapping, columnMappings, row); + row[SourceColumnNameForDestinationOrderCustomerAccessUserId] = accessUserId; } } + if (OrderShippingMethodCodeMapping is not null) + { + ProcessShipping(mapping, columnMappings, row); + } + if (OrderPaymentMethodCodeMapping is not null) + { + ProcessPayment(mapping, columnMappings, row); + } } private void RemoveMissingRows(IEnumerable writers, SqlTransaction sqlTransaction) @@ -610,7 +728,6 @@ private void RemoveMissingRows(IEnumerable writers, SqlT } } - private void ProcessShipping(Mapping mapping, ColumnMappingCollection columnMappings, Dictionary row) { var code = GetValue(OrderShippingMethodCodeMapping, row); @@ -699,4 +816,3 @@ private string GetValue(ColumnMapping? columnMapping, Dictionary return result; } } -