private coreModel.CatalogProduct UpdateProduct(webModel.Product product)
        {
            var moduleProduct = product.ToModuleModel(_blobUrlResolver);

            if (moduleProduct.Id == null)
            {
                if (moduleProduct.SeoInfos == null || !moduleProduct.SeoInfos.Any())
                {
                    var slugUrl = GenerateProductDefaultSlugUrl(product);
                    if (!string.IsNullOrEmpty(slugUrl))
                    {
                        var catalog             = _catalogService.GetById(product.CatalogId);
                        var defaultLanguageCode = catalog.Languages.First(x => x.IsDefault).LanguageCode;
                        var seoInfo             = new SeoInfo
                        {
                            LanguageCode = defaultLanguageCode,
                            SemanticUrl  = slugUrl
                        };
                        moduleProduct.SeoInfos = new SeoInfo[] { seoInfo };
                    }
                }

                base.CheckCurrentUserHasPermissionForObjects(CatalogPredefinedPermissions.Create, moduleProduct);
                return(_itemsService.Create(moduleProduct));
            }
            else
            {
                base.CheckCurrentUserHasPermissionForObjects(CatalogPredefinedPermissions.Update, moduleProduct);
                _itemsService.Update(new[] { moduleProduct });
            }

            return(null);
        }
Ejemplo n.º 2
0
        // GET: /blogs/{blogname}/tag/{tag}
        public ActionResult GetArticlesByTag(string blogName, string tag)
        {
            var blog = WorkContext.Blogs.FirstOrDefault(b => b.Name.Equals(blogName, StringComparison.OrdinalIgnoreCase));

            if (blog != null)
            {
                var blogClone = new Blog();
                //Need to clone exist blog because it may be memory cached
                blogClone.InjectFrom <NullableAndEnumValueInjecter>(blog);
                var seoInfo = new SeoInfo
                {
                    Language        = blog.Language,
                    MetaDescription = blog.Title,
                    Slug            = string.Format("/blogs/{0}/tag/{1}", blog, tag),
                    Title           = blog.Title
                };

                var articles = blog.Articles.Where(a => a.Tags != null && a.Tags.Contains(tag, StringComparer.OrdinalIgnoreCase) && a.PublicationStatus != ContentPublicationStatus.Private);
                if (articles != null)
                {
                    blogClone.Articles = new MutablePagedList <BlogArticle>(articles);
                }

                WorkContext.CurrentBlog    = blogClone;
                WorkContext.CurrentPageSeo = seoInfo;
            }

            return(View("blog", blog.Layout, WorkContext));
        }
Ejemplo n.º 3
0
        public CsvProduct(CatalogProduct product, IBlobUrlResolver blobUrlResolver, Price price, InventoryInfo inventory, SeoInfo seoInfo)
            : this()
        {
            _blobUrlResolver = blobUrlResolver;

            this.InjectFrom(product);
            Properties   = product.Properties;
            Images       = product.Images;
            Assets       = product.Assets;
            Links        = product.Links;
            Variations   = product.Variations;
            SeoInfos     = product.SeoInfos;
            Reviews      = product.Reviews;
            Associations = product.Associations;
            if (price != null)
            {
                Price = price;
            }
            if (inventory != null)
            {
                Inventory = inventory;
            }
            if (seoInfo != null)
            {
                SeoInfo = seoInfo;
            }
        }
Ejemplo n.º 4
0
 public static SeoInfo ToWebModel(this VirtoCommerce.Client.Model.VirtoCommerceDomainCommerceModelSeoInfo seoDto)
 {
     var retVal = new SeoInfo();
     retVal.InjectFrom(seoDto);
     retVal.Slug = seoDto.SemanticUrl;
     retVal.Title = seoDto.PageTitle;
     return retVal;
 }
Ejemplo n.º 5
0
        public static SeoInfo ToWebModel(this VirtoCommerce.Client.Model.VirtoCommerceDomainCommerceModelSeoInfo seoDto)
        {
            var retVal = new SeoInfo();

            retVal.InjectFrom(seoDto);
            retVal.Slug  = seoDto.SemanticUrl;
            retVal.Title = seoDto.PageTitle;
            return(retVal);
        }
Ejemplo n.º 6
0
 public static SeoInfo ToWebModel(this VirtoCommerce.Client.Model.VirtoCommerceDomainCommerceModelSeoInfo seoDto)
 {
     var retVal = new SeoInfo();
     retVal.InjectFrom(seoDto);
     retVal.Slug = seoDto.SemanticUrl;
     retVal.Title = seoDto.PageTitle;
     retVal.Language = String.IsNullOrEmpty(seoDto.LanguageCode) ? Language.InvariantLanguage : new Language(seoDto.LanguageCode);
     return retVal;
 }
Ejemplo n.º 7
0
        public static SeoInfo ToWebModel(this VirtoCommerce.Client.Model.VirtoCommerceDomainCommerceModelSeoInfo seoDto)
        {
            var retVal = new SeoInfo();

            retVal.InjectFrom(seoDto);
            retVal.Slug     = seoDto.SemanticUrl;
            retVal.Title    = seoDto.PageTitle;
            retVal.Language = String.IsNullOrEmpty(seoDto.LanguageCode) ? Language.InvariantLanguage : new Language(seoDto.LanguageCode);
            return(retVal);
        }
