envmatic 1.0.0

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.
Files changed (102) hide show
  1. package/README.md +567 -0
  2. package/dist/cli.d.ts +7 -0
  3. package/dist/cli.d.ts.map +1 -0
  4. package/dist/cli.js +203 -0
  5. package/dist/cli.js.map +1 -0
  6. package/dist/commands/add.d.ts +11 -0
  7. package/dist/commands/add.d.ts.map +1 -0
  8. package/dist/commands/add.js +77 -0
  9. package/dist/commands/add.js.map +1 -0
  10. package/dist/commands/delete.d.ts +6 -0
  11. package/dist/commands/delete.d.ts.map +1 -0
  12. package/dist/commands/delete.js +78 -0
  13. package/dist/commands/delete.js.map +1 -0
  14. package/dist/commands/edit.d.ts +13 -0
  15. package/dist/commands/edit.d.ts.map +1 -0
  16. package/dist/commands/edit.js +364 -0
  17. package/dist/commands/edit.js.map +1 -0
  18. package/dist/commands/import.d.ts +11 -0
  19. package/dist/commands/import.d.ts.map +1 -0
  20. package/dist/commands/import.js +103 -0
  21. package/dist/commands/import.js.map +1 -0
  22. package/dist/commands/init.d.ts +8 -0
  23. package/dist/commands/init.d.ts.map +1 -0
  24. package/dist/commands/init.js +237 -0
  25. package/dist/commands/init.js.map +1 -0
  26. package/dist/commands/link.d.ts +16 -0
  27. package/dist/commands/link.d.ts.map +1 -0
  28. package/dist/commands/link.js +157 -0
  29. package/dist/commands/link.js.map +1 -0
  30. package/dist/commands/list.d.ts +9 -0
  31. package/dist/commands/list.d.ts.map +1 -0
  32. package/dist/commands/list.js +73 -0
  33. package/dist/commands/list.js.map +1 -0
  34. package/dist/commands/lock.d.ts +16 -0
  35. package/dist/commands/lock.d.ts.map +1 -0
  36. package/dist/commands/lock.js +245 -0
  37. package/dist/commands/lock.js.map +1 -0
  38. package/dist/commands/rotate.d.ts +15 -0
  39. package/dist/commands/rotate.d.ts.map +1 -0
  40. package/dist/commands/rotate.js +406 -0
  41. package/dist/commands/rotate.js.map +1 -0
  42. package/dist/commands/show.d.ts +9 -0
  43. package/dist/commands/show.d.ts.map +1 -0
  44. package/dist/commands/show.js +72 -0
  45. package/dist/commands/show.js.map +1 -0
  46. package/dist/commands/sync.d.ts +13 -0
  47. package/dist/commands/sync.d.ts.map +1 -0
  48. package/dist/commands/sync.js +174 -0
  49. package/dist/commands/sync.js.map +1 -0
  50. package/dist/commands/use.d.ts +19 -0
  51. package/dist/commands/use.d.ts.map +1 -0
  52. package/dist/commands/use.js +238 -0
  53. package/dist/commands/use.js.map +1 -0
  54. package/dist/constants.d.ts +20 -0
  55. package/dist/constants.d.ts.map +1 -0
  56. package/dist/constants.js +47 -0
  57. package/dist/constants.js.map +1 -0
  58. package/dist/index.d.ts +15 -0
  59. package/dist/index.d.ts.map +1 -0
  60. package/dist/index.js +21 -0
  61. package/dist/index.js.map +1 -0
  62. package/dist/services/config.d.ts +64 -0
  63. package/dist/services/config.d.ts.map +1 -0
  64. package/dist/services/config.js +133 -0
  65. package/dist/services/config.js.map +1 -0
  66. package/dist/services/encryption.d.ts +30 -0
  67. package/dist/services/encryption.d.ts.map +1 -0
  68. package/dist/services/encryption.js +146 -0
  69. package/dist/services/encryption.js.map +1 -0
  70. package/dist/services/envfile.d.ts +76 -0
  71. package/dist/services/envfile.d.ts.map +1 -0
  72. package/dist/services/envfile.js +247 -0
  73. package/dist/services/envfile.js.map +1 -0
  74. package/dist/services/git.d.ts +60 -0
  75. package/dist/services/git.d.ts.map +1 -0
  76. package/dist/services/git.js +239 -0
  77. package/dist/services/git.js.map +1 -0
  78. package/dist/services/linker.d.ts +46 -0
  79. package/dist/services/linker.d.ts.map +1 -0
  80. package/dist/services/linker.js +222 -0
  81. package/dist/services/linker.js.map +1 -0
  82. package/dist/services/protection.d.ts +32 -0
  83. package/dist/services/protection.d.ts.map +1 -0
  84. package/dist/services/protection.js +190 -0
  85. package/dist/services/protection.js.map +1 -0
  86. package/dist/types/index.d.ts +73 -0
  87. package/dist/types/index.d.ts.map +1 -0
  88. package/dist/types/index.js +5 -0
  89. package/dist/types/index.js.map +1 -0
  90. package/dist/utils/display.d.ts +74 -0
  91. package/dist/utils/display.d.ts.map +1 -0
  92. package/dist/utils/display.js +138 -0
  93. package/dist/utils/display.js.map +1 -0
  94. package/dist/utils/editor.d.ts +22 -0
  95. package/dist/utils/editor.d.ts.map +1 -0
  96. package/dist/utils/editor.js +159 -0
  97. package/dist/utils/editor.js.map +1 -0
  98. package/dist/utils/prompts.d.ts +41 -0
  99. package/dist/utils/prompts.d.ts.map +1 -0
  100. package/dist/utils/prompts.js +222 -0
  101. package/dist/utils/prompts.js.map +1 -0
  102. package/package.json +69 -0
