appwrite-utils-cli 0.10.85 → 1.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (178) hide show
  1. package/.appwrite/.yaml_schemas/appwrite-config.schema.json +380 -0
  2. package/.appwrite/.yaml_schemas/collection.schema.json +255 -0
  3. package/.appwrite/collections/Categories.yaml +182 -0
  4. package/.appwrite/collections/ExampleCollection.yaml +36 -0
  5. package/.appwrite/collections/Posts.yaml +227 -0
  6. package/.appwrite/collections/Users.yaml +149 -0
  7. package/.appwrite/config.yaml +109 -0
  8. package/.appwrite/import/README.md +148 -0
  9. package/.appwrite/import/categories-import.yaml +129 -0
  10. package/.appwrite/import/posts-import.yaml +208 -0
  11. package/.appwrite/import/users-import.yaml +130 -0
  12. package/.appwrite/importData/categories.json +194 -0
  13. package/.appwrite/importData/posts.json +270 -0
  14. package/.appwrite/importData/users.json +220 -0
  15. package/.appwrite/schemas/categories.json +128 -0
  16. package/.appwrite/schemas/exampleCollection.json +52 -0
  17. package/.appwrite/schemas/posts.json +173 -0
  18. package/.appwrite/schemas/users.json +125 -0
  19. package/README.md +261 -33
  20. package/dist/collections/attributes.js +3 -2
  21. package/dist/collections/methods.js +56 -38
  22. package/dist/config/yamlConfig.d.ts +501 -0
  23. package/dist/config/yamlConfig.js +452 -0
  24. package/dist/databases/setup.d.ts +6 -0
  25. package/dist/databases/setup.js +119 -0
  26. package/dist/functions/methods.d.ts +1 -1
  27. package/dist/functions/methods.js +5 -2
  28. package/dist/functions/openapi.d.ts +4 -0
  29. package/dist/functions/openapi.js +60 -0
  30. package/dist/interactiveCLI.d.ts +5 -0
  31. package/dist/interactiveCLI.js +196 -52
  32. package/dist/main.js +91 -30
  33. package/dist/migrations/afterImportActions.js +2 -2
  34. package/dist/migrations/appwriteToX.d.ts +10 -0
  35. package/dist/migrations/appwriteToX.js +15 -4
  36. package/dist/migrations/backup.d.ts +16 -16
  37. package/dist/migrations/dataLoader.d.ts +83 -1
  38. package/dist/migrations/dataLoader.js +4 -4
  39. package/dist/migrations/importController.js +25 -18
  40. package/dist/migrations/importDataActions.js +2 -2
  41. package/dist/migrations/logging.d.ts +9 -1
  42. package/dist/migrations/logging.js +41 -22
  43. package/dist/migrations/migrationHelper.d.ts +4 -4
  44. package/dist/migrations/relationships.js +1 -1
  45. package/dist/migrations/services/DataTransformationService.d.ts +55 -0
  46. package/dist/migrations/services/DataTransformationService.js +158 -0
  47. package/dist/migrations/services/FileHandlerService.d.ts +75 -0
  48. package/dist/migrations/services/FileHandlerService.js +236 -0
  49. package/dist/migrations/services/ImportOrchestrator.d.ts +97 -0
  50. package/dist/migrations/services/ImportOrchestrator.js +488 -0
  51. package/dist/migrations/services/RateLimitManager.d.ts +138 -0
  52. package/dist/migrations/services/RateLimitManager.js +279 -0
  53. package/dist/migrations/services/RelationshipResolver.d.ts +120 -0
  54. package/dist/migrations/services/RelationshipResolver.js +332 -0
  55. package/dist/migrations/services/UserMappingService.d.ts +109 -0
  56. package/dist/migrations/services/UserMappingService.js +277 -0
  57. package/dist/migrations/services/ValidationService.d.ts +74 -0
  58. package/dist/migrations/services/ValidationService.js +260 -0
  59. package/dist/migrations/transfer.d.ts +0 -6
  60. package/dist/migrations/transfer.js +16 -132
  61. package/dist/migrations/yaml/YamlImportConfigLoader.d.ts +384 -0
  62. package/dist/migrations/yaml/YamlImportConfigLoader.js +375 -0
  63. package/dist/migrations/yaml/YamlImportIntegration.d.ts +87 -0
  64. package/dist/migrations/yaml/YamlImportIntegration.js +330 -0
  65. package/dist/migrations/yaml/generateImportSchemas.d.ts +17 -0
  66. package/dist/migrations/yaml/generateImportSchemas.js +575 -0
  67. package/dist/schemas/authUser.d.ts +9 -9
  68. package/dist/shared/attributeManager.d.ts +17 -0
  69. package/dist/shared/attributeManager.js +273 -0
  70. package/dist/shared/confirmationDialogs.d.ts +75 -0
  71. package/dist/shared/confirmationDialogs.js +236 -0
  72. package/dist/shared/functionManager.d.ts +48 -0
  73. package/dist/shared/functionManager.js +322 -0
  74. package/dist/shared/indexManager.d.ts +24 -0
  75. package/dist/shared/indexManager.js +150 -0
  76. package/dist/shared/jsonSchemaGenerator.d.ts +51 -0
  77. package/dist/shared/jsonSchemaGenerator.js +313 -0
  78. package/dist/shared/logging.d.ts +10 -0
  79. package/dist/shared/logging.js +46 -0
  80. package/dist/shared/messageFormatter.d.ts +37 -0
  81. package/dist/shared/messageFormatter.js +152 -0
  82. package/dist/shared/migrationHelpers.d.ts +173 -0
  83. package/dist/shared/migrationHelpers.js +142 -0
  84. package/dist/shared/operationLogger.d.ts +3 -0
  85. package/dist/shared/operationLogger.js +25 -0
  86. package/dist/shared/operationQueue.d.ts +13 -0
  87. package/dist/shared/operationQueue.js +79 -0
  88. package/dist/shared/progressManager.d.ts +62 -0
  89. package/dist/shared/progressManager.js +215 -0
  90. package/dist/shared/schemaGenerator.d.ts +18 -0
  91. package/dist/shared/schemaGenerator.js +523 -0
  92. package/dist/storage/methods.d.ts +3 -1
  93. package/dist/storage/methods.js +144 -55
  94. package/dist/storage/schemas.d.ts +56 -16
  95. package/dist/types.d.ts +2 -2
  96. package/dist/types.js +1 -1
  97. package/dist/users/methods.d.ts +16 -0
  98. package/dist/users/methods.js +276 -0
  99. package/dist/utils/configMigration.d.ts +1 -0
  100. package/dist/utils/configMigration.js +156 -0
  101. package/dist/utils/dataConverters.d.ts +46 -0
  102. package/dist/utils/dataConverters.js +139 -0
  103. package/dist/utils/loadConfigs.d.ts +15 -4
  104. package/dist/utils/loadConfigs.js +377 -51
  105. package/dist/utils/schemaStrings.js +2 -1
  106. package/dist/utils/setupFiles.d.ts +2 -1
  107. package/dist/utils/setupFiles.js +723 -28
  108. package/dist/utils/validationRules.d.ts +43 -0
  109. package/dist/utils/validationRules.js +42 -0
  110. package/dist/utils/yamlConverter.d.ts +48 -0
  111. package/dist/utils/yamlConverter.js +98 -0
  112. package/dist/utilsController.js +65 -43
  113. package/package.json +19 -15
  114. package/src/collections/attributes.ts +3 -2
  115. package/src/collections/methods.ts +85 -51
  116. package/src/config/yamlConfig.ts +488 -0
  117. package/src/{migrations/setupDatabase.ts → databases/setup.ts} +11 -5
  118. package/src/functions/methods.ts +8 -4
  119. package/src/functions/templates/count-docs-in-collection/package.json +25 -0
  120. package/src/functions/templates/count-docs-in-collection/tsconfig.json +28 -0
  121. package/src/functions/templates/typescript-node/package.json +24 -0
  122. package/src/functions/templates/typescript-node/tsconfig.json +28 -0
  123. package/src/functions/templates/uv/README.md +31 -0
  124. package/src/functions/templates/uv/pyproject.toml +29 -0
  125. package/src/interactiveCLI.ts +230 -63
  126. package/src/main.ts +111 -37
  127. package/src/migrations/afterImportActions.ts +2 -2
  128. package/src/migrations/appwriteToX.ts +17 -4
  129. package/src/migrations/dataLoader.ts +4 -4
  130. package/src/migrations/importController.ts +30 -22
  131. package/src/migrations/importDataActions.ts +2 -2
  132. package/src/migrations/relationships.ts +1 -1
  133. package/src/migrations/services/DataTransformationService.ts +196 -0
  134. package/src/migrations/services/FileHandlerService.ts +311 -0
  135. package/src/migrations/services/ImportOrchestrator.ts +669 -0
  136. package/src/migrations/services/RateLimitManager.ts +363 -0
  137. package/src/migrations/services/RelationshipResolver.ts +461 -0
  138. package/src/migrations/services/UserMappingService.ts +345 -0
  139. package/src/migrations/services/ValidationService.ts +349 -0
  140. package/src/migrations/transfer.ts +22 -228
  141. package/src/migrations/yaml/YamlImportConfigLoader.ts +427 -0
  142. package/src/migrations/yaml/YamlImportIntegration.ts +419 -0
  143. package/src/migrations/yaml/generateImportSchemas.ts +589 -0
  144. package/src/shared/attributeManager.ts +429 -0
  145. package/src/shared/confirmationDialogs.ts +327 -0
  146. package/src/shared/functionManager.ts +515 -0
  147. package/src/shared/indexManager.ts +253 -0
  148. package/src/shared/jsonSchemaGenerator.ts +403 -0
  149. package/src/shared/logging.ts +74 -0
  150. package/src/shared/messageFormatter.ts +195 -0
  151. package/src/{migrations/migrationHelper.ts → shared/migrationHelpers.ts} +22 -4
  152. package/src/{migrations/helper.ts → shared/operationLogger.ts} +7 -2
  153. package/src/{migrations/queue.ts → shared/operationQueue.ts} +1 -1
  154. package/src/shared/progressManager.ts +278 -0
  155. package/src/{migrations/schemaStrings.ts → shared/schemaGenerator.ts} +71 -17
  156. package/src/storage/methods.ts +199 -78
  157. package/src/types.ts +2 -2
  158. package/src/{migrations/users.ts → users/methods.ts} +2 -2
  159. package/src/utils/configMigration.ts +212 -0
  160. package/src/utils/loadConfigs.ts +414 -52
  161. package/src/utils/schemaStrings.ts +2 -1
  162. package/src/utils/setupFiles.ts +742 -40
  163. package/src/{migrations → utils}/validationRules.ts +1 -1
  164. package/src/utils/yamlConverter.ts +131 -0
  165. package/src/utilsController.ts +75 -54
  166. package/src/functions/templates/poetry/README.md +0 -30
  167. package/src/functions/templates/poetry/pyproject.toml +0 -16
  168. package/src/migrations/attributes.ts +0 -561
  169. package/src/migrations/backup.ts +0 -205
  170. package/src/migrations/databases.ts +0 -39
  171. package/src/migrations/dbHelpers.ts +0 -92
  172. package/src/migrations/indexes.ts +0 -40
  173. package/src/migrations/logging.ts +0 -29
  174. package/src/migrations/storage.ts +0 -538
  175. /package/src/{migrations → functions}/openapi.ts +0 -0
  176. /package/src/functions/templates/{poetry → uv}/src/__init__.py +0 -0
  177. /package/src/functions/templates/{poetry → uv}/src/index.py +0 -0
  178. /package/src/{migrations/converters.ts → utils/dataConverters.ts} +0 -0
