@knocklabs/cli 0.1.0-rc.2 → 0.1.0-rc.4
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 +82 -6
- package/dist/commands/commit/index.js +4 -18
- package/dist/commands/commit/promote.js +4 -17
- package/dist/commands/translation/list.js +82 -0
- package/dist/commands/translation/pull.js +124 -0
- package/dist/commands/translation/push.js +130 -0
- package/dist/commands/translation/validate.js +122 -0
- package/dist/commands/workflow/activate.js +5 -18
- package/dist/commands/workflow/new.js +3 -3
- package/dist/commands/workflow/pull.js +70 -17
- package/dist/commands/workflow/push.js +3 -3
- package/dist/commands/workflow/validate.js +3 -3
- package/dist/lib/api-v1.js +38 -2
- package/dist/lib/base-command.js +2 -2
- package/dist/lib/helpers/error.js +16 -8
- package/dist/lib/helpers/flag.js +63 -3
- package/dist/lib/helpers/fs.js +52 -0
- package/dist/lib/helpers/json.js +6 -2
- package/dist/lib/helpers/object.js +43 -0
- package/dist/lib/helpers/page.js +3 -1
- package/dist/lib/helpers/request.js +17 -49
- package/dist/lib/helpers/ux.js +42 -0
- package/dist/lib/marshal/translation/helpers.js +185 -0
- package/dist/lib/marshal/translation/index.js +19 -0
- package/dist/lib/marshal/translation/reader.js +118 -0
- package/dist/lib/marshal/translation/types.js +4 -0
- package/dist/lib/marshal/translation/writer.js +86 -0
- package/dist/lib/marshal/workflow/generator.js +46 -5
- package/dist/lib/marshal/workflow/helpers.js +2 -0
- package/dist/lib/marshal/workflow/reader.js +136 -117
- package/dist/lib/marshal/workflow/writer.js +235 -98
- package/dist/lib/{helpers/dir-context.js → run-context/helpers.js} +1 -1
- package/dist/lib/run-context/index.js +22 -0
- package/dist/lib/{run-context.js → run-context/loader.js} +22 -7
- package/dist/lib/run-context/types.js +4 -0
- package/oclif.manifest.json +253 -1
- package/package.json +11 -10
- package/dist/lib/helpers/spinner.js +0 -20
package/README.md
CHANGED
|
@@ -16,7 +16,7 @@ $ npm install -g @knocklabs/cli
|
|
|
16
16
|
$ knock COMMAND
|
|
17
17
|
running command...
|
|
18
18
|
$ knock (--version)
|
|
19
|
-
@knocklabs/cli/0.1.0-rc.
|
|
19
|
+
@knocklabs/cli/0.1.0-rc.4 linux-x64 node-v16.4.2
|
|
20
20
|
$ knock --help [COMMAND]
|
|
21
21
|
USAGE
|
|
22
22
|
$ knock COMMAND
|
|
@@ -40,6 +40,10 @@ USAGE
|
|
|
40
40
|
* [`knock plugins:uninstall PLUGIN...`](#knock-pluginsuninstall-plugin-1)
|
|
41
41
|
* [`knock plugins:uninstall PLUGIN...`](#knock-pluginsuninstall-plugin-2)
|
|
42
42
|
* [`knock plugins update`](#knock-plugins-update)
|
|
43
|
+
* [`knock translation list`](#knock-translation-list)
|
|
44
|
+
* [`knock translation pull`](#knock-translation-pull)
|
|
45
|
+
* [`knock translation push [TRANSLATIONREF]`](#knock-translation-push-translationref)
|
|
46
|
+
* [`knock translation validate [TRANSLATIONREF]`](#knock-translation-validate-translationref)
|
|
43
47
|
* [`knock workflow activate WORKFLOWKEY`](#knock-workflow-activate-workflowkey)
|
|
44
48
|
* [`knock workflow get WORKFLOWKEY`](#knock-workflow-get-workflowkey)
|
|
45
49
|
* [`knock workflow list`](#knock-workflow-list)
|
|
@@ -62,7 +66,7 @@ FLAGS
|
|
|
62
66
|
--service-token=<value> (required) The service token to authenticate with
|
|
63
67
|
```
|
|
64
68
|
|
|
65
|
-
_See code: [dist/commands/commit/index.ts](https://github.com/knocklabs/knock-cli/blob/v0.1.0-rc.
|
|
69
|
+
_See code: [dist/commands/commit/index.ts](https://github.com/knocklabs/knock-cli/blob/v0.1.0-rc.4/dist/commands/commit/index.ts)_
|
|
66
70
|
|
|
67
71
|
## `knock commit promote`
|
|
68
72
|
|
|
@@ -94,7 +98,7 @@ DESCRIPTION
|
|
|
94
98
|
Display help for knock.
|
|
95
99
|
```
|
|
96
100
|
|
|
97
|
-
_See code: [@oclif/plugin-help](https://github.com/oclif/plugin-help/blob/v5.2.
|
|
101
|
+
_See code: [@oclif/plugin-help](https://github.com/oclif/plugin-help/blob/v5.2.9/src/commands/help.ts)_
|
|
98
102
|
|
|
99
103
|
## `knock ping`
|
|
100
104
|
|
|
@@ -114,7 +118,7 @@ EXAMPLES
|
|
|
114
118
|
$ knock ping
|
|
115
119
|
```
|
|
116
120
|
|
|
117
|
-
_See code: [dist/commands/ping.ts](https://github.com/knocklabs/knock-cli/blob/v0.1.0-rc.
|
|
121
|
+
_See code: [dist/commands/ping.ts](https://github.com/knocklabs/knock-cli/blob/v0.1.0-rc.4/dist/commands/ping.ts)_
|
|
118
122
|
|
|
119
123
|
## `knock plugins`
|
|
120
124
|
|
|
@@ -134,7 +138,7 @@ EXAMPLES
|
|
|
134
138
|
$ knock plugins
|
|
135
139
|
```
|
|
136
140
|
|
|
137
|
-
_See code: [@oclif/plugin-plugins](https://github.com/oclif/plugin-plugins/blob/v2.
|
|
141
|
+
_See code: [@oclif/plugin-plugins](https://github.com/oclif/plugin-plugins/blob/v2.4.7/src/commands/plugins/index.ts)_
|
|
138
142
|
|
|
139
143
|
## `knock plugins:install PLUGIN...`
|
|
140
144
|
|
|
@@ -349,6 +353,74 @@ DESCRIPTION
|
|
|
349
353
|
Update installed plugins.
|
|
350
354
|
```
|
|
351
355
|
|
|
356
|
+
## `knock translation list`
|
|
357
|
+
|
|
358
|
+
```
|
|
359
|
+
USAGE
|
|
360
|
+
$ knock translation list --service-token <value> [--environment <value>] [--hide-uncommitted-changes] [--after
|
|
361
|
+
<value>] [--before <value>] [--limit <value>] [--json]
|
|
362
|
+
|
|
363
|
+
FLAGS
|
|
364
|
+
--after=<value>
|
|
365
|
+
--before=<value>
|
|
366
|
+
--environment=<value> [default: development]
|
|
367
|
+
--hide-uncommitted-changes
|
|
368
|
+
--limit=<value>
|
|
369
|
+
--service-token=<value> (required) The service token to authenticate with
|
|
370
|
+
|
|
371
|
+
GLOBAL FLAGS
|
|
372
|
+
--json Format output as json.
|
|
373
|
+
```
|
|
374
|
+
|
|
375
|
+
## `knock translation pull`
|
|
376
|
+
|
|
377
|
+
```
|
|
378
|
+
USAGE
|
|
379
|
+
$ knock translation pull --service-token <value> [--environment <value>] [--translations-dir <value> --all]
|
|
380
|
+
[--hide-uncommitted-changes] [--force]
|
|
381
|
+
|
|
382
|
+
FLAGS
|
|
383
|
+
--all
|
|
384
|
+
--environment=<value> [default: development]
|
|
385
|
+
--force
|
|
386
|
+
--hide-uncommitted-changes
|
|
387
|
+
--service-token=<value> (required) The service token to authenticate with
|
|
388
|
+
--translations-dir=<value>
|
|
389
|
+
```
|
|
390
|
+
|
|
391
|
+
## `knock translation push [TRANSLATIONREF]`
|
|
392
|
+
|
|
393
|
+
```
|
|
394
|
+
USAGE
|
|
395
|
+
$ knock translation push [TRANSLATIONREF] --service-token <value> [--environment development] [--translations-dir
|
|
396
|
+
<value> --all] [-m <value> --commit]
|
|
397
|
+
|
|
398
|
+
FLAGS
|
|
399
|
+
-m, --commit-message=<value> Use the given value as the commit message
|
|
400
|
+
--all
|
|
401
|
+
--commit Push and commit the translation(s) at the same time
|
|
402
|
+
--environment=<option> [default: development] Pushing a translation is only allowed in the development
|
|
403
|
+
environment
|
|
404
|
+
<options: development>
|
|
405
|
+
--service-token=<value> (required) The service token to authenticate with
|
|
406
|
+
--translations-dir=<value>
|
|
407
|
+
```
|
|
408
|
+
|
|
409
|
+
## `knock translation validate [TRANSLATIONREF]`
|
|
410
|
+
|
|
411
|
+
```
|
|
412
|
+
USAGE
|
|
413
|
+
$ knock translation validate [TRANSLATIONREF] --service-token <value> [--environment development] [--translations-dir
|
|
414
|
+
<value> --all]
|
|
415
|
+
|
|
416
|
+
FLAGS
|
|
417
|
+
--all
|
|
418
|
+
--environment=<option> [default: development] Validating a workflow is only done in the development environment
|
|
419
|
+
<options: development>
|
|
420
|
+
--service-token=<value> (required) The service token to authenticate with
|
|
421
|
+
--translations-dir=<value>
|
|
422
|
+
```
|
|
423
|
+
|
|
352
424
|
## `knock workflow activate WORKFLOWKEY`
|
|
353
425
|
|
|
354
426
|
```
|
|
@@ -402,12 +474,16 @@ GLOBAL FLAGS
|
|
|
402
474
|
|
|
403
475
|
```
|
|
404
476
|
USAGE
|
|
405
|
-
$ knock workflow pull [WORKFLOWKEY] --service-token <value> [--environment <value>] [--
|
|
477
|
+
$ knock workflow pull [WORKFLOWKEY] --service-token <value> [--environment <value>] [--workflows-dir <value>
|
|
478
|
+
--all] [--hide-uncommitted-changes] [--force]
|
|
406
479
|
|
|
407
480
|
FLAGS
|
|
481
|
+
--all
|
|
408
482
|
--environment=<value> [default: development]
|
|
483
|
+
--force
|
|
409
484
|
--hide-uncommitted-changes
|
|
410
485
|
--service-token=<value> (required) The service token to authenticate with
|
|
486
|
+
--workflows-dir=<value>
|
|
411
487
|
```
|
|
412
488
|
|
|
413
489
|
## `knock workflow push [WORKFLOWKEY]`
|
|
@@ -7,37 +7,23 @@ Object.defineProperty(exports, "default", {
|
|
|
7
7
|
get: ()=>Commit
|
|
8
8
|
});
|
|
9
9
|
const _core = require("@oclif/core");
|
|
10
|
-
const _enquirer = /*#__PURE__*/ _interopRequireDefault(require("enquirer"));
|
|
11
10
|
const _baseCommand = /*#__PURE__*/ _interopRequireDefault(require("../../lib/base-command"));
|
|
12
11
|
const _const = require("../../lib/helpers/const");
|
|
13
12
|
const _request = require("../../lib/helpers/request");
|
|
13
|
+
const _ux = require("../../lib/helpers/ux");
|
|
14
14
|
function _interopRequireDefault(obj) {
|
|
15
15
|
return obj && obj.__esModule ? obj : {
|
|
16
16
|
default: obj
|
|
17
17
|
};
|
|
18
18
|
}
|
|
19
|
-
// TODO(KNO-2647): Abstract this out as a helper.
|
|
20
|
-
const promptToConfirm = async ()=>{
|
|
21
|
-
try {
|
|
22
|
-
const { input } = await _enquirer.default.prompt({
|
|
23
|
-
type: "confirm",
|
|
24
|
-
name: "input",
|
|
25
|
-
message: "Commit all changes in the development environment?"
|
|
26
|
-
});
|
|
27
|
-
return input;
|
|
28
|
-
} catch (error) {
|
|
29
|
-
console.log(error);
|
|
30
|
-
}
|
|
31
|
-
};
|
|
32
19
|
class Commit extends _baseCommand.default {
|
|
33
20
|
async run() {
|
|
34
21
|
const { flags } = this.props;
|
|
35
22
|
// Confirm first as we are about to commit changes to go live in the
|
|
36
23
|
// development environment, unless forced.
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
}
|
|
24
|
+
const prompt = "Commit all changes in the development environment?";
|
|
25
|
+
const input = flags.force || await (0, _ux.promptToConfirm)(prompt);
|
|
26
|
+
if (!input) return;
|
|
41
27
|
await (0, _request.withSpinner)(()=>this.apiV1.commitAllChanges(this.props));
|
|
42
28
|
this.log(`‣ Successfully committed all changes in \`${flags.environment}\` environment`);
|
|
43
29
|
}
|
|
@@ -7,35 +7,22 @@ Object.defineProperty(exports, "default", {
|
|
|
7
7
|
get: ()=>CommitPromote
|
|
8
8
|
});
|
|
9
9
|
const _core = require("@oclif/core");
|
|
10
|
-
const _enquirer = /*#__PURE__*/ _interopRequireDefault(require("enquirer"));
|
|
11
10
|
const _baseCommand = /*#__PURE__*/ _interopRequireDefault(require("../../lib/base-command"));
|
|
12
11
|
const _request = require("../../lib/helpers/request");
|
|
12
|
+
const _ux = require("../../lib/helpers/ux");
|
|
13
13
|
function _interopRequireDefault(obj) {
|
|
14
14
|
return obj && obj.__esModule ? obj : {
|
|
15
15
|
default: obj
|
|
16
16
|
};
|
|
17
17
|
}
|
|
18
|
-
const promptToConfirm = async ({ flags })=>{
|
|
19
|
-
try {
|
|
20
|
-
const { input } = await _enquirer.default.prompt({
|
|
21
|
-
type: "confirm",
|
|
22
|
-
name: "input",
|
|
23
|
-
message: `Promote all changes to \`${flags.to}\` environment?`
|
|
24
|
-
});
|
|
25
|
-
return input;
|
|
26
|
-
} catch (error) {
|
|
27
|
-
console.log(error);
|
|
28
|
-
}
|
|
29
|
-
};
|
|
30
18
|
class CommitPromote extends _baseCommand.default {
|
|
31
19
|
async run() {
|
|
32
20
|
const { flags } = this.props;
|
|
33
21
|
// Confirm first as we are about to promote changes to go live in the target
|
|
34
22
|
// environment, unless forced.
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
}
|
|
23
|
+
const prompt = `Promote all changes to \`${flags.to}\` environment?`;
|
|
24
|
+
const input = flags.force || await (0, _ux.promptToConfirm)(prompt);
|
|
25
|
+
if (!input) return;
|
|
39
26
|
await (0, _request.withSpinner)(()=>this.apiV1.promoteAllChanges(this.props));
|
|
40
27
|
this.log(`‣ Successfully promoted all changes to \`${flags.to}\` environment`);
|
|
41
28
|
}
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", {
|
|
3
|
+
value: true
|
|
4
|
+
});
|
|
5
|
+
Object.defineProperty(exports, "default", {
|
|
6
|
+
enumerable: true,
|
|
7
|
+
get: ()=>TranslationList
|
|
8
|
+
});
|
|
9
|
+
const _core = require("@oclif/core");
|
|
10
|
+
const _localeCodes = /*#__PURE__*/ _interopRequireDefault(require("locale-codes"));
|
|
11
|
+
const _baseCommand = /*#__PURE__*/ _interopRequireDefault(require("../../lib/base-command"));
|
|
12
|
+
const _date = require("../../lib/helpers/date");
|
|
13
|
+
const _object = require("../../lib/helpers/object");
|
|
14
|
+
const _page = require("../../lib/helpers/page");
|
|
15
|
+
const _request = require("../../lib/helpers/request");
|
|
16
|
+
function _interopRequireDefault(obj) {
|
|
17
|
+
return obj && obj.__esModule ? obj : {
|
|
18
|
+
default: obj
|
|
19
|
+
};
|
|
20
|
+
}
|
|
21
|
+
class TranslationList extends _baseCommand.default {
|
|
22
|
+
async run() {
|
|
23
|
+
const resp = await this.request();
|
|
24
|
+
const { flags } = this.props;
|
|
25
|
+
if (flags.json) return resp.data;
|
|
26
|
+
this.render(resp.data);
|
|
27
|
+
}
|
|
28
|
+
async request(pageParams = {}) {
|
|
29
|
+
const props = (0, _object.merge)(this.props, {
|
|
30
|
+
flags: {
|
|
31
|
+
...pageParams
|
|
32
|
+
}
|
|
33
|
+
});
|
|
34
|
+
return (0, _request.withSpinner)(()=>this.apiV1.listTranslations(props));
|
|
35
|
+
}
|
|
36
|
+
async render(data) {
|
|
37
|
+
const { entries } = data;
|
|
38
|
+
const { environment: env , "hide-uncommitted-changes": committedOnly } = this.props.flags;
|
|
39
|
+
const qualifier = env === "development" && !committedOnly ? "(including uncommitted)" : "";
|
|
40
|
+
this.log(`‣ Showing ${entries.length} translations in \`${env}\` environment ${qualifier}\n`);
|
|
41
|
+
/*
|
|
42
|
+
* Translations list table
|
|
43
|
+
*/ _core.CliUx.ux.table(entries, {
|
|
44
|
+
language_name: {
|
|
45
|
+
header: "Language",
|
|
46
|
+
get: (entry)=>{
|
|
47
|
+
const language = _localeCodes.default.getByTag(entry.locale_code);
|
|
48
|
+
return language.location ? `${language.name}, ${language.location}` : language.name;
|
|
49
|
+
}
|
|
50
|
+
},
|
|
51
|
+
locale_code: {
|
|
52
|
+
header: "Locale code"
|
|
53
|
+
},
|
|
54
|
+
namespace: {
|
|
55
|
+
header: "Namespace"
|
|
56
|
+
},
|
|
57
|
+
updated_at: {
|
|
58
|
+
header: "Updated at",
|
|
59
|
+
get: (entry)=>(0, _date.formatDate)(entry.updated_at)
|
|
60
|
+
}
|
|
61
|
+
});
|
|
62
|
+
return this.prompt(data);
|
|
63
|
+
}
|
|
64
|
+
async prompt(data) {
|
|
65
|
+
const { page_info } = data;
|
|
66
|
+
const pageAction = await (0, _page.maybePromptPageAction)(page_info);
|
|
67
|
+
const pageParams = pageAction && (0, _page.paramsForPageAction)(pageAction, page_info);
|
|
68
|
+
if (pageParams) {
|
|
69
|
+
this.log("\n");
|
|
70
|
+
const resp = await this.request(pageParams);
|
|
71
|
+
return this.render(resp.data);
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
TranslationList.flags = {
|
|
76
|
+
environment: _core.Flags.string({
|
|
77
|
+
default: "development"
|
|
78
|
+
}),
|
|
79
|
+
"hide-uncommitted-changes": _core.Flags.boolean(),
|
|
80
|
+
..._page.pageFlags
|
|
81
|
+
};
|
|
82
|
+
TranslationList.enableJsonFlag = true;
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", {
|
|
3
|
+
value: true
|
|
4
|
+
});
|
|
5
|
+
Object.defineProperty(exports, "default", {
|
|
6
|
+
enumerable: true,
|
|
7
|
+
get: ()=>TranslationPull
|
|
8
|
+
});
|
|
9
|
+
const _core = require("@oclif/core");
|
|
10
|
+
const _baseCommand = /*#__PURE__*/ _interopRequireDefault(require("../../lib/base-command"));
|
|
11
|
+
const _error = require("../../lib/helpers/error");
|
|
12
|
+
const _flag = /*#__PURE__*/ _interopRequireWildcard(require("../../lib/helpers/flag"));
|
|
13
|
+
const _object = require("../../lib/helpers/object");
|
|
14
|
+
const _page = require("../../lib/helpers/page");
|
|
15
|
+
const _request = require("../../lib/helpers/request");
|
|
16
|
+
const _ux = require("../../lib/helpers/ux");
|
|
17
|
+
const _translation = /*#__PURE__*/ _interopRequireWildcard(require("../../lib/marshal/translation"));
|
|
18
|
+
function _interopRequireDefault(obj) {
|
|
19
|
+
return obj && obj.__esModule ? obj : {
|
|
20
|
+
default: obj
|
|
21
|
+
};
|
|
22
|
+
}
|
|
23
|
+
function _getRequireWildcardCache(nodeInterop) {
|
|
24
|
+
if (typeof WeakMap !== "function") return null;
|
|
25
|
+
var cacheBabelInterop = new WeakMap();
|
|
26
|
+
var cacheNodeInterop = new WeakMap();
|
|
27
|
+
return (_getRequireWildcardCache = function(nodeInterop) {
|
|
28
|
+
return nodeInterop ? cacheNodeInterop : cacheBabelInterop;
|
|
29
|
+
})(nodeInterop);
|
|
30
|
+
}
|
|
31
|
+
function _interopRequireWildcard(obj, nodeInterop) {
|
|
32
|
+
if (!nodeInterop && obj && obj.__esModule) {
|
|
33
|
+
return obj;
|
|
34
|
+
}
|
|
35
|
+
if (obj === null || typeof obj !== "object" && typeof obj !== "function") {
|
|
36
|
+
return {
|
|
37
|
+
default: obj
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
var cache = _getRequireWildcardCache(nodeInterop);
|
|
41
|
+
if (cache && cache.has(obj)) {
|
|
42
|
+
return cache.get(obj);
|
|
43
|
+
}
|
|
44
|
+
var newObj = {};
|
|
45
|
+
var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor;
|
|
46
|
+
for(var key in obj){
|
|
47
|
+
if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) {
|
|
48
|
+
var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null;
|
|
49
|
+
if (desc && (desc.get || desc.set)) {
|
|
50
|
+
Object.defineProperty(newObj, key, desc);
|
|
51
|
+
} else {
|
|
52
|
+
newObj[key] = obj[key];
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
newObj.default = obj;
|
|
57
|
+
if (cache) {
|
|
58
|
+
cache.set(obj, newObj);
|
|
59
|
+
}
|
|
60
|
+
return newObj;
|
|
61
|
+
}
|
|
62
|
+
class TranslationPull extends _baseCommand.default {
|
|
63
|
+
async run() {
|
|
64
|
+
const { flags } = this.props;
|
|
65
|
+
// TODO MKD: Enable pulling a single translation or group of translations for locale
|
|
66
|
+
return flags.all ? this.pullAllTranslations() : this.error("Must use --all to pull all translations");
|
|
67
|
+
}
|
|
68
|
+
/*
|
|
69
|
+
* Pull all translations
|
|
70
|
+
*/ async pullAllTranslations() {
|
|
71
|
+
const { flags } = this.props;
|
|
72
|
+
// TODO: In the future we should default to the knock project config first
|
|
73
|
+
// if present, before defaulting to the cwd.
|
|
74
|
+
const defaultToCwd = {
|
|
75
|
+
abspath: this.runContext.cwd,
|
|
76
|
+
exists: true
|
|
77
|
+
};
|
|
78
|
+
const targetDirCtx = flags["translations-dir"] || defaultToCwd;
|
|
79
|
+
const prompt = targetDirCtx.exists ? `Pull latest translations into ${targetDirCtx.abspath}?\n This will overwrite the contents of this directory.` : `Create a new translations directory at ${targetDirCtx.abspath}?`;
|
|
80
|
+
const input = flags.force || await (0, _ux.promptToConfirm)(prompt);
|
|
81
|
+
if (!input) return;
|
|
82
|
+
// Fetch all translations then write them to the local file system.
|
|
83
|
+
_ux.spinner.start(`‣ Loading`);
|
|
84
|
+
const translations = await this.listAllTranslations();
|
|
85
|
+
await _translation.writeTranslationsIndexDir(targetDirCtx, translations);
|
|
86
|
+
_ux.spinner.stop();
|
|
87
|
+
const action = targetDirCtx.exists ? "updated" : "created";
|
|
88
|
+
this.log(`‣ Successfully ${action} the translations directory at ${targetDirCtx.abspath}`);
|
|
89
|
+
}
|
|
90
|
+
async listAllTranslations(pageParams = {}, translationsFetchedSoFar = []) {
|
|
91
|
+
const props = (0, _object.merge)(this.props, {
|
|
92
|
+
flags: {
|
|
93
|
+
...pageParams,
|
|
94
|
+
limit: _page.MAX_PAGINATION_LIMIT
|
|
95
|
+
}
|
|
96
|
+
});
|
|
97
|
+
const resp = await this.apiV1.listTranslations(props);
|
|
98
|
+
if (!(0, _request.isSuccessResp)(resp)) {
|
|
99
|
+
const message = (0, _request.formatErrorRespMessage)(resp);
|
|
100
|
+
this.error(new _error.ApiError(message));
|
|
101
|
+
}
|
|
102
|
+
const { entries , page_info: pageInfo } = resp.data;
|
|
103
|
+
const translations = [
|
|
104
|
+
...translationsFetchedSoFar,
|
|
105
|
+
...entries
|
|
106
|
+
];
|
|
107
|
+
return pageInfo.after ? this.listAllTranslations({
|
|
108
|
+
after: pageInfo.after
|
|
109
|
+
}, translations) : translations;
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
TranslationPull.flags = {
|
|
113
|
+
environment: _core.Flags.string({
|
|
114
|
+
default: "development"
|
|
115
|
+
}),
|
|
116
|
+
all: _core.Flags.boolean(),
|
|
117
|
+
"translations-dir": _flag.dirPath({
|
|
118
|
+
dependsOn: [
|
|
119
|
+
"all"
|
|
120
|
+
]
|
|
121
|
+
}),
|
|
122
|
+
"hide-uncommitted-changes": _core.Flags.boolean(),
|
|
123
|
+
force: _core.Flags.boolean()
|
|
124
|
+
};
|
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", {
|
|
3
|
+
value: true
|
|
4
|
+
});
|
|
5
|
+
Object.defineProperty(exports, "default", {
|
|
6
|
+
enumerable: true,
|
|
7
|
+
get: ()=>TranslationPush
|
|
8
|
+
});
|
|
9
|
+
const _core = require("@oclif/core");
|
|
10
|
+
const _baseCommand = /*#__PURE__*/ _interopRequireDefault(require("../../lib/base-command"));
|
|
11
|
+
const _const = require("../../lib/helpers/const");
|
|
12
|
+
const _error = require("../../lib/helpers/error");
|
|
13
|
+
const _flag = /*#__PURE__*/ _interopRequireWildcard(require("../../lib/helpers/flag"));
|
|
14
|
+
const _request = require("../../lib/helpers/request");
|
|
15
|
+
const _string = require("../../lib/helpers/string");
|
|
16
|
+
const _ux = require("../../lib/helpers/ux");
|
|
17
|
+
const _translation = /*#__PURE__*/ _interopRequireWildcard(require("../../lib/marshal/translation"));
|
|
18
|
+
const _validate = /*#__PURE__*/ _interopRequireDefault(require("./validate"));
|
|
19
|
+
function _interopRequireDefault(obj) {
|
|
20
|
+
return obj && obj.__esModule ? obj : {
|
|
21
|
+
default: obj
|
|
22
|
+
};
|
|
23
|
+
}
|
|
24
|
+
function _getRequireWildcardCache(nodeInterop) {
|
|
25
|
+
if (typeof WeakMap !== "function") return null;
|
|
26
|
+
var cacheBabelInterop = new WeakMap();
|
|
27
|
+
var cacheNodeInterop = new WeakMap();
|
|
28
|
+
return (_getRequireWildcardCache = function(nodeInterop) {
|
|
29
|
+
return nodeInterop ? cacheNodeInterop : cacheBabelInterop;
|
|
30
|
+
})(nodeInterop);
|
|
31
|
+
}
|
|
32
|
+
function _interopRequireWildcard(obj, nodeInterop) {
|
|
33
|
+
if (!nodeInterop && obj && obj.__esModule) {
|
|
34
|
+
return obj;
|
|
35
|
+
}
|
|
36
|
+
if (obj === null || typeof obj !== "object" && typeof obj !== "function") {
|
|
37
|
+
return {
|
|
38
|
+
default: obj
|
|
39
|
+
};
|
|
40
|
+
}
|
|
41
|
+
var cache = _getRequireWildcardCache(nodeInterop);
|
|
42
|
+
if (cache && cache.has(obj)) {
|
|
43
|
+
return cache.get(obj);
|
|
44
|
+
}
|
|
45
|
+
var newObj = {};
|
|
46
|
+
var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor;
|
|
47
|
+
for(var key in obj){
|
|
48
|
+
if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) {
|
|
49
|
+
var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null;
|
|
50
|
+
if (desc && (desc.get || desc.set)) {
|
|
51
|
+
Object.defineProperty(newObj, key, desc);
|
|
52
|
+
} else {
|
|
53
|
+
newObj[key] = obj[key];
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
newObj.default = obj;
|
|
58
|
+
if (cache) {
|
|
59
|
+
cache.set(obj, newObj);
|
|
60
|
+
}
|
|
61
|
+
return newObj;
|
|
62
|
+
}
|
|
63
|
+
class TranslationPush extends _baseCommand.default {
|
|
64
|
+
async run() {
|
|
65
|
+
// First read all translation files found for the given command.
|
|
66
|
+
const target = await _translation.ensureValidCommandTarget(this.props, this.runContext);
|
|
67
|
+
const [translations, readErrors] = await _translation.readTranslationFilesForCommandTarget(target);
|
|
68
|
+
if (readErrors.length > 0) {
|
|
69
|
+
this.error((0, _error.formatErrors)(readErrors, {
|
|
70
|
+
prependBy: "\n\n"
|
|
71
|
+
}));
|
|
72
|
+
}
|
|
73
|
+
if (translations.length === 0) {
|
|
74
|
+
this.error(`No translation files found in ${target.context.abspath}`);
|
|
75
|
+
}
|
|
76
|
+
// Then validate them all ahead of pushing them.
|
|
77
|
+
_ux.spinner.start(`‣ Validating`);
|
|
78
|
+
const apiErrors = await _validate.default.validateAll(this.apiV1, this.props, translations);
|
|
79
|
+
if (apiErrors.length > 0) {
|
|
80
|
+
this.error((0, _error.formatErrors)(apiErrors));
|
|
81
|
+
}
|
|
82
|
+
// Finally push up each translation file, abort on the first error.
|
|
83
|
+
for (const translation of translations){
|
|
84
|
+
// eslint-disable-next-line no-await-in-loop
|
|
85
|
+
const resp = await this.apiV1.upsertTranslation(this.props, {
|
|
86
|
+
locale_code: translation.localeCode,
|
|
87
|
+
namespace: translation.namespace,
|
|
88
|
+
content: translation.content
|
|
89
|
+
});
|
|
90
|
+
if ((0, _request.isSuccessResp)(resp)) continue;
|
|
91
|
+
const message = (0, _request.formatErrorRespMessage)(resp);
|
|
92
|
+
const error = new _error.SourceError(message, translation.abspath, "ApiError");
|
|
93
|
+
this.error((0, _error.formatError)(error));
|
|
94
|
+
}
|
|
95
|
+
_ux.spinner.stop();
|
|
96
|
+
const handledRefs = translations.map((t)=>t.ref);
|
|
97
|
+
this.log(`‣ Successfully pushed ${translations.length} translation(s):\n` + (0, _string.indentString)(handledRefs.join("\n"), 4));
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
TranslationPush.flags = {
|
|
101
|
+
environment: _core.Flags.string({
|
|
102
|
+
summary: "Pushing a translation is only allowed in the development environment",
|
|
103
|
+
default: _const.KnockEnv.Development,
|
|
104
|
+
options: [
|
|
105
|
+
_const.KnockEnv.Development
|
|
106
|
+
]
|
|
107
|
+
}),
|
|
108
|
+
all: _core.Flags.boolean(),
|
|
109
|
+
"translations-dir": _flag.dirPath({
|
|
110
|
+
dependsOn: [
|
|
111
|
+
"all"
|
|
112
|
+
]
|
|
113
|
+
}),
|
|
114
|
+
commit: _core.Flags.boolean({
|
|
115
|
+
summary: "Push and commit the translation(s) at the same time"
|
|
116
|
+
}),
|
|
117
|
+
"commit-message": _core.Flags.string({
|
|
118
|
+
summary: "Use the given value as the commit message",
|
|
119
|
+
char: "m",
|
|
120
|
+
dependsOn: [
|
|
121
|
+
"commit"
|
|
122
|
+
]
|
|
123
|
+
})
|
|
124
|
+
};
|
|
125
|
+
TranslationPush.args = [
|
|
126
|
+
{
|
|
127
|
+
name: "translationRef",
|
|
128
|
+
required: false
|
|
129
|
+
}
|
|
130
|
+
];
|
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", {
|
|
3
|
+
value: true
|
|
4
|
+
});
|
|
5
|
+
Object.defineProperty(exports, "default", {
|
|
6
|
+
enumerable: true,
|
|
7
|
+
get: ()=>TranslationValidate
|
|
8
|
+
});
|
|
9
|
+
const _core = require("@oclif/core");
|
|
10
|
+
const _baseCommand = /*#__PURE__*/ _interopRequireDefault(require("../../lib/base-command"));
|
|
11
|
+
const _const = require("../../lib/helpers/const");
|
|
12
|
+
const _error = require("../../lib/helpers/error");
|
|
13
|
+
const _flag = /*#__PURE__*/ _interopRequireWildcard(require("../../lib/helpers/flag"));
|
|
14
|
+
const _request = require("../../lib/helpers/request");
|
|
15
|
+
const _string = require("../../lib/helpers/string");
|
|
16
|
+
const _ux = require("../../lib/helpers/ux");
|
|
17
|
+
const _translation = /*#__PURE__*/ _interopRequireWildcard(require("../../lib/marshal/translation"));
|
|
18
|
+
function _interopRequireDefault(obj) {
|
|
19
|
+
return obj && obj.__esModule ? obj : {
|
|
20
|
+
default: obj
|
|
21
|
+
};
|
|
22
|
+
}
|
|
23
|
+
function _getRequireWildcardCache(nodeInterop) {
|
|
24
|
+
if (typeof WeakMap !== "function") return null;
|
|
25
|
+
var cacheBabelInterop = new WeakMap();
|
|
26
|
+
var cacheNodeInterop = new WeakMap();
|
|
27
|
+
return (_getRequireWildcardCache = function(nodeInterop) {
|
|
28
|
+
return nodeInterop ? cacheNodeInterop : cacheBabelInterop;
|
|
29
|
+
})(nodeInterop);
|
|
30
|
+
}
|
|
31
|
+
function _interopRequireWildcard(obj, nodeInterop) {
|
|
32
|
+
if (!nodeInterop && obj && obj.__esModule) {
|
|
33
|
+
return obj;
|
|
34
|
+
}
|
|
35
|
+
if (obj === null || typeof obj !== "object" && typeof obj !== "function") {
|
|
36
|
+
return {
|
|
37
|
+
default: obj
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
var cache = _getRequireWildcardCache(nodeInterop);
|
|
41
|
+
if (cache && cache.has(obj)) {
|
|
42
|
+
return cache.get(obj);
|
|
43
|
+
}
|
|
44
|
+
var newObj = {};
|
|
45
|
+
var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor;
|
|
46
|
+
for(var key in obj){
|
|
47
|
+
if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) {
|
|
48
|
+
var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null;
|
|
49
|
+
if (desc && (desc.get || desc.set)) {
|
|
50
|
+
Object.defineProperty(newObj, key, desc);
|
|
51
|
+
} else {
|
|
52
|
+
newObj[key] = obj[key];
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
newObj.default = obj;
|
|
57
|
+
if (cache) {
|
|
58
|
+
cache.set(obj, newObj);
|
|
59
|
+
}
|
|
60
|
+
return newObj;
|
|
61
|
+
}
|
|
62
|
+
class TranslationValidate extends _baseCommand.default {
|
|
63
|
+
async run() {
|
|
64
|
+
const target = await _translation.ensureValidCommandTarget(this.props, this.runContext);
|
|
65
|
+
const [translations, readErrors] = await _translation.readTranslationFilesForCommandTarget(target);
|
|
66
|
+
if (readErrors.length > 0) {
|
|
67
|
+
this.error((0, _error.formatErrors)(readErrors, {
|
|
68
|
+
prependBy: "\n\n"
|
|
69
|
+
}));
|
|
70
|
+
}
|
|
71
|
+
if (translations.length === 0) {
|
|
72
|
+
this.error(`No translation files found in ${target.context.abspath}`);
|
|
73
|
+
}
|
|
74
|
+
_ux.spinner.start(`‣ Validating`);
|
|
75
|
+
const apiErrors = await TranslationValidate.validateAll(this.apiV1, this.props, translations);
|
|
76
|
+
if (apiErrors.length > 0) {
|
|
77
|
+
this.error((0, _error.formatErrors)(apiErrors, {
|
|
78
|
+
prependBy: "\n\n"
|
|
79
|
+
}));
|
|
80
|
+
}
|
|
81
|
+
_ux.spinner.stop();
|
|
82
|
+
const handledRefs = translations.map((t)=>t.ref);
|
|
83
|
+
this.log(`‣ Successfully validated ${translations.length} translation(s):\n` + (0, _string.indentString)(handledRefs.join("\n"), 4));
|
|
84
|
+
}
|
|
85
|
+
static async validateAll(api, props, translations) {
|
|
86
|
+
// TODO: Throw if a non validation error (e.g. authentication error) instead
|
|
87
|
+
// of printing out same error messages repeatedly.
|
|
88
|
+
const errorPromises = translations.map(async (translation)=>{
|
|
89
|
+
const resp = await api.validateTranslation(props, {
|
|
90
|
+
locale_code: translation.localeCode,
|
|
91
|
+
namespace: translation.namespace,
|
|
92
|
+
content: translation.content
|
|
93
|
+
});
|
|
94
|
+
if ((0, _request.isSuccessResp)(resp)) return;
|
|
95
|
+
const message = (0, _request.formatErrorRespMessage)(resp);
|
|
96
|
+
return new _error.SourceError(message, translation.abspath, "ApiError");
|
|
97
|
+
});
|
|
98
|
+
const errors = (await Promise.all(errorPromises)).filter((e)=>Boolean(e));
|
|
99
|
+
return errors;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
TranslationValidate.flags = {
|
|
103
|
+
environment: _core.Flags.string({
|
|
104
|
+
summary: "Validating a workflow is only done in the development environment",
|
|
105
|
+
default: _const.KnockEnv.Development,
|
|
106
|
+
options: [
|
|
107
|
+
_const.KnockEnv.Development
|
|
108
|
+
]
|
|
109
|
+
}),
|
|
110
|
+
all: _core.Flags.boolean(),
|
|
111
|
+
"translations-dir": _flag.dirPath({
|
|
112
|
+
dependsOn: [
|
|
113
|
+
"all"
|
|
114
|
+
]
|
|
115
|
+
})
|
|
116
|
+
};
|
|
117
|
+
TranslationValidate.args = [
|
|
118
|
+
{
|
|
119
|
+
name: "translationRef",
|
|
120
|
+
required: false
|
|
121
|
+
}
|
|
122
|
+
];
|