@@ -0,0 +1,237 @@
1
+ /**
2
+ * Init Command
3
+ * Initialize Envmatic with a Git repository
4
+ */
5
+ import ora from 'ora';
6
+ import inquirer from 'inquirer';
7
+ import { isConfigured, saveConfig, createInitialConfig, ensureEnvmaticHome } from '../services/config.js';
8
+ import { cloneRepository, initRepository, isVaultInitialized, checkRemoteAccess } from '../services/git.js';
9
+ import { verifyEncryption, validateSSHKey } from '../services/encryption.js';
10
+ import { printBanner, success, error, info, warning, colors } from '../utils/display.js';
11
+ import { DEFAULT_BRANCH } from '../constants.js';
12
+ export async function initCommand(options) {
13
+ printBanner();
14
+ // Check if already configured
15
+ if (await isConfigured() && !options.force) {
16
+ error('Envmatic is already initialized.');
17
+ info('Use --force to reinitialize (this will overwrite current settings).');
18
+ return;
19
+ }
20
+ console.log('Let\'s set up your secure environment vault.\n');
21
+ // Get repository URL
22
+ const { repoUrl } = await inquirer.prompt([
23
+ {
24
+ type: 'input',
25
+ name: 'repoUrl',
26
+ message: 'Enter your private Git repository URL:',
27
+ validate: (input) => {
28
+ if (!input || input.trim().length === 0) {
29
+ return 'Repository URL is required';
30
+ }
31
+ if (!input.includes('git') && !input.includes('github') && !input.includes('gitlab') && !input.includes('bitbucket')) {
32
+ return 'Please enter a valid Git repository URL';
33
+ }
34
+ return true;
35
+ },
36
+ },
37
+ ]);
38
+ // Check repository access
39
+ const accessSpinner = ora('Checking repository access...').start();
40
+ const hasAccess = await checkRemoteAccess(repoUrl);
41
+ if (!hasAccess) {
42
+ accessSpinner.fail('Cannot access repository');
43
+ console.log();
44
+ warning('Make sure you have:');
45
+ console.log(' • Created the repository');
46
+ console.log(' • Configured SSH keys or credentials');
47
+ console.log(' • Have push access to the repository');
48
+ console.log();
49
+ info('Tip: Test with: git ls-remote ' + repoUrl);
50
+ return;
51
+ }
52
+ accessSpinner.succeed('Repository is accessible');
53
+ // Ask about encryption
54
+ const { enableEncryption } = await inquirer.prompt([
55
+ {
56
+ type: 'confirm',
57
+ name: 'enableEncryption',
58
+ message: 'Enable encryption for extra security?',
59
+ default: true,
60
+ },
61
+ ]);
62
+ let encryptionMethod;
63
+ let sshKeyPath;
64
+ let password;
65
+ if (enableEncryption) {
66
+ const { method } = await inquirer.prompt([
67
+ {
68
+ type: 'list',
69
+ name: 'method',
70
+ message: 'Choose encryption method:',
71
+ choices: [
72
+ { name: 'Password (you\'ll be prompted when accessing secrets)', value: 'password' },
73
+ { name: 'SSH Key (uses your existing SSH key for encryption)', value: 'ssh' },
74
+ ],
75
+ },
76
+ ]);
77
+ encryptionMethod = method;
78
+ if (method === 'password') {
79
+ // Show password security warning
80
+ console.log();
81
+ console.log(colors.error('╔══════════════════════════════════════════════════════════════╗'));
82
+ console.log(colors.error('║') + colors.warning(' ⚠️ PASSWORD SECURITY WARNING ') + colors.error('║'));
83
+ console.log(colors.error('╠══════════════════════════════════════════════════════════════╣'));
84
+ console.log(colors.error('║') + ' Your password is the ONLY way to decrypt your secrets. ' + colors.error('║'));
85
+ console.log(colors.error('║') + ' There is NO password recovery mechanism. ' + colors.error('║'));
86
+ console.log(colors.error('║') + ' ' + colors.error('║'));
87
+ console.log(colors.error('║') + colors.warning(' If you forget your password: ') + colors.error('║'));
88
+ console.log(colors.error('║') + colors.error(' → All encrypted data will be PERMANENTLY LOST ') + colors.error('║'));
89
+ console.log(colors.error('║') + colors.error(' → There is NO way to recover your secrets ') + colors.error('║'));
90
+ console.log(colors.error('║') + ' ' + colors.error('║'));
91
+ console.log(colors.error('║') + ' We strongly recommend: ' + colors.error('║'));
92
+ console.log(colors.error('║') + ' • Using a password manager to store your password ' + colors.error('║'));
93
+ console.log(colors.error('║') + ' • Writing it down and storing it securely offline ' + colors.error('║'));
94
+ console.log(colors.error('║') + ' • Consider using SSH key encryption instead ' + colors.error('║'));
95
+ console.log(colors.error('╚══════════════════════════════════════════════════════════════╝'));
96
+ console.log();
97
+ const { understood } = await inquirer.prompt([
98
+ {
99
+ type: 'confirm',
100
+ name: 'understood',
101
+ message: 'I understand that forgetting my password means losing all encrypted data',
102
+ default: false,
103
+ },
104
+ ]);
105
+ if (!understood) {
106
+ info('Setup cancelled. Consider using SSH key encryption instead.');
107
+ return;
108
+ }
109
+ }
110
+ if (method === 'ssh') {
111
+ const { keyPath } = await inquirer.prompt([
112
+ {
113
+ type: 'input',
114
+ name: 'keyPath',
115
+ message: 'Path to SSH private key:',
116
+ default: '~/.ssh/id_rsa',
117
+ },
118
+ ]);
119
+ sshKeyPath = keyPath.replace(/^~/, process.env.HOME || '');
120
+ const validKey = await validateSSHKey(sshKeyPath);
121
+ if (!validKey) {
122
+ error('Invalid SSH key file. Please check the path and try again.');
123
+ return;
124
+ }
125
+ success('SSH key validated');
126
+ }
127
+ else {
128
+ // Password method
129
+ const { pwd } = await inquirer.prompt([
130
+ {
131
+ type: 'password',
132
+ name: 'pwd',
133
+ message: 'Create an encryption password:',
134
+ mask: '*',
135
+ validate: (input) => {
136
+ if (!input || input.length < 8) {
137
+ return 'Password must be at least 8 characters';
138
+ }
139
+ return true;
140
+ },
141
+ },
142
+ ]);
143
+ const { confirmPwd } = await inquirer.prompt([
144
+ {
145
+ type: 'password',
146
+ name: 'confirmPwd',
147
+ message: 'Confirm password:',
148
+ mask: '*',
149
+ validate: (input) => {
150
+ if (input !== pwd) {
151
+ return 'Passwords do not match';
152
+ }
153
+ return true;
154
+ },
155
+ },
156
+ ]);
157
+ password = pwd;
158
+ }
159
+ // Verify encryption works
160
+ const verifySpinner = ora('Verifying encryption...').start();
161
+ const encryptionOptions = encryptionMethod === 'ssh'
162
+ ? { method: 'ssh', sshKeyPath: sshKeyPath }
163
+ : { method: 'password', password: password };
164
+ const verified = await verifyEncryption(encryptionOptions);
165
+ if (!verified) {
166
+ verifySpinner.fail('Encryption verification failed');
167
+ return;
168
+ }
169
+ verifySpinner.succeed('Encryption verified');
170
+ }
171
+ // Ask about immutability
172
+ const { immutableByDefault } = await inquirer.prompt([
173
+ {
174
+ type: 'confirm',
175
+ name: 'immutableByDefault',
176
+ message: 'Make files immutable by default (prevents accidental edits)?',
177
+ default: true,
178
+ },
179
+ ]);
180
+ // Initialize envmatic home
181
+ await ensureEnvmaticHome();
182
+ // Clone or init repository
183
+ const repoSpinner = ora('Setting up vault...').start();
184
+ try {
185
+ if (await isVaultInitialized() && options.force) {
186
+ // Clear existing vault
187
+ const fs = await import('fs-extra');
188
+ const { VAULT_PATH } = await import('../constants.js');
189
+ await fs.remove(VAULT_PATH);
190
+ }
191
+ try {
192
+ // Try to clone (repo has content)
193
+ await cloneRepository(repoUrl, DEFAULT_BRANCH);
194
+ repoSpinner.succeed('Vault cloned from repository');
195
+ }
196
+ catch {
197
+ // Repository might be empty, initialize it
198
+ await initRepository(repoUrl, DEFAULT_BRANCH);
199
+ repoSpinner.succeed('Vault initialized (new repository)');
200
+ }
201
+ }
202
+ catch (err) {
203
+ repoSpinner.fail('Failed to set up vault');
204
+ const errorMessage = err instanceof Error ? err.message : String(err);
205
+ error(errorMessage);
206
+ return;
207
+ }
208
+ // Save configuration
209
+ const config = createInitialConfig(repoUrl, {
210
+ encryptionEnabled: enableEncryption,
211
+ encryptionMethod,
212
+ sshKeyPath,
213
+ immutableByDefault,
214
+ branch: DEFAULT_BRANCH,
215
+ });
216
+ await saveConfig(config);
217
+ console.log();
218
+ success('Envmatic initialized successfully!');
219
+ console.log();
220
+ console.log(colors.muted('Next steps:'));
221
+ console.log(' • Add your first env file: ' + colors.primary('envmatic add'));
222
+ console.log(' • Import an existing .env: ' + colors.primary('envmatic import .env'));
223
+ console.log(' • View all commands: ' + colors.primary('envmatic --help'));
224
+ console.log();
225
+ if (enableEncryption && encryptionMethod === 'password') {
226
+ console.log(colors.warning('┌─────────────────────────────────────────────────────┐'));
227
+ console.log(colors.warning('│') + colors.error(' ⚠️ REMEMBER YOUR PASSWORD! ') + colors.warning('│'));
228
+ console.log(colors.warning('│') + ' It cannot be recovered. If you forget it, ' + colors.warning('│'));
229
+ console.log(colors.warning('│') + ' all encrypted data will be permanently lost. ' + colors.warning('│'));
230
+ console.log(colors.warning('│') + ' ' + colors.warning('│'));
231
+ console.log(colors.warning('│') + ' To change your password later: ' + colors.warning('│'));
232
+ console.log(colors.warning('│') + colors.primary(' envmatic change-password ') + colors.warning('│'));
233
+ console.log(colors.warning('└─────────────────────────────────────────────────────┘'));
234
+ console.log();
235
+ }
236
+ }
237
+ //# sourceMappingURL=init.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"init.js","sourceRoot":"","sources":["../../src/commands/init.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,16 @@
1
+ /**
2
+ * Link Command
3
+ * Create symlink or copy of env file to target path
4
+ */
5
+ export declare function linkCommand(fileId?: string, targetPath?: string, options?: {
6
+ copy?: boolean;
7
+ autoSync?: boolean;
8
+ }): Promise<void>;
9
+ export declare function copyCommand(fileId?: string, targetPath?: string, options?: {
10
+ autoSync?: boolean;
11
+ }): Promise<void>;
12
+ export declare function unlinkCommand(targetPath?: string): Promise<void>;
13
+ export declare function listLinksCommand(options?: {
14
+ json?: boolean;
15
+ }): Promise<void>;
16
+ //# sourceMappingURL=link.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"link.d.ts","sourceRoot":"","sources":["../../src/commands/link.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAmBH,wBAAsB,WAAW,CAC/B,MAAM,CAAC,EAAE,MAAM,EACf,UAAU,CAAC,EAAE,MAAM,EACnB,OAAO,GAAE;IACP,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,QAAQ,CAAC,EAAE,OAAO,CAAC;CACf,GACL,OAAO,CAAC,IAAI,CAAC,CAwGf;AAED,wBAAsB,WAAW,CAC/B,MAAM,CAAC,EAAE,MAAM,EACf,UAAU,CAAC,EAAE,MAAM,EACnB,OAAO,GAAE;IAAE,QAAQ,CAAC,EAAE,OAAO,CAAA;CAAO,GACnC,OAAO,CAAC,IAAI,CAAC,CAEf;AAED,wBAAsB,aAAa,CAAC,UAAU,CAAC,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAyCtE;AAED,wBAAsB,gBAAgB,CAAC,OAAO,GAAE;IAAE,IAAI,CAAC,EAAE,OAAO,CAAA;CAAO,GAAG,OAAO,CAAC,IAAI,CAAC,CAmCtF"}
@@ -0,0 +1,157 @@
1
+ /**
2
+ * Link Command
3
+ * Create symlink or copy of env file to target path
4
+ */
5
+ import path from 'path';
6
+ import ora from 'ora';
7
+ import { listEnvFiles } from '../services/envfile.js';
8
+ import { createSymlink, createCopy, listLinks, unlink } from '../services/linker.js';
9
+ import { getConfig } from '../services/config.js';
10
+ import { getManifest } from '../services/git.js';
11
+ import { printBanner, success, error, warning, info, colors, formatFileId } from '../utils/display.js';
12
+ import { getEncryptionOptions, select, confirm } from '../utils/prompts.js';
13
+ export async function linkCommand(fileId, targetPath, options = {}) {
14
+ printBanner();
15
+ const config = await getConfig();
16
+ if (!config) {
17
+ error('Envmatic is not initialized. Run `envmatic init` first.');
18
+ return;
19
+ }
20
+ // If no file ID provided, prompt for selection
21
+ if (!fileId) {
22
+ const files = await listEnvFiles();
23
+ if (files.length === 0) {
24
+ error('No env files found. Add one with `envmatic add`');
25
+ return;
26
+ }
27
+ fileId = await select('Select an env file to link:', files.map(f => ({
28
+ name: `${f.project}/${f.environment || 'default'}/${f.name}`,
29
+ value: f.id,
30
+ })));
31
+ }
32
+ // Verify file exists
33
+ const manifest = await getManifest();
34
+ const metadata = manifest.files.find(f => f.id === fileId);
35
+ if (!metadata) {
36
+ error(`Env file not found: ${fileId}`);
37
+ return;
38
+ }
39
+ // Get target path
40
+ if (!targetPath) {
41
+ const { target } = await (await import('inquirer')).default.prompt([
42
+ {
43
+ type: 'input',
44
+ name: 'target',
45
+ message: 'Target path (e.g., ./.env):',
46
+ default: './.env',
47
+ },
48
+ ]);
49
+ targetPath = target;
50
+ }
51
+ const resolvedTarget = path.resolve(targetPath);
52
+ // Check if encrypted file - must use copy
53
+ if (metadata.encrypted && !options.copy) {
54
+ warning('Encrypted files cannot be symlinked. Using copy mode instead.');
55
+ options.copy = true;
56
+ }
57
+ const encryptionOptions = await getEncryptionOptions();
58
+ const spinner = ora(options.copy ? 'Creating copy...' : 'Creating symlink...').start();
59
+ try {
60
+ let link;
61
+ if (options.copy) {
62
+ link = await createCopy(fileId, resolvedTarget, encryptionOptions, options.autoSync ?? false);
63
+ }
64
+ else {
65
+ link = await createSymlink(fileId, resolvedTarget, encryptionOptions);
66
+ }
67
+ spinner.succeed(options.copy ? 'Copy created' : 'Symlink created');
68
+ console.log();
69
+ success(`Linked ${formatFileId(fileId)}`);
70
+ console.log();
71
+ console.log(' Target: ' + colors.secondary(resolvedTarget));
72
+ console.log(' Type: ' + (link.type === 'symlink' ? 'symlink' : 'copy'));
73
+ if (link.type === 'copy') {
74
+ console.log(' Sync: ' + (link.autoSync ? 'auto' : 'manual'));
75
+ console.log();
76
+ info('This is a copy. Run `envmatic sync-links` to update it.');
77
+ }
78
+ else {
79
+ console.log();
80
+ info('This is a symlink. Changes to source will be reflected automatically.');
81
+ }
82
+ }
83
+ catch (err) {
84
+ spinner.fail('Failed to create link');
85
+ const errorMessage = err instanceof Error ? err.message : String(err);
86
+ error(errorMessage);
87
+ if (errorMessage.includes('Developer Mode')) {
88
+ console.log();
89
+ info('Alternative: Use --copy flag to create a copy instead of symlink.');
90
+ }
91
+ }
92
+ }
93
+ export async function copyCommand(fileId, targetPath, options = {}) {
94
+ return linkCommand(fileId, targetPath, { ...options, copy: true });
95
+ }
96
+ export async function unlinkCommand(targetPath) {
97
+ printBanner();
98
+ const config = await getConfig();
99
+ if (!config) {
100
+ error('Envmatic is not initialized. Run `envmatic init` first.');
101
+ return;
102
+ }
103
+ // If no target provided, show list and let user select
104
+ if (!targetPath) {
105
+ const links = await listLinks();
106
+ if (links.length === 0) {
107
+ info('No linked files found.');
108
+ return;
109
+ }
110
+ targetPath = await select('Select a link to remove:', links.map(l => ({
111
+ name: `${l.targetPath} (${l.type})`,
112
+ value: l.targetPath,
113
+ })));
114
+ }
115
+ const confirmed = await confirm(`Remove link at ${targetPath}?`);
116
+ if (!confirmed) {
117
+ info('Cancelled.');
118
+ return;
119
+ }
120
+ const removed = await unlink(targetPath);
121
+ if (removed) {
122
+ success('Link removed');
123
+ }
124
+ else {
125
+ warning('Link not found in registry');
126
+ }
127
+ }
128
+ export async function listLinksCommand(options = {}) {
129
+ if (!options.json) {
130
+ printBanner();
131
+ }
132
+ const config = await getConfig();
133
+ if (!config) {
134
+ error('Envmatic is not initialized. Run `envmatic init` first.');
135
+ return;
136
+ }
137
+ const links = await listLinks();
138
+ if (options.json) {
139
+ console.log(JSON.stringify(links, null, 2));
140
+ return;
141
+ }
142
+ if (links.length === 0) {
143
+ info('No linked files found.');
144
+ console.log();
145
+ console.log('Create a link: ' + colors.primary('envmatic link <file-id> <target>'));
146
+ return;
147
+ }
148
+ console.log(colors.muted(`Found ${links.length} link(s)\n`));
149
+ for (const link of links) {
150
+ const typeIcon = link.type === 'symlink' ? '🔗' : '📄';
151
+ const syncIcon = link.autoSync ? '🔄' : '';
152
+ console.log(`${typeIcon} ${colors.secondary(link.targetPath)} ${syncIcon}`);
153
+ console.log(colors.muted(` └─ ${link.sourceId}`));
154
+ console.log();
155
+ }
156
+ }
157
+ //# sourceMappingURL=link.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"link.js","sourceRoot":"","sources":["../../src/commands/link.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,9 @@
1
+ /**
2
+ * List Command
3
+ * List all env files in the vault
4
+ */
5
+ export declare function listCommand(options: {
6
+ project?: string;
7
+ json?: boolean;
8
+ }): Promise<void>;
9
+ //# sourceMappingURL=list.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list.d.ts","sourceRoot":"","sources":["../../src/commands/list.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAOH,wBAAsB,WAAW,CAAC,OAAO,EAAE;IACzC,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,IAAI,CAAC,EAAE,OAAO,CAAC;CAChB,GAAG,OAAO,CAAC,IAAI,CAAC,CAiFhB"}
@@ -0,0 +1,73 @@
1
+ /**
2
+ * List Command
3
+ * List all env files in the vault
4
+ */
5
+ import { listEnvFiles, listProjects } from '../services/envfile.js';
6
+ import { getConfig } from '../services/config.js';
7
+ import { printBanner, error, colors, dim } from '../utils/display.js';
8
+ export async function listCommand(options) {
9
+ if (!options.json) {
10
+ printBanner();
11
+ }
12
+ const config = await getConfig();
13
+ if (!config) {
14
+ error('Envmatic is not initialized. Run `envmatic init` first.');
15
+ return;
16
+ }
17
+ const files = await listEnvFiles(options.project);
18
+ const projects = await listProjects();
19
+ if (options.json) {
20
+ console.log(JSON.stringify({ projects, files }, null, 2));
21
+ return;
22
+ }
23
+ if (files.length === 0) {
24
+ dim('No env files found.');
25
+ console.log();
26
+ console.log('Add your first file: ' + colors.primary('envmatic add'));
27
+ return;
28
+ }
29
+ // Group files by project
30
+ const grouped = {};
31
+ for (const file of files) {
32
+ if (!grouped[file.project]) {
33
+ grouped[file.project] = [];
34
+ }
35
+ grouped[file.project].push(file);
36
+ }
37
+ console.log(colors.muted(`Found ${files.length} file(s) in ${projects.length} project(s)\n`));
38
+ for (const project of Object.keys(grouped).sort()) {
39
+ const projectFiles = grouped[project];
40
+ console.log(colors.primary.bold(`◆ ${project}`));
41
+ for (let i = 0; i < projectFiles.length; i++) {
42
+ const file = projectFiles[i];
43
+ const isLast = i === projectFiles.length - 1;
44
+ const connector = isLast ? '└─' : '├─';
45
+ const envLabel = file.environment
46
+ ? colors.secondary(file.environment)
47
+ : colors.muted('default');
48
+ const flags = [];
49
+ if (file.encrypted)
50
+ flags.push(colors.accent('🔒'));
51
+ if (file.immutable)
52
+ flags.push(colors.muted('📌'));
53
+ const flagStr = flags.length > 0 ? ' ' + flags.join(' ') : '';
54
+ console.log(colors.muted(` ${connector} `) +
55
+ envLabel +
56
+ colors.muted('/') +
57
+ file.name +
58
+ flagStr);
59
+ if (file.description) {
60
+ const descConnector = isLast ? ' ' : '│ ';
61
+ console.log(colors.muted(` ${descConnector} ${file.description}`));
62
+ }
63
+ }
64
+ console.log();
65
+ }
66
+ console.log(colors.muted('Legend: 🔒 encrypted 📌 immutable'));
67
+ console.log();
68
+ console.log(colors.muted('Commands:'));
69
+ console.log(' Show file: ' + colors.primary('envmatic show <file-id>'));
70
+ console.log(' Link file: ' + colors.primary('envmatic link <file-id> <target>'));
71
+ console.log(' Edit file: ' + colors.primary('envmatic edit <file-id>'));
72
+ }
73
+ //# sourceMappingURL=list.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"list.js","sourceRoot":"","sources":["../../src/commands/list.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,16 @@
1
+ /**
2
+ * Lock Command
3
+ * List and lock mutable (unlocked) env files
4
+ */
5
+ /**
6
+ * Lock command - list and lock mutable files
7
+ */
8
+ export declare function lockCommand(fileId?: string, options?: {
9
+ all?: boolean;
10
+ }): Promise<void>;
11
+ /**
12
+ * Unlock command - unlock a file for editing
13
+ * (This is primarily used internally by the edit --editor command)
14
+ */
15
+ export declare function unlockFileForEditing(fileId: string): Promise<string | null>;
16
+ //# sourceMappingURL=lock.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"lock.d.ts","sourceRoot":"","sources":["../../src/commands/lock.ts"],"names":[],"mappings":"AAAA;;;GAGG;AA4DH;;GAEG;AACH,wBAAsB,WAAW,CAC/B,MAAM,CAAC,EAAE,MAAM,EACf,OAAO,GAAE;IAAE,GAAG,CAAC,EAAE,OAAO,CAAA;CAAO,GAC9B,OAAO,CAAC,IAAI,CAAC,CAkNf;AAED;;;GAGG;AACH,wBAAsB,oBAAoB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAejF"}