Ejemplo n.º 8
0
        public static webModel.SeoKeyword ToWebModel(this SeoInfo seoInfo)
        {
            var retVal = new webModel.SeoKeyword();

            retVal.InjectFrom(seoInfo);
            retVal.Keyword  = seoInfo.SemanticUrl;
            retVal.Language = seoInfo.LanguageCode;
            retVal.Title    = seoInfo.PageTitle;

            return(retVal);
        }
Ejemplo n.º 9
0
        public static SeoInfo ToSeoInfo(this coreDto.SeoInfo seoDto)
        {
            var retVal = new SeoInfo();

            retVal.InjectFrom(seoDto);

            retVal.Slug     = seoDto.SemanticUrl;
            retVal.Title    = seoDto.PageTitle;
            retVal.Language = string.IsNullOrEmpty(seoDto.LanguageCode) ? Language.InvariantLanguage : new Language(seoDto.LanguageCode);
            return(retVal);
        }
        public static SeoInfo ToSeoInfo(this coreDto.SeoInfo seoDto)
        {
            var retVal = new SeoInfo();

            retVal.MetaDescription = seoDto.MetaDescription;
            retVal.MetaKeywords    = seoDto.MetaKeywords;

            retVal.Slug     = seoDto.SemanticUrl;
            retVal.Title    = seoDto.PageTitle;
            retVal.Language = string.IsNullOrEmpty(seoDto.LanguageCode) ? Language.InvariantLanguage : new Language(seoDto.LanguageCode);
            return(retVal);
        }
        public virtual void MergeFrom(SeoInfo source)
        {
            SemanticUrl  = source.SemanticUrl;
            LanguageCode = source.LanguageCode;
            StoreId      = source.StoreId;

            if (PageTitle.IsNullOrEmpty())
            {
                PageTitle = source.PageTitle;
            }

            if (MetaDescription.IsNullOrEmpty())
            {
                MetaDescription = source.MetaDescription;
            }
        }
Ejemplo n.º 12
0
        public static SeoInfo ToWebModel(this storeModel.SeoInfo seoDto)
        {
            SeoInfo retVal = null;

            if (seoDto != null)
            {
                retVal = new SeoInfo();
                retVal.InjectFrom(seoDto);

                retVal.Slug     = seoDto.SemanticUrl;
                retVal.Title    = seoDto.PageTitle;
                retVal.Language = string.IsNullOrEmpty(seoDto.LanguageCode) ? Language.InvariantLanguage : new Language(seoDto.LanguageCode);
            }

            return(retVal);
        }
        private coreModel.CatalogProduct[] InnerSaveProducts(webModel.Product[] products)
        {
            var toUpdateList = new List <coreModel.CatalogProduct>();
            var toCreateList = new List <coreModel.CatalogProduct>();

            foreach (var product in products)
            {
                var moduleProduct = product.ToModuleModel(_blobUrlResolver);
                if (moduleProduct.IsTransient())
                {
                    if (moduleProduct.SeoInfos == null || !moduleProduct.SeoInfos.Any())
                    {
                        var slugUrl = GenerateProductDefaultSlugUrl(product);
                        if (!string.IsNullOrEmpty(slugUrl))
                        {
                            var catalog             = _catalogService.GetById(product.CatalogId);
                            var defaultLanguageCode = catalog.Languages.First(x => x.IsDefault).LanguageCode;
                            var seoInfo             = new SeoInfo
                            {
                                LanguageCode = defaultLanguageCode,
                                SemanticUrl  = slugUrl
                            };
                            moduleProduct.SeoInfos = new[] { seoInfo };
                        }
                    }

                    CheckCurrentUserHasPermissionForObjects(CatalogPredefinedPermissions.Create, moduleProduct);
                    toCreateList.Add(moduleProduct);
                }
                else
                {
                    CheckCurrentUserHasPermissionForObjects(CatalogPredefinedPermissions.Update, moduleProduct);
                    toUpdateList.Add(moduleProduct);
                }
            }

            if (!toCreateList.IsNullOrEmpty())
            {
                _itemsService.Create(toCreateList.ToArray());
            }
            if (!toUpdateList.IsNullOrEmpty())
            {
                _itemsService.Update(toUpdateList.ToArray());
            }

            return(toCreateList.Concat(toUpdateList).ToArray());
        }
Ejemplo n.º 14
0
        public virtual SeoInfo ToModel(SeoInfo seoInfo)
        {
            seoInfo.Id           = Id;
            seoInfo.CreatedBy    = CreatedBy;
            seoInfo.CreatedDate  = CreatedDate;
            seoInfo.ModifiedBy   = ModifiedBy;
            seoInfo.ModifiedDate = ModifiedDate;

            seoInfo.LanguageCode        = Language;
            seoInfo.SemanticUrl         = Keyword;
            seoInfo.PageTitle           = Title;
            seoInfo.ImageAltDescription = ImageAltDescription;
            seoInfo.IsActive            = IsActive;
            seoInfo.MetaDescription     = MetaDescription;
            seoInfo.MetaKeywords        = MetaKeywords;
            seoInfo.ObjectId            = ItemId ?? CategoryId;
            seoInfo.ObjectType          = ItemId != null ? "CatalogProduct" : "Category";
            seoInfo.StoreId             = StoreId;

            return(seoInfo);
        }
