polyv-live-cli 1.1.5 → 1.1.8

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 (121) hide show
  1. package/dist/commands/account.commands.d.ts +3 -0
  2. package/dist/commands/account.commands.d.ts.map +1 -0
  3. package/dist/commands/account.commands.js +386 -0
  4. package/dist/commands/account.commands.js.map +1 -0
  5. package/dist/commands/channel.commands.d.ts.map +1 -1
  6. package/dist/commands/channel.commands.js +84 -60
  7. package/dist/commands/channel.commands.js.map +1 -1
  8. package/dist/commands/index.d.ts +2 -0
  9. package/dist/commands/index.d.ts.map +1 -1
  10. package/dist/commands/index.js +5 -1
  11. package/dist/commands/index.js.map +1 -1
  12. package/dist/commands/stream.commands.d.ts.map +1 -1
  13. package/dist/commands/stream.commands.js +141 -63
  14. package/dist/commands/stream.commands.js.map +1 -1
  15. package/dist/commands/use.commands.d.ts +9 -0
  16. package/dist/commands/use.commands.d.ts.map +1 -0
  17. package/dist/commands/use.commands.js +66 -0
  18. package/dist/commands/use.commands.js.map +1 -0
  19. package/dist/components/alert.panel.d.ts.map +1 -1
  20. package/dist/components/alert.panel.js +3 -2
  21. package/dist/components/alert.panel.js.map +1 -1
  22. package/dist/components/index.d.ts +2 -1
  23. package/dist/components/index.d.ts.map +1 -1
  24. package/dist/components/index.js.map +1 -1
  25. package/dist/config/account-config.d.ts +27 -0
  26. package/dist/config/account-config.d.ts.map +1 -0
  27. package/dist/config/account-config.js +358 -0
  28. package/dist/config/account-config.js.map +1 -0
  29. package/dist/config/account-crypto.d.ts +17 -0
  30. package/dist/config/account-crypto.d.ts.map +1 -0
  31. package/dist/config/account-crypto.js +129 -0
  32. package/dist/config/account-crypto.js.map +1 -0
  33. package/dist/config/account-encryption.d.ts +35 -0
  34. package/dist/config/account-encryption.d.ts.map +1 -0
  35. package/dist/config/account-encryption.js +207 -0
  36. package/dist/config/account-encryption.js.map +1 -0
  37. package/dist/config/auth-adapter.d.ts +23 -0
  38. package/dist/config/auth-adapter.d.ts.map +1 -0
  39. package/dist/config/auth-adapter.js +49 -0
  40. package/dist/config/auth-adapter.js.map +1 -0
  41. package/dist/config/auth-provider.d.ts +27 -0
  42. package/dist/config/auth-provider.d.ts.map +1 -0
  43. package/dist/config/auth-provider.js +54 -0
  44. package/dist/config/auth-provider.js.map +1 -0
  45. package/dist/config/auth-source-manager.d.ts +61 -0
  46. package/dist/config/auth-source-manager.d.ts.map +1 -0
  47. package/dist/config/auth-source-manager.js +402 -0
  48. package/dist/config/auth-source-manager.js.map +1 -0
  49. package/dist/config/config-recovery-manager.d.ts +67 -0
  50. package/dist/config/config-recovery-manager.d.ts.map +1 -0
  51. package/dist/config/config-recovery-manager.js +593 -0
  52. package/dist/config/config-recovery-manager.js.map +1 -0
  53. package/dist/config/config-version-manager.d.ts +44 -0
  54. package/dist/config/config-version-manager.d.ts.map +1 -0
  55. package/dist/config/config-version-manager.js +319 -0
  56. package/dist/config/config-version-manager.js.map +1 -0
  57. package/dist/config/file-permission-manager.d.ts +41 -0
  58. package/dist/config/file-permission-manager.d.ts.map +1 -0
  59. package/dist/config/file-permission-manager.js +290 -0
  60. package/dist/config/file-permission-manager.js.map +1 -0
  61. package/dist/config/layout-manager.d.ts.map +1 -1
  62. package/dist/config/layout-manager.js +2 -1
  63. package/dist/config/layout-manager.js.map +1 -1
  64. package/dist/config/secure-account-manager.d.ts +54 -0
  65. package/dist/config/secure-account-manager.d.ts.map +1 -0
  66. package/dist/config/secure-account-manager.js +438 -0
  67. package/dist/config/secure-account-manager.js.map +1 -0
  68. package/dist/config/session-state.d.ts +37 -0
  69. package/dist/config/session-state.d.ts.map +1 -0
  70. package/dist/config/session-state.js +207 -0
  71. package/dist/config/session-state.js.map +1 -0
  72. package/dist/config/session-storage.d.ts +21 -0
  73. package/dist/config/session-storage.d.ts.map +1 -0
  74. package/dist/config/session-storage.js +235 -0
  75. package/dist/config/session-storage.js.map +1 -0
  76. package/dist/config/theme-manager.d.ts.map +1 -1
  77. package/dist/config/theme-manager.js +2 -1
  78. package/dist/config/theme-manager.js.map +1 -1
  79. package/dist/handlers/stream.handler.d.ts.map +1 -1
  80. package/dist/handlers/stream.handler.js +6 -0
  81. package/dist/handlers/stream.handler.js.map +1 -1
  82. package/dist/handlers/use.handler.d.ts +13 -0
  83. package/dist/handlers/use.handler.d.ts.map +1 -0
  84. package/dist/handlers/use.handler.js +118 -0
  85. package/dist/handlers/use.handler.js.map +1 -0
  86. package/dist/index.d.ts.map +1 -1
  87. package/dist/index.js +19 -12
  88. package/dist/index.js.map +1 -1
  89. package/dist/performance/batch-request-manager.d.ts +1 -0
  90. package/dist/performance/batch-request-manager.d.ts.map +1 -1
  91. package/dist/performance/batch-request-manager.js +7 -3
  92. package/dist/performance/batch-request-manager.js.map +1 -1
  93. package/dist/performance/change-detector.d.ts.map +1 -1
  94. package/dist/performance/change-detector.js +32 -3
  95. package/dist/performance/change-detector.js.map +1 -1
  96. package/dist/performance/error-recovery-manager.d.ts.map +1 -1
  97. package/dist/performance/error-recovery-manager.js +2 -2
  98. package/dist/performance/error-recovery-manager.js.map +1 -1
  99. package/dist/performance/index.d.ts +24 -12
  100. package/dist/performance/index.d.ts.map +1 -1
  101. package/dist/performance/index.js.map +1 -1
  102. package/dist/services/index.d.ts +4 -2
  103. package/dist/services/index.d.ts.map +1 -1
  104. package/dist/services/index.js.map +1 -1
  105. package/dist/types/account.types.d.ts +79 -0
  106. package/dist/types/account.types.d.ts.map +1 -0
  107. package/dist/types/account.types.js +23 -0
  108. package/dist/types/account.types.js.map +1 -0
  109. package/dist/types/auth-source.types.d.ts +62 -0
  110. package/dist/types/auth-source.types.d.ts.map +1 -0
  111. package/dist/types/auth-source.types.js +25 -0
  112. package/dist/types/auth-source.types.js.map +1 -0
  113. package/dist/types/session.types.d.ts +43 -0
  114. package/dist/types/session.types.d.ts.map +1 -0
  115. package/dist/types/session.types.js +27 -0
  116. package/dist/types/session.types.js.map +1 -0
  117. package/dist/utils/auth-diagnostics.d.ts +47 -0
  118. package/dist/utils/auth-diagnostics.d.ts.map +1 -0
  119. package/dist/utils/auth-diagnostics.js +245 -0
  120. package/dist/utils/auth-diagnostics.js.map +1 -0
  121. package/package.json +19 -7
