@clivly/core 0.9.1 → 0.9.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -14,6 +14,9 @@ the view compiler that turns a mapping into SQL. Its only runtime dependency is
14
14
  > to import it from. Reach for `@clivly/core` when you are building an adapter
15
15
  > or working with the entity config outside an SDK instance.
16
16
 
17
+ Connection and presence transport live in `@clivly/sdk`, not this package.
18
+ That includes the opt-in WebSocket presence transport and its HTTP fallback.
19
+
17
20
  ## Prerequisites
18
21
 
19
22
  | Requirement | Version / note |
@@ -1,4 +1,4 @@
1
- import { f as DiscoveredColumnMeta, p as DiscoveredSchemaTable } from "./entity-config-CLxI8dVb.cjs";
1
+ import { m as DiscoveredSchemaTable, p as DiscoveredColumnMeta } from "./entity-config-buOIVtMM.cjs";
2
2
  import { Table } from "drizzle-orm";
3
3
  //#region src/drizzle.d.ts
4
4
  /**
@@ -1,4 +1,4 @@
1
- import { f as DiscoveredColumnMeta, p as DiscoveredSchemaTable } from "./entity-config-CLxI8dVb.mjs";
1
+ import { m as DiscoveredSchemaTable, p as DiscoveredColumnMeta } from "./entity-config-buOIVtMM.mjs";
2
2
  import { Table } from "drizzle-orm";
3
3
  //#region src/drizzle.d.ts
4
4
  /**
@@ -438,10 +438,23 @@ const entitySchema = zod.z.strictObject({
438
438
  relationships: zod.z.record(zod.z.string(), relationshipSchema).optional(),
439
439
  /**
440
440
  * For a "custom" entity, the crm_object_types row this materializes into.
441
- * Required for custom (enforced at the API layer), unused for standard concepts.
441
+ * Server-generated, so pasting one into config couples the file to a
442
+ * specific workspace. Prefer declaring `objectType` and letting
443
+ * `clivly push-schema` resolve the id by slug.
442
444
  */
443
445
  targetObjectTypeId: zod.z.string().min(1).optional(),
444
446
  /**
447
+ * Declares the custom object this entity materializes into, so config is
448
+ * self-contained: the entity key is the slug (unique per org and immutable),
449
+ * and `clivly push-schema` creates the object type if the workspace does not
450
+ * have it yet. An alternative to pasting a `targetObjectTypeId`.
451
+ */
452
+ objectType: zod.z.strictObject({
453
+ name: zod.z.string().min(1),
454
+ pluralName: zod.z.string().min(1).optional(),
455
+ iconKey: zod.z.string().min(1).optional()
456
+ }).optional(),
457
+ /**
445
458
  * Advanced mapping: derive this entity from a base table plus explicit joins
446
459
  * instead of a single source table. Valid only for `concept: "custom"`.
447
460
  *
@@ -483,17 +496,22 @@ function defaultWarn(message) {
483
496
  console.warn(message);
484
497
  }
485
498
  /**
486
- * Structural helper for `clivly.config.ts`. Gives full type inference on the
487
- * literal you pass and eagerly parses it, so shape errors surface at config
488
- * load rather than at sync time.
489
- *
490
- * It also catches the silent-data-loss footgun: a non-canonical field key for a
491
- * materialised concept (e.g. `fullName` instead of `name` on a `contact`) has no
492
- * destination column, so the store would write an empty value. By default these
493
- * are reported via `onWarn` (a `console.warn`); pass `{ strict: true }` to throw
494
- * a `ClivlyConfigError` instead. Does NOT validate against the host schema — that
495
- * needs the discovered schema; see `validateEntitiesConfig`.
499
+ * The custom objects a config declares, keyed by entity slug. Entities that
500
+ * already carry an explicit `targetObjectTypeId` are omitted: their object type
501
+ * exists server-side and re-declaring it would be a no-op at best.
496
502
  */
503
+ function customObjectDeclarations(config) {
504
+ const declarations = [];
505
+ for (const [slug, entity] of Object.entries(config.entities)) {
506
+ if (entity.concept !== "custom" || entity.targetObjectTypeId) continue;
507
+ if (!entity.objectType) continue;
508
+ declarations.push({
509
+ slug,
510
+ ...entity.objectType
511
+ });
512
+ }
513
+ return declarations;
514
+ }
497
515
  /**
498
516
  * The `fields` entry a projection binding implies, qualified as `ref.column`.
499
517
  * Qualified rather than bare: two bindings can pull the same column name from
@@ -633,7 +651,7 @@ function validateEntity(v, config, key, entity, schema) {
633
651
  }
634
652
  if (entity.projection) {
635
653
  if (entity.concept !== "custom") v.report(`${base}.projection`, `projection mappings are only supported for concept "${CUSTOM_CONCEPT}"`);
636
- if (!entity.targetObjectTypeId) v.report(`${base}.targetObjectTypeId`, "a projection mapping must target a custom object type");
654
+ if (!(entity.targetObjectTypeId || entity.objectType)) v.report(`${base}.targetObjectTypeId`, "a projection mapping must target a custom object type — declare `objectType: { name: \"…\" }` (recommended: the entity key becomes its slug) or set an explicit `targetObjectTypeId`");
637
655
  if (entity.source !== entity.projection.baseTable) v.report(`${base}.source`, `"source" ("${entity.source}") must match "projection.baseTable" ("${entity.projection.baseTable}") — the view compiler reads baseTable and the sync engine reads source, so a mismatch makes them disagree about which table this entity is`);
638
656
  for (const error of validateProjection(entity.projection, schema, base)) v.report(error.path, error.message);
639
657
  validateReadOnly(v, base, entity);
@@ -705,6 +723,12 @@ Object.defineProperty(exports, "coversUniqueKey", {
705
723
  return coversUniqueKey;
706
724
  }
707
725
  });
726
+ Object.defineProperty(exports, "customObjectDeclarations", {
727
+ enumerable: true,
728
+ get: function() {
729
+ return customObjectDeclarations;
730
+ }
731
+ });
708
732
  Object.defineProperty(exports, "defineClivlyConfig", {
709
733
  enumerable: true,
710
734
  get: function() {
@@ -438,10 +438,23 @@ const entitySchema = z.strictObject({
438
438
  relationships: z.record(z.string(), relationshipSchema).optional(),
439
439
  /**
440
440
  * For a "custom" entity, the crm_object_types row this materializes into.
441
- * Required for custom (enforced at the API layer), unused for standard concepts.
441
+ * Server-generated, so pasting one into config couples the file to a
442
+ * specific workspace. Prefer declaring `objectType` and letting
443
+ * `clivly push-schema` resolve the id by slug.
442
444
  */
