Пример #1
0
        public object Create(object parent, object configContext, XmlNode section)
        {
            var result = new FeedGenerationFileInstructionsConfigurationSection {
                FeedGenerationFileInstructions = new List <FeedGenerationFileInstruction>()
            };

            if (section.ChildNodes.Count == 0)
            {
                return(result);
            }

            foreach (XmlNode childNode in section.ChildNodes)
            {
                if (childNode.Attributes == null || childNode.Attributes["key"] == null)
                {
                    continue;
                }

                var fileInstruction = new FeedGenerationFileInstruction {
                    Key = childNode.Attributes["key"].Value, Aid = childNode.Attributes["aid"].Value, LineItems = new List <FeedGenerationFileLineItem>()
                };
                foreach (XmlNode childNodeChild in childNode.ChildNodes)
                {
                    if (childNodeChild == null || childNodeChild.Attributes == null)
                    {
                        continue;
                    }

                    var lineItem = new FeedGenerationFileLineItem
                    {
                        Catalog = childNodeChild.Attributes["catalog"].Value,
                        Catalogattributesection = childNodeChild.Attributes["catalogattributesection"].Value,
                        IsIncluded          = bool.Parse(childNodeChild.Attributes["isIncluded"].Value),
                        RangeDatas          = childNodeChild.Attributes["ranges"].Value,
                        StoredProcedureName = childNodeChild.Attributes["storedProcedureName"].Value
                    };

                    fileInstruction.LineItems.Add(lineItem);
                }

                result.FeedGenerationFileInstructions.Add(fileInstruction);
            }
            return(result);
        }
 private static string GetFeedFilePath(FeedGenerationFileItemRange fileItemRange, FeedGenerationFileLineItem feedGenerationFileLineItem,
                                       string languageString, string pathBase)
 {
     return(string.Format("{0}/{1}/{2}-{3}-{4}.txt", pathBase, languageString, feedGenerationFileLineItem.Catalog,
                          fileItemRange.Begin, fileItemRange.End));
 }
Пример #3
0
        private void WriteRangeFile(FeedGenerationFileLineItem fileComponent, FeedGenerationFileItemRange range,
                                    IEnumerable <AbstractFileFeedWriter> feedWriters)
        {
            using (var sqlConnection = new SqlConnection(OdysseyCommerceConnectionString))
            {
                sqlConnection.Open();

                var catalog       = fileComponent.Catalog;
                var sqlParameters = new SqlParameter[2];
                if (!fileComponent.IsIncluded)
                {
                    Log.InfoFormat("FeedGenerationFileLineItem [{0}-{1}] was excluded from feed generation.", catalog,
                                   fileComponent.RangeDatas);
                    return;
                }

                var identifier = string.Format("{0}_{1}", catalog, fileComponent.RangeDatas);
                try
                {
                    sqlParameters[0] = new SqlParameter("@PIDRangeStart", range.Begin);
                    sqlParameters[1] = new SqlParameter("@PIDRangeEnd ", range.End);
                    identifier       = string.Format("{0}_{1}_{2}", catalog, range.Begin, range.End);

                    var startDt = DateTime.Now;
                    Log.DebugFormat("[{0}] start", identifier);
                    using (var sqlCommand = new SqlCommand(fileComponent.StoredProcedureName, sqlConnection)
                    {
                        CommandType = CommandType.StoredProcedure,
                        CommandTimeout = SearchDataCommandTimeout
                    })
                    {
                        if (!(sqlParameters[0].Value.ToString() == "0" && sqlParameters[1].Value.ToString() == "99"))
                        {
                            sqlCommand.Parameters.AddRange(sqlParameters);
                        }

                        if (LimitTo100Products)
                        {
                            sqlCommand.Parameters.AddWithValue("@GetTop100", 1);
                        }

                        if (_isIncrementalRun)
                        {
                            sqlCommand.Parameters.AddWithValue("@IsIncremental", 1);
                            sqlCommand.Parameters.AddWithValue("@DateChanged", _effectiveFromTime);
                        }

                        using (var sqlDataReader = sqlCommand.ExecuteReader())
                        {
                            if (!sqlDataReader.HasRows)
                            {
                                Log.InfoFormat("Runner.WriteRangeFile. sqlDataReader has no rows. catalog: {0}", catalog);
                            }

                            while (sqlDataReader.Read())
                            {
                                foreach (var writer in feedWriters)
                                {
                                    try
                                    {
                                        writer.Write(sqlDataReader, identifier);
                                    }
                                    catch (Exception ex)
                                    {
                                        if (_isIncrementalRun || !AllowItemErrorsInFiles)
                                        {
                                            throw;
                                        }

                                        Log.Error(string.Format("[Feed] {0} errored out.", identifier), ex);
                                        _hasError = true;
                                    }
                                }
                            }
                        } //using sqldatareader
                    }     //using sqlCommand
                    var endDt    = DateTime.Now;
                    var execTime = endDt - startDt;
                    Log.InfoFormat("[{0}] completed. Execution time in seconds: {1}", identifier, execTime.TotalSeconds);
                }
                catch (Exception ex)
                {
                    Log.Error(string.Format("Runner.WriteRangeFile(). [Feed] {0} errored out.", identifier), ex);
                    _hasError = true;

                    if (_isIncrementalRun || !AllowItemErrorsInFiles)
                    {
                        throw;
                    }
                }
            }
        }
