@strapi/database 5.12.0 → 5.12.2

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 (321) hide show
  1. package/dist/connection.js +43 -0
  2. package/dist/connection.js.map +1 -0
  3. package/dist/connection.mjs +41 -0
  4. package/dist/connection.mjs.map +1 -0
  5. package/dist/dialects/dialect.js +54 -0
  6. package/dist/dialects/dialect.js.map +1 -0
  7. package/dist/dialects/dialect.mjs +52 -0
  8. package/dist/dialects/dialect.mjs.map +1 -0
  9. package/dist/dialects/index.js +44 -0
  10. package/dist/dialects/index.js.map +1 -0
  11. package/dist/dialects/index.mjs +42 -0
  12. package/dist/dialects/index.mjs.map +1 -0
  13. package/dist/dialects/mysql/constants.js +8 -0
  14. package/dist/dialects/mysql/constants.js.map +1 -0
  15. package/dist/dialects/mysql/constants.mjs +5 -0
  16. package/dist/dialects/mysql/constants.mjs.map +1 -0
  17. package/dist/dialects/mysql/database-inspector.js +35 -0
  18. package/dist/dialects/mysql/database-inspector.js.map +1 -0
  19. package/dist/dialects/mysql/database-inspector.mjs +33 -0
  20. package/dist/dialects/mysql/database-inspector.mjs.map +1 -0
  21. package/dist/dialects/mysql/index.js +75 -0
  22. package/dist/dialects/mysql/index.js.map +1 -0
  23. package/dist/dialects/mysql/index.mjs +73 -0
  24. package/dist/dialects/mysql/index.mjs.map +1 -0
  25. package/dist/dialects/mysql/schema-inspector.js +297 -0
  26. package/dist/dialects/mysql/schema-inspector.js.map +1 -0
  27. package/dist/dialects/mysql/schema-inspector.mjs +295 -0
  28. package/dist/dialects/mysql/schema-inspector.mjs.map +1 -0
  29. package/dist/dialects/postgresql/index.js +62 -0
  30. package/dist/dialects/postgresql/index.js.map +1 -0
  31. package/dist/dialects/postgresql/index.mjs +60 -0
  32. package/dist/dialects/postgresql/index.mjs.map +1 -0
  33. package/dist/dialects/postgresql/schema-inspector.js +316 -0
  34. package/dist/dialects/postgresql/schema-inspector.js.map +1 -0
  35. package/dist/dialects/postgresql/schema-inspector.mjs +314 -0
  36. package/dist/dialects/postgresql/schema-inspector.mjs.map +1 -0
  37. package/dist/dialects/sqlite/index.js +82 -0
  38. package/dist/dialects/sqlite/index.js.map +1 -0
  39. package/dist/dialects/sqlite/index.mjs +80 -0
  40. package/dist/dialects/sqlite/index.mjs.map +1 -0
  41. package/dist/dialects/sqlite/schema-inspector.js +211 -0
  42. package/dist/dialects/sqlite/schema-inspector.js.map +1 -0
  43. package/dist/dialects/sqlite/schema-inspector.mjs +209 -0
  44. package/dist/dialects/sqlite/schema-inspector.mjs.map +1 -0
  45. package/dist/entity-manager/entity-repository.js +139 -0
  46. package/dist/entity-manager/entity-repository.js.map +1 -0
  47. package/dist/entity-manager/entity-repository.mjs +137 -0
  48. package/dist/entity-manager/entity-repository.mjs.map +1 -0
  49. package/dist/entity-manager/index.js +1186 -0
  50. package/dist/entity-manager/index.js.map +1 -0
  51. package/dist/entity-manager/index.mjs +1184 -0
  52. package/dist/entity-manager/index.mjs.map +1 -0
  53. package/dist/entity-manager/morph-relations.js +73 -0
  54. package/dist/entity-manager/morph-relations.js.map +1 -0
  55. package/dist/entity-manager/morph-relations.mjs +69 -0
  56. package/dist/entity-manager/morph-relations.mjs.map +1 -0
  57. package/dist/entity-manager/regular-relations.js +247 -0
  58. package/dist/entity-manager/regular-relations.js.map +1 -0
  59. package/dist/entity-manager/regular-relations.mjs +242 -0
  60. package/dist/entity-manager/regular-relations.mjs.map +1 -0
  61. package/dist/entity-manager/relations-orderer.js +221 -0
  62. package/dist/entity-manager/relations-orderer.js.map +1 -0
  63. package/dist/entity-manager/relations-orderer.mjs +218 -0
  64. package/dist/entity-manager/relations-orderer.mjs.map +1 -0
  65. package/dist/errors/database.js +13 -0
  66. package/dist/errors/database.js.map +1 -0
  67. package/dist/errors/database.mjs +11 -0
  68. package/dist/errors/database.mjs.map +1 -0
  69. package/dist/errors/index.js +18 -0
  70. package/dist/errors/index.js.map +1 -0
  71. package/dist/errors/index.mjs +7 -0
  72. package/dist/errors/index.mjs.map +1 -0
  73. package/dist/errors/invalid-date.js +13 -0
  74. package/dist/errors/invalid-date.js.map +1 -0
  75. package/dist/errors/invalid-date.mjs +11 -0
  76. package/dist/errors/invalid-date.mjs.map +1 -0
  77. package/dist/errors/invalid-datetime.js +13 -0
  78. package/dist/errors/invalid-datetime.js.map +1 -0
  79. package/dist/errors/invalid-datetime.mjs +11 -0
  80. package/dist/errors/invalid-datetime.mjs.map +1 -0
  81. package/dist/errors/invalid-relation.js +13 -0
  82. package/dist/errors/invalid-relation.js.map +1 -0
  83. package/dist/errors/invalid-relation.mjs +11 -0
  84. package/dist/errors/invalid-relation.mjs.map +1 -0
  85. package/dist/errors/invalid-time.js +13 -0
  86. package/dist/errors/invalid-time.js.map +1 -0
  87. package/dist/errors/invalid-time.mjs +11 -0
  88. package/dist/errors/invalid-time.mjs.map +1 -0
  89. package/dist/errors/not-null.js +17 -0
  90. package/dist/errors/not-null.js.map +1 -0
  91. package/dist/errors/not-null.mjs +15 -0
  92. package/dist/errors/not-null.mjs.map +1 -0
  93. package/dist/fields/biginteger.js +9 -0
  94. package/dist/fields/biginteger.js.map +1 -0
  95. package/dist/fields/biginteger.mjs +7 -0
  96. package/dist/fields/biginteger.mjs.map +1 -0
  97. package/dist/fields/boolean.js +48 -0
  98. package/dist/fields/boolean.js.map +1 -0
  99. package/dist/fields/boolean.mjs +46 -0
  100. package/dist/fields/boolean.mjs.map +1 -0
  101. package/dist/fields/date.js +16 -0
  102. package/dist/fields/date.js.map +1 -0
  103. package/dist/fields/date.mjs +14 -0
  104. package/dist/fields/date.mjs.map +1 -0
  105. package/dist/fields/datetime.js +37 -0
  106. package/dist/fields/datetime.js.map +1 -0
  107. package/dist/fields/datetime.mjs +16 -0
  108. package/dist/fields/datetime.mjs.map +1 -0
  109. package/dist/fields/field.js +16 -0
  110. package/dist/fields/field.js.map +1 -0
  111. package/dist/fields/field.mjs +14 -0
  112. package/dist/fields/field.mjs.map +1 -0
  113. package/dist/fields/index.js +45 -0
  114. package/dist/fields/index.js.map +1 -0
  115. package/dist/fields/index.mjs +43 -0
  116. package/dist/fields/index.mjs.map +1 -0
  117. package/dist/fields/json.js +36 -0
  118. package/dist/fields/json.js.map +1 -0
  119. package/dist/fields/json.mjs +34 -0
  120. package/dist/fields/json.mjs.map +1 -0
  121. package/dist/fields/number.js +20 -0
  122. package/dist/fields/number.js.map +1 -0
  123. package/dist/fields/number.mjs +18 -0
  124. package/dist/fields/number.mjs.map +1 -0
  125. package/dist/fields/shared/parsers.js +91 -0
  126. package/dist/fields/shared/parsers.js.map +1 -0
  127. package/dist/fields/shared/parsers.mjs +68 -0
  128. package/dist/fields/shared/parsers.mjs.map +1 -0
  129. package/dist/fields/string.js +16 -0
  130. package/dist/fields/string.js.map +1 -0
  131. package/dist/fields/string.mjs +14 -0
  132. package/dist/fields/string.mjs.map +1 -0
  133. package/dist/fields/time.js +17 -0
  134. package/dist/fields/time.js.map +1 -0
  135. package/dist/fields/time.mjs +15 -0
  136. package/dist/fields/time.mjs.map +1 -0
  137. package/dist/fields/timestamp.js +37 -0
  138. package/dist/fields/timestamp.js.map +1 -0
  139. package/dist/fields/timestamp.mjs +16 -0
  140. package/dist/fields/timestamp.mjs.map +1 -0
  141. package/dist/index.js +33 -8569
  142. package/dist/index.js.map +1 -1
  143. package/dist/index.mjs +16 -8532
  144. package/dist/index.mjs.map +1 -1
  145. package/dist/lifecycles/index.js +73 -0
  146. package/dist/lifecycles/index.js.map +1 -0
  147. package/dist/lifecycles/index.mjs +71 -0
  148. package/dist/lifecycles/index.mjs.map +1 -0
  149. package/dist/lifecycles/subscribers/index.js +10 -0
  150. package/dist/lifecycles/subscribers/index.js.map +1 -0
  151. package/dist/lifecycles/subscribers/index.mjs +8 -0
  152. package/dist/lifecycles/subscribers/index.mjs.map +1 -0
  153. package/dist/lifecycles/subscribers/models-lifecycles.js +13 -0
  154. package/dist/lifecycles/subscribers/models-lifecycles.js.map +1 -0
  155. package/dist/lifecycles/subscribers/models-lifecycles.mjs +11 -0
  156. package/dist/lifecycles/subscribers/models-lifecycles.mjs.map +1 -0
  157. package/dist/lifecycles/subscribers/timestamps.js +55 -0
  158. package/dist/lifecycles/subscribers/timestamps.js.map +1 -0
  159. package/dist/lifecycles/subscribers/timestamps.mjs +53 -0
  160. package/dist/lifecycles/subscribers/timestamps.mjs.map +1 -0
  161. package/dist/metadata/index.js +24 -0
  162. package/dist/metadata/index.js.map +1 -0
  163. package/dist/metadata/index.mjs +16 -0
  164. package/dist/metadata/index.mjs.map +1 -0
  165. package/dist/metadata/metadata.js +100 -0
  166. package/dist/metadata/metadata.js.map +1 -0
  167. package/dist/metadata/metadata.mjs +98 -0
  168. package/dist/metadata/metadata.mjs.map +1 -0
  169. package/dist/metadata/relations.js +545 -0
  170. package/dist/metadata/relations.js.map +1 -0
  171. package/dist/metadata/relations.mjs +536 -0
  172. package/dist/metadata/relations.mjs.map +1 -0
  173. package/dist/migrations/common.js +8 -0
  174. package/dist/migrations/common.js.map +1 -0
  175. package/dist/migrations/common.mjs +6 -0
  176. package/dist/migrations/common.mjs.map +1 -0
  177. package/dist/migrations/index.js +39 -0
  178. package/dist/migrations/index.js.map +1 -0
  179. package/dist/migrations/index.mjs +37 -0
  180. package/dist/migrations/index.mjs.map +1 -0
  181. package/dist/migrations/internal-migrations/5.0.0-01-convert-identifiers-long-than-max-length.js +179 -0
  182. package/dist/migrations/internal-migrations/5.0.0-01-convert-identifiers-long-than-max-length.js.map +1 -0
  183. package/dist/migrations/internal-migrations/5.0.0-01-convert-identifiers-long-than-max-length.mjs +177 -0
  184. package/dist/migrations/internal-migrations/5.0.0-01-convert-identifiers-long-than-max-length.mjs.map +1 -0
  185. package/dist/migrations/internal-migrations/5.0.0-02-document-id.js +125 -0
  186. package/dist/migrations/internal-migrations/5.0.0-02-document-id.js.map +1 -0
  187. package/dist/migrations/internal-migrations/5.0.0-02-document-id.mjs +123 -0
  188. package/dist/migrations/internal-migrations/5.0.0-02-document-id.mjs.map +1 -0
  189. package/dist/migrations/internal-migrations/5.0.0-03-locale.js +41 -0
  190. package/dist/migrations/internal-migrations/5.0.0-03-locale.js.map +1 -0
  191. package/dist/migrations/internal-migrations/5.0.0-03-locale.mjs +39 -0
  192. package/dist/migrations/internal-migrations/5.0.0-03-locale.mjs.map +1 -0
  193. package/dist/migrations/internal-migrations/5.0.0-04-published-at.js +45 -0
  194. package/dist/migrations/internal-migrations/5.0.0-04-published-at.js.map +1 -0
  195. package/dist/migrations/internal-migrations/5.0.0-04-published-at.mjs +43 -0
  196. package/dist/migrations/internal-migrations/5.0.0-04-published-at.mjs.map +1 -0
  197. package/dist/migrations/internal-migrations/5.0.0-05-drop-slug-unique-index.js +43 -0
  198. package/dist/migrations/internal-migrations/5.0.0-05-drop-slug-unique-index.js.map +1 -0
  199. package/dist/migrations/internal-migrations/5.0.0-05-drop-slug-unique-index.mjs +41 -0
  200. package/dist/migrations/internal-migrations/5.0.0-05-drop-slug-unique-index.mjs.map +1 -0
  201. package/dist/migrations/internal-migrations/index.js +26 -0
  202. package/dist/migrations/internal-migrations/index.js.map +1 -0
  203. package/dist/migrations/internal-migrations/index.mjs +24 -0
  204. package/dist/migrations/internal-migrations/index.mjs.map +1 -0
  205. package/dist/migrations/internal.js +63 -0
  206. package/dist/migrations/internal.js.map +1 -0
  207. package/dist/migrations/internal.mjs +61 -0
  208. package/dist/migrations/internal.mjs.map +1 -0
  209. package/dist/migrations/logger.js +24 -0
  210. package/dist/migrations/logger.js.map +1 -0
  211. package/dist/migrations/logger.mjs +22 -0
  212. package/dist/migrations/logger.mjs.map +1 -0
  213. package/dist/migrations/storage.js +39 -0
  214. package/dist/migrations/storage.js.map +1 -0
  215. package/dist/migrations/storage.mjs +37 -0
  216. package/dist/migrations/storage.mjs.map +1 -0
  217. package/dist/migrations/users.js +87 -0
  218. package/dist/migrations/users.js.map +1 -0
  219. package/dist/migrations/users.mjs +85 -0
  220. package/dist/migrations/users.mjs.map +1 -0
  221. package/dist/query/helpers/join.js +127 -0
  222. package/dist/query/helpers/join.js.map +1 -0
  223. package/dist/query/helpers/join.mjs +122 -0
  224. package/dist/query/helpers/join.mjs.map +1 -0
  225. package/dist/query/helpers/order-by.js +167 -0
  226. package/dist/query/helpers/order-by.js.map +1 -0
  227. package/dist/query/helpers/order-by.mjs +163 -0
  228. package/dist/query/helpers/order-by.mjs.map +1 -0
  229. package/dist/query/helpers/populate/apply.js +592 -0
  230. package/dist/query/helpers/populate/apply.js.map +1 -0
  231. package/dist/query/helpers/populate/apply.mjs +590 -0
  232. package/dist/query/helpers/populate/apply.mjs.map +1 -0
  233. package/dist/query/helpers/populate/process.js +92 -0
  234. package/dist/query/helpers/populate/process.js.map +1 -0
  235. package/dist/query/helpers/populate/process.mjs +90 -0
  236. package/dist/query/helpers/populate/process.mjs.map +1 -0
  237. package/dist/query/helpers/search.js +67 -0
  238. package/dist/query/helpers/search.js.map +1 -0
  239. package/dist/query/helpers/search.mjs +65 -0
  240. package/dist/query/helpers/search.mjs.map +1 -0
  241. package/dist/query/helpers/streams/readable.js +131 -0
  242. package/dist/query/helpers/streams/readable.js.map +1 -0
  243. package/dist/query/helpers/streams/readable.mjs +129 -0
  244. package/dist/query/helpers/streams/readable.mjs.map +1 -0
  245. package/dist/query/helpers/transform.js +77 -0
  246. package/dist/query/helpers/transform.js.map +1 -0
  247. package/dist/query/helpers/transform.mjs +73 -0
  248. package/dist/query/helpers/transform.mjs.map +1 -0
  249. package/dist/query/helpers/where.js +372 -0
  250. package/dist/query/helpers/where.js.map +1 -0
  251. package/dist/query/helpers/where.mjs +369 -0
  252. package/dist/query/helpers/where.mjs.map +1 -0
  253. package/dist/query/query-builder.js +507 -0
  254. package/dist/query/query-builder.js.map +1 -0
  255. package/dist/query/query-builder.mjs +505 -0
  256. package/dist/query/query-builder.mjs.map +1 -0
  257. package/dist/repairs/index.js +13 -0
  258. package/dist/repairs/index.js.map +1 -0
  259. package/dist/repairs/index.mjs +11 -0
  260. package/dist/repairs/index.mjs.map +1 -0
  261. package/dist/repairs/operations/remove-orphan-morph-types.js +54 -0
  262. package/dist/repairs/operations/remove-orphan-morph-types.js.map +1 -0
  263. package/dist/repairs/operations/remove-orphan-morph-types.mjs +52 -0
  264. package/dist/repairs/operations/remove-orphan-morph-types.mjs.map +1 -0
  265. package/dist/schema/builder.js +354 -0
  266. package/dist/schema/builder.js.map +1 -0
  267. package/dist/schema/builder.mjs +352 -0
  268. package/dist/schema/builder.mjs.map +1 -0
  269. package/dist/schema/diff.js +379 -0
  270. package/dist/schema/diff.js.map +1 -0
  271. package/dist/schema/diff.mjs +377 -0
  272. package/dist/schema/diff.mjs.map +1 -0
  273. package/dist/schema/index.js +93 -0
  274. package/dist/schema/index.js.map +1 -0
  275. package/dist/schema/index.mjs +91 -0
  276. package/dist/schema/index.mjs.map +1 -0
  277. package/dist/schema/schema.js +266 -0
  278. package/dist/schema/schema.js.map +1 -0
  279. package/dist/schema/schema.mjs +264 -0
  280. package/dist/schema/schema.mjs.map +1 -0
  281. package/dist/schema/storage.js +58 -0
  282. package/dist/schema/storage.js.map +1 -0
  283. package/dist/schema/storage.mjs +56 -0
  284. package/dist/schema/storage.mjs.map +1 -0
  285. package/dist/transaction-context.js +65 -0
  286. package/dist/transaction-context.js.map +1 -0
  287. package/dist/transaction-context.mjs +63 -0
  288. package/dist/transaction-context.mjs.map +1 -0
  289. package/dist/utils/async-curry.js +19 -0
  290. package/dist/utils/async-curry.js.map +1 -0
  291. package/dist/utils/async-curry.mjs +17 -0
  292. package/dist/utils/async-curry.mjs.map +1 -0
  293. package/dist/utils/identifiers/hash.js +30 -0
  294. package/dist/utils/identifiers/hash.js.map +1 -0
  295. package/dist/utils/identifiers/hash.mjs +28 -0
  296. package/dist/utils/identifiers/hash.mjs.map +1 -0
  297. package/dist/utils/identifiers/index.js +414 -0
  298. package/dist/utils/identifiers/index.js.map +1 -0
  299. package/dist/utils/identifiers/index.mjs +411 -0
  300. package/dist/utils/identifiers/index.mjs.map +1 -0
  301. package/dist/utils/knex.js +21 -0
  302. package/dist/utils/knex.js.map +1 -0
  303. package/dist/utils/knex.mjs +18 -0
  304. package/dist/utils/knex.mjs.map +1 -0
  305. package/dist/utils/types.js +51 -0
  306. package/dist/utils/types.js.map +1 -0
  307. package/dist/utils/types.mjs +44 -0
  308. package/dist/utils/types.mjs.map +1 -0
  309. package/dist/validations/index.js +12 -0
  310. package/dist/validations/index.js.map +1 -0
  311. package/dist/validations/index.mjs +10 -0
  312. package/dist/validations/index.mjs.map +1 -0
  313. package/dist/validations/relations/bidirectional.js +64 -0
  314. package/dist/validations/relations/bidirectional.js.map +1 -0
  315. package/dist/validations/relations/bidirectional.mjs +62 -0
  316. package/dist/validations/relations/bidirectional.mjs.map +1 -0
  317. package/dist/validations/relations/index.js +13 -0
  318. package/dist/validations/relations/index.js.map +1 -0
  319. package/dist/validations/relations/index.mjs +11 -0
  320. package/dist/validations/relations/index.mjs.map +1 -0
  321. package/package.json +4 -4
