lingo.dev 0.92.3 → 0.92.5

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/build/cli.mjs CHANGED
@@ -3134,18 +3134,17 @@ function parseVueFile(input2) {
3134
3134
 
3135
3135
  // src/cli/loaders/typescript/index.ts
3136
3136
  import { parse as parse2 } from "@babel/parser";
3137
+ import _18 from "lodash";
3137
3138
  import babelTraverseModule from "@babel/traverse";
3138
3139
  import * as t from "@babel/types";
3139
3140
  import babelGenerateModule from "@babel/generator";
3140
- import { flatten as flatten2, unflatten as unflatten2 } from "flat";
3141
- import _18 from "lodash";
3142
3141
 
3143
3142
  // src/cli/loaders/typescript/cjs-interop.ts
3144
3143
  function resolveCjsExport(mod, name = "module") {
3145
3144
  if (typeof mod === "function" || typeof mod !== "object" || mod === null) {
3146
3145
  return mod;
3147
3146
  }
3148
- if (typeof mod.default !== "undefined") {
3147
+ if ("default" in mod && typeof mod.default !== "undefined") {
3149
3148
  return mod.default;
3150
3149
  }
3151
3150
  console.error(
@@ -3165,33 +3164,20 @@ function createTypescriptLoader() {
3165
3164
  if (!input2) {
3166
3165
  return {};
3167
3166
  }
3168
- try {
3169
- const ast = parseTypeScript(input2);
3170
- const extractedStrings = extractStringsFromDefaultExport(ast);
3171
- return flattenExtractedStrings(extractedStrings);
3172
- } catch (error) {
3173
- console.error("Error parsing TypeScript file:", error);
3174
- return {};
3175
- }
3167
+ const ast = parseTypeScript(input2);
3168
+ const extractedStrings = extractStringsFromDefaultExport(ast);
3169
+ return extractedStrings;
3176
3170
  },
3177
3171
  push: async (locale, data, originalInput, defaultLocale, pullInput, pullOutput) => {
3178
- if (!data) {
3179
- return "";
3180
- }
3181
- const input2 = originalInput;
3182
- try {
3183
- const ast = parseTypeScript(input2);
3184
- const nestedData = unflattenStringData(data);
3185
- const modified = updateStringsInDefaultExport(ast, nestedData);
3186
- if (!modified) {
3187
- return input2;
3172
+ const ast = parseTypeScript(originalInput || "");
3173
+ const finalData = _18.merge({}, pullOutput, data);
3174
+ updateStringsInDefaultExport(ast, finalData);
3175
+ const { code } = generate(ast, {
3176
+ jsescOption: {
3177
+ minimal: true
3188
3178
  }
3189
- const { code } = generate(ast);
3190
- return code;
3191
- } catch (error) {
3192
- console.error("Error updating TypeScript file:", error);
3193
- return input2;
3194
- }
3179
+ });
3180
+ return code;
3195
3181
  }
3196
3182
  });
3197
3183
  }
@@ -3201,218 +3187,159 @@ function parseTypeScript(input2) {
3201
3187
  plugins: ["typescript"]
3202
3188
  });
3203
3189
  }
