@constructive-io/graphql-codegen 2.19.0 → 2.20.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 (301) hide show
  1. package/README.md +1818 -113
  2. package/__tests__/codegen/input-types-generator.test.d.ts +1 -0
  3. package/__tests__/codegen/input-types-generator.test.js +635 -0
  4. package/cli/codegen/barrel.d.ts +27 -0
  5. package/cli/codegen/barrel.js +163 -0
  6. package/cli/codegen/client.d.ts +4 -0
  7. package/cli/codegen/client.js +170 -0
  8. package/cli/codegen/custom-mutations.d.ts +38 -0
  9. package/cli/codegen/custom-mutations.js +149 -0
  10. package/cli/codegen/custom-queries.d.ts +38 -0
  11. package/cli/codegen/custom-queries.js +358 -0
  12. package/cli/codegen/filters.d.ts +27 -0
  13. package/cli/codegen/filters.js +357 -0
  14. package/cli/codegen/gql-ast.d.ts +41 -0
  15. package/cli/codegen/gql-ast.js +329 -0
  16. package/cli/codegen/index.d.ts +71 -0
  17. package/cli/codegen/index.js +147 -0
  18. package/cli/codegen/mutations.d.ts +30 -0
  19. package/cli/codegen/mutations.js +410 -0
  20. package/cli/codegen/orm/barrel.d.ts +18 -0
  21. package/cli/codegen/orm/barrel.js +48 -0
  22. package/cli/codegen/orm/client-generator.d.ts +45 -0
  23. package/cli/codegen/orm/client-generator.js +646 -0
  24. package/cli/codegen/orm/custom-ops-generator.d.ts +30 -0
  25. package/cli/codegen/orm/custom-ops-generator.js +350 -0
  26. package/cli/codegen/orm/index.d.ts +38 -0
  27. package/cli/codegen/orm/index.js +88 -0
  28. package/cli/codegen/orm/input-types-generator.d.ts +21 -0
  29. package/cli/codegen/orm/input-types-generator.js +705 -0
  30. package/cli/codegen/orm/input-types-generator.test.d.ts +1 -0
  31. package/cli/codegen/orm/input-types-generator.test.js +75 -0
  32. package/cli/codegen/orm/model-generator.d.ts +32 -0
  33. package/cli/codegen/orm/model-generator.js +264 -0
  34. package/cli/codegen/orm/query-builder.d.ts +161 -0
  35. package/cli/codegen/orm/query-builder.js +366 -0
  36. package/cli/codegen/orm/select-types.d.ts +169 -0
  37. package/cli/codegen/orm/select-types.js +16 -0
  38. package/cli/codegen/orm/select-types.test.d.ts +11 -0
  39. package/cli/codegen/orm/select-types.test.js +22 -0
  40. package/cli/codegen/queries.d.ts +25 -0
  41. package/cli/codegen/queries.js +438 -0
  42. package/cli/codegen/scalars.d.ts +12 -0
  43. package/cli/codegen/scalars.js +71 -0
  44. package/cli/codegen/schema-gql-ast.d.ts +51 -0
  45. package/cli/codegen/schema-gql-ast.js +385 -0
  46. package/cli/codegen/ts-ast.d.ts +122 -0
  47. package/cli/codegen/ts-ast.js +280 -0
  48. package/cli/codegen/type-resolver.d.ts +96 -0
  49. package/cli/codegen/type-resolver.js +246 -0
  50. package/cli/codegen/types.d.ts +12 -0
  51. package/cli/codegen/types.js +69 -0
  52. package/cli/codegen/utils.d.ts +163 -0
  53. package/cli/codegen/utils.js +326 -0
  54. package/cli/commands/generate-orm.d.ts +37 -0
  55. package/cli/commands/generate-orm.js +195 -0
  56. package/cli/commands/generate.d.ts +39 -0
  57. package/cli/commands/generate.js +299 -0
  58. package/cli/commands/index.d.ts +7 -0
  59. package/cli/commands/index.js +12 -0
  60. package/cli/commands/init.d.ts +35 -0
  61. package/cli/commands/init.js +176 -0
  62. package/cli/index.d.ts +4 -0
  63. package/cli/index.js +291 -0
  64. package/cli/introspect/fetch-meta.d.ts +31 -0
  65. package/cli/introspect/fetch-meta.js +108 -0
  66. package/cli/introspect/fetch-schema.d.ts +21 -0
  67. package/cli/introspect/fetch-schema.js +86 -0
  68. package/cli/introspect/index.d.ts +8 -0
  69. package/cli/introspect/index.js +16 -0
  70. package/cli/introspect/meta-query.d.ts +111 -0
  71. package/cli/introspect/meta-query.js +191 -0
  72. package/cli/introspect/schema-query.d.ts +20 -0
  73. package/cli/introspect/schema-query.js +123 -0
  74. package/cli/introspect/transform-schema.d.ts +74 -0
  75. package/cli/introspect/transform-schema.js +269 -0
  76. package/cli/introspect/transform-schema.test.d.ts +1 -0
  77. package/cli/introspect/transform-schema.test.js +67 -0
  78. package/cli/introspect/transform.d.ts +21 -0
  79. package/cli/introspect/transform.js +216 -0
  80. package/cli/watch/cache.d.ts +45 -0
  81. package/cli/watch/cache.js +111 -0
  82. package/cli/watch/debounce.d.ts +19 -0
  83. package/cli/watch/debounce.js +89 -0
  84. package/cli/watch/hash.d.ts +17 -0
  85. package/cli/watch/hash.js +48 -0
  86. package/cli/watch/index.d.ts +10 -0
  87. package/cli/watch/index.js +22 -0
  88. package/cli/watch/orchestrator.d.ts +63 -0
  89. package/cli/watch/orchestrator.js +228 -0
  90. package/cli/watch/poller.d.ts +65 -0
  91. package/cli/watch/poller.js +203 -0
  92. package/cli/watch/types.d.ts +67 -0
  93. package/cli/watch/types.js +5 -0
  94. package/client/error.d.ts +95 -0
  95. package/client/error.js +255 -0
  96. package/client/execute.d.ts +57 -0
  97. package/client/execute.js +124 -0
  98. package/client/index.d.ts +6 -0
  99. package/client/index.js +18 -0
  100. package/client/typed-document.d.ts +31 -0
  101. package/client/typed-document.js +44 -0
  102. package/core/ast.d.ts +10 -0
  103. package/core/ast.js +593 -0
  104. package/core/custom-ast.d.ts +35 -0
  105. package/core/custom-ast.js +204 -0
  106. package/core/index.d.ts +8 -0
  107. package/core/index.js +33 -0
  108. package/core/meta-object/convert.d.ts +65 -0
  109. package/core/meta-object/convert.js +63 -0
  110. package/core/meta-object/format.json +93 -0
  111. package/core/meta-object/index.d.ts +2 -0
  112. package/core/meta-object/index.js +18 -0
  113. package/core/meta-object/validate.d.ts +9 -0
  114. package/core/meta-object/validate.js +34 -0
  115. package/core/query-builder.d.ts +46 -0
  116. package/core/query-builder.js +412 -0
  117. package/core/types.d.ts +139 -0
  118. package/core/types.js +28 -0
  119. package/esm/__tests__/codegen/input-types-generator.test.d.ts +1 -0
  120. package/esm/__tests__/codegen/input-types-generator.test.js +633 -0
  121. package/esm/cli/codegen/barrel.d.ts +27 -0
  122. package/esm/cli/codegen/barrel.js +156 -0
  123. package/esm/cli/codegen/client.d.ts +4 -0
  124. package/esm/cli/codegen/client.js +167 -0
  125. package/esm/cli/codegen/custom-mutations.d.ts +38 -0
  126. package/esm/cli/codegen/custom-mutations.js +145 -0
  127. package/esm/cli/codegen/custom-queries.d.ts +38 -0
  128. package/esm/cli/codegen/custom-queries.js +354 -0
  129. package/esm/cli/codegen/filters.d.ts +27 -0
  130. package/esm/cli/codegen/filters.js +351 -0
  131. package/esm/cli/codegen/gql-ast.d.ts +41 -0
  132. package/esm/cli/codegen/gql-ast.js +288 -0
  133. package/esm/cli/codegen/index.d.ts +71 -0
  134. package/esm/cli/codegen/index.js +124 -0
  135. package/esm/cli/codegen/mutations.d.ts +30 -0
  136. package/esm/cli/codegen/mutations.js +404 -0
  137. package/esm/cli/codegen/orm/barrel.d.ts +18 -0
  138. package/esm/cli/codegen/orm/barrel.js +44 -0
  139. package/esm/cli/codegen/orm/client-generator.d.ts +45 -0
  140. package/esm/cli/codegen/orm/client-generator.js +640 -0
  141. package/esm/cli/codegen/orm/custom-ops-generator.d.ts +30 -0
  142. package/esm/cli/codegen/orm/custom-ops-generator.js +346 -0
  143. package/esm/cli/codegen/orm/index.d.ts +38 -0
  144. package/esm/cli/codegen/orm/index.js +75 -0
  145. package/esm/cli/codegen/orm/input-types-generator.d.ts +21 -0
  146. package/esm/cli/codegen/orm/input-types-generator.js +700 -0
  147. package/esm/cli/codegen/orm/input-types-generator.test.d.ts +1 -0
  148. package/esm/cli/codegen/orm/input-types-generator.test.js +73 -0
  149. package/esm/cli/codegen/orm/model-generator.d.ts +32 -0
  150. package/esm/cli/codegen/orm/model-generator.js +260 -0
  151. package/esm/cli/codegen/orm/query-builder.d.ts +161 -0
  152. package/esm/cli/codegen/orm/query-builder.js +353 -0
  153. package/esm/cli/codegen/orm/select-types.d.ts +169 -0
  154. package/esm/cli/codegen/orm/select-types.js +15 -0
  155. package/esm/cli/codegen/orm/select-types.test.d.ts +11 -0
  156. package/esm/cli/codegen/orm/select-types.test.js +21 -0
  157. package/esm/cli/codegen/queries.d.ts +25 -0
  158. package/esm/cli/codegen/queries.js +433 -0
  159. package/esm/cli/codegen/scalars.d.ts +12 -0
  160. package/esm/cli/codegen/scalars.js +66 -0
  161. package/esm/cli/codegen/schema-gql-ast.d.ts +51 -0
  162. package/esm/cli/codegen/schema-gql-ast.js +343 -0
  163. package/esm/cli/codegen/ts-ast.d.ts +122 -0
  164. package/esm/cli/codegen/ts-ast.js +260 -0
  165. package/esm/cli/codegen/type-resolver.d.ts +96 -0
  166. package/esm/cli/codegen/type-resolver.js +224 -0
  167. package/esm/cli/codegen/types.d.ts +12 -0
  168. package/esm/cli/codegen/types.js +65 -0
  169. package/esm/cli/codegen/utils.d.ts +163 -0
  170. package/esm/cli/codegen/utils.js +288 -0
  171. package/esm/cli/commands/generate-orm.d.ts +37 -0
  172. package/esm/cli/commands/generate-orm.js +192 -0
  173. package/esm/cli/commands/generate.d.ts +39 -0
  174. package/esm/cli/commands/generate.js +262 -0
  175. package/esm/cli/commands/index.d.ts +7 -0
  176. package/esm/cli/commands/index.js +5 -0
  177. package/esm/cli/commands/init.d.ts +35 -0
  178. package/esm/cli/commands/init.js +138 -0
  179. package/esm/cli/index.d.ts +4 -0
  180. package/esm/cli/index.js +256 -0
  181. package/esm/cli/introspect/fetch-meta.d.ts +31 -0
  182. package/esm/cli/introspect/fetch-meta.js +104 -0
  183. package/esm/cli/introspect/fetch-schema.d.ts +21 -0
  184. package/esm/cli/introspect/fetch-schema.js +83 -0
  185. package/esm/cli/introspect/index.d.ts +8 -0
  186. package/esm/cli/introspect/index.js +6 -0
  187. package/esm/cli/introspect/meta-query.d.ts +111 -0
  188. package/esm/cli/introspect/meta-query.js +188 -0
  189. package/esm/cli/introspect/schema-query.d.ts +20 -0
  190. package/esm/cli/introspect/schema-query.js +120 -0
  191. package/esm/cli/introspect/transform-schema.d.ts +74 -0
  192. package/esm/cli/introspect/transform-schema.js +259 -0
  193. package/esm/cli/introspect/transform-schema.test.d.ts +1 -0
  194. package/esm/cli/introspect/transform-schema.test.js +65 -0
  195. package/esm/cli/introspect/transform.d.ts +21 -0
  196. package/esm/cli/introspect/transform.js +210 -0
  197. package/esm/cli/watch/cache.d.ts +45 -0
  198. package/esm/cli/watch/cache.js +73 -0
  199. package/esm/cli/watch/debounce.d.ts +19 -0
  200. package/esm/cli/watch/debounce.js +85 -0
  201. package/esm/cli/watch/hash.d.ts +17 -0
  202. package/esm/cli/watch/hash.js +43 -0
  203. package/esm/cli/watch/index.d.ts +10 -0
  204. package/esm/cli/watch/index.js +8 -0
  205. package/esm/cli/watch/orchestrator.d.ts +63 -0
  206. package/esm/cli/watch/orchestrator.js +223 -0
  207. package/esm/cli/watch/poller.d.ts +65 -0
  208. package/esm/cli/watch/poller.js +198 -0
  209. package/esm/cli/watch/types.d.ts +67 -0
  210. package/esm/cli/watch/types.js +4 -0
  211. package/esm/client/error.d.ts +95 -0
  212. package/esm/client/error.js +249 -0
  213. package/esm/client/execute.d.ts +57 -0
  214. package/esm/client/execute.js +120 -0
  215. package/esm/client/index.d.ts +6 -0
  216. package/esm/client/index.js +6 -0
  217. package/esm/client/typed-document.d.ts +31 -0
  218. package/esm/client/typed-document.js +40 -0
  219. package/esm/core/ast.d.ts +10 -0
  220. package/esm/core/ast.js +549 -0
  221. package/esm/core/custom-ast.d.ts +35 -0
  222. package/esm/core/custom-ast.js +161 -0
  223. package/esm/core/index.d.ts +8 -0
  224. package/esm/core/index.js +12 -0
  225. package/esm/core/meta-object/convert.d.ts +65 -0
  226. package/esm/core/meta-object/convert.js +60 -0
  227. package/esm/core/meta-object/format.json +93 -0
  228. package/esm/core/meta-object/index.d.ts +2 -0
  229. package/esm/core/meta-object/index.js +2 -0
  230. package/esm/core/meta-object/validate.d.ts +9 -0
  231. package/esm/core/meta-object/validate.js +28 -0
  232. package/esm/core/query-builder.d.ts +46 -0
  233. package/esm/core/query-builder.js +375 -0
  234. package/esm/core/types.d.ts +139 -0
  235. package/esm/core/types.js +24 -0
  236. package/esm/generators/field-selector.d.ts +30 -0
  237. package/esm/generators/field-selector.js +355 -0
  238. package/esm/generators/index.d.ts +6 -0
  239. package/esm/generators/index.js +9 -0
  240. package/esm/generators/mutations.d.ts +31 -0
  241. package/esm/generators/mutations.js +197 -0
  242. package/esm/generators/select.d.ts +50 -0
  243. package/esm/generators/select.js +636 -0
  244. package/esm/index.d.ts +12 -0
  245. package/esm/index.js +17 -3
  246. package/esm/react/index.d.ts +5 -0
  247. package/esm/react/index.js +6 -0
  248. package/esm/types/config.d.ts +199 -0
  249. package/esm/types/config.js +106 -0
  250. package/esm/types/index.d.ts +9 -0
  251. package/esm/types/index.js +4 -0
  252. package/esm/types/introspection.d.ts +121 -0
  253. package/esm/types/introspection.js +54 -0
  254. package/esm/types/mutation.d.ts +45 -0
  255. package/esm/types/mutation.js +4 -0
  256. package/esm/types/query.d.ts +82 -0
  257. package/esm/types/query.js +4 -0
  258. package/esm/types/schema.d.ts +253 -0
  259. package/esm/types/schema.js +5 -0
  260. package/esm/types/selection.d.ts +43 -0
  261. package/esm/types/selection.js +4 -0
  262. package/esm/utils/index.d.ts +4 -0
  263. package/esm/utils/index.js +4 -0
  264. package/generators/field-selector.d.ts +30 -0
  265. package/generators/field-selector.js +361 -0
  266. package/generators/index.d.ts +6 -0
  267. package/generators/index.js +27 -0
  268. package/generators/mutations.d.ts +31 -0
  269. package/generators/mutations.js +235 -0
  270. package/generators/select.d.ts +50 -0
  271. package/generators/select.js +679 -0
  272. package/index.d.ts +12 -3
  273. package/index.js +19 -3
  274. package/package.json +59 -38
  275. package/react/index.d.ts +5 -0
  276. package/react/index.js +9 -0
  277. package/types/config.d.ts +199 -0
  278. package/types/config.js +111 -0
  279. package/types/index.d.ts +9 -0
  280. package/types/index.js +10 -0
  281. package/types/introspection.d.ts +121 -0
  282. package/types/introspection.js +62 -0
  283. package/types/mutation.d.ts +45 -0
  284. package/types/mutation.js +5 -0
  285. package/types/query.d.ts +82 -0
  286. package/types/query.js +5 -0
  287. package/types/schema.d.ts +253 -0
  288. package/types/schema.js +6 -0
  289. package/types/selection.d.ts +43 -0
  290. package/types/selection.js +5 -0
  291. package/utils/index.d.ts +4 -0
  292. package/utils/index.js +7 -0
  293. package/codegen.d.ts +0 -13
  294. package/codegen.js +0 -293
  295. package/esm/codegen.js +0 -253
  296. package/esm/gql.js +0 -939
  297. package/esm/options.js +0 -27
  298. package/gql.d.ts +0 -188
  299. package/gql.js +0 -992
  300. package/options.d.ts +0 -45
  301. package/options.js +0 -31
