mepcli 0.5.5 → 0.6.1
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 +173 -6
- package/dist/ansi.d.ts +1 -0
- package/dist/ansi.js +1 -0
- package/dist/base.d.ts +5 -34
- package/dist/base.js +65 -98
- package/dist/core.d.ts +23 -1
- package/dist/core.js +60 -0
- package/dist/highlight.d.ts +1 -0
- package/dist/highlight.js +40 -0
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -1
- package/dist/input.js +26 -14
- package/dist/prompts/autocomplete.d.ts +1 -1
- package/dist/prompts/autocomplete.js +2 -7
- package/dist/prompts/calendar.d.ts +20 -0
- package/dist/prompts/calendar.js +329 -0
- package/dist/prompts/checkbox.d.ts +1 -1
- package/dist/prompts/checkbox.js +38 -8
- package/dist/prompts/code.d.ts +17 -0
- package/dist/prompts/code.js +210 -0
- package/dist/prompts/color.d.ts +14 -0
- package/dist/prompts/color.js +147 -0
- package/dist/prompts/confirm.d.ts +1 -1
- package/dist/prompts/confirm.js +1 -1
- package/dist/prompts/cron.d.ts +13 -0
- package/dist/prompts/cron.js +176 -0
- package/dist/prompts/date.d.ts +1 -1
- package/dist/prompts/date.js +15 -5
- package/dist/prompts/editor.js +2 -2
- package/dist/prompts/file.d.ts +7 -0
- package/dist/prompts/file.js +56 -60
- package/dist/prompts/form.d.ts +17 -0
- package/dist/prompts/form.js +225 -0
- package/dist/prompts/grid.d.ts +14 -0
- package/dist/prompts/grid.js +178 -0
- package/dist/prompts/keypress.d.ts +2 -2
- package/dist/prompts/keypress.js +2 -2
- package/dist/prompts/list.d.ts +1 -1
- package/dist/prompts/list.js +42 -22
- package/dist/prompts/multi-select.d.ts +1 -1
- package/dist/prompts/multi-select.js +39 -4
- package/dist/prompts/number.d.ts +1 -1
- package/dist/prompts/number.js +2 -2
- package/dist/prompts/range.d.ts +9 -0
- package/dist/prompts/range.js +140 -0
- package/dist/prompts/rating.d.ts +1 -1
- package/dist/prompts/rating.js +1 -1
- package/dist/prompts/select.d.ts +1 -1
- package/dist/prompts/select.js +1 -1
- package/dist/prompts/slider.d.ts +1 -1
- package/dist/prompts/slider.js +1 -1
- package/dist/prompts/snippet.d.ts +18 -0
- package/dist/prompts/snippet.js +203 -0
- package/dist/prompts/sort.d.ts +1 -1
- package/dist/prompts/sort.js +1 -4
- package/dist/prompts/spam.d.ts +17 -0
- package/dist/prompts/spam.js +62 -0
- package/dist/prompts/table.d.ts +1 -1
- package/dist/prompts/table.js +1 -1
- package/dist/prompts/text.d.ts +1 -0
- package/dist/prompts/text.js +13 -31
- package/dist/prompts/toggle.d.ts +1 -1
- package/dist/prompts/toggle.js +1 -1
- package/dist/prompts/transfer.d.ts +18 -0
- package/dist/prompts/transfer.js +203 -0
- package/dist/prompts/tree-select.d.ts +32 -0
- package/dist/prompts/tree-select.js +277 -0
- package/dist/prompts/tree.d.ts +3 -3
- package/dist/prompts/tree.js +27 -19
- package/dist/prompts/wait.d.ts +18 -0
- package/dist/prompts/wait.js +62 -0
- package/dist/types.d.ts +84 -0
- package/dist/utils.js +1 -1
- package/example.ts +150 -15
- package/package.json +2 -2
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { Prompt } from '../base';
|
|
2
|
+
import { BaseOptions } from '../types';
|
|
3
|
+
interface WaitOptions extends BaseOptions {
|
|
4
|
+
seconds: number;
|
|
5
|
+
autoSubmit?: boolean;
|
|
6
|
+
}
|
|
7
|
+
export declare class WaitPrompt extends Prompt<void, WaitOptions> {
|
|
8
|
+
private remaining;
|
|
9
|
+
private timer?;
|
|
10
|
+
private isDone;
|
|
11
|
+
constructor(options: WaitOptions);
|
|
12
|
+
run(): Promise<void>;
|
|
13
|
+
private stopTimer;
|
|
14
|
+
protected cleanup(): void;
|
|
15
|
+
protected render(_firstRender: boolean): void;
|
|
16
|
+
protected handleInput(char: string): void;
|
|
17
|
+
}
|
|
18
|
+
export {};
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.WaitPrompt = void 0;
|
|
4
|
+
// src/prompts/wait.ts
|
|
5
|
+
const ansi_1 = require("../ansi");
|
|
6
|
+
const base_1 = require("../base");
|
|
7
|
+
const theme_1 = require("../theme");
|
|
8
|
+
class WaitPrompt extends base_1.Prompt {
|
|
9
|
+
constructor(options) {
|
|
10
|
+
super(options);
|
|
11
|
+
this.isDone = false;
|
|
12
|
+
this.remaining = options.seconds;
|
|
13
|
+
}
|
|
14
|
+
run() {
|
|
15
|
+
// Start the countdown immediately upon running
|
|
16
|
+
this.timer = setInterval(() => {
|
|
17
|
+
this.remaining--;
|
|
18
|
+
if (this.remaining <= 0) {
|
|
19
|
+
this.isDone = true;
|
|
20
|
+
this.stopTimer();
|
|
21
|
+
if (this.options.autoSubmit) {
|
|
22
|
+
this.submit();
|
|
23
|
+
}
|
|
24
|
+
else {
|
|
25
|
+
this.render(false);
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
else {
|
|
29
|
+
this.render(false);
|
|
30
|
+
}
|
|
31
|
+
}, 1000);
|
|
32
|
+
return super.run();
|
|
33
|
+
}
|
|
34
|
+
stopTimer() {
|
|
35
|
+
if (this.timer) {
|
|
36
|
+
clearInterval(this.timer);
|
|
37
|
+
this.timer = undefined;
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
cleanup() {
|
|
41
|
+
this.stopTimer();
|
|
42
|
+
super.cleanup();
|
|
43
|
+
}
|
|
44
|
+
render(_firstRender) {
|
|
45
|
+
let output = `${theme_1.theme.title}${this.options.message}${ansi_1.ANSI.RESET} `;
|
|
46
|
+
if (this.isDone) {
|
|
47
|
+
output += `${theme_1.theme.success}Done! Press Enter to continue.${ansi_1.ANSI.RESET}`;
|
|
48
|
+
}
|
|
49
|
+
else {
|
|
50
|
+
// Fun countdown visualization
|
|
51
|
+
output += `${theme_1.theme.muted}Please wait... ${this.remaining}s${ansi_1.ANSI.RESET}`;
|
|
52
|
+
}
|
|
53
|
+
this.renderFrame(output);
|
|
54
|
+
}
|
|
55
|
+
handleInput(char) {
|
|
56
|
+
if (this.isDone && (char === '\r' || char === '\n')) {
|
|
57
|
+
this.submit();
|
|
58
|
+
}
|
|
59
|
+
// Else: Ignore all input while waiting
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
exports.WaitPrompt = WaitPrompt;
|
package/dist/types.d.ts
CHANGED
|
@@ -19,6 +19,9 @@ export interface MouseEvent {
|
|
|
19
19
|
button: number;
|
|
20
20
|
action: 'press' | 'release' | 'move' | 'scroll';
|
|
21
21
|
scroll?: 'up' | 'down';
|
|
22
|
+
shift?: boolean;
|
|
23
|
+
ctrl?: boolean;
|
|
24
|
+
meta?: boolean;
|
|
22
25
|
}
|
|
23
26
|
export interface TextOptions extends BaseOptions {
|
|
24
27
|
placeholder?: string;
|
|
@@ -26,6 +29,7 @@ export interface TextOptions extends BaseOptions {
|
|
|
26
29
|
validate?: (value: string) => string | boolean | Promise<string | boolean>;
|
|
27
30
|
isPassword?: boolean;
|
|
28
31
|
multiline?: boolean;
|
|
32
|
+
mask?: string;
|
|
29
33
|
}
|
|
30
34
|
export interface Separator {
|
|
31
35
|
separator: true;
|
|
@@ -39,6 +43,14 @@ export interface SelectChoice<V> {
|
|
|
39
43
|
export interface SelectOptions<V> extends BaseOptions {
|
|
40
44
|
choices: (SelectChoice<V> | Separator)[];
|
|
41
45
|
}
|
|
46
|
+
export interface TransferOptions<V> extends BaseOptions {
|
|
47
|
+
source: (string | SelectChoice<V>)[];
|
|
48
|
+
target?: (string | SelectChoice<V>)[];
|
|
49
|
+
}
|
|
50
|
+
export interface CronOptions extends BaseOptions {
|
|
51
|
+
initial?: string;
|
|
52
|
+
placeholder?: string;
|
|
53
|
+
}
|
|
42
54
|
export interface CheckboxChoice<V> extends SelectChoice<V> {
|
|
43
55
|
selected?: boolean;
|
|
44
56
|
}
|
|
@@ -74,6 +86,13 @@ export interface SliderOptions extends BaseOptions {
|
|
|
74
86
|
step?: number;
|
|
75
87
|
unit?: string;
|
|
76
88
|
}
|
|
89
|
+
export interface RangeOptions extends BaseOptions {
|
|
90
|
+
min: number;
|
|
91
|
+
max: number;
|
|
92
|
+
initial?: [number, number];
|
|
93
|
+
step?: number;
|
|
94
|
+
unit?: string;
|
|
95
|
+
}
|
|
77
96
|
export interface RatingOptions extends BaseOptions {
|
|
78
97
|
min?: number;
|
|
79
98
|
max?: number;
|
|
@@ -120,6 +139,7 @@ export interface TreeNode<V> {
|
|
|
120
139
|
children?: TreeNode<V>[];
|
|
121
140
|
expanded?: boolean;
|
|
122
141
|
disabled?: boolean;
|
|
142
|
+
selected?: boolean | 'indeterminate';
|
|
123
143
|
}
|
|
124
144
|
export interface TreeOptions<V> extends BaseOptions {
|
|
125
145
|
data: TreeNode<V>[];
|
|
@@ -130,3 +150,67 @@ export interface KeypressOptions extends BaseOptions {
|
|
|
130
150
|
keys?: string[];
|
|
131
151
|
showInvisible?: boolean;
|
|
132
152
|
}
|
|
153
|
+
export interface FormField {
|
|
154
|
+
name: string;
|
|
155
|
+
message: string;
|
|
156
|
+
initial?: string;
|
|
157
|
+
validate?: (value: string) => string | boolean | Promise<string | boolean>;
|
|
158
|
+
}
|
|
159
|
+
export interface FormOptions extends BaseOptions {
|
|
160
|
+
fields: FormField[];
|
|
161
|
+
}
|
|
162
|
+
export interface SnippetOptions extends BaseOptions {
|
|
163
|
+
template: string;
|
|
164
|
+
values?: Record<string, string>;
|
|
165
|
+
fields?: Record<string, {
|
|
166
|
+
message?: string;
|
|
167
|
+
validate?: (value: string) => string | boolean;
|
|
168
|
+
}>;
|
|
169
|
+
}
|
|
170
|
+
export interface SpamOptions extends BaseOptions {
|
|
171
|
+
threshold: number;
|
|
172
|
+
spamKey?: string;
|
|
173
|
+
decay?: boolean;
|
|
174
|
+
}
|
|
175
|
+
export interface WaitOptions extends BaseOptions {
|
|
176
|
+
seconds: number;
|
|
177
|
+
autoSubmit?: boolean;
|
|
178
|
+
}
|
|
179
|
+
export interface CodeOptions extends BaseOptions {
|
|
180
|
+
template: string;
|
|
181
|
+
language?: 'json' | 'yaml';
|
|
182
|
+
/**
|
|
183
|
+
* Enable syntax highlighting (Experimental).
|
|
184
|
+
* @default true
|
|
185
|
+
*/
|
|
186
|
+
highlight?: boolean;
|
|
187
|
+
}
|
|
188
|
+
export interface TreeSelectNode<V> {
|
|
189
|
+
title: string;
|
|
190
|
+
value: V;
|
|
191
|
+
children?: TreeSelectNode<V>[];
|
|
192
|
+
expanded?: boolean;
|
|
193
|
+
disabled?: boolean;
|
|
194
|
+
selected?: boolean | 'indeterminate';
|
|
195
|
+
}
|
|
196
|
+
export interface TreeSelectOptions<V> extends BaseOptions {
|
|
197
|
+
data: TreeSelectNode<V>[];
|
|
198
|
+
initial?: V[];
|
|
199
|
+
indent?: number;
|
|
200
|
+
}
|
|
201
|
+
export interface ColorOptions extends BaseOptions {
|
|
202
|
+
initial?: string;
|
|
203
|
+
format?: 'hex' | 'rgb' | 'hsl';
|
|
204
|
+
}
|
|
205
|
+
export interface GridOptions extends BaseOptions {
|
|
206
|
+
rows: string[];
|
|
207
|
+
columns: string[];
|
|
208
|
+
initial?: boolean[][];
|
|
209
|
+
}
|
|
210
|
+
export interface CalendarOptions extends BaseOptions {
|
|
211
|
+
mode?: 'single' | 'range';
|
|
212
|
+
initial?: Date | [Date, Date];
|
|
213
|
+
min?: Date;
|
|
214
|
+
max?: Date;
|
|
215
|
+
weekStart?: 0 | 1;
|
|
216
|
+
}
|
package/dist/utils.js
CHANGED
|
@@ -13,7 +13,7 @@ function detectCapabilities() {
|
|
|
13
13
|
// Check for CI
|
|
14
14
|
const isCI = !!env.CI;
|
|
15
15
|
// Check for True Color support
|
|
16
|
-
const hasTrueColor = env.COLORTERM === 'truecolor';
|
|
16
|
+
const hasTrueColor = env.COLORTERM === 'truecolor' || !!env.WT_SESSION;
|
|
17
17
|
// Check if it is a TTY
|
|
18
18
|
const isTTY = process.stdout.isTTY;
|
|
19
19
|
const isWindows = process.platform === 'win32';
|
package/example.ts
CHANGED
|
@@ -8,7 +8,7 @@ import { MepCLI } from './src'; // Or 'mepcli' if installed via NPM
|
|
|
8
8
|
*/
|
|
9
9
|
async function runComprehensiveDemo() {
|
|
10
10
|
console.clear();
|
|
11
|
-
console.log("--- MepCLI Comprehensive Demo (All
|
|
11
|
+
console.log("--- MepCLI Comprehensive Demo (All Prompts + Spin Utility) ---\n");
|
|
12
12
|
|
|
13
13
|
try {
|
|
14
14
|
// --- 1. Text Prompt (Input with Validation and initial value) ---
|
|
@@ -30,6 +30,13 @@ async function runComprehensiveDemo() {
|
|
|
30
30
|
});
|
|
31
31
|
console.log(`\n Password Result: API key entered (length: ${apiKey.length})`);
|
|
32
32
|
|
|
33
|
+
// --- 2.5. Secret Prompt (Completely hidden input) ---
|
|
34
|
+
const secretToken = await MepCLI.secret({
|
|
35
|
+
message: "Enter secret token (no feedback):",
|
|
36
|
+
validate: (v) => v.length > 0 || "Token required"
|
|
37
|
+
});
|
|
38
|
+
console.log(`\n Secret Result: Token entered (length: ${secretToken.length})`);
|
|
39
|
+
|
|
33
40
|
// --- 3. Select Prompt (Single choice, supports filtering/searching by typing) ---
|
|
34
41
|
const theme = await MepCLI.select({
|
|
35
42
|
message: "Choose your preferred editor color theme:",
|
|
@@ -77,7 +84,7 @@ async function runComprehensiveDemo() {
|
|
|
77
84
|
});
|
|
78
85
|
console.log(`\n Toggle Result: HTTPS enabled: ${isSecure}`);
|
|
79
86
|
|
|
80
|
-
// --- 7. List / Tags Input
|
|
87
|
+
// --- 7. List / Tags Input ---
|
|
81
88
|
const keywords = await MepCLI.list({
|
|
82
89
|
message: "Enter keywords for package.json (Enter to add, Backspace to remove):",
|
|
83
90
|
initial: ["cli", "mep"],
|
|
@@ -85,7 +92,7 @@ async function runComprehensiveDemo() {
|
|
|
85
92
|
});
|
|
86
93
|
console.log(`\n List Result: Keywords: [${keywords.join(', ')}]`);
|
|
87
94
|
|
|
88
|
-
// --- 8. Slider / Scale
|
|
95
|
+
// --- 8. Slider / Scale ---
|
|
89
96
|
const brightness = await MepCLI.slider({
|
|
90
97
|
message: "Set initial brightness:",
|
|
91
98
|
min: 0,
|
|
@@ -96,7 +103,18 @@ async function runComprehensiveDemo() {
|
|
|
96
103
|
});
|
|
97
104
|
console.log(`\n Slider Result: Brightness: ${brightness}%`);
|
|
98
105
|
|
|
99
|
-
// ---
|
|
106
|
+
// --- 8.1. Range Prompt (Dual Slider) ---
|
|
107
|
+
const priceRange = await MepCLI.range({
|
|
108
|
+
message: "Filter by price range:",
|
|
109
|
+
min: 0,
|
|
110
|
+
max: 1000,
|
|
111
|
+
initial: [200, 800],
|
|
112
|
+
step: 50,
|
|
113
|
+
unit: "$"
|
|
114
|
+
});
|
|
115
|
+
console.log(`\n Range Result: $${priceRange[0]} - $${priceRange[1]}`);
|
|
116
|
+
|
|
117
|
+
// --- 9. Rating Prompt ---
|
|
100
118
|
const userRating = await MepCLI.rating({
|
|
101
119
|
message: "How would you rate this CLI tool?",
|
|
102
120
|
min: 1,
|
|
@@ -105,7 +123,7 @@ async function runComprehensiveDemo() {
|
|
|
105
123
|
});
|
|
106
124
|
console.log(`\n Rating Result: You rated it: ${userRating}/5`);
|
|
107
125
|
|
|
108
|
-
// --- 10. Date / Time Picker
|
|
126
|
+
// --- 10. Date / Time Picker ---
|
|
109
127
|
// We capture 'now' once to ensure initial >= min
|
|
110
128
|
const now = new Date();
|
|
111
129
|
const releaseDate = await MepCLI.date({
|
|
@@ -115,14 +133,14 @@ async function runComprehensiveDemo() {
|
|
|
115
133
|
});
|
|
116
134
|
console.log(`\n Date Result: Release set for: ${releaseDate.toLocaleString()}`);
|
|
117
135
|
|
|
118
|
-
// --- 11. File Path Selector
|
|
136
|
+
// --- 11. File Path Selector ---
|
|
119
137
|
const configPath = await MepCLI.file({
|
|
120
138
|
message: "Select configuration file (Tab to autocomplete):",
|
|
121
139
|
basePath: process.cwd()
|
|
122
140
|
});
|
|
123
141
|
console.log(`\n File Result: Path: ${configPath}`);
|
|
124
142
|
|
|
125
|
-
// --- 12. Multi-Select Autocomplete
|
|
143
|
+
// --- 12. Multi-Select Autocomplete ---
|
|
126
144
|
const linters = await MepCLI.multiSelect({
|
|
127
145
|
message: "Select linters to install (Type to search, Space to select):",
|
|
128
146
|
choices: [
|
|
@@ -137,7 +155,7 @@ async function runComprehensiveDemo() {
|
|
|
137
155
|
});
|
|
138
156
|
console.log(`\n MultiSelect Result: Linters: [${linters.join(', ')}]`);
|
|
139
157
|
|
|
140
|
-
// --- 13. Autocomplete Prompt
|
|
158
|
+
// --- 13. Autocomplete Prompt ---
|
|
141
159
|
const city = await MepCLI.autocomplete({
|
|
142
160
|
message: "Search for a city (simulated async):",
|
|
143
161
|
suggest: async (query) => {
|
|
@@ -157,14 +175,22 @@ async function runComprehensiveDemo() {
|
|
|
157
175
|
});
|
|
158
176
|
console.log(`\n Autocomplete Result: City code: ${city}`);
|
|
159
177
|
|
|
160
|
-
// --- 14. Sort Prompt
|
|
178
|
+
// --- 14. Sort Prompt ---
|
|
161
179
|
const priorities = await MepCLI.sort({
|
|
162
180
|
message: "Rank your top priorities (Space to grab/drop, Arrows to move):",
|
|
163
181
|
items: ["Performance", "Security", "Features", "Usability", "Cost"]
|
|
164
182
|
});
|
|
165
183
|
console.log(`\n Sort Result: Priorities: [${priorities.join(', ')}]`);
|
|
166
184
|
|
|
167
|
-
// ---
|
|
185
|
+
// --- 14.1 Transfer Prompt (PickList) ---
|
|
186
|
+
const teamA = await MepCLI.transfer({
|
|
187
|
+
message: "Assign members to Team A (Space to move):",
|
|
188
|
+
source: ["Alice", "Bob", "Charlie", "David", "Eve"],
|
|
189
|
+
target: ["Frank"] // Pre-assigned
|
|
190
|
+
});
|
|
191
|
+
console.log(`\n Transfer Result: Team A: [${teamA[1].join(', ')}] (Remaining: [${teamA[0].join(', ')}])`);
|
|
192
|
+
|
|
193
|
+
// --- 15. Table Prompt ---
|
|
168
194
|
const userId = await MepCLI.table({
|
|
169
195
|
message: "Select a user from the database:",
|
|
170
196
|
columns: ["ID", "Name", "Role", "Status"],
|
|
@@ -184,7 +210,7 @@ async function runComprehensiveDemo() {
|
|
|
184
210
|
});
|
|
185
211
|
console.log(`\n Confirm Result: Deployment decision: ${proceed ? 'Proceed' : 'Cancel'}`);
|
|
186
212
|
|
|
187
|
-
// --- 17. Editor Prompt
|
|
213
|
+
// --- 17. Editor Prompt ---
|
|
188
214
|
const bio = await MepCLI.editor({
|
|
189
215
|
message: "Write your biography (opens default editor):",
|
|
190
216
|
initial: "Hi, I am a developer...",
|
|
@@ -193,7 +219,7 @@ async function runComprehensiveDemo() {
|
|
|
193
219
|
});
|
|
194
220
|
console.log(`\n Editor Result: Biography length: ${bio.length} chars`);
|
|
195
221
|
|
|
196
|
-
// --- 18. Keypress Prompt
|
|
222
|
+
// --- 18. Keypress Prompt ---
|
|
197
223
|
console.log("\n--- Press any key to continue to the Tree Prompt Demo... ---");
|
|
198
224
|
const key = await MepCLI.keypress({
|
|
199
225
|
message: "Press any key to proceed (or 'q' to quit):",
|
|
@@ -202,7 +228,7 @@ async function runComprehensiveDemo() {
|
|
|
202
228
|
console.log(`\n Keypress Result: You pressed '${key}'`);
|
|
203
229
|
if (key === 'q') return;
|
|
204
230
|
|
|
205
|
-
// --- 19. Tree Prompt
|
|
231
|
+
// --- 19. Tree Prompt ---
|
|
206
232
|
const selectedFile = await MepCLI.tree({
|
|
207
233
|
message: "Select a file from the project structure (Space to toggle, Enter to select):",
|
|
208
234
|
data: [
|
|
@@ -235,12 +261,121 @@ async function runComprehensiveDemo() {
|
|
|
235
261
|
});
|
|
236
262
|
console.log(`\n Tree Result: Selected path: ${selectedFile}`);
|
|
237
263
|
|
|
238
|
-
// --- 20.
|
|
264
|
+
// --- 20. Form Prompt ---
|
|
265
|
+
const userDetails = await MepCLI.form({
|
|
266
|
+
message: "Enter User Details (Up/Down/Tab to navigate):",
|
|
267
|
+
fields: [
|
|
268
|
+
{ name: "firstname", message: "First Name", initial: "John" },
|
|
269
|
+
{ name: "lastname", message: "Last Name", validate: (v) => v.length > 0 ? true : "Required" },
|
|
270
|
+
{ name: "email", message: "Email", validate: (v) => v.includes("@") || "Invalid email" },
|
|
271
|
+
{ name: "role", message: "Job Role", initial: "Developer" }
|
|
272
|
+
]
|
|
273
|
+
});
|
|
274
|
+
console.log(`\n Form Result: User: ${JSON.stringify(userDetails)}`);
|
|
275
|
+
|
|
276
|
+
// --- 21. Snippet Prompt ---
|
|
277
|
+
const commitMsg = await MepCLI.snippet({
|
|
278
|
+
message: "Compose Commit Message (Tab/Shift+Tab to navigate variables):",
|
|
279
|
+
template: "feat(${scope}): ${message} (Refs: #${issue})",
|
|
280
|
+
values: {
|
|
281
|
+
scope: "cli",
|
|
282
|
+
issue: "123"
|
|
283
|
+
}
|
|
284
|
+
});
|
|
285
|
+
console.log(`\n Snippet Result: "${commitMsg}"`);
|
|
286
|
+
|
|
287
|
+
// --- 22. Spam Prompt ---
|
|
288
|
+
const spamConfirmed = await MepCLI.spam({
|
|
289
|
+
message: "Hold on! Confirm deployment by mashing the Space key!",
|
|
290
|
+
threshold: 10,
|
|
291
|
+
decay: false, // We're not devil
|
|
292
|
+
spamKey: ' ' // Space key
|
|
293
|
+
});
|
|
294
|
+
console.log(`\n Spam Result: Deployment confirmed: ${spamConfirmed}`);
|
|
295
|
+
|
|
296
|
+
// --- 23. Wait Prompt ---
|
|
297
|
+
await MepCLI.wait({
|
|
298
|
+
message: "Please wait while we finalize the setup...",
|
|
299
|
+
seconds: 3, // Just 3 seconds for demo
|
|
300
|
+
autoSubmit: true // Automatically proceeds after time is up
|
|
301
|
+
});
|
|
302
|
+
console.log("\n Wait Result: Wait complete.");
|
|
303
|
+
|
|
304
|
+
// --- 24. Code Prompt ---
|
|
305
|
+
const config = await MepCLI.code({
|
|
306
|
+
message: "Configure Server (JSON) - Tab to nav:",
|
|
307
|
+
language: "json",
|
|
308
|
+
highlight: true, // Experimental syntax highlighting
|
|
309
|
+
template: `
|
|
310
|
+
{
|
|
311
|
+
"host": "\${host}",
|
|
312
|
+
"port": \${port},
|
|
313
|
+
"debug": \${debug}
|
|
314
|
+
}
|
|
315
|
+
`
|
|
316
|
+
});
|
|
317
|
+
console.log(`\n Code Result: Config: ${config.replace(/\n/g, ' ')}`);
|
|
318
|
+
|
|
319
|
+
// --- 25. Tree Select Prompt ---
|
|
320
|
+
const selectedTreeItems = await MepCLI.treeSelect({
|
|
321
|
+
message: "Select files to backup (Multi-select Tree):",
|
|
322
|
+
data: [
|
|
323
|
+
{
|
|
324
|
+
title: "src",
|
|
325
|
+
value: "src",
|
|
326
|
+
children: [
|
|
327
|
+
{ title: "index.ts", value: "src/index.ts" },
|
|
328
|
+
{ title: "utils.ts", value: "src/utils.ts" }
|
|
329
|
+
]
|
|
330
|
+
},
|
|
331
|
+
{
|
|
332
|
+
title: "tests",
|
|
333
|
+
value: "tests",
|
|
334
|
+
expanded: true,
|
|
335
|
+
children: [
|
|
336
|
+
{ title: "e2e", value: "tests/e2e", selected: true },
|
|
337
|
+
{ title: "unit", value: "tests/unit" }
|
|
338
|
+
]
|
|
339
|
+
}
|
|
340
|
+
]
|
|
341
|
+
});
|
|
342
|
+
console.log(`\n TreeSelect Result: Selected: [${selectedTreeItems.join(', ')}]`);
|
|
343
|
+
|
|
344
|
+
// --- 26. Cron Prompt ---
|
|
345
|
+
const schedule = await MepCLI.cron({
|
|
346
|
+
message: "Set backup schedule (Cron):",
|
|
347
|
+
initial: "0 4 * * *" // Daily at 4:00 AM
|
|
348
|
+
});
|
|
349
|
+
console.log(`\n Cron Result: "${schedule}"`);
|
|
350
|
+
|
|
351
|
+
// --- 27. Color Prompt ---
|
|
352
|
+
const themeColor = await MepCLI.color({
|
|
353
|
+
message: "Pick your brand color (RGB):",
|
|
354
|
+
initial: "#6366f1"
|
|
355
|
+
});
|
|
356
|
+
console.log(`\n Color Result: "${themeColor}"`);
|
|
357
|
+
|
|
358
|
+
// --- 28. Grid Prompt ---
|
|
359
|
+
const permissions = await MepCLI.grid({
|
|
360
|
+
message: "Configure Access Permissions:",
|
|
361
|
+
rows: ["Admin", "User", "Guest"],
|
|
362
|
+
columns: ["Read", "Write", "Execute"]
|
|
363
|
+
});
|
|
364
|
+
console.log(`\n Grid Result: (Boolean Matrix)`, permissions);
|
|
365
|
+
|
|
366
|
+
// --- 29. Calendar Prompt ---
|
|
367
|
+
const bookingRange = await MepCLI.calendar({
|
|
368
|
+
message: "Select booking period:",
|
|
369
|
+
mode: "range"
|
|
370
|
+
});
|
|
371
|
+
console.log(`\n Calendar Result:`, bookingRange);
|
|
372
|
+
|
|
373
|
+
// --- 30. Spin Utility (Loading/Async Task Indicator) ---
|
|
239
374
|
const s = MepCLI.spinner("Finalizing configuration and deploying...").start();
|
|
240
375
|
await new Promise(resolve => setTimeout(resolve, 1500)); // Simulates a 1.5 second async task
|
|
241
376
|
s.success();
|
|
242
377
|
|
|
243
|
-
console.log("\n--- Deployment successful! All MepCLI features
|
|
378
|
+
console.log("\n--- Deployment successful! All MepCLI features demonstrated! ---");
|
|
244
379
|
|
|
245
380
|
} catch (e) {
|
|
246
381
|
// Global handler for Ctrl+C closure
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "mepcli",
|
|
3
|
-
"version": "0.
|
|
4
|
-
"description": "Zero-dependency,
|
|
3
|
+
"version": "0.6.1",
|
|
4
|
+
"description": "Zero-dependency, interactive CLI prompt for Node.js",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
7
7
|
"url": "git+https://github.com/CodeTease/mep.git"
|