UNPKG

@stackbit/annotations

Version:
93 lines (84 loc) 3.07 kB
export const StackbitObjectIdAttrName = 'data-sb-object-id'; export const StackbitFieldPathAttrName = 'data-sb-field-path'; export type StackbitObjectId = { [StackbitObjectIdAttrName]?: string }; export type StackbitFieldPath = { [StackbitFieldPathAttrName]?: string }; export type StackbitAnnotations = StackbitObjectId & StackbitFieldPath; export function getObjectId(props?: StackbitObjectId): string | undefined { return props?.[StackbitObjectIdAttrName]; } export function getFieldPath(props?: StackbitFieldPath): string | undefined { return props?.[StackbitFieldPathAttrName]; } /** * Takes a string and returns an object with that string wrapped into the * `data-sb-object-id` attribute. * * @example * toObjectId('xyz') * => { 'data-sb-object-id': 'xyz' } * * @param objectId */ export function toObjectId(objectId?: string): StackbitObjectId { if (process.env.NODE_ENV === 'production') { return {}; } if (!objectId) { return {}; } return { [StackbitObjectIdAttrName]: objectId }; } export type FieldPathDescriptor = ({ fieldPath: string } | { fp: string }) & ({ objectId?: string } | { oid?: string }) & { xpath?: string }; /** * Takes field-path and returns an object with all field-paths concatenated into * the `data-sb-field-path` attribute. Each field-path can be a string or a * FieldPathDescriptor. * * @example * toFieldPath('.button', { objectId: 'xyz', fieldPath: 'link', xpath: '@href' }) * => { 'data-sb-field-path': '.button xyz:link#@href' } * * toFieldPath({ oid: 'abc', fp: 'image', xpath: 'img[1]/@src' }) * => { 'data-sb-field-path': 'abc:image#img[1]/@src' } * * @param fieldPaths */ export function toFieldPath(...fieldPaths: (undefined | null | string | FieldPathDescriptor)[]): StackbitFieldPath { if (process.env.NODE_ENV === 'production') { return {}; } const fieldPath = fieldPaths .map((fieldPath) => { if (!fieldPath) { return null; } if (typeof fieldPath === 'string') { return fieldPath; } const fp = 'fieldPath' in fieldPath ? fieldPath.fieldPath : fieldPath.fp; const oid = 'objectId' in fieldPath ? fieldPath.objectId : 'oid' in fieldPath ? fieldPath.oid : ''; const xpath = 'xpath' in fieldPath ? fieldPath.xpath : ''; return (oid ? `${oid}:` : '') + fp + (xpath ? `#${xpath}` : ''); }) .filter(Boolean) .join(' ') .trim(); return fieldPath ? { [StackbitFieldPathAttrName]: fieldPath } : {}; } /** * Takes an object and returns a new object with only the properties that start * with `data-` * * @param props */ export function pickDataAttrs(props?: Record<string, any>): Record<string, any> { if (!props) { return {}; } return Object.entries(props).reduce((dataAttrs: Record<string, any>, [key, value]) => { if (key.startsWith('data-')) { dataAttrs[key] = value; } return dataAttrs; }, {}); }