@contentful/experience-design-system-cli 2.37.1-dev-build-845e7310.0 → 2.37.1-dev-build-923f560a.0

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.
Files changed (27) hide show
  1. package/dist/app.js +2937 -2374
  2. package/dist/index.js +3226 -2591
  3. package/dist/package.json +1 -1
  4. package/dist/src/tui/import/shared/index.d.ts +0 -1
  5. package/dist/src/tui/import/steps/01-welcome/controls.d.ts +1 -1
  6. package/dist/src/tui/import/steps/02-token-input/screen.d.ts +1 -4
  7. package/dist/src/tui/import/steps/03-path-validation/logic.d.ts +1 -7
  8. package/dist/src/tui/import/steps/03-path-validation/screen.d.ts +1 -3
  9. package/dist/src/tui/import/steps/04-credentials/logic.d.ts +0 -5
  10. package/dist/src/tui/import/steps/04-credentials/screen.d.ts +1 -3
  11. package/dist/src/tui/import/steps/05-token-reuse/logic.d.ts +22 -0
  12. package/dist/src/tui/import/steps/05-token-reuse/screen.d.ts +10 -0
  13. package/dist/src/tui/import/steps/06-extraction/logic.d.ts +3 -1
  14. package/dist/src/tui/import/steps/06-extraction/types.d.ts +5 -2
  15. package/dist/src/tui/import/steps/10-flow/flow/build-flow-start.d.ts +0 -1
  16. package/dist/src/tui/import/steps/10-flow/flow/controller.d.ts +0 -7
  17. package/dist/src/tui/import/steps/10-flow/screens/DoneStep.d.ts +1 -6
  18. package/dist/src/tui/import/steps/10-flow/screens/PushingStep.d.ts +1 -3
  19. package/dist/src/tui/import/steps/index.d.ts +1 -1
  20. package/package.json +3 -3
  21. package/dist/src/tui/import/shared/overview-box/overview-box.d.ts +0 -10
  22. package/dist/src/tui/import/steps/00-preflight/controls.d.ts +0 -17
  23. package/dist/src/tui/import/steps/00-preflight/logic.d.ts +0 -46
  24. package/dist/src/tui/import/steps/00-preflight/screen.d.ts +0 -8
  25. package/dist/src/tui/import/steps/06-extraction/run-tokens-only.d.ts +0 -31
  26. package/dist/src/tui/import/steps/06-extraction/use-tokens-only.d.ts +0 -12
  27. package/dist/src/tui/import/steps/10-flow/support/produced.d.ts +0 -15
package/dist/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@contentful/experience-design-system-cli",
3
- "version": "2.37.1-dev-build-845e7310.0",
3
+ "version": "2.37.1-dev-build-923f560a.0",
4
4
  "description": "Contentful Experiences design system import CLI",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -1,4 +1,3 @@
1
1
  export { ErrorStep } from './error-step/error-step.js';
2
2
  export { GateStep } from './gate-step/gate-step.js';
3
- export { OverviewBox, type OverviewStep } from './overview-box/overview-box.js';
4
3
  export { RunningStep } from './running-step/running-step.js';
@@ -6,6 +6,6 @@ export declare const WELCOME_CONTROLS: readonly [{
6
6
  readonly label: "Clear";
7
7
  }, {
8
8
  readonly keys: "Esc";
9
- readonly label: "Back";
9
+ readonly label: "Back to menu";
10
10
  }];
11
11
  export declare function useWelcomeControls(onQuit: () => void): void;
@@ -1,11 +1,8 @@
1
1
  import React from 'react';
2
- import { type OverviewStep } from '../../shared/index.js';
3
2
  interface TokenInputScreenProps {
4
3
  onConfirm: (tokensPath: string) => void;
5
4
  onBack: () => void;
6
5
  initialPath?: string;
7
- /** The steps of the import, shown above the prompt when this is the first screen the user sees (tokens only). */
8
- overview?: readonly OverviewStep[];
9
6
  }
10
- export declare function TokenInputScreen({ onConfirm, onBack, initialPath, overview, }: TokenInputScreenProps): React.ReactElement;
7
+ export declare function TokenInputScreen({ onConfirm, onBack, initialPath }: TokenInputScreenProps): React.ReactElement;
11
8
  export {};
@@ -33,13 +33,7 @@ interface Key {
33
33
  return: boolean;
34
34
  }