443
445
  targetObjectTypeId: z.string().min(1).optional(),
444
446
  /**
447
+ * Declares the custom object this entity materializes into, so config is
448
+ * self-contained: the entity key is the slug (unique per org and immutable),
449
+ * and `clivly push-schema` creates the object type if the workspace does not
450
+ * have it yet. An alternative to pasting a `targetObjectTypeId`.
451
+ */
452
+ objectType: z.strictObject({
453
+ name: z.string().min(1),
454
+ pluralName: z.string().min(1).optional(),
455
+ iconKey: z.string().min(1).optional()
456
+ }).optional(),
457
+ /**
445
458
  * Advanced mapping: derive this entity from a base table plus explicit joins
446
459
  * instead of a single source table. Valid only for `concept: "custom"`.
447
460
  *
@@ -483,17 +496,22 @@ function defaultWarn(message) {
483
496
  console.warn(message);
484
497
  }
485
498
  /**
486
- * Structural helper for `clivly.config.ts`. Gives full type inference on the
487
- * literal you pass and eagerly parses it, so shape errors surface at config
488
- * load rather than at sync time.
489
- *
490
- * It also catches the silent-data-loss footgun: a non-canonical field key for a
491
- * materialised concept (e.g. `fullName` instead of `name` on a `contact`) has no
492
- * destination column, so the store would write an empty value. By default these
493
- * are reported via `onWarn` (a `console.warn`); pass `{ strict: true }` to throw
494
- * a `ClivlyConfigError` instead. Does NOT validate against the host schema — that
495
- * needs the discovered schema; see `validateEntitiesConfig`.
499
+ * The custom objects a config declares, keyed by entity slug. Entities that
500
+ * already carry an explicit `targetObjectTypeId` are omitted: their object type
501
+ * exists server-side and re-declaring it would be a no-op at best.
496
502
  */
503
+ function customObjectDeclarations(config) {
504
+ const declarations = [];
505
+ for (const [slug, entity] of Object.entries(config.entities)) {
506
+ if (entity.concept !== "custom" || entity.targetObjectTypeId) continue;
507
+ if (!entity.objectType) continue;
508
+ declarations.push({
509
+ slug,
510
+ ...entity.objectType
511
+ });
512
+ }
513
+ return declarations;
514
+ }
497
515
  /**
498
516
  * The `fields` entry a projection binding implies, qualified as `ref.column`.
499
517
  * Qualified rather than bare: two bindings can pull the same column name from
@@ -633,7 +651,7 @@ function validateEntity(v, config, key, entity, schema) {
633
651
  }
634
652
  if (entity.projection) {
635
653
  if (entity.concept !== "custom") v.report(`${base}.projection`, `projection mappings are only supported for concept "${CUSTOM_CONCEPT}"`);
636
- if (!entity.targetObjectTypeId) v.report(`${base}.targetObjectTypeId`, "a projection mapping must target a custom object type");
654
+ if (!(entity.targetObjectTypeId || entity.objectType)) v.report(`${base}.targetObjectTypeId`, "a projection mapping must target a custom object type — declare `objectType: { name: \"…\" }` (recommended: the entity key becomes its slug) or set an explicit `targetObjectTypeId`");
637
655
  if (entity.source !== entity.projection.baseTable) v.report(`${base}.source`, `"source" ("${entity.source}") must match "projection.baseTable" ("${entity.projection.baseTable}") — the view compiler reads baseTable and the sync engine reads source, so a mismatch makes them disagree about which table this entity is`);
638
656
  for (const error of validateProjection(entity.projection, schema, base)) v.report(error.path, error.message);
639
657
  validateReadOnly(v, base, entity);
@@ -663,4 +681,4 @@ function validateEntitiesConfig(config, schema) {
663
681
  };
664
682
  }
665
683
  //#endregion
666
- export { coversUniqueKey as _, MATERIALIZING_CONCEPTS as a, filterSchema as c, relationshipsSchema as d, validateEntitiesConfig as f, columnMetaFor as g, joinFansOut as h, ClivlyConfigError as i, projectionFields as l, fanOutJoins as m, CRM_CONCEPTS as n, defineClivlyConfig as o, validateProjection as p, CUSTOM_CONCEPT as r, entitiesConfigSchema as s, CANONICAL_FIELDS as t, relationshipSchema as u, hasRichMeta as v, primaryKeyColumns as y };
684
+ export { columnMetaFor as _, MATERIALIZING_CONCEPTS as a, primaryKeyColumns as b, entitiesConfigSchema as c, relationshipSchema as d, relationshipsSchema as f, joinFansOut as g, fanOutJoins as h, ClivlyConfigError as i, filterSchema as l, validateProjection as m, CRM_CONCEPTS as n, customObjectDeclarations as o, validateEntitiesConfig as p, CUSTOM_CONCEPT as r, defineClivlyConfig as s, CANONICAL_FIELDS as t, projectionFields as u, coversUniqueKey as v, hasRichMeta as y };
@@ -311,6 +311,11 @@ declare const entitySchema: z.ZodObject<{
311
311
  }, z.core.$strict>]>;
312
312
  }, z.core.$strict>>>;
313
313
  targetObjectTypeId: z.ZodOptional<z.ZodString>;
314
+ objectType: z.ZodOptional<z.ZodObject<{
315
+ name: z.ZodString;
316
+ pluralName: z.ZodOptional<z.ZodString>;
317
+ iconKey: z.ZodOptional<z.ZodString>;
318
+ }, z.core.$strict>>;
314
319
  projection: z.ZodOptional<z.ZodObject<{
315
320
  version: z.ZodLiteral<1>;
316
321
  kind: z.ZodLiteral<"projection">;
@@ -406,6 +411,11 @@ declare const entitiesConfigSchema: z.ZodObject<{
406
411
  }, z.core.$strict>]>;
407
412
  }, z.core.$strict>>>;
408
413
  targetObjectTypeId: z.ZodOptional<z.ZodString>;
414
+ objectType: z.ZodOptional<z.ZodObject<{
415
+ name: z.ZodString;
416
+ pluralName: z.ZodOptional<z.ZodString>;
417
+ iconKey: z.ZodOptional<z.ZodString>;
418
+ }, z.core.$strict>>;
409
419
  projection: z.ZodOptional<z.ZodObject<{
410
420
  version: z.ZodLiteral<1>;
411
421
  kind: z.ZodLiteral<"projection">;
@@ -488,6 +498,20 @@ declare class ClivlyConfigError extends Error {
488
498
  * a `ClivlyConfigError` instead. Does NOT validate against the host schema — that
489
499
  * needs the discovered schema; see `validateEntitiesConfig`.
490
500
  */
