0
# History and Storage
1
2
Command history and local storage management for persistent data and user experience.
3
4
## Capabilities
5
6
### Command History Management
7
8
Sets an ID for command history, which enables history persistence across sessions.
9
10
```javascript { .api }
11
/**
12
* Sets an ID for command history persistence
13
* @param id - Unique identifier for history storage
14
* @returns Vorpal instance for chaining
15
*/
16
function history(id: string): Vorpal;
17
```
18
19
**Usage Example:**
20
21
```javascript
22
const vorpal = require('vorpal')();
23
24
// Enable persistent history with unique ID
25
vorpal
26
.history('my-cli-app')
27
.delimiter('myapp$')
28
.show();
29
30
// Users can now use up/down arrows to navigate command history
31
// History persists between application restarts
32
```
33
34
### History Storage Path
35
36
Sets the storage path for command history files.
37
38
```javascript { .api }
39
/**
40
* Sets file path for history storage
41
* @param path - File system path for storing history
42
* @returns Vorpal instance for chaining
43
*/
44
function historyStoragePath(path: string): Vorpal;
45
```
46
47
**Usage Example:**
48
49
```javascript
50
const vorpal = require('vorpal')();
51
const path = require('path');
52
const os = require('os');
53
54
// Set custom history storage location
55
const historyPath = path.join(os.homedir(), '.my-app', 'history');
56
57
vorpal
58
.history('my-app')
59
.historyStoragePath(historyPath)
60
.delimiter('myapp$')
61
.show();
62
```
63
64
### Local Storage
65
66
Sets up local storage for the CLI application with a unique identifier.
67
68
```javascript { .api }
69
/**
70
* Sets up local storage for CLI application
71
* @param id - Unique identifier for local storage
72
* @returns Vorpal instance for chaining
73
*/
74
function localStorage(id: string): Vorpal;
75
```
76
77
**Usage Example:**
78
79
```javascript
80
const vorpal = require('vorpal')();
81
82
// Enable local storage
83
vorpal
84
.localStorage('my-app-storage')
85
.command('set <key> <value>', 'Store a key-value pair')
86
.action(function(args, callback) {
87
// Access local storage through vorpal instance
88
this.parent.localStorage.setItem(args.key, args.value);
89
this.log(`Stored: ${args.key} = ${args.value}`);
90
callback();
91
});
92
93
vorpal
94
.command('get <key>', 'Retrieve a stored value')
95
.action(function(args, callback) {
96
const value = this.parent.localStorage.getItem(args.key);
97
if (value !== undefined) {
98
this.log(`${args.key} = ${value}`);
99
} else {
100
this.log(`Key '${args.key}' not found`);
101
}
102
callback();
103
});
104
105
vorpal
106
.delimiter('storage$')
107
.show();
108
```
109
110
## Local Storage Operations
111
112
### Store Item
113
114
Sets a value in local storage.
115
116
```javascript { .api }
117
/**
118
* Sets a key-value pair in local storage
119
* @param key - Storage key
120
* @param value - Value to store (any serializable type)
121
* @returns Stored value
122
*/
123
function setItem(key: string, value: any): any;
124
```
125
126
### Retrieve Item
127
128
Gets a value from local storage.
129
130
```javascript { .api }
131
/**
132
* Gets a value from local storage
133
* @param key - Storage key to retrieve
134
* @returns Retrieved value or undefined if not found
135
*/
136
function getItem(key: string): any;
137
```
138
139
### Remove Item
140
141
Removes a key-value pair from local storage.
142
143
```javascript { .api }
144
/**
145
* Removes a key-value pair from local storage
146
* @param key - Storage key to remove
147
* @returns Removed value or undefined if not found
148
*/
149
function removeItem(key: string): any;
150
```
151
152
**Complete Storage Example:**
153
154
```javascript
155
const vorpal = require('vorpal')();
156
157
vorpal
158
.localStorage('settings-app')
159
.command('config:set <key> <value>', 'Set configuration value')
160
.action(function(args, callback) {
161
this.parent.localStorage.setItem(args.key, args.value);
162
this.log(`Configuration set: ${args.key} = ${args.value}`);
163
callback();
164
});
165
166
vorpal
167
.command('config:get [key]', 'Get configuration value(s)')
168
.action(function(args, callback) {
169
if (args.key) {
170
const value = this.parent.localStorage.getItem(args.key);
171
if (value !== undefined) {
172
this.log(`${args.key} = ${value}`);
173
} else {
174
this.log(`Configuration '${args.key}' not found`);
175
}
176
} else {
177
// List all stored configurations
178
const storage = this.parent.localStorage;
179
this.log('All configurations:');
180
// Note: Actual implementation would need to iterate storage
181
}
182
callback();
183
});
184
185
vorpal
186
.command('config:remove <key>', 'Remove configuration value')
187
.action(function(args, callback) {
188
const removed = this.parent.localStorage.removeItem(args.key);
189
if (removed !== undefined) {
190
this.log(`Removed configuration: ${args.key}`);
191
} else {
192
this.log(`Configuration '${args.key}' not found`);
193
}
194
callback();
195
});
196
```
197
198
## History Operations
199
200
### History Class Methods
201
202
The History class provides methods for programmatic history management.
203
204
```javascript { .api }
205
/**
206
* Sets the ID for history storage
207
* @param id - History identifier
208
*/
209
function setId(id: string): void;
210
211
/**
212
* Sets custom storage path for history
213
* @param path - File system path
214
*/
215
function setStoragePath(path: string): void;
216
217
/**
218
* Gets previous command from history
219
* @returns Previous command string
220
*/
221
function getPreviousHistory(): string;
222
223
/**
224
* Gets next command from history
225
* @returns Next command string
226
*/
227
function getNextHistory(): string;
228
229
/**
230
* Peeks at history without changing position
231
* @param depth - How far back to look (optional)
232
* @returns Command at specified depth
233
*/
234
function peek(depth?: number): string;
235
236
/**
237
* Adds new command to history
238
* @param cmd - Command string to add
239
*/
240
function newCommand(cmd: string): void;
241
242
/**
243
* Handles mode entry for history
244
*/
245
function enterMode(): void;
246
247
/**
248
* Handles mode exit for history
249
*/
250
function exitMode(): void;
251
252
/**
253
* Clears command history
254
*/
255
function clear(): void;
256
```
257
258
**Advanced History Usage:**
259
260
```javascript
261
const vorpal = require('vorpal')();
262
263
vorpal
264
.history('advanced-app')
265
.command('history:clear', 'Clear command history')
266
.action(function(args, callback) {
267
this.parent.cmdHistory.clear();
268
this.log('Command history cleared');
269
callback();
270
});
271
272
vorpal
273
.command('history:show [count]', 'Show recent commands')
274
.action(function(args, callback) {
275
const count = parseInt(args.count) || 10;
276
this.log(`Last ${count} commands:`);
277
278
// Note: Actual implementation would access history data
279
for (let i = 0; i < count; i++) {
280
const cmd = this.parent.cmdHistory.peek(i);
281
if (cmd) {
282
this.log(`${i + 1}: ${cmd}`);
283
}
284
}
285
callback();
286
});
287
```
288
289
## Persistent Configuration Example
290
291
```javascript
292
const vorpal = require('vorpal')();
293
const path = require('path');
294
const os = require('os');
295
296
// Setup persistent storage and history
297
const appDataPath = path.join(os.homedir(), '.my-cli-app');
298
const historyPath = path.join(appDataPath, 'history');
299
300
vorpal
301
.history('my-cli-app')
302
.historyStoragePath(historyPath)
303
.localStorage('my-cli-app-config');
304
305
// User preferences command
306
vorpal
307
.command('prefs:set <key> <value>', 'Set user preference')
308
.action(function(args, callback) {
309
const preferences = this.parent.localStorage.getItem('preferences') || {};
310
preferences[args.key] = args.value;
311
this.parent.localStorage.setItem('preferences', preferences);
312
this.log(`Preference set: ${args.key} = ${args.value}`);
313
callback();
314
});
315
316
vorpal
317
.command('prefs:get [key]', 'Get user preference(s)')
318
.action(function(args, callback) {
319
const preferences = this.parent.localStorage.getItem('preferences') || {};
320
321
if (args.key) {
322
const value = preferences[args.key];
323
if (value !== undefined) {
324
this.log(`${args.key} = ${value}`);
325
} else {
326
this.log(`Preference '${args.key}' not set`);
327
}
328
} else {
329
this.log('All preferences:');
330
Object.keys(preferences).forEach(key => {
331
this.log(` ${key} = ${preferences[key]}`);
332
});
333
}
334
callback();
335
});
336
337
// Session state management
338
vorpal
339
.command('session:save', 'Save current session state')
340
.action(function(args, callback) {
341
const sessionState = {
342
timestamp: new Date().toISOString(),
343
delimiter: this.parent.session.delimiter(),
344
commands: this.parent.commands.length
345
};
346
347
this.parent.localStorage.setItem('lastSession', sessionState);
348
this.log('Session state saved');
349
callback();
350
});
351
352
vorpal
353
.command('session:restore', 'Show last session info')
354
.action(function(args, callback) {
355
const sessionState = this.parent.localStorage.getItem('lastSession');
356
357
if (sessionState) {
358
this.log('Last session:');
359
this.log(' Time:', sessionState.timestamp);
360
this.log(' Delimiter:', sessionState.delimiter);
361
this.log(' Commands available:', sessionState.commands);
362
} else {
363
this.log('No previous session found');
364
}
365
callback();
366
});
367
368
// Usage tracking
369
vorpal
370
.command('stats', 'Show usage statistics')
371
.action(function(args, callback) {
372
const stats = this.parent.localStorage.getItem('stats') || {
373
commandsRun: 0,
374
sessionsStarted: 0,
375
firstUse: new Date().toISOString()
376
};
377
378
this.log('Usage Statistics:');
379
this.log(' Commands run:', stats.commandsRun);
380
this.log(' Sessions started:', stats.sessionsStarted);
381
this.log(' First use:', stats.firstUse);
382
callback();
383
});
384
385
// Track command usage (hook into all command executions)
386
const originalExec = vorpal.exec;
387
vorpal.exec = function(command, args, callback) {
388
// Update stats
389
const stats = this.localStorage.getItem('stats') || {
390
commandsRun: 0,
391
sessionsStarted: 0,
392
firstUse: new Date().toISOString()
393
};
394
395
stats.commandsRun++;
396
this.localStorage.setItem('stats', stats);
397
398
// Call original exec method
399
return originalExec.call(this, command, args, callback);
400
};
401
402
// Initialize session tracking
403
const stats = vorpal.localStorage.getItem('stats') || {
404
commandsRun: 0,
405
sessionsStarted: 0,
406
firstUse: new Date().toISOString()
407
};
408
409
stats.sessionsStarted++;
410
vorpal.localStorage.setItem('stats', stats);
411
412
vorpal
413
.delimiter('myapp$')
414
.show();
415
```
416
417
## Storage Best Practices
418
419
### Data Serialization
420
421
Store complex objects properly:
422
423
```javascript
424
// Storing objects
425
const complexData = {
426
settings: { theme: 'dark', language: 'en' },
427
history: ['command1', 'command2'],
428
metadata: { version: '1.0.0' }
429
};
430
431
vorpal.localStorage.setItem('appData', JSON.stringify(complexData));
432
433
// Retrieving objects
434
const retrieved = JSON.parse(vorpal.localStorage.getItem('appData') || '{}');
435
```
436
437
### Error Handling
438
439
Handle storage errors gracefully:
440
441
```javascript
442
vorpal
443
.command('safe-store <key> <value>', 'Safely store data')
444
.action(function(args, callback) {
445
try {
446
this.parent.localStorage.setItem(args.key, args.value);
447
this.log(`Stored: ${args.key}`);
448
} catch (error) {
449
this.log(`Storage error: ${error.message}`);
450
}
451
callback();
452
});
453
```
454
455
### Migration Support
456
457
Handle data format changes:
458
459
```javascript
460
function migrateStorageData(vorpal) {
461
const version = vorpal.localStorage.getItem('dataVersion') || '1.0';
462
463
if (version === '1.0') {
464
// Migrate from v1.0 to v2.0 format
465
const oldData = vorpal.localStorage.getItem('userData');
466
if (oldData) {
467
const newData = transformDataV1ToV2(oldData);
468
vorpal.localStorage.setItem('userData', newData);
469
vorpal.localStorage.setItem('dataVersion', '2.0');
470
}
471
}
472
}
473
```