Skip to main content

DkHome - Item sync

DkHome Connector - Item Update The DkHome Connector's Item Update function synchronizes product information from the DkHome REST API to t...

Updated over a week ago

DkHome Connector - Item Update

The DkHome Connector's Item Update function synchronizes product information from the DkHome REST API to the App4Sales internal item database. This process runs periodically to ensure that product details, pricing, stock levels, images, and classifications are up-to-date within the App4Sales platform. It retrieves items in batches and processes them, updating various related entities like item descriptions, free fields, prices, and classifications.

Data Source Configuration

The DkHome connector retrieves item data via a REST API, which is configured using various endpoints. The base URL for the API is defined in the connector's settings. Data is pulled from the API in a paginated manner, allowing for efficient synchronization of large datasets.

  • Items: Fetched from the /Items endpoint. Supports pagination using the $skip parameter (e.g., /Items?$orderby=ItemCode&$skip={offset}).

  • Sales Prices: Item-specific sales prices are included with each item or fetched in batches from the /ItemPrices endpoint if UseItemPricesBatch is enabled.

  • Warehouses: Retrieved from the /Warehouses endpoint.

  • Item Group Name Translations: Retrieved from the /ItemGroupNameTranslations endpoint.

  • Item Group Value Translations: Retrieved from the /ItemGroupValueTranslations endpoint.

Data Mapping Table: Items (RestJsonItem to App4Sales Item)

App4Sales Field

Source Field (API/Excel/DB)

Logic/Notes

CreatedDate

Created

Timestamp of item creation. Falls back to current date/time if source is null.

EanCode

EanCode

European Article Number. Direct mapping.

FreeSortField

FreeSortField

A flexible field for custom sorting criteria. Direct mapping.

ItemCode

ItemCode

Unique identifier for the item. Whitespace is trimmed.

LastAvailableStock

LastAvailableStock

The most recently available stock quantity. Direct mapping.

NextDelivery

NextDelivery

Expected date of next stock delivery. Direct mapping.

PurchasePackageSize

PurchasePackageSize

Quantity per purchase package. Direct mapping.

SalesPrice

SalesPriceExcl

Base sales price excluding VAT.

Unit

Unit

Unit of measure for the item (e.g., 'pcs', 'kg'). Direct mapping.

Sysmodified

Modified

Timestamp of last modification in the ERP. Falls back to current date/time if source is null.

VatIncluded

Derived

Hardcoded to 'E'.

VatPercentage

VatPercentage

The VAT percentage applicable to the item. Direct mapping.

AcceptsDefaultDiscount

AcceptsDefaultDiscount

Boolean indicating if the item is eligible for default discounts. Direct mapping.

MatrixParent

MatrixCode

Code for the parent item in a matrix structure.

MatrixParentDescription

MatrixDescription

Description for the parent item in a matrix structure.

MatrixParentId

MatrixId

Unique ID for the parent item in a matrix structure.

MatrixXValue

MatrixXValue

Value for the X-axis of a matrix item (e.g., 'Small', 'Red').

MatrixXDescription

MatrixXDescription

Description for the X-axis of a matrix item.

MatrixYValue

MatrixYValue

Value for the Y-axis of a matrix item (e.g., 'Cotton', 'Blue').

MatrixYDescription

MatrixYDescription

Description for the Y-axis of a matrix item.

Data Mapping Table: Item Descriptions

App4Sales Field

Source Field (API/Excel/DB)

Logic/Notes

Description, Description2, ..., Description5

Descriptions (List of RestJsonDescription) -> Description property

The Description property from the source is mapped to one of the five App4Sales description fields based on the DescriptionField property of the matched language configuration (1-5). If a language configuration is not found or the source description is null, it is skipped.

Data Mapping Table: Free Item Fields

App4Sales Field

Source Field (API/Excel/DB)

Logic/Notes

FreeItemFields

FreeFields (List of RestJsonFreeField)

Converts a list of key-value pairs (Key, Value) from RestJsonFreeField into an XML string.

Data Mapping Table: Item Prices

The connector processes sales prices provided with the items. Each RestJsonItemPrice from the source is used to update the App4Sales item price data.

App4Sales Field

Source Field (API/Excel/DB)

Logic/Notes

ItemCode (in ItemPriceDataTable)

ItemCode (from RestJsonItemPrice) or parent ItemCode

The ItemCode is set on each RestJsonItemPrice. If the source ItemCode is empty, the ItemCode of the parent item is used. The value is trimmed.

Price (in ItemPriceDataTable)

PriceExcl (from RestJsonItemPrice)

The sales price excluding VAT.

Id, Code, Description (in ItemPriceDataTable)

PriceList (GUID) or PriceListExternalId (string) from RestJsonItemPrice, matched against RestJsonPriceList

The connector attempts to match the PriceList GUID or PriceListExternalId from the item price to an existing RestJsonPriceList. If a match is found, its Code and Description are used. If no specific price list is found and a default PriceList 1 is not provided by the ERP, a default PriceList 1 ("Default") will be created. If PriceList 1 exists in the ERP, prices without an explicit price list are skipped to prevent overwriting ERP data.