3204
- function flattenExtractedStrings(obj) {
3205
- const flattened = flatten2(obj, { delimiter: "/" });
3206
- return Object.entries(flattened).reduce(
3207
- (acc, [key, value]) => {
3208
- if (typeof value === "string") {
3209
- acc[key] = value;
3210
- }
3211
- return acc;
3212
- },
3213
- {}
3214
- );
3215
- }
3216
- function unflattenStringData(data) {
3217
- return unflatten2(data, { delimiter: "/" });
3218
- }
3219
3190
  function extractStringsFromDefaultExport(ast) {
3220
- const result = {};
3191
+ let extracted = {};
3221
3192
  traverse(ast, {
3222
3193
  ExportDefaultDeclaration(path17) {
3223
- if (t.isObjectExpression(path17.node.declaration)) {
3224
- extractStringsFromObjectExpression(path17.node.declaration, result, "");
3225
- } else if (t.isIdentifier(path17.node.declaration)) {
3226
- extractStringsFromExportedIdentifier(path17, result, "");
3194
+ const { declaration } = path17.node;
3195
+ const decl = unwrapTSAsExpression(declaration);
3196
+ if (t.isObjectExpression(decl)) {
3197
+ extracted = objectExpressionToObject(decl);
3198
+ } else if (t.isArrayExpression(decl)) {
3199
+ extracted = arrayExpressionToArray(decl);
3200
+ } else if (t.isIdentifier(decl)) {
3201
+ const binding = path17.scope.bindings[decl.name];
3202
+ if (binding && t.isVariableDeclarator(binding.path.node) && binding.path.node.init) {
3203
+ const initRaw = binding.path.node.init;
3204
+ const init = initRaw ? unwrapTSAsExpression(initRaw) : initRaw;
3205
+ if (t.isObjectExpression(init)) {
3206
+ extracted = objectExpressionToObject(init);
3207
+ } else if (t.isArrayExpression(init)) {
3208
+ extracted = arrayExpressionToArray(init);
3209
+ }
3210
+ }
3227
3211
  }
3228
3212
  }
3229
3213
  });
3230
- return result;
3214
+ return extracted;
3215
+ }
3216
+ function unwrapTSAsExpression(node) {
3217
+ let current = node;
3218
+ while (t.isTSAsExpression(current)) {
3219
+ current = current.expression;
3220
+ }
3221
+ return current;
3231
3222
  }
3232
- function extractStringsFromObjectExpression(objectExpression, result, path17) {
3223
+ function objectExpressionToObject(objectExpression) {
3224
+ const obj = {};
3233
3225
  objectExpression.properties.forEach((prop) => {
3234
- if (t.isObjectProperty(prop)) {
3235
- const key = getPropertyKey(prop);
3236
- const currentPath = path17 ? `${path17}/${key}` : key;
3237
- if (t.isStringLiteral(prop.value)) {
3238
- _18.set(result, currentPath, prop.value.value);
3239
- } else if (t.isObjectExpression(prop.value)) {
3240
- extractStringsFromObjectExpression(prop.value, result, currentPath);
3241
- } else if (t.isArrayExpression(prop.value)) {
3242
- extractStringsFromArrayExpression(prop.value, result, currentPath);
3226
+ if (!t.isObjectProperty(prop)) return;
3227
+ const key = getPropertyKey(prop);
3228
+ if (t.isStringLiteral(prop.value)) {
3229
+ obj[key] = prop.value.value;
3230
+ } else if (t.isObjectExpression(prop.value)) {
3231
+ const nested = objectExpressionToObject(prop.value);
3232
+ if (Object.keys(nested).length > 0) {
3233
+ obj[key] = nested;
3234
+ }
3235
+ } else if (t.isArrayExpression(prop.value)) {
3236
+ const arr = arrayExpressionToArray(prop.value);
3237
+ if (arr.length > 0) {
3238
+ obj[key] = arr;
3243
3239
  }
3244
3240
  }
3245
3241
  });
3242
+ return obj;
3246
3243
  }
3247
- function extractStringsFromArrayExpression(arrayExpression, result, path17) {
3248
- arrayExpression.elements.forEach((element, index) => {
3249
- const currentPath = `${path17}/${index}`;
3244
+ function arrayExpressionToArray(arrayExpression) {
3245
+ const arr = [];
3246
+ arrayExpression.elements.forEach((element) => {
3247
+ if (!element) return;
3250
3248
  if (t.isStringLiteral(element)) {
3251
- _18.set(result, currentPath, element.value);
3249
+ arr.push(element.value);
3252
3250
  } else if (t.isObjectExpression(element)) {
3253
- extractStringsFromObjectExpression(element, result, currentPath);
3251
+ const nestedObj = objectExpressionToObject(element);
3252
+ arr.push(nestedObj);
3254
3253
  } else if (t.isArrayExpression(element)) {
3255
- extractStringsFromArrayExpression(element, result, currentPath);
3254
+ arr.push(arrayExpressionToArray(element));
3256
3255
  }
3257
3256
  });
3258
- }
3259
- function extractStringsFromExportedIdentifier(path17, result, basePath) {
3260
- const exportName = path17.node.declaration.name;
3261
- const binding = path17.scope.bindings[exportName];
3262
- if (binding && binding.path.node) {
3263
- const bindingPath = binding.path;
3264
- if (t.isVariableDeclarator(bindingPath.node) && bindingPath.node.init) {
3265
- if (t.isObjectExpression(bindingPath.node.init)) {
3266
- extractStringsFromObjectExpression(
3267
- bindingPath.node.init,
3268
- result,
3269
- basePath
3270
- );
3271
- } else if (t.isArrayExpression(bindingPath.node.init)) {
3272
- extractStringsFromArrayExpression(
3273
- bindingPath.node.init,
3274
- result,
3275
- basePath
3276
- );
3277
- }
3278
- }
3279
- }
3257
+ return arr;
3280
3258
  }
3281
3259
  function updateStringsInDefaultExport(ast, data) {
3282
3260
  let modified = false;
3283
3261
  traverse(ast, {
3284
3262
  ExportDefaultDeclaration(path17) {
3285
- if (t.isObjectExpression(path17.node.declaration)) {
3286
- modified = updateStringsInObjectExpression(path17.node.declaration, data, "") || modified;
3287
- } else if (t.isIdentifier(path17.node.declaration)) {
3288
- modified = updateStringsInExportedIdentifier(path17, data, "") || modified;
3263
+ const { declaration } = path17.node;
3264
+ const decl = unwrapTSAsExpression(declaration);
3265
+ if (t.isObjectExpression(decl)) {
3266
+ modified = updateStringsInObjectExpression(decl, data) || modified;
3267
+ } else if (t.isArrayExpression(decl)) {
3268
+ if (Array.isArray(data)) {
3269
+ modified = updateStringsInArrayExpression(decl, data) || modified;
3270
+ }
3271
+ } else if (t.isIdentifier(decl)) {
3272
+ modified = updateStringsInExportedIdentifier(path17, data) || modified;
3289
3273
  }
3290
3274
  }
3291
3275
  });
3292
3276
  return modified;
3293
3277
  }
3294
- function updateStringsInObjectExpression(objectExpression, data, path17) {
3278
+ function updateStringsInObjectExpression(objectExpression, data) {
3295
3279
  let modified = false;
3296
3280
  objectExpression.properties.forEach((prop) => {
3297
- if (t.isObjectProperty(prop)) {
3298
- const key = getPropertyKey(prop);
3299
- const currentPath = path17 ? `${path17}/${key}` : key;
3300
- if (t.isStringLiteral(prop.value)) {
3301
- if (data[currentPath] !== void 0) {
3302
- prop.value.value = data[currentPath];
3303
- modified = true;
3304
- } else if (path17 === "" && data[key] !== void 0) {
3305
- prop.value.value = data[key];
3306
- modified = true;
3307
- }
3308
- } else if (t.isObjectExpression(prop.value)) {
3309
- if (data[key] && typeof data[key] === "object") {
3310
- const subModified = updateStringsInObjectExpression(
3311
- prop.value,
3312
- data[key],
3313
- ""
3314
- );
3315
- modified = subModified || modified;
3316
- } else {
3317
- const subModified = updateStringsInObjectExpression(
3318
- prop.value,
3319
- data,
3320
- currentPath
3321
- );
3322
- modified = subModified || modified;
3323
- }
3324
- } else if (t.isArrayExpression(prop.value)) {
3325
- if (data[key] && Array.isArray(data[key])) {
3326
- const subModified = updateStringsInArrayExpression(
3327
- prop.value,
3328
- data[key],
3329
- ""
3330
- );
3331
- modified = subModified || modified;
3332
- } else {
3333
- const subModified = updateStringsInArrayExpression(
3334
- prop.value,
3335
- data,
3336
- currentPath
3337
- );
3338
- modified = subModified || modified;
3339
- }
3281
+ if (!t.isObjectProperty(prop)) return;
3282
+ const key = getPropertyKey(prop);
3283
+ const incomingVal = data?.[key];
3284
+ if (incomingVal === void 0) {
3285
+ return;
3286
+ }
3287
+ if (t.isStringLiteral(prop.value) && typeof incomingVal === "string") {
3288
+ if (prop.value.value !== incomingVal) {
3289
+ prop.value.value = incomingVal;
3290
+ modified = true;
3340
3291
  }
3292
+ } else if (t.isObjectExpression(prop.value) && typeof incomingVal === "object" && !Array.isArray(incomingVal)) {
3293
+ const subModified = updateStringsInObjectExpression(
3294
+ prop.value,
3295
+ incomingVal
3296
+ );
3297
+ modified = subModified || modified;
3298
+ } else if (t.isArrayExpression(prop.value) && Array.isArray(incomingVal)) {
3299
+ const subModified = updateStringsInArrayExpression(
3300
+ prop.value,
3301
+ incomingVal
3302
+ );
3303
+ modified = subModified || modified;
3341
3304
  }
3342
3305
  });
3343
3306
  return modified;
3344
3307
  }
3345
- function updateStringsInArrayExpression(arrayExpression, data, path17) {
3308
+ function updateStringsInArrayExpression(arrayExpression, incoming) {
3346
3309
  let modified = false;
3347
3310
  arrayExpression.elements.forEach((element, index) => {
3348
- const currentPath = `${path17}/${index}`;
3349
- if (t.isStringLiteral(element)) {
3350
- if (Array.isArray(data) && data[index] !== void 0) {
3351
- element.value = data[index];
3352
- modified = true;
3353
- } else if (!Array.isArray(data) && data[currentPath] !== void 0) {
3354
- element.value = data[currentPath];
3311
+ if (!element) return;
3312
+ const incomingVal = incoming?.[index];
3313
+ if (incomingVal === void 0) return;
3314
+ if (t.isStringLiteral(element) && typeof incomingVal === "string") {
3315
+ if (element.value !== incomingVal) {
3316
+ element.value = incomingVal;
3355
3317
  modified = true;
3356
3318
  }
3357
- } else if (t.isObjectExpression(element)) {
3358
- if (Array.isArray(data) && data[index] && typeof data[index] === "object") {
3359
- const subModified = updateStringsInObjectExpression(
3360
- element,
3361
- data[index],
3362
- ""
3363
- );
3364
- modified = subModified || modified;
3365
- } else {
3366
- const subModified = updateStringsInObjectExpression(
3367
- element,
3368
- data,
3369
- currentPath
3370
- );
3371
- modified = subModified || modified;
3372
- }
3373
- } else if (t.isArrayExpression(element)) {
3374
- if (Array.isArray(data) && data[index] && Array.isArray(data[index])) {
3375
- const subModified = updateStringsInArrayExpression(
3376
- element,
3377
- data[index],
3378
- ""
3379
- );
3380
- modified = subModified || modified;
3381
- } else {
3382
- const subModified = updateStringsInArrayExpression(
3383
- element,
3384
- data,
3385
- currentPath
3386
- );
3387
- modified = subModified || modified;
3388
- }
3319
+ } else if (t.isObjectExpression(element) && typeof incomingVal === "object" && !Array.isArray(incomingVal)) {
3320
+ const subModified = updateStringsInObjectExpression(element, incomingVal);
3321
+ modified = subModified || modified;
3322
+ } else if (t.isArrayExpression(element) && Array.isArray(incomingVal)) {
3323
+ const subModified = updateStringsInArrayExpression(element, incomingVal);
3324
+ modified = subModified || modified;
3389
3325
  }
3390
3326
  });
3391
3327
  return modified;
3392
3328
  }
3393
- function updateStringsInExportedIdentifier(path17, data, basePath) {
3394
- let modified = false;
3329
+ function updateStringsInExportedIdentifier(path17, data) {
3395
3330
  const exportName = path17.node.declaration.name;
3396
3331
  const binding = path17.scope.bindings[exportName];
3397
- if (binding && binding.path.node) {
3398
- const bindingPath = binding.path;
3399
- if (t.isVariableDeclarator(bindingPath.node) && bindingPath.node.init) {
3400
- if (t.isObjectExpression(bindingPath.node.init)) {
3401
- modified = updateStringsInObjectExpression(
3402
- bindingPath.node.init,
3403
- data,
3404
- basePath
3405
- ) || modified;
3406
- } else if (t.isArrayExpression(bindingPath.node.init)) {
3407
- modified = updateStringsInArrayExpression(
3408
- bindingPath.node.init,
3409
- data,
3410
- basePath
3411
- ) || modified;
3412
- }
3332
+ if (!binding || !binding.path.node) return false;
3333
+ if (t.isVariableDeclarator(binding.path.node) && binding.path.node.init) {
3334
+ const initRaw = binding.path.node.init;
3335
+ const init = initRaw ? unwrapTSAsExpression(initRaw) : initRaw;
3336
+ if (t.isObjectExpression(init)) {
3337
+ return updateStringsInObjectExpression(init, data);
3338
+ } else if (t.isArrayExpression(init)) {
3339
+ return updateStringsInArrayExpression(init, data);
3413
3340
  }
3414
3341
  }
3415
- return modified;
3342
+ return false;
3416
3343
  }
3417
3344
  function getPropertyKey(prop) {
3418
3345
  if (t.isIdentifier(prop.key)) {
@@ -4114,11 +4041,14 @@ function withExponentialBackoff(fn, maxAttempts = 3, baseDelay = 1e3) {
4114
4041
  }
4115
4042
 
4116
4043
  // src/cli/utils/observability.ts
4044
+ import pkg from "node-machine-id";
4045
+ var { machineIdSync } = pkg;
4117
4046
  async function trackEvent(distinctId, event, properties) {
4118
4047
  if (process.env.DO_NOT_TRACK) {
4119
4048
  return;
4120
4049
  }
4121
4050
  try {
4051
+ const actualId = distinctId || `device-${machineIdSync()}`;
4122
4052
  const { PostHog } = await import("posthog-node");
4123
4053
  const safeProperties = properties ? JSON.parse(
4124
4054
  JSON.stringify(properties, (key, value) => {
@@ -4141,7 +4071,7 @@ async function trackEvent(distinctId, event, properties) {
4141
4071
  }
4142
4072
  );
4143
4073
  await posthog.capture({
4144
- distinctId,
4074
+ distinctId: actualId,
4145
4075
  event,
4146
4076
  properties: {
4147
4077
  ...safeProperties,
@@ -4267,7 +4197,7 @@ function createDeltaProcessor(fileKey) {
4267
4197
  }
4268
4198
 
4269
4199
  // src/cli/cmd/i18n.ts
4270
- import { flatten as flatten3, unflatten as unflatten3 } from "flat";
4200
+ import { flatten as flatten2, unflatten as unflatten2 } from "flat";
4271
4201
  var i18n_default = new Command6().command("i18n").description("Run Localization engine").helpOption("-h, --help", "Show help").option(
4272
4202
  "--locale <locale>",
4273
4203
  "Locale to process",
@@ -4327,9 +4257,15 @@ var i18n_default = new Command6().command("i18n").description("Run Localization
4327
4257
  validateParams(i18nConfig, flags);
4328
4258
  ora.succeed("Localization configuration is valid");
4329
4259
  ora.start("Connecting to Lingo.dev Localization Engine...");
4330
- const auth = await validateAuth(settings);
4331
- authId = auth.id;
4332
- ora.succeed(`Authenticated as ${auth.email}`);
4260
+ const isByokMode = i18nConfig?.provider && i18nConfig.provider.id !== "lingo";
4261
+ if (isByokMode) {
4262
+ authId = null;
4263
+ ora.succeed("Using external provider (BYOK mode)");
4264
+ } else {
4265
+ const auth = await validateAuth(settings);
4266
+ authId = auth.id;
4267
+ ora.succeed(`Authenticated as ${auth.email}`);
4268
+ }
4333
4269
  trackEvent(authId, "cmd.i18n.start", {
4334
4270
  i18nConfig,
4335
4271
  flags
@@ -4417,7 +4353,7 @@ var i18n_default = new Command6().command("i18n").description("Run Localization
4417
4353
  );
4418
4354
  const sourceContent = tryReadFile(sourcePath, null);
4419
4355
  const sourceData = JSON.parse(sourceContent || "{}");
4420
- const sourceFlattenedData = flatten3(sourceData, {
4356
+ const sourceFlattenedData = flatten2(sourceData, {
4421
4357
  delimiter: "/",
4422
4358
  transformKey(key) {
4423
4359
  return encodeURIComponent(key);
@@ -4434,7 +4370,7 @@ var i18n_default = new Command6().command("i18n").description("Run Localization
4434
4370
  );
4435
4371
  const targetContent = tryReadFile(targetPath, null);
4436
4372
  const targetData = JSON.parse(targetContent || "{}");
4437
- const targetFlattenedData = flatten3(targetData, {
4373
+ const targetFlattenedData = flatten2(targetData, {
4438
4374
  delimiter: "/",
4439
4375
  transformKey(key) {
4440
4376
  return encodeURIComponent(key);
@@ -4453,7 +4389,7 @@ var i18n_default = new Command6().command("i18n").description("Run Localization
4453
4389
  targetFlattenedData[newKey] = targetFlattenedData[oldKey];
4454
4390
  delete targetFlattenedData[oldKey];
4455
4391
  }
4456
- const updatedTargetData = unflatten3(targetFlattenedData, {
4392
+ const updatedTargetData = unflatten2(targetFlattenedData, {
4457
4393
  delimiter: "/",
4458
4394
  transformKey(key) {
4459
4395
  return decodeURIComponent(key);
@@ -4706,7 +4642,7 @@ var i18n_default = new Command6().command("i18n").description("Run Localization
4706
4642
  console.log();
4707
4643
  if (!hasErrors) {
4708
4644
  ora.succeed("Localization completed.");
4709
- trackEvent(auth.id, "cmd.i18n.success", {
4645
+ trackEvent(authId, "cmd.i18n.success", {
4710
4646
  i18nConfig,
4711
4647
  flags
4712
4648
  });
@@ -6355,7 +6291,7 @@ async function renderHero() {
6355
6291
  // package.json
6356
6292
  var package_default = {
6357
6293
  name: "lingo.dev",
6358
- version: "0.92.3",
6294
+ version: "0.92.5",
6359
6295
  description: "Lingo.dev CLI",
6360
6296
  private: false,
6361
6297
  publishConfig: {
@@ -6456,6 +6392,7 @@ var package_default = {
6456
6392
  "mdast-util-from-markdown": "^2.0.2",
6457
6393
  "mdast-util-gfm": "^3.1.0",
6458
6394
  "micromark-extension-gfm": "^3.0.0",
6395
+ "node-machine-id": "^1.1.12",
6459
6396
  "node-webvtt": "^1.9.4",
6460
6397
  "object-hash": "^3.0.0",
6461
6398
  octokit: "^4.0.2",