Ejemplo n.º 15
0
        public virtual SeoInfoEntity FromModel(SeoInfo seoInfo, PrimaryKeyResolvingMap pkMap)
        {
            pkMap.AddPair(seoInfo, this);

            Id           = seoInfo.Id;
            CreatedBy    = seoInfo.CreatedBy;
            CreatedDate  = seoInfo.CreatedDate;
            ModifiedBy   = seoInfo.ModifiedBy;
            ModifiedDate = seoInfo.ModifiedDate;

            Language            = seoInfo.LanguageCode;
            Keyword             = seoInfo.SemanticUrl;
            Title               = seoInfo.PageTitle;
            ImageAltDescription = seoInfo.ImageAltDescription;
            IsActive            = seoInfo.IsActive;
            MetaDescription     = seoInfo.MetaDescription;
            MetaKeywords        = seoInfo.MetaKeywords;
            StoreId             = seoInfo.StoreId;

            return(this);
        }
Ejemplo n.º 16
0
        public virtual SeoInfo ToModel(SeoInfo seoInfo)
        {
            seoInfo.Id           = Id;
            seoInfo.CreatedBy    = CreatedBy;
            seoInfo.CreatedDate  = CreatedDate;
            seoInfo.ModifiedBy   = ModifiedBy;
            seoInfo.ModifiedDate = ModifiedDate;

            seoInfo.LanguageCode        = Language;
            seoInfo.SemanticUrl         = Keyword;
            seoInfo.PageTitle           = Title;
            seoInfo.ImageAltDescription = ImageAltDescription;
            seoInfo.IsActive            = IsActive;
            seoInfo.MetaDescription     = MetaDescription;
            seoInfo.MetaKeywords        = MetaKeywords;
            seoInfo.ObjectId            = MemberId;
            seoInfo.ObjectType          = "Member";
            seoInfo.StoreId             = StoreId;

            return(seoInfo);
        }
Ejemplo n.º 17
0
        public CsvProduct()
        {
            SeoInfos       = new List <SeoInfo>();
            Reviews        = new List <EditorialReview>();
            PropertyValues = new List <PropertyValue>();
            Images         = new List <Image>();
            Assets         = new List <Asset>();


            Price = new Price()
            {
                Currency = CurrencyCodes.USD
            };
            Inventory       = new InventoryInfo();
            EditorialReview = new EditorialReview();
            Reviews         = new List <EditorialReview>();
            Reviews.Add(EditorialReview);
            SeoInfo  = new SeoInfo();
            SeoInfos = new List <SeoInfo>();
            SeoInfos.Add(SeoInfo);
        }
        private async Task <CatalogProduct[]> InnerSaveProducts(CatalogProduct[] products)
        {
            var toSaveList = new List <CatalogProduct>();
            var catalogs   = await _catalogService.GetByIdsAsync(products.Select(pr => pr.CatalogId).Distinct().ToArray());

            foreach (var product in products)
            {
                if (product.IsTransient())
                {
                    if (product.SeoInfos == null || !product.SeoInfos.Any())
                    {
                        var slugUrl = GenerateProductDefaultSlugUrl(product);
                        if (!string.IsNullOrEmpty(slugUrl))
                        {
                            var catalog             = catalogs.FirstOrDefault(c => c.Id.EqualsInvariant(product.CatalogId));
                            var defaultLanguageCode = catalog?.Languages.First(x => x.IsDefault).LanguageCode;
                            var seoInfo             = new SeoInfo
                            {
                                LanguageCode = defaultLanguageCode,
                                SemanticUrl  = slugUrl
                            };
                            product.SeoInfos = new[] { seoInfo };
                        }
                    }

                    //CheckCurrentUserHasPermissionForObjects(CatalogPredefinedPermissions.Create, moduleProduct);
                }

                toSaveList.Add(product);
            }

            if (!toSaveList.IsNullOrEmpty())
            {
                await _itemsService.SaveChangesAsync(toSaveList.ToArray());
            }

            return(toSaveList.ToArray());
        }
Ejemplo n.º 19
0
        public CsvProduct()
        {
            SeoInfos       = new List <SeoInfo>();
            Reviews        = new List <EditorialReview>();
            PropertyValues = new List <PropertyValue>();
            Images         = new List <Image>();
            Assets         = new List <Asset>();

            Price = new Price {
                Currency = "USD"
            };
            Inventory       = new InventoryInfo();
            EditorialReview = new EditorialReview();
            Reviews         = new List <EditorialReview> {
                EditorialReview
            };
            SeoInfo = new SeoInfo {
                ObjectType = typeof(CatalogProduct).Name
            };
            SeoInfos = new List <SeoInfo> {
                SeoInfo
            };
        }
