Class DefaultProductService<P extends Product>

java.lang.Object
com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P>
com.broadleafcommerce.data.tracking.core.service.BaseRsqlCrudEntityService<P>
com.broadleafcommerce.catalog.service.product.DefaultProductService<P>
All Implemented Interfaces:
ProductService<P>, com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P>, com.broadleafcommerce.data.tracking.core.service.RsqlCrudEntityService<P>

public class DefaultProductService<P extends Product> extends com.broadleafcommerce.data.tracking.core.service.BaseRsqlCrudEntityService<P> implements ProductService<P>
Author:
Jeff Fischer, Samarth Dhruva (samarthd)
  • Field Details

  • Constructor Details

    • DefaultProductService

      public DefaultProductService(ProductRepository<com.broadleafcommerce.data.tracking.core.Trackable> repository, com.broadleafcommerce.data.tracking.core.service.RsqlCrudEntityHelper helper, VariantService<Variant> variantService, CategoryProductService<CategoryProduct> categoryProductService, @Nullable com.broadleafcommerce.common.extension.cache.CacheStateManager cacheStateManager, com.broadleafcommerce.data.tracking.core.filtering.fetch.FilterParser<cz.jirutka.rsql.parser.ast.Node> parser, com.broadleafcommerce.common.extension.TypeFactory typeFactory)
  • Method Details

    • setSingleIndexRequestMessageFactory

      @Autowired(required=false) public void setSingleIndexRequestMessageFactory(@Nullable com.broadleafcommerce.common.messaging.notification.MessageFactory<com.broadleafcommerce.data.tracking.core.messaging.search.domain.SingleIndexRequest<com.broadleafcommerce.data.tracking.core.Identifiable>> singleIndexRequestMessageFactory)
    • existsById

      public boolean existsById(String id, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Description copied from interface: ProductService
      Returns whether there is a product with the given context ID in the data store.
      Specified by:
      existsById in interface ProductService<P extends Product>
      Parameters:
      id - the ID to search for
      contextInfo - context information around sandboxing and multitenant state
      Returns:
      true if a product exists matching the given ID, false otherwise
    • existsByBusinessType

      public boolean existsByBusinessType(String typeKey, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Description copied from interface: ProductService
      Checks whether any Products exist that use the given BusinessType typeKey.
      Specified by:
      existsByBusinessType in interface ProductService<P extends Product>
      Parameters:
      typeKey - The BusinessType.getTypeKey() to match with.
      contextInfo - Additional multitenant and sandbox information.
      Returns:
      Whether any Products exist that use the given typeKey.
    • readAllByName

      public org.springframework.data.domain.Page<P> readAllByName(@Nullable String name, @Nullable cz.jirutka.rsql.parser.ast.Node filters, @Nullable org.springframework.data.domain.Pageable page, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Specified by:
      readAllByName in interface ProductService<P extends Product>
    • readAllByContextIds

      public org.springframework.data.domain.Page<P> readAllByContextIds(Collection<String> productIds, @Nullable org.springframework.data.domain.Pageable page, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Return all of the products with IDs in the supplied list.
      Specified by:
      readAllByContextIds in interface ProductService<P extends Product>
      Parameters:
      productIds - the product context IDs to search for
      page - the requested page of results from the database
      context - the context to perform the operation in
      Returns:
      the products that matched with the IDs in the given list
    • readAllByCategoryContextId

      public org.springframework.data.domain.Page<P> readAllByCategoryContextId(String categoryId, @Nullable Boolean isSorted, @Nullable cz.jirutka.rsql.parser.ast.Node filters, @Nullable org.springframework.data.domain.Pageable page, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Finds all products in a given category.
      Specified by:
      readAllByCategoryContextId in interface ProductService<P extends Product>
      Parameters:
      categoryId - the context id of the category.
      isSorted - – Whether to return CategoryProducts where CategoryProduct.sorted is true, else false.
      filters - additional filters to apply in the query. Should be EmptyNode if no additional filters should be applied.
      page - the requested amount of results from the database. -1 indicates no limit.
      context - Request context information around sandbox and multitenant state
      Returns:
      All the products in the given category
    • readAllByCategoryContextIdAndSortType

      public org.springframework.data.domain.Page<P> readAllByCategoryContextIdAndSortType(String categoryId, String sortType, @Nullable cz.jirutka.rsql.parser.ast.Node filters, @Nullable org.springframework.data.domain.Pageable page, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Finds all products in a given category and sorts them by the given sort type.
      Specified by:
      readAllByCategoryContextIdAndSortType in interface ProductService<P extends Product>
      Parameters:
      categoryId - the context id of the category
      sortType - the sort type to apply
      filters - additional filters to apply in the query. Should be EmptyNode if no additional filters should be applied.
      page - the requested amount of results from the database. -1 indicates no limit.
      context - Request context information around sandbox and multitenant state
      Returns:
      All the products in the given category sorted by the given sort type
    • readAllWithSortType

      public org.springframework.data.domain.Page<P> readAllWithSortType(String sortType, @Nullable cz.jirutka.rsql.parser.ast.Node filters, @Nullable org.springframework.data.domain.Pageable page, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Finds all products and sorts them by the given sort type.
      Specified by:
      readAllWithSortType in interface ProductService<P extends Product>
      Parameters:
      sortType - the sort type to apply
      filters - additional filters to apply in the query. Should be EmptyNode if no additional filters should be applied.
      page - the requested amount of results from the database. -1 indicates no limit.
      context - Request context information around sandbox and multitenant state
      Returns:
      All products sorted by the given sort type
    • readAllByFiltersExcluding

      public Stream<P> readAllByFiltersExcluding(@Nullable cz.jirutka.rsql.parser.ast.Node filters, @Nullable List<String> exclusions, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Description copied from interface: ProductService
      Returns all of the products matching the given filters, excluding any products whose IDs match any of the values in exclusions.
      Specified by:
      readAllByFiltersExcluding in interface ProductService<P extends Product>
      Parameters:
      filters - the RSQL Node used to restrict results, must not be null
      exclusions - a list of product IDs that should be excluded from the results
      contextInfo - context information surrounding sandboxing and multitenant state
      Returns:
      all of the products matching the given filters, excluding any products whose IDs match any of the values in exclusions
    • readAllByContextIds

      public List<P> readAllByContextIds(@NonNull @NonNull @NonNull Collection<String> productIds, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Description copied from interface: ProductService
      Return all of the products with IDs in the supplied collection.
      Specified by:
      readAllByContextIds in interface ProductService<P extends Product>
      Parameters:
      productIds - the product context IDs to search for
      contextInfo - context information surrounding sandboxing and multitenant state
      Returns:
      the products that matched with the IDs in the given collection
    • readAllByContextIds

      public List<P> readAllByContextIds(@NonNull @NonNull Collection<String> ids, @Nullable cz.jirutka.rsql.parser.ast.Node filters, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Description copied from interface: ProductService
      Return all of the products with IDs in the supplied collection.
      Specified by:
      readAllByContextIds in interface ProductService<P extends Product>
      Parameters:
      ids - the products context IDs to search for
      filters - the filters to apply to the search
      contextInfo - context information surrounding sandboxing and multitenant state
      Returns:
      the products that matched with the IDs in the given collection
    • readByUri

      public Optional<P> readByUri(String uri, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Read a product by a given URI
      Specified by:
      readByUri in interface ProductService<P extends Product>
      Parameters:
      uri - the URI to search for
      Returns:
      an Optional representing a found Product or an empty optional if none found
    • readAllUniqueIds

      public List<String> readAllUniqueIds(int page, @Nullable cz.jirutka.rsql.parser.ast.Node filters)
      Description copied from interface: ProductService
      Return all of the unique product IDs.
      Specified by:
      readAllUniqueIds in interface ProductService<P extends Product>
      Parameters:
      page - the requested amount of results from the database. -1 indicates no limit.
      filters - additional filters to apply in the query. Should be EmptyNode if no additional filters should be applied.
      Returns:
      unique product IDs
    • readAllUniqueIdsPerContext

      public List<String> readAllUniqueIdsPerContext(int page, @Nullable cz.jirutka.rsql.parser.ast.Node filters, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Retrieves a narrowed list of unique product context IDs narrowed on a ContextInfo
      Specified by:
      readAllUniqueIdsPerContext in interface ProductService<P extends Product>
      Parameters:
      page - the requested amount of results from the database. -1 indicates no limit.
      filters - additional filters to apply in the query. Should be EmptyNode if no additional filters should be applied.
      context - The context used to help narrowing. For example, narrowing results to a particular catalog.
      Returns:
      The narrowed list of unique product context IDs
    • readAllUniqueIdsPerContextWithOptionalStipulations

      public List<String> readAllUniqueIdsPerContextWithOptionalStipulations(@Nullable cz.jirutka.rsql.parser.ast.Node filters, @Nullable ProductStipulations stipulations, int pageSize, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Retrieves a list of unique product context IDs narrowed on a ContextInfo
      Specified by:
      readAllUniqueIdsPerContextWithOptionalStipulations in interface ProductService<P extends Product>
      Parameters:
      filters - additional filters to apply in the query.
      stipulations - Additional filtering context to be applied during product fetch. Optional.
      pageSize - the requested amount of results from the database. -1 indicates no limit.
      context - The context used to help narrowing. For example, narrowing results to a particular catalog.
      Returns:
      The narrowed list of unique product context IDs
    • readAllSkusByProductId

      public List<SKUContainer> readAllSkusByProductId(@NonNull @NonNull @NonNull String productId, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Reads all the SKUs for the the specified product ID.
      Specified by:
      readAllSkusByProductId in interface ProductService<P extends Product>
      Parameters:
      productId - the product ID
      context - the information surrounding sandboxing and multitenant state
      Returns:
      the list of SKUContainer for the specified product ID
      See Also:
    • readAllSkusByProduct

      public List<SKUContainer> readAllSkusByProduct(@NonNull @NonNull P product, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Reads all the SKUs for the the specified product. This method is the same as ProductService.readAllSkusByProductId(String, ContextInfo) except it does not perform any query for Product and directly uses the POJO's id and sku for producing the result.
      Specified by:
      readAllSkusByProduct in interface ProductService<P extends Product>
      Parameters:
      product - the Product
      context - the information surrounding sandboxing and multitenant state
      Returns:
      the list of SKUContainer for the specified product ID
    • readAllSkusByProductIdAndQuery

      public List<SKUContainer> readAllSkusByProductIdAndQuery(@NonNull @NonNull @NonNull String productId, @NonNull @NonNull @NonNull String sku, @Nullable cz.jirutka.rsql.parser.ast.Node filters, @Nullable org.springframework.data.domain.Pageable page, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Reads all the SKUs for the the specified product ID and SKU identifier.
      Specified by:
      readAllSkusByProductIdAndQuery in interface ProductService<P extends Product>
      Parameters:
      productId - the product ID
      sku - the SKU identifier to search
      filters - the RSQL Node used to restrict result
      page - the requested page of results from the database
      context - the information surrounding sandboxing and multitenant state
      Returns:
      the list of SKUContainer for the specified Product id
    • getRepositoryDomain

      @NonNull public String getRepositoryDomain()
      Specified by:
      getRepositoryDomain in interface ProductService<P extends Product>
    • readAllByUris

      public List<P> readAllByUris(@NonNull @NonNull Iterable<String> uris, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Description copied from interface: ProductService
      Finds the product matching the uris.
      Specified by:
      readAllByUris in interface ProductService<P extends Product>
      Parameters:
      uris - URIs to match
      contextInfo - the information surrounding sandboxing and multitenant state
      Returns:
      The product matching the uris
    • readAllByExternalIds

      public List<P> readAllByExternalIds(Collection<String> externalIds, com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Description copied from interface: ProductService
      Fetches products based on the provided external IDs.
      Specified by:
      readAllByExternalIds in interface ProductService<P extends Product>
      Parameters:
      externalIds - a collection of external IDs
      contextInfo - the information surrounding sandboxing and multitenant state
      Returns:
      Products matching the provided external IDs
    • readAllByContextIdAndInheritanceLine

      public List<P> readAllByContextIdAndInheritanceLine(Set<String> contextIds, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Description copied from interface: ProductService
      Finds all products by context id for a given catalog inheritance line
      Specified by:
      readAllByContextIdAndInheritanceLine in interface ProductService<P extends Product>
      Parameters:
      contextIds - the context ids to find
      contextInfo - the information surrounding sandboxing and multitenant state, used to determine the catalog inheritance line
      Returns:
      All products by context id for a given catalog inheritance line
    • create

      public P create(@NonNull P businessInstance, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Performs the same behavior as BaseCrudEntityService.create(Object, ContextInfo) with the addition of Product.getPrimaryCategory() and ProductCharacteristic management.
      Specified by:
      create in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      create in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
      Parameters:
      businessInstance - The business domain instance. In general, the DomainMapperManager is responsible for converting to a repository platform type for persistence.
      context - Context information used to discriminate the correct version of an entity by context id when multiple verions may be available across sandboxes, catalogs and applications.
      Returns:
      the created product
    • doWithForceBuiltAndSuppressedSingleIndexRequest

      protected <V> V doWithForceBuiltAndSuppressedSingleIndexRequest(Supplier<V> supplier)
      Do the requested work, simultaneously leveraging SuppressNotificationContext for SingleIndexRequest to prevent initial message send, but still forcing the notification state to be built via SingleIndexRequestNotificationStateBuildContext
      Type Parameters:
      V - return type of the supplier
      Parameters:
      supplier - the requested work to do
      Returns:
      the result of executing the requested supplier
      Since:
      DataTracking 2.0.7
    • getCollectedPersistedDomainInstancesAndNotifySingleIndexRequest

      protected void getCollectedPersistedDomainInstancesAndNotifySingleIndexRequest(Set<String> productContextIds, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)

      In product CRUD flows, we don't want to emit the SingleIndexRequest on the product until the characteristics have been properly persisted/updated as well (thereby guaranteeing that reindexing will only be requested once everything has settled).

      Thus, we expect that when the product is persisted, SuppressNotificationContext is used to disable emission of SingleIndexRequest messages. Note that we still expect SingleIndexRequestNotificationStateMapperMember to run and establish the NotificationState - we just want to delay the initial send until after the characteristics have all been persisted. We also expect that the product persistence flow leverages CollectedProductPersistedDomainContext to collect the persisted domain instances into a thread local.

      After the product and characteristics are finished persisting, this method should be called to access the CollectedProductPersistedDomainContext and invoke the single index request notification on those instances.

      Parameters:
      productContextIds - context IDs that we want to notify on
      contextInfo - context information
    • notifySingleIndexRequest

      protected void notifySingleIndexRequest(com.broadleafcommerce.data.tracking.core.Trackable domain, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Replicates what CrudEntityHelper.notify(Trackable, ContextInfo, NotificationStateRepository) does for SingleIndexRequest.
      Parameters:
      domain - the persisted domain instance to pass to NotificationManager.handleAsync(NotificationStateRepository, NotificationStateAware, String)
      context - context information
    • update

      public P update(@NonNull @NonNull String id, @NonNull P businessInstance, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Performs the same behavior as BaseCrudEntityService.update(String, Object, ContextInfo) with the addition of ProductCharacteristic management.
      Specified by:
      update in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      update in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
      Parameters:
      id - The context id for the entity. This is the id by which the business recognizes the item.
      businessInstance - The payload type that domain class should be converted to. In general, the payload is what the rest API responds with.
      context - Context information used to discriminate the correct version of an entity by context id when multiple versions may be available across sandboxes, catalogs and applications.
      Returns:
      the updated product
    • replace

      public P replace(@NonNull @NonNull String id, @NonNull P businessInstance, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Performs the same behavior as BaseCrudEntityService.replace(String, Object, ContextInfo) with the addition of Product.getPrimaryCategory() and ProductCharacteristic management.
      Specified by:
      replace in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      replace in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
      Parameters:
      id - The context id for the entity. This is the id by which the business recognizes the item.
      businessInstance - The payload type that domain class should be converted to. In general, the payload is what the rest API responds with.
      context - Context information used to discriminate the correct version of an entity by context id when multiple versions may be available across sandboxes, catalogs and applications.
      Returns:
      the replaced product
    • readProductCountUsingReferencedOptionTemplate

      public long readProductCountUsingReferencedOptionTemplate(@NonNull @NonNull String optionTemplateId, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Description copied from interface: ProductService
      Returns the count of products that have ProductOption that is isAddedByReference with the given option template ID.

      This is useful for validation purposes to prevent deletion of an option template that is in use.

      Specified by:
      readProductCountUsingReferencedOptionTemplate in interface ProductService<P extends Product>
      Parameters:
      optionTemplateId - the option template ID to check for references
      context - the context information surrounding sandboxing and multitenant state
      Returns:
      the count of products that reference the given option template ID
    • createAll

      public List<P> createAll(List<P> businessInstances, com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Performs the same behavior as BaseCrudEntityService.createAll(List, ContextInfo) with the addition of ProductCharacteristic management.
      Specified by:
      createAll in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      createAll in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
      Parameters:
      businessInstances - the list of business instances to create
      context - context information surrounding sandboxing and multitenant state
      Returns:
      the created products
    • createAllAllowingPartialSuccess

      public com.broadleafcommerce.data.tracking.core.service.BulkPersistenceResponse<P> createAllAllowingPartialSuccess(List<P> businessInstances, com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Specified by:
      createAllAllowingPartialSuccess in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      createAllAllowingPartialSuccess in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
    • replaceAll

      public List<P> replaceAll(List<com.broadleafcommerce.data.tracking.core.service.Update<P>> replacements, com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Performs the same behavior as BaseCrudEntityService.replaceAll(List, ContextInfo) with the addition of ProductCharacteristic management.
      Specified by:
      replaceAll in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      replaceAll in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
      Parameters:
      replacements - the list of updates to replace
      context - context information surrounding sandboxing and multitenant state
      Returns:
      the replaced products
    • replaceAllAllowingPartialSuccess

      public com.broadleafcommerce.data.tracking.core.service.BulkPersistenceResponse<P> replaceAllAllowingPartialSuccess(List<com.broadleafcommerce.data.tracking.core.service.Update<P>> replacements, com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Specified by:
      replaceAllAllowingPartialSuccess in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      replaceAllAllowingPartialSuccess in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
    • updateAll

      public List<P> updateAll(List<com.broadleafcommerce.data.tracking.core.service.Update<P>> updates, com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Performs the same behavior as BaseCrudEntityService.updateAll(List, ContextInfo) with the addition of ProductCharacteristic management.
      Specified by:
      updateAll in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      updateAll in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
      Parameters:
      updates - the list of updates to perform
      context - context information surrounding sandboxing and multitenant state
      Returns:
      the updated products
    • updateAllAllowingPartialSuccess

      public com.broadleafcommerce.data.tracking.core.service.BulkPersistenceResponse<P> updateAllAllowingPartialSuccess(List<com.broadleafcommerce.data.tracking.core.service.Update<P>> updates, com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Specified by:
      updateAllAllowingPartialSuccess in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      updateAllAllowingPartialSuccess in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
    • extractSuccessfulProductIds

      protected Set<String> extractSuccessfulProductIds(com.broadleafcommerce.data.tracking.core.service.BulkPersistenceResponse<P> bulkPersistenceResponse)
    • populateFullyPersistedProducts

      protected void populateFullyPersistedProducts(ProductCharacteristicManagementRequest request, List<P> persistedProducts)
    • populateFullyPersistedProducts

      protected void populateFullyPersistedProducts(ProductCharacteristicManagementRequest request, com.broadleafcommerce.data.tracking.core.service.BulkPersistenceResponse<P> response)
    • managePrimaryCategory

      protected void managePrimaryCategory(@NonNull @NonNull String productId, @Nullable Category requestedPrimary, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Enables direct management of the primary category product relationship for a product.

      • If requestedPrimary is null or doesn't have an ID, the current primary category-product relationship will be unmarked as primary if it exists
      • If requestedPrimary is already the primary category for the product, nothing will be changed
      • If the product currently has a different primary category, it will be unmarked as primary before the new primary is set
      • If there is already a category-product relationship between the product and the requested primary, it will simply be updated to be set as primary
      • If there is not already a category-product relationship between the product and the requested primary, a new one will be created
      Parameters:
      productId - the id of the product for which the primary category needs to be managed
      requestedPrimary - the requested primary category (typically supplied by an API caller in Product.getPrimaryCategory())
      contextInfo - context information surrounding sandboxing and multitenant state
    • getOverriddenChangeContainerContext

      @Nullable protected com.broadleafcommerce.data.tracking.core.context.ContextInfo getOverriddenChangeContainerContext(@Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context, String product)
    • changeContainerIdAlreadySet

      protected boolean changeContainerIdAlreadySet(@Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
    • overrideChangeContainerId

      @Nullable protected com.broadleafcommerce.data.tracking.core.context.ContextInfo overrideChangeContainerId(String changeContainerId, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
    • copyChangeContainer

      protected com.broadleafcommerce.data.tracking.core.filtering.domain.ChangeContainer copyChangeContainer(com.broadleafcommerce.data.tracking.core.filtering.domain.ChangeContainer changeContainer)
    • unsetCurrentPrimaryCategoryProduct

      protected void unsetCurrentPrimaryCategoryProduct(@NonNull @NonNull String productId, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Finds the current primary category product for the given productId and unmarks it as primary if it exists.
      Parameters:
      productId - the ID of the product whose primary category product should be unmarked
      contextInfo - context information surrounding sandboxing and multitenant state
    • getCurrentPrimaryCategoryProduct

      protected Optional<CategoryProduct> getCurrentPrimaryCategoryProduct(@NonNull @NonNull String productId, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      Finds the current primary category product for the given productId.
      Parameters:
      productId - the ID of the product whose primary category product should be found
      contextInfo - context information surrounding sandboxing and multitenant state
      Returns:
      an Optional containing the primary category product if found, else Optional.empty()
    • buildPrimaryCategoryProduct

      protected CategoryProduct buildPrimaryCategoryProduct(@NonNull @NonNull String productId, @NonNull @NonNull String categoryId)
      Builds a new CategoryProduct POJO for productId and categoryId with CategoryProduct.isPrimary() set to true.
      Parameters:
      productId - the ID of the product to set on the new category-product
      categoryId - the ID of the category to set on the new category-product
      Returns:
      a new primary CategoryProduct POJO for the given entities
    • delete

      public void delete(@NonNull @NonNull String id, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Specified by:
      delete in interface com.broadleafcommerce.data.tracking.core.service.CrudEntityService<P extends Product>
      Overrides:
      delete in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
    • isEligibleForClearOverride

      protected boolean isEligibleForClearOverride(Product product, @Nullable String targetCatalogId)
      Parameters:
      product - the product instance for which a 'clear overrides' request has been submitted by the caller
      targetCatalogId - the catalog ID which the 'clear overrides' request has been determined to target its changes in
      Returns:
      whether we should proceed with the 'clear overrides' request for the product, or if we should skip. See delete(String, ContextInfo) for broader context on why this precondition is necessary, particularly when considering characteristics management.
      Since:
      Catalog Service 2.3.0, Release Train 2.3.0
    • isEntityDirectlyDefinedInTargetCatalog

      protected boolean isEntityDirectlyDefinedInTargetCatalog(Product product, @Nullable String targetCatalogId)
      Parameters:
      product - the product instance to evaluate
      targetCatalogId - the catalog ID which the API caller's request has been determined to target its changes in
      Returns:
      whether the given product is directly defined in the specified target catalog (as opposed to being inherited from a parent catalog)
      Since:
      Catalog Service 2.3.0, Release Train 2.3.0
    • containsAnyProductionLevelFieldChanges

      protected boolean containsAnyProductionLevelFieldChanges(com.broadleafcommerce.data.tracking.core.filtering.business.domain.ContextState contextState)
      Parameters:
      contextState - the context state of an entity
      Returns:
      whether the entity contains any production-level field changes that would indicate it is a production-level override record
      Since:
      Catalog Service 2.3.0, Release Train 2.3.0
    • determineTargetCatalogIdForDelete

      @Nullable protected String determineTargetCatalogIdForDelete(P product, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo contextInfo)
      See delete(String, ContextInfo) for broader context on why this evaluation is necessary.
      Parameters:
      product - the product being targeted for delete
      contextInfo - the current context from which to derive the catalog that the changes will target
      Returns:
      the actual catalog ID that the delete operation will end up impacting
      Since:
      Catalog Service 2.3.0, Release Train 2.3.0
    • getOverrideOrBaseCatalogId

      @Nullable protected String getOverrideOrBaseCatalogId(com.broadleafcommerce.data.tracking.core.filtering.business.domain.ContextState contextState)
      Parameters:
      contextState - the context state to extract catalog information from
      Returns:
      the ContextState.getOverrideCatalogId() if set, else ContextState.getCatalog() ID. This allows us to clearly identify the catalog in which the entity actually resides. See ContextStateBuilder to understand where these fields come from
      Since:
      Catalog Service 2.3.0, Release Train 2.3.0
    • validateNoNonProductionRecordsForRelatedEntities

      protected void validateNoNonProductionRecordsForRelatedEntities(@NonNull @NonNull String productIdToDelete, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Validates that there are no non-production records for the relationship entities for the product being deleted.
      Parameters:
      productIdToDelete - the id of the product being deleted
      context - context info for multitenant and sandbox conditions
    • throwIfHasRecords

      protected void throwIfHasRecords(@NonNull @NonNull BiFunction<Collection<String>,com.broadleafcommerce.data.tracking.core.context.ContextInfo,Long> countFunction, @NonNull @NonNull String entityType, @NonNull @NonNull String productIdToDelete, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Throws an UnsupportedOperationException if the given count function has a count > 0.
      Parameters:
      countFunction - a BiFunction used to get the count of non-production records matching the product id
      entityType - the type of entity that the count function is for, e.g. Variant, ProductTag
      productIdToDelete - the id of the product being deleted
      context - context info for multitenant and sandbox conditions
    • getSandboxRecordValidationError

      protected String getSandboxRecordValidationError(@NonNull @NonNull String entityType, @NonNull @NonNull String productIdToDelete, long count)
    • clearReferencedOptions

      protected List<ProductOption> clearReferencedOptions(@NotNull P businessInstance)
      Iterates through a Product.getOptions() list to clear generated fields of options where ProductOption.isAddedByReference() is true.
      Parameters:
      businessInstance - the business instance
      Returns:
      a List of ProductOption without fields generated by reference
    • gatherAndValidateDeletableProductCharacteristics

      protected List<ProductCharacteristic> gatherAndValidateDeletableProductCharacteristics(P product, @Nullable String targetCatalogId, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Parameters:
      product - the product being targeted for delete
      targetCatalogId - the catalog ID which the API caller's request has been determined to target its changes in
      context - the current catalog/tenant context the request is operating in
      Returns:
      the list of characteristics that should be requested for delete or clear override for the requested product
      Since:
      Catalog Service 2.3.0, Release Train 2.3.0
    • manageProductCharacteristics

      protected ProductCharacteristicManagementResult manageProductCharacteristics(@NonNull @NonNull String id, @NonNull P apiPayload, @NonNull P persistedProduct, @Nullable com.broadleafcommerce.data.tracking.core.context.ContextInfo context)
      Manages the characteristics of a single product. This is a convenience method that wraps the more general ProductCharacteristicManagementUtility.manageProductCharacteristics(ProductCharacteristicManagementRequest, ContextInfo) method for a single product.
      Parameters:
      id - the ID of the product
      apiPayload - the incoming product data from the API
      persistedProduct - the currently persisted state of the product
      context - the context information for the request
      Returns:
      a ProductCharacteristicManagementResult containing the latest state of the product characteristics
    • getRepository

      protected ProductRepository<com.broadleafcommerce.data.tracking.core.Trackable> getRepository()
      Overrides:
      getRepository in class com.broadleafcommerce.data.tracking.core.service.BaseCrudEntityService<P extends Product>
    • getVariantService

      protected VariantService<Variant> getVariantService()
    • getCategoryProductService

      protected CategoryProductService<CategoryProduct> getCategoryProductService()
    • setCacheByActiveProductKeyGen

      @Autowired @Qualifier("catalogCacheByActiveProduct") public void setCacheByActiveProductKeyGen(@Nullable com.broadleafcommerce.common.extension.cache.key.ContextKeyGen cacheByActiveProductKeyGen)
      See Also:
    • getCacheByActiveProductKeyGen

      @Nullable protected com.broadleafcommerce.common.extension.cache.key.ContextKeyGen getCacheByActiveProductKeyGen()
      See Also:
    • setCacheByActiveProductUriKeyGen

      @Autowired @Qualifier("catalogCacheByActiveProductUri") public void setCacheByActiveProductUriKeyGen(@Nullable com.broadleafcommerce.common.extension.cache.key.ContextKeyGen cacheByActiveProductUriKeyGen)
      See Also:
    • getCacheByActiveProductUriKeyGen

      @Nullable protected com.broadleafcommerce.common.extension.cache.key.ContextKeyGen getCacheByActiveProductUriKeyGen()
      See Also:
    • getParser

      protected com.broadleafcommerce.data.tracking.core.filtering.fetch.FilterParser<cz.jirutka.rsql.parser.ast.Node> getParser()
    • getTypeFactory

      protected com.broadleafcommerce.common.extension.TypeFactory getTypeFactory()
    • getProductTagService

      protected ProductTagService<ProductTag> getProductTagService()
    • setProductTagService

      @Autowired @Lazy public void setProductTagService(ProductTagService<ProductTag> productTagService)
    • getPromotionalProductService

      protected PromotionalProductService<PromotionalProduct> getPromotionalProductService()
    • setPromotionalProductService

      @Autowired @Lazy public void setPromotionalProductService(PromotionalProductService<PromotionalProduct> promotionalProductService)
    • getProductAssetService

      protected ProductAssetService<ProductAsset> getProductAssetService()
    • setProductAssetService

      @Autowired public void setProductAssetService(ProductAssetService<ProductAsset> productAssetService)
    • getTranslationEntityService

      protected com.broadleafcommerce.translation.service.TranslationEntityService<com.broadleafcommerce.translation.domain.Translation> getTranslationEntityService()
    • setTranslationEntityService

      @Autowired public void setTranslationEntityService(com.broadleafcommerce.translation.service.TranslationEntityService<com.broadleafcommerce.translation.domain.Translation> translationEntityService)
    • getProductCharacteristicService

      protected ProductCharacteristicService<ProductCharacteristic> getProductCharacteristicService()
    • setProductCharacteristicService

      @Autowired @Lazy public void setProductCharacteristicService(ProductCharacteristicService<ProductCharacteristic> productCharacteristicService)
    • getCatalogFinder

      protected com.broadleafcommerce.data.tracking.core.policy.trackable.CatalogFinder<com.broadleafcommerce.data.tracking.core.tenant.domain.Catalog> getCatalogFinder()
    • setCatalogFinder

      @Autowired @Lazy public void setCatalogFinder(com.broadleafcommerce.data.tracking.core.policy.trackable.CatalogFinder<com.broadleafcommerce.data.tracking.core.tenant.domain.Catalog> catalogFinder)
    • getNotificationManager

      protected com.broadleafcommerce.common.messaging.notification.NotificationManager getNotificationManager()
    • setNotificationManager

      @Autowired public void setNotificationManager(com.broadleafcommerce.common.messaging.notification.NotificationManager notificationManager)
    • getBusinessTypeService

      protected BusinessTypeService<BusinessType> getBusinessTypeService()
    • setBusinessTypeService

      @Autowired public void setBusinessTypeService(BusinessTypeService<BusinessType> businessTypeService)
    • getCharacteristicService

      protected CharacteristicService<Characteristic> getCharacteristicService()
    • setCharacteristicService

      @Autowired public void setCharacteristicService(CharacteristicService<Characteristic> characteristicService)
    • getSingleIndexRequestMessageFactory

      @Nullable protected com.broadleafcommerce.data.tracking.core.messaging.search.SingleIndexRequestMessageFactory getSingleIndexRequestMessageFactory()
    • getProductHydrationService

      protected ProductHydrationService getProductHydrationService()
    • setProductHydrationService

      @Autowired @Lazy public void setProductHydrationService(ProductHydrationService productHydrationService)
    • getTrackableBehaviorUtil

      @NonNull protected com.broadleafcommerce.data.tracking.core.TrackableBehaviorUtil getTrackableBehaviorUtil()
    • setTrackableBehaviorUtil

      @Autowired public void setTrackableBehaviorUtil(com.broadleafcommerce.data.tracking.core.TrackableBehaviorUtil trackableBehaviorUtil)
    • getCharacteristicManagementUtility

      protected ProductCharacteristicManagementUtility<P> getCharacteristicManagementUtility()
    • setCharacteristicManagementUtility

      @Autowired public void setCharacteristicManagementUtility(ProductCharacteristicManagementUtility<P> characteristicManagementUtility)