@@ -0,0 +1,203 @@
1
+ "use strict";
2
+ /**
3
+ * Schema polling logic with EventEmitter pattern
4
+ *
5
+ * Uses in-memory hash comparison for efficiency.
6
+ * No file I/O during normal polling - only touchFile is optional file write.
7
+ */
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ exports.SchemaPoller = void 0;
10
+ exports.computeSchemaHash = computeSchemaHash;
11
+ const node_events_1 = require("node:events");
12
+ const fetch_meta_1 = require("../introspect/fetch-meta");
13
+ const fetch_schema_1 = require("../introspect/fetch-schema");
14
+ const cache_1 = require("./cache");
15
+ const hash_1 = require("./hash");
16
+ /**
17
+ * Schema poller that periodically introspects a GraphQL endpoint
18
+ * and emits events when the schema changes.
19
+ *
20
+ * Uses in-memory caching for hash comparison - no file I/O overhead.
21
+ */
22
+ class SchemaPoller extends node_events_1.EventEmitter {
23
+ options;
24
+ cache;
25
+ pollTimer = null;
26
+ isPolling = false;
27
+ consecutiveErrors = 0;
28
+ MAX_CONSECUTIVE_ERRORS = 5;
29
+ constructor(options) {
30
+ super();
31
+ this.options = options;
32
+ this.cache = new cache_1.SchemaCache();
33
+ }
34
+ /**
35
+ * Start the polling loop
36
+ */
37
+ start() {
38
+ if (this.pollTimer) {
39
+ return; // Already running
40
+ }
41
+ // Do an immediate poll
42
+ this.poll();
43
+ // Set up interval
44
+ this.pollTimer = setInterval(() => {
45
+ this.poll();
46
+ }, this.options.pollInterval);
47
+ }
48
+ /**
49
+ * Stop the polling loop
50
+ */
51
+ stop() {
52
+ if (this.pollTimer) {
53
+ clearInterval(this.pollTimer);
54
+ this.pollTimer = null;
55
+ }
56
+ }
57
+ /**
58
+ * Perform a single poll operation
59
+ */
60
+ async poll() {
61
+ // Prevent concurrent polls
62
+ if (this.isPolling) {
63
+ return { success: false, changed: false, error: 'Poll already in progress' };
64
+ }
65
+ this.isPolling = true;
66
+ const startTime = Date.now();
67
+ this.emit('poll-start', this.createEvent('poll-start'));
68
+ try {
69
+ // Fetch both _meta and __schema
70
+ const [metaResult, schemaResult] = await Promise.all([
71
+ (0, fetch_meta_1.fetchMeta)({
72
+ endpoint: this.options.endpoint,
73
+ authorization: this.options.authorization,
74
+ headers: this.options.headers,
75
+ timeout: 30000,
76
+ }),
77
+ (0, fetch_schema_1.fetchSchema)({
78
+ endpoint: this.options.endpoint,
79
+ authorization: this.options.authorization,
80
+ headers: this.options.headers,
81
+ timeout: 30000,
82
+ }),
83
+ ]);
84
+ const duration = Date.now() - startTime;
85
+ // Check for errors
86
+ if (!metaResult.success) {
87
+ return this.handleError(`_meta fetch failed: ${metaResult.error}`, duration);
88
+ }
89
+ if (!schemaResult.success) {
90
+ return this.handleError(`__schema fetch failed: ${schemaResult.error}`, duration);
91
+ }
92
+ const meta = metaResult.data;
93
+ const schema = schemaResult.data;
94
+ // Check if schema changed
95
+ const { changed, newHash } = await this.cache.hasChanged(meta, schema);
96
+ // Reset error counter on success
97
+ this.consecutiveErrors = 0;
98
+ if (changed) {
99
+ // Update in-memory hash
100
+ this.cache.updateHash(newHash);
101
+ // Touch trigger file if configured (only file I/O in watch mode)
102
+ if (this.options.touchFile) {
103
+ (0, cache_1.touchFile)(this.options.touchFile);
104
+ }
105
+ this.emit('schema-changed', this.createEvent('schema-changed', { hash: newHash, duration }));
106
+ return { success: true, changed: true, hash: newHash, meta, schema };
107
+ }
108
+ this.emit('schema-unchanged', this.createEvent('schema-unchanged', { duration }));
109
+ this.emit('poll-success', this.createEvent('poll-success', { duration }));
110
+ return { success: true, changed: false, hash: newHash, meta, schema };
111
+ }
112
+ catch (err) {
113
+ const duration = Date.now() - startTime;
114
+ const error = err instanceof Error ? err.message : 'Unknown error';
115
+ return this.handleError(error, duration);
116
+ }
117
+ finally {
118
+ this.isPolling = false;
119
+ }
120
+ }
121
+ /**
122
+ * Perform a single poll without starting the loop (for initial generation)
123
+ */
124
+ async pollOnce() {
125
+ return this.poll();
126
+ }
127
+ /**
128
+ * Seed the cache with current schema hash without emitting events.
129
+ * Call this after initial generation to prevent first poll from triggering regeneration.
130
+ */
131
+ async seedCache() {
132
+ try {
133
+ const [metaResult, schemaResult] = await Promise.all([
134
+ (0, fetch_meta_1.fetchMeta)({
135
+ endpoint: this.options.endpoint,
136
+ authorization: this.options.authorization,
137
+ headers: this.options.headers,
138
+ timeout: 30000,
139
+ }),
140
+ (0, fetch_schema_1.fetchSchema)({
141
+ endpoint: this.options.endpoint,
142
+ authorization: this.options.authorization,
143
+ headers: this.options.headers,
144
+ timeout: 30000,
145
+ }),
146
+ ]);
147
+ if (metaResult.success && schemaResult.success) {
148
+ const { newHash } = await this.cache.hasChanged(metaResult.data, schemaResult.data);
149
+ this.cache.updateHash(newHash);
150
+ }
151
+ }
152
+ catch {
153
+ // Silently fail - cache will be seeded on first successful poll
154
+ }
155
+ }
156
+ /**
157
+ * Get the current cached schema hash
158
+ */
159
+ getCurrentHash() {
160
+ return this.cache.getHash();
161
+ }
162
+ /**
163
+ * Get the cache instance for direct access
164
+ */
165
+ getCache() {
166
+ return this.cache;
167
+ }
168
+ /**
169
+ * Check if the poller is currently running
170
+ */
171
+ isRunning() {
172
+ return this.pollTimer !== null;
173
+ }
174
+ handleError(error, duration) {
175
+ this.consecutiveErrors++;
176
+ this.emit('poll-error', this.createEvent('poll-error', { error, duration }));
177
+ // Slow down polling after multiple consecutive errors
178
+ if (this.consecutiveErrors >= this.MAX_CONSECUTIVE_ERRORS && this.pollTimer) {
179
+ this.stop();
180
+ const newInterval = this.options.pollInterval * 2;
181
+ this.pollTimer = setInterval(() => {
182
+ this.poll();
183
+ }, newInterval);
184
+ }
185
+ return { success: false, changed: false, error };
186
+ }
187
+ createEvent(type, extra) {
188
+ return {
189
+ type,
190
+ timestamp: Date.now(),
191
+ ...extra,
192
+ };
193
+ }
194
+ }
195
+ exports.SchemaPoller = SchemaPoller;
196
+ /**
197
+ * Utility to compute schema hash without full poll
198
+ */
199
+ async function computeSchemaHash(meta, schema) {
200
+ const metaHash = await (0, hash_1.hashObject)(meta);
201
+ const schemaHash = await (0, hash_1.hashObject)(schema);
202
+ return (0, hash_1.combineHashes)(metaHash, schemaHash);
203
+ }
@@ -0,0 +1,67 @@
1
+ /**
2
+ * Watch mode types
3
+ */
4
+ import type { MetaQueryResponse } from '../introspect/meta-query';
5
+ import type { IntrospectionQueryResponse } from '../../types/introspection';
6
+ /**
7
+ * Result of a schema poll operation
8
+ */
9
+ export interface PollResult {
10
+ success: boolean;
11
+ /** Whether the schema changed since last poll */
12
+ changed: boolean;
13
+ /** Error message if poll failed */
14
+ error?: string;
15
+ /** The new hash if successful */
16
+ hash?: string;
17
+ /** Meta response if successful */
18
+ meta?: MetaQueryResponse;
19
+ /** Schema response if successful */
20
+ schema?: IntrospectionQueryResponse;
21
+ }
22
+ /**
23
+ * Watch mode options passed to the watch orchestrator
24
+ */
25
+ export interface WatchOptions {
26
+ /** GraphQL endpoint URL */
27
+ endpoint: string;
28
+ /** Authorization header value */
29
+ authorization?: string;
30
+ /** Additional headers */
31
+ headers?: Record<string, string>;
32
+ /** Polling interval in ms */
33
+ pollInterval: number;
34
+ /** Debounce delay in ms */
35
+ debounce: number;
36
+ /** File to touch on schema change (optional) */
37
+ touchFile: string | null;
38
+ /** Clear terminal on regeneration */
39
+ clearScreen: boolean;
40
+ /** Verbose output */
41
+ verbose: boolean;
42
+ }
43
+ /**
44
+ * Events emitted by the SchemaPoller
45
+ */
46
+ export type PollEventType = 'poll-start' | 'poll-success' | 'poll-error' | 'schema-changed' | 'schema-unchanged';
47
+ /**
48
+ * Event handler signature for poll events
49
+ */
50
+ export type PollEventHandler = (event: PollEvent) => void;
51
+ /**
52
+ * Poll event payload
53
+ */
54
+ export interface PollEvent {
55
+ type: PollEventType;
56
+ timestamp: number;
57
+ /** Error message if type is 'poll-error' */
58
+ error?: string;
59
+ /** New hash if schema changed */
60
+ hash?: string;
61
+ /** Duration of the poll in ms */
62
+ duration?: number;
63
+ }
64
+ /**
65
+ * Generator type for watch mode
66
+ */
67
+ export type GeneratorType = 'generate' | 'generate-orm';
@@ -0,0 +1,5 @@
1
+ "use strict";
2
+ /**
3
+ * Watch mode types
4
+ */
5
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,95 @@
1
+ /**
2
+ * Error handling for GraphQL operations
3
+ * Provides consistent error types and parsing for PostGraphile responses
4
+ */
5
+ export declare const DataErrorType: {
6
+ readonly NETWORK_ERROR: "NETWORK_ERROR";
7
+ readonly TIMEOUT_ERROR: "TIMEOUT_ERROR";
8
+ readonly VALIDATION_FAILED: "VALIDATION_FAILED";
9
+ readonly REQUIRED_FIELD_MISSING: "REQUIRED_FIELD_MISSING";
10
+ readonly INVALID_MUTATION_DATA: "INVALID_MUTATION_DATA";
11
+ readonly QUERY_GENERATION_FAILED: "QUERY_GENERATION_FAILED";
12
+ readonly QUERY_EXECUTION_FAILED: "QUERY_EXECUTION_FAILED";
13
+ readonly UNAUTHORIZED: "UNAUTHORIZED";
14
+ readonly FORBIDDEN: "FORBIDDEN";
15
+ readonly TABLE_NOT_FOUND: "TABLE_NOT_FOUND";
16
+ readonly BAD_REQUEST: "BAD_REQUEST";
17
+ readonly NOT_FOUND: "NOT_FOUND";
18
+ readonly GRAPHQL_ERROR: "GRAPHQL_ERROR";
19
+ readonly UNIQUE_VIOLATION: "UNIQUE_VIOLATION";
20
+ readonly FOREIGN_KEY_VIOLATION: "FOREIGN_KEY_VIOLATION";
21
+ readonly NOT_NULL_VIOLATION: "NOT_NULL_VIOLATION";
22
+ readonly CHECK_VIOLATION: "CHECK_VIOLATION";
23
+ readonly EXCLUSION_VIOLATION: "EXCLUSION_VIOLATION";
24
+ readonly UNKNOWN_ERROR: "UNKNOWN_ERROR";
25
+ };
26
+ export type DataErrorType = (typeof DataErrorType)[keyof typeof DataErrorType];
27
+ export interface DataErrorOptions {
28
+ tableName?: string;
29
+ fieldName?: string;
30
+ constraint?: string;
31
+ originalError?: Error;
32
+ code?: string;
33
+ context?: Record<string, unknown>;
34
+ }
35
+ /**
36
+ * Standard error class for data layer operations
37
+ */
38
+ export declare class DataError extends Error {
39
+ readonly type: DataErrorType;
40
+ readonly code?: string;
41
+ readonly originalError?: Error;
42
+ readonly context?: Record<string, unknown>;
43
+ readonly tableName?: string;
44
+ readonly fieldName?: string;
45
+ readonly constraint?: string;
46
+ constructor(type: DataErrorType, message: string, options?: DataErrorOptions);
47
+ getUserMessage(): string;
48
+ isRetryable(): boolean;
49
+ }
50
+ export declare const PG_ERROR_CODES: {
51
+ readonly UNIQUE_VIOLATION: "23505";
52
+ readonly FOREIGN_KEY_VIOLATION: "23503";
53
+ readonly NOT_NULL_VIOLATION: "23502";
54
+ readonly CHECK_VIOLATION: "23514";
55
+ readonly EXCLUSION_VIOLATION: "23P01";
56
+ readonly NUMERIC_VALUE_OUT_OF_RANGE: "22003";
57
+ readonly STRING_DATA_RIGHT_TRUNCATION: "22001";
58
+ readonly INVALID_TEXT_REPRESENTATION: "22P02";
59
+ readonly DATETIME_FIELD_OVERFLOW: "22008";
60
+ readonly UNDEFINED_TABLE: "42P01";
61
+ readonly UNDEFINED_COLUMN: "42703";
62
+ readonly INSUFFICIENT_PRIVILEGE: "42501";
63
+ };
64
+ export declare const createError: {
65
+ network: (originalError?: Error) => DataError;
66
+ timeout: (originalError?: Error) => DataError;
67
+ unauthorized: (message?: string) => DataError;
68
+ forbidden: (message?: string) => DataError;
69
+ badRequest: (message: string, code?: string) => DataError;
70
+ notFound: (message?: string) => DataError;
71
+ graphql: (message: string, code?: string) => DataError;
72
+ uniqueViolation: (message: string, fieldName?: string, constraint?: string) => DataError;
73
+ foreignKeyViolation: (message: string, fieldName?: string, constraint?: string) => DataError;
74
+ notNullViolation: (message: string, fieldName?: string, constraint?: string) => DataError;
75
+ unknown: (originalError: Error) => DataError;
76
+ };
77
+ export interface GraphQLError {
78
+ message: string;
79
+ extensions?: {
80
+ code?: string;
81
+ } & Record<string, unknown>;
82
+ locations?: Array<{
83
+ line: number;
84
+ column: number;
85
+ }>;
86
+ path?: Array<string | number>;
87
+ }
88
+ /**
89
+ * Parse any error into a DataError
90
+ */
91
+ export declare function parseGraphQLError(error: unknown): DataError;
92
+ /**
93
+ * Check if value is a DataError
94
+ */
95
+ export declare function isDataError(error: unknown): error is DataError;
@@ -0,0 +1,255 @@
1
+ "use strict";
2
+ /**
3
+ * Error handling for GraphQL operations
4
+ * Provides consistent error types and parsing for PostGraphile responses
5
+ */
6
+ Object.defineProperty(exports, "__esModule", { value: true });
7
+ exports.createError = exports.PG_ERROR_CODES = exports.DataError = exports.DataErrorType = void 0;
8
+ exports.parseGraphQLError = parseGraphQLError;
9
+ exports.isDataError = isDataError;
10
+ // ============================================================================
11
+ // Error Types
12
+ // ============================================================================
13
+ exports.DataErrorType = {
14
+ // Network/Connection errors
15
+ NETWORK_ERROR: 'NETWORK_ERROR',
16
+ TIMEOUT_ERROR: 'TIMEOUT_ERROR',
17
+ // Validation errors
18
+ VALIDATION_FAILED: 'VALIDATION_FAILED',
19
+ REQUIRED_FIELD_MISSING: 'REQUIRED_FIELD_MISSING',
20
+ INVALID_MUTATION_DATA: 'INVALID_MUTATION_DATA',
21
+ // Query errors
22
+ QUERY_GENERATION_FAILED: 'QUERY_GENERATION_FAILED',
23
+ QUERY_EXECUTION_FAILED: 'QUERY_EXECUTION_FAILED',
24
+ // Permission errors
25
+ UNAUTHORIZED: 'UNAUTHORIZED',
26
+ FORBIDDEN: 'FORBIDDEN',
27
+ // Schema errors
28
+ TABLE_NOT_FOUND: 'TABLE_NOT_FOUND',
29
+ // Request errors
30
+ BAD_REQUEST: 'BAD_REQUEST',
31
+ NOT_FOUND: 'NOT_FOUND',
32
+ // GraphQL-specific errors
33
+ GRAPHQL_ERROR: 'GRAPHQL_ERROR',
34
+ // PostgreSQL constraint errors (surfaced via PostGraphile)
35
+ UNIQUE_VIOLATION: 'UNIQUE_VIOLATION',
36
+ FOREIGN_KEY_VIOLATION: 'FOREIGN_KEY_VIOLATION',
37
+ NOT_NULL_VIOLATION: 'NOT_NULL_VIOLATION',
38
+ CHECK_VIOLATION: 'CHECK_VIOLATION',
39
+ EXCLUSION_VIOLATION: 'EXCLUSION_VIOLATION',
40
+ // Generic errors
41
+ UNKNOWN_ERROR: 'UNKNOWN_ERROR',
42
+ };
43
+ /**
44
+ * Standard error class for data layer operations
45
+ */
46
+ class DataError extends Error {
47
+ type;
48
+ code;
49
+ originalError;
50
+ context;
51
+ tableName;
52
+ fieldName;
53
+ constraint;
54
+ constructor(type, message, options = {}) {
55
+ super(message);
56
+ this.name = 'DataError';
57
+ this.type = type;
58
+ this.code = options.code;
59
+ this.originalError = options.originalError;
60
+ this.context = options.context;
61
+ this.tableName = options.tableName;
62
+ this.fieldName = options.fieldName;
63
+ this.constraint = options.constraint;
64
+ if (Error.captureStackTrace) {
65
+ Error.captureStackTrace(this, DataError);
66
+ }
67
+ }
68
+ getUserMessage() {
69
+ switch (this.type) {
70
+ case exports.DataErrorType.NETWORK_ERROR:
71
+ return 'Network error. Please check your connection and try again.';
72
+ case exports.DataErrorType.TIMEOUT_ERROR:
73
+ return 'Request timed out. Please try again.';
74
+ case exports.DataErrorType.UNAUTHORIZED:
75
+ return 'You are not authorized. Please log in and try again.';
76
+ case exports.DataErrorType.FORBIDDEN:
77
+ return 'You do not have permission to access this resource.';
78
+ case exports.DataErrorType.VALIDATION_FAILED:
79
+ return 'Validation failed. Please check your input and try again.';
80
+ case exports.DataErrorType.REQUIRED_FIELD_MISSING:
81
+ return this.fieldName
82
+ ? `The field "${this.fieldName}" is required.`
83
+ : 'A required field is missing.';
84
+ case exports.DataErrorType.UNIQUE_VIOLATION:
85
+ return this.fieldName
86
+ ? `A record with this ${this.fieldName} already exists.`
87
+ : 'A record with this value already exists.';
88
+ case exports.DataErrorType.FOREIGN_KEY_VIOLATION:
89
+ return 'This record references a record that does not exist.';
90
+ case exports.DataErrorType.NOT_NULL_VIOLATION:
91
+ return this.fieldName
92
+ ? `The field "${this.fieldName}" cannot be empty.`
93
+ : 'A required field cannot be empty.';
94
+ case exports.DataErrorType.CHECK_VIOLATION:
95
+ return this.fieldName
96
+ ? `The value for "${this.fieldName}" is not valid.`
97
+ : 'The value does not meet the required constraints.';
98
+ default:
99
+ return this.message || 'An unexpected error occurred.';
100
+ }
101
+ }
102
+ isRetryable() {
103
+ return (this.type === exports.DataErrorType.NETWORK_ERROR ||
104
+ this.type === exports.DataErrorType.TIMEOUT_ERROR);
105
+ }
106
+ }
107
+ exports.DataError = DataError;
108
+ // ============================================================================
109
+ // PostgreSQL Error Codes
110
+ // ============================================================================
111
+ exports.PG_ERROR_CODES = {
112
+ UNIQUE_VIOLATION: '23505',
113
+ FOREIGN_KEY_VIOLATION: '23503',
114
+ NOT_NULL_VIOLATION: '23502',
115
+ CHECK_VIOLATION: '23514',
116
+ EXCLUSION_VIOLATION: '23P01',
117
+ NUMERIC_VALUE_OUT_OF_RANGE: '22003',
118
+ STRING_DATA_RIGHT_TRUNCATION: '22001',
119
+ INVALID_TEXT_REPRESENTATION: '22P02',
120
+ DATETIME_FIELD_OVERFLOW: '22008',
121
+ UNDEFINED_TABLE: '42P01',
122
+ UNDEFINED_COLUMN: '42703',
123
+ INSUFFICIENT_PRIVILEGE: '42501',
124
+ };
125
+ // ============================================================================
126
+ // Error Factory
127
+ // ============================================================================
128
+ exports.createError = {
129
+ network: (originalError) => new DataError(exports.DataErrorType.NETWORK_ERROR, 'Network error occurred', { originalError }),
130
+ timeout: (originalError) => new DataError(exports.DataErrorType.TIMEOUT_ERROR, 'Request timed out', { originalError }),
131
+ unauthorized: (message = 'Authentication required') => new DataError(exports.DataErrorType.UNAUTHORIZED, message),
132
+ forbidden: (message = 'Access forbidden') => new DataError(exports.DataErrorType.FORBIDDEN, message),
133
+ badRequest: (message, code) => new DataError(exports.DataErrorType.BAD_REQUEST, message, { code }),
134
+ notFound: (message = 'Resource not found') => new DataError(exports.DataErrorType.NOT_FOUND, message),
135
+ graphql: (message, code) => new DataError(exports.DataErrorType.GRAPHQL_ERROR, message, { code }),
136
+ uniqueViolation: (message, fieldName, constraint) => new DataError(exports.DataErrorType.UNIQUE_VIOLATION, message, { fieldName, constraint, code: '23505' }),
137
+ foreignKeyViolation: (message, fieldName, constraint) => new DataError(exports.DataErrorType.FOREIGN_KEY_VIOLATION, message, { fieldName, constraint, code: '23503' }),
138
+ notNullViolation: (message, fieldName, constraint) => new DataError(exports.DataErrorType.NOT_NULL_VIOLATION, message, { fieldName, constraint, code: '23502' }),
139
+ unknown: (originalError) => new DataError(exports.DataErrorType.UNKNOWN_ERROR, originalError.message, { originalError }),
140
+ };
141
+ function parseGraphQLErrorCode(code) {
142
+ if (!code)
143
+ return exports.DataErrorType.UNKNOWN_ERROR;
144
+ const normalized = code.toUpperCase();
145
+ // GraphQL standard codes
146
+ if (normalized === 'UNAUTHENTICATED')
147
+ return exports.DataErrorType.UNAUTHORIZED;
148
+ if (normalized === 'FORBIDDEN')
149
+ return exports.DataErrorType.FORBIDDEN;
150
+ if (normalized === 'GRAPHQL_VALIDATION_FAILED')
151
+ return exports.DataErrorType.QUERY_GENERATION_FAILED;
152
+ // PostgreSQL SQLSTATE codes
153
+ if (code === exports.PG_ERROR_CODES.UNIQUE_VIOLATION)
154
+ return exports.DataErrorType.UNIQUE_VIOLATION;
155
+ if (code === exports.PG_ERROR_CODES.FOREIGN_KEY_VIOLATION)
156
+ return exports.DataErrorType.FOREIGN_KEY_VIOLATION;
157
+ if (code === exports.PG_ERROR_CODES.NOT_NULL_VIOLATION)
158
+ return exports.DataErrorType.NOT_NULL_VIOLATION;
159
+ if (code === exports.PG_ERROR_CODES.CHECK_VIOLATION)
160
+ return exports.DataErrorType.CHECK_VIOLATION;
161
+ if (code === exports.PG_ERROR_CODES.EXCLUSION_VIOLATION)
162
+ return exports.DataErrorType.EXCLUSION_VIOLATION;
163
+ return exports.DataErrorType.UNKNOWN_ERROR;
164
+ }
165
+ function classifyByMessage(message) {
166
+ const lower = message.toLowerCase();
167
+ if (lower.includes('timeout') || lower.includes('timed out')) {
168
+ return exports.DataErrorType.TIMEOUT_ERROR;
169
+ }
170
+ if (lower.includes('network') || lower.includes('fetch') || lower.includes('failed to fetch')) {
171
+ return exports.DataErrorType.NETWORK_ERROR;
172
+ }
173
+ if (lower.includes('unauthorized') || lower.includes('authentication required')) {
174
+ return exports.DataErrorType.UNAUTHORIZED;
175
+ }
176
+ if (lower.includes('forbidden') || lower.includes('permission')) {
177
+ return exports.DataErrorType.FORBIDDEN;
178
+ }
179
+ if (lower.includes('duplicate key') || lower.includes('already exists')) {
180
+ return exports.DataErrorType.UNIQUE_VIOLATION;
181
+ }
182
+ if (lower.includes('foreign key constraint')) {
183
+ return exports.DataErrorType.FOREIGN_KEY_VIOLATION;
184
+ }
185
+ if (lower.includes('not-null constraint') || lower.includes('null value in column')) {
186
+ return exports.DataErrorType.NOT_NULL_VIOLATION;
187
+ }
188
+ return exports.DataErrorType.UNKNOWN_ERROR;
189
+ }
190
+ function extractFieldFromError(message, constraint, column) {
191
+ if (column)
192
+ return column;
193
+ const columnMatch = message.match(/column\s+"?([a-z_][a-z0-9_]*)"?/i);
194
+ if (columnMatch)
195
+ return columnMatch[1];
196
+ if (constraint) {
197
+ const constraintMatch = constraint.match(/_([a-z_][a-z0-9_]*)_(?:key|fkey|check|pkey)$/i);
198
+ if (constraintMatch)
199
+ return constraintMatch[1];
200
+ }
201
+ const keyMatch = message.match(/Key\s+\(([a-z_][a-z0-9_]*)\)/i);
202
+ if (keyMatch)
203
+ return keyMatch[1];
204
+ return undefined;
205
+ }
206
+ /**
207
+ * Parse any error into a DataError
208
+ */
209
+ function parseGraphQLError(error) {
210
+ if (error instanceof DataError) {
211
+ return error;
212
+ }
213
+ // GraphQL error object
214
+ if (error &&
215
+ typeof error === 'object' &&
216
+ 'message' in error &&
217
+ typeof error.message === 'string') {
218
+ const gqlError = error;
219
+ const extCode = gqlError.extensions?.code;
220
+ const mappedType = parseGraphQLErrorCode(extCode);
221
+ const column = gqlError.extensions?.column;
222
+ const constraint = gqlError.extensions?.constraint;
223
+ const fieldName = extractFieldFromError(gqlError.message, constraint, column);
224
+ if (mappedType !== exports.DataErrorType.UNKNOWN_ERROR) {
225
+ return new DataError(mappedType, gqlError.message, {
226
+ code: extCode,
227
+ fieldName,
228
+ constraint,
229
+ context: gqlError.extensions,
230
+ });
231
+ }
232
+ // Fallback: classify by message
233
+ const fallbackType = classifyByMessage(gqlError.message);
234
+ return new DataError(fallbackType, gqlError.message, {
235
+ code: extCode,
236
+ fieldName,
237
+ constraint,
238
+ context: gqlError.extensions,
239
+ });
240
+ }
241
+ // Standard Error
242
+ if (error instanceof Error) {
243
+ const type = classifyByMessage(error.message);
244
+ return new DataError(type, error.message, { originalError: error });
245
+ }
246
+ // Unknown
247
+ const message = typeof error === 'string' ? error : 'Unknown error occurred';
248
+ return new DataError(exports.DataErrorType.UNKNOWN_ERROR, message);
249
+ }
250
+ /**
251
+ * Check if value is a DataError
252
+ */
253
+ function isDataError(error) {
254
+ return error instanceof DataError;
255
+ }
@@ -0,0 +1,57 @@
1
+ /**
2
+ * GraphQL execution utilities
3
+ */
4
+ import type { DocumentNode } from 'graphql';
5
+ import { TypedDocumentString } from './typed-document';
6
+ type ExecutableDocument = TypedDocumentString<unknown, unknown> | DocumentNode | string;
7
+ type ResultOf<TDocument> = TDocument extends TypedDocumentString<infer TResult, unknown> ? TResult : unknown;
8
+ type VariablesOf<TDocument> = TDocument extends TypedDocumentString<unknown, infer TVariables> ? TVariables : Record<string, unknown>;
9
+ export interface ExecuteOptions {
10
+ /** Custom headers to include */
11
+ headers?: Record<string, string>;
12
+ /** Request timeout in milliseconds */
13
+ timeout?: number;
14
+ /** Signal for request cancellation */
15
+ signal?: AbortSignal;
16
+ }
17
+ export interface GraphQLResponse<T = unknown> {
18
+ data?: T;
19
+ errors?: Array<{
20
+ message: string;
21
+ extensions?: {
22
+ code?: string;
23
+ } & Record<string, unknown>;
24
+ locations?: Array<{
25
+ line: number;
26
+ column: number;
27
+ }>;
28
+ path?: Array<string | number>;
29
+ }>;
30
+ }
31
+ /**
32
+ * Execute a GraphQL operation against an endpoint
33
+ */
34
+ export declare function execute<TDocument extends ExecutableDocument>(endpoint: string, document: TDocument, variables?: VariablesOf<TDocument>, options?: ExecuteOptions): Promise<ResultOf<TDocument>>;
35
+ export interface GraphQLClientOptions {
36
+ /** GraphQL endpoint URL */
37
+ endpoint: string;
38
+ /** Default headers to include with every request */
39
+ headers?: Record<string, string>;
40
+ /** Default timeout in milliseconds */
41
+ timeout?: number;
42
+ }
43
+ /**
44
+ * Create a GraphQL client instance
45
+ */
46
+ export declare function createGraphQLClient(options: GraphQLClientOptions): {
47
+ /**
48
+ * Execute a GraphQL operation
49
+ */
50
+ execute<TDocument extends ExecutableDocument>(document: TDocument, variables?: VariablesOf<TDocument>, options?: ExecuteOptions): Promise<ResultOf<TDocument>>;
51
+ /**
52
+ * Get the endpoint URL
53
+ */
54
+ getEndpoint(): string;
55
+ };
56
+ export type GraphQLClient = ReturnType<typeof createGraphQLClient>;
57
+ export {};