Member Junction
    Preparing search index...

    Core engine for synchronizing MemberJunction metadata between database and files

    SyncEngine

    const syncEngine = new SyncEngine(systemUser);

    // Process a field value with special references
    const value = await syncEngine.processFieldValue('@lookup:Users.Email=admin@example.com', '/path/to/base');
    Index

    Constructors

    Methods

    • Build cascading defaults for a file path and process field values

      Walks up the directory tree from the file location, collecting defaults from entity config and folder configs, with deeper folders overriding parent values. All default values are processed for special references.

      Parameters

      • filePath: string

        Path to the file being processed

      • entityConfig: EntityConfig

        Entity configuration containing base defaults

      Returns Promise<Record<string, any>>

      Processed defaults with all references resolved

      Error if any default value processing fails

    • Calculate SHA256 checksum for data

      Generates a deterministic hash of the provided data by converting it to formatted JSON and calculating a SHA256 digest. Used for change detection in sync operations.

      Parameters

      • data: any

        Any data structure to calculate checksum for

      Returns string

      Hexadecimal string representation of the SHA256 hash

      const checksum = syncEngine.calculateChecksum({
      name: 'Test Record',
      value: 42,
      tags: ['a', 'b']
      });
      // Returns consistent hash for same data structure
    • Calculate checksum including resolved file content

      Enhanced checksum calculation that resolves

      Parameters

      • data: any

        Fields object that may contain

      • entityDir: string

        Directory for resolving relative file paths

      Returns Promise<string>

      Promise resolving to checksum string

      references and includes the actual file content (with

      directives processed) in the checksum. This ensures that changes to referenced files are detected.

      references

    • Create a new entity object instance

      Uses the MemberJunction metadata system to properly instantiate an entity object. This ensures correct class registration and respects any custom entity subclasses.

      Parameters

      • entityName: string

        Name of the entity to create

      Returns Promise<BaseEntity<unknown>>

      Promise resolving to the new BaseEntity instance

      Error if entity creation fails

      const entity = await syncEngine.createEntityObject('MJ: AI Prompts');
      entity.NewRecord();
      entity.Set('Name', 'My Prompt');
      await entity.Save();
    • Get entity metadata information by name

      Retrieves the EntityInfo object containing schema metadata for the specified entity. Returns null if the entity is not found in the metadata cache.

      Parameters

      • entityName: string

        Name of the entity to look up

      Returns EntityInfo

      EntityInfo object with schema details or null if not found

      const entityInfo = syncEngine.getEntityInfo('MJ: AI Prompts');
      if (entityInfo) {
      console.log(`Primary keys: ${entityInfo.PrimaryKeys.map(pk => pk.Name).join(', ')}`);
      }
    • Returns the metadata provider this engine is using.

      mj sync runs as a single-purpose CLI process with one configured provider per run, so this proxies to the global default (the only provider the process will ever see). Surfacing it through SyncEngine keeps callers from reaching for Metadata.Provider directly and makes it obvious which provider the sync is bound to.

      Returns IMetadataProvider

    • Load an entity record by primary key

      Retrieves an existing entity record from the database using its primary key values. Supports both single and composite primary keys. Returns null if the record is not found.

      Parameters

      • entityName: string

        Name of the entity to load

      • primaryKey: Record<string, any>

        Object containing primary key field names and values

      Returns Promise<BaseEntity<unknown>>

      Promise resolving to the loaded entity or null if not found

      Error if entity metadata is not found

      // Single primary key
      const entity = await syncEngine.loadEntity('Users', { ID: '123-456' });

      // Composite primary key
      const entity = await syncEngine.loadEntity('UserRoles', {
      UserID: '123-456',
      RoleID: '789-012'
      });
    • Process special references in field values and handle complex objects

      Automatically handles:

      • Arrays and objects are converted to JSON strings
      • Scalars (strings, numbers, booleans, null) pass through unchanged

      Handles the following reference types for string values:

      • @parent:fieldName - References a field from the parent record
      • @root:fieldName - References a field from the root record
      • @file:path - Reads content from an external file
      • @url:address - Fetches content from a URL
      • @lookup:Entity.Field=Value - Looks up an entity ID by field value
      • @env:VARIABLE - Reads an environment variable

      Parameters

      • value: any

        The field value to process

      • baseDir: string

        Base directory for resolving relative file paths

      • OptionalparentRecord: BatchContextStub | BaseEntity<unknown>

        Optional parent entity for

      • OptionalrootRecord: BatchContextStub | BaseEntity<unknown>

        Optional root entity for

      • depth: number = 0

        Current recursion depth (for preventing infinite loops)

      • OptionalbatchContext: BatchContext

        Optional batch context for in-memory entity resolution

      • OptionalresolutionCollector: SyncResolutionCollector

        Optional collector for tracking

      • OptionalfieldName: string

        Optional field name for tracking resolutions

      Returns Promise<any>

      The processed value with all references resolved

      references

      references

      and

      resolutions

      Error if a reference cannot be resolved

      // File reference
      const content = await processFieldValue('@file:template.md', '/path/to/dir');

      // Lookup with auto-create
      const userId = await processFieldValue('@lookup:Users.Email=john@example.com?create', '/path');

      // Complex object - automatically stringified
      const jsonStr = await processFieldValue({items: [{id: 1}, {id: 2}]}, '/path');
      // Returns: '{\n "items": [\n {\n "id": 1\n },\n {\n "id": 2\n }\n ]\n}'

      // With resolution collector for tracking
      const collector: SyncResolutionCollector = { notes: [], fieldPrefix: 'fields' };
      const result = await processFieldValue('@lookup:Users.Email=admin@example.com', '/path', null, null, 0, undefined, collector, 'UserID');
      // collector.notes will contain the resolution info
    • Parameters

      • entityName: string
      • lookupFields: { fieldName: string; fieldValue: string }[]
      • autoCreate: boolean = false
      • createFields: Record<string, any> = {}
      • OptionalbatchContext: BatchContext
      • allowDefer: boolean = false
      • OptionaloriginalValue: string

      Returns Promise<string>