@kopynator/cli 1.0.11 → 1.0.12

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/dist/index.js CHANGED
@@ -204,6 +204,7 @@ async function checkCommand() {
204
204
  var import_chalk3 = __toESM(require("chalk"));
205
205
  var import_fs3 = __toESM(require("fs"));
206
206
  var import_path3 = __toESM(require("path"));
207
+ var import_inquirer2 = __toESM(require("inquirer"));
207
208
  function detectFramework() {
208
209
  const angularJson = import_path3.default.join(process.cwd(), "angular.json");
209
210
  const packageJson = import_path3.default.join(process.cwd(), "package.json");
@@ -267,6 +268,59 @@ function extractApiKey() {
267
268
  }
268
269
  return null;
269
270
  }
271
+ async function getSyncConfig() {
272
+ const configPath = import_path3.default.join(process.cwd(), "kopynator.sync.config.json");
273
+ if (import_fs3.default.existsSync(configPath)) {
274
+ try {
275
+ const config2 = JSON.parse(import_fs3.default.readFileSync(configPath, "utf-8"));
276
+ console.log(import_chalk3.default.blue("\u2139\uFE0F Using existing sync configuration"));
277
+ return config2;
278
+ } catch (e) {
279
+ console.log(import_chalk3.default.yellow("\u26A0\uFE0F Error reading sync config, creating new one"));
280
+ }
281
+ }
282
+ console.log(import_chalk3.default.blue("\n\u{1F4DD} First time sync! Let's configure your preferences:\n"));
283
+ const answers = await import_inquirer2.default.prompt([
284
+ {
285
+ type: "confirm",
286
+ name: "nested",
287
+ message: 'Use nested JSON structure? (e.g., {"nav": {"home": "Home"}})',
288
+ default: false
289
+ },
290
+ {
291
+ type: "confirm",
292
+ name: "includeLangKey",
293
+ message: 'Include language key in output? (e.g., {"en": {...}, "es": {...}})',
294
+ default: false
295
+ },
296
+ {
297
+ type: "confirm",
298
+ name: "pretty",
299
+ message: "Pretty print JSON?",
300
+ default: true
301
+ },
302
+ {
303
+ type: "list",
304
+ name: "indent",
305
+ message: "Indentation style:",
306
+ choices: [
307
+ { name: "2 spaces", value: "2" },
308
+ { name: "4 spaces", value: "4" },
309
+ { name: "Tabs", value: "tab" }
310
+ ],
311
+ default: "2"
312
+ }
313
+ ]);
314
+ const config = {
315
+ nested: answers.nested,
316
+ includeLangKey: answers.includeLangKey,
317
+ pretty: answers.pretty,
318
+ indent: answers.indent
319
+ };
320
+ import_fs3.default.writeFileSync(configPath, JSON.stringify(config, null, 2));
321
+ console.log(import_chalk3.default.green("\u2705 Configuration saved to kopynator.sync.config.json\n"));
322
+ return config;
323
+ }
270
324
  async function syncCommand() {
271
325
  console.log(import_chalk3.default.bold.blue("\n\u2601\uFE0F Syncing with Kopynator Cloud...\n"));
272
326
  const framework = detectFramework();
@@ -277,6 +331,7 @@ async function syncCommand() {
277
331
  console.log(import_chalk3.default.yellow("Run `npx kopynator init` first or configure your API key manually."));
278
332
  return;
279
333
  }
334
+ const syncConfig = await getSyncConfig();
280
335
  const baseUrl = config.baseUrl || "http://localhost:7300/api/tokens";
281
336
  const token = config.apiKey;
282
337
  try {
@@ -296,7 +351,7 @@ async function syncCommand() {
296
351
  }
297
352
  for (const locale of languages) {
298
353
  console.log(import_chalk3.default.blue(`\u2B07\uFE0F Downloading ${locale}...`));
299
- const fetchUrl = `${baseUrl}/fetch?token=${token}&langs=${locale}&nested=false&includeLangKey=false&pretty=true&indent=2`;
354
+ const fetchUrl = `${baseUrl}/fetch?token=${token}&langs=${locale}&nested=${syncConfig.nested}&includeLangKey=${syncConfig.includeLangKey}&pretty=${syncConfig.pretty}&indent=${syncConfig.indent}`;
300
355
  const translationResponse = await fetch(fetchUrl);
301
356
  if (!translationResponse.ok) {
302
357
  console.log(import_chalk3.default.yellow(`\u26A0\uFE0F Failed to fetch ${locale}: ${translationResponse.status}`));
@@ -304,7 +359,14 @@ async function syncCommand() {
304
359
  }
305
360
  const translationData = await translationResponse.json();
306
361
  const outputPath = import_path3.default.join(i18nDir, `${locale}.json`);
307
- import_fs3.default.writeFileSync(outputPath, JSON.stringify(translationData, null, 2));
362
+ let jsonString;
363
+ if (syncConfig.pretty) {
364
+ const indentValue = syncConfig.indent === "tab" ? " " : Number(syncConfig.indent);
365
+ jsonString = JSON.stringify(translationData, null, indentValue);
366
+ } else {
367
+ jsonString = JSON.stringify(translationData);
368
+ }
369
+ import_fs3.default.writeFileSync(outputPath, jsonString);
308
370
  console.log(import_chalk3.default.green(`\u2705 Saved ${locale}.json`));
309
371
  }
310
372
  console.log(import_chalk3.default.bold.green("\n\u{1F389} Sync completed successfully!\n"));
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kopynator/cli",
3
- "version": "1.0.11",
3
+ "version": "1.0.12",
4
4
  "description": "CLI tool for Kopynator - The i18n management solution",
5
5
  "bin": {
6
6
  "kopynator": "dist/index.js"
@@ -1,12 +1,20 @@
1
1
  import chalk from 'chalk';
2
2
  import fs from 'fs';
3
3
  import path from 'path';
4
+ import inquirer from 'inquirer';
4
5
 
5
6
  interface KopyConfig {
6
7
  apiKey: string;
7
8
  baseUrl?: string;
8
9
  }
9
10
 
11
+ interface SyncConfig {
12
+ nested: boolean;
13
+ includeLangKey: boolean;
14
+ pretty: boolean;
15
+ indent: '2' | '4' | 'tab';
16
+ }
17
+
10
18
  /**
11
19
  * Detect the framework being used in the current project
12
20
  */
@@ -100,6 +108,72 @@ function extractApiKey(): KopyConfig | null {
100
108
  return null;
101
109
  }
102
110
 
111
+ /**
112
+ * Load or create sync configuration
113
+ */
114
+ async function getSyncConfig(): Promise<SyncConfig> {
115
+ const configPath = path.join(process.cwd(), 'kopynator.sync.config.json');
116
+
117
+ // If config exists, load it
118
+ if (fs.existsSync(configPath)) {
119
+ try {
120
+ const config = JSON.parse(fs.readFileSync(configPath, 'utf-8'));
121
+ console.log(chalk.blue('ℹ️ Using existing sync configuration'));
122
+ return config;
123
+ } catch (e) {
124
+ console.log(chalk.yellow('⚠️ Error reading sync config, creating new one'));
125
+ }
126
+ }
127
+
128
+ // Ask user for preferences
129
+ console.log(chalk.blue('\n📝 First time sync! Let\'s configure your preferences:\n'));
130
+
131
+ const answers = await inquirer.prompt([
132
+ {
133
+ type: 'confirm',
134
+ name: 'nested',
135
+ message: 'Use nested JSON structure? (e.g., {"nav": {"home": "Home"}})',
136
+ default: false,
137
+ },
138
+ {
139
+ type: 'confirm',
140
+ name: 'includeLangKey',
141
+ message: 'Include language key in output? (e.g., {"en": {...}, "es": {...}})',
142
+ default: false,
143
+ },
144
+ {
145
+ type: 'confirm',
146
+ name: 'pretty',
147
+ message: 'Pretty print JSON?',
148
+ default: true,
149
+ },
150
+ {
151
+ type: 'list',
152
+ name: 'indent',
153
+ message: 'Indentation style:',
154
+ choices: [
155
+ { name: '2 spaces', value: '2' },
156
+ { name: '4 spaces', value: '4' },
157
+ { name: 'Tabs', value: 'tab' },
158
+ ],
159
+ default: '2',
160
+ },
161
+ ]);
162
+
163
+ const config: SyncConfig = {
164
+ nested: answers.nested,
165
+ includeLangKey: answers.includeLangKey,
166
+ pretty: answers.pretty,
167
+ indent: answers.indent,
168
+ };
169
+
170
+ // Save config
171
+ fs.writeFileSync(configPath, JSON.stringify(config, null, 2));
172
+ console.log(chalk.green('✅ Configuration saved to kopynator.sync.config.json\n'));
173
+
174
+ return config;
175
+ }
176
+
103
177
  export async function syncCommand() {
104
178
  console.log(chalk.bold.blue('\n☁️ Syncing with Kopynator Cloud...\n'));
105
179
 
@@ -115,6 +189,9 @@ export async function syncCommand() {
115
189
  return;
116
190
  }
117
191
 
192
+ // Get sync configuration
193
+ const syncConfig = await getSyncConfig();
194
+
118
195
  const baseUrl = config.baseUrl || 'http://localhost:7300/api/tokens';
119
196
  const token = config.apiKey;
120
197
 
@@ -142,7 +219,7 @@ export async function syncCommand() {
142
219
  // 3. Download translations for each language
143
220
  for (const locale of languages) {
144
221
  console.log(chalk.blue(`⬇️ Downloading ${locale}...`));
145
- const fetchUrl = `${baseUrl}/fetch?token=${token}&langs=${locale}&nested=false&includeLangKey=false&pretty=true&indent=2`;
222
+ const fetchUrl = `${baseUrl}/fetch?token=${token}&langs=${locale}&nested=${syncConfig.nested}&includeLangKey=${syncConfig.includeLangKey}&pretty=${syncConfig.pretty}&indent=${syncConfig.indent}`;
146
223
  const translationResponse = await fetch(fetchUrl);
147
224
 
148
225
  if (!translationResponse.ok) {
@@ -152,7 +229,17 @@ export async function syncCommand() {
152
229
 
153
230
  const translationData = await translationResponse.json();
154
231
  const outputPath = path.join(i18nDir, `${locale}.json`);
155
- fs.writeFileSync(outputPath, JSON.stringify(translationData, null, 2));
232
+
233
+ // Format based on config
234
+ let jsonString: string;
235
+ if (syncConfig.pretty) {
236
+ const indentValue = syncConfig.indent === 'tab' ? '\t' : Number(syncConfig.indent);
237
+ jsonString = JSON.stringify(translationData, null, indentValue);
238
+ } else {
239
+ jsonString = JSON.stringify(translationData);
240
+ }
241
+
242
+ fs.writeFileSync(outputPath, jsonString);
156
243
  console.log(chalk.green(`✅ Saved ${locale}.json`));
157
244
  }
158
245