screenci 0.0.71 → 0.0.72

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 (95) hide show
  1. package/README.md +12 -12
  2. package/dist/cli.d.ts +8 -0
  3. package/dist/cli.d.ts.map +1 -1
  4. package/dist/cli.js +133 -10
  5. package/dist/cli.js.map +1 -1
  6. package/dist/docs/manifest.d.ts +3 -3
  7. package/dist/docs/manifest.js +1 -1
  8. package/dist/docs/manifest.js.map +1 -1
  9. package/dist/docs/video-sources/installation.screenci.js +13 -12
  10. package/dist/docs/video-sources/installation.screenci.js.map +1 -1
  11. package/dist/docs/video-sources/landing.screenci.js +16 -9
  12. package/dist/docs/video-sources/landing.screenci.js.map +1 -1
  13. package/dist/docs/video-sources/product-pitch.screenci.js +97 -32
  14. package/dist/docs/video-sources/product-pitch.screenci.js.map +1 -1
  15. package/dist/docs/video-sources/public-urls.screenci.js +16 -9
  16. package/dist/docs/video-sources/public-urls.screenci.js.map +1 -1
  17. package/dist/docs/video-sources/studio.screenci.js +42 -27
  18. package/dist/docs/video-sources/studio.screenci.js.map +1 -1
  19. package/dist/index.d.ts +7 -5
  20. package/dist/index.d.ts.map +1 -1
  21. package/dist/index.js +3 -4
  22. package/dist/index.js.map +1 -1
  23. package/dist/src/asset.d.ts +8 -23
  24. package/dist/src/asset.d.ts.map +1 -1
  25. package/dist/src/asset.js +10 -32
  26. package/dist/src/asset.js.map +1 -1
  27. package/dist/src/audio.d.ts +6 -24
  28. package/dist/src/audio.d.ts.map +1 -1
  29. package/dist/src/audio.js +10 -35
  30. package/dist/src/audio.js.map +1 -1
  31. package/dist/src/builder.d.ts +214 -0
  32. package/dist/src/builder.d.ts.map +1 -0
  33. package/dist/src/builder.js +212 -0
  34. package/dist/src/builder.js.map +1 -0
  35. package/dist/src/cue.d.ts +40 -123
  36. package/dist/src/cue.d.ts.map +1 -1
  37. package/dist/src/cue.js +190 -30
  38. package/dist/src/cue.js.map +1 -1
  39. package/dist/src/events.d.ts +80 -15
  40. package/dist/src/events.d.ts.map +1 -1
  41. package/dist/src/events.js +72 -6
  42. package/dist/src/events.js.map +1 -1
  43. package/dist/src/init.d.ts.map +1 -1
  44. package/dist/src/init.js +14 -13
  45. package/dist/src/init.js.map +1 -1
  46. package/dist/src/locales.d.ts +19 -0
  47. package/dist/src/locales.d.ts.map +1 -0
  48. package/dist/src/locales.js +60 -0
  49. package/dist/src/locales.js.map +1 -0
  50. package/dist/src/localize.d.ts +135 -0
  51. package/dist/src/localize.d.ts.map +1 -0
  52. package/dist/src/localize.js +195 -0
  53. package/dist/src/localize.js.map +1 -0
  54. package/dist/src/localizeRuntime.d.ts +53 -0
  55. package/dist/src/localizeRuntime.d.ts.map +1 -0
  56. package/dist/src/localizeRuntime.js +79 -0
  57. package/dist/src/localizeRuntime.js.map +1 -0
  58. package/dist/src/recordingData.d.ts +5 -4
  59. package/dist/src/recordingData.d.ts.map +1 -1
  60. package/dist/src/runtimeContext.d.ts +3 -4
  61. package/dist/src/runtimeContext.d.ts.map +1 -1
  62. package/dist/src/runtimeContext.js.map +1 -1
  63. package/dist/src/runtimeMode.d.ts +47 -0
  64. package/dist/src/runtimeMode.d.ts.map +1 -1
  65. package/dist/src/runtimeMode.js +124 -0
  66. package/dist/src/runtimeMode.js.map +1 -1
  67. package/dist/src/screenshot.d.ts +56 -2
  68. package/dist/src/screenshot.d.ts.map +1 -1
  69. package/dist/src/screenshot.js +47 -10
  70. package/dist/src/screenshot.js.map +1 -1
  71. package/dist/src/stillCapture.d.ts +2 -3
  72. package/dist/src/stillCapture.d.ts.map +1 -1
  73. package/dist/src/stillCapture.js.map +1 -1
  74. package/dist/src/studio.d.ts +55 -22
  75. package/dist/src/studio.d.ts.map +1 -1
  76. package/dist/src/studio.js +38 -12
  77. package/dist/src/studio.js.map +1 -1
  78. package/dist/src/types.d.ts +18 -5
  79. package/dist/src/types.d.ts.map +1 -1
  80. package/dist/src/types.js.map +1 -1
  81. package/dist/src/video.d.ts +149 -13
  82. package/dist/src/video.d.ts.map +1 -1
  83. package/dist/src/video.js +91 -24
  84. package/dist/src/video.js.map +1 -1
  85. package/dist/src/voiceConfig.d.ts +110 -0
  86. package/dist/src/voiceConfig.d.ts.map +1 -0
  87. package/dist/src/voiceConfig.js +2 -0
  88. package/dist/src/voiceConfig.js.map +1 -0
  89. package/dist/src/voices.d.ts +27 -23
  90. package/dist/src/voices.d.ts.map +1 -1
  91. package/dist/src/voices.js +7 -4
  92. package/dist/src/voices.js.map +1 -1
  93. package/dist/tsconfig.tsbuildinfo +1 -1
  94. package/package.json +1 -1
  95. package/skills/screenci/SKILL.md +39 -30