Пример #4
0
        private void WriteFileComponentContent(XmlWriter xmlWriter, FeedGenerationFileLineItem fileComponent, IDataReader reader, string identifier, ref Tuple <int, int, int> countRec)
        {
            var attributesDictionary = ConfigurationManager.GetSection(fileComponent.Catalogattributesection) as StringDictionary;

            if (countRec == null)
            {
                throw new ArgumentNullException("countRec");
            }
            var countProcessed = 0;
            var countDeleted   = 0;
            var countError     = 0;

            //<entry>
            while (reader.Read())
            {
                Log.DebugFormat("{0}::Processing record [{1}]: {2}", identifier, (countProcessed + countError + countDeleted), reader["PID"]);

                var id    = reader[attributesDictionary["gId"]].ToString();
                var title = reader[attributesDictionary["title"]].ToString();
                try
                {
                    var haveRulesChanged = _runnerHelper.HaveRulesChanged;
                    var linkSku          = reader[attributesDictionary["linkSku"]].ToString();
                    var brandName        = !attributesDictionary.ContainsKey("gBrand") ? string.Empty : reader[attributesDictionary["gBrand"]].ToString();
                    var cContributors    = GetContributors(attributesDictionary, reader);
                    // Get the breadcrumb value
                    var defaultCategory = FeedUtils.GetFeedGeneratorIndigoCategory(_feedGeneratorCategoryService, reader, attributesDictionary, fileComponent.Catalog, Log);
                    var productData     = FeedUtils.GetProductData(attributesDictionary, reader, linkSku, fileComponent.Catalog, brandName, cContributors, defaultCategory);
                    var sanitizedTitle  = (string.IsNullOrWhiteSpace(title)) ? string.Empty : FeedUtils.SanitizeString(title);
                    var gAvailability   = !attributesDictionary.ContainsKey("gAvailability") ? FeedUtils.GetGoogleAvailability(1) : FeedUtils.GetGoogleAvailability((int)reader[attributesDictionary["gAvailability"]]);
                    var availability    = !attributesDictionary.ContainsKey("gAvailability") ? 1 : (int)reader[attributesDictionary["gAvailability"]];
                    var recordType      = !attributesDictionary.ContainsKey("recordType") ? string.Empty : reader[attributesDictionary["recordType"]].ToString();
                    var merchandiseType = !attributesDictionary.ContainsKey("merchandiseType") ? string.Empty : reader[attributesDictionary["merchandiseType"]].ToString();
                    if (string.IsNullOrWhiteSpace(merchandiseType))
                    {
                        _missingMerchandiseTypeProductInfos.Add(new MissingMerchandiseTypeProductInfo {
                            Breadcrumb = defaultCategory.Breadcrumb, Sku = linkSku, Title = sanitizedTitle
                        });
                    }

                    IRuleEvaluationResult newZeroCommissionResult  = null;
                    IRuleEvaluationResult newPromotionalTextResult = null;
                    if (_isIncrementalRun)
                    {
                        var isModifiedData = int.Parse(reader["IsModified"].ToString());
                        if (isModifiedData == 0)
                        {
                            if (!haveRulesChanged)
                            {
                                Log.DebugFormat(
                                    "Product with pid {0} is skipped in incremental mode as it wasn't modified and the rules haven't changed.",
                                    id);
                                continue;
                            }

                            var oldZeroCommissionResult = _runnerHelper.GetZeroCommissionRuleResult(productData, true);
                            newZeroCommissionResult = _runnerHelper.GetZeroCommissionRuleResult(productData, false);
                            var oldPromotionalTextResult = _runnerHelper.GetPromotionalTextRuleResult(productData, true);
                            newPromotionalTextResult = _runnerHelper.GetPromotionalTextRuleResult(productData, false);
                            if (oldZeroCommissionResult.HasMatch == newZeroCommissionResult.HasMatch &&
                                oldPromotionalTextResult.HasMatch == newPromotionalTextResult.HasMatch &&
                                oldPromotionalTextResult.MatchingRulePayLoads.First()
                                .Equals(newPromotionalTextResult.MatchingRulePayLoads.First()))
                            {
                                countDeleted++;
                                Log.DebugFormat(
                                    "Product with pid {0} is skipped in incremental mode as it wasn't modified and rule evaluations yielded same results.",
                                    id);
                                continue;
                            }

                            // At this point, we know that rules have changed, which means we need to resend this product as modified
                        }
                        else
                        {
                            newZeroCommissionResult  = _runnerHelper.GetZeroCommissionRuleResult(productData, false);
                            newPromotionalTextResult = _runnerHelper.GetPromotionalTextRuleResult(productData, false);
                        }
                    }
                    else
                    {
                        newZeroCommissionResult  = _runnerHelper.GetZeroCommissionRuleResult(productData, false);
                        newPromotionalTextResult = _runnerHelper.GetPromotionalTextRuleResult(productData, false);
                    }

                    var isZeroCommissionElement = newZeroCommissionResult.HasMatch || IsZeroCommissionElement(sanitizedTitle, _feedId, true, availability, recordType);
                    if (isZeroCommissionElement)
                    {
                        Log.DebugFormat("Product with pid {0} is being placed in zero commission list due to either data issues or zero commission rules.)", id);
                    }

                    var linkCatalog = attributesDictionary["linkCatalog"];
                    if (string.IsNullOrWhiteSpace(sanitizedTitle))
                    {
                        sanitizedTitle = "(No Title)";
                    }
                    var description = reader[attributesDictionary["description"]].ToString();
                    description = string.IsNullOrWhiteSpace(description) ? sanitizedTitle : FeedUtils.SanitizeString(description);

                    // Get the breadcrumb value
                    var breadcrumb     = defaultCategory.Breadcrumb;
                    var gPrice         = string.IsNullOrEmpty(attributesDictionary["price"]) ? "" : reader[attributesDictionary["price"]].ToString();
                    var gAdjustedPrice = string.IsNullOrEmpty(attributesDictionary["adjustedPrice"]) ? string.Empty : reader[attributesDictionary["adjustedPrice"]].ToString();
                    var publisherName  = !attributesDictionary.ContainsKey("publisherName") ? string.Empty : reader[attributesDictionary["publisherName"]].ToString();
                    if (!string.IsNullOrWhiteSpace(recordType) &&
                        recordType.Equals("GCard_Electronic", StringComparison.OrdinalIgnoreCase))
                    {
                        gPrice         = DefaultEGiftCardPrice;
                        gAdjustedPrice = DefaultEGiftCardPrice;
                    }


                    var entry = EntryAttribute(fileComponent.Catalog, reader, attributesDictionary
                                               , id
                                               , sanitizedTitle
                                               , linkCatalog, linkSku
                                               , gPrice
                                               , gAdjustedPrice
                                               , gAvailability
                                               , brandName, publisherName, cContributors, breadcrumb, isZeroCommissionElement, merchandiseType, newPromotionalTextResult, description);

                    countProcessed++;
                    //out of memory exception will be thrown if we keep the xml entries in memory
                    entry.WriteTo(xmlWriter);
                }
                catch (Exception e)
                {
                    countError++;
                    Log.ErrorFormat("Can't process the item. Id:{0};title:{1}", id, title);
                    Log.DebugFormat("Error stack trace: {0}", e);
                    _executionLogLogger.AddCustomMessage(string.Format("Can't process the item. Id: {0};title: {1}, file identifier: {2}", id, title, identifier));
                    if (!AllowItemErrorsInFiles || _isIncrementalRun)
                    {
                        _hasError = true;
                    }
                }
            }

            // Now process the deleted items for the range & producttypeid and put them in the xml file as "deleted" items
            if (_isIncrementalRun)
            {
                // Don't do it for gift card file component
                if (!fileComponent.StoredProcedureName.Equals("uspCJFeedGeneralMerchandiseGiftCard",
                                                              StringComparison.OrdinalIgnoreCase))
                {
                    foreach (var deletedProductInfo in GetDeletedProductInfos(identifier))
                    {
                        GetDeletedElement(deletedProductInfo).WriteTo(xmlWriter);
                        countDeleted++;
                    }
                }
            }

            Log.InfoFormat("{0} completed. Processed record count: {1}, Error record count: {2}, deleted/skipped record count {3}", identifier, countProcessed, countError, countDeleted);
            countRec = new Tuple <int, int, int>(countRec.Item1 + countProcessed, countRec.Item2 + countError, countRec.Item3 + countDeleted);
        }