Data Mapping Table: Item Classes / Item Groups (Hierarchical - when 'Use multiple item group levels' is enabled)

When the 'Use multiple item group levels' setting is enabled, the connector processes hierarchical item groups from the source. These are mapped to App4Sales ItemClass and ItemClassValueDescription entities.

App4Sales Field

Source Field (API/Excel/DB)

Logic/Notes

ItemClass.Description

Derived from hierarchy level

The description of the ItemClass is set to the hierarchy level (e.g., "1", "2", "3").

ItemClass.Id

Derived from hierarchy level

The ID of the ItemClass is set to the hierarchy level (e.g., 1, 2, 3).

ItemClassValue.Value

RestJsonItemGroup.Name or RestJsonItemGroup.DutchText

The concrete value for an ItemClass. Name is preferred; DutchText is used as a fallback if Name is empty.

ItemClassValueDescription.Value

RestJsonItemGroup.DutchText, GermanText, FrenchText

Translations for the ItemClassValue. Mapped to LanguageCode "nl", "de", "fr" respectively.

Data Mapping Table: Item Classes / Item Groups (Flat - when 'Use multiple item group levels' is disabled)

When the 'Use multiple item group levels' setting is disabled, the connector processes a flat list of item groups from the source. These are mapped to App4Sales ItemClass entities.

App4Sales Field

Source Field (API/Excel/DB)

Logic/Notes

ItemClass.Description

RestJsonItemGroup.Name

The name of the item class.

ItemClassValue.Value

RestJsonItemGroup.Value

The concrete value for the item class, only if RestJsonItemGroup.Value is not null.

Special Logic & Filters

  • Pagination: Items are retrieved iteratively using $skip to handle large datasets, fetching a batch of items in each loop.

  • Duplicate Item Code Detection: If DisallowDuplicateData is enabled in settings, the system checks for duplicate item codes within batches. If duplicates are found, the synchronization is stopped.

  • Batch Update Control: The synchronization loop can be prematurely exited if DisableBatchUpdate is enabled in settings (e.g., for specific legacy connectors).

  • Item Group Processing: The method uses UseMultipleItemGroupLevels setting to determine whether to process item groups as a flat list or a hierarchical structure (Lookbooks/Editions).

    • If UseMultipleItemGroupLevels is true and Session.Administration.Upgraded is true, Lookbooks and Lookbook Items are updated.

    • If UseMultipleItemGroupLevels is true and Session.Administration.Upgraded is false, Editions and Mood Pictures are updated.

  • Picture Handling: Images are downloaded only if AdministrationSession.CurrentSession.PimSettings.UseImagesOnlyFromPIM is false. Pictures can be downloaded from PictureUrls (a list of URLs with sequence) or a single PictureUrl.

    • SetPictureOnItem: This helper method downloads images from the provided URL, handles Base64 conversion, caches downloaded images to avoid re-downloading, and stores them in item.PicturesBytes. It also tracks invalid URLs to prevent repeated download attempts.

    • Settings.UseRelativePictureUrl determines whether to download raw content or from a full URL.

  • Stock Indicator: The item's StockIndicator is taken directly from the RestJsonItem if available; otherwise, it's looked up from the database using the ItemCode. If no stock indicator is found, it defaults to -1.

  • Full Stock Values: If a specific Settings.Warehouse is not defined, and RestJsonItem.StockValues are present, these are stored in fullStockValues. If AvailableStock is not explicitly provided in StockValues, it's calculated using a formula (`ExecuteStockFormula()`).

  • Language Processing: Languages for descriptions are added dynamically based on available translations.

  • Error Handling: Catches RestException, RequestException, and general Exception during API calls and processing, logging errors with relevant context (route, content).

Domain Specifics (Expanded)

Price Logic

The DkHome connector retrieves sales prices directly from the SalesPriceExcl field within the item data or via a batch call to the /ItemPrices endpoint. These prices are stored in the App4Sales system as ItemPriceDataTable entries.

  • **Base Price:** SalesPriceExcl from the RestJsonItem maps to SalesPrice in App4Sales.

  • **Price Lists:** The PriceList GUID or PriceListExternalId associated with each sales price from the source is used to identify or create the corresponding Price List in App4Sales.

    • If the ERP provides a PriceList with Code 1, this is used as the default.

    • If no PriceList is explicitly linked to a price and no ERP-provided PriceList with Code 1 exists, a "Default" Price List (Code 1) is created in App4Sales.

    • Prices from the ERP that are not linked to a known PriceList are skipped if a default PriceList 1 is already provided by the ERP.

  • **Currency:** The currency symbol for the default price list is derived from Session.Administration.CurrencySymbol.

Image Handling

The connector can retrieve product images from specified URLs. This process is active only if images are not solely managed by PIM (Product Information Management) system.

  • **Data Sources:** Image URLs are provided either as a list (PictureUrls) with sequence numbers or as a single PictureUrl within the RestJsonItem entity.

  • **Filenames & Matching:** Image URLs are processed directly.

  • **Formats:** Assumes images can be converted to Base64.

  • **Limitations:** No explicit resize/compression logic is mentioned in the code; it downloads and converts the image as-is. Error handling is present for download failures and invalid Base64 strings. Missing images will result in an empty Base64Picture and the URL being marked as invalid.

  • **Relative URLs:** The UseRelativePictureUrl setting determines if image URLs are treated as relative paths for downloading raw content.