35
35
  export declare function describeFailure(failure: ScanFailureCode, path: string): FailureMessage;
36
- /**
37
- * The scan result as rows and a warning. When the import does not generate tokens (components only), `.json` files are
38
- * not design tokens here, so the row says they are ignored and the warnings do not mention tokens.
39
- */
40
- export declare function summarize(counts: FileCounts, { hasTokens }?: {
41
- hasTokens?: boolean;
42
- }): Summary;
36
+ export declare function summarize(counts: FileCounts): Summary;
43
37
  export declare function phaseOf(scan: ScanResult | undefined): PathPhase;
44
38
  export declare function keyAction(phase: PathPhase, input: string, key: Key): KeyAction | undefined;
45
39
  export {};
@@ -7,8 +7,6 @@ interface PathValidationScreenProps {
7
7
  }) => void;
8
8
  onChangePath: () => void;
9
9
  onBack: () => void;
10
- /** False when the import does not generate tokens, so `.json` files are not described as design tokens. */
11
- hasTokens?: boolean;
12
10
  }
13
- export declare function PathValidationScreen({ projectPath, onConfirm, onChangePath, onBack, hasTokens, }: PathValidationScreenProps): React.ReactElement;
11
+ export declare function PathValidationScreen({ projectPath, onConfirm, onChangePath, onBack, }: PathValidationScreenProps): React.ReactElement;
14
12
  export {};
@@ -1,11 +1,6 @@
1
1
  export declare const FIELDS: readonly ["spaceId", "environmentId", "cmaToken", "host"];
2
2
  export type CredentialField = (typeof FIELDS)[number];
3
3
  export type CredentialValues = Record<CredentialField, string>;