501
+ /** A custom object the host declares in config, for `push-schema` to ensure. */
502
+ interface CustomObjectDeclaration {
503
+ iconKey?: string;
504
+ name: string;
505
+ pluralName?: string;
506
+ /** Unique per org and immutable — the entity key. */
507
+ slug: string;
508
+ }
509
+ /**
510
+ * The custom objects a config declares, keyed by entity slug. Entities that
511
+ * already carry an explicit `targetObjectTypeId` are omitted: their object type
512
+ * exists server-side and re-declaring it would be a no-op at best.
513
+ */
514
+ declare function customObjectDeclarations(config: ClivlyEntitiesConfig): CustomObjectDeclaration[];
491
515
  /**
492
516
  * The `fields` entry a projection binding implies, qualified as `ref.column`.
493
517
  * Qualified rather than bare: two bindings can pull the same column name from
@@ -553,4 +577,4 @@ interface ConfigValidationResult {
553
577
  */
554
578
  declare function validateEntitiesConfig(config: ClivlyEntitiesConfig, schema: DiscoveredSchemaTable[]): ConfigValidationResult;
555
579
  //#endregion
556
- export { ProjectionIdentity as A, filterSchema as C, validateEntitiesConfig as D, relationshipsSchema as E, projectionSchema as F, ProjectionMapping as M, ProjectionRef as N, BASE_REF as O, identityRefs as P, entitiesConfigSchema as S, relationshipSchema as T, MaterializingConcept as _, ClivlyEntitiesConfig as a, RelationshipsMap as b, ClivlyEntityConfigInput as c, CrmConcept as d, DiscoveredColumnMeta as f, MATERIALIZING_CONCEPTS as g, FilterValue as h, ClivlyConfigError as i, ProjectionJoin as j, ProjectionFieldBinding as k, ConfigValidationError as l, FilterExpr as m, CRM_CONCEPTS as n, ClivlyEntitiesConfigInput as o, DiscoveredSchemaTable as p, CUSTOM_CONCEPT as r, ClivlyEntityConfig as s, CANONICAL_FIELDS as t, ConfigValidationResult as u, RelationshipSpec as v, projectionFields as w, defineClivlyConfig as x, RelationshipVia as y };
580
+ export { BASE_REF as A, defineClivlyConfig as C, relationshipSchema as D, projectionFields as E, ProjectionRef as F, identityRefs as I, projectionSchema as L, ProjectionIdentity as M, ProjectionJoin as N, relationshipsSchema as O, ProjectionMapping as P, customObjectDeclarations as S, filterSchema as T, MATERIALIZING_CONCEPTS as _, ClivlyEntitiesConfig as a, RelationshipVia as b, ClivlyEntityConfigInput as c, CrmConcept as d, CustomObjectDeclaration as f, FilterValue as g, FilterExpr as h, ClivlyConfigError as i, ProjectionFieldBinding as j, validateEntitiesConfig as k, ConfigValidationError as l, DiscoveredSchemaTable as m, CRM_CONCEPTS as n, ClivlyEntitiesConfigInput as o, DiscoveredColumnMeta as p, CUSTOM_CONCEPT as r, ClivlyEntityConfig as s, CANONICAL_FIELDS as t, ConfigValidationResult as u, MaterializingConcept as v, entitiesConfigSchema as w, RelationshipsMap as x, RelationshipSpec as y };
@@ -311,6 +311,11 @@ declare const entitySchema: z.ZodObject<{
311
311
  }, z.core.$strict>]>;
312
312
  }, z.core.$strict>>>;
313
313
  targetObjectTypeId: z.ZodOptional<z.ZodString>;
314
+ objectType: z.ZodOptional<z.ZodObject<{
315
+ name: z.ZodString;
316
+ pluralName: z.ZodOptional<z.ZodString>;
317
+ iconKey: z.ZodOptional<z.ZodString>;
318
+ }, z.core.$strict>>;
314
319
  projection: z.ZodOptional<z.ZodObject<{
315
320
  version: z.ZodLiteral<1>;
316
321
  kind: z.ZodLiteral<"projection">;
@@ -406,6 +411,11 @@ declare const entitiesConfigSchema: z.ZodObject<{
406
411
  }, z.core.$strict>]>;
407
412
  }, z.core.$strict>>>;
408
413
  targetObjectTypeId: z.ZodOptional<z.ZodString>;