@@ -0,0 +1,319 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.defaultConfigVersionManager = exports.ConfigVersionManager = exports.MINIMUM_SUPPORTED_VERSION = exports.CURRENT_VERSION = void 0;
4
+ const SUPPORTED_VERSIONS = {
5
+ '1.0': {
6
+ version: '1.0',
7
+ description: 'Initial secure configuration format with AES-256-GCM encryption',
8
+ features: [
9
+ 'AES-256-GCM encryption for appSecret',
10
+ 'File permission management',
11
+ 'Account metadata tracking',
12
+ 'Environment variable key support'
13
+ ],
14
+ breakingChanges: []
15
+ },
16
+ '0.9': {
17
+ version: '0.9',
18
+ description: 'Legacy format with basic encryption (migration target)',
19
+ features: [
20
+ 'Basic AES-256-CBC encryption',
21
+ 'Simple account storage'
22
+ ],
23
+ breakingChanges: []
24
+ },
25
+ '0.8': {
26
+ version: '0.8',
27
+ description: 'Pre-encryption format (plain text storage)',
28
+ features: [
29
+ 'Plain text account storage',
30
+ 'Basic metadata'
31
+ ],
32
+ breakingChanges: []
33
+ }
34
+ };
35
+ exports.CURRENT_VERSION = '1.0';
36
+ exports.MINIMUM_SUPPORTED_VERSION = '0.8';
37
+ class ConfigVersionManager {
38
+ getCurrentVersion() {
39
+ return exports.CURRENT_VERSION;
40
+ }
41
+ getSupportedVersions() {
42
+ return Object.values(SUPPORTED_VERSIONS);
43
+ }
44
+ isVersionSupported(version) {
45
+ return version in SUPPORTED_VERSIONS;
46
+ }
47
+ getVersionInfo(version) {
48
+ return SUPPORTED_VERSIONS[version] || null;
49
+ }
50
+ compareVersions(version1, version2) {
51
+ const v1Parts = version1.split('.').map(Number);
52
+ const v2Parts = version2.split('.').map(Number);
53
+ const maxLength = Math.max(v1Parts.length, v2Parts.length);
54
+ for (let i = 0; i < maxLength; i++) {
55
+ const v1Part = v1Parts[i] || 0;
56
+ const v2Part = v2Parts[i] || 0;
57
+ if (v1Part < v2Part)
58
+ return -1;
59
+ if (v1Part > v2Part)
60
+ return 1;
61
+ }
62
+ return 0;
63
+ }
64
+ detectVersion(config) {
65
+ if (!config || typeof config !== 'object') {
66
+ throw new Error('Invalid configuration object');
67
+ }
68
+ const configObj = config;
69
+ if (configObj['version'] && typeof configObj['version'] === 'string') {
70
+ return configObj['version'];
71
+ }
72
+ if (configObj['accounts'] && configObj['metadata']) {
73
+ const accounts = configObj['accounts'];
74
+ const firstAccount = Object.values(accounts)[0];
75
+ if (firstAccount && typeof firstAccount.appSecret === 'object') {
76
+ return '1.0';
77
+ }
78
+ else if (firstAccount && typeof firstAccount.appSecret === 'string') {
79
+ try {
80
+ const decoded = Buffer.from(firstAccount.appSecret, 'base64').toString('utf8');
81
+ const parsed = JSON.parse(decoded);
82
+ if (parsed.data && parsed.meta) {
83
+ return '0.9';
84
+ }
85
+ }
86
+ catch {
87
+ return '0.8';
88
+ }
89
+ }
90
+ }
91
+ return exports.MINIMUM_SUPPORTED_VERSION;
92
+ }
93
+ validateVersion(config) {
94
+ try {
95
+ const detectedVersion = this.detectVersion(config);
96
+ const currentVersion = this.getCurrentVersion();
97
+ if (!this.isVersionSupported(detectedVersion)) {
98
+ return {
99
+ isValid: false,
100
+ message: `Unsupported configuration version: ${detectedVersion}`,
101
+ detectedVersion,
102
+ compatibility: 'incompatible',
103
+ requiredActions: [
104
+ 'Configuration version is not supported',
105
+ 'Please create a new configuration or contact support'
106
+ ]
107
+ };
108
+ }
109
+ const comparison = this.compareVersions(detectedVersion, currentVersion);
110
+ if (comparison === 0) {
111
+ return {
112
+ isValid: true,
113
+ message: `Configuration is using current version: ${detectedVersion}`,
114
+ detectedVersion,
115
+ compatibility: 'compatible',
116
+ requiredActions: []
117
+ };
118
+ }
119
+ else if (comparison < 0) {
120
+ return {
121
+ isValid: true,
122
+ message: `Configuration is using older version: ${detectedVersion}. Migration is available.`,
123
+ detectedVersion,
124
+ compatibility: 'upgradeable',
125
+ requiredActions: [
126
+ `Run: polyv-cli config migrate --from ${detectedVersion} --to ${currentVersion}`,
127
+ 'Backup your configuration before migration'
128
+ ]
129
+ };
130
+ }
131
+ else {
132
+ return {
133
+ isValid: false,
134
+ message: `Configuration is using newer version: ${detectedVersion}. Please update the CLI.`,
135
+ detectedVersion,
136
+ compatibility: 'incompatible',
137
+ requiredActions: [
138
+ 'Update PolyV CLI to the latest version',
139
+ 'Check for CLI updates: npm update -g polyv-live-cli'
140
+ ]
141
+ };
142
+ }
143
+ }
144
+ catch (error) {
145
+ return {
146
+ isValid: false,
147
+ message: `Failed to validate version: ${error instanceof Error ? error.message : 'Unknown error'}`,
148
+ compatibility: 'incompatible',
149
+ requiredActions: [
150
+ 'Check configuration file format',
151
+ 'Verify file is not corrupted'
152
+ ]
153
+ };
154
+ }
155
+ }
156
+ migrateConfiguration(config, fromVersion, toVersion) {
157
+ const steps = [];
158
+ const warnings = [];
159
+ try {
160
+ if (!this.isVersionSupported(fromVersion)) {
161
+ return {
162
+ success: false,
163
+ message: `Source version ${fromVersion} is not supported`,
164
+ fromVersion,
165
+ toVersion,
166
+ steps: [],
167
+ warnings: []
168
+ };
169
+ }
170
+ if (!this.isVersionSupported(toVersion)) {
171
+ return {
172
+ success: false,
173
+ message: `Target version ${toVersion} is not supported`,
174
+ fromVersion,
175
+ toVersion,
176
+ steps: [],
177
+ warnings: []
178
+ };
179
+ }
180
+ if (fromVersion === toVersion) {
181
+ return {
182
+ success: true,
183
+ message: 'No migration needed - versions are the same',
184
+ fromVersion,
185
+ toVersion,
186
+ steps: ['No migration required'],
187
+ warnings: [],
188
+ migratedConfig: config
189
+ };
190
+ }
191
+ let migratedConfig = this.deepClone(config);
192
+ if (fromVersion === '0.8' && this.compareVersions(toVersion, '0.9') >= 0) {
193
+ migratedConfig = this.migrateFrom08To09(migratedConfig);
194
+ steps.push('Migrated from v0.8 to v0.9: Added basic encryption');
195
+ warnings.push('App secrets have been encrypted using basic encryption');
196
+ }
197
+ if ((fromVersion === '0.8' || fromVersion === '0.9') && toVersion === '1.0') {
198
+ migratedConfig = this.migrateFrom09To10(migratedConfig);
199
+ steps.push('Migrated from v0.9 to v1.0: Upgraded to AES-256-GCM encryption');
200
+ warnings.push('Encryption has been upgraded to AES-256-GCM for better security');
201
+ }
202
+ if (typeof migratedConfig === 'object' && migratedConfig !== null) {
203
+ migratedConfig.version = toVersion;
204
+ steps.push(`Set configuration version to ${toVersion}`);
205
+ }
206
+ return {
207
+ success: true,
208
+ message: `Successfully migrated configuration from ${fromVersion} to ${toVersion}`,
209
+ fromVersion,
210
+ toVersion,
211
+ steps,
212
+ warnings,
213
+ migratedConfig: migratedConfig
214
+ };
215
+ }
216
+ catch (error) {
217
+ return {
218
+ success: false,
219
+ message: `Migration failed: ${error instanceof Error ? error.message : 'Unknown error'}`,
220
+ fromVersion,
221
+ toVersion,
222
+ steps,
223
+ warnings
224
+ };
225
+ }
226
+ }
227
+ migrateFrom08To09(config) {
228
+ if (!config.accounts) {
229
+ return config;
230
+ }
231
+ for (const accountName in config.accounts) {
232
+ const account = config.accounts[accountName];
233
+ if (typeof account.appSecret === 'string' && !account.appSecret.includes('base64')) {
234
+ account._needsEncryption = true;
235
+ }
236
+ }
237
+ config.version = '0.9';
238
+ return config;
239
+ }
240
+ migrateFrom09To10(config) {
241
+ if (!config.accounts) {
242
+ return config;
243
+ }
244
+ if (!config.metadata) {
245
+ const now = new Date().toISOString();
246
+ config.metadata = {
247
+ createdAt: now,
248
+ updatedAt: now
249
+ };
250
+ }
251
+ for (const accountName in config.accounts) {
252
+ const account = config.accounts[accountName];
253
+ account._needsReencryption = true;
254
+ }
255
+ config.version = '1.0';
256
+ return config;
257
+ }
258
+ getMigrationPath(fromVersion, toVersion) {
259
+ if (fromVersion === toVersion) {
260
+ return [];
261
+ }
262
+ const path = [];
263
+ if (fromVersion === '0.8' && toVersion === '0.9') {
264
+ path.push('0.8 → 0.9: Encrypt plain text secrets');
265
+ }
266
+ else if (fromVersion === '0.9' && toVersion === '1.0') {
267
+ path.push('0.9 → 1.0: Upgrade to AES-256-GCM encryption');
268
+ }
269
+ else if (fromVersion === '0.8' && toVersion === '1.0') {
270
+ path.push('0.8 → 0.9: Encrypt plain text secrets');
271
+ path.push('0.9 → 1.0: Upgrade to AES-256-GCM encryption');
272
+ }
273
+ return path;
274
+ }
275
+ createNewConfiguration() {
276
+ const now = new Date().toISOString();
277
+ return {
278
+ version: this.getCurrentVersion(),
279
+ accounts: {},
280
+ metadata: {
281
+ createdAt: now,
282
+ updatedAt: now
283
+ }
284
+ };
285
+ }
286
+ deepClone(obj) {
287
+ return JSON.parse(JSON.stringify(obj));
288
+ }
289
+ isMigrationRequired(config) {
290
+ try {
291
+ const detectedVersion = this.detectVersion(config);
292
+ const currentVersion = this.getCurrentVersion();
293
+ return this.compareVersions(detectedVersion, currentVersion) < 0;
294
+ }
295
+ catch {
296
+ return false;
297
+ }
298
+ }
299
+ getBreakingChanges(fromVersion, toVersion) {
300
+ const changes = [];
301
+ const versions = Object.keys(SUPPORTED_VERSIONS).sort(this.compareVersions.bind(this));
302
+ const fromIndex = versions.indexOf(fromVersion);
303
+ const toIndex = versions.indexOf(toVersion);
304
+ if (fromIndex === -1 || toIndex === -1 || fromIndex >= toIndex) {
305
+ return changes;
306
+ }
307
+ for (let i = fromIndex + 1; i <= toIndex; i++) {
308
+ const version = versions[i];
309
+ if (version && SUPPORTED_VERSIONS[version]) {
310
+ const versionInfo = SUPPORTED_VERSIONS[version];
311
+ changes.push(...versionInfo.breakingChanges);
312
+ }
313
+ }
314
+ return changes;
315
+ }
316
+ }
317
+ exports.ConfigVersionManager = ConfigVersionManager;
318
+ exports.defaultConfigVersionManager = new ConfigVersionManager();
319
+ //# sourceMappingURL=config-version-manager.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config-version-manager.js","sourceRoot":"","sources":["../../src/config/config-version-manager.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,41 @@
1
+ export interface FilePermissionInfo {
2
+ path: string;
3
+ mode: number;
4
+ isSecure: boolean;
5
+ description: string;
6
+ warnings: string[];
7
+ }
8
+ export interface PermissionValidationResult {
9
+ isValid: boolean;
10
+ message: string;
11
+ recommendations: string[];
12
+ permissionInfo?: FilePermissionInfo;
13
+ }
14
+ export interface PermissionRepairResult {
15
+ success: boolean;
16
+ message: string;
17
+ before?: FilePermissionInfo;
18
+ after?: FilePermissionInfo;
19
+ }
20
+ export declare class FilePermissionManager {
21
+ private readonly platform;
22
+ constructor();
23
+ private supportsUnixPermissions;
24
+ getPermissionInfo(filePath: string): FilePermissionInfo;
25
+ private isPermissionSecure;
26
+ private describePermissions;
27
+ private formatPermissionGroup;
28
+ private generatePermissionWarnings;
29
+ validatePermissions(filePath: string): PermissionValidationResult;
30
+ setSecurePermissions(filePath: string, isDirectory?: boolean): PermissionRepairResult;
31
+ ensureSecureDirectory(dirPath: string): PermissionRepairResult;
32
+ repairConfigurationFile(filePath: string): PermissionRepairResult;
33
+ detectPotentialTampering(filePath: string): {
34
+ isTampered: boolean;
35
+ reasons: string[];
36
+ recommendations: string[];
37
+ };
38
+ getSecurityRecommendations(): string[];
39
+ }
40
+ export declare const defaultFilePermissionManager: FilePermissionManager;
41
+ //# sourceMappingURL=file-permission-manager.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"file-permission-manager.d.ts","sourceRoot":"","sources":["../../src/config/file-permission-manager.ts"],"names":[],"mappings":"AAqBA,MAAM,WAAW,kBAAkB;IAEjC,IAAI,EAAE,MAAM,CAAC;IAEb,IAAI,EAAE,MAAM,CAAC;IAEb,QAAQ,EAAE,OAAO,CAAC;IAElB,WAAW,EAAE,MAAM,CAAC;IAEpB,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAKD,MAAM,WAAW,0BAA0B;IAEzC,OAAO,EAAE,OAAO,CAAC;IAEjB,OAAO,EAAE,MAAM,CAAC;IAEhB,eAAe,EAAE,MAAM,EAAE,CAAC;IAE1B,cAAc,CAAC,EAAE,kBAAkB,CAAC;CACrC;AAKD,MAAM,WAAW,sBAAsB;IAErC,OAAO,EAAE,OAAO,CAAC;IAEjB,OAAO,EAAE,MAAM,CAAC;IAEhB,MAAM,CAAC,EAAE,kBAAkB,CAAC;IAE5B,KAAK,CAAC,EAAE,kBAAkB,CAAC;CAC5B;AAeD,qBAAa,qBAAqB;IAChC,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAkB;;IAa3C,OAAO,CAAC,uBAAuB;IASxB,iBAAiB,CAAC,QAAQ,EAAE,MAAM,GAAG,kBAAkB;IAwB9D,OAAO,CAAC,kBAAkB;IAiB1B,OAAO,CAAC,mBAAmB;IAiB3B,OAAO,CAAC,qBAAqB;IAa7B,OAAO,CAAC,0BAA0B;IAqC3B,mBAAmB,CAAC,QAAQ,EAAE,MAAM,GAAG,0BAA0B;IAkDjE,oBAAoB,CAAC,QAAQ,EAAE,MAAM,EAAE,WAAW,GAAE,OAAe,GAAG,sBAAsB;IA+C5F,qBAAqB,CAAC,OAAO,EAAE,MAAM,GAAG,sBAAsB;IA0B9D,uBAAuB,CAAC,QAAQ,EAAE,MAAM,GAAG,sBAAsB;IAmCjE,wBAAwB,CAAC,QAAQ,EAAE,MAAM,GAAG;QACjD,UAAU,EAAE,OAAO,CAAC;QACpB,OAAO,EAAE,MAAM,EAAE,CAAC;QAClB,eAAe,EAAE,MAAM,EAAE,CAAC;KAC3B;IAwDM,0BAA0B,IAAI,MAAM,EAAE;CAuB9C;AAKD,eAAO,MAAM,4BAA4B,uBAA8B,CAAC"}
@@ -0,0 +1,290 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ exports.defaultFilePermissionManager = exports.FilePermissionManager = void 0;
37
+ const fs = __importStar(require("fs"));
38
+ const path = __importStar(require("path"));
39
+ const os = __importStar(require("os"));
40
+ const SECURE_PERMISSIONS = {
41
+ OWNER_RW: 0o600,
42
+ OWNER_RWX: 0o700
43
+ };
44
+ class FilePermissionManager {
45
+ constructor() {
46
+ this.platform = os.platform();
47
+ }
48
+ supportsUnixPermissions() {
49
+ return this.platform !== 'win32';
50
+ }
51
+ getPermissionInfo(filePath) {
52
+ try {
53
+ const stats = fs.statSync(filePath);
54
+ const mode = stats.mode & parseInt('777', 8);
55
+ const isSecure = this.isPermissionSecure(mode, stats.isDirectory());
56
+ return {
57
+ path: filePath,
58
+ mode,
59
+ isSecure,
60
+ description: this.describePermissions(mode),
61
+ warnings: this.generatePermissionWarnings(mode, stats.isDirectory())
62
+ };
63
+ }
64
+ catch (error) {
65
+ throw new Error(`Failed to get permission info for ${filePath}: ${error instanceof Error ? error.message : 'Unknown error'}`);
66
+ }
67
+ }
68
+ isPermissionSecure(mode, isDirectory) {
69
+ if (!this.supportsUnixPermissions()) {
70
+ return true;
71
+ }
72
+ const expectedMode = isDirectory ? SECURE_PERMISSIONS.OWNER_RWX : SECURE_PERMISSIONS.OWNER_RW;
73
+ return mode === expectedMode;
74
+ }
75
+ describePermissions(mode) {
76
+ if (!this.supportsUnixPermissions()) {
77
+ return 'Windows NTFS permissions (managed by system)';
78
+ }
79
+ const owner = this.formatPermissionGroup((mode >> 6) & 7);
80
+ const group = this.formatPermissionGroup((mode >> 3) & 7);
81
+ const others = this.formatPermissionGroup(mode & 7);
82
+ return `Owner: ${owner}, Group: ${group}, Others: ${others} (${mode.toString(8)})`;
83
+ }
84
+ formatPermissionGroup(perms) {
85
+ const read = (perms & 4) ? 'r' : '-';
86
+ const write = (perms & 2) ? 'w' : '-';
87
+ const execute = (perms & 1) ? 'x' : '-';
88
+ return `${read}${write}${execute}`;
89
+ }
90
+ generatePermissionWarnings(mode, _isDirectory) {
91
+ const warnings = [];
92
+ if (!this.supportsUnixPermissions()) {
93
+ return warnings;
94
+ }
95
+ const groupPerms = (mode >> 3) & 7;
96
+ if (groupPerms > 0) {
97
+ warnings.push('Group has access permissions - configuration file should be accessible only by owner');
98
+ }
99
+ const otherPerms = mode & 7;
100
+ if (otherPerms > 0) {
101
+ warnings.push('Others have access permissions - configuration file should be accessible only by owner');
102
+ }
103
+ if (otherPerms & 4) {
104
+ warnings.push('SECURITY RISK: Configuration file is world-readable');
105
+ }
106
+ if (otherPerms & 2) {
107
+ warnings.push('CRITICAL SECURITY RISK: Configuration file is world-writable');
108
+ }
109
+ return warnings;
110
+ }
111
+ validatePermissions(filePath) {
112
+ try {
113
+ if (!fs.existsSync(filePath)) {
114
+ return {
115
+ isValid: false,
116
+ message: `File does not exist: ${filePath}`,
117
+ recommendations: ['Create the configuration file first']
118
+ };
119
+ }
120
+ const permissionInfo = this.getPermissionInfo(filePath);
121
+ const recommendations = [];
122
+ if (!permissionInfo.isSecure) {
123
+ if (this.supportsUnixPermissions()) {
124
+ recommendations.push(`Run: chmod 600 ${filePath}`);
125
+ recommendations.push('Or use: polyv-cli config fix-permissions');
126
+ }
127
+ else {
128
+ recommendations.push('Ensure only your user account has access to the configuration file');
129
+ recommendations.push('Check Windows file properties and remove other users\' access');
130
+ }
131
+ }
132
+ if (permissionInfo.warnings.length > 0) {
133
+ recommendations.push('Review and fix permission warnings above');
134
+ }
135
+ return {
136
+ isValid: permissionInfo.isSecure && permissionInfo.warnings.length === 0,
137
+ message: permissionInfo.isSecure
138
+ ? 'File permissions are secure'
139
+ : 'File permissions are not secure - configuration file should only be accessible by owner',
140
+ recommendations,
141
+ permissionInfo
142
+ };
143
+ }
144
+ catch (error) {
145
+ return {
146
+ isValid: false,
147
+ message: `Failed to validate permissions: ${error instanceof Error ? error.message : 'Unknown error'}`,
148
+ recommendations: ['Check if file exists and is accessible']
149
+ };
150
+ }
151
+ }
152
+ setSecurePermissions(filePath, isDirectory = false) {
153
+ try {
154
+ if (!fs.existsSync(filePath)) {
155
+ return {
156
+ success: false,
157
+ message: `Cannot set permissions: File does not exist: ${filePath}`
158
+ };
159
+ }
160
+ const before = this.getPermissionInfo(filePath);
161
+ if (!this.supportsUnixPermissions()) {
162
+ return {
163
+ success: true,
164
+ message: 'Windows NTFS permissions are managed by the system. Ensure only your user account has access.',
165
+ before,
166
+ after: before
167
+ };
168
+ }
169
+ const targetMode = isDirectory ? SECURE_PERMISSIONS.OWNER_RWX : SECURE_PERMISSIONS.OWNER_RW;
170
+ fs.chmodSync(filePath, targetMode);
171
+ const after = this.getPermissionInfo(filePath);
172
+ return {
173
+ success: true,
174
+ message: `Successfully set secure permissions (${targetMode.toString(8)}) on ${filePath}`,
175
+ before,
176
+ after
177
+ };
178
+ }
179
+ catch (error) {
180
+ return {
181
+ success: false,
182
+ message: `Failed to set secure permissions: ${error instanceof Error ? error.message : 'Unknown error'}`
183
+ };
184
+ }
185
+ }
186
+ ensureSecureDirectory(dirPath) {
187
+ try {
188
+ if (!fs.existsSync(dirPath)) {
189
+ const parentDir = path.dirname(dirPath);
190
+ if (!fs.existsSync(parentDir)) {
191
+ fs.mkdirSync(parentDir, { recursive: true, mode: SECURE_PERMISSIONS.OWNER_RWX });
192
+ }
193
+ fs.mkdirSync(dirPath, { mode: SECURE_PERMISSIONS.OWNER_RWX });
194
+ }
195
+ return this.setSecurePermissions(dirPath, true);
196
+ }
197
+ catch (error) {
198
+ return {
199
+ success: false,
200
+ message: `Failed to ensure secure directory: ${error instanceof Error ? error.message : 'Unknown error'}`
201
+ };
202
+ }
203
+ }
204
+ repairConfigurationFile(filePath) {
205
+ try {
206
+ const dirPath = path.dirname(filePath);
207
+ const dirResult = this.ensureSecureDirectory(dirPath);
208
+ if (!dirResult.success) {
209
+ return {
210
+ success: false,
211
+ message: `Failed to secure parent directory: ${dirResult.message}`
212
+ };
213
+ }
214
+ if (fs.existsSync(filePath)) {
215
+ return this.setSecurePermissions(filePath, false);
216
+ }
217
+ else {
218
+ return {
219
+ success: true,
220
+ message: `Parent directory secured. Configuration file ${filePath} will be created with secure permissions.`
221
+ };
222
+ }
223
+ }
224
+ catch (error) {
225
+ return {
226
+ success: false,
227
+ message: `Failed to repair configuration file permissions: ${error instanceof Error ? error.message : 'Unknown error'}`
228
+ };
229
+ }
230
+ }
231
+ detectPotentialTampering(filePath) {
232
+ const reasons = [];
233
+ const recommendations = [];
234
+ try {
235
+ if (!fs.existsSync(filePath)) {
236
+ return {
237
+ isTampered: false,
238
+ reasons: ['File does not exist'],
239
+ recommendations: ['Create configuration file if needed']
240
+ };
241
+ }
242
+ const permissionInfo = this.getPermissionInfo(filePath);
243
+ if (permissionInfo.warnings.length > 0) {
244
+ reasons.push('Insecure file permissions detected');
245
+ reasons.push(...permissionInfo.warnings);
246
+ recommendations.push('Run permission repair: polyv-cli config fix-permissions');
247
+ }
248
+ if (this.supportsUnixPermissions()) {
249
+ const mode = permissionInfo.mode;
250
+ if (mode & 2) {
251
+ reasons.push('File is world-writable - possible tampering risk');
252
+ recommendations.push('Immediately secure the file with: chmod 600 ' + filePath);
253
+ }
254
+ if (mode & 0o020) {
255
+ reasons.push('File is group-writable - possible unauthorized access');
256
+ recommendations.push('Remove group write access');
257
+ }
258
+ }
259
+ return {
260
+ isTampered: reasons.length > 0,
261
+ reasons,
262
+ recommendations
263
+ };
264
+ }
265
+ catch (error) {
266
+ return {
267
+ isTampered: true,
268
+ reasons: [`Error checking file permissions: ${error instanceof Error ? error.message : 'Unknown error'}`],
269
+ recommendations: ['Verify file exists and is accessible']
270
+ };
271
+ }
272
+ }
273
+ getSecurityRecommendations() {
274
+ const recommendations = [
275
+ 'Keep your configuration file in a secure location',
276
+ 'Regularly backup your configuration file',
277
+ 'Use the POLYV_MASTER_KEY environment variable for additional security'
278
+ ];
279
+ if (this.supportsUnixPermissions()) {
280
+ recommendations.push('Ensure configuration file permissions are set to 600 (owner read/write only)', 'Configuration directory permissions should be 700 (owner access only)', 'Use "ls -la" to check file permissions');
281
+ }
282
+ else {
283
+ recommendations.push('On Windows, ensure only your user account has access to the configuration file', 'Use Windows file properties to review and manage access permissions', 'Consider using Windows folder encryption for additional security');
284
+ }
285
+ return recommendations;
286
+ }
287
+ }
288
+ exports.FilePermissionManager = FilePermissionManager;
289
+ exports.defaultFilePermissionManager = new FilePermissionManager();
290
+ //# sourceMappingURL=file-permission-manager.js.map