appwrite-utils-cli 1.11.0 → 1.12.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 (250) hide show
  1. package/{src/adapters/index.ts → dist/adapters/index.d.ts} +0 -1
  2. package/dist/adapters/index.js +10 -0
  3. package/dist/backups/operations/bucketBackup.d.ts +19 -0
  4. package/dist/backups/operations/bucketBackup.js +197 -0
  5. package/dist/backups/operations/collectionBackup.d.ts +30 -0
  6. package/dist/backups/operations/collectionBackup.js +201 -0
  7. package/dist/backups/operations/comprehensiveBackup.d.ts +25 -0
  8. package/dist/backups/operations/comprehensiveBackup.js +238 -0
  9. package/dist/backups/schemas/bucketManifest.d.ts +93 -0
  10. package/dist/backups/schemas/bucketManifest.js +33 -0
  11. package/dist/backups/schemas/comprehensiveManifest.d.ts +108 -0
  12. package/dist/backups/schemas/comprehensiveManifest.js +32 -0
  13. package/dist/backups/tracking/centralizedTracking.d.ts +34 -0
  14. package/dist/backups/tracking/centralizedTracking.js +274 -0
  15. package/dist/cli/commands/configCommands.d.ts +8 -0
  16. package/dist/cli/commands/configCommands.js +210 -0
  17. package/dist/cli/commands/databaseCommands.d.ts +14 -0
  18. package/dist/cli/commands/databaseCommands.js +696 -0
  19. package/dist/cli/commands/functionCommands.d.ts +7 -0
  20. package/dist/cli/commands/functionCommands.js +330 -0
  21. package/dist/cli/commands/importFileCommands.d.ts +7 -0
  22. package/dist/cli/commands/importFileCommands.js +674 -0
  23. package/dist/cli/commands/schemaCommands.d.ts +7 -0
  24. package/dist/cli/commands/schemaCommands.js +169 -0
  25. package/dist/cli/commands/storageCommands.d.ts +5 -0
  26. package/dist/cli/commands/storageCommands.js +142 -0
  27. package/dist/cli/commands/transferCommands.d.ts +5 -0
  28. package/dist/cli/commands/transferCommands.js +382 -0
  29. package/dist/collections/columns.d.ts +13 -0
  30. package/dist/collections/columns.js +1339 -0
  31. package/dist/collections/indexes.d.ts +12 -0
  32. package/dist/collections/indexes.js +215 -0
  33. package/dist/collections/methods.d.ts +19 -0
  34. package/dist/collections/methods.js +605 -0
  35. package/dist/collections/tableOperations.d.ts +87 -0
  36. package/dist/collections/tableOperations.js +466 -0
  37. package/dist/collections/transferOperations.d.ts +8 -0
  38. package/dist/collections/transferOperations.js +411 -0
  39. package/dist/collections/wipeOperations.d.ts +17 -0
  40. package/dist/collections/wipeOperations.js +306 -0
  41. package/dist/databases/methods.d.ts +6 -0
  42. package/dist/databases/methods.js +35 -0
  43. package/dist/databases/setup.d.ts +5 -0
  44. package/dist/databases/setup.js +45 -0
  45. package/dist/examples/yamlTerminologyExample.d.ts +42 -0
  46. package/dist/examples/yamlTerminologyExample.js +272 -0
  47. package/dist/functions/deployments.d.ts +4 -0
  48. package/dist/functions/deployments.js +146 -0
  49. package/dist/functions/fnConfigDiscovery.d.ts +3 -0
  50. package/dist/functions/fnConfigDiscovery.js +108 -0
  51. package/dist/functions/methods.d.ts +16 -0
  52. package/dist/functions/methods.js +174 -0
  53. package/dist/init.d.ts +2 -0
  54. package/dist/init.js +57 -0
  55. package/dist/interactiveCLI.d.ts +36 -0
  56. package/dist/interactiveCLI.js +952 -0
  57. package/dist/main.d.ts +2 -0
  58. package/dist/main.js +1125 -0
  59. package/dist/migrations/afterImportActions.d.ts +17 -0
  60. package/dist/migrations/afterImportActions.js +305 -0
  61. package/dist/migrations/appwriteToX.d.ts +211 -0
  62. package/dist/migrations/appwriteToX.js +493 -0
  63. package/dist/migrations/comprehensiveTransfer.d.ts +147 -0
  64. package/dist/migrations/comprehensiveTransfer.js +1315 -0
  65. package/dist/migrations/dataLoader.d.ts +755 -0
  66. package/dist/migrations/dataLoader.js +1272 -0
  67. package/dist/migrations/importController.d.ts +25 -0
  68. package/dist/migrations/importController.js +283 -0
  69. package/dist/migrations/importDataActions.d.ts +50 -0
  70. package/dist/migrations/importDataActions.js +230 -0
  71. package/dist/migrations/relationships.d.ts +29 -0
  72. package/dist/migrations/relationships.js +203 -0
  73. package/dist/migrations/services/DataTransformationService.d.ts +55 -0
  74. package/dist/migrations/services/DataTransformationService.js +158 -0
  75. package/dist/migrations/services/FileHandlerService.d.ts +75 -0
  76. package/dist/migrations/services/FileHandlerService.js +236 -0
  77. package/dist/migrations/services/ImportOrchestrator.d.ts +99 -0
  78. package/dist/migrations/services/ImportOrchestrator.js +493 -0
  79. package/dist/migrations/services/RateLimitManager.d.ts +138 -0
  80. package/dist/migrations/services/RateLimitManager.js +279 -0
  81. package/dist/migrations/services/RelationshipResolver.d.ts +120 -0
  82. package/dist/migrations/services/RelationshipResolver.js +332 -0
  83. package/dist/migrations/services/UserMappingService.d.ts +109 -0
  84. package/dist/migrations/services/UserMappingService.js +277 -0
  85. package/dist/migrations/services/ValidationService.d.ts +74 -0
  86. package/dist/migrations/services/ValidationService.js +260 -0
  87. package/dist/migrations/transfer.d.ts +30 -0
  88. package/dist/migrations/transfer.js +661 -0
  89. package/dist/migrations/yaml/YamlImportConfigLoader.d.ts +131 -0
  90. package/dist/migrations/yaml/YamlImportConfigLoader.js +383 -0
  91. package/dist/migrations/yaml/YamlImportIntegration.d.ts +93 -0
  92. package/dist/migrations/yaml/YamlImportIntegration.js +341 -0
  93. package/dist/migrations/yaml/generateImportSchemas.d.ts +30 -0
  94. package/dist/migrations/yaml/generateImportSchemas.js +1327 -0
  95. package/dist/schemas/authUser.d.ts +24 -0
  96. package/dist/schemas/authUser.js +17 -0
  97. package/dist/setup.d.ts +2 -0
  98. package/{src/setup.ts → dist/setup.js} +0 -3
  99. package/dist/setupCommands.d.ts +58 -0
  100. package/dist/setupCommands.js +489 -0
  101. package/dist/setupController.d.ts +9 -0
  102. package/dist/setupController.js +34 -0
  103. package/dist/shared/backupMetadataSchema.d.ts +94 -0
  104. package/dist/shared/backupMetadataSchema.js +38 -0
  105. package/dist/shared/backupTracking.d.ts +18 -0
  106. package/dist/shared/backupTracking.js +176 -0
  107. package/dist/shared/confirmationDialogs.d.ts +75 -0
  108. package/dist/shared/confirmationDialogs.js +236 -0
  109. package/dist/shared/migrationHelpers.d.ts +61 -0
  110. package/dist/shared/migrationHelpers.js +145 -0
  111. package/{src/shared/operationLogger.ts → dist/shared/operationLogger.d.ts} +1 -11
  112. package/dist/shared/operationLogger.js +12 -0
  113. package/dist/shared/operationQueue.d.ts +40 -0
  114. package/dist/shared/operationQueue.js +310 -0
  115. package/dist/shared/operationsTable.d.ts +26 -0
  116. package/dist/shared/operationsTable.js +287 -0
  117. package/dist/shared/operationsTableSchema.d.ts +48 -0
  118. package/dist/shared/operationsTableSchema.js +35 -0
  119. package/dist/shared/progressManager.d.ts +62 -0
  120. package/dist/shared/progressManager.js +215 -0
  121. package/dist/shared/relationshipExtractor.d.ts +56 -0
  122. package/dist/shared/relationshipExtractor.js +138 -0
  123. package/dist/shared/selectionDialogs.d.ts +220 -0
  124. package/dist/shared/selectionDialogs.js +588 -0
  125. package/dist/storage/backupCompression.d.ts +20 -0
  126. package/dist/storage/backupCompression.js +67 -0
  127. package/dist/storage/methods.d.ts +44 -0
  128. package/dist/storage/methods.js +475 -0
  129. package/dist/storage/schemas.d.ts +842 -0
  130. package/dist/storage/schemas.js +175 -0
  131. package/dist/tables/indexManager.d.ts +65 -0
  132. package/dist/tables/indexManager.js +294 -0
  133. package/{src/types.ts → dist/types.d.ts} +1 -6
  134. package/dist/types.js +3 -0
  135. package/dist/users/methods.d.ts +16 -0
  136. package/dist/users/methods.js +276 -0
  137. package/dist/utils/configMigration.d.ts +1 -0
  138. package/dist/utils/configMigration.js +261 -0
  139. package/dist/utils/index.js +2 -0
  140. package/dist/utils/loadConfigs.d.ts +50 -0
  141. package/dist/utils/loadConfigs.js +357 -0
  142. package/dist/utils/setupFiles.d.ts +4 -0
  143. package/dist/utils/setupFiles.js +1190 -0
  144. package/dist/utilsController.d.ts +114 -0
  145. package/dist/utilsController.js +898 -0
  146. package/package.json +6 -3
  147. package/CHANGELOG.md +0 -35
  148. package/CONFIG_TODO.md +0 -1189
  149. package/SELECTION_DIALOGS.md +0 -146
  150. package/SERVICE_IMPLEMENTATION_REPORT.md +0 -462
  151. package/scripts/copy-templates.ts +0 -23
  152. package/src/backups/operations/bucketBackup.ts +0 -277
  153. package/src/backups/operations/collectionBackup.ts +0 -310
  154. package/src/backups/operations/comprehensiveBackup.ts +0 -342
  155. package/src/backups/schemas/bucketManifest.ts +0 -78
  156. package/src/backups/schemas/comprehensiveManifest.ts +0 -76
  157. package/src/backups/tracking/centralizedTracking.ts +0 -352
  158. package/src/cli/commands/configCommands.ts +0 -265
  159. package/src/cli/commands/databaseCommands.ts +0 -931
  160. package/src/cli/commands/functionCommands.ts +0 -419
  161. package/src/cli/commands/importFileCommands.ts +0 -815
  162. package/src/cli/commands/schemaCommands.ts +0 -200
  163. package/src/cli/commands/storageCommands.ts +0 -151
  164. package/src/cli/commands/transferCommands.ts +0 -454
  165. package/src/collections/attributes.ts.backup +0 -1555
  166. package/src/collections/columns.ts +0 -2025
  167. package/src/collections/indexes.ts +0 -350
  168. package/src/collections/methods.ts +0 -714
  169. package/src/collections/tableOperations.ts +0 -542
  170. package/src/collections/transferOperations.ts +0 -589
  171. package/src/collections/wipeOperations.ts +0 -449
  172. package/src/databases/methods.ts +0 -49
  173. package/src/databases/setup.ts +0 -77
  174. package/src/examples/yamlTerminologyExample.ts +0 -346
  175. package/src/functions/deployments.ts +0 -221
  176. package/src/functions/fnConfigDiscovery.ts +0 -103
  177. package/src/functions/methods.ts +0 -284
  178. package/src/init.ts +0 -62
  179. package/src/interactiveCLI.ts +0 -1201
  180. package/src/main.ts +0 -1517
  181. package/src/migrations/afterImportActions.ts +0 -579
  182. package/src/migrations/appwriteToX.ts +0 -668
  183. package/src/migrations/comprehensiveTransfer.ts +0 -2285
  184. package/src/migrations/dataLoader.ts +0 -1729
  185. package/src/migrations/importController.ts +0 -440
  186. package/src/migrations/importDataActions.ts +0 -315
  187. package/src/migrations/relationships.ts +0 -333
  188. package/src/migrations/services/DataTransformationService.ts +0 -196
  189. package/src/migrations/services/FileHandlerService.ts +0 -311
  190. package/src/migrations/services/ImportOrchestrator.ts +0 -675
  191. package/src/migrations/services/RateLimitManager.ts +0 -363
  192. package/src/migrations/services/RelationshipResolver.ts +0 -461
  193. package/src/migrations/services/UserMappingService.ts +0 -345
  194. package/src/migrations/services/ValidationService.ts +0 -349
  195. package/src/migrations/transfer.ts +0 -1113
  196. package/src/migrations/yaml/YamlImportConfigLoader.ts +0 -439
  197. package/src/migrations/yaml/YamlImportIntegration.ts +0 -446
  198. package/src/migrations/yaml/generateImportSchemas.ts +0 -1354
  199. package/src/schemas/authUser.ts +0 -23
  200. package/src/setupCommands.ts +0 -602
  201. package/src/setupController.ts +0 -43
  202. package/src/shared/backupMetadataSchema.ts +0 -93
  203. package/src/shared/backupTracking.ts +0 -211
  204. package/src/shared/confirmationDialogs.ts +0 -327
  205. package/src/shared/migrationHelpers.ts +0 -232
  206. package/src/shared/operationQueue.ts +0 -376
  207. package/src/shared/operationsTable.ts +0 -338
  208. package/src/shared/operationsTableSchema.ts +0 -60
  209. package/src/shared/progressManager.ts +0 -278
  210. package/src/shared/relationshipExtractor.ts +0 -214
  211. package/src/shared/selectionDialogs.ts +0 -802
  212. package/src/storage/backupCompression.ts +0 -88
  213. package/src/storage/methods.ts +0 -711
  214. package/src/storage/schemas.ts +0 -205
  215. package/src/tables/indexManager.ts +0 -409
  216. package/src/types/node-appwrite-tablesdb.d.ts +0 -44
  217. package/src/users/methods.ts +0 -358
  218. package/src/utils/configMigration.ts +0 -348
  219. package/src/utils/loadConfigs.ts +0 -457
  220. package/src/utils/setupFiles.ts +0 -1236
  221. package/src/utilsController.ts +0 -1263
  222. package/tests/README.md +0 -497
  223. package/tests/adapters/AdapterFactory.test.ts +0 -277
  224. package/tests/integration/syncOperations.test.ts +0 -463
  225. package/tests/jest.config.js +0 -25
  226. package/tests/migration/configMigration.test.ts +0 -546
  227. package/tests/setup.ts +0 -62
  228. package/tests/testUtils.ts +0 -340
  229. package/tests/utils/loadConfigs.test.ts +0 -350
  230. package/tests/validation/configValidation.test.ts +0 -412
  231. package/tsconfig.json +0 -44
  232. /package/{src → dist}/functions/templates/count-docs-in-collection/README.md +0 -0
  233. /package/{src → dist}/functions/templates/count-docs-in-collection/src/main.ts +0 -0
  234. /package/{src → dist}/functions/templates/count-docs-in-collection/src/request.ts +0 -0
  235. /package/{src → dist}/functions/templates/hono-typescript/README.md +0 -0
  236. /package/{src → dist}/functions/templates/hono-typescript/src/adapters/request.ts +0 -0
  237. /package/{src → dist}/functions/templates/hono-typescript/src/adapters/response.ts +0 -0
  238. /package/{src → dist}/functions/templates/hono-typescript/src/app.ts +0 -0
  239. /package/{src → dist}/functions/templates/hono-typescript/src/context.ts +0 -0
  240. /package/{src → dist}/functions/templates/hono-typescript/src/main.ts +0 -0
  241. /package/{src → dist}/functions/templates/hono-typescript/src/middleware/appwrite.ts +0 -0
  242. /package/{src → dist}/functions/templates/typescript-node/README.md +0 -0
  243. /package/{src → dist}/functions/templates/typescript-node/src/context.ts +0 -0
  244. /package/{src → dist}/functions/templates/typescript-node/src/main.ts +0 -0
  245. /package/{src → dist}/functions/templates/uv/README.md +0 -0
  246. /package/{src → dist}/functions/templates/uv/pyproject.toml +0 -0
  247. /package/{src → dist}/functions/templates/uv/src/__init__.py +0 -0
  248. /package/{src → dist}/functions/templates/uv/src/context.py +0 -0
  249. /package/{src → dist}/functions/templates/uv/src/main.py +0 -0
  250. /package/{src/utils/index.ts → dist/utils/index.d.ts} +0 -0