package/README.md CHANGED
@@ -71,18 +71,18 @@ but remap its rendered duration.
71
71
 
72
72
  ## Authoring helpers
73
73
 
74
- | Export | What it does |
75
- | ----------------- | -------------------------------------------------------- |
76
- | `defineConfig` | Wraps Playwright config with ScreenCI defaults |
77
- | `video` | Declares a video recording test |
78
- | `createNarration` | Creates typed narration controllers |
79
- | `hide` | Cuts setup or cleanup out of the visible recording |
80
- | `autoZoom` | Smooth camera follow for an interaction block |
81
- | `zoomTo` | Manual camera framing for a locator or point |
82
- | `resetZoom` | Returns from manual framing to the full viewport |
83
- | `createOverlays` | Inserts timed media overlays into the recording timeline |
84
- | `voices` | Available voice constants such as `voices.Ava` |
85
- | `modelTypes` | Narration model constants |
74
+ | Export | What it does |
75
+ | ---------------- | ------------------------------------------------------------ |
76
+ | `defineConfig` | Wraps Playwright config with ScreenCI defaults |
77
+ | `video` | Declares a video recording test |
78
+ | `video.localize` | Declares localized narration / text and records per language |
79
+ | `hide` | Cuts setup or cleanup out of the visible recording |
80
+ | `autoZoom` | Smooth camera follow for an interaction block |
81
+ | `zoomTo` | Manual camera framing for a locator or point |
82
+ | `resetZoom` | Returns from manual framing to the full viewport |
83
+ | `createOverlays` | Inserts timed media overlays into the recording timeline |
84
+ | `voices` | Available voice constants such as `voices.Ava` |
85
+ | `modelTypes` | Narration model constants |
86
86
 
87
87
  See the [docs](https://screenci.com/docs) for configuration, narration,
88
88
  camera, and CI setup.
package/dist/cli.d.ts CHANGED
@@ -75,5 +75,13 @@ export declare function ensureScreenciSecret(resolvedConfigPath?: string, opts?:
75
75
  pollAuth?: boolean;
76
76
  }): Promise<string | undefined>;