@@ -0,0 +1,173 @@
1
+ import { type Databases } from "node-appwrite";
2
+ import { z } from "zod";
3
+ /**
4
+ * Object that contains the context for an action that needs to be executed after import
5
+ * Used in the afterImportActionsDefinitions
6
+ * @type {ContextObject}
7
+ * @typedef {Object} ContextObject
8
+ * @property {string} collectionId - The ID of the collection
9
+ * @property {any} finalItem - The final item that was imported
10
+ * @property {string} action - The name of the action
11
+ * @property {string[]} params - The parameters for the action
12
+ * @property {Object} context - The context object for the action (all the data of this specific item)
13
+ */
14
+ export declare const ContextObject: z.ZodObject<{
15
+ dbId: z.ZodString;
16
+ collectionId: z.ZodString;
17
+ finalItem: z.ZodAny;
18
+ attributeMappings: z.ZodArray<z.ZodObject<{
19
+ oldKey: z.ZodOptional<z.ZodString>;
20
+ oldKeys: z.ZodOptional<z.ZodArray<z.ZodString, "many">>;
21
+ targetKey: z.ZodString;
22
+ valueToSet: z.ZodOptional<z.ZodAny>;
23
+ fileData: z.ZodOptional<z.ZodObject<{
24
+ name: z.ZodString;
25
+ path: z.ZodString;
26
+ }, "strip", z.ZodTypeAny, {
27
+ path: string;
28
+ name: string;
29
+ }, {
30
+ path: string;
31
+ name: string;
32
+ }>>;
33
+ converters: z.ZodOptional<z.ZodDefault<z.ZodArray<z.ZodString, "many">>>;
34
+ validationActions: z.ZodOptional<z.ZodDefault<z.ZodArray<z.ZodObject<{
35
+ action: z.ZodString;
36
+ params: z.ZodArray<z.ZodString, "many">;
37
+ }, "strip", z.ZodTypeAny, {
38
+ params: string[];
39
+ action: string;
40
+ }, {
41
+ params: string[];
42
+ action: string;
43
+ }>, "many">>>;
44
+ postImportActions: z.ZodOptional<z.ZodDefault<z.ZodArray<z.ZodObject<{
45
+ action: z.ZodString;
46
+ params: z.ZodArray<z.ZodUnion<[z.ZodString, z.ZodRecord<z.ZodString, z.ZodAny>]>, "many">;
47
+ }, "strip", z.ZodTypeAny, {
48
+ params: (string | Record<string, any>)[];
49
+ action: string;
50
+ }, {
51
+ params: (string | Record<string, any>)[];
52
+ action: string;
53
+ }>, "many">>>;
54
+ }, "strip", z.ZodTypeAny, {
55
+ targetKey: string;
56
+ oldKey?: string | undefined;
57
+ oldKeys?: string[] | undefined;
58
+ valueToSet?: any;
59
+ fileData?: {
60
+ path: string;
61
+ name: string;
62
+ } | undefined;
63
+ converters?: string[] | undefined;
64
+ validationActions?: {
65
+ params: string[];
66
+ action: string;
67
+ }[] | undefined;
68
+ postImportActions?: {
69
+ params: (string | Record<string, any>)[];
70
+ action: string;
71
+ }[] | undefined;
72
+ }, {
73
+ targetKey: string;
74
+ oldKey?: string | undefined;
75
+ oldKeys?: string[] | undefined;
76
+ valueToSet?: any;
77
+ fileData?: {
78
+ path: string;
79
+ name: string;
80
+ } | undefined;
81
+ converters?: string[] | undefined;
82
+ validationActions?: {
83
+ params: string[];
84
+ action: string;
85
+ }[] | undefined;
86
+ postImportActions?: {
87
+ params: (string | Record<string, any>)[];
88
+ action: string;
89
+ }[] | undefined;
90
+ }>, "many">;
91
+ context: z.ZodAny;
92
+ }, "strip", z.ZodTypeAny, {
93
+ collectionId: string;
94
+ attributeMappings: {
95
+ targetKey: string;
96
+ oldKey?: string | undefined;
97
+ oldKeys?: string[] | undefined;
98
+ valueToSet?: any;
99
+ fileData?: {
100
+ path: string;
101
+ name: string;
102
+ } | undefined;
103
+ converters?: string[] | undefined;
104
+ validationActions?: {
105
+ params: string[];
106
+ action: string;
107
+ }[] | undefined;
108
+ postImportActions?: {
109
+ params: (string | Record<string, any>)[];
110
+ action: string;
111
+ }[] | undefined;
112
+ }[];
113
+ dbId: string;
114
+ context?: any;
115
+ finalItem?: any;
116
+ }, {
117
+ collectionId: string;
118
+ attributeMappings: {
119
+ targetKey: string;
120
+ oldKey?: string | undefined;
121
+ oldKeys?: string[] | undefined;
122
+ valueToSet?: any;
123
+ fileData?: {
124
+ path: string;
125
+ name: string;
126
+ } | undefined;
127
+ converters?: string[] | undefined;
128
+ validationActions?: {
129
+ params: string[];
130
+ action: string;
131
+ }[] | undefined;
132
+ postImportActions?: {
133
+ params: (string | Record<string, any>)[];
134
+ action: string;
135
+ }[] | undefined;
136
+ }[];
137
+ dbId: string;
138
+ context?: any;
139
+ finalItem?: any;
140
+ }>;
141
+ export type ContextObject = z.infer<typeof ContextObject>;
142
+ export declare const createOrFindAfterImportOperation: (database: Databases, collectionId: string, context: ContextObject, useMigrations?: boolean) => Promise<void>;
143
+ export declare const addBatch: (database: Databases, data: string) => Promise<string>;
144
+ export declare const getAfterImportOperations: (database: Databases, collectionId: string, useMigrations?: boolean) => Promise<{
145
+ status: "error" | "pending" | "ready" | "in_progress" | "completed" | "cancelled";
146
+ error: string;
147
+ $id: string;
148
+ $createdAt: string;
149
+ $updatedAt: string;
150
+ collectionId: string;
151
+ operationType: string;
152
+ progress: number;
153
+ total: number;
154
+ data?: any;
155
+ batches?: string[] | undefined;
156
+ }[]>;
157
+ export declare const findOrCreateOperation: (database: Databases, collectionId: string, operationType: string, additionalQueries?: string[]) => Promise<{
158
+ status: "error" | "pending" | "ready" | "in_progress" | "completed" | "cancelled";
159
+ error: string;
160
+ $id: string;
161
+ $createdAt: string;
162
+ $updatedAt: string;
163
+ collectionId: string;
164
+ operationType: string;
165
+ progress: number;
166
+ total: number;
167
+ data?: any;
168
+ batches?: string[] | undefined;
169
+ }>;
170
+ export declare const updateOperation: (database: Databases, operationId: string, updateFields: any, useMigrations?: boolean) => Promise<void>;
171
+ export declare const maxDataLength = 1073741820;
172
+ export declare const maxBatchItems = 25;
173
+ export declare const splitIntoBatches: (data: any[]) => any[][];
@@ -0,0 +1,142 @@
1
+ import { ID, Query } from "node-appwrite";
2
+ import { BatchSchema, OperationSchema } from "../storage/schemas.js";
3
+ import { AttributeMappingsSchema } from "appwrite-utils";
4
+ import { z } from "zod";
5
+ import { logger } from "./logging.js";
6
+ import { tryAwaitWithRetry } from "../utils/helperFunctions.js";
7
+ /**
8
+ * Object that contains the context for an action that needs to be executed after import
9
+ * Used in the afterImportActionsDefinitions
10
+ * @type {ContextObject}
11
+ * @typedef {Object} ContextObject
12
+ * @property {string} collectionId - The ID of the collection
13
+ * @property {any} finalItem - The final item that was imported
14
+ * @property {string} action - The name of the action
15
+ * @property {string[]} params - The parameters for the action
16
+ * @property {Object} context - The context object for the action (all the data of this specific item)
17
+ */
18
+ export const ContextObject = z.object({
19
+ dbId: z.string(),
20
+ collectionId: z.string(),
21
+ finalItem: z.any(),
22
+ attributeMappings: AttributeMappingsSchema,
23
+ context: z.any(),
24
+ });
25
+ export const createOrFindAfterImportOperation = async (database, collectionId, context, useMigrations = true) => {
26
+ if (!useMigrations) {
27
+ logger.info("Migrations disabled, skipping after import operation tracking");
28
+ return;
29
+ }
30
+ let operation = await findOrCreateOperation(database, collectionId, "afterImportAction");
31
+ if (!operation.batches) {
32
+ operation.batches = [];
33
+ }
34
+ // Directly create a new batch for the context without checking for an existing batch
35
+ const contextData = JSON.stringify(context);
36
+ // Create a new batch with the contextData
37
+ const newBatchId = await addBatch(database, contextData);
38
+ // Update the operation with the new batch's $id
39
+ operation.batches = [...operation.batches, newBatchId];
40
+ await database.updateDocument("migrations", "currentOperations", operation.$id, { batches: operation.batches });
41
+ };
42
+ export const addBatch = async (database, data) => {
43
+ const batch = await database.createDocument("migrations", "batches", ID.unique(), {
44
+ data,
45
+ processed: false,
46
+ });
47
+ return batch.$id;
48
+ };
49
+ export const getAfterImportOperations = async (database, collectionId, useMigrations = true) => {
50
+ if (!useMigrations) {
51
+ logger.info("Migrations disabled, returning empty operations list");
52
+ return [];
53
+ }
54
+ let lastDocumentId;
55
+ const allOperations = [];
56
+ let total = 0;
57
+ do {
58
+ const query = [
59
+ Query.equal("collectionId", collectionId),
60
+ Query.equal("operationType", "afterImportAction"),
61
+ Query.limit(100),
62
+ ];
63
+ if (lastDocumentId) {
64
+ query.push(Query.cursorAfter(lastDocumentId));
65
+ }
66
+ const operations = await database.listDocuments("migrations", "currentOperations", query);
67
+ total = operations.total; // Update total with the latest fetch
68
+ allOperations.push(...operations.documents);
69
+ if (operations.documents.length > 0 && operations.documents.length >= 100) {
70
+ lastDocumentId =
71
+ operations.documents[operations.documents.length - 1].$id;
72
+ }
73
+ } while (allOperations.length < total);
74
+ const allOps = allOperations.map((op) => OperationSchema.parse(op));
75
+ return allOps;
76
+ };
77
+ export const findOrCreateOperation = async (database, collectionId, operationType, additionalQueries) => {
78
+ const operations = await tryAwaitWithRetry(async () => await database.listDocuments("migrations", "currentOperations", [
79
+ Query.equal("collectionId", collectionId),
80
+ Query.equal("operationType", operationType),
81
+ Query.equal("status", "pending"),
82
+ ...(additionalQueries || []),
83
+ ]));
84
+ if (operations.documents.length > 0) {
85
+ return OperationSchema.parse(operations.documents[0]); // Assuming the first document is the operation we want
86
+ }
87
+ else {
88
+ // Create a new operation document
89
+ const op = await tryAwaitWithRetry(async () => await database.createDocument("migrations", "currentOperations", ID.unique(), {
90
+ operationType,
91
+ collectionId,
92
+ status: "pending",
93
+ batches: [],
94
+ progress: 0,
95
+ total: 0,
96
+ error: "",
97
+ }));
98
+ return OperationSchema.parse(op);
99
+ }
100
+ };
101
+ export const updateOperation = async (database, operationId, updateFields, useMigrations = true) => {
102
+ if (!useMigrations) {
103
+ logger.info("Migrations disabled, skipping operation update");
104
+ return;
105
+ }
106
+ await tryAwaitWithRetry(async () => await database.updateDocument("migrations", "currentOperations", operationId, updateFields));
107
+ };
108
+ // Actual max 1073741824
109
+ export const maxDataLength = 1073741820;
110
+ export const maxBatchItems = 25;
111
+ export const splitIntoBatches = (data) => {
112
+ let batches = [];
113
+ let currentBatch = [];
114
+ let currentBatchLength = 0;
115
+ let currentBatchItemCount = 0;
116
+ data.forEach((item, index) => {
117
+ const itemLength = JSON.stringify(item).length;
118
+ if (itemLength > maxDataLength) {
119
+ console.log(item, `Large item found at index ${index} with length ${itemLength}:`);
120
+ }
121
+ // Check if adding the current item would exceed the max length or max items per batch
122
+ if (currentBatchLength + itemLength >= maxDataLength ||
123
+ currentBatchItemCount >= maxBatchItems) {
124
+ // If so, start a new batch
125
+ batches.push(currentBatch);
126
+ currentBatch = [item];
127
+ currentBatchLength = itemLength;
128
+ currentBatchItemCount = 1; // Reset item count for the new batch
129
+ }
130
+ else {
131
+ // Otherwise, add the item to the current batch
132
+ currentBatch.push(item);
133
+ currentBatchLength += itemLength;
134
+ currentBatchItemCount++;
135
+ }
136
+ });
137
+ // Don't forget to add the last batch if it's not empty
138
+ if (currentBatch.length > 0) {
139
+ batches.push(currentBatch);
140
+ }
141
+ return batches;
142
+ };
@@ -0,0 +1,3 @@
1
+ import type { Databases, Models } from "node-appwrite";
2
+ import type { OperationCreate } from "../storage/schemas.js";
3
+ export declare const logOperation: (db: Databases, dbId: string, operationDetails: OperationCreate, operationId?: string, useMigrations?: boolean) => Promise<Models.Document | null>;
@@ -0,0 +1,25 @@
1
+ import { tryAwaitWithRetry } from "appwrite-utils";
2
+ import { ulid } from "ulidx";
3
+ export const logOperation = async (db, dbId, operationDetails, operationId, useMigrations = true) => {
4
+ if (!useMigrations) {
5
+ console.log("Migrations disabled, skipping operation logging");
6
+ return null;
7
+ }
8
+ try {
9
+ let operation;
10
+ if (operationId) {
11
+ // Update existing operation log
12
+ operation = await tryAwaitWithRetry(async () => await db.updateDocument("migrations", "currentOperations", operationId, operationDetails));
13
+ }
14
+ else {
15
+ // Create new operation log
16
+ operation = await db.createDocument("migrations", "currentOperations", ulid(), operationDetails);
17
+ }
18
+ console.log(`Operation logged: ${operation.$id}`);
19
+ return operation;
20
+ }
21
+ catch (error) {
22
+ console.error(`Error logging operation: ${error}`);
23
+ throw error;
24
+ }
25
+ };
@@ -0,0 +1,13 @@
1
+ import { type Databases, type Models } from "node-appwrite";
2
+ import type { Attribute } from "appwrite-utils";
3
+ export interface QueuedOperation {
4
+ type: "attribute";
5
+ collectionId?: string;
6
+ attribute?: Attribute;
7
+ collection?: Models.Collection;
8
+ dependencies?: string[];
9
+ }
10
+ export declare const queuedOperations: QueuedOperation[];
11
+ export declare const nameToIdMapping: Map<string, string>;
12
+ export declare const enqueueOperation: (operation: QueuedOperation) => void;
13
+ export declare const processQueue: (db: Databases, dbId: string) => Promise<void>;
@@ -0,0 +1,79 @@
1
+ import { Query } from "node-appwrite";
2
+ import { createOrUpdateAttribute } from "../collections/attributes.js";
3
+ import { fetchAndCacheCollectionByName } from "../collections/methods.js";
4
+ import { tryAwaitWithRetry } from "../utils/helperFunctions.js";
5
+ export const queuedOperations = [];
6
+ export const nameToIdMapping = new Map();
7
+ export const enqueueOperation = (operation) => {
8
+ queuedOperations.push(operation);
9
+ };
10
+ export const processQueue = async (db, dbId) => {
11
+ console.log("---------------------------------");
12
+ console.log(`Starting Queue processing of ${dbId}`);
13
+ console.log("---------------------------------");
14
+ let progress = true;
15
+ while (progress) {
16
+ progress = false;
17
+ console.log("Processing queued operations:");
18
+ for (let i = 0; i < queuedOperations.length; i++) {
19
+ const operation = queuedOperations[i];
20
+ let collectionFound;
21
+ // Handle relationship attribute operations
22
+ if (operation.attribute?.type === "relationship") {
23
+ // Attempt to resolve the collection directly if collectionId is specified
24
+ if (operation.collectionId) {
25
+ console.log(`\tFetching collection by ID: ${operation.collectionId}`);
26
+ try {
27
+ collectionFound = await tryAwaitWithRetry(async () => await db.getCollection(dbId, operation.collectionId));
28
+ }
29
+ catch (e) {
30
+ console.log(`\tCollection not found by ID: ${operation.collectionId}`);
31
+ }
32
+ }
33
+ // Attempt to resolve related collection if specified and not already found
34
+ if (!collectionFound && operation.attribute?.relatedCollection) {
35
+ collectionFound = await fetchAndCacheCollectionByName(db, dbId, operation.attribute.relatedCollection);
36
+ }
37
+ // Handle dependencies if collection still not found
38
+ if (!collectionFound) {
39
+ for (const dep of operation.dependencies || []) {
40
+ collectionFound = await fetchAndCacheCollectionByName(db, dbId, dep);
41
+ if (collectionFound)
42
+ break; // Break early if collection is found
43
+ }
44
+ }
45
+ }
46
+ else if (operation.collectionId) {
47
+ // Handle non-relationship operations with a specified collectionId
48
+ console.log(`\tFetching collection by ID: ${operation.collectionId}`);
49
+ try {
50
+ collectionFound = await tryAwaitWithRetry(async () => await db.getCollection(dbId, operation.collectionId));
51
+ }
52
+ catch (e) {
53
+ console.log(`\tCollection not found by ID: ${operation.collectionId}`);
54
+ }
55
+ }
56
+ // Process the operation if the collection is found
57
+ if (collectionFound && operation.attribute) {
58
+ console.log(`\tProcessing attribute: ${operation.attribute.key} for collection ID: ${collectionFound.$id}`);
59
+ await createOrUpdateAttribute(db, dbId, collectionFound, operation.attribute);
60
+ queuedOperations.splice(i, 1);
61
+ i--; // Adjust index since we're modifying the array
62
+ progress = true;
63
+ }
64
+ else {
65
+ console.error(`\tCollection not found for operation, removing from queue: ${JSON.stringify(operation)}`);
66
+ queuedOperations.splice(i, 1);
67
+ i--; // Adjust index since we're modifying the array
68
+ }
69
+ }
70
+ console.log(`\tFinished processing queued operations`);
71
+ }
72
+ if (queuedOperations.length > 0) {
73
+ console.error("Unresolved operations remain due to unmet dependencies.");
74
+ console.log(queuedOperations);
75
+ }
76
+ console.log("---------------------------------");
77
+ console.log(`Queue processing complete for ${dbId}`);
78
+ console.log("---------------------------------");
79
+ };
@@ -0,0 +1,62 @@
1
+ export interface ProgressOptions {
2
+ title?: string;
3
+ showETA?: boolean;
4
+ showSpeed?: boolean;
5
+ showPercentage?: boolean;
6
+ width?: number;
7
+ format?: string;
8
+ }
9
+ export declare class ProgressManager {
10
+ private static instances;
11
+ private bar;
12
+ private startTime;
13
+ private totalItems;
14
+ private completed;
15
+ private id;
16
+ private title;
17
+ private constructor();
18
+ static create(id: string, total: number, options?: ProgressOptions): ProgressManager;
19
+ static get(id: string): ProgressManager | undefined;
20
+ update(current: number, detail?: string): void;
21
+ increment(amount?: number, detail?: string): void;
22
+ setTotal(total: number): void;
23
+ stop(showSummary?: boolean): void;
24
+ fail(error: string): void;
25
+ getStats(): {
26
+ completed: number;
27
+ total: number;
28
+ percentage: number;
29
+ duration: number;
30
+ rate: number;
31
+ remaining: number;
32
+ eta: number;
33
+ };
34
+ static stopAll(): void;
35
+ }
36
+ export declare class MultiProgressManager {
37
+ private multiBar;
38
+ private bars;
39
+ private startTime;
40
+ constructor(options?: ProgressOptions);
41
+ addTask(id: string, total: number, title: string): void;
42
+ updateTask(id: string, current: number, detail?: string): void;
43
+ incrementTask(id: string, amount?: number, detail?: string): void;
44
+ completeTask(id: string): void;
45
+ failTask(id: string, error: string): void;
46
+ stop(showSummary?: boolean): void;
47
+ getTaskStats(id: string): {
48
+ completed: number;
49
+ total: number;
50
+ percentage: number;
51
+ remaining: number;
52
+ } | null;
53
+ getAllStats(): Map<string, any>;
54
+ }
55
+ export declare const ProgressUtils: {
56
+ withProgress<T>(id: string, total: number, title: string, operation: (progress: ProgressManager) => Promise<T>): Promise<T>;
57
+ processArrayWithProgress<T, R>(items: T[], processor: (item: T, index: number) => Promise<R>, options?: {
58
+ title?: string;
59
+ batchSize?: number;
60
+ showDetail?: boolean;
61
+ }): Promise<R[]>;
62
+ };