Пример #5
0
        private void WriteFileComponent(XmlWriter xmlWriter, FeedGenerationFileLineItem fileComponent, ref Tuple <int, int, int> countRec)
        {
            using (var sqlConnection = new SqlConnection(OdysseyCommerceConnectionString))
            {
                sqlConnection.Open();

                var catalog       = fileComponent.Catalog;
                var sqlParameters = new SqlParameter[2];
                if (!fileComponent.IsIncluded)
                {
                    Log.InfoFormat("FeedGenerationFileLineItem [{0}-{1}] was excluded from feed generation.", catalog, fileComponent.RangeDatas);
                    return;
                }

                var identifier = string.Format("{0}_{1}", catalog, fileComponent.RangeDatas);
                try
                {
                    var ranges = fileComponent.GetRanges();
                    foreach (var range in ranges)
                    {
                        sqlParameters[0] = new SqlParameter("@PIDRangeStart", range.Begin);
                        sqlParameters[1] = new SqlParameter("@PIDRangeEnd ", range.End);
                        identifier       = string.Format("{0}_{1}_{2}", catalog, range.Begin, range.End);

                        var startDt = DateTime.Now;
                        Log.DebugFormat("[{0}] start", identifier);
                        using (var sqlCommand = new SqlCommand(fileComponent.StoredProcedureName, sqlConnection)
                        {
                            CommandType = CommandType.StoredProcedure,
                            CommandTimeout = SearchDataCommandTimeout
                        })
                        {
                            if (sqlParameters.Length == 2 && !(sqlParameters[0].Value.ToString() == "0" && sqlParameters[1].Value.ToString() == "99"))
                            {
                                sqlCommand.Parameters.AddRange(sqlParameters);
                            }

                            if (LimitTo100Products)
                            {
                                sqlCommand.Parameters.AddWithValue("@GetTop100", 1);
                            }

                            if (_isIncrementalRun)
                            {
                                sqlCommand.Parameters.AddWithValue("@IsIncremental", 1);
                                sqlCommand.Parameters.AddWithValue("@DateChanged", _effectiveFromTime);
                            }

                            using (var sqlDataReader = sqlCommand.ExecuteReader())
                            {
                                if (sqlDataReader.HasRows)
                                {
                                    WriteFileComponentContent(xmlWriter, fileComponent, sqlDataReader, identifier, ref countRec);
                                }
                            } //using sqldatareader
                        }     //using sqlCommand
                        var endDt    = DateTime.Now;
                        var execTime = endDt - startDt;
                        Log.InfoFormat("[{0}] completed. Execution time in seconds: {1}", identifier, execTime.TotalSeconds);
                    }
                }
                catch (Exception ex)
                {
                    Log.Error(string.Format("[Feed] {0} errored out.", identifier), ex);
                    _hasError = true;
                }
            }
        }