Stock & Availability

Stock information is updated with each item synchronization, providing both an overall stock indicator and detailed stock values per item.

  • **Stock Indicator:** The StockIndicator (integer) from the RestJsonItem is directly used if available. Otherwise, the system attempts to retrieve it from existing stock indicators in the database based on the ItemCode. If still not found, it defaults to -1.

  • **Detailed Stock Values:** The StockValues (a list of key-value pairs like AvailableStock, ShelfStock, ToBeReceived, ToBeDelivered) from the RestJsonItem are used when no specific warehouse is configured in settings.

    • LastAvailableStock in App4Sales is set from RestJsonItem.LastAvailableStock directly, or calculated using the ExecuteStockFormula() if not explicitly provided in StockValues.

  • **Multi-warehouse:** The Warehouse setting allows filtering stock for a specific warehouse. If this setting is empty, all stock values provided by the ERP are considered.

Matrix & Attributes

The DkHome connector supports the synchronization of matrix items and their attributes.

  • **Parent-Child Relationships:** Identified through MatrixCode, MatrixDescription, and MatrixId (for the parent) and MatrixXValue, MatrixXDescription, MatrixYValue, MatrixYDescription for the child variants.

  • **Attributes:** Item classifications are handled via Item Groups from the source.

Classification & Attributes

Item classifications are derived from RestJsonItemGroup entities, which can be processed in a flat or hierarchical manner based on connector settings.

  • **Item Classes & Values:** RestJsonItemGroup.Name and RestJsonItemGroup.Value are used to create ItemClass and ItemClassValue objects in App4Sales. The DutchText property can serve as a fallback for the ItemClassValue.Value if Name is empty.

  • **Hierarchical (Lookbooks/Editions):** If UseMultipleItemGroupLevels is enabled, item groups are mapped to a multi-level structure.

    • Level "1", "2", etc., become ItemClass.Description and ItemClass.Id.

    • Translations for ItemClassValueDescription (Dutch, German, French) are created from RestJsonItemGroup.DutchText, GermanText, FrenchText.

  • **Translations:** Item group names and values can have associated translations which are retrieved from the API via /ItemGroupNameTranslations and /ItemGroupValueTranslations endpoints and used to update ItemClassDescriptions and ItemClassValueDescriptions.

Related Settings & Prerequisites

The following settings influence the DkHome Item Update process. These can typically be configured in the App4Sales administration panel for the connector instance.

  • Warehouse: (Text field) Specifies a default warehouse code to filter stock data. If left empty, all stock values provided by the ERP are considered.

  • Use Relative Picture Url: (Boolean) If true, picture URLs are treated as relative paths for raw content download; otherwise, they are treated as full URLs.

  • Use Multiple Item Group Levels: (Boolean) If true, item groups are processed as a hierarchical structure (Lookbooks/Editions); otherwise, they are processed as a flat list.

  • Real-time info calls based on comma-separated: (Boolean) Influences the format of URL parameters for real-time information queries, including item stock.

  • Supports Stock Batch Call: (Boolean, defaults to true) Indicates if the connector supports batch calls for stock retrieval.

  • Disallow Duplicate Data: (Boolean) If true, the connector will throw an exception and stop synchronization if duplicate item codes are detected within a batch, indicating instability in the REST API implementation.

  • Disable Batch Update: (Boolean) If true, the item update process will stop after the first batch, typically used for connectors with specific limitations.

  • Use Warehouse From User: (Boolean) If true, the warehouse for stock searches will be determined from the logged-in user's warehouse setting, overriding the connector's default Warehouse setting.

  • Use Stock For Items Batch: (Boolean) If true, the connector attempts to retrieve stock for multiple items in a single batch call.

  • Use Item Prices Batch: (Boolean) If true, the connector attempts to retrieve item prices for multiple items in a single batch call (via the /ItemPrices endpoint).

  • Use Url Parameters For Item Stock Search: (Boolean) If true, item stock search uses URL parameters (e.g., ?ItemCode=X&Warehouse=Y). If false, it uses OData filtering.

  • Use OData Filter For Stock: (Boolean) If true, OData filter syntax is used for item stock queries (e.g., $filter=ItemCode eq 'X').

Known Limitations

  • The connector hardcodes VatIncluded to 'E'. If DkHome uses a different logic for VAT inclusion, this might lead to discrepancies.

  • Image resizing or compression is not explicitly handled by the connector; images are downloaded and stored as-is.

  • The system explicitly checks for and throws an exception on duplicate item codes if DisallowDuplicateData is enabled, suggesting potential issues with the source API's data consistency for certain ERPs.

  • If the ERP provides a PriceList with Code 1, prices without an explicit price list are skipped to prevent overwriting ERP data, which means if the default PriceList in DkHome is not consistently linked to all prices, some prices might not be synchronized.

Did this answer your question?