Ejemplo n.º 20
0
        /// <example>
        ///{
        ///    product(id: "f1b26974b7634abaa0900e575a99476f")
        ///    {
        ///        id
        ///        code
        ///        category{ id code name hasParent slug }
        ///        name
        ///        metaTitle
        ///        metaDescription
        ///        metaKeywords
        ///        brandName
        ///        slug
        ///        imgSrc
        ///        productType
        ///        masterVariation {
        ///        images{ id url name }
        ///        assets{ id size url }
        ///        prices(cultureName: "en-us"){
        ///            list { amount }
        ///            currency
        ///        }
        ///        availabilityData{
        ///            availableQuantity
        ///            inventories{
        ///                inStockQuantity
        ///                fulfillmentCenterId
        ///                fulfillmentCenterName
        ///                allowPreorder
        ///                allowBackorder
        ///            }
        ///        }
        ///        properties{ id name valueType value valueId }
        ///    }
        ///}
        /// </example>
        public ProductType(IMediator mediator, IDataLoaderContextAccessor dataLoader)
        {
            Name        = "Product";
            Description = "Products are the sellable goods in an e-commerce project.";

            Field(d => d.IndexedProduct.Id).Description("The unique ID of the product.");
            Field(d => d.IndexedProduct.Code, nullable: false).Description("The product SKU.");
            Field <StringGraphType>("catalogId",
                                    "The unique ID of the catalog",
                                    resolve: context => context.Source.IndexedProduct.CatalogId);
            Field(d => d.IndexedProduct.ProductType, nullable: true).Description("The type of product");
            Field(d => d.IndexedProduct.MinQuantity, nullable: true).Description("Min. quantity");
            Field(d => d.IndexedProduct.MaxQuantity, nullable: true).Description("Max. quantity");

            FieldAsync <StringGraphType>("outline", resolve: async context =>
            {
                var outlines = context.Source.IndexedProduct.Outlines;
                if (outlines.IsNullOrEmpty())
                {
                    return(null);
                }

                var loadRelatedCatalogOutlineQuery      = context.GetCatalogQuery <LoadRelatedCatalogOutlineQuery>();
                loadRelatedCatalogOutlineQuery.Outlines = outlines;

                var response = await mediator.Send(loadRelatedCatalogOutlineQuery);
                return(response.Outline);
            }, description: @"All parent categories ids relative to the requested catalog and concatenated with \ . E.g. (1/21/344)");

            FieldAsync <StringGraphType>("slug", resolve: async context =>
            {
                var outlines = context.Source.IndexedProduct.Outlines;
                if (outlines.IsNullOrEmpty())
                {
                    return(null);
                }

                var loadRelatedSlugPathQuery      = context.GetCatalogQuery <LoadRelatedSlugPathQuery>();
                loadRelatedSlugPathQuery.Outlines = outlines;

                var response = await mediator.Send(loadRelatedSlugPathQuery);
                return(response.Slug);
            }, description: "Request related slug for product");

            Field(d => d.IndexedProduct.Name, nullable: false).Description("The name of the product.");

            Field <SeoInfoType>("seoInfo", resolve: context =>
            {
                var source      = context.Source;
                var storeId     = context.GetArgumentOrValue <string>("storeId");
                var cultureName = context.GetArgumentOrValue <string>("cultureName");

                SeoInfo seoInfo = null;

                if (!source.IndexedProduct.SeoInfos.IsNullOrEmpty())
                {
                    seoInfo = source.IndexedProduct.SeoInfos.GetBestMatchingSeoInfo(storeId, cultureName);
                }

                return(seoInfo ?? GetFallbackSeoInfo(source, cultureName));
            }, description: "Request related SEO info");

            Field <ListGraphType <DescriptionType> >("descriptions",
                                                     arguments: new QueryArguments(new QueryArgument <StringGraphType> {
                Name = "type"
            }),
                                                     resolve: context =>
            {
                var reviews     = context.Source.IndexedProduct.Reviews;
                var cultureName = context.GetArgumentOrValue <string>("cultureName");
                var type        = context.GetArgumentOrValue <string>("type");
                if (cultureName != null)
                {
                    reviews = reviews.Where(x => string.IsNullOrEmpty(x.LanguageCode) || x.LanguageCode.EqualsInvariant(cultureName)).ToList();
                }
                if (type != null)
                {
                    reviews = reviews.Where(x => x.ReviewType?.EqualsInvariant(type) ?? true).ToList();
                }
                return(reviews);
            });

            Field <DescriptionType>("description",
                                    arguments: new QueryArguments(new QueryArgument <StringGraphType> {
                Name = "type"
            }),
                                    resolve: context =>
            {
                var reviews     = context.Source.IndexedProduct.Reviews;
                var type        = context.GetArgumentOrValue <string>("type");
                var cultureName = context.GetArgumentOrValue <string>("cultureName");

                if (!reviews.IsNullOrEmpty())
                {
                    return(reviews.Where(x => x.ReviewType.EqualsInvariant(type ?? "FullReview")).FirstBestMatchForLanguage(cultureName) as EditorialReview
                           ?? reviews.FirstBestMatchForLanguage(cultureName) as EditorialReview);
                }

                return(null);
            });

            FieldAsync <CategoryType>(
                "category",
                resolve: async context =>
            {
                var categoryId = context.Source.IndexedProduct.CategoryId;

                var loadCategoryQuery           = context.GetCatalogQuery <LoadCategoryQuery>();
                loadCategoryQuery.ObjectIds     = new[] { categoryId };
                loadCategoryQuery.IncludeFields = context.SubFields.Values.GetAllNodesPaths();

                var responce = await mediator.Send(loadCategoryQuery);

                return(responce.Categories.FirstOrDefault());
            });

            Field <StringGraphType>(
                "imgSrc",
                description: "The product main image URL.",
                resolve: context => context.Source.IndexedProduct.ImgSrc);

            Field(d => d.IndexedProduct.OuterId, nullable: true).Description("The outer identifier");

            Field <StringGraphType>(
                "brandName",
                description: "Get brandName for product.",
                resolve: context =>
            {
                var brandName = context.Source.IndexedProduct.Properties
                                ?.FirstOrDefault(x => x.Name.EqualsInvariant("Brand"))
                                ?.Values
                                ?.FirstOrDefault(x => x.Value != null)
                                ?.Value;

                return(brandName?.ToString());
            });

            FieldAsync <VariationType>(
                "masterVariation",
                resolve: async context =>
            {
                if (string.IsNullOrEmpty(context.Source.IndexedProduct.MainProductId))
                {
                    return(null);
                }

                var query           = context.GetCatalogQuery <LoadProductsQuery>();
                query.ObjectIds     = new[] { context.Source.IndexedProduct.MainProductId };
                query.IncludeFields = context.SubFields.Values.GetAllNodesPaths();

                var response = await mediator.Send(query);

                return(response.Products.Select(expProduct => new ExpVariation(expProduct)).FirstOrDefault());
            });

            FieldAsync <ListGraphType <VariationType> >(
                "variations",
                resolve: async context =>
            {
                var productIds = context.Source.IndexedVariationIds.ToArray();
                if (productIds.IsNullOrEmpty())
                {
                    return(new List <ExpVariation>());
                }

                var query           = context.GetCatalogQuery <LoadProductsQuery>();
                query.ObjectIds     = context.Source.IndexedVariationIds.ToArray();
                query.IncludeFields = context.SubFields.Values.GetAllNodesPaths();

                var response = await mediator.Send(query);

                return(response.Products.Select(expProduct => new ExpVariation(expProduct)));
            });

            Field <BooleanGraphType>(
                "hasVariations",
                resolve: context =>
            {
                var result = context.Source.IndexedVariationIds?.Any() ?? false;
                return(result);
            });

            Field(
                GraphTypeExtenstionHelper.GetActualType <AvailabilityDataType>(),
                "availabilityData",
                "Product availability data",
                resolve: context => new ExpAvailabilityData
            {
                AvailableQuantity = context.Source.AvailableQuantity,
                InventoryAll      = context.Source.AllInventories,
                IsBuyable         = context.Source.IsBuyable,
                IsAvailable       = context.Source.IsAvailable,
                IsInStock         = context.Source.IsInStock,
                IsActive          = context.Source.IndexedProduct.IsActive ?? false,
                IsTrackInventory  = context.Source.IndexedProduct.TrackInventory ?? false,
            });

            Field <ListGraphType <ImageType> >(
                "images",
                "Product images",
                resolve: context =>
            {
                var images = context.Source.IndexedProduct.Images;

                return(context.GetValue <string>("cultureName") switch
                {
                    // Get images with null or current cultureName value if cultureName is passed
                    string languageCode => images.Where(x => string.IsNullOrEmpty(x.LanguageCode) || x.LanguageCode.EqualsInvariant(languageCode)).ToList(),

                    // CultureName is null
                    _ => images
                });
        /// <summary>
        /// Try to find (create if not) categories for products with Category.Path
        /// </summary>
        private void SaveCategoryTree(Catalog catalog, IEnumerable <CsvProduct> csvProducts, ExportImportProgressInfo progressInfo, Action <ExportImportProgressInfo> progressCallback)
        {
            int i = 1;
            var cachedCategoryMap = new Dictionary <string, Category>();

            foreach (var csvProduct in csvProducts.Where(x => x.Category != null && !string.IsNullOrEmpty(x.Category.Path)))
            {
                var    outline = "";
                var    productCategoryNames = csvProduct.Category.Path.Split(_categoryDelimiters);
                string parentCategoryId     = null;
                foreach (var categoryName in productCategoryNames)
                {
                    outline += "\\" + categoryName;
                    Category category;
                    if (!cachedCategoryMap.TryGetValue(outline, out category))
                    {
                        var searchCriteria = new SearchCriteria
                        {
                            CatalogId     = catalog.Id,
                            CategoryId    = parentCategoryId,
                            ResponseGroup = SearchResponseGroup.WithCategories
                        };
                        category = _searchService.Search(searchCriteria).Categories.FirstOrDefault(x => x.Name == categoryName);
                    }

                    if (category == null)
                    {
                        var seo = new SeoInfo();

                        var code = categoryName.GenerateSlug();
                        if (string.IsNullOrEmpty(code))
                        {
                            code = Guid.NewGuid().ToString("N");
                        }

                        // Adding SEO infos to categories.
                        if (addedCategories.Any(s => s.EqualsInvariant(code)))
                        {
                            seo.SemanticUrl = code + i.ToString();
                            i++;
                        }
                        else
                        {
                            addedCategories.Add(code);
                            seo.SemanticUrl = code;
                        }

                        seo.LanguageCode = csvProduct.SeoLanguage;
                        seo.PageTitle    = categoryName;
                        seo.IsActive     = true;
                        seo.Name         = code;

                        category = _categoryService.Create(new Category()
                        {
                            Name      = categoryName,
                            Code      = code,
                            CatalogId = catalog.Id,
                            ParentId  = parentCategoryId,
                            SeoInfos  = new SeoInfo[] { seo }
                        });

                        //Raise notification each notifyCategorySizeLimit category
                        var count = progressInfo.ProcessedCount;
                        progressInfo.Description = $"Creating categories: {++count} created";
                        progressCallback(progressInfo);
                    }

                    csvProduct.CategoryId      = category.Id;
                    csvProduct.Category        = category;
                    parentCategoryId           = category.Id;
                    cachedCategoryMap[outline] = category;
                }
            }
        }
Ejemplo n.º 22
0
        public CategoryType(IMediator mediator, IDataLoaderContextAccessor dataLoader)
        {
            Name = "Category";

            Field(x => x.Id, nullable: false).Description("Id of category.");
            Field(x => x.Category.ImgSrc, nullable: true).Description("The category image.");
            Field(x => x.Category.Code, nullable: false).Description("SKU of category.");
            Field(x => x.Category.Name, nullable: false).Description("Name of category.");
            Field(x => x.Level, nullable: true).Description(@"Level in hierarchy");

            FieldAsync <StringGraphType>("outline", resolve: async context =>
            {
                var outlines = context.Source.Category.Outlines;
                if (outlines.IsNullOrEmpty())
                {
                    return(null);
                }

                var loadRelatedCatalogOutlineQuery      = context.GetCatalogQuery <LoadRelatedCatalogOutlineQuery>();
                loadRelatedCatalogOutlineQuery.Outlines = outlines;

                var response = await mediator.Send(loadRelatedCatalogOutlineQuery);
                return(response.Outline);
            }, description: @"All parent categories ids relative to the requested catalog and concatenated with \ . E.g. (1/21/344)");

            FieldAsync <StringGraphType>("slug", resolve: async context =>
            {
                var outlines = context.Source.Category.Outlines;
                if (outlines.IsNullOrEmpty())
                {
                    return(null);
                }

                var loadRelatedSlugPathQuery      = context.GetCatalogQuery <LoadRelatedSlugPathQuery>();
                loadRelatedSlugPathQuery.Outlines = outlines;

                var response = await mediator.Send(loadRelatedSlugPathQuery);
                return(response.Slug);
            }, description: @"Request related slug for category");

            Field(x => x.Category.Path, nullable: true).Description("Category path in to the requested catalog  (all parent categories names concatenated. E.g. (parent1/parent2))");

            Field <SeoInfoType>("seoInfo", resolve: context =>
            {
                var source      = context.Source;
                var storeId     = context.GetArgumentOrValue <string>("storeId");
                var cultureName = context.GetArgumentOrValue <string>("cultureName");

                SeoInfo seoInfo = null;

                if (!source.Category.SeoInfos.IsNullOrEmpty())
                {
                    seoInfo = source.Category.SeoInfos.GetBestMatchingSeoInfo(storeId, cultureName);
                }

                return(seoInfo ?? GetFallbackSeoInfo(source, cultureName));
            }, description: "Request related SEO info");

            Field <ListGraphType <CategoryDescriptionType> >("descriptions",
                                                             arguments: new QueryArguments(new QueryArgument <StringGraphType> {
                Name = "type"
            }),
                                                             resolve: context =>
            {
                var descriptions = context.Source.Category.Descriptions;
                var cultureName  = context.GetArgumentOrValue <string>("cultureName");
                var type         = context.GetArgumentOrValue <string>("type");
                if (cultureName != null)
                {
                    descriptions = descriptions.Where(x => string.IsNullOrEmpty(x.LanguageCode) || x.LanguageCode.EqualsInvariant(cultureName)).ToList();
                }
                if (type != null)
                {
                    descriptions = descriptions.Where(x => x.DescriptionType?.EqualsInvariant(type) ?? true).ToList();
                }
                return(descriptions);
            });

            Field <CategoryDescriptionType>("description",
                                            arguments: new QueryArguments(new QueryArgument <StringGraphType> {
                Name = "type"
            }),
                                            resolve: context =>
            {
                var descriptions = context.Source.Category.Descriptions;
                var type         = context.GetArgumentOrValue <string>("type");
                var cultureName  = context.GetArgumentOrValue <string>("cultureName");

                if (!descriptions.IsNullOrEmpty())
                {
                    return(descriptions.Where(x => x.DescriptionType.EqualsInvariant(type ?? "FullReview")).FirstBestMatchForLanguage(cultureName) as CategoryDescription
                           ?? descriptions.FirstBestMatchForLanguage(cultureName) as CategoryDescription);
                }

                return(null);
            });

            Field <CategoryType, ExpCategory>("parent").ResolveAsync(ctx =>
            {
                var loader = dataLoader.Context.GetOrAddBatchLoader <string, ExpCategory>("parentsCategoryLoader", (ids) => LoadCategoriesAsync(mediator, ids, ctx));
                if (TryGetCategoryParentId(ctx, out var parentCategoryId))
                {
                    return(loader.LoadAsync(parentCategoryId));
                }
                return(null);
            });

            Field <BooleanGraphType>("hasParent",
                                     "Have a parent",
                                     resolve: context => TryGetCategoryParentId(context, out _));
            Field <ListGraphType <OutlineType> >("outlines",
                                                 "Outlines",
                                                 resolve: context => context.Source.Category.Outlines);
            Field <ListGraphType <ImageType> >("images",
                                               "Images",
                                               resolve: context => context.Source.Category.Images);
            Field <ListGraphType <BreadcrumbType> >("breadcrumbs",
                                                    "Breadcrumbs",
                                                    resolve: context =>
            {
                var store       = context.GetArgumentOrValue <Store>("store");
                var cultureName = context.GetValue <string>("cultureName");

                return(context.Source.Category.Outlines.GetBreadcrumbsFromOutLine(store, cultureName));
            });

            ExtendableField <ListGraphType <PropertyType> >("properties",
                                                            arguments: new QueryArguments(new QueryArgument <ListGraphType <StringGraphType> > {
                Name = "names"
            }),
                                                            resolve: context =>
            {
                var names       = context.GetArgument <string[]>("names");
                var cultureName = context.GetValue <string>("cultureName");
                var result      = context.Source.Category.Properties.ExpandByValues(cultureName);
                if (!names.IsNullOrEmpty())
                {
                    result = result.Where(x => names.Contains(x.Name, StringComparer.InvariantCultureIgnoreCase)).ToList();
                }
                return(result);
            });
        }
Ejemplo n.º 23
0
        public CatalogProduct Convert(ShopifyProduct shopifyProduct, ShopifyImportParams importParams, ShopifyData shopifyData, VirtoData virtoData)
        {
            var retVal = new CatalogProduct
            {
                Id          = shopifyProduct.Handle + "-" + shopifyProduct.Id.ToString(),
                Name        = shopifyProduct.Title,
                Code        = shopifyProduct.Handle,
                StartDate   = shopifyProduct.PublishedAt,
                IsActive    = true,
                CatalogId   = importParams.VirtoCatalogId,
                ProductType = shopifyProduct.ProductType,
                Vendor      = shopifyProduct.Vendor
            };

            //Images
            if (shopifyProduct.Image != null)
            {
                retVal.Images = new List <Image>();
                retVal.Images.Add(Convert(shopifyProduct.Image, true));
            }

            //Review
            if (shopifyProduct.BodyHtml != null)
            {
                retVal.Reviews = new List <EditorialReview>();
                var review = new EditorialReview
                {
                    Content      = shopifyProduct.BodyHtml,
                    LanguageCode = "en-US",
                };
                retVal.Reviews.Add(review);
            }

            //Seo
            retVal.SeoInfos = new List <SeoInfo>();
            var seoInfo = new SeoInfo
            {
                SemanticUrl  = shopifyProduct.Title.GenerateSlug(),
                LanguageCode = "en-US"
            };

            retVal.SeoInfos.Add(seoInfo);

            //TODO: Inventory

            //Variation
            if (shopifyProduct.Variants != null)
            {
                retVal.Variations = new List <CatalogProduct>();
                var isFirst = true;
                foreach (var shopifyVariant in shopifyProduct.Variants)
                {
                    var variation = isFirst ? retVal : new CatalogProduct();
                    variation.Name     = String.Format("{0} ({1})", retVal.Name, shopifyVariant.Title);
                    variation.Code     = (shopifyProduct.Handle + "-" + shopifyVariant.Title).GenerateSlug();
                    variation.IsActive = true;

                    variation.SeoInfos = new List <SeoInfo>();
                    seoInfo            = new SeoInfo
                    {
                        SemanticUrl  = variation.Name.GenerateSlug(),
                        LanguageCode = "en-US"
                    };
                    retVal.SeoInfos.Add(seoInfo);

                    if (shopifyVariant.ImageId != null && shopifyProduct.Images != null)
                    {
                        variation.Images = new List <Image>();
                        var image = shopifyProduct.Images.Where(x => x.Id == shopifyVariant.ImageId).Select(x => Convert(x, true)).FirstOrDefault();
                        if (image != null)
                        {
                            variation.Images.Add(image);
                        }
                    }

                    //Price
                    variation.Prices = new List <Price>();
                    variation.Prices.Add(new Price
                    {
                        Sale     = shopifyVariant.Price,
                        List     = shopifyVariant.Price,
                        Currency = "USD"
                    });


                    //Properties (need refactor)
                    variation.PropertyValues = new List <PropertyValue>();

                    var orderedProperties = shopifyProduct.Options.OrderBy(option => option.Position).ToArray();

                    if (shopifyVariant.Option1 != null)
                    {
                        var propValue = new PropertyValue
                        {
                            PropertyName = orderedProperties[0].Name,
                            Value        = shopifyVariant.Option1,
                            ValueType    = PropertyValueType.ShortText,
                        };
                        variation.PropertyValues.Add(propValue);
                    }
                    if (shopifyVariant.Option2 != null)
                    {
                        var propValue = new PropertyValue
                        {
                            PropertyName = orderedProperties[1].Name,
                            Value        = shopifyVariant.Option2,
                            ValueType    = PropertyValueType.ShortText
                        };
                        variation.PropertyValues.Add(propValue);
                    }
                    if (shopifyVariant.Option3 != null)
                    {
                        var propValue = new PropertyValue
                        {
                            PropertyName = orderedProperties[2].Name,
                            Value        = shopifyVariant.Option3,
                            ValueType    = PropertyValueType.ShortText
                        };
                        variation.PropertyValues.Add(propValue);
                    }

                    if (!isFirst)
                    {
                        retVal.Variations.Add(variation);
                    }
                    isFirst = false;
                }
            }


            if (importParams.ImportCollections)
            {
                var firstCollect = shopifyData.Collects.FirstOrDefault(collect => collect.ProductId == shopifyProduct.Id);
                if (firstCollect != null)
                {
                    retVal.Category = new Category()
                    {
                        Code =
                            shopifyData.Collections.First(collection => collection.Id == firstCollect.CollectionId)
                            .Handle
                    };
                }
            }

            return(retVal);
        }
Ejemplo n.º 24
0
        public CategoryType(IMediator mediator, IDataLoaderContextAccessor dataLoader)
        {
            Name = "Category";

            Field(x => x.Id, nullable: false).Description("Id of category.");
            Field(x => x.Category.ImgSrc, nullable: true).Description("The category image.");
            Field(x => x.Category.Code, nullable: false).Description("SKU of category.");
            Field(x => x.Category.Name, nullable: false).Description("Name of category.");
            Field(x => x.Level, nullable: true).Description(@"Level in hierarchy");

            FieldAsync <StringGraphType>("outline", resolve: async context =>
            {
                var outlines = context.Source.Category.Outlines;
                if (outlines.IsNullOrEmpty())
                {
                    return(null);
                }

                var loadRelatedCatalogOutlineQuery      = context.GetCatalogQuery <LoadRelatedCatalogOutlineQuery>();
                loadRelatedCatalogOutlineQuery.Outlines = outlines;

                var response = await mediator.Send(loadRelatedCatalogOutlineQuery);
                return(response.Outline);
            }, description: @"All parent categories ids relative to the requested catalog and concatenated with \ . E.g. (1/21/344)");

            FieldAsync <StringGraphType>("slug", resolve: async context =>
            {
                var outlines = context.Source.Category.Outlines;
                if (outlines.IsNullOrEmpty())
                {
                    return(null);
                }

                var loadRelatedSlugPathQuery      = context.GetCatalogQuery <LoadRelatedSlugPathQuery>();
                loadRelatedSlugPathQuery.Outlines = outlines;

                var response = await mediator.Send(loadRelatedSlugPathQuery);
                return(response.Slug);
            }, description: @"Request related slug for category");

            Field(x => x.Category.Path, nullable: true).Description("Category path in to the requested catalog  (all parent categories names concatenated. E.g. (parent1/parent2))");

            Field <SeoInfoType>("seoInfo", resolve: context =>
            {
                var source      = context.Source;
                var storeId     = context.GetArgumentOrValue <string>("storeId");
                var cultureName = context.GetArgumentOrValue <string>("cultureName");

                SeoInfo seoInfo = null;

                if (!source.Category.SeoInfos.IsNullOrEmpty())
                {
                    seoInfo = source.Category.SeoInfos.GetBestMatchingSeoInfo(storeId, cultureName);
                }

                return(seoInfo ?? new SeoInfo
                {
                    SemanticUrl = source.Id,
                    LanguageCode = cultureName,
                    Name = source.Category.Name
                });
            }, description: "Request related SEO info");


            Field <CategoryType, ExpCategory>("parent").ResolveAsync(ctx =>
            {
                var loader = dataLoader.Context.GetOrAddBatchLoader <string, ExpCategory>("parentsCategoryLoader", (ids) => LoadCategoriesAsync(mediator, ids, ctx));
                if (TryGetParentId(ctx, out var parentCategoryId))
                {
                    return(loader.LoadAsync(parentCategoryId));
                }
                return(null);
            });

            Field <BooleanGraphType>("hasParent", resolve: context => TryGetParentId(context, out _));

            Field <ListGraphType <OutlineType> >("outlines", resolve: context => context.Source.Category.Outlines);

            Field <ListGraphType <ImageType> >("images", resolve: context => context.Source.Category.Images);
        }