@wpmoo/toolkit 0.9.17 → 0.9.19
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/cli.js +3 -3
- package/dist/cockpit/menu.js +21 -19
- package/dist/prompts/index.js +44 -5
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -280,8 +280,8 @@ async function showStartup(argv, skipUpdateCheck, details) {
|
|
|
280
280
|
}
|
|
281
281
|
console.log();
|
|
282
282
|
}
|
|
283
|
-
async function selectCockpitCommandFromMenu(serviceStatus) {
|
|
284
|
-
const selection = await selectCockpitTopLevelMenu({ serviceStatus });
|
|
283
|
+
async function selectCockpitCommandFromMenu(serviceStatus, moduleCount) {
|
|
284
|
+
const selection = await selectCockpitTopLevelMenu({ serviceStatus, moduleCount });
|
|
285
285
|
if (selection.kind === 'exit') {
|
|
286
286
|
return 'exit';
|
|
287
287
|
}
|
|
@@ -1453,7 +1453,7 @@ export async function runCli(cliArgv = process.argv.slice(2), cwd = process.cwd(
|
|
|
1453
1453
|
};
|
|
1454
1454
|
while (true) {
|
|
1455
1455
|
try {
|
|
1456
|
-
const command = await selectCockpitCommandFromMenu(serviceStatus);
|
|
1456
|
+
const command = await selectCockpitCommandFromMenu(serviceStatus, status.kind === 'environment' ? status.moduleCandidateCount : undefined);
|
|
1457
1457
|
if (command === 'exit') {
|
|
1458
1458
|
return;
|
|
1459
1459
|
}
|
package/dist/cockpit/menu.js
CHANGED
|
@@ -20,6 +20,7 @@ const topLevelCategoryOrder = [
|
|
|
20
20
|
];
|
|
21
21
|
const topLevelCommands = topLevelCategoryOrder.flatMap((category) => cockpitCommands.filter((command) => command.category === category && command.id !== 'exit'));
|
|
22
22
|
const topLevelCommandLabelWidth = Math.max(...topLevelCommands.map((command) => command.label.length));
|
|
23
|
+
const moduleDependentCommandIds = new Set(['list-modules', 'install', 'update', 'test', 'lint', 'pot', 'remove-module']);
|
|
23
24
|
function rgb(red, green, blue, value) {
|
|
24
25
|
return `\u001B[38;2;${red};${green};${blue}m${value}\u001B[39m`;
|
|
25
26
|
}
|
|
@@ -32,7 +33,7 @@ function categoryHeading(category) {
|
|
|
32
33
|
function commandName(command) {
|
|
33
34
|
return `${rgb(226, 184, 96, ` ${command.label.padEnd(topLevelCommandLabelWidth)}`)}${dim(` ${command.description}`)}`;
|
|
34
35
|
}
|
|
35
|
-
function
|
|
36
|
+
function serviceDisabledReason(command, serviceStatus) {
|
|
36
37
|
if (command.category !== 'services' || !serviceStatus)
|
|
37
38
|
return undefined;
|
|
38
39
|
if (serviceStatus.kind === 'docker-not-running')
|
|
@@ -44,31 +45,32 @@ function disabledReason(command, serviceStatus) {
|
|
|
44
45
|
}
|
|
45
46
|
return undefined;
|
|
46
47
|
}
|
|
47
|
-
function
|
|
48
|
-
|
|
49
|
-
return 'Docker not running.';
|
|
50
|
-
if (serviceStatus?.kind === 'running')
|
|
51
|
-
return 'Already running.';
|
|
52
|
-
if (serviceStatus?.kind === 'stopped')
|
|
53
|
-
return 'Services stopped.';
|
|
54
|
-
return undefined;
|
|
48
|
+
function moduleDisabledReason(command, moduleCount) {
|
|
49
|
+
return moduleCount === 0 && moduleDependentCommandIds.has(command.id) ? 'No modules found.' : undefined;
|
|
55
50
|
}
|
|
56
|
-
function
|
|
57
|
-
|
|
58
|
-
|
|
51
|
+
function disabledReason(command, serviceStatus, moduleCount) {
|
|
52
|
+
return serviceDisabledReason(command, serviceStatus) ?? moduleDisabledReason(command, moduleCount);
|
|
53
|
+
}
|
|
54
|
+
function disabledError() {
|
|
55
|
+
return 'This option is disabled and cannot be selected.';
|
|
56
|
+
}
|
|
57
|
+
function commandDisabledValue(reason) {
|
|
58
|
+
if (!reason) {
|
|
59
|
+
return undefined;
|
|
60
|
+
}
|
|
61
|
+
return reason;
|
|
59
62
|
}
|
|
60
|
-
function categoryChoices(category, index, serviceStatus) {
|
|
63
|
+
function categoryChoices(category, index, serviceStatus, moduleCount) {
|
|
61
64
|
const choices = [
|
|
62
65
|
promptSeparator(categoryHeading(category)),
|
|
63
66
|
...topLevelCommands
|
|
64
67
|
.filter((command) => command.category === category)
|
|
65
68
|
.map((command) => {
|
|
66
|
-
const reason = disabledReason(command, serviceStatus);
|
|
67
69
|
return {
|
|
68
70
|
value: command,
|
|
69
71
|
name: commandName(command),
|
|
70
72
|
short: command.label,
|
|
71
|
-
disabled:
|
|
73
|
+
disabled: commandDisabledValue(disabledReason(command, serviceStatus, moduleCount)),
|
|
72
74
|
};
|
|
73
75
|
}),
|
|
74
76
|
];
|
|
@@ -101,8 +103,8 @@ function menuDeps(deps = {}) {
|
|
|
101
103
|
function isCockpitCommand(value) {
|
|
102
104
|
return typeof value === 'object' && value !== null && 'id' in value && 'slashAlias' in value;
|
|
103
105
|
}
|
|
104
|
-
function topLevelChoices(serviceStatus) {
|
|
105
|
-
return topLevelCategoryOrder.flatMap((category, index) => categoryChoices(category, index, serviceStatus));
|
|
106
|
+
function topLevelChoices(serviceStatus, moduleCount) {
|
|
107
|
+
return topLevelCategoryOrder.flatMap((category, index) => categoryChoices(category, index, serviceStatus, moduleCount));
|
|
106
108
|
}
|
|
107
109
|
function defaultCommand(serviceStatus) {
|
|
108
110
|
if (serviceStatus?.kind === 'running') {
|
|
@@ -115,7 +117,7 @@ function defaultCommand(serviceStatus) {
|
|
|
115
117
|
}
|
|
116
118
|
export async function selectCockpitTopLevelMenu(options = {}) {
|
|
117
119
|
const deps = menuDeps(options);
|
|
118
|
-
const choices = topLevelChoices(options.serviceStatus);
|
|
120
|
+
const choices = topLevelChoices(options.serviceStatus, options.moduleCount);
|
|
119
121
|
const cancelAction = 'back';
|
|
120
122
|
const selected = await deps.select({
|
|
121
123
|
message: '',
|
|
@@ -124,7 +126,7 @@ export async function selectCockpitTopLevelMenu(options = {}) {
|
|
|
124
126
|
pageSize: topLevelPageSize(choices.length),
|
|
125
127
|
loop: false,
|
|
126
128
|
hideMessage: true,
|
|
127
|
-
disabledError: disabledError(
|
|
129
|
+
disabledError: disabledError(),
|
|
128
130
|
navigationWarning: options.navigationWarning,
|
|
129
131
|
escapeBehavior: 'ignore',
|
|
130
132
|
});
|
package/dist/prompts/index.js
CHANGED
|
@@ -129,13 +129,30 @@ function renderedNavigationWarning(navigationWarning) {
|
|
|
129
129
|
const warning = typeof navigationWarning === 'function' ? navigationWarning() : navigationWarning;
|
|
130
130
|
return warning ? `\u001B[2m\u001B[38;2;226;184;96m${warning}\u001B[0m` : undefined;
|
|
131
131
|
}
|
|
132
|
-
function hiddenSelectTheme(disabledError, navigationHelp = 'exit', navigationWarning, hideMessage = true) {
|
|
132
|
+
function hiddenSelectTheme(disabledError, navigationHelp = 'exit', navigationWarning, hideMessage = true, disabledReasonLabels = []) {
|
|
133
|
+
let activeDisabledReason;
|
|
133
134
|
const keysHelpTip = navigationHelp === 'back'
|
|
134
135
|
? '↑↓ navigate • ⏎ select • Esc to go back'
|
|
135
136
|
: '↑↓ navigate • ⏎ select • Ctrl+C exit';
|
|
137
|
+
const disabledLabelPattern = / \(disabled\)$/u;
|
|
138
|
+
const disabledReasonSuffixes = [...disabledReasonLabels]
|
|
139
|
+
.sort((left, right) => right.length - left.length)
|
|
140
|
+
.map((reason) => ` ${reason}`);
|
|
141
|
+
const cursor = '\u001B[38;2;226;184;96m❯\u001B[39m';
|
|
142
|
+
const disabledCursor = '-';
|
|
136
143
|
const style = {
|
|
137
144
|
highlight: (text) => text,
|
|
138
|
-
disabled: (text) =>
|
|
145
|
+
disabled: (text) => {
|
|
146
|
+
let renderedText = text.replace(disabledLabelPattern, '');
|
|
147
|
+
const reasonSuffix = disabledReasonSuffixes.find((suffix) => renderedText.endsWith(suffix));
|
|
148
|
+
if (reasonSuffix) {
|
|
149
|
+
renderedText = renderedText.slice(0, -reasonSuffix.length);
|
|
150
|
+
}
|
|
151
|
+
if (text.startsWith(`${cursor} `) || text.startsWith(`${disabledCursor} ${cursor} `)) {
|
|
152
|
+
activeDisabledReason = reasonSuffix?.trim();
|
|
153
|
+
}
|
|
154
|
+
return styleText('dim', renderedText, { validateStream: false });
|
|
155
|
+
},
|
|
139
156
|
keysHelpTip: () => {
|
|
140
157
|
const warning = renderedNavigationWarning(navigationWarning);
|
|
141
158
|
return warning ? `${warning}\n${keysHelpTip}` : keysHelpTip;
|
|
@@ -147,12 +164,34 @@ function hiddenSelectTheme(disabledError, navigationHelp = 'exit', navigationWar
|
|
|
147
164
|
return {
|
|
148
165
|
prefix: '',
|
|
149
166
|
icon: {
|
|
150
|
-
cursor
|
|
167
|
+
cursor,
|
|
151
168
|
},
|
|
152
169
|
style,
|
|
153
|
-
i18n: disabledError ?
|
|
170
|
+
i18n: disabledError ? disabledErrorI18n(disabledError, () => activeDisabledReason) : undefined,
|
|
154
171
|
};
|
|
155
172
|
}
|
|
173
|
+
function disabledErrorI18n(disabledError, activeReason) {
|
|
174
|
+
const i18n = { disabledError };
|
|
175
|
+
Object.defineProperty(i18n, 'disabledError', {
|
|
176
|
+
get: () => {
|
|
177
|
+
const reason = activeReason();
|
|
178
|
+
return reason ? `${disabledError}\nReason: ${reason}` : disabledError;
|
|
179
|
+
},
|
|
180
|
+
});
|
|
181
|
+
return i18n;
|
|
182
|
+
}
|
|
183
|
+
function collectDisabledReasonLabels(choices) {
|
|
184
|
+
const reasons = new Set();
|
|
185
|
+
for (const choice of choices) {
|
|
186
|
+
if (typeof choice === 'object' &&
|
|
187
|
+
choice !== null &&
|
|
188
|
+
'disabled' in choice &&
|
|
189
|
+
typeof choice.disabled === 'string') {
|
|
190
|
+
reasons.add(choice.disabled);
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
return [...reasons];
|
|
194
|
+
}
|
|
156
195
|
function withHiddenSelectMessage(config) {
|
|
157
196
|
if (!config.hideMessage &&
|
|
158
197
|
!config.disabledError &&
|
|
@@ -165,7 +204,7 @@ function withHiddenSelectMessage(config) {
|
|
|
165
204
|
return {
|
|
166
205
|
...inquirerConfig,
|
|
167
206
|
message: config.hideMessage ? '' : inquirerConfig.message,
|
|
168
|
-
theme: hiddenSelectTheme(disabledError, navigationHelp, navigationWarning, Boolean(config.hideMessage)),
|
|
207
|
+
theme: hiddenSelectTheme(disabledError, navigationHelp, navigationWarning, Boolean(config.hideMessage), collectDisabledReasonLabels(inquirerConfig.choices)),
|
|
169
208
|
};
|
|
170
209
|
}
|
|
171
210
|
function asInquirerConfirmConfig(options) {
|