Uniqueness¶
VibeIQ allows users to configure custom uniqueness requirements at the type property level. These constraints ensure that certain property values remain unique according to user-defined settings.
Uniqueness constraints are commonly used for properties like SKU numbers, product codes, style numbers, or other identifiers where duplicate values would cause conflicts or data integrity issues.
Types of Uniqueness¶
Globally Unique Properties¶
When a property is marked as globally unique, VibeIQ ensures that the value for this property is never duplicated across any existing records in that type hierarchy.
Scope¶
- The uniqueness constraint applies across the entire type hierarchy
- For example, if
sku
is globally unique foritem
, the value must be unique acrossitem
,item:footwear
,item:apparel
, and all other item types - A given value can only be used once across all entities of that type
- You can turn off uniqueness for a subtype
Enforcement¶
When you create or update an entity with a globally unique property:
- The system checks if the property value already exists for any other entity in the type hierarchy
- If it exists, the create/update operation is blocked
- If it doesn't exist, the operation proceeds
Supported Entity Types¶
Currently, uniqueness constraints can be applied to:
- Items
- Project Items
Family-Level Uniqueness¶
When a property is marked as unique within a family, VibeIQ enforces uniqueness only within that specific family.
Scope¶
- The value can be reused across different families
- Duplicate values within the same family are not allowed
- This applies to Items and Project Items that support family-level organization
Example¶
If colorCode
is marked as family-unique:
- Family A can have an option with
colorCode: "RED-01"
- Family B can also have an option with
colorCode: "RED-01"
- Within Family A, no two options can share the same
colorCode
value
How to Configure Uniqueness¶
Uniqueness is configured at the type property level through the Admin Console:
- Navigate to Type Configuration in the Admin Console
- Select the type you want to configure (e.g.,
item:footwear
) - Open the property you want to make unique
- In the Uniqueness section, choose one of the following:
- Globally unique - The property value is unique across all items
- Unique in family - The property value is unique for an item family
Configuration UI¶
When editing a type property, you'll see the Uniqueness section with two toggle options:
- ☑️ Globally unique? The property value is unique across all items.
- ☐ Unique in family? The property value is unique for an item family.
These options are mutually exclusive - you can enable one or neither, but not both.
Important Limits¶
- Only 10 properties per entity can be marked as globally unique
- This limit helps maintain performance and data integrity
Once configured, the system will automatically enforce uniqueness constraints on all create and update operations going forward.
Backfilling Uniqueness Constraints¶
When you mark a property as unique, you need to ensure that all existing entity data complies with the uniqueness constraint. The backfill endpoint validates existing data and registers unique values.
When to Backfill¶
Use the backfill endpoint when:
- A property is newly marked as globally unique and you need to validate existing data
- You need to ensure all existing entities comply with uniqueness constraints
- You want to identify duplicate values that must be resolved before enforcing uniqueness
Backfill Endpoint¶
POST /identities/backfill
Request Body¶
{
"typePath": "item:product",
"propertySlug": "sku"
}
Parameters¶
Parameter | Type | Required | Description |
---|---|---|---|
typePath |
string |
Yes | The type path for the entities. Single type: "item:product" - backfills only that specific typeType hierarchy: "item" - backfills all types in the hierarchy |
propertySlug |
string |
Yes | The slug of the property marked as globally unique. The property must have isUniqueProperty: true in the type definition. |
How Backfill Works¶
Single Type Backfill¶
When typePath
specifies a complete type path (e.g., "item:product"
):
- Validates that the property is marked as globally unique for that type
- Fetches all entities of that specific type
- Filters entities that have values for the specified property
- Checks for duplicate values within the existing entity data
- Checks for duplicate values against property values already registered in the system
- Registers globally unique property values only for entities with non-duplicate values
- Reports any duplicate values found so they can be resolved
Multiple Type Backfill¶
When typePath
specifies only a root type (e.g., "item"
):
- Retrieves the entire type hierarchy for that root
- Iterates through each type in the hierarchy
- Performs single type backfill for each type that has the property marked as globally unique
- Continues processing even if some types fail, returning all errors at the end
Property Level Handling¶
For multi-level entity types (item
and project-item
), the backfill respects property levels:
- Family-level properties: Only processes entities with the
family
role - Option-level properties: Only processes entities with the
option
role - Overridable properties: Treated as family-level
Response¶
Success (200)¶
Returns when all property values have been successfully validated and registered for global uniqueness enforcement.
{}
Error (400)¶
Returns detailed error information if duplicate values are found or validation fails.
{
"incomingDuplicates": {
"message": "Duplicate property values found in incoming entities",
"details": {
"SKU-123": ["item-id-1", "item-id-2"],
"SKU-456": ["item-id-3", "item-id-4"]
}
},
"incomingAndExistingDuplicates": {
"message": "Duplicate property values found in incoming + existing entities",
"details": {
"SKU-789": ["item-id-5", "item-id-6"]
}
},
"creation": {
"message": "Error registering globally unique values",
"details": "..."
}
}
Backfill Examples¶
Example 1: Backfill a Specific Type¶
Validate and register all SKU values for a single type:
curl -X POST https://api.vibeiq.com/identities/backfill \
-H "Content-Type: application/json" \
-H "Authorization: Bearer YOUR_TOKEN" \
-d '{
"typePath": "item:shoe",
"propertySlug": "sku"
}'
This processes all entities of type item:shoe
and ensures SKU values are globally unique. If duplicate SKUs are found, they will be reported in the error response.
Example 2: Backfill an Entire Type Hierarchy¶
Validate and register product codes across all types in a hierarchy:
curl -X POST https://api.vibeiq.com/identities/backfill \
-H "Content-Type: application/json" \
-H "Authorization: Bearer YOUR_TOKEN" \
-d '{
"typePath": "item",
"propertySlug": "productCode"
}'
This processes all types in the item
hierarchy (e.g., item
, item:shoe
, item:apparel
) where productCode
is marked as globally unique.
Error Scenarios¶
The backfill endpoint handles several validation scenarios:
Property Not Marked as Globally Unique¶
The property must have isUniqueProperty: true
in the type definition. If not, a BadRequestException
is thrown.
Type Not Found¶
If the specified typePath
doesn't exist, a BadRequestException
is thrown.
Duplicate Values in Entity Data¶
When entities share the same property value, those duplicates are reported in the error response. These duplicates must be resolved before global uniqueness can be enforced.
Duplicate Values Already Registered¶
Property values that have already been registered for global uniqueness enforcement are automatically skipped.
Registration Errors¶
Any errors that occur during the registration process are reported in the error response.
Important Considerations¶
Processing Behavior¶
- Only entities with non-null, non-undefined, and non-empty values are processed
- Entities whose property values are already registered are automatically skipped
- For multi-type backfills, processing continues even if individual types fail
Authentication¶
The backfill endpoint follows the standard Contrail authentication patterns. Ensure your request includes proper credentials and organization ID.