@@ -0,0 +1,357 @@
1
+ import path from "path";
2
+ import fs from "fs";
3
+ import {} from "appwrite-utils";
4
+ import { register } from "tsx/esm/api"; // Import the register function
5
+ import { pathToFileURL } from "node:url";
6
+ import chalk from "chalk";
7
+ import { findYamlConfig, loadYamlConfig, loadYamlConfigWithSession, extractSessionOptionsFromConfig, validateCollectionsTablesConfig, reportValidationResults } from "appwrite-utils-helpers";
8
+ import { detectAppwriteVersionCached, fetchServerVersion, isVersionAtLeast } from 'appwrite-utils-helpers';
9
+ import { MessageFormatter } from "appwrite-utils-helpers";
10
+ import { resolveCollectionsDir, resolveTablesDir } from 'appwrite-utils-helpers';
11
+ import { findAppwriteConfig, findAppwriteConfigTS, findFunctionsDir, discoverCollections, discoverTables, discoverLegacyDirectory } from 'appwrite-utils-helpers';
12
+ /**
13
+ * Helper function to create session preservation options from session data
14
+ * @param sessionCookie The session cookie string
15
+ * @param email Optional email associated with the session
16
+ * @param expiresAt Optional expiration timestamp
17
+ * @returns SessionPreservationOptions object
18
+ */
19
+ export function createSessionPreservation(sessionCookie, email, expiresAt) {
20
+ return {
21
+ sessionCookie,
22
+ authMethod: "session",
23
+ sessionMetadata: {
24
+ ...(email && { email }),
25
+ ...(expiresAt && { expiresAt })
26
+ }
27
+ };
28
+ }
29
+ // Re-export config discovery functions for backward compatibility
30
+ export { findAppwriteConfig, findFunctionsDir } from 'appwrite-utils-helpers';
31
+ /**
32
+ * Loads the Appwrite configuration and returns both config and the path where it was found.
33
+ * @param configDir The directory to search for config files.
34
+ * @param options Loading options including validation settings and session preservation.
35
+ * @returns Object containing the config, path, and validation results.
36
+ */
37
+ export const loadConfigWithPath = async (configDir, options = {}) => {
38
+ const { validate = true, strictMode = false, reportValidation = true } = options;
39
+ let config = null;
40
+ let actualConfigPath = null;
41
+ // Convert session preservation options to YAML format
42
+ const yamlSessionOptions = options.preserveAuth ? {
43
+ sessionCookie: options.preserveAuth.sessionCookie,
44
+ authMethod: options.preserveAuth.authMethod,
45
+ sessionMetadata: options.preserveAuth.sessionMetadata,
46
+ } : undefined;
47
+ // Check if we're given the .appwrite directory directly
48
+ if (configDir.endsWith('.appwrite')) {
49
+ // Look for config files directly in this directory
50
+ const possibleYamlFiles = ['config.yaml', 'config.yml', 'appwriteConfig.yaml', 'appwriteConfig.yml'];
51
+ for (const fileName of possibleYamlFiles) {
52
+ const yamlPath = path.join(configDir, fileName);
53
+ if (fs.existsSync(yamlPath)) {
54
+ config = yamlSessionOptions
55
+ ? await loadYamlConfigWithSession(yamlPath, yamlSessionOptions)
56
+ : await loadYamlConfig(yamlPath);
57
+ actualConfigPath = yamlPath;
58
+ break;
59
+ }
60
+ }
61
+ }
62
+ else {
63
+ // Original logic: search for .appwrite directories
64
+ const yamlConfigPath = findYamlConfig(configDir);
65
+ if (yamlConfigPath) {
66
+ config = yamlSessionOptions
67
+ ? await loadYamlConfigWithSession(yamlConfigPath, yamlSessionOptions)
68
+ : await loadYamlConfig(yamlConfigPath);
69
+ actualConfigPath = yamlConfigPath;
70
+ }
71
+ }
72
+ // Fall back to TypeScript config if YAML not found or failed to load
73
+ if (!config) {
74
+ const configPath = path.join(configDir, "appwriteConfig.ts");
75
+ // Only try to load TypeScript config if the file exists
76
+ if (fs.existsSync(configPath)) {
77
+ const unregister = register(); // Register tsx enhancement
78
+ try {
79
+ const configUrl = pathToFileURL(configPath).href;
80
+ const configModule = (await import(configUrl));
81
+ config = configModule.default?.default || configModule.default || configModule;
82
+ if (!config) {
83
+ throw new Error("Failed to load config");
84
+ }
85
+ actualConfigPath = configPath;
86
+ }
87
+ finally {
88
+ unregister(); // Unregister tsx when done
89
+ }
90
+ }
91
+ }
92
+ if (!config || !actualConfigPath) {
93
+ throw new Error("No valid configuration found");
94
+ }
95
+ // Preserve session authentication if provided
96
+ // This allows maintaining session context when config is reloaded during CLI operations
97
+ if (options.preserveAuth) {
98
+ const { sessionCookie, authMethod, sessionMetadata } = options.preserveAuth;
99
+ // Inject session cookie into the loaded config
100
+ if (sessionCookie) {
101
+ config.sessionCookie = sessionCookie;
102
+ }
103
+ // Set or override authentication method preference
104
+ if (authMethod) {
105
+ config.authMethod = authMethod;
106
+ }
107
+ // Merge session metadata (email, expiration, etc.) with existing metadata
108
+ if (sessionMetadata) {
109
+ config.sessionMetadata = {
110
+ ...config.sessionMetadata,
111
+ ...sessionMetadata
112
+ };
113
+ }
114
+ // Auto-detect authentication method if not explicitly provided
115
+ // If we have a session cookie but no auth method specified, prefer session auth
116
+ if (!authMethod && sessionCookie) {
117
+ config.authMethod = "session";
118
+ }
119
+ }
120
+ // Enhanced dual folder support: Load from BOTH collections/ AND tables/ directories
121
+ const configFileDir = path.dirname(actualConfigPath);
122
+ // Look for collections/tables directories in the same directory as the config file
123
+ const collectionsDir = resolveCollectionsDir(configFileDir);
124
+ const tablesDir = resolveTablesDir(configFileDir);
125
+ // Initialize collections array
126
+ config.collections = [];
127
+ // Load from collections/ directory first (higher priority)
128
+ const collectionsResult = await discoverCollections(collectionsDir);
129
+ config.collections.push(...collectionsResult.collections);
130
+ // Load from tables/ directory second (lower priority, check for conflicts)
131
+ const tablesResult = await discoverTables(tablesDir, collectionsResult.loadedNames);
132
+ config.collections.push(...tablesResult.tables);
133
+ // Combine conflicts from both discovery operations
134
+ const allConflicts = [...collectionsResult.conflicts, ...tablesResult.conflicts];
135
+ // Report conflicts if any
136
+ if (allConflicts.length > 0) {
137
+ MessageFormatter.warning(`Found ${allConflicts.length} naming conflicts between collections/ and tables/`, { prefix: "Config" });
138
+ allConflicts.forEach(conflict => {
139
+ MessageFormatter.info(` - '${conflict.name}': ${conflict.source1} (used) vs ${conflict.source2} (skipped)`, { prefix: "Config" });
140
+ });
141
+ }
142
+ // Fallback: If neither directory exists, try legacy single-directory detection
143
+ if (!fs.existsSync(collectionsDir) && !fs.existsSync(tablesDir)) {
144
+ // Determine directory (collections or tables) based on server version / API mode
145
+ let dirName = "collections";
146
+ try {
147
+ const det = await detectAppwriteVersionCached(config.appwriteEndpoint, config.appwriteProject, config.appwriteKey);
148
+ if (det.apiMode === 'tablesdb' || isVersionAtLeast(det.serverVersion, '1.8.0')) {
149
+ dirName = 'tables';
150
+ }
151
+ else {
152
+ // Try health version if not provided
153
+ const ver = await fetchServerVersion(config.appwriteEndpoint);
154
+ if (isVersionAtLeast(ver || undefined, '1.8.0'))
155
+ dirName = 'tables';
156
+ }
157
+ }
158
+ catch { }
159
+ const legacyItems = await discoverLegacyDirectory(configFileDir, dirName);
160
+ config.collections.push(...legacyItems);
161
+ }
162
+ // Ensure array exists even if empty
163
+ config.collections = config.collections || [];
164
+ // Log the final result
165
+ const allCollections = config.collections || [];
166
+ const fromCollectionsDir = allCollections.filter((c) => !c._isFromTablesDir).length;
167
+ const fromTablesDir = allCollections.filter((c) => c._isFromTablesDir).length;
168
+ const totalLoaded = allCollections.length;
169
+ if (totalLoaded > 0) {
170
+ if (fromTablesDir > 0) {
171
+ MessageFormatter.success(`Successfully loaded ${totalLoaded} items total: ${fromCollectionsDir} from collections/ and ${fromTablesDir} from tables/`, { prefix: "Config" });
172
+ }
173
+ else {
174
+ MessageFormatter.success(`Successfully loaded ${totalLoaded} collections from collections/`, { prefix: "Config" });
175
+ }
176
+ }
177
+ // Validate configuration if requested
178
+ let validation;
179
+ if (validate) {
180
+ validation = validateCollectionsTablesConfig(config);
181
+ // In strict mode, treat warnings as errors
182
+ if (strictMode && validation.warnings.length > 0) {
183
+ const strictValidation = {
184
+ ...validation,
185
+ isValid: false,
186
+ errors: [...validation.errors, ...validation.warnings.map(w => ({ ...w, severity: "error" }))],
187
+ warnings: []
188
+ };
189
+ validation = strictValidation;
190
+ }
191
+ // Report validation results if requested
192
+ if (reportValidation) {
193
+ reportValidationResults(validation, { verbose: true });
194
+ }
195
+ // Throw error if validation fails in strict mode
196
+ if (strictMode && !validation.isValid) {
197
+ throw new Error(`Configuration validation failed in strict mode. Found ${validation.errors.length} validation errors.`);
198
+ }
199
+ }
200
+ return { config, actualConfigPath, validation };
201
+ };
202
+ /**
203
+ * Loads the Appwrite configuration and all collection configurations from a specified directory.
204
+ * Supports both YAML and TypeScript config formats with backward compatibility.
205
+ * @param configDir The directory containing the config file and collections folder.
206
+ * @param options Loading options including validation settings and session preservation.
207
+ * @returns The loaded Appwrite configuration including collections.
208
+ */
209
+ export const loadConfig = async (configDir, options = {}) => {
210
+ const { validate = false, strictMode = false, reportValidation = false } = options;
211
+ let config = null;
212
+ let actualConfigPath = null;
213
+ // Convert session preservation options to YAML format
214
+ const yamlSessionOptions = options.preserveAuth ? {
215
+ sessionCookie: options.preserveAuth.sessionCookie,
216
+ authMethod: options.preserveAuth.authMethod,
217
+ sessionMetadata: options.preserveAuth.sessionMetadata,
218
+ } : undefined;
219
+ // First try to find and load YAML config
220
+ const yamlConfigPath = findYamlConfig(configDir);
221
+ if (yamlConfigPath) {
222
+ config = yamlSessionOptions
223
+ ? await loadYamlConfigWithSession(yamlConfigPath, yamlSessionOptions)
224
+ : await loadYamlConfig(yamlConfigPath);
225
+ actualConfigPath = yamlConfigPath;
226
+ }
227
+ // Fall back to TypeScript config if YAML not found or failed to load
228
+ if (!config) {
229
+ const configPath = path.join(configDir, "appwriteConfig.ts");
230
+ // Only try to load TypeScript config if the file exists
231
+ if (fs.existsSync(configPath)) {
232
+ const unregister = register(); // Register tsx enhancement
233
+ try {
234
+ const configUrl = pathToFileURL(configPath).href;
235
+ const configModule = (await import(configUrl));
236
+ config = configModule.default?.default || configModule.default || configModule;
237
+ if (!config) {
238
+ throw new Error("Failed to load config");
239
+ }
240
+ actualConfigPath = configPath;
241
+ }
242
+ finally {
243
+ unregister(); // Unregister tsx when done
244
+ }
245
+ }
246
+ }
247
+ if (!config) {
248
+ throw new Error("No valid configuration found");
249
+ }
250
+ // Preserve session authentication if provided
251
+ // This allows maintaining session context when config is reloaded during CLI operations
252
+ if (options.preserveAuth) {
253
+ const { sessionCookie, authMethod, sessionMetadata } = options.preserveAuth;
254
+ // Inject session cookie into the loaded config
255
+ if (sessionCookie) {
256
+ config.sessionCookie = sessionCookie;
257
+ }
258
+ // Set or override authentication method preference
259
+ if (authMethod) {
260
+ config.authMethod = authMethod;
261
+ }
262
+ // Merge session metadata (email, expiration, etc.) with existing metadata
263
+ if (sessionMetadata) {
264
+ config.sessionMetadata = {
265
+ ...config.sessionMetadata,
266
+ ...sessionMetadata
267
+ };
268
+ }
269
+ // Auto-detect authentication method if not explicitly provided
270
+ // If we have a session cookie but no auth method specified, prefer session auth
271
+ if (!authMethod && sessionCookie) {
272
+ config.authMethod = "session";
273
+ }
274
+ }
275
+ // Enhanced dual folder support: Load from BOTH collections/ AND tables/ directories
276
+ const configFileDir = actualConfigPath ? path.dirname(actualConfigPath) : configDir;
277
+ // Look for collections/tables directories in the same directory as the config file
278
+ const collectionsDir = resolveCollectionsDir(configFileDir);
279
+ const tablesDir = resolveTablesDir(configFileDir);
280
+ // Initialize collections array
281
+ config.collections = [];
282
+ // Load from collections/ directory first (higher priority)
283
+ const collectionsResult = await discoverCollections(collectionsDir);
284
+ config.collections.push(...collectionsResult.collections);
285
+ // Load from tables/ directory second (lower priority, check for conflicts)
286
+ const tablesResult = await discoverTables(tablesDir, collectionsResult.loadedNames);
287
+ config.collections.push(...tablesResult.tables);
288
+ // Combine conflicts from both discovery operations
289
+ const allConflicts = [...collectionsResult.conflicts, ...tablesResult.conflicts];
290
+ // Report conflicts if any
291
+ if (allConflicts.length > 0) {
292
+ MessageFormatter.warning(`Found ${allConflicts.length} naming conflicts between collections/ and tables/`, { prefix: "Config" });
293
+ allConflicts.forEach(conflict => {
294
+ MessageFormatter.info(` - '${conflict.name}': ${conflict.source1} (used) vs ${conflict.source2} (skipped)`, { prefix: "Config" });
295
+ });
296
+ }
297
+ // Fallback: If neither directory exists, try legacy single-directory detection
298
+ if (!fs.existsSync(collectionsDir) && !fs.existsSync(tablesDir)) {
299
+ // Determine directory (collections or tables) based on server version / API mode
300
+ let dirName = "collections";
301
+ try {
302
+ const det = await detectAppwriteVersionCached(config.appwriteEndpoint, config.appwriteProject, config.appwriteKey);
303
+ if (det.apiMode === 'tablesdb' || isVersionAtLeast(det.serverVersion, '1.8.0')) {
304
+ dirName = 'tables';
305
+ }
306
+ else {
307
+ const ver = await fetchServerVersion(config.appwriteEndpoint);
308
+ if (isVersionAtLeast(ver || undefined, '1.8.0'))
309
+ dirName = 'tables';
310
+ }
311
+ }
312
+ catch { }
313
+ const legacyItems = await discoverLegacyDirectory(configFileDir, dirName);
314
+ config.collections.push(...legacyItems);
315
+ }
316
+ // Ensure array exists even if empty
317
+ config.collections = config.collections || [];
318
+ // Log the final result
319
+ const allCollections = config.collections || [];
320
+ const fromCollectionsDir = allCollections.filter((c) => !c._isFromTablesDir).length;
321
+ const fromTablesDir = allCollections.filter((c) => c._isFromTablesDir).length;
322
+ const totalLoaded = allCollections.length;
323
+ if (totalLoaded > 0) {
324
+ if (fromTablesDir > 0) {
325
+ MessageFormatter.success(`Successfully loaded ${totalLoaded} items total: ${fromCollectionsDir} from collections/ and ${fromTablesDir} from tables/`, { prefix: "Config" });
326
+ }
327
+ else {
328
+ MessageFormatter.success(`Successfully loaded ${totalLoaded} collections from collections/`, { prefix: "Config" });
329
+ }
330
+ }
331
+ // Log successful config loading
332
+ if (actualConfigPath) {
333
+ MessageFormatter.success(`Loaded config from: ${actualConfigPath}`, { prefix: "Config" });
334
+ }
335
+ // Validate configuration if requested
336
+ if (validate) {
337
+ let validation = validateCollectionsTablesConfig(config);
338
+ // In strict mode, treat warnings as errors
339
+ if (strictMode && validation.warnings.length > 0) {
340
+ validation = {
341
+ ...validation,
342
+ isValid: false,
343
+ errors: [...validation.errors, ...validation.warnings.map(w => ({ ...w, severity: "error" }))],
344
+ warnings: []
345
+ };
346
+ }
347
+ // Report validation results if requested
348
+ if (reportValidation) {
349
+ reportValidationResults(validation, { verbose: true });
350
+ }
351
+ // Throw error if validation fails in strict mode
352
+ if (strictMode && !validation.isValid) {
353
+ throw new Error(`Configuration validation failed in strict mode. Found ${validation.errors.length} validation errors.`);
354
+ }
355
+ }
356
+ return config;
357
+ };
@@ -0,0 +1,4 @@
1
+ export declare const customDefinitionsFile = "import type { ConverterFunctions, ValidationRules, AfterImportActions } from \"appwrite-utils\";\n\nexport const customConverterFunctions: ConverterFunctions = {\n // Add your custom converter functions here\n}\nexport const customValidationRules: ValidationRules = {\n // Add your custom validation rules here\n}\nexport const customAfterImportActions: AfterImportActions = {\n // Add your custom after import actions here\n}";
2
+ export declare const createEmptyCollection: (collectionName: string) => void;
3
+ export declare const generateYamlConfig: (currentDir?: string, useAppwriteDir?: boolean) => string;
4
+ export declare const setupDirsFiles: (example?: boolean, currentDir?: string, useYaml?: boolean) => Promise<void>;