77
77
  export declare function main(): Promise<void>;
78
+ export declare function parseRecordCliArgs(args: string[]): {
79
+ configPath: string | undefined;
80
+ verbose: boolean;
81
+ pollAuth: boolean;
82
+ remote: boolean;
83
+ languages: string | undefined;
84
+ otherArgs: string[];
85
+ };
78
86
  export declare function logCliError(error: unknown): void;
79
87
  //# sourceMappingURL=cli.d.ts.map
package/dist/cli.d.ts.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../cli.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"cli.d.ts","sourceRoot":"","sources":["../cli.ts"],"names":[],"mappings":"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"}
package/dist/cli.js CHANGED
@@ -10,7 +10,7 @@ import { Command, CommanderError } from 'commander';
10
10
  import pc from 'picocolors';
11
11
  import { logger } from './src/logger.js';
12
12
  import { determinePackageManager, parsePackageManager, runInit, } from './src/init.js';
13
- import { SCREENCI_DISABLE_RECORDING_TIMINGS_ENV, SCREENCI_MOCK_RECORD_ENV, } from './src/runtimeMode.js';
13
+ import { SCREENCI_DISABLE_RECORDING_TIMINGS_ENV, SCREENCI_MOCK_RECORD_ENV, SCREENCI_LANGUAGES_ENV, SCREENCI_TEXT_OVERRIDES_ENV, SCREENCI_RECORD_OPTIONS_ENV, } from './src/runtimeMode.js';
14
14
  import { DEFAULT_RECORD_UPLOAD_POLICY } from './src/defaults.js';
15
15
  import { findDuplicateTitles, formatDuplicateTitlesMessage, } from './src/titleValidation.js';
16
16
  import { createLinkSessionSpec, deletePersistedLinkSessionSpec, getCliLinkSessionApiUrl, getDevBackendUrl, getDevFrontendUrl, getLinkSessionFilePath, getScreenCIEnvironment, isStoredLinkSessionReusable, readPersistedLinkSessionSpec, SCREENCI_LINK_SESSION_FILE, writePersistedLinkSessionSpec, } from './src/linkSession.js';