4
- /**
5
- * Why the space is asked for. Components are looked up in it before they are generated, so that is part of the reason
6
- * unless the import only generates tokens, which has nothing to look up.
7
- */
8
- export declare function credentialsPurpose(tokensOnly: boolean): string;
9
4
  interface Key {
10
5
  escape: boolean;
11
6
  tab: boolean;
@@ -12,8 +12,6 @@ interface CredentialsScreenProps {
12
12
  onBack: () => void;
13
13
  initial?: Partial<CredentialValues>;
14
14
  validate?: (values: CredentialValues) => Promise<ValidationResult>;
15
- /** The import only generates tokens, so there are no components to look up in the space. */
16
- tokensOnly?: boolean;
17
15
  }
18
- export declare function CredentialsScreen({ onDone, onBack, initial, validate, tokensOnly, }: CredentialsScreenProps): React.ReactElement;
16
+ export declare function CredentialsScreen({ onDone, onBack, initial, validate, }: CredentialsScreenProps): React.ReactElement;
19
17
  export {};
@@ -0,0 +1,22 @@
1
+ export type { TokenStrategy } from '../06-extraction/types.js';
2
+ export type TokensState = {
3
+ kind: 'none';
4
+ } | {
5
+ kind: 'cached';
6
+ tokensPath: string;
7
+ sourceChanged: boolean;
8
+ };
9
+ interface InspectInput {
10
+ rawTokensPath: string;
11
+ /** The `.contentful` folder: the sessions' `dsi-import` folders sit inside it, and an older `tokens.json` may sit in it. */
12
+ contentfulDir: string;
13
+ cache: boolean;
14
+ }
15
+ export declare function inspectTokens({ rawTokensPath, contentfulDir, cache }: InspectInput): Promise<TokensState>;
16
+ export declare function gateText({ tokensPath, sourceChanged }: {
17
+ tokensPath: string;
18
+ sourceChanged: boolean;
19
+ }): {
20
+ summary: string;
21
+ context?: string;
22
+ };
@@ -0,0 +1,10 @@
1
+ import React from 'react';
2
+ interface TokenReuseScreenProps {
3
+ tokensPath: string;
4
+ sourceChanged: boolean;
5
+ onReuse: () => void;
6
+ onRegenerate: () => void;
7
+ onQuit: () => void;
8
+ }
9
+ export declare function TokenReuseScreen({ tokensPath, sourceChanged, onReuse, onRegenerate, onQuit, }: TokenReuseScreenProps): React.ReactElement;
10
+ export {};
@@ -4,11 +4,13 @@ import type { ExtractionProgress } from './types.js';
4
4
  export type ProgressEvent = ExtractAndComposeProgress;
5
5
  /**
6
6
  * Every job the stage will run starts on the first frame, so no row appears later as a surprise. A job that does not
7
- * apply stays 'idle' and has no row: existing entities need credentials, and token definitions need a raw tokens file.
7
+ * apply stays 'idle' and has no row: existing entities need credentials, token definitions need a raw tokens file, and
8
+ * reused tokens are already complete.
8
9
  */
9
10
  export declare function initialProgress(input: {
10
11
  hasCredentials: boolean;
11
12
  hasRawTokens: boolean;
13
+ reuseTokens: boolean;
12
14
  }): ExtractionProgress;
13
15
  export declare function applyProgressEvent(progress: ExtractionProgress, event: ProgressEvent): ExtractionProgress;
14
16
  /** The rows the screen shows, in the order the wizard showed them. Rows that do not apply are left out. */
@@ -1,12 +1,15 @@
1
- import type { ExtractionHandoff } from '@contentful/experience-design-system-types/handoff';
1
+ import type { ExtractionHandoff, ImportHandoff } from '@contentful/experience-design-system-types/handoff';
2
+ export type TokenStrategy = ImportHandoff['tokens']['strategy'];
2
3
  export interface ExtractionInput {
3
4
  projectPath: string;
4
5
  /** Where the stage writes tokens.json and the other files. Defaults to `<projectPath>/.contentful`. */
5
6
  outDir?: string;
6
7
  /** Absolute source files from the path-validation step (collectFiles output). */
7
8
  filePaths: string[];
8
- /** Raw tokens file the user pointed at. Empty when the import does not generate tokens (components only). */
9
+ /** Raw tokens file the user pointed at (always set: v2 asks for one). */
9
10
  rawTokensPath: string;
11
+ /** From the token reuse step. 'reuse' skips token generation entirely. */
12
+ tokenStrategy: TokenStrategy;
10
13
  /** Null when the user skipped credentials: no existing-entities fetch happens. */
11
14
  credentials: {
12
15
  spaceId: string;
@@ -17,6 +17,5 @@ export declare function buildFlowStart(input: {
17
17
  handoff: ImportHandoff;
18
18
  saved?: SavedCredentials;
19
19
  generatePromptPath?: string;
20
- tokensOnly?: FlowStart['tokensOnly'];
21
20
  }): FlowStart;
22
21
  export {};
@@ -17,13 +17,6 @@ export interface FlowStart {
17
17
  cmaToken: string;
18
18
  host: string;
19
19
  };
20
- /** Set when the import only generates tokens: there is no extraction or generation, so the flow starts at saving. */
21
- tokensOnly?: {
22
- tokensPath: string;
23
- tokenSessionId: string | null;
24
- tokenCount: number;
25
- outDir: string;
26
- };
27
20
  /** A custom prompt for `generate components`, shown as a warning above every step. */
28
21
  generatePromptPath?: string;
29
22
  }
@@ -1,5 +1,4 @@
1
1
  import React from 'react';
2
- import type { Produced } from '../support/produced.js';
3
2
  type EntityResult = {
4
3
  created: number;
5
4
  updated: number;
@@ -17,10 +16,6 @@ type DoneStepProps = {
17
16
  spaceId: string;
18
17
  environmentId: string;
19
18
  host?: string;
20
- /** What the import produced, so only the links to those things are offered. */
21
- produced: Produced;
22
- /** The user skipped the credentials, so nothing could be pushed: the files were only saved. */
23
- credentialsSkipped?: boolean;
24
19
  runTeaser?: string;
25
20
  failures?: Array<{
26
21
  entityType: string;
@@ -29,5 +24,5 @@ type DoneStepProps = {
29
24
  }>;
30
25
  onExit: () => void;
31
26
  };
32
- export declare function DoneStep({ componentTypes, designTokens, summary, spaceId, environmentId, host, produced, credentialsSkipped, failures, onExit, }: DoneStepProps): React.ReactElement;
27
+ export declare function DoneStep({ componentTypes, designTokens, summary, spaceId, environmentId, host, failures, onExit, }: DoneStepProps): React.ReactElement;
33
28
  export {};
@@ -1,11 +1,9 @@
1
1
  import React from 'react';
2
2
  import type { PushProgress } from '../support/push-progress.js';
3
- import { type Produced } from '../support/produced.js';
4
3
  type PushingStepProps = {
5
4
  stepNumber: number;
6
5
  totalSteps: number;
7
6
  progress: PushProgress;
8
- produced: Produced;
9
7
  };
10
- export declare function PushingStep({ stepNumber, totalSteps, progress, produced }: PushingStepProps): React.ReactElement;
8
+ export declare function PushingStep({ stepNumber, totalSteps, progress }: PushingStepProps): React.ReactElement;
11
9
  export {};
@@ -1,6 +1,6 @@
1
- export { PreflightScreen } from './00-preflight/screen.js';
2
1
  export { WelcomeScreen } from './01-welcome/screen.js';
3
2
  export { TokenInputScreen } from './02-token-input/screen.js';
4
3
  export { PathValidationScreen } from './03-path-validation/screen.js';
5
4
  export { CredentialsScreen } from './04-credentials/screen.js';
5
+ export { TokenReuseScreen } from './05-token-reuse/screen.js';
6
6
  export { ExtractionScreen } from './06-extraction/screen.js';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@contentful/experience-design-system-cli",
3
- "version": "2.37.1-dev-build-845e7310.0",
3
+ "version": "2.37.1-dev-build-923f560a.0",
4
4
  "description": "Contentful Experiences design system import CLI",
5
5
  "license": "MIT",
6
6
  "type": "module",
@@ -45,8 +45,8 @@
45
45
  "ts-morph": "^27.0.2",
46
46
  "typescript": "^5.9.3",
47
47
  "zod": "^4.6.5",
48
- "@contentful/experience-design-system-backend-pipeline": "2.37.1-dev-build-845e7310.0",
49
- "@contentful/experience-design-system-types": "2.37.1-dev-build-845e7310.0"
48
+ "@contentful/experience-design-system-backend-pipeline": "2.37.1-dev-build-923f560a.0",
49
+ "@contentful/experience-design-system-types": "2.37.1-dev-build-923f560a.0"
50
50
  },
51
51
  "devDependencies": {
52
52
  "@tsconfig/node24": "^24.0.4",
@@ -1,10 +0,0 @@
1
- import React from 'react';
2
- export interface OverviewStep {
3
- description: string;
4
- /** Whether the step uses the user's local AI agent. */
5
- ai: boolean;
6
- }
7
- /** The framed list of the steps an import goes through, with the AI disclosure under it. Shown by the intro screens. */
8
- export declare function OverviewBox({ steps }: {
9
- steps: readonly OverviewStep[];
10
- }): React.ReactElement;
@@ -1,17 +0,0 @@
1
- import { type ImportTarget } from './logic.js';
2
- export declare const PREFLIGHT_CONTROLS: readonly [{
3
- readonly keys: "↑/↓";
4
- readonly label: "Choose";
5
- }, {
6
- readonly keys: "Enter";
7
- readonly label: "Continue";
8
- }, {
9
- readonly keys: "Esc";
10
- readonly label: "Back to menu";
11
- }];
12
- export declare function usePreflightControls(handlers: {
13
- focus: number;
14
- onFocus: (focus: number) => void;
15
- onChoose: (target: ImportTarget) => void;
16
- onQuit: () => void;
17
- }): void;
@@ -1,46 +0,0 @@
1
- import type { OverviewStep } from '../../shared/index.js';
2
- export type ImportTarget = 'both' | 'tokens' | 'components';
3
- export declare const IMPORT_TARGET_OPTIONS: ReadonlyArray<{
4
- target: ImportTarget;
5
- label: string;
6
- }>;
7
- export declare const TOKENS_ONLY_OVERVIEW: readonly OverviewStep[];
8
- export declare const TOKENS_ONLY_STEP_COUNT: number;
9
- export type ImportStepId = 'project' | 'token-file' | 'path-validation' | 'credentials' | 'component-extraction' | 'token-generation' | 'scope-gate' | 'generation' | 'review' | 'save-push';
10
- export declare function stepsFor(target: ImportTarget): readonly ImportStepId[];
11
- export interface InputAnswers {
12
- projectPath?: string;
13
- tokensPath?: string;
14
- scannedFiles?: string[];
15
- }
16
- /**
17
- * The input screen to show: the first step of this mode whose answer is still missing, or 'credentials' once every
18
- * earlier one is answered. A mode never shows a screen it does not list, so skipping one needs no special case.
19
- */
20
- export declare function currentInputStep(target: ImportTarget, answers: InputAnswers): Extract<ImportStepId, 'project' | 'token-file' | 'path-validation' | 'credentials'>;
21
- /**
22
- * What Back from `current` does: leave for the preflight when it is the first screen of the mode, otherwise clear the
23
- * previous step's answer so that screen shows again.
24
- */
25
- export declare function goBack(target: ImportTarget, current: ImportStepId, answers: InputAnswers): {
26
- to: 'preflight';
27
- } | {
28
- to: 'step';
29
- answers: InputAnswers;
30
- };
31
- /**
32
- * Where a run writes its files when it has no project to put them in: the Root Project Directory setting if there is
33
- * one, otherwise the folder the token file is in. Components runs always have a project and use it.
34
- */
35
- export declare function runBaseDir(input: {
36
- projectPath?: string;
37
- tokensPath?: string;
38
- configuredBaseDir?: string;
39
- }): string;
40
- interface FocusKey {
41
- upArrow: boolean;
42
- downArrow: boolean;
43
- }
44
- /** The option focused after a key: arrows move through the list and wrap around. */
45
- export declare function moveFocus(focus: number, key: FocusKey, count: number): number;
46
- export {};
@@ -1,8 +0,0 @@
1
- import React from 'react';
2
- import { type ImportTarget } from './logic.js';
3
- interface PreflightScreenProps {
4
- onChoose: (target: ImportTarget) => void;
5
- onQuit: () => void;
6
- }
7
- export declare function PreflightScreen({ onChoose, onQuit }: PreflightScreenProps): React.ReactElement;
8
- export {};
@@ -1,31 +0,0 @@
1
- import { checkAgentAuth, runGenerateTokensSession } from '@contentful/experience-design-system-backend-pipeline';
2
- export interface TokensOnlyInput {
3
- rawTokensPath: string;
4
- /** Where tokens.json is written: this import run's folder. */
5
- outDir: string;
6
- agent: string;
7
- agentModel?: string;
8
- promptOverrides: string[];
9
- noCache: boolean;
10
- }
11
- export type TokensOnlyResult = {
12
- ok: true;
13
- tokensPath: string;
14
- tokenSessionId: string | null;
15
- tokenCount: number;
16
- } | {
17
- ok: false;
18
- step: 'generate tokens' | `${string} auth check`;
19
- message: string;
20
- };
21
- /** The outside world the stage talks to, so it can be tested without an agent. */
22
- export interface TokensOnlyDeps {
23
- checkAgentAuth: typeof checkAgentAuth;
24
- runGenerateTokensSession: typeof runGenerateTokensSession;
25
- }
26
- /**
27
- * The extraction stage for an import that only generates tokens: the same auth check and token generation the full stage
28
- * runs, without scanning components, composing them or selecting. The full stage fails when it finds no components, so it
29
- * cannot be used for this.
30
- */
31
- export declare function runTokensOnly(input: TokensOnlyInput, deps?: TokensOnlyDeps): Promise<TokensOnlyResult>;
@@ -1,12 +0,0 @@
1
- import { type TokensOnlyInput, type TokensOnlyResult } from './run-tokens-only.js';
2
- export type TokensOnlyState = {
3
- status: 'running';
4
- } | {
5
- status: 'done';
6
- result: TokensOnlyResult;
7
- };
8
- /**
9
- * Runs the tokens-only stage once for the given input. Passing nothing leaves it idle. A run that finishes after the
10
- * input changed or the screen went away is ignored.
11
- */
12
- export declare function useTokensOnly(input: TokensOnlyInput | undefined): TokensOnlyState | undefined;
@@ -1,15 +0,0 @@
1
- import type { FlowState } from '../flow/types.js';
2
- /** What an import produced, so the screens after the work can describe what happened and not a fixed pair. */
3
- export interface Produced {
4
- components: boolean;
5
- tokens: boolean;
6
- }
7
- /** Components exist when extraction ran; tokens exist when the token stage left a catalog or a session behind. */
8
- export declare function producedOf(state: Pick<FlowState, 'extractSessionId' | 'tokensPath' | 'tokenSessionId'>): Produced;
9
- /**
10
- * How the saved file is described: the file is always named `components.json`, but when only tokens were generated it
11
- * holds just the tokens, and calling it a components file would mislead.
12
- */
13
- export declare function fileSummaryLabel({ components }: Produced): string;
14
- /** "component types and design tokens", "design tokens", or "component types": the things this run writes. */
15
- export declare function writtenThings({ components, tokens }: Produced): string;