414
+ objectType: z.ZodOptional<z.ZodObject<{
415
+ name: z.ZodString;
416
+ pluralName: z.ZodOptional<z.ZodString>;
417
+ iconKey: z.ZodOptional<z.ZodString>;
418
+ }, z.core.$strict>>;
409
419
  projection: z.ZodOptional<z.ZodObject<{
410
420
  version: z.ZodLiteral<1>;
411
421
  kind: z.ZodLiteral<"projection">;
@@ -488,6 +498,20 @@ declare class ClivlyConfigError extends Error {
488
498
  * a `ClivlyConfigError` instead. Does NOT validate against the host schema — that
489
499
  * needs the discovered schema; see `validateEntitiesConfig`.
490
500
  */
501
+ /** A custom object the host declares in config, for `push-schema` to ensure. */
502
+ interface CustomObjectDeclaration {
503
+ iconKey?: string;
504
+ name: string;
505
+ pluralName?: string;
506
+ /** Unique per org and immutable — the entity key. */
507
+ slug: string;
508
+ }
509
+ /**
510
+ * The custom objects a config declares, keyed by entity slug. Entities that
511
+ * already carry an explicit `targetObjectTypeId` are omitted: their object type
512
+ * exists server-side and re-declaring it would be a no-op at best.
513
+ */
514
+ declare function customObjectDeclarations(config: ClivlyEntitiesConfig): CustomObjectDeclaration[];
491
515
  /**
492
516
  * The `fields` entry a projection binding implies, qualified as `ref.column`.
493
517
  * Qualified rather than bare: two bindings can pull the same column name from
@@ -553,4 +577,4 @@ interface ConfigValidationResult {
553
577
  */
554
578
  declare function validateEntitiesConfig(config: ClivlyEntitiesConfig, schema: DiscoveredSchemaTable[]): ConfigValidationResult;
555
579
  //#endregion
556
- export { ProjectionIdentity as A, filterSchema as C, validateEntitiesConfig as D, relationshipsSchema as E, projectionSchema as F, ProjectionMapping as M, ProjectionRef as N, BASE_REF as O, identityRefs as P, entitiesConfigSchema as S, relationshipSchema as T, MaterializingConcept as _, ClivlyEntitiesConfig as a, RelationshipsMap as b, ClivlyEntityConfigInput as c, CrmConcept as d, DiscoveredColumnMeta as f, MATERIALIZING_CONCEPTS as g, FilterValue as h, ClivlyConfigError as i, ProjectionJoin as j, ProjectionFieldBinding as k, ConfigValidationError as l, FilterExpr as m, CRM_CONCEPTS as n, ClivlyEntitiesConfigInput as o, DiscoveredSchemaTable as p, CUSTOM_CONCEPT as r, ClivlyEntityConfig as s, CANONICAL_FIELDS as t, ConfigValidationResult as u, RelationshipSpec as v, projectionFields as w, defineClivlyConfig as x, RelationshipVia as y };
580
+ export { BASE_REF as A, defineClivlyConfig as C, relationshipSchema as D, projectionFields as E, ProjectionRef as F, identityRefs as I, projectionSchema as L, ProjectionIdentity as M, ProjectionJoin as N, relationshipsSchema as O, ProjectionMapping as P, customObjectDeclarations as S, filterSchema as T, MATERIALIZING_CONCEPTS as _, ClivlyEntitiesConfig as a, RelationshipVia as b, ClivlyEntityConfigInput as c, CrmConcept as d, CustomObjectDeclaration as f, FilterValue as g, FilterExpr as h, ClivlyConfigError as i, ProjectionFieldBinding as j, validateEntitiesConfig as k, ConfigValidationError as l, DiscoveredSchemaTable as m, CRM_CONCEPTS as n, ClivlyEntitiesConfigInput as o, DiscoveredColumnMeta as p, CUSTOM_CONCEPT as r, ClivlyEntityConfig as s, CANONICAL_FIELDS as t, ConfigValidationResult as u, MaterializingConcept as v, entitiesConfigSchema as w, RelationshipsMap as x, RelationshipSpec as y };
@@ -1,10 +1,11 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- const require_entity_config = require("./entity-config-Dh8aEcgj.cjs");
2
+ const require_entity_config = require("./entity-config-Bfq3OkCU.cjs");
3
3
  exports.CANONICAL_FIELDS = require_entity_config.CANONICAL_FIELDS;
4
4
  exports.CRM_CONCEPTS = require_entity_config.CRM_CONCEPTS;
5
5
  exports.CUSTOM_CONCEPT = require_entity_config.CUSTOM_CONCEPT;
6
6
  exports.ClivlyConfigError = require_entity_config.ClivlyConfigError;
7
7
  exports.MATERIALIZING_CONCEPTS = require_entity_config.MATERIALIZING_CONCEPTS;
8
+ exports.customObjectDeclarations = require_entity_config.customObjectDeclarations;
8
9
  exports.defineClivlyConfig = require_entity_config.defineClivlyConfig;
9
10
  exports.entitiesConfigSchema = require_entity_config.entitiesConfigSchema;
10
11
  exports.filterSchema = require_entity_config.filterSchema;
@@ -1,2 +1,2 @@
1
- import { C as filterSchema, D as validateEntitiesConfig, E as relationshipsSchema, S as entitiesConfigSchema, T as relationshipSchema, _ as MaterializingConcept, a as ClivlyEntitiesConfig, b as RelationshipsMap, c as ClivlyEntityConfigInput, d as CrmConcept, f as DiscoveredColumnMeta, g as MATERIALIZING_CONCEPTS, h as FilterValue, i as ClivlyConfigError, l as ConfigValidationError, m as FilterExpr, n as CRM_CONCEPTS, o as ClivlyEntitiesConfigInput, p as DiscoveredSchemaTable, r as CUSTOM_CONCEPT, s as ClivlyEntityConfig, t as CANONICAL_FIELDS, u as ConfigValidationResult, v as RelationshipSpec, w as projectionFields, x as defineClivlyConfig, y as RelationshipVia } from "./entity-config-CLxI8dVb.cjs";
2
- export { CANONICAL_FIELDS, CRM_CONCEPTS, CUSTOM_CONCEPT, ClivlyConfigError, ClivlyEntitiesConfig, ClivlyEntitiesConfigInput, ClivlyEntityConfig, ClivlyEntityConfigInput, ConfigValidationError, ConfigValidationResult, CrmConcept, DiscoveredColumnMeta, DiscoveredSchemaTable, FilterExpr, FilterValue, MATERIALIZING_CONCEPTS, MaterializingConcept, RelationshipSpec, RelationshipVia, RelationshipsMap, defineClivlyConfig, entitiesConfigSchema, filterSchema, projectionFields, relationshipSchema, relationshipsSchema, validateEntitiesConfig };
1
+ import { C as defineClivlyConfig, D as relationshipSchema, E as projectionFields, O as relationshipsSchema, S as customObjectDeclarations, T as filterSchema, _ as MATERIALIZING_CONCEPTS, a as ClivlyEntitiesConfig, b as RelationshipVia, c as ClivlyEntityConfigInput, d as CrmConcept, f as CustomObjectDeclaration, g as FilterValue, h as FilterExpr, i as ClivlyConfigError, k as validateEntitiesConfig, l as ConfigValidationError, m as DiscoveredSchemaTable, n as CRM_CONCEPTS, o as ClivlyEntitiesConfigInput, p as DiscoveredColumnMeta, r as CUSTOM_CONCEPT, s as ClivlyEntityConfig, t as CANONICAL_FIELDS, u as ConfigValidationResult, v as MaterializingConcept, w as entitiesConfigSchema, x as RelationshipsMap, y as RelationshipSpec } from "./entity-config-buOIVtMM.cjs";
2
+ export { CANONICAL_FIELDS, CRM_CONCEPTS, CUSTOM_CONCEPT, ClivlyConfigError, ClivlyEntitiesConfig, ClivlyEntitiesConfigInput, ClivlyEntityConfig, ClivlyEntityConfigInput, ConfigValidationError, ConfigValidationResult, CrmConcept, CustomObjectDeclaration, DiscoveredColumnMeta, DiscoveredSchemaTable, FilterExpr, FilterValue, MATERIALIZING_CONCEPTS, MaterializingConcept, RelationshipSpec, RelationshipVia, RelationshipsMap, customObjectDeclarations, defineClivlyConfig, entitiesConfigSchema, filterSchema, projectionFields, relationshipSchema, relationshipsSchema, validateEntitiesConfig };
@@ -1,2 +1,2 @@
1
- import { C as filterSchema, D as validateEntitiesConfig, E as relationshipsSchema, S as entitiesConfigSchema, T as relationshipSchema, _ as MaterializingConcept, a as ClivlyEntitiesConfig, b as RelationshipsMap, c as ClivlyEntityConfigInput, d as CrmConcept, f as DiscoveredColumnMeta, g as MATERIALIZING_CONCEPTS, h as FilterValue, i as ClivlyConfigError, l as ConfigValidationError, m as FilterExpr, n as CRM_CONCEPTS, o as ClivlyEntitiesConfigInput, p as DiscoveredSchemaTable, r as CUSTOM_CONCEPT, s as ClivlyEntityConfig, t as CANONICAL_FIELDS, u as ConfigValidationResult, v as RelationshipSpec, w as projectionFields, x as defineClivlyConfig, y as RelationshipVia } from "./entity-config-CLxI8dVb.mjs";
2
- export { CANONICAL_FIELDS, CRM_CONCEPTS, CUSTOM_CONCEPT, ClivlyConfigError, ClivlyEntitiesConfig, ClivlyEntitiesConfigInput, ClivlyEntityConfig, ClivlyEntityConfigInput, ConfigValidationError, ConfigValidationResult, CrmConcept, DiscoveredColumnMeta, DiscoveredSchemaTable, FilterExpr, FilterValue, MATERIALIZING_CONCEPTS, MaterializingConcept, RelationshipSpec, RelationshipVia, RelationshipsMap, defineClivlyConfig, entitiesConfigSchema, filterSchema, projectionFields, relationshipSchema, relationshipsSchema, validateEntitiesConfig };
1
+ import { C as defineClivlyConfig, D as relationshipSchema, E as projectionFields, O as relationshipsSchema, S as customObjectDeclarations, T as filterSchema, _ as MATERIALIZING_CONCEPTS, a as ClivlyEntitiesConfig, b as RelationshipVia, c as ClivlyEntityConfigInput, d as CrmConcept, f as CustomObjectDeclaration, g as FilterValue, h as FilterExpr, i as ClivlyConfigError, k as validateEntitiesConfig, l as ConfigValidationError, m as DiscoveredSchemaTable, n as CRM_CONCEPTS, o as ClivlyEntitiesConfigInput, p as DiscoveredColumnMeta, r as CUSTOM_CONCEPT, s as ClivlyEntityConfig, t as CANONICAL_FIELDS, u as ConfigValidationResult, v as MaterializingConcept, w as entitiesConfigSchema, x as RelationshipsMap, y as RelationshipSpec } from "./entity-config-buOIVtMM.mjs";
2
+ export { CANONICAL_FIELDS, CRM_CONCEPTS, CUSTOM_CONCEPT, ClivlyConfigError, ClivlyEntitiesConfig, ClivlyEntitiesConfigInput, ClivlyEntityConfig, ClivlyEntityConfigInput, ConfigValidationError, ConfigValidationResult, CrmConcept, CustomObjectDeclaration, DiscoveredColumnMeta, DiscoveredSchemaTable, FilterExpr, FilterValue, MATERIALIZING_CONCEPTS, MaterializingConcept, RelationshipSpec, RelationshipVia, RelationshipsMap, customObjectDeclarations, defineClivlyConfig, entitiesConfigSchema, filterSchema, projectionFields, relationshipSchema, relationshipsSchema, validateEntitiesConfig };
@@ -1,2 +1,2 @@
1
- import { a as MATERIALIZING_CONCEPTS, c as filterSchema, d as relationshipsSchema, f as validateEntitiesConfig, i as ClivlyConfigError, l as projectionFields, n as CRM_CONCEPTS, o as defineClivlyConfig, r as CUSTOM_CONCEPT, s as entitiesConfigSchema, t as CANONICAL_FIELDS, u as relationshipSchema } from "./entity-config-8Fgr6IOH.mjs";
2
- export { CANONICAL_FIELDS, CRM_CONCEPTS, CUSTOM_CONCEPT, ClivlyConfigError, MATERIALIZING_CONCEPTS, defineClivlyConfig, entitiesConfigSchema, filterSchema, projectionFields, relationshipSchema, relationshipsSchema, validateEntitiesConfig };
1
+ import { a as MATERIALIZING_CONCEPTS, c as entitiesConfigSchema, d as relationshipSchema, f as relationshipsSchema, i as ClivlyConfigError, l as filterSchema, n as CRM_CONCEPTS, o as customObjectDeclarations, p as validateEntitiesConfig, r as CUSTOM_CONCEPT, s as defineClivlyConfig, t as CANONICAL_FIELDS, u as projectionFields } from "./entity-config-DFJ8L9jm.mjs";
2
+ export { CANONICAL_FIELDS, CRM_CONCEPTS, CUSTOM_CONCEPT, ClivlyConfigError, MATERIALIZING_CONCEPTS, customObjectDeclarations, defineClivlyConfig, entitiesConfigSchema, filterSchema, projectionFields, relationshipSchema, relationshipsSchema, validateEntitiesConfig };
@@ -1,5 +1,5 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- const require_entity_config = require("./entity-config-Dh8aEcgj.cjs");
2
+ const require_entity_config = require("./entity-config-Bfq3OkCU.cjs");
3
3
  const require_mapping_score = require("./mapping-score.cjs");
4
4
  //#region src/entity-heuristics.ts
5
5
  const TARGET_CONCEPTS = [
@@ -1,4 +1,4 @@
1
- import { f as DiscoveredColumnMeta } from "./entity-config-CLxI8dVb.cjs";
1
+ import { p as DiscoveredColumnMeta } from "./entity-config-buOIVtMM.cjs";
2
2
  import { Scored } from "./mapping-score.cjs";
3
3
  //#region src/entity-heuristics.d.ts
4
4
  declare const TARGET_CONCEPTS: readonly ["contact", "company", "deal", "activity", "conversation", "note"];
@@ -1,4 +1,4 @@
1
- import { f as DiscoveredColumnMeta } from "./entity-config-CLxI8dVb.mjs";
1
+ import { p as DiscoveredColumnMeta } from "./entity-config-buOIVtMM.mjs";
2
2
  import { Scored } from "./mapping-score.mjs";
3
3
  //#region src/entity-heuristics.d.ts
4
4
  declare const TARGET_CONCEPTS: readonly ["contact", "company", "deal", "activity", "conversation", "note"];
@@ -1,4 +1,4 @@
1
- import { a as MATERIALIZING_CONCEPTS } from "./entity-config-8Fgr6IOH.mjs";
1
+ import { a as MATERIALIZING_CONCEPTS } from "./entity-config-DFJ8L9jm.mjs";
2
2
  import { CONCEPT_TIERS, FIELD_TIERS, RELATIONSHIP_TIERS, W, isAmbiguous, isNumericLike, isTextLike, isTimestampLike, tierFor } from "./mapping-score.mjs";
3
3
  //#region src/entity-heuristics.ts
4
4
  const TARGET_CONCEPTS = [
package/dist/index.cjs CHANGED
@@ -1,7 +1,7 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
2
  const require_auth_adapter = require("./auth-adapter.cjs");
3
3
  const require_projection = require("./projection-BXBkh7qp.cjs");
4
- const require_entity_config = require("./entity-config-Dh8aEcgj.cjs");
4
+ const require_entity_config = require("./entity-config-Bfq3OkCU.cjs");
5
5
  const require_mapping_form = require("./mapping-form.cjs");
6
6
  const require_mappings_config = require("./mappings-config.cjs");
7
7
  const require_view_compiler = require("./view-compiler-BpNI8Ttw.cjs");
package/dist/index.d.cts CHANGED
@@ -1,7 +1,7 @@
1
1
  import { Activity, ActivityType, Company, Contact, ContactFilters, ContactStatus, CreateActivityInput, CreateCompanyInput, CreateContactInput, CreateDealInput, CreateTaskInput, CrmRole, Deal, DealStage, Note, RecordSource, Task, TaskEntityType, TaskFilters, TaskPriority, TaskStatus, UpdateContactInput, UpdateDealInput, UpdateTaskInput } from "./types.cjs";
2
2
  import { CRMAdapter } from "./adapter.cjs";
3
3
  import { ClivlyAuthAdapter, ClivlyUser, CrmMembership, MembershipResolver, authCustom } from "./auth-adapter.cjs";
4
- import { A as ProjectionIdentity, C as filterSchema, D as validateEntitiesConfig, E as relationshipsSchema, F as projectionSchema, M as ProjectionMapping, N as ProjectionRef, O as BASE_REF, P as identityRefs, S as entitiesConfigSchema, T as relationshipSchema, _ as MaterializingConcept, a as ClivlyEntitiesConfig, b as RelationshipsMap, d as CrmConcept, f as DiscoveredColumnMeta, g as MATERIALIZING_CONCEPTS, h as FilterValue, i as ClivlyConfigError, j as ProjectionJoin, k as ProjectionFieldBinding, l as ConfigValidationError, m as FilterExpr, n as CRM_CONCEPTS, p as DiscoveredSchemaTable, s as ClivlyEntityConfig, t as CANONICAL_FIELDS, u as ConfigValidationResult, v as RelationshipSpec, x as defineClivlyConfig, y as RelationshipVia } from "./entity-config-CLxI8dVb.cjs";
4
+ import { A as BASE_REF, C as defineClivlyConfig, D as relationshipSchema, F as ProjectionRef, I as identityRefs, L as projectionSchema, M as ProjectionIdentity, N as ProjectionJoin, O as relationshipsSchema, P as ProjectionMapping, T as filterSchema, _ as MATERIALIZING_CONCEPTS, a as ClivlyEntitiesConfig, b as RelationshipVia, d as CrmConcept, g as FilterValue, h as FilterExpr, i as ClivlyConfigError, j as ProjectionFieldBinding, k as validateEntitiesConfig, l as ConfigValidationError, m as DiscoveredSchemaTable, n as CRM_CONCEPTS, p as DiscoveredColumnMeta, s as ClivlyEntityConfig, t as CANONICAL_FIELDS, u as ConfigValidationResult, v as MaterializingConcept, w as entitiesConfigSchema, x as RelationshipsMap, y as RelationshipSpec } from "./entity-config-buOIVtMM.cjs";
5
5
  import { RelationshipCandidate, buildFilterFromDiscriminator, buildRelationships, relationshipViaSignature } from "./mapping-form.cjs";
6
6
  import { EntityMappingRow, mappingsToEntitiesConfig } from "./mappings-config.cjs";
7
7
  import { CompileOptions, CompiledView, DEFAULT_VIEW_PREFIX, ExplainResult, compileEntityView, compileEntityViews, explainEntitiesConfig } from "./view-compiler.cjs";
package/dist/index.d.mts CHANGED
@@ -1,7 +1,7 @@
1
1
  import { Activity, ActivityType, Company, Contact, ContactFilters, ContactStatus, CreateActivityInput, CreateCompanyInput, CreateContactInput, CreateDealInput, CreateTaskInput, CrmRole, Deal, DealStage, Note, RecordSource, Task, TaskEntityType, TaskFilters, TaskPriority, TaskStatus, UpdateContactInput, UpdateDealInput, UpdateTaskInput } from "./types.mjs";
2
2
  import { CRMAdapter } from "./adapter.mjs";
3
3
  import { ClivlyAuthAdapter, ClivlyUser, CrmMembership, MembershipResolver, authCustom } from "./auth-adapter.mjs";
4
- import { A as ProjectionIdentity, C as filterSchema, D as validateEntitiesConfig, E as relationshipsSchema, F as projectionSchema, M as ProjectionMapping, N as ProjectionRef, O as BASE_REF, P as identityRefs, S as entitiesConfigSchema, T as relationshipSchema, _ as MaterializingConcept, a as ClivlyEntitiesConfig, b as RelationshipsMap, d as CrmConcept, f as DiscoveredColumnMeta, g as MATERIALIZING_CONCEPTS, h as FilterValue, i as ClivlyConfigError, j as ProjectionJoin, k as ProjectionFieldBinding, l as ConfigValidationError, m as FilterExpr, n as CRM_CONCEPTS, p as DiscoveredSchemaTable, s as ClivlyEntityConfig, t as CANONICAL_FIELDS, u as ConfigValidationResult, v as RelationshipSpec, x as defineClivlyConfig, y as RelationshipVia } from "./entity-config-CLxI8dVb.mjs";
4
+ import { A as BASE_REF, C as defineClivlyConfig, D as relationshipSchema, F as ProjectionRef, I as identityRefs, L as projectionSchema, M as ProjectionIdentity, N as ProjectionJoin, O as relationshipsSchema, P as ProjectionMapping, T as filterSchema, _ as MATERIALIZING_CONCEPTS, a as ClivlyEntitiesConfig, b as RelationshipVia, d as CrmConcept, g as FilterValue, h as FilterExpr, i as ClivlyConfigError, j as ProjectionFieldBinding, k as validateEntitiesConfig, l as ConfigValidationError, m as DiscoveredSchemaTable, n as CRM_CONCEPTS, p as DiscoveredColumnMeta, s as ClivlyEntityConfig, t as CANONICAL_FIELDS, u as ConfigValidationResult, v as MaterializingConcept, w as entitiesConfigSchema, x as RelationshipsMap, y as RelationshipSpec } from "./entity-config-buOIVtMM.mjs";
5
5
  import { RelationshipCandidate, buildFilterFromDiscriminator, buildRelationships, relationshipViaSignature } from "./mapping-form.mjs";
6
6
  import { EntityMappingRow, mappingsToEntitiesConfig } from "./mappings-config.mjs";
7
7
  import { CompileOptions, CompiledView, DEFAULT_VIEW_PREFIX, ExplainResult, compileEntityView, compileEntityViews, explainEntitiesConfig } from "./view-compiler.mjs";
package/dist/index.mjs CHANGED
@@ -1,6 +1,6 @@
1
1
  import { authCustom } from "./auth-adapter.mjs";
2
2
  import { i as projectionSchema, n as PROJECTION_KEY_PATTERN, r as identityRefs, t as BASE_REF } from "./projection-C_EMRmZ8.mjs";
3
- import { _ as coversUniqueKey, a as MATERIALIZING_CONCEPTS, c as filterSchema, d as relationshipsSchema, f as validateEntitiesConfig, g as columnMetaFor, h as joinFansOut, i as ClivlyConfigError, m as fanOutJoins, n as CRM_CONCEPTS, o as defineClivlyConfig, p as validateProjection, s as entitiesConfigSchema, t as CANONICAL_FIELDS, u as relationshipSchema, v as hasRichMeta, y as primaryKeyColumns } from "./entity-config-8Fgr6IOH.mjs";
3
+ import { _ as columnMetaFor, a as MATERIALIZING_CONCEPTS, b as primaryKeyColumns, c as entitiesConfigSchema, d as relationshipSchema, f as relationshipsSchema, g as joinFansOut, h as fanOutJoins, i as ClivlyConfigError, l as filterSchema, m as validateProjection, n as CRM_CONCEPTS, p as validateEntitiesConfig, s as defineClivlyConfig, t as CANONICAL_FIELDS, v as coversUniqueKey, y as hasRichMeta } from "./entity-config-DFJ8L9jm.mjs";
4
4
  import { buildFilterFromDiscriminator, buildRelationships, relationshipViaSignature } from "./mapping-form.mjs";
5
5
  import { mappingsToEntitiesConfig } from "./mappings-config.mjs";
6
6
  import { i as explainEntitiesConfig, n as compileEntityView, r as compileEntityViews, t as DEFAULT_VIEW_PREFIX } from "./view-compiler-CcqsGxv4.mjs";
@@ -31,8 +31,6 @@ const STEP_PREREQUISITES = {
31
31
  function stepIndex(id) {
32
32
  return INTEGRATION_STEPS.indexOf(id);
33
33
  }
34
- /** A heartbeat older than this means the app stopped checking in. */
35
- const HEARTBEAT_STALE_MS = 600 * 1e3;
36
34
  function formatAge(ms) {
37
35
  if (ms < 6e4) return `${Math.max(1, Math.round(ms / 1e3))}s ago`;
38
36
  if (ms < 36e5) return `${Math.round(ms / 6e4)}m ago`;
@@ -41,12 +39,96 @@ function formatAge(ms) {
41
39
  function heartbeatAge(facts) {
42
40
  return facts.lastHeartbeatAt === null ? null : facts.now - facts.lastHeartbeatAt;
43
41
  }
42
+ /** The cadence `createClivlySDK` uses when the host app configures none. */
43
+ const DEFAULT_HEARTBEAT_INTERVAL_MS = 6e4;
44
+ const LIVE_INTERVALS = 2.5;
45
+ const STALE_INTERVALS = 10;
46
+ /**
47
+ * The two boundaries that separate live from stale from offline, in terms of
48
+ * the app's own reported cadence. A cadence we cannot believe — absent, zero,
49
+ * negative — falls back to the SDK default rather than producing a window of
50
+ * zero that would call every app offline.
51
+ */
52
+ function livenessWindows(intervalMs) {
53
+ const interval = typeof intervalMs === "number" && intervalMs > 0 ? intervalMs : DEFAULT_HEARTBEAT_INTERVAL_MS;
54
+ return {
55
+ liveMs: interval * LIVE_INTERVALS,
56
+ staleMs: interval * STALE_INTERVALS
57
+ };
58
+ }
59
+ /**
60
+ * Faults worth showing on an app that is up. Deliberately excludes anything the
61
+ * developer simply has not done yet — no schema, no mapping, no trigger are all
62
+ * setup stages, and painting a fresh install amber would make the signal
63
+ * meaningless.
64
+ */
65
+ function livenessIssues(facts) {
66
+ const issues = [...facts.reportedIssues ?? []];
67
+ if (facts.lastRun && !facts.lastRun.ok) issues.push({
68
+ code: "sync_failed",
69
+ message: facts.lastRun.message ?? "The last sync run failed.",
70
+ fix: "Open the run log to see how your app responded."
71
+ });
72
+ return issues;
73
+ }
74
+ function websocketLiveness(facts, presence, base) {
75
+ if (!(presence.connectionState === "connected" && presence.activeInstanceCount > 0)) {
76
+ const health = presence.connectionState === "reconnecting" ? "stale" : "offline";
77
+ return {
78
+ ...base,
79
+ health,
80
+ issues: [],
81
+ reachable: false
82
+ };
83
+ }
84
+ const issues = livenessIssues(facts);
85
+ return {
86
+ ...base,
87
+ health: issues.length > 0 ? "live_with_issues" : "live",
88
+ issues,
89
+ reachable: true
90
+ };
91
+ }
92
+ function deriveLiveness(facts) {
93
+ const ageMs = heartbeatAge(facts);
94
+ const environment = facts.environment ?? null;
95
+ const { liveMs, staleMs } = livenessWindows(facts.heartbeatIntervalMs);
96
+ const base = {
97
+ ageMs,
98
+ ageLabel: ageMs === null ? "No heartbeat yet" : formatAge(ageMs),
99
+ environment,
100
+ ...facts.presence ? { presence: {
101
+ connectionState: facts.presence.connectionState,
102
+ transport: facts.presence.transport
103
+ } } : {}
104
+ };
105
+ if (facts.presence && facts.presence.transport === "websocket") return websocketLiveness(facts, facts.presence, base);
106
+ if (ageMs === null || ageMs >= staleMs) return {
107
+ ...base,
108
+ health: "offline",
109
+ issues: [],
110
+ reachable: false
111
+ };
112
+ if (ageMs >= liveMs) return {
113
+ ...base,
114
+ health: "stale",
115
+ issues: [],
116
+ reachable: false
117
+ };
118
+ const issues = livenessIssues(facts);
119
+ return {
120
+ ...base,
121
+ health: issues.length > 0 ? "live_with_issues" : "live",
122
+ issues,
123
+ reachable: true
124
+ };
125
+ }
44
126
  /** Is the raw condition behind each step met, ignoring prerequisites? */
45
127
  function isSatisfied(id, facts) {
46
128
  const age = heartbeatAge(facts);
47
129
  switch (id) {
48
130
  case "credential": return facts.hasCredential;
49
- case "application": return age !== null && age < HEARTBEAT_STALE_MS;
131
+ case "application": return facts.everConnected || age !== null;
50
132
  case "schema": return facts.discoveredTableCount > 0;
51
133
  case "mapping": return facts.mappedEntityCount > 0;
52
134
  case "trigger": return facts.triggerConfigured;
@@ -69,19 +151,6 @@ function problemFor(id, facts) {
69
151
  message: facts.lastRun.message ?? "The last sync run failed.",
70
152
  fix: "Open the run log to see the host response."
71
153
  };
72
- if (id === "application") {
73
- const age = heartbeatAge(facts);
74
- if (age !== null && age >= HEARTBEAT_STALE_MS) return {
75
- code: "heartbeat_stale",
76
- message: `Your app stopped checking in ${formatAge(age)}.`,
77
- fix: "Start your app, then run `npx clivly status`."
78
- };
79
- if (age === null && facts.everConnected) return {
80
- code: "heartbeat_stale",
81
- message: "Your application stopped checking in.",
82
- fix: "Start your app, then run `npx clivly status`."
83
- };
84
- }
85
154
  return null;
86
155
  }
87
156
  /**
@@ -147,14 +216,12 @@ const STEP_STATUS_WHEN_ACTIVE = {
147
216
  widget: "healthy"
148
217
  };
149
218
  /**
150
- * Collapse the ladder to the single status the surfaces switch on. Live
151
- * conditions — a run in flight, a failure, a heartbeat gone quiet — win over
152
- * ladder position, because they describe the integration as it is now rather
153
- * than how far setup once got.
219
+ * Collapse the ladder to the single status the surfaces switch on. This is the
220
+ * setup dimension only: it answers how far configuration got, never whether the
221
+ * app is up. Pair it with `deriveLiveness` for the second half of the picture.
154
222
  */
155
223
  function deriveStatus(steps, facts) {
156
224
  if (facts.syncInFlight) return "syncing";
157
- if (steps.find((step) => step.id === "application")?.problem?.code === "heartbeat_stale") return "disconnected";
158
225
  if (steps.some((step) => step.state === "failed")) return "error";
159
226
  const blocking = steps.find((step) => step.state === "active" || step.state === "blocked");
160
227
  if (blocking) return STEP_STATUS_WHEN_ACTIVE[blocking.id];
@@ -209,13 +276,13 @@ const NEXT_BY_STEP = {
209
276
  * as the fix for a write problem (C-05). If you need a command for the
210
277
  * next-action slot, call this — do not write another one.
211
278
  */
212
- function nextAction(steps, status) {
279
+ function nextAction(steps, status, liveness) {
213
280
  if (status === "healthy" || status === "syncing") return null;
214
281
  const blocking = steps.find((step) => step.state === "failed") ?? steps.find((step) => step.state === "active");
215
282
  if (!blocking) return null;
216
- if (blocking.problem?.code === "heartbeat_stale") return {
217
- label: "Reconnect your app",
218
- command: "npx clivly status",
283
+ if (steps.find((step) => step.id === "application")?.state === "done" && !liveness.reachable) return {
284
+ label: "Start your app",
285
+ command: null,
219
286
  envFile: null
220
287
  };
221
288
  return NEXT_BY_STEP[blocking.id];
@@ -223,20 +290,25 @@ function nextAction(steps, status) {
223
290
  function computeIntegrationState(facts) {
224
291
  const steps = resolveSteps(facts);
225
292
  const status = deriveStatus(steps, facts);
293
+ const liveness = deriveLiveness(facts);
226
294
  return {
227
295
  status,
228
296
  steps,
229
- next: nextAction(steps, status)
297
+ liveness,
298
+ next: nextAction(steps, status, liveness)
230
299
  };
231
300
  }
232
301
  //#endregion
302
+ exports.DEFAULT_HEARTBEAT_INTERVAL_MS = DEFAULT_HEARTBEAT_INTERVAL_MS;
233
303
  exports.INSTALL_COMMAND = INSTALL_COMMAND;
234
304
  exports.INTEGRATION_STEPS = INTEGRATION_STEPS;
235
305
  exports.INTEGRATION_STEP_LABELS = INTEGRATION_STEP_LABELS;
236
306
  exports.STEP_PREREQUISITES = STEP_PREREQUISITES;
237
307
  exports.computeIntegrationState = computeIntegrationState;
308
+ exports.deriveLiveness = deriveLiveness;
238
309
  exports.deriveStatus = deriveStatus;
239
310
  exports.formatAge = formatAge;
311
+ exports.livenessWindows = livenessWindows;
240
312
  exports.nextAction = nextAction;
241
313
  exports.resolveSteps = resolveSteps;
242
314
  exports.stepIndex = stepIndex;