@@ -1004,7 +1004,7 @@ export function formatFailedVideoMessage(videoName, message) {
1004
1004
  if (message.startsWith(EXPRESSIVE_TIER_ERROR_PREFIX)) {
1005
1005
  return [
1006
1006
  `${videoName}: ${message}`,
1007
- "If you want to keep using the current tier, remove `voice.style` or `modelType: 'expressive'` from `createNarration()`.",
1007
+ "If you want to keep using the current tier, remove `voice.style` or `modelType: 'expressive'` from the localize `voice`.",
1008
1008
  ].join('\n');
1009
1009
  }
1010
1010
  return `${videoName}: ${message}`;
@@ -1447,7 +1447,7 @@ export function extractGrep(args) {
1447
1447
  // authenticated commands; the backend dispatches the workflow using the GitHub
1448
1448
  // token stored for the project. An optional `--grep` records only matching
1449
1449
  // videos/screenshots.
1450
- async function triggerRemoteRun(configPath, grep) {
1450
+ async function triggerRemoteRun(configPath, grep, languages) {
1451
1451
  const { screenciConfig, secret, apiUrl } = await requireScreenCISecret(configPath, { interactive: detectInteractiveSession() });
1452
1452
  const res = await fetch(`${apiUrl}/cli/trigger-run`, {
1453
1453
  method: 'POST',
@@ -1458,14 +1458,19 @@ async function triggerRemoteRun(configPath, grep) {
1458
1458
  body: JSON.stringify({
1459
1459
  projectName: screenciConfig.projectName,
1460
1460
  ...(grep ? { grep } : {}),
1461
+ ...(languages ? { languages } : {}),
1461
1462
  }),
1462
1463
  });
1463
1464
  if (!res.ok) {
1464
1465
  const text = await res.text();
1465
1466
  throw new Error(`Failed to trigger remote run: ${res.status} ${text}${hint401(res.status, secret)}`);
1466
1467
  }
1467
- logger.info(grep
1468
- ? `Triggered the remote recording workflow for "${screenciConfig.projectName}" (filter: ${grep}).`
1468
+ const filters = [
1469
+ ...(grep ? [`filter: ${grep}`] : []),
1470
+ ...(languages ? [`languages: ${languages}`] : []),
1471
+ ];
1472
+ logger.info(filters.length > 0
1473
+ ? `Triggered the remote recording workflow for "${screenciConfig.projectName}" (${filters.join(', ')}).`
1469
1474
  : `Triggered the remote recording workflow for "${screenciConfig.projectName}".`);
1470
1475
  }
1471
1476
  function getLastRecordFilePath(screenciDir) {
@@ -1721,19 +1726,21 @@ export async function main() {
1721
1726
  .option('-v, --verbose', 'verbose output')
1722
1727
  .option('--poll-auth', 'wait for sign-in to complete (polling every 5s, up to 5 minutes) instead of exiting, then continue recording')
1723
1728
  .option('--remote', 'trigger the GitHub Actions recording workflow for this project remotely instead of recording locally')
1729
+ .option('--languages <langs>', 'record/render only these languages (comma-separated, e.g. fi,en)')
1724
1730
  .allowUnknownOption(true)
1725
1731
  .action(async () => {
1726
1732
  const parsed = parseRecordCliArgs(getSubcommandArgv('record'));
1727
1733
  // `--remote` is a pure dispatch: it fires the project's GitHub Actions
1728
1734
  // recording workflow and exits, so there is no local Playwright run. A
1729
- // pass-through `--grep` becomes the remote recording filter.
1735
+ // pass-through `--grep` becomes the remote recording filter, and
1736
+ // `--languages` limits which language versions are recorded.
1730
1737
  if (parsed.remote) {
1731
- await triggerRemoteRun(parsed.configPath, extractGrep(parsed.otherArgs));
1738
+ await triggerRemoteRun(parsed.configPath, extractGrep(parsed.otherArgs), parsed.languages);
1732
1739
  return;
1733
1740
  }
1734
1741
  let playwrightFailure = null;
1735
1742
  try {
1736
- await run('record', parsed.otherArgs, parsed.configPath, parsed.verbose, false, parsed.pollAuth);
1743
+ await run('record', parsed.otherArgs, parsed.configPath, parsed.verbose, false, parsed.pollAuth, parsed.languages);
1737
1744
  }
1738
1745
  catch (error) {
1739
1746
  if (!(error instanceof Error))
@@ -1966,11 +1973,12 @@ function getSubcommandArgv(command) {
1966
1973
  const commandIndex = argv.indexOf(command);
1967
1974
  return commandIndex === -1 ? [] : argv.slice(commandIndex + 1);
1968
1975
  }
1969
- function parseRecordCliArgs(args) {
1976
+ export function parseRecordCliArgs(args) {
1970
1977
  let configPath;
1971
1978
  let verbose = false;
1972
1979
  let pollAuth = false;
1973
1980
  let remote = false;
1981
+ let languages;
1974
1982
  const otherArgs = [];
1975
1983
  for (let i = 0; i < args.length; i++) {
1976
1984
  const arg = args[i];
@@ -1985,6 +1993,20 @@ function parseRecordCliArgs(args) {
1985
1993
  configPath = nextArg;
1986
1994
  i++;
1987
1995
  }
1996
+ else if (arg === '--languages' || arg === '--language') {
1997
+ // screenci-only flag: parsed out so it is not forwarded to Playwright.
1998
+ const nextArg = args[i + 1];
1999
+ if (nextArg === undefined) {
2000
+ logger.error('Error: --languages requires a comma-separated value');
2001
+ process.exit(1);
2002
+ }
2003
+ languages = nextArg;
2004
+ i++;
2005
+ }
2006
+ else if (arg.startsWith('--languages=') ||
2007
+ arg.startsWith('--language=')) {
2008
+ languages = arg.slice(arg.indexOf('=') + 1);
2009
+ }
1988
2010
  else if (arg === '--verbose' || arg === '-v') {
1989
2011
  verbose = true;
1990
2012
  }
@@ -2003,6 +2025,7 @@ function parseRecordCliArgs(args) {
2003
2025
  verbose,
2004
2026
  pollAuth,
2005
2027
  remote,
2028
+ languages,
2006
2029
  otherArgs,
2007
2030
  };
2008
2031
  }
@@ -2053,7 +2076,85 @@ function validateArgs(args) {
2053
2076
  }
2054
2077
  }
2055
2078
  }
2056
- async function run(command, additionalArgs, customConfigPath, verbose = false, mockRecord = false, pollAuth = false) {
2079
+ /**
2080
+ * Fetch the project's current Studio text-field overrides so they can be
2081
+ * injected as SCREENCI_TEXT_OVERRIDES before a recording. On-screen `text`
2082
+ * fields render during the recording (they cannot be patched at render time),
2083
+ * so any Studio edits must be present here; code-declared seeds are the
2084
+ * fallback. Best-effort: any failure returns an empty env so the SDK uses the
2085
+ * code seeds, and a recording is never blocked by this fetch.
2086
+ */
2087
+ async function fetchTextOverridesEnv(configPath, languages, verbose) {
2088
+ try {
2089
+ const { screenciConfig, secret, apiUrl } = await requireScreenCISecret(configPath, { interactive: false });
2090
+ const params = new URLSearchParams({
2091
+ projectName: screenciConfig.projectName,
2092
+ });
2093
+ if (languages)
2094
+ params.set('languages', languages);
2095
+ const res = await fetch(`${apiUrl}/cli/text-overrides?${params.toString()}`, { headers: { 'X-ScreenCI-Secret': secret } });
2096
+ if (!res.ok) {
2097
+ if (verbose) {
2098
+ logger.warn(`Could not fetch Studio text overrides (${res.status}); using code-declared values.`);
2099
+ }
2100
+ return {};
2101
+ }
2102
+ const body = (await res.json());
2103
+ const overrides = body.overrides;
2104
+ if (overrides === undefined ||
2105
+ overrides === null ||
2106
+ typeof overrides !== 'object' ||
2107
+ Object.keys(overrides).length === 0) {
2108
+ return {};
2109
+ }
2110
+ return { [SCREENCI_TEXT_OVERRIDES_ENV]: JSON.stringify(overrides) };
2111
+ }
2112
+ catch (error) {
2113
+ if (verbose) {
2114
+ logger.warn(`Could not fetch Studio text overrides; using code-declared values.${error instanceof Error ? ` (${error.message})` : ''}`);
2115
+ }
2116
+ return {};
2117
+ }
2118
+ }
2119
+ /**
2120
+ * Fetch the project's current Studio record-option overrides so they can be
2121
+ * injected as SCREENCI_RECORD_OPTIONS before a recording. Record options (aspect
2122
+ * ratio, quality, fps) change the captured viewport/encode, so any Studio edits
2123
+ * must be present here; code-declared values are the fallback. Best-effort: any
2124
+ * failure returns an empty env so the SDK uses the code values, and a recording
2125
+ * is never blocked by this fetch.
2126
+ */
2127
+ async function fetchRecordOptionsEnv(configPath, verbose) {
2128
+ try {
2129
+ const { screenciConfig, secret, apiUrl } = await requireScreenCISecret(configPath, { interactive: false });
2130
+ const params = new URLSearchParams({
2131
+ projectName: screenciConfig.projectName,
2132
+ });
2133
+ const res = await fetch(`${apiUrl}/cli/record-options?${params.toString()}`, { headers: { 'X-ScreenCI-Secret': secret } });
2134
+ if (!res.ok) {
2135
+ if (verbose) {
2136
+ logger.warn(`Could not fetch Studio record options (${res.status}); using code-declared values.`);
2137
+ }
2138
+ return {};
2139
+ }
2140
+ const body = (await res.json());
2141
+ const recordOptions = body.recordOptions;
2142
+ if (recordOptions === undefined ||
2143
+ recordOptions === null ||
2144
+ typeof recordOptions !== 'object' ||
2145
+ Object.keys(recordOptions).length === 0) {
2146
+ return {};
2147
+ }
2148
+ return { [SCREENCI_RECORD_OPTIONS_ENV]: JSON.stringify(recordOptions) };
2149
+ }
2150
+ catch (error) {
2151
+ if (verbose) {
2152
+ logger.warn(`Could not fetch Studio record options; using code-declared values.${error instanceof Error ? ` (${error.message})` : ''}`);
2153
+ }
2154
+ return {};
2155
+ }
2156
+ }
2157
+ async function run(command, additionalArgs, customConfigPath, verbose = false, mockRecord = false, pollAuth = false, languages) {
2057
2158
  const configPath = resolveScreenCIConfigPathOrExit(customConfigPath);
2058
2159
  if (command === 'test' || process.env.SCREENCI_RECORDING !== 'true') {
2059
2160
  await loadEnvFileFromConfigSource(configPath, false);
@@ -2070,11 +2171,25 @@ async function run(command, additionalArgs, customConfigPath, verbose = false, m
2070
2171
  const screenciDir = resolve(dirname(configPath), '.screenci');
2071
2172
  clearRecordingDirectories(screenciDir);
2072
2173
  }
2174
+ // Studio text-field overrides are injected for the record command only: they
2175
+ // resolve in the SDK's `text` fixture before the recording runs. `test` (the
2176
+ // preview run) keeps code-declared values.
2177
+ const textOverridesEnv = command === 'record'
2178
+ ? await fetchTextOverridesEnv(configPath, languages, verbose)
2179
+ : {};
2180
+ // Studio record-option overrides are likewise injected for record only: they
2181
+ // resolve in the SDK's `recordOptions` fixture before the capture runs.
2182
+ const recordOptionsEnv = command === 'record' ? await fetchRecordOptionsEnv(configPath, verbose) : {};
2073
2183
  const envForChild = { ...process.env };
2074
2184
  await validateUniqueDiscoveredTestTitles(configPath, additionalArgs, {
2075
2185
  ...envForChild,
2076
2186
  SCREENCI_CONFIG_DIR: dirname(configPath),
2077
2187
  ...(command === 'record' ? { SCREENCI_RECORDING: 'true' } : {}),
2188
+ ...(command === 'record' && languages
2189
+ ? { [SCREENCI_LANGUAGES_ENV]: languages }
2190
+ : {}),
2191
+ ...textOverridesEnv,
2192
+ ...recordOptionsEnv,
2078
2193
  ...(command === 'test' && !mockRecord
2079
2194
  ? { [SCREENCI_DISABLE_RECORDING_TIMINGS_ENV]: 'true' }
2080
2195
  : {}),
@@ -2101,6 +2216,14 @@ async function run(command, additionalArgs, customConfigPath, verbose = false, m
2101
2216
  SCREENCI_CONFIG_DIR: dirname(configPath),
2102
2217
  // Enable recording only for record command
2103
2218
  ...(command === 'record' ? { SCREENCI_RECORDING: 'true' } : {}),
2219
+ // Per-language filter: the builder records only these languages.
2220
+ ...(command === 'record' && languages
2221
+ ? { [SCREENCI_LANGUAGES_ENV]: languages }
2222
+ : {}),
2223
+ // Studio text-field overrides resolved from the backend (record only).
2224
+ ...textOverridesEnv,
2225
+ // Studio record-option overrides resolved from the backend (record only).
2226
+ ...recordOptionsEnv,
2104
2227
  ...(command === 'test' && !mockRecord
2105
2228
  ? { [SCREENCI_DISABLE_RECORDING_TIMINGS_ENV]: 'true' }
2106
2229
  : {}),