@@ -0,0 +1,414 @@
1
+ 'use strict';
2
+
3
+ var _ = require('lodash/fp');
4
+ var hash = require('./hash.js');
5
+
6
+ /**
7
+ * This file contains utility functions for generating names used in the database.
8
+ * These names include table names, column names, join table names, index names, and more.
9
+ * The generated names can be customized with prefixes, suffixes, and maximum length.
10
+ * These utility functions are used throughout the codebase to ensure consistent and standardized naming conventions in the database.
11
+ *
12
+ * The reason for checking maxLength for suffixes and prefixes and using the long ones from Strapi 4 is so that we always
13
+ * have access to the full length names, in particular for migration purposes, but also so that (in theory) the feature
14
+ * could be disabled and stay compatible with v4 database structure.
15
+ */ function _class_private_field_loose_base(receiver, privateKey) {
16
+ if (!Object.prototype.hasOwnProperty.call(receiver, privateKey)) {
17
+ throw new TypeError("attempted to use private field on non-instance");
18
+ }
19
+ return receiver;
20
+ }
21
+ var id = 0;
22
+ function _class_private_field_loose_key(name) {
23
+ return "__private_" + id++ + "_" + name;
24
+ }
25
+ const IDENTIFIER_MAX_LENGTH = 55;
26
+ var // Fixed compression map for suffixes and prefixes
27
+ _replacementMap = /*#__PURE__*/ _class_private_field_loose_key("_replacementMap"), _options = /*#__PURE__*/ _class_private_field_loose_key("_options");
28
+ class Identifiers {
29
+ get replacementMap() {
30
+ return _class_private_field_loose_base(this, _replacementMap)[_replacementMap];
31
+ }
32
+ get options() {
33
+ return _class_private_field_loose_base(this, _options)[_options];
34
+ }
35
+ constructor(options){
36
+ Object.defineProperty(this, _replacementMap, {
37
+ writable: true,
38
+ value: void 0
39
+ });
40
+ Object.defineProperty(this, _options, {
41
+ writable: true,
42
+ value: void 0
43
+ });
44
+ this.ID_COLUMN = 'id';
45
+ this.ORDER_COLUMN = 'order';
46
+ this.FIELD_COLUMN = 'field';
47
+ this.HASH_LENGTH = 5;
48
+ this.HASH_SEPARATOR = '' // no separator is needed, we will just attach hash directly to shortened name
49
+ ;
50
+ this.IDENTIFIER_SEPARATOR = '_';
51
+ this.MIN_TOKEN_LENGTH = 3 // the min characters required at the beginning of a name part
52
+ ;
53
+ _class_private_field_loose_base(this, _replacementMap)[_replacementMap] = {
54
+ links: 'lnk',
55
+ order_inv_fk: 'oifk',
56
+ order: 'ord',
57
+ morphs: 'mph',
58
+ index: 'idx',
59
+ inv_fk: 'ifk',
60
+ order_fk: 'ofk',
61
+ id_column_index: 'idix',
62
+ order_index: 'oidx',
63
+ unique: 'uq',
64
+ primary: 'pk'
65
+ };
66
+ this.mapshortNames = (name)=>{
67
+ if (name in this.replacementMap) {
68
+ return this.replacementMap[name];
69
+ }
70
+ return undefined;
71
+ };
72
+ // Generic name handler that must be used by all helper functions
73
+ /**
74
+ * TODO: we should be requiring snake_case inputs for all names here, but we
75
+ * aren't and it will require some refactoring to make it work. Currently if
76
+ * we get names 'myModel' and 'my_model' they would be converted to the same
77
+ * final string my_model which generally works but is not entirely safe
78
+ * */ this.getName = (names, options)=>{
79
+ const tokens = _.castArray(names).map((name)=>{
80
+ return {
81
+ name,
82
+ compressible: true
83
+ };
84
+ });
85
+ if (options?.suffix) {
86
+ tokens.push({
87
+ name: options.suffix,
88
+ compressible: false,
89
+ shortName: this.mapshortNames(options.suffix)
90
+ });
91
+ }
92
+ if (options?.prefix) {
93
+ tokens.unshift({
94
+ name: options.prefix,
95
+ compressible: false,
96
+ shortName: this.mapshortNames(options.prefix)
97
+ });
98
+ }
99
+ return this.getNameFromTokens(tokens);
100
+ };
101
+ /**
102
+ * TABLES
103
+ */ this.getTableName = (name, options)=>{
104
+ return this.getName(name, options);
105
+ };
106
+ this.getJoinTableName = (collectionName, attributeName, options)=>{
107
+ return this.getName([
108
+ collectionName,
109
+ attributeName
110
+ ], {
111
+ suffix: 'links',
112
+ ...options
113
+ });
114
+ };
115
+ this.getMorphTableName = (collectionName, attributeName, options)=>{
116
+ return this.getName([
117
+ _.snakeCase(collectionName),
118
+ _.snakeCase(attributeName)
119
+ ], {
120
+ suffix: 'morphs',
121
+ ...options
122
+ });
123
+ };
124
+ /**
125
+ * COLUMNS
126
+ */ this.getColumnName = (attributeName, options)=>{
127
+ return this.getName(attributeName, options);
128
+ };
129
+ this.getJoinColumnAttributeIdName = (attributeName, options)=>{
130
+ return this.getName(attributeName, {
131
+ suffix: 'id',
132
+ ...options
133
+ });
134
+ };
135
+ this.getInverseJoinColumnAttributeIdName = (attributeName, options)=>{
136
+ return this.getName(_.snakeCase(attributeName), {
137
+ suffix: 'id',
138
+ prefix: 'inv',
139
+ ...options
140
+ });
141
+ };
142
+ this.getOrderColumnName = (singularName, options)=>{
143
+ return this.getName(singularName, {
144
+ suffix: 'order',
145
+ ...options
146
+ });
147
+ };
148
+ this.getInverseOrderColumnName = (singularName, options)=>{
149
+ return this.getName(singularName, {
150
+ suffix: 'order',
151
+ prefix: 'inv',
152
+ ...options
153
+ });
154
+ };
155
+ /**
156
+ * Morph Join Tables
157
+ */ this.getMorphColumnJoinTableIdName = (singularName, options)=>{
158
+ return this.getName(_.snakeCase(singularName), {
159
+ suffix: 'id',
160
+ ...options
161
+ });
162
+ };
163
+ this.getMorphColumnAttributeIdName = (attributeName, options)=>{
164
+ return this.getName(_.snakeCase(attributeName), {
165
+ suffix: 'id',
166
+ ...options
167
+ });
168
+ };
169
+ this.getMorphColumnTypeName = (attributeName, options)=>{
170
+ return this.getName(_.snakeCase(attributeName), {
171
+ suffix: 'type',
172
+ ...options
173
+ });
174
+ };
175
+ /**
176
+ * INDEXES
177
+ * Note that these methods are generally used to reference full table names + attribute(s), which
178
+ * may already be shortened strings rather than individual parts.
179
+ * That is fine and expected to compress the previously incompressible parts of those strings,
180
+ * because in these cases the relevant information is the table name and we can't really do
181
+ * any better; shortening the individual parts again might make it even more confusing.
182
+ *
183
+ * So for example, the fk for the table `mytable_myattr4567d_localizations` will become
184
+ * mytable_myattr4567d_loc63bf2_fk
185
+ */ // base index types
186
+ this.getIndexName = (names, options)=>{
187
+ return this.getName(names, {
188
+ suffix: 'index',
189
+ ...options
190
+ });
191
+ };
192
+ this.getFkIndexName = (names, options)=>{
193
+ return this.getName(names, {
194
+ suffix: 'fk',
195
+ ...options
196
+ });
197
+ };
198
+ this.getUniqueIndexName = (names, options)=>{
199
+ return this.getName(names, {
200
+ suffix: 'unique',
201
+ ...options
202
+ });
203
+ };
204
+ this.getPrimaryIndexName = (names, options)=>{
205
+ return this.getName(names, {
206
+ suffix: 'primary',
207
+ ...options
208
+ });
209
+ };
210
+ // custom index types
211
+ this.getInverseFkIndexName = (names, options)=>{
212
+ return this.getName(names, {
213
+ suffix: 'inv_fk',
214
+ ...options
215
+ });
216
+ };
217
+ this.getOrderFkIndexName = (names, options)=>{
218
+ return this.getName(names, {
219
+ suffix: 'order_fk',
220
+ ...options
221
+ });
222
+ };
223
+ this.getOrderInverseFkIndexName = (names, options)=>{
224
+ return this.getName(names, {
225
+ suffix: 'order_inv_fk',
226
+ ...options
227
+ });
228
+ };
229
+ this.getIdColumnIndexName = (names, options)=>{
230
+ return this.getName(names, {
231
+ suffix: 'id_column_index',
232
+ ...options
233
+ });
234
+ };
235
+ this.getOrderIndexName = (names, options)=>{
236
+ return this.getName(names, {
237
+ suffix: 'order_index',
238
+ ...options
239
+ });
240
+ };
241
+ /**
242
+ * Generates a string with a max length, appending a hash at the end if necessary to keep it unique
243
+ *
244
+ * @example
245
+ * // if we have strings such as "longstring1" and "longstring2" with a max length of 9,
246
+ * // we don't want to end up with "longstrin" and "longstrin"
247
+ * // we want something such as "longs0b23" and "longs953f"
248
+ * const token1 = generateToken("longstring1", 9); // "longs0b23"
249
+ * const token2 = generateToken("longstring2", 9); // "longs953f"
250
+ *
251
+ * @param name - The base name
252
+ * @param len - The desired length of the token.
253
+ * @returns The generated token with hash.
254
+ * @throws Error if the length is not a positive integer, or if the length is too short for the token.
255
+ * @internal
256
+ */ this.getShortenedName = (name, len)=>{
257
+ if (!_.isInteger(len) || len <= 0) {
258
+ throw new Error(`tokenWithHash length must be a positive integer, received ${len}`);
259
+ }
260
+ if (name.length <= len) {
261
+ return name;
262
+ }
263
+ if (len < this.MIN_TOKEN_LENGTH + this.HASH_LENGTH) {
264
+ throw new Error(`length for part of identifier too short, minimum is hash length (${this.HASH_LENGTH}) plus min token length (${this.MIN_TOKEN_LENGTH}), received ${len} for token ${name}`);
265
+ }
266
+ const availableLength = len - this.HASH_LENGTH - this.HASH_SEPARATOR.length;
267
+ if (availableLength < this.MIN_TOKEN_LENGTH) {
268
+ throw new Error(`length for part of identifier minimum is less than min token length (${this.MIN_TOKEN_LENGTH}), received ${len} for token ${name}`);
269
+ }
270
+ return `${name.substring(0, availableLength)}${this.HASH_SEPARATOR}${hash.createHash(name, this.HASH_LENGTH)}`;
271
+ };
272
+ /**
273
+ * Constructs a name from an array of name tokens within a specified maximum length. It ensures the final name does not exceed
274
+ * this limit by selectively compressing tokens marked as compressible. If the name exceeds the maximum length and cannot be
275
+ * compressed sufficiently, an error is thrown. This function supports dynamic adjustment of token lengths to fit within the
276
+ * maxLength constraint (that is, it will always make use of all available space), while also ensuring the preservation of
277
+ * incompressible tokens.
278
+ * @internal
279
+ */ this.getNameFromTokens = (nameTokens)=>{
280
+ const { maxLength } = this.options;
281
+ if (!_.isInteger(maxLength) || maxLength < 0) {
282
+ throw new Error('maxLength must be a positive integer or 0 (for unlimited length)');
283
+ }
284
+ const unshortenedName = nameTokens.map((token)=>{
285
+ return token.name;
286
+ }).join(this.IDENTIFIER_SEPARATOR);
287
+ // if maxLength == 0 we want the legacy v4 name without any shortening
288
+ if (maxLength === 0) {
289
+ this.setUnshortenedName(unshortenedName, unshortenedName);
290
+ return unshortenedName;
291
+ }
292
+ // check the full length name (but with incompressible tokens using shortNames if available)
293
+ const fullLengthName = nameTokens.map((token)=>{
294
+ if (token.compressible) {
295
+ return token.name;
296
+ }
297
+ return token.shortName ?? token.name;
298
+ }).join(this.IDENTIFIER_SEPARATOR);
299
+ if (fullLengthName.length <= maxLength) {
300
+ this.setUnshortenedName(fullLengthName, unshortenedName);
301
+ return fullLengthName;
302
+ }
303
+ // Split tokens by compressibility
304
+ const [compressible, incompressible] = _.partition((token)=>token.compressible, nameTokens);
305
+ const totalIncompressibleLength = _.sumBy((token)=>token.compressible === false && token.shortName !== undefined ? token.shortName.length : token.name.length)(incompressible);
306
+ const totalSeparatorsLength = nameTokens.length * this.IDENTIFIER_SEPARATOR.length - 1;
307
+ const available = maxLength - totalIncompressibleLength - totalSeparatorsLength;
308
+ const availablePerToken = Math.floor(available / compressible.length);
309
+ if (totalIncompressibleLength + totalSeparatorsLength > maxLength || availablePerToken < this.MIN_TOKEN_LENGTH) {
310
+ throw new Error('Maximum length is too small to accommodate all tokens');
311
+ }
312
+ // Calculate the remainder from the division and add it to the surplus
313
+ let surplus = available % compressible.length;
314
+ // Check that it's even possible to proceed
315
+ const minHashedLength = this.HASH_LENGTH + this.HASH_SEPARATOR.length + this.MIN_TOKEN_LENGTH;
316
+ const totalLength = nameTokens.reduce((total, token)=>{
317
+ if (token.compressible) {
318
+ if (token.name.length < availablePerToken) {
319
+ return total + token.name.length;
320
+ }
321
+ return total + minHashedLength;
322
+ }
323
+ const tokenName = token.shortName ?? token.name;
324
+ return total + tokenName.length;
325
+ }, nameTokens.length * this.IDENTIFIER_SEPARATOR.length - 1);
326
+ // TODO: this is the weakest thing of the shortener, but fortunately it can be improved later without a breaking change if it turns out to be a problem (for example, if there is some case we need 6+ name parts in one identifier). We could take this "shortest string we could generate" that is too long and apply the hash directly to that, which would work fine even though it would be very difficult to determine what it was actually referring to
327
+ // Check if the maximum length is less than the total length
328
+ if (maxLength < totalLength) {
329
+ throw new Error('Maximum length is too small to accommodate all tokens');
330
+ }
331
+ // Calculate total surplus length from shorter strings and total deficit length from longer strings
332
+ let deficits = [];
333
+ compressible.forEach((token)=>{
334
+ const actualLength = token.name.length;
335
+ if (actualLength < availablePerToken) {
336
+ surplus += availablePerToken - actualLength;
337
+ token.allocatedLength = actualLength;
338
+ } else {
339
+ token.allocatedLength = availablePerToken;
340
+ deficits.push(token);
341
+ }
342
+ });
343
+ // Redistribute surplus length to longer strings, one character at a time
344
+ // This way we avoid issues with greed and trying to handle floating points by dividing available length
345
+ function filterAndIncreaseLength(token) {
346
+ if (token.allocatedLength < token.name.length && surplus > 0) {
347
+ token.allocatedLength += 1;
348
+ surplus -= 1;
349
+ // if it hasn't reached its full length, keep it in array for next round
350
+ return token.allocatedLength < token.name.length;
351
+ }
352
+ return false; // Remove this token from the deficits array
353
+ }
354
+ // Redistribute surplus length to longer strings, one character at a time
355
+ let previousSurplus = surplus + 1; // infinite loop protection
356
+ while(surplus > 0 && deficits.length > 0){
357
+ deficits = deficits.filter((token)=>filterAndIncreaseLength(token));
358
+ // infinite loop protection; if the surplus hasn't changed, there was nothing left to distribute it to
359
+ if (surplus === previousSurplus) {
360
+ break;
361
+ }
362
+ previousSurplus = surplus;
363
+ }
364
+ // Build final string
365
+ const shortenedName = nameTokens.map((token)=>{
366
+ // if it is compressible, shorten it
367
+ if (token.compressible && 'allocatedLength' in token && token.allocatedLength !== undefined) {
368
+ return this.getShortenedName(token.name, token.allocatedLength);
369
+ }
370
+ // if is is only compressible as a fixed value, use that
371
+ if (token.compressible === false && token.shortName) {
372
+ return token.shortName;
373
+ }
374
+ // otherwise return it as-is
375
+ return token.name;
376
+ }).join(this.IDENTIFIER_SEPARATOR);
377
+ // this should be unreachable, but add a final check for potential edge cases we missed
378
+ if (shortenedName.length > maxLength) {
379
+ throw new Error(`name shortening failed to generate a name of the correct maxLength; name ${shortenedName}`);
380
+ }
381
+ this.setUnshortenedName(shortenedName, unshortenedName);
382
+ return shortenedName;
383
+ };
384
+ // We need to be able to find the full-length name for any shortened name, primarily for migration purposes
385
+ // Therefore we store every name that passes through so we can retrieve the original later
386
+ this.nameMap = new Map();
387
+ this.getUnshortenedName = (shortName)=>{
388
+ return this.nameMap.get(this.serializeKey(shortName)) ?? shortName;
389
+ };
390
+ this.setUnshortenedName = (shortName, fullName)=>{
391
+ // This is protection against cases where a name is shortened twice, for example shortened in a model outside of createMetadata
392
+ // and then run through the shortener against inside createMetadata, which would do nothing at all but replace the original
393
+ // name in this mapping
394
+ if (this.nameMap.get(this.serializeKey(shortName)) && shortName === fullName) {
395
+ return;
396
+ }
397
+ // set the name
398
+ this.nameMap.set(this.serializeKey(shortName), fullName);
399
+ };
400
+ this.serializeKey = (shortName)=>{
401
+ return `${shortName}.${this.options.maxLength}`;
402
+ };
403
+ _class_private_field_loose_base(this, _options)[_options] = options;
404
+ }
405
+ }
406
+ // TODO: instead of instantiating this here as a global metadata should create its own to use
407
+ // However, that would require refactoring all of the metadata methods to be instantiated to keep a centralized identifiers
408
+ const identifiers = new Identifiers({
409
+ maxLength: IDENTIFIER_MAX_LENGTH
410
+ });
411
+
412
+ exports.Identifiers = Identifiers;
413
+ exports.identifiers = identifiers;
414
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sources":["../../../src/utils/identifiers/index.ts"],"sourcesContent":["/**\n * This file contains utility functions for generating names used in the database.\n * These names include table names, column names, join table names, index names, and more.\n * The generated names can be customized with prefixes, suffixes, and maximum length.\n * These utility functions are used throughout the codebase to ensure consistent and standardized naming conventions in the database.\n *\n * The reason for checking maxLength for suffixes and prefixes and using the long ones from Strapi 4 is so that we always\n * have access to the full length names, in particular for migration purposes, but also so that (in theory) the feature\n * could be disabled and stay compatible with v4 database structure.\n */\nimport _, { isInteger, partition, snakeCase, sumBy } from 'lodash/fp';\nimport { createHash } from './hash';\nimport {\n IdentifiersOptions,\n NameInput,\n NameOptions,\n NameToken,\n NameTokenWithAllocation,\n} from './types';\n\nconst IDENTIFIER_MAX_LENGTH = 55 as const;\n\nexport class Identifiers {\n ID_COLUMN = 'id' as const;\n\n ORDER_COLUMN = 'order' as const;\n\n FIELD_COLUMN = 'field' as const;\n\n HASH_LENGTH = 5 as const;\n\n HASH_SEPARATOR = '' as const; // no separator is needed, we will just attach hash directly to shortened name\n\n IDENTIFIER_SEPARATOR = '_' as const;\n\n MIN_TOKEN_LENGTH = 3 as const; // the min characters required at the beginning of a name part\n\n // Fixed compression map for suffixes and prefixes\n #replacementMap = {\n links: 'lnk',\n order_inv_fk: 'oifk',\n order: 'ord',\n morphs: 'mph',\n index: 'idx',\n inv_fk: 'ifk',\n order_fk: 'ofk',\n id_column_index: 'idix',\n order_index: 'oidx',\n unique: 'uq',\n primary: 'pk',\n };\n\n #options: IdentifiersOptions;\n\n constructor(options: { maxLength: number }) {\n this.#options = options;\n }\n\n get replacementMap() {\n return this.#replacementMap;\n }\n\n get options() {\n return this.#options;\n }\n\n mapshortNames = (name: string): string | undefined => {\n if (name in this.replacementMap) {\n return (this.replacementMap as any)[name];\n }\n return undefined;\n };\n\n // Generic name handler that must be used by all helper functions\n /**\n * TODO: we should be requiring snake_case inputs for all names here, but we\n * aren't and it will require some refactoring to make it work. Currently if\n * we get names 'myModel' and 'my_model' they would be converted to the same\n * final string my_model which generally works but is not entirely safe\n * */\n getName = (names: NameInput, options?: NameOptions) => {\n const tokens: NameToken[] = _.castArray(names).map((name) => {\n return {\n name,\n compressible: true,\n };\n });\n\n if (options?.suffix) {\n tokens.push({\n name: options.suffix,\n compressible: false,\n shortName: this.mapshortNames(options.suffix),\n });\n }\n\n if (options?.prefix) {\n tokens.unshift({\n name: options.prefix,\n compressible: false,\n shortName: this.mapshortNames(options.prefix),\n });\n }\n\n return this.getNameFromTokens(tokens);\n };\n\n /**\n * TABLES\n */\n\n getTableName = (name: string, options?: NameOptions) => {\n return this.getName(name, options);\n };\n\n getJoinTableName = (collectionName: string, attributeName: string, options?: NameOptions) => {\n return this.getName([collectionName, attributeName], {\n suffix: 'links',\n ...options,\n });\n };\n\n getMorphTableName = (collectionName: string, attributeName: string, options?: NameOptions) => {\n return this.getName([snakeCase(collectionName), snakeCase(attributeName)], {\n suffix: 'morphs',\n ...options,\n });\n };\n\n /**\n * COLUMNS\n */\n\n getColumnName = (attributeName: string, options?: NameOptions) => {\n return this.getName(attributeName, options);\n };\n\n getJoinColumnAttributeIdName = (attributeName: string, options?: NameOptions) => {\n return this.getName(attributeName, { suffix: 'id', ...options });\n };\n\n getInverseJoinColumnAttributeIdName = (attributeName: string, options?: NameOptions) => {\n return this.getName(snakeCase(attributeName), { suffix: 'id', prefix: 'inv', ...options });\n };\n\n getOrderColumnName = (singularName: string, options?: NameOptions) => {\n return this.getName(singularName, { suffix: 'order', ...options });\n };\n\n getInverseOrderColumnName = (singularName: string, options?: NameOptions) => {\n return this.getName(singularName, {\n suffix: 'order',\n prefix: 'inv',\n ...options,\n });\n };\n\n /**\n * Morph Join Tables\n */\n getMorphColumnJoinTableIdName = (singularName: string, options?: NameOptions) => {\n return this.getName(snakeCase(singularName), { suffix: 'id', ...options });\n };\n\n getMorphColumnAttributeIdName = (attributeName: string, options?: NameOptions) => {\n return this.getName(snakeCase(attributeName), { suffix: 'id', ...options });\n };\n\n getMorphColumnTypeName = (attributeName: string, options?: NameOptions) => {\n return this.getName(snakeCase(attributeName), { suffix: 'type', ...options });\n };\n\n /**\n * INDEXES\n * Note that these methods are generally used to reference full table names + attribute(s), which\n * may already be shortened strings rather than individual parts.\n * That is fine and expected to compress the previously incompressible parts of those strings,\n * because in these cases the relevant information is the table name and we can't really do\n * any better; shortening the individual parts again might make it even more confusing.\n *\n * So for example, the fk for the table `mytable_myattr4567d_localizations` will become\n * mytable_myattr4567d_loc63bf2_fk\n */\n\n // base index types\n getIndexName = (names: NameInput, options?: NameOptions) => {\n return this.getName(names, { suffix: 'index', ...options });\n };\n\n getFkIndexName = (names: NameInput, options?: NameOptions) => {\n return this.getName(names, { suffix: 'fk', ...options });\n };\n\n getUniqueIndexName = (names: NameInput, options?: NameOptions) => {\n return this.getName(names, { suffix: 'unique', ...options });\n };\n\n getPrimaryIndexName = (names: NameInput, options?: NameOptions) => {\n return this.getName(names, { suffix: 'primary', ...options });\n };\n\n // custom index types\n getInverseFkIndexName = (names: NameInput, options?: NameOptions) => {\n return this.getName(names, { suffix: 'inv_fk', ...options });\n };\n\n getOrderFkIndexName = (names: NameInput, options?: NameOptions) => {\n return this.getName(names, { suffix: 'order_fk', ...options });\n };\n\n getOrderInverseFkIndexName = (names: NameInput, options?: NameOptions) => {\n return this.getName(names, { suffix: 'order_inv_fk', ...options });\n };\n\n getIdColumnIndexName = (names: NameInput, options?: NameOptions) => {\n return this.getName(names, { suffix: 'id_column_index', ...options });\n };\n\n getOrderIndexName = (names: NameInput, options?: NameOptions) => {\n return this.getName(names, { suffix: 'order_index', ...options });\n };\n\n /**\n * Generates a string with a max length, appending a hash at the end if necessary to keep it unique\n *\n * @example\n * // if we have strings such as \"longstring1\" and \"longstring2\" with a max length of 9,\n * // we don't want to end up with \"longstrin\" and \"longstrin\"\n * // we want something such as \"longs0b23\" and \"longs953f\"\n * const token1 = generateToken(\"longstring1\", 9); // \"longs0b23\"\n * const token2 = generateToken(\"longstring2\", 9); // \"longs953f\"\n *\n * @param name - The base name\n * @param len - The desired length of the token.\n * @returns The generated token with hash.\n * @throws Error if the length is not a positive integer, or if the length is too short for the token.\n * @internal\n */\n getShortenedName = (name: string, len: number) => {\n if (!isInteger(len) || len <= 0) {\n throw new Error(`tokenWithHash length must be a positive integer, received ${len}`);\n }\n if (name.length <= len) {\n return name;\n }\n if (len < this.MIN_TOKEN_LENGTH + this.HASH_LENGTH) {\n throw new Error(\n `length for part of identifier too short, minimum is hash length (${this.HASH_LENGTH}) plus min token length (${this.MIN_TOKEN_LENGTH}), received ${len} for token ${name}`\n );\n }\n\n const availableLength = len - this.HASH_LENGTH - this.HASH_SEPARATOR.length;\n if (availableLength < this.MIN_TOKEN_LENGTH) {\n throw new Error(\n `length for part of identifier minimum is less than min token length (${this.MIN_TOKEN_LENGTH}), received ${len} for token ${name}`\n );\n }\n\n return `${name.substring(0, availableLength)}${this.HASH_SEPARATOR}${createHash(\n name,\n this.HASH_LENGTH\n )}`;\n };\n\n /**\n * Constructs a name from an array of name tokens within a specified maximum length. It ensures the final name does not exceed\n * this limit by selectively compressing tokens marked as compressible. If the name exceeds the maximum length and cannot be\n * compressed sufficiently, an error is thrown. This function supports dynamic adjustment of token lengths to fit within the\n * maxLength constraint (that is, it will always make use of all available space), while also ensuring the preservation of\n * incompressible tokens.\n * @internal\n */\n getNameFromTokens = (nameTokens: NameToken[]): string => {\n const { maxLength } = this.options;\n\n if (!isInteger(maxLength) || maxLength < 0) {\n throw new Error('maxLength must be a positive integer or 0 (for unlimited length)');\n }\n\n const unshortenedName = nameTokens\n .map((token) => {\n return token.name;\n })\n .join(this.IDENTIFIER_SEPARATOR);\n\n // if maxLength == 0 we want the legacy v4 name without any shortening\n if (maxLength === 0) {\n this.setUnshortenedName(unshortenedName, unshortenedName);\n return unshortenedName;\n }\n\n // check the full length name (but with incompressible tokens using shortNames if available)\n const fullLengthName = nameTokens\n .map((token) => {\n if (token.compressible) {\n return token.name;\n }\n return token.shortName ?? token.name;\n })\n .join(this.IDENTIFIER_SEPARATOR);\n\n if (fullLengthName.length <= maxLength) {\n this.setUnshortenedName(fullLengthName, unshortenedName);\n return fullLengthName;\n }\n\n // Split tokens by compressibility\n const [compressible, incompressible] = partition(\n (token: NameToken) => token.compressible,\n nameTokens\n );\n\n const totalIncompressibleLength = sumBy((token: NameToken) =>\n token.compressible === false && token.shortName !== undefined\n ? token.shortName.length\n : token.name.length\n )(incompressible);\n const totalSeparatorsLength = nameTokens.length * this.IDENTIFIER_SEPARATOR.length - 1;\n const available = maxLength - totalIncompressibleLength - totalSeparatorsLength;\n const availablePerToken = Math.floor(available / compressible.length);\n\n if (\n totalIncompressibleLength + totalSeparatorsLength > maxLength ||\n availablePerToken < this.MIN_TOKEN_LENGTH\n ) {\n throw new Error('Maximum length is too small to accommodate all tokens');\n }\n\n // Calculate the remainder from the division and add it to the surplus\n let surplus = available % compressible.length;\n\n // Check that it's even possible to proceed\n const minHashedLength = this.HASH_LENGTH + this.HASH_SEPARATOR.length + this.MIN_TOKEN_LENGTH;\n const totalLength = nameTokens.reduce(\n (total, token) => {\n if (token.compressible) {\n if (token.name.length < availablePerToken) {\n return total + token.name.length;\n }\n return total + minHashedLength;\n }\n const tokenName = token.shortName ?? token.name;\n return total + tokenName.length;\n },\n nameTokens.length * this.IDENTIFIER_SEPARATOR.length - 1\n );\n\n // TODO: this is the weakest thing of the shortener, but fortunately it can be improved later without a breaking change if it turns out to be a problem (for example, if there is some case we need 6+ name parts in one identifier). We could take this \"shortest string we could generate\" that is too long and apply the hash directly to that, which would work fine even though it would be very difficult to determine what it was actually referring to\n // Check if the maximum length is less than the total length\n if (maxLength < totalLength) {\n throw new Error('Maximum length is too small to accommodate all tokens');\n }\n\n // Calculate total surplus length from shorter strings and total deficit length from longer strings\n let deficits: NameTokenWithAllocation[] = [];\n compressible.forEach((token) => {\n const actualLength = token.name.length;\n if (actualLength < availablePerToken) {\n surplus += availablePerToken - actualLength;\n token.allocatedLength = actualLength;\n } else {\n token.allocatedLength = availablePerToken;\n deficits.push(token as NameTokenWithAllocation);\n }\n });\n\n // Redistribute surplus length to longer strings, one character at a time\n // This way we avoid issues with greed and trying to handle floating points by dividing available length\n function filterAndIncreaseLength(token: NameTokenWithAllocation) {\n if (token.allocatedLength < token.name.length && surplus > 0) {\n token.allocatedLength += 1;\n surplus -= 1;\n // if it hasn't reached its full length, keep it in array for next round\n return token.allocatedLength < token.name.length;\n }\n return false; // Remove this token from the deficits array\n }\n\n // Redistribute surplus length to longer strings, one character at a time\n let previousSurplus = surplus + 1; // infinite loop protection\n while (surplus > 0 && deficits.length > 0) {\n deficits = deficits.filter((token) => filterAndIncreaseLength(token));\n\n // infinite loop protection; if the surplus hasn't changed, there was nothing left to distribute it to\n if (surplus === previousSurplus) {\n break;\n }\n previousSurplus = surplus;\n }\n\n // Build final string\n const shortenedName = nameTokens\n .map((token) => {\n // if it is compressible, shorten it\n if (\n token.compressible &&\n 'allocatedLength' in token &&\n token.allocatedLength !== undefined\n ) {\n return this.getShortenedName(token.name, token.allocatedLength);\n }\n\n // if is is only compressible as a fixed value, use that\n if (token.compressible === false && token.shortName) {\n return token.shortName;\n }\n\n // otherwise return it as-is\n return token.name;\n })\n .join(this.IDENTIFIER_SEPARATOR);\n\n // this should be unreachable, but add a final check for potential edge cases we missed\n if (shortenedName.length > maxLength) {\n throw new Error(\n `name shortening failed to generate a name of the correct maxLength; name ${shortenedName}`\n );\n }\n\n this.setUnshortenedName(shortenedName, unshortenedName);\n return shortenedName;\n };\n\n // We need to be able to find the full-length name for any shortened name, primarily for migration purposes\n // Therefore we store every name that passes through so we can retrieve the original later\n nameMap = new Map<string, string>();\n\n getUnshortenedName = (shortName: string) => {\n return this.nameMap.get(this.serializeKey(shortName)) ?? shortName;\n };\n\n setUnshortenedName = (shortName: string, fullName: string) => {\n // This is protection against cases where a name is shortened twice, for example shortened in a model outside of createMetadata\n // and then run through the shortener against inside createMetadata, which would do nothing at all but replace the original\n // name in this mapping\n if (this.nameMap.get(this.serializeKey(shortName)) && shortName === fullName) {\n return;\n }\n\n // set the name\n this.nameMap.set(this.serializeKey(shortName), fullName);\n };\n\n serializeKey = (shortName: string) => {\n return `${shortName}.${this.options.maxLength}`;\n };\n}\n\n// TODO: instead of instantiating this here as a global metadata should create its own to use\n// However, that would require refactoring all of the metadata methods to be instantiated to keep a centralized identifiers\nexport const identifiers = new Identifiers({ maxLength: IDENTIFIER_MAX_LENGTH });\n"],"names":["IDENTIFIER_MAX_LENGTH","Identifiers","replacementMap","options","constructor","ID_COLUMN","ORDER_COLUMN","FIELD_COLUMN","HASH_LENGTH","HASH_SEPARATOR","IDENTIFIER_SEPARATOR","MIN_TOKEN_LENGTH","links","order_inv_fk","order","morphs","index","inv_fk","order_fk","id_column_index","order_index","unique","primary","mapshortNames","name","undefined","getName","names","tokens","_","castArray","map","compressible","suffix","push","shortName","prefix","unshift","getNameFromTokens","getTableName","getJoinTableName","collectionName","attributeName","getMorphTableName","snakeCase","getColumnName","getJoinColumnAttributeIdName","getInverseJoinColumnAttributeIdName","getOrderColumnName","singularName","getInverseOrderColumnName","getMorphColumnJoinTableIdName","getMorphColumnAttributeIdName","getMorphColumnTypeName","getIndexName","getFkIndexName","getUniqueIndexName","getPrimaryIndexName","getInverseFkIndexName","getOrderFkIndexName","getOrderInverseFkIndexName","getIdColumnIndexName","getOrderIndexName","getShortenedName","len","isInteger","Error","length","availableLength","substring","createHash","nameTokens","maxLength","unshortenedName","token","join","setUnshortenedName","fullLengthName","incompressible","partition","totalIncompressibleLength","sumBy","totalSeparatorsLength","available","availablePerToken","Math","floor","surplus","minHashedLength","totalLength","reduce","total","tokenName","deficits","forEach","actualLength","allocatedLength","filterAndIncreaseLength","previousSurplus","filter","shortenedName","nameMap","Map","getUnshortenedName","get","serializeKey","fullName","set","identifiers"],"mappings":";;;;;AAAA;;;;;;;;;AASC,IAAA,SAAA,+BAAA,CAAA,QAAA,EAAA,UAAA,EAAA;;;;;;;;;;AAWD,MAAMA,qBAAwB,GAAA,EAAA;;AAkB5B,eAcA,iBAAA,8BAAA,CAAA,iBAAA,CAAA,EAAA,QAAA,iBAAA,8BAAA,CAAA,UAAA,CAAA;AA9BK,MAAMC,WAAAA,CAAAA;AAoCX,IAAA,IAAIC,cAAiB,GAAA;QACnB,OAAO,+BAAA,CAAA,IAAI,EAAEA,eAAAA,CAAAA,CAAAA,eAAAA,CAAAA;AACf;AAEA,IAAA,IAAIC,OAAU,GAAA;QACZ,OAAO,+BAAA,CAAA,IAAI,EAAEA,QAAAA,CAAAA,CAAAA,QAAAA,CAAAA;AACf;AAVAC,IAAAA,WAAAA,CAAYD,OAA8B,CAAE;QAhB5C,MAAA,CAAA,cAAA,CAAA,IAAA,EAAA,eAAA,EAAA;;mBAAA,KAAA;;QAcA,MAAA,CAAA,cAAA,CAAA,IAAA,EAAA,QAAA,EAAA;;mBAAA,KAAA;;aA7BAE,SAAY,GAAA,IAAA;aAEZC,YAAe,GAAA,OAAA;aAEfC,YAAe,GAAA,OAAA;aAEfC,WAAc,GAAA,CAAA;AAEdC,QAAAA,IAAAA,CAAAA,cAAAA,GAAiB;;aAEjBC,oBAAuB,GAAA,GAAA;AAEvBC,QAAAA,IAAAA,CAAAA,gBAAAA,GAAmB;;AAGlBT,QAAAA,+BAAAA,CAAAA,IAAAA,EAAAA,eAAAA,CAAAA,CAAAA,eAAiB,CAAA,GAAA;YAChBU,KAAO,EAAA,KAAA;YACPC,YAAc,EAAA,MAAA;YACdC,KAAO,EAAA,KAAA;YACPC,MAAQ,EAAA,KAAA;YACRC,KAAO,EAAA,KAAA;YACPC,MAAQ,EAAA,KAAA;YACRC,QAAU,EAAA,KAAA;YACVC,eAAiB,EAAA,MAAA;YACjBC,WAAa,EAAA,MAAA;YACbC,MAAQ,EAAA,IAAA;YACRC,OAAS,EAAA;AACX,SAAA;AAgBAC,QAAAA,IAAAA,CAAAA,aAAAA,GAAgB,CAACC,IAAAA,GAAAA;AACf,YAAA,IAAIA,IAAQ,IAAA,IAAI,CAACtB,cAAc,EAAE;AAC/B,gBAAA,OAAO,IAAK,CAACA,cAAsB,CAACsB,IAAK,CAAA;AAC3C;YACA,OAAOC,SAAAA;AACT,SAAA;;AAGA;;;;;QAMAC,IAAAA,CAAAA,OAAAA,GAAU,CAACC,KAAkBxB,EAAAA,OAAAA,GAAAA;AAC3B,YAAA,MAAMyB,SAAsBC,CAAEC,CAAAA,SAAS,CAACH,KAAOI,CAAAA,CAAAA,GAAG,CAAC,CAACP,IAAAA,GAAAA;gBAClD,OAAO;AACLA,oBAAAA,IAAAA;oBACAQ,YAAc,EAAA;AAChB,iBAAA;AACF,aAAA,CAAA;AAEA,YAAA,IAAI7B,SAAS8B,MAAQ,EAAA;AACnBL,gBAAAA,MAAAA,CAAOM,IAAI,CAAC;AACVV,oBAAAA,IAAAA,EAAMrB,QAAQ8B,MAAM;oBACpBD,YAAc,EAAA,KAAA;AACdG,oBAAAA,SAAAA,EAAW,IAAI,CAACZ,aAAa,CAACpB,QAAQ8B,MAAM;AAC9C,iBAAA,CAAA;AACF;AAEA,YAAA,IAAI9B,SAASiC,MAAQ,EAAA;AACnBR,gBAAAA,MAAAA,CAAOS,OAAO,CAAC;AACbb,oBAAAA,IAAAA,EAAMrB,QAAQiC,MAAM;oBACpBJ,YAAc,EAAA,KAAA;AACdG,oBAAAA,SAAAA,EAAW,IAAI,CAACZ,aAAa,CAACpB,QAAQiC,MAAM;AAC9C,iBAAA,CAAA;AACF;YAEA,OAAO,IAAI,CAACE,iBAAiB,CAACV,MAAAA,CAAAA;AAChC,SAAA;AAEA;;MAIAW,IAAAA,CAAAA,YAAAA,GAAe,CAACf,IAAcrB,EAAAA,OAAAA,GAAAA;AAC5B,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACF,IAAMrB,EAAAA,OAAAA,CAAAA;AAC5B,SAAA;aAEAqC,gBAAmB,GAAA,CAACC,gBAAwBC,aAAuBvC,EAAAA,OAAAA,GAAAA;YACjE,OAAO,IAAI,CAACuB,OAAO,CAAC;AAACe,gBAAAA,cAAAA;AAAgBC,gBAAAA;aAAc,EAAE;gBACnDT,MAAQ,EAAA,OAAA;AACR,gBAAA,GAAG9B;AACL,aAAA,CAAA;AACF,SAAA;aAEAwC,iBAAoB,GAAA,CAACF,gBAAwBC,aAAuBvC,EAAAA,OAAAA,GAAAA;YAClE,OAAO,IAAI,CAACuB,OAAO,CAAC;gBAACkB,WAAUH,CAAAA,cAAAA,CAAAA;gBAAiBG,WAAUF,CAAAA,aAAAA;aAAe,EAAE;gBACzET,MAAQ,EAAA,QAAA;AACR,gBAAA,GAAG9B;AACL,aAAA,CAAA;AACF,SAAA;AAEA;;MAIA0C,IAAAA,CAAAA,aAAAA,GAAgB,CAACH,aAAuBvC,EAAAA,OAAAA,GAAAA;AACtC,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACgB,aAAevC,EAAAA,OAAAA,CAAAA;AACrC,SAAA;AAEA2C,QAAAA,IAAAA,CAAAA,4BAAAA,GAA+B,CAACJ,aAAuBvC,EAAAA,OAAAA,GAAAA;AACrD,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACgB,aAAe,EAAA;gBAAET,MAAQ,EAAA,IAAA;AAAM,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAChE,SAAA;AAEA4C,QAAAA,IAAAA,CAAAA,mCAAAA,GAAsC,CAACL,aAAuBvC,EAAAA,OAAAA,GAAAA;AAC5D,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACkB,YAAUF,aAAgB,CAAA,EAAA;gBAAET,MAAQ,EAAA,IAAA;gBAAMG,MAAQ,EAAA,KAAA;AAAO,gBAAA,GAAGjC;AAAQ,aAAA,CAAA;AAC1F,SAAA;AAEA6C,QAAAA,IAAAA,CAAAA,kBAAAA,GAAqB,CAACC,YAAsB9C,EAAAA,OAAAA,GAAAA;AAC1C,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACuB,YAAc,EAAA;gBAAEhB,MAAQ,EAAA,OAAA;AAAS,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAClE,SAAA;AAEA+C,QAAAA,IAAAA,CAAAA,yBAAAA,GAA4B,CAACD,YAAsB9C,EAAAA,OAAAA,GAAAA;AACjD,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACuB,YAAc,EAAA;gBAChChB,MAAQ,EAAA,OAAA;gBACRG,MAAQ,EAAA,KAAA;AACR,gBAAA,GAAGjC;AACL,aAAA,CAAA;AACF,SAAA;AAEA;;MAGAgD,IAAAA,CAAAA,6BAAAA,GAAgC,CAACF,YAAsB9C,EAAAA,OAAAA,GAAAA;AACrD,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACkB,YAAUK,YAAe,CAAA,EAAA;gBAAEhB,MAAQ,EAAA,IAAA;AAAM,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAC1E,SAAA;AAEAiD,QAAAA,IAAAA,CAAAA,6BAAAA,GAAgC,CAACV,aAAuBvC,EAAAA,OAAAA,GAAAA;AACtD,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACkB,YAAUF,aAAgB,CAAA,EAAA;gBAAET,MAAQ,EAAA,IAAA;AAAM,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAC3E,SAAA;AAEAkD,QAAAA,IAAAA,CAAAA,sBAAAA,GAAyB,CAACX,aAAuBvC,EAAAA,OAAAA,GAAAA;AAC/C,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACkB,YAAUF,aAAgB,CAAA,EAAA;gBAAET,MAAQ,EAAA,MAAA;AAAQ,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAC7E,SAAA;AAEA;;;;;;;;;;AAUC;AAGDmD,QAAAA,IAAAA,CAAAA,YAAAA,GAAe,CAAC3B,KAAkBxB,EAAAA,OAAAA,GAAAA;AAChC,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACC,KAAO,EAAA;gBAAEM,MAAQ,EAAA,OAAA;AAAS,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAC3D,SAAA;AAEAoD,QAAAA,IAAAA,CAAAA,cAAAA,GAAiB,CAAC5B,KAAkBxB,EAAAA,OAAAA,GAAAA;AAClC,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACC,KAAO,EAAA;gBAAEM,MAAQ,EAAA,IAAA;AAAM,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AACxD,SAAA;AAEAqD,QAAAA,IAAAA,CAAAA,kBAAAA,GAAqB,CAAC7B,KAAkBxB,EAAAA,OAAAA,GAAAA;AACtC,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACC,KAAO,EAAA;gBAAEM,MAAQ,EAAA,QAAA;AAAU,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAC5D,SAAA;AAEAsD,QAAAA,IAAAA,CAAAA,mBAAAA,GAAsB,CAAC9B,KAAkBxB,EAAAA,OAAAA,GAAAA;AACvC,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACC,KAAO,EAAA;gBAAEM,MAAQ,EAAA,SAAA;AAAW,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAC7D,SAAA;;AAGAuD,QAAAA,IAAAA,CAAAA,qBAAAA,GAAwB,CAAC/B,KAAkBxB,EAAAA,OAAAA,GAAAA;AACzC,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACC,KAAO,EAAA;gBAAEM,MAAQ,EAAA,QAAA;AAAU,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAC5D,SAAA;AAEAwD,QAAAA,IAAAA,CAAAA,mBAAAA,GAAsB,CAAChC,KAAkBxB,EAAAA,OAAAA,GAAAA;AACvC,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACC,KAAO,EAAA;gBAAEM,MAAQ,EAAA,UAAA;AAAY,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAC9D,SAAA;AAEAyD,QAAAA,IAAAA,CAAAA,0BAAAA,GAA6B,CAACjC,KAAkBxB,EAAAA,OAAAA,GAAAA;AAC9C,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACC,KAAO,EAAA;gBAAEM,MAAQ,EAAA,cAAA;AAAgB,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AAClE,SAAA;AAEA0D,QAAAA,IAAAA,CAAAA,oBAAAA,GAAuB,CAAClC,KAAkBxB,EAAAA,OAAAA,GAAAA;AACxC,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACC,KAAO,EAAA;gBAAEM,MAAQ,EAAA,iBAAA;AAAmB,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AACrE,SAAA;AAEA2D,QAAAA,IAAAA,CAAAA,iBAAAA,GAAoB,CAACnC,KAAkBxB,EAAAA,OAAAA,GAAAA;AACrC,YAAA,OAAO,IAAI,CAACuB,OAAO,CAACC,KAAO,EAAA;gBAAEM,MAAQ,EAAA,aAAA;AAAe,gBAAA,GAAG9B;AAAQ,aAAA,CAAA;AACjE,SAAA;AAEA;;;;;;;;;;;;;;;MAgBA4D,IAAAA,CAAAA,gBAAAA,GAAmB,CAACvC,IAAcwC,EAAAA,GAAAA,GAAAA;AAChC,YAAA,IAAI,CAACC,WAAAA,CAAUD,GAAQA,CAAAA,IAAAA,GAAAA,IAAO,CAAG,EAAA;AAC/B,gBAAA,MAAM,IAAIE,KAAM,CAAA,CAAC,0DAA0D,EAAEF,IAAI,CAAC,CAAA;AACpF;YACA,IAAIxC,IAAAA,CAAK2C,MAAM,IAAIH,GAAK,EAAA;gBACtB,OAAOxC,IAAAA;AACT;YACA,IAAIwC,GAAAA,GAAM,IAAI,CAACrD,gBAAgB,GAAG,IAAI,CAACH,WAAW,EAAE;gBAClD,MAAM,IAAI0D,MACR,CAAC,iEAAiE,EAAE,IAAI,CAAC1D,WAAW,CAAC,yBAAyB,EAAE,IAAI,CAACG,gBAAgB,CAAC,YAAY,EAAEqD,GAAI,CAAA,WAAW,EAAExC,IAAAA,CAAK,CAAC,CAAA;AAE/K;YAEA,MAAM4C,eAAAA,GAAkBJ,GAAM,GAAA,IAAI,CAACxD,WAAW,GAAG,IAAI,CAACC,cAAc,CAAC0D,MAAM;AAC3E,YAAA,IAAIC,eAAkB,GAAA,IAAI,CAACzD,gBAAgB,EAAE;AAC3C,gBAAA,MAAM,IAAIuD,KAAAA,CACR,CAAC,qEAAqE,EAAE,IAAI,CAACvD,gBAAgB,CAAC,YAAY,EAAEqD,GAAAA,CAAI,WAAW,EAAExC,KAAK,CAAC,CAAA;AAEvI;AAEA,YAAA,OAAO,CAAC,EAAEA,IAAAA,CAAK6C,SAAS,CAAC,CAAA,EAAGD,iBAAiB,EAAE,IAAI,CAAC3D,cAAc,CAAC,EAAE6D,eACnE9C,CAAAA,IAAAA,EACA,IAAI,CAAChB,WAAW,EAChB,CAAC;AACL,SAAA;AAEA;;;;;;;AAOC,MAAA,IAAA,CACD8B,oBAAoB,CAACiC,UAAAA,GAAAA;AACnB,YAAA,MAAM,EAAEC,SAAS,EAAE,GAAG,IAAI,CAACrE,OAAO;AAElC,YAAA,IAAI,CAAC8D,WAAAA,CAAUO,SAAcA,CAAAA,IAAAA,SAAAA,GAAY,CAAG,EAAA;AAC1C,gBAAA,MAAM,IAAIN,KAAM,CAAA,kEAAA,CAAA;AAClB;AAEA,YAAA,MAAMO,eAAkBF,GAAAA,UAAAA,CACrBxC,GAAG,CAAC,CAAC2C,KAAAA,GAAAA;AACJ,gBAAA,OAAOA,MAAMlD,IAAI;AACnB,aAAA,CAAA,CACCmD,IAAI,CAAC,IAAI,CAACjE,oBAAoB,CAAA;;AAGjC,YAAA,IAAI8D,cAAc,CAAG,EAAA;gBACnB,IAAI,CAACI,kBAAkB,CAACH,eAAiBA,EAAAA,eAAAA,CAAAA;gBACzC,OAAOA,eAAAA;AACT;;AAGA,YAAA,MAAMI,cAAiBN,GAAAA,UAAAA,CACpBxC,GAAG,CAAC,CAAC2C,KAAAA,GAAAA;gBACJ,IAAIA,KAAAA,CAAM1C,YAAY,EAAE;AACtB,oBAAA,OAAO0C,MAAMlD,IAAI;AACnB;AACA,gBAAA,OAAOkD,KAAMvC,CAAAA,SAAS,IAAIuC,KAAAA,CAAMlD,IAAI;AACtC,aAAA,CAAA,CACCmD,IAAI,CAAC,IAAI,CAACjE,oBAAoB,CAAA;YAEjC,IAAImE,cAAAA,CAAeV,MAAM,IAAIK,SAAW,EAAA;gBACtC,IAAI,CAACI,kBAAkB,CAACC,cAAgBJ,EAAAA,eAAAA,CAAAA;gBACxC,OAAOI,cAAAA;AACT;;YAGA,MAAM,CAAC7C,cAAc8C,cAAe,CAAA,GAAGC,YACrC,CAACL,KAAAA,GAAqBA,KAAM1C,CAAAA,YAAY,EACxCuC,UAAAA,CAAAA;YAGF,MAAMS,yBAAAA,GAA4BC,QAAM,CAACP,KAAAA,GACvCA,MAAM1C,YAAY,KAAK,SAAS0C,KAAMvC,CAAAA,SAAS,KAAKV,SAChDiD,GAAAA,KAAAA,CAAMvC,SAAS,CAACgC,MAAM,GACtBO,KAAMlD,CAAAA,IAAI,CAAC2C,MAAM,CACrBW,CAAAA,cAAAA,CAAAA;YACF,MAAMI,qBAAAA,GAAwBX,WAAWJ,MAAM,GAAG,IAAI,CAACzD,oBAAoB,CAACyD,MAAM,GAAG,CAAA;YACrF,MAAMgB,SAAAA,GAAYX,YAAYQ,yBAA4BE,GAAAA,qBAAAA;AAC1D,YAAA,MAAME,oBAAoBC,IAAKC,CAAAA,KAAK,CAACH,SAAAA,GAAYnD,aAAamC,MAAM,CAAA;AAEpE,YAAA,IACEa,4BAA4BE,qBAAwBV,GAAAA,SAAAA,IACpDY,oBAAoB,IAAI,CAACzE,gBAAgB,EACzC;AACA,gBAAA,MAAM,IAAIuD,KAAM,CAAA,uDAAA,CAAA;AAClB;;YAGA,IAAIqB,OAAAA,GAAUJ,SAAYnD,GAAAA,YAAAA,CAAamC,MAAM;;AAG7C,YAAA,MAAMqB,eAAkB,GAAA,IAAI,CAAChF,WAAW,GAAG,IAAI,CAACC,cAAc,CAAC0D,MAAM,GAAG,IAAI,CAACxD,gBAAgB;AAC7F,YAAA,MAAM8E,WAAclB,GAAAA,UAAAA,CAAWmB,MAAM,CACnC,CAACC,KAAOjB,EAAAA,KAAAA,GAAAA;gBACN,IAAIA,KAAAA,CAAM1C,YAAY,EAAE;AACtB,oBAAA,IAAI0C,KAAMlD,CAAAA,IAAI,CAAC2C,MAAM,GAAGiB,iBAAmB,EAAA;AACzC,wBAAA,OAAOO,KAAQjB,GAAAA,KAAAA,CAAMlD,IAAI,CAAC2C,MAAM;AAClC;AACA,oBAAA,OAAOwB,KAAQH,GAAAA,eAAAA;AACjB;AACA,gBAAA,MAAMI,SAAYlB,GAAAA,KAAAA,CAAMvC,SAAS,IAAIuC,MAAMlD,IAAI;gBAC/C,OAAOmE,KAAAA,GAAQC,UAAUzB,MAAM;aAEjCI,EAAAA,UAAAA,CAAWJ,MAAM,GAAG,IAAI,CAACzD,oBAAoB,CAACyD,MAAM,GAAG,CAAA,CAAA;;;AAKzD,YAAA,IAAIK,YAAYiB,WAAa,EAAA;AAC3B,gBAAA,MAAM,IAAIvB,KAAM,CAAA,uDAAA,CAAA;AAClB;;AAGA,YAAA,IAAI2B,WAAsC,EAAE;YAC5C7D,YAAa8D,CAAAA,OAAO,CAAC,CAACpB,KAAAA,GAAAA;AACpB,gBAAA,MAAMqB,YAAerB,GAAAA,KAAAA,CAAMlD,IAAI,CAAC2C,MAAM;AACtC,gBAAA,IAAI4B,eAAeX,iBAAmB,EAAA;AACpCG,oBAAAA,OAAAA,IAAWH,iBAAoBW,GAAAA,YAAAA;AAC/BrB,oBAAAA,KAAAA,CAAMsB,eAAe,GAAGD,YAAAA;iBACnB,MAAA;AACLrB,oBAAAA,KAAAA,CAAMsB,eAAe,GAAGZ,iBAAAA;AACxBS,oBAAAA,QAAAA,CAAS3D,IAAI,CAACwC,KAAAA,CAAAA;AAChB;AACF,aAAA,CAAA;;;AAIA,YAAA,SAASuB,wBAAwBvB,KAA8B,EAAA;gBAC7D,IAAIA,KAAAA,CAAMsB,eAAe,GAAGtB,KAAAA,CAAMlD,IAAI,CAAC2C,MAAM,IAAIoB,OAAAA,GAAU,CAAG,EAAA;AAC5Db,oBAAAA,KAAAA,CAAMsB,eAAe,IAAI,CAAA;oBACzBT,OAAW,IAAA,CAAA;;AAEX,oBAAA,OAAOb,MAAMsB,eAAe,GAAGtB,KAAMlD,CAAAA,IAAI,CAAC2C,MAAM;AAClD;AACA,gBAAA,OAAO;AACT;;YAGA,IAAI+B,eAAAA,GAAkBX,OAAU,GAAA,CAAA,CAAA;AAChC,YAAA,MAAOA,OAAU,GAAA,CAAA,IAAKM,QAAS1B,CAAAA,MAAM,GAAG,CAAG,CAAA;AACzC0B,gBAAAA,QAAAA,GAAWA,QAASM,CAAAA,MAAM,CAAC,CAACzB,QAAUuB,uBAAwBvB,CAAAA,KAAAA,CAAAA,CAAAA;;AAG9D,gBAAA,IAAIa,YAAYW,eAAiB,EAAA;AAC/B,oBAAA;AACF;gBACAA,eAAkBX,GAAAA,OAAAA;AACpB;;AAGA,YAAA,MAAMa,aAAgB7B,GAAAA,UAAAA,CACnBxC,GAAG,CAAC,CAAC2C,KAAAA,GAAAA;;gBAEJ,IACEA,KAAAA,CAAM1C,YAAY,IAClB,iBAAA,IAAqB0C,SACrBA,KAAMsB,CAAAA,eAAe,KAAKvE,SAC1B,EAAA;oBACA,OAAO,IAAI,CAACsC,gBAAgB,CAACW,MAAMlD,IAAI,EAAEkD,MAAMsB,eAAe,CAAA;AAChE;;AAGA,gBAAA,IAAItB,MAAM1C,YAAY,KAAK,KAAS0C,IAAAA,KAAAA,CAAMvC,SAAS,EAAE;AACnD,oBAAA,OAAOuC,MAAMvC,SAAS;AACxB;;AAGA,gBAAA,OAAOuC,MAAMlD,IAAI;AACnB,aAAA,CAAA,CACCmD,IAAI,CAAC,IAAI,CAACjE,oBAAoB,CAAA;;YAGjC,IAAI0F,aAAAA,CAAcjC,MAAM,GAAGK,SAAW,EAAA;AACpC,gBAAA,MAAM,IAAIN,KACR,CAAA,CAAC,yEAAyE,EAAEkC,cAAc,CAAC,CAAA;AAE/F;YAEA,IAAI,CAACxB,kBAAkB,CAACwB,aAAe3B,EAAAA,eAAAA,CAAAA;YACvC,OAAO2B,aAAAA;AACT,SAAA;;;AAIAC,QAAAA,IAAAA,CAAAA,OAAAA,GAAU,IAAIC,GAAAA,EAAAA;AAEdC,QAAAA,IAAAA,CAAAA,kBAAAA,GAAqB,CAACpE,SAAAA,GAAAA;YACpB,OAAO,IAAI,CAACkE,OAAO,CAACG,GAAG,CAAC,IAAI,CAACC,YAAY,CAACtE,SAAeA,CAAAA,CAAAA,IAAAA,SAAAA;AAC3D,SAAA;AAEAyC,QAAAA,IAAAA,CAAAA,kBAAAA,GAAqB,CAACzC,SAAmBuE,EAAAA,QAAAA,GAAAA;;;;AAIvC,YAAA,IAAI,IAAI,CAACL,OAAO,CAACG,GAAG,CAAC,IAAI,CAACC,YAAY,CAACtE,SAAeA,CAAAA,CAAAA,IAAAA,SAAAA,KAAcuE,QAAU,EAAA;AAC5E,gBAAA;AACF;;YAGA,IAAI,CAACL,OAAO,CAACM,GAAG,CAAC,IAAI,CAACF,YAAY,CAACtE,SAAYuE,CAAAA,EAAAA,QAAAA,CAAAA;AACjD,SAAA;AAEAD,QAAAA,IAAAA,CAAAA,YAAAA,GAAe,CAACtE,SAAAA,GAAAA;YACd,OAAO,CAAC,EAAEA,SAAAA,CAAU,CAAC,EAAE,IAAI,CAAChC,OAAO,CAACqE,SAAS,CAAC,CAAC;AACjD,SAAA;QAtYE,+BAAA,CAAA,IAAI,EAAErE,QAAAA,CAAAA,CAAAA,QAAUA,CAAAA,GAAAA,OAAAA;AAClB;AAsYF;AAEA;AACA;AACO,MAAMyG,WAAc,GAAA,IAAI3G,WAAY,CAAA;IAAEuE,SAAWxE,EAAAA;AAAsB,CAAG;;;;;"}