@his-her/connect
v1.0.1
Published
Shared His & Her customer hub integration library
Readme
@his-her/connect
Shared His & Her customer hub integration library.
Features
- Platform-agnostic — configure any identity component for your platform
- Identity matching — cascading lookup: platform ID → email → phone
- Reward accounts — automatic creation when a ledger is configured
- Seller onboarding sync — create Strapi service accounts and loyalty providers from Mercur seller onboarding
- Simple API — one-call
syncCustomer()or lower-level methods
Installation
# From the consuming project (e.g. hisher-multistore/backend)
yarn add @his-her/connect@file:../../libs/hisher-connectCustomer sync quick start
import { createCustomerSyncClient } from '@his-her/connect'
const sync = createCustomerSyncClient({
cdpHost: process.env.CDP_HOST || 'http://localhost:1337',
cdpApiToken: process.env.CDP_API_TOKEN,
platformIdentity: {
component: 'identity.his-and-her-store',
externalIdField: 'medusaCustomerId',
},
rewardLedger: 'reward-points',
})
// One-call sync (find-or-create + reward account)
const result = await sync.syncCustomer({
externalId: 'cus_abc123',
email: '[email protected]',
phone: '+66812345678',
firstName: 'Jane',
lastName: 'Doe',
})
console.log(result.documentId) // Strapi contact documentId
console.log(result.created) // true if new contact
console.log(result.rewardAccountCreated) // true if reward account was createdMercur seller onboarding sync
import {
createHisHerConnectClient,
createHisHerCustomerConfigFromEnv,
} from '@his-her/connect'
const hisHer = createHisHerConnectClient(createHisHerCustomerConfigFromEnv())
const result = await hisHer.features.mercurSeller.syncOnboarding({
seller: {
id: 'sel_123',
handle: 'brand_handle',
name: 'Brand Name',
email: '[email protected]',
phone: '+66123456789',
description: 'Marketplace seller',
},
ownerMember: {
id: 'mem_123',
email: '[email protected]',
},
})
console.log(result.metadata) // safe to store in Mercur seller metadataSeller sync environment
HIS_HER_CUSTOMER_STRAPI_URL=http://localhost:1337
HIS_HER_CUSTOMER_STRAPI_API_TOKEN=your-strapi-token
HIS_HER_CUSTOMER_AUTH_MODE=service-jwt
HIS_HER_CUSTOMER_SERVICE_ACCOUNT_PASSWORD=service-user-password
HIS_HER_CUSTOMER_SERVICE_ACCOUNT_ROLE_ID=3
HIS_HER_CUSTOMER_SERVICE_ACCOUNT_EMAIL_DOMAIN=service.local
HIS_HER_CUSTOMER_SERVICE_ACCOUNT_ORGANIZATION_ID=12
HIS_HER_CUSTOMER_LOYALTY_PROVIDER_PARTNER_HANDLE=hisher
LOYALTY_CHANNEL_HANDLE=multistoreThe older CDP_HOST, CDP_API_TOKEN, CDP_SERVICE_ACCOUNT_ROLE_ID, CDP_SERVICE_ACCOUNT_EMAIL_DOMAIN, and CDP_MAIN_ORGANIZATION names are still supported as fallbacks.
Gift-card coupon sync
await hisHer.loyaltyCoupons.syncGiftCardCoupon({
code: giftCard.code,
channelHandle: process.env.LOYALTY_CHANNEL_HANDLE,
expiresAt: giftCard.expires_at ?? null,
})The Strapi sync endpoint stores the gift-card code in coupon externals[] and derives coupon ownership from the authenticated service user's sellerProvider.
Using from another platform
const sync = createCustomerSyncClient({
cdpHost: 'https://cdp.example.com',
cdpApiToken: 'token',
platformIdentity: {
component: 'identity.shopify-store',
externalIdField: 'shopifyCustomerId',
},
rewardLedger: 'reward-points',
})Lower-level API
// Find only
const found = await sync.findContact('cus_abc123', '[email protected]')
// Create
const { contact, documentId } = await sync.createContact({
firstName: 'Jane',
identities: sync.buildIdentities({ externalId: 'cus_abc123', email: '[email protected]' }),
})
// Update
await sync.updateContact(documentId, { lastName: 'Smith' })
// Reward account
await sync.ensureRewardAccount(documentId)
// Raw Strapi client
const strapi = sync.getStrapiClient()Custom logger
import { createCustomerSyncClient, type SyncLogger } from '@his-her/connect'
const logger: SyncLogger = {
info: (msg) => myLogger.info(msg),
warn: (msg) => myLogger.warn(msg),
error: (msg, err) => myLogger.error(msg, err),
}
const sync = createCustomerSyncClient(config, logger)