@futdevpro/nts-dynamo 1.15.98 → 1.15.100

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 (380) hide show
  1. package/.c8rc.json +26 -26
  2. package/.copilot/patterns.json +7 -7
  3. package/.cursor/rules/__assistant_guide.mdc +30 -30
  4. package/.cursor/rules/_ag_backend-structure.mdc +85 -85
  5. package/.cursor/rules/_ag_backend.mdc +16 -16
  6. package/.cursor/rules/_ag_frontend-structure.mdc +86 -86
  7. package/.cursor/rules/_ag_frontend.mdc +39 -39
  8. package/.cursor/rules/_ag_import-rules.mdc +44 -44
  9. package/.cursor/rules/_ag_naming.mdc +115 -115
  10. package/.cursor/rules/_ag_should-be.mdc +6 -6
  11. package/.cursor/rules/ai_development_guide.md +60 -60
  12. package/.cursor/rules/cursor-rules.md +160 -160
  13. package/.cursor/rules/default-command.mdc +464 -464
  14. package/.cursor/rules/error_code_pattern.md +39 -39
  15. package/.cursor/rules/saved rule mcp server use.md +15 -15
  16. package/.dynamo/logs/cicd-pipeline/output.log +2875 -0
  17. package/.dynamo/logs/cicd-pipeline/status.json +74 -0
  18. package/.vscode/settings.json +10 -10
  19. package/HOWTO.md +15 -15
  20. package/LICENSE +21 -21
  21. package/__documentations/nts-integration-tests-2026-03-17.md +26 -26
  22. package/__documentations/plans/BEDROCK-HYPERPLAN.md +95 -95
  23. package/_specifications/BACKLOG.md +92 -92
  24. package/_specifications/TODO.md +15 -15
  25. package/_specifications/agent.md +138 -138
  26. package/build/_collections/client-safe-error.util.d.ts +33 -0
  27. package/build/_collections/client-safe-error.util.d.ts.map +1 -0
  28. package/build/_collections/client-safe-error.util.js +68 -0
  29. package/build/_collections/client-safe-error.util.js.map +1 -0
  30. package/build/_models/control-models/endpoint-params.control-model.d.ts.map +1 -1
  31. package/build/_models/control-models/endpoint-params.control-model.js +14 -11
  32. package/build/_models/control-models/endpoint-params.control-model.js.map +1 -1
  33. package/build/_services/server/app.server.d.ts.map +1 -1
  34. package/build/_services/server/app.server.js +5 -1
  35. package/build/_services/server/app.server.js.map +1 -1
  36. package/build/index.d.ts +1 -0
  37. package/build/index.d.ts.map +1 -1
  38. package/build/index.js +1 -0
  39. package/build/index.js.map +1 -1
  40. package/eslint.config.js +3 -3
  41. package/nodemon.json +24 -24
  42. package/package.json +1 -1
  43. package/pnpm-workspace.yaml +5 -5
  44. package/scripts/run-coverage-tests.js +28 -28
  45. package/spec/support/helpers/spec-reporter-loader.js +359 -359
  46. package/spec/support/helpers/ts-node-helper.js +93 -93
  47. package/spec/support/jasmine.coverage.json +24 -24
  48. package/spec/support/jasmine.json +24 -24
  49. package/src/_collections/archive.util.spec.ts +57 -57
  50. package/src/_collections/archive.util.ts +18 -18
  51. package/src/_collections/atlas-default-db-options.const.ts +9 -9
  52. package/src/_collections/client-safe-error.util.spec.ts +95 -0
  53. package/src/_collections/client-safe-error.util.ts +72 -0
  54. package/src/_collections/default-fallback-cache-max-age.const.spec.ts +11 -11
  55. package/src/_collections/default-fallback-cache-max-age.const.ts +2 -2
  56. package/src/_collections/default-not-found-page.const.spec.ts +19 -19
  57. package/src/_collections/default-not-found-page.const.ts +22 -22
  58. package/src/_collections/default-socket-path.const.spec.ts +12 -12
  59. package/src/_collections/default-socket-path.const.ts +2 -2
  60. package/src/_collections/get-environment-settings.util.spec.ts +210 -210
  61. package/src/_collections/get-environment-settings.util.ts +48 -48
  62. package/src/_collections/global-settings.const.ts +109 -109
  63. package/src/_collections/sample.env +21 -21
  64. package/src/_collections/star.controller.spec.ts +224 -224
  65. package/src/_collections/star.controller.ts +129 -129
  66. package/src/_enums/data-model-type.enum.ts +14 -14
  67. package/src/_enums/data-service-function.enum.ts +24 -24
  68. package/src/_enums/predefined-data-types.enum.ts +16 -16
  69. package/src/_enums/route-security.enum.ts +12 -12
  70. package/src/_models/control-models/api-call-params.control-model.spec.ts +152 -152
  71. package/src/_models/control-models/api-call-params.control-model.ts +142 -142
  72. package/src/_models/control-models/app-ext-system-controls.control-model.spec.ts +52 -52
  73. package/src/_models/control-models/app-ext-system-controls.control-model.ts +9 -9
  74. package/src/_models/control-models/app-params.control-model.spec.ts +225 -225
  75. package/src/_models/control-models/app-params.control-model.ts +136 -136
  76. package/src/_models/control-models/app-system-controls.control-model.spec.ts +31 -31
  77. package/src/_models/control-models/app-system-controls.control-model.ts +9 -9
  78. package/src/_models/control-models/endpoint-params.control-model.spec.ts +669 -627
  79. package/src/_models/control-models/endpoint-params.control-model.ts +628 -627
  80. package/src/_models/control-models/http-settings.control-model.spec.ts +77 -77
  81. package/src/_models/control-models/http-settings.control-model.ts +37 -37
  82. package/src/_models/control-models/system-control.control-model.spec.ts +27 -27
  83. package/src/_models/control-models/system-control.control-model.ts +12 -12
  84. package/src/_models/interfaces/certification-settings.interface.ts +7 -7
  85. package/src/_models/interfaces/environment-settings.interface.ts +59 -59
  86. package/src/_models/interfaces/global-log-settings.interface.ts +171 -171
  87. package/src/_models/interfaces/global-service-settings.interface.ts +47 -47
  88. package/src/_models/interfaces/global-settings.interface.ts +259 -259
  89. package/src/_models/interfaces/routing-module-settings.interface.ts +21 -21
  90. package/src/_models/interfaces/static-client-settings.interface.spec.ts +29 -29
  91. package/src/_models/interfaces/static-client-settings.interface.ts +28 -28
  92. package/src/_models/types/db-update.type.ts +100 -100
  93. package/src/_modules/ai/_models/ai-input-interfaces.ts +117 -117
  94. package/src/_modules/ai/_models/ai-test-generation-result.interface.ts +16 -16
  95. package/src/_modules/ai/_modules/anthropic/_services/aai-user-key.control-service.ts +138 -138
  96. package/src/_modules/ai/_modules/anthropic/index.ts +5 -5
  97. package/src/_modules/ai/_modules/document-ai/_collections/dai-chunking.util.spec.ts +242 -242
  98. package/src/_modules/ai/_modules/document-ai/_collections/dai-chunking.util.ts +639 -639
  99. package/src/_modules/ai/_modules/document-ai/_collections/dai-code-chunking.util.spec.ts +295 -295
  100. package/src/_modules/ai/_modules/document-ai/_collections/dai-code-chunking.util.ts +518 -518
  101. package/src/_modules/ai/_modules/document-ai/_collections/dai-document.util.spec.ts +209 -209
  102. package/src/_modules/ai/_modules/document-ai/_collections/dai-document.util.ts +85 -85
  103. package/src/_modules/ai/_modules/document-ai/_enums/dai-compare-result-type.enum.ts +7 -7
  104. package/src/_modules/ai/_modules/document-ai/_models/data-models/dai-doc-chunk.data-model.ts +146 -146
  105. package/src/_modules/ai/_modules/document-ai/_models/data-models/dai-doc-page.data-model.ts +162 -162
  106. package/src/_modules/ai/_modules/document-ai/_models/data-models/dai-document.data-model.ts +99 -99
  107. package/src/_modules/ai/_modules/document-ai/_models/interfaces/dai-code-chunk.interface.ts +68 -68
  108. package/src/_modules/ai/_modules/document-ai/_models/interfaces/dai-doc-chunk-compare-result.interface.ts +18 -18
  109. package/src/_modules/ai/_modules/document-ai/_models/interfaces/dai-doc-page-compare-result.interface.ts +19 -19
  110. package/src/_modules/ai/_modules/document-ai/_models/interfaces/dai-document-compare-result.interface.ts +25 -25
  111. package/src/_modules/ai/_modules/document-ai/index.ts +30 -30
  112. package/src/_modules/ai/_modules/fdp-ai/_services/fdpai-user-key.control-service.ts +189 -189
  113. package/src/_modules/ai/_modules/fdp-ai/index.ts +5 -5
  114. package/src/_modules/ai/_modules/open-ai/_collections/oai-global-settings.const.ts +9 -9
  115. package/src/_modules/ai/_modules/open-ai/_collections/oai-llm-predefined-requests-hu.conts.ts +82 -82
  116. package/src/_modules/ai/_modules/open-ai/_collections/oai-llm-predefined-requests.conts.ts +75 -75
  117. package/src/_modules/ai/_modules/open-ai/_enums/oai-gpt-message-role.enum.ts +45 -45
  118. package/src/_modules/ai/_modules/open-ai/_models/interfaces/oai-global-settings.interface.ts +7 -7
  119. package/src/_modules/ai/_modules/open-ai/_models/interfaces/oai-gpt-message.interface.ts +7 -7
  120. package/src/_modules/ai/_modules/open-ai/_models/interfaces/oai-llm-predefined-requests.interface.ts +57 -57
  121. package/src/_modules/ai/_modules/open-ai/_services/data-services/oai-doc-chunk-data.service.ts +292 -292
  122. package/src/_modules/ai/_modules/open-ai/_services/data-services/oai-document.data-service.spec.ts +342 -342
  123. package/src/_modules/ai/_modules/open-ai/_services/data-services/oai-vector-data.service.spec.ts +550 -550
  124. package/src/_modules/ai/_modules/open-ai/_services/data-services/oai-vector-data.service.ts +630 -630
  125. package/src/_modules/ai/_modules/open-ai/_services/oai-embedding.control-service.spec.ts +332 -332
  126. package/src/_modules/ai/_modules/open-ai/_services/oai-llm-chat.service-base.spec.ts +462 -462
  127. package/src/_modules/ai/_modules/open-ai/_services/oai-llm-chat.service-base.ts +634 -634
  128. package/src/_modules/ai/_modules/open-ai/_services/oai-llm.service-base.spec.ts +489 -489
  129. package/src/_modules/ai/_modules/open-ai/_services/oai-llm.service-base.tools.spec.ts +173 -173
  130. package/src/_modules/ai/_modules/open-ai/_services/oai-llm.service-base.ts +1033 -1033
  131. package/src/_modules/ai/_modules/open-ai/_services/oai-user-key.control-service.ts +157 -157
  132. package/src/_modules/ai/_services/ai-embedding-mock.service.spec.ts +115 -115
  133. package/src/_modules/ai/_services/ai-embedding-mock.service.ts +212 -212
  134. package/src/_modules/ai/_services/ai-embedding-provider.registry.spec.ts +110 -110
  135. package/src/_modules/ai/_services/ai-embedding-provider.registry.ts +110 -110
  136. package/src/_modules/ai/_services/ai-embedding.service-base.spec.ts +98 -98
  137. package/src/_modules/ai/_services/ai-embedding.service-base.ts +48 -48
  138. package/src/_modules/ai/_services/ai-llm-chat.service-base.spec.ts +229 -229
  139. package/src/_modules/ai/_services/ai-llm-chat.service-base.ts +68 -68
  140. package/src/_modules/ai/_services/ai-llm.service-base.spec.ts +250 -250
  141. package/src/_modules/ai/_services/ai-llm.service-base.ts +519 -519
  142. package/src/_modules/ai/_services/ai-provider.service-base.spec.ts +158 -158
  143. package/src/_modules/ai/_services/ai-user-key.service-base.ts +59 -59
  144. package/src/_modules/ai/_services/lmstudio-embedding.control-service.spec.ts +197 -197
  145. package/src/_modules/ai/_services/lmstudio-embedding.control-service.ts +371 -371
  146. package/src/_modules/ai/index.ts +23 -23
  147. package/src/_modules/assistant/_collections/ass-global-settings.const.ts +13 -13
  148. package/src/_modules/assistant/_collections/ass.util.spec.ts +176 -176
  149. package/src/_modules/assistant/_collections/ass.util.ts +50 -50
  150. package/src/_modules/assistant/_models/ass-global-settings.interface.ts +15 -15
  151. package/src/_modules/assistant/_services/ass-io.control-service.spec.ts +140 -140
  152. package/src/_modules/assistant/_services/ass-main.control-service.spec.ts +192 -192
  153. package/src/_modules/assistant/_services/ass-main.control-service.ts +107 -107
  154. package/src/_modules/bot/_collections/bot-default-commands.const.ts +12 -12
  155. package/src/_modules/bot/_collections/bot-global-settings.const.ts +39 -39
  156. package/src/_modules/bot/_models/bot-channel-wrapper.interface.ts +62 -62
  157. package/src/_modules/bot/_models/bot-command.interface.ts +8 -8
  158. package/src/_modules/bot/_models/bot-global-settings.interface.ts +96 -96
  159. package/src/_modules/bot/_models/bot-last-mention-date.interface.ts +6 -6
  160. package/src/_modules/bot/_models/bot-last-message-date.interface.ts +5 -5
  161. package/src/_modules/bot/_models/bot-user-wrapper.interface.ts +41 -41
  162. package/src/_modules/bot/_modules/discord-bot/_models/dib-platform.types.ts +9 -9
  163. package/src/_modules/bot/_modules/discord-bot/_services/dib-messaging-provider.control-service.spec.ts +431 -431
  164. package/src/_modules/bot/_modules/dynamo-bot/_collections/dyb-operations.util.spec.ts +160 -160
  165. package/src/_modules/bot/_modules/dynamo-bot/_collections/dyb-operations.util.ts +55 -55
  166. package/src/_modules/bot/_modules/dynamo-bot/_models/dyb-platform.types.ts +15 -15
  167. package/src/_modules/bot/_modules/dynamo-bot/_services/dyb-messaging-provider.control-service.spec.ts +374 -374
  168. package/src/_modules/bot/_modules/dynamo-bot/_services/dyb-messaging-provider.control-service.ts +447 -447
  169. package/src/_modules/bot/_modules/dynamo-bot/index.ts +15 -15
  170. package/src/_modules/bot/_modules/slack-bot/_models/slb-platform.types.ts +9 -9
  171. package/src/_modules/bot/_modules/slack-bot/_services/slb-messaging-provider.control-service.spec.ts +344 -344
  172. package/src/_modules/bot/_modules/slack-bot/_services/slb-messaging-provider.control-service.ts +197 -197
  173. package/src/_modules/bot/_modules/teams-bot/_models/teb-platform.types.ts +9 -9
  174. package/src/_modules/bot/_modules/teams-bot/_services/teb-messaging-provider.control-service.spec.ts +345 -345
  175. package/src/_modules/bot/_modules/teams-bot/_services/teb-messaging-provider.control-service.ts +197 -197
  176. package/src/_modules/bot/_services/bot-commands.control-service.spec.ts +116 -116
  177. package/src/_modules/bot/_services/bot-io.control-service.spec.ts +285 -285
  178. package/src/_modules/bot/_services/bot-main.control-service.spec.ts +208 -208
  179. package/src/_modules/bot/_services/bot-messaging-provider.service-base.spec.ts +349 -349
  180. package/src/_modules/bot/_services/bot-routines.control-service.spec.ts +111 -111
  181. package/src/_modules/custom-data/custom-data.controller.spec.ts +49 -49
  182. package/src/_modules/custom-data/custom-data.controller.ts +67 -67
  183. package/src/_modules/custom-data/custom-data.data-service.spec.ts +54 -54
  184. package/src/_modules/custom-data/custom-data.data-service.ts +21 -21
  185. package/src/_modules/custom-data/get-custom-data-routing-module.util.spec.ts +28 -28
  186. package/src/_modules/custom-data/get-custom-data-routing-module.util.ts +24 -24
  187. package/src/_modules/custom-data/index.ts +9 -9
  188. package/src/_modules/data-readers/_collections/dynts-sqlite-reader.util.spec.ts +161 -161
  189. package/src/_modules/data-readers/_collections/dynts-sqlite-reader.util.ts +203 -203
  190. package/src/_modules/data-readers/_models/interfaces/dynts-sqlite-reader.interface.ts +33 -33
  191. package/src/_modules/data-readers/index.ts +11 -11
  192. package/src/_modules/defaults/_collections/default-endpoints.util.ts +487 -487
  193. package/src/_modules/defaults/_models/default-user.data-model.ts +72 -72
  194. package/src/_modules/defaults/_services/default-auth.service.spec.ts +269 -269
  195. package/src/_modules/defaults/_services/default-auth.service.ts +177 -177
  196. package/src/_modules/defaults/_services/default-socket-events.service.spec.ts +42 -42
  197. package/src/_modules/defaults/_services/default-socket-events.service.ts +61 -61
  198. package/src/_modules/defaults/_services/default-user.data-service.spec.ts +187 -187
  199. package/src/_modules/defaults/_services/default-user.data-service.ts +98 -98
  200. package/src/_modules/defaults/index.ts +17 -17
  201. package/src/_modules/discord-assistant/_collections/dias-global-settings.const.ts +19 -19
  202. package/src/_modules/discord-assistant/_collections/dias.util.spec.ts +366 -366
  203. package/src/_modules/discord-assistant/_collections/dias.util.ts +132 -132
  204. package/src/_modules/discord-assistant/_models/dias-global-settings.interface.ts +19 -19
  205. package/src/_modules/discord-assistant/_models/dias-knowledge.data-model.ts +52 -52
  206. package/src/_modules/discord-assistant/_services/dias-chunk.data-service.ts +177 -177
  207. package/src/_modules/discord-assistant/_services/dias-io.control-service.spec.ts +108 -108
  208. package/src/_modules/discord-assistant/_services/dias-io.control-service.ts +69 -69
  209. package/src/_modules/discord-assistant/_services/dias-main.control-service.spec.ts +22 -22
  210. package/src/_modules/discord-assistant/_services/dias-main.control-service.ts +27 -27
  211. package/src/_modules/discord-assistant/_services/dias.service-base.spec.ts +195 -195
  212. package/src/_modules/discord-assistant/_services/dias.service-base.ts +76 -76
  213. package/src/_modules/discord-assistant/index.ts +38 -38
  214. package/src/_modules/discord-assistant-voiced/_services/dias-discord-bot.control-service.spec.ts +34 -34
  215. package/src/_modules/discord-assistant-voiced/_services/dias-discord-bot.control-service.ts +11 -11
  216. package/src/_modules/discord-assistant-voiced/index.ts +36 -36
  217. package/src/_modules/discord-bot/_collections/dibo-default-commands.const.ts +16 -16
  218. package/src/_modules/discord-bot/_collections/dibo-global-settings.conts.ts +55 -55
  219. package/src/_modules/discord-bot/_collections/dibo-operations.util.spec.ts +214 -214
  220. package/src/_modules/discord-bot/_collections/dibo-operations.util.ts +387 -387
  221. package/src/_modules/discord-bot/_models/dibo-command.interface.ts +12 -12
  222. package/src/_modules/discord-bot/_models/dibo-global-settings.interface.ts +98 -98
  223. package/src/_modules/discord-bot/_models/dibo-last-mention-date.inteface.ts +7 -7
  224. package/src/_modules/discord-bot/_models/dibo-last-message-date.interface.ts +6 -6
  225. package/src/_modules/discord-bot/_services/dibo-commands.control-service.spec.ts +154 -154
  226. package/src/_modules/discord-bot/_services/dibo-commands.control-service.ts +153 -153
  227. package/src/_modules/discord-bot/_services/dibo-io.control-service.spec.ts +264 -264
  228. package/src/_modules/discord-bot/_services/dibo-io.control-service.ts +306 -306
  229. package/src/_modules/discord-bot/_services/dibo-main.control-service.spec.ts +408 -408
  230. package/src/_modules/discord-bot/_services/dibo-main.control-service.ts +487 -487
  231. package/src/_modules/discord-bot/_services/dibo-routines.control-service.spec.ts +105 -105
  232. package/src/_modules/discord-bot/index.ts +36 -36
  233. package/src/_modules/local-vector-search/_enums/lvs-search-mode.enum.ts +35 -35
  234. package/src/_modules/local-vector-search/_models/data-models/lvs-vector-persist.data-model.ts +59 -59
  235. package/src/_modules/local-vector-search/_models/lvs-search-result.interface.ts +17 -17
  236. package/src/_modules/local-vector-search/_services/lvs-doc-chunk-data.service.spec.ts +418 -418
  237. package/src/_modules/local-vector-search/_services/lvs-doc-chunk-data.service.ts +276 -276
  238. package/src/_modules/local-vector-search/_services/lvs-local-vector-search.data-service.spec.ts +480 -480
  239. package/src/_modules/local-vector-search/_services/lvs-local-vector-search.data-service.ts +416 -416
  240. package/src/_modules/local-vector-search/_services/lvs-persistent-vector-pool.control-service.spec.ts +198 -198
  241. package/src/_modules/local-vector-search/_services/lvs-persistent-vector-pool.control-service.ts +146 -146
  242. package/src/_modules/local-vector-search/_services/lvs-vector-persist.data-service.spec.ts +167 -167
  243. package/src/_modules/local-vector-search/_services/lvs-vector-persist.data-service.ts +106 -106
  244. package/src/_modules/local-vector-search/_services/lvs-vector-pool.control-service.spec.ts +507 -507
  245. package/src/_modules/local-vector-search/_services/lvs-vector-pool.control-service.ts +272 -272
  246. package/src/_modules/local-vector-search/index.ts +16 -16
  247. package/src/_modules/logs/index.ts +11 -11
  248. package/src/_modules/mcp/_models/interfaces/dynts-mcp.interface.ts +111 -111
  249. package/src/_modules/mcp/_services/dynts-mcp-server.service-base.spec.ts +142 -142
  250. package/src/_modules/mcp/_services/dynts-mcp-server.service-base.ts +120 -120
  251. package/src/_modules/mcp/_services/dynts-mcp.adapter.ts +168 -168
  252. package/src/_modules/mcp/index.ts +13 -13
  253. package/src/_modules/messaging/README.md +354 -354
  254. package/src/_modules/messaging/_collections/get-messaging-routing-module.util.ts +26 -26
  255. package/src/_modules/messaging/_collections/msg-global-settings.const.ts +22 -22
  256. package/src/_modules/messaging/_collections/msg.util.spec.ts +226 -226
  257. package/src/_modules/messaging/_models/msg-global-settings.interface.ts +37 -37
  258. package/src/_modules/messaging/_services/msg-conversation.data-service.ts +146 -146
  259. package/src/_modules/messaging/_services/msg-events.service.spec.ts +219 -219
  260. package/src/_modules/messaging/_services/msg-events.service.ts +267 -267
  261. package/src/_modules/messaging/_services/msg-integration.control-service.ts +179 -179
  262. package/src/_modules/messaging/_services/msg-main.control-service.spec.ts +147 -147
  263. package/src/_modules/messaging/_services/msg-main.control-service.ts +571 -571
  264. package/src/_modules/messaging/_services/msg-message.data-service.ts +129 -129
  265. package/src/_modules/messaging/_services/msg.controller.spec.ts +201 -201
  266. package/src/_modules/messaging/index.ts +30 -30
  267. package/src/_modules/mock/app-extended-server.mock.ts +201 -201
  268. package/src/_modules/mock/app-integration-test.mock.ts +51 -51
  269. package/src/_modules/mock/app-params.mock.spec.ts +21 -21
  270. package/src/_modules/mock/app-params.mock.ts +9 -9
  271. package/src/_modules/mock/app-server.mock.ts +188 -188
  272. package/src/_modules/mock/auth-service.mock.spec.ts +47 -47
  273. package/src/_modules/mock/auth-service.mock.ts +28 -28
  274. package/src/_modules/mock/controller.mock.spec.ts +26 -26
  275. package/src/_modules/mock/controller.mock.ts +16 -16
  276. package/src/_modules/mock/data-model.mock.spec.ts +111 -111
  277. package/src/_modules/mock/data-model.mock.ts +82 -82
  278. package/src/_modules/mock/email-service-collection.mock.spec.ts +24 -24
  279. package/src/_modules/mock/email-service-collection.mock.ts +15 -15
  280. package/src/_modules/mock/email-service.mock.spec.ts +17 -17
  281. package/src/_modules/mock/email-service.mock.ts +20 -20
  282. package/src/_modules/mock/email-template.mock.html +14 -14
  283. package/src/_modules/mock/endpoint.mock.ts +91 -91
  284. package/src/_modules/mock/socket-client.mock.spec.ts +40 -40
  285. package/src/_modules/mock/socket-client.mock.ts +45 -45
  286. package/src/_modules/mock/socket-server.mock.spec.ts +44 -44
  287. package/src/_modules/mock/socket-server.mock.ts +46 -46
  288. package/src/_modules/oauth2/_routes/oauth2.controller.spec.ts +107 -107
  289. package/src/_modules/oauth2/_routes/oauth2.controller.ts +98 -98
  290. package/src/_modules/oauth2/_services/oauth2.auth-service.spec.ts +254 -254
  291. package/src/_modules/oauth2/_services/oauth2.auth-service.ts +232 -232
  292. package/src/_modules/oauth2/_services/oauth2.control-service.spec.ts +585 -585
  293. package/src/_modules/oauth2/_services/oauth2.control-service.ts +653 -653
  294. package/src/_modules/oauth2/index.ts +17 -17
  295. package/src/_modules/scheduler/_models/scheduler-job.interface.ts +35 -35
  296. package/src/_modules/scheduler/get-scheduler-routing-module.util.ts +33 -33
  297. package/src/_modules/scheduler/index.ts +8 -8
  298. package/src/_modules/scheduler/scheduler.controller.spec.ts +42 -42
  299. package/src/_modules/scheduler/scheduler.controller.ts +69 -69
  300. package/src/_modules/scheduler/scheduler.service.spec.ts +141 -141
  301. package/src/_modules/scheduler/scheduler.service.ts +176 -176
  302. package/src/_modules/scoped-config/_enums/dynts-scoped-config-level.enum.ts +22 -22
  303. package/src/_modules/scoped-config/_models/data-models/dynts-scoped-config.data-model.ts +81 -81
  304. package/src/_modules/scoped-config/_models/interfaces/dynts-scoped-config.interface.ts +107 -107
  305. package/src/_modules/scoped-config/_services/dynts-scoped-config.control-service.spec.ts +306 -306
  306. package/src/_modules/scoped-config/_services/dynts-scoped-config.control-service.ts +295 -295
  307. package/src/_modules/scoped-config/_services/dynts-scoped-config.data-service.spec.ts +118 -118
  308. package/src/_modules/scoped-config/_services/dynts-scoped-config.data-service.ts +105 -105
  309. package/src/_modules/scoped-config/index.ts +17 -17
  310. package/src/_modules/server/errors/errors.control-service.spec.ts +238 -238
  311. package/src/_modules/server/errors/errors.control-service.ts +100 -100
  312. package/src/_modules/server/errors/errors.controller.spec.ts +268 -268
  313. package/src/_modules/server/errors/errors.controller.ts +515 -515
  314. package/src/_modules/server/errors/errors.data-service.spec.ts +480 -480
  315. package/src/_modules/server/index.ts +30 -30
  316. package/src/_modules/server/server-status/server-status-snapshot.control-service.spec.ts +70 -70
  317. package/src/_modules/server/server-status/server-status-snapshot.control-service.ts +17 -17
  318. package/src/_modules/server/server-status/server-status-snapshot.data-service.spec.ts +77 -77
  319. package/src/_modules/server/server-status/server-status-snapshot.data-service.ts +37 -37
  320. package/src/_modules/server/server-status/server-status.control-service.spec.ts +576 -576
  321. package/src/_modules/server/server-status/server-status.control-service.ts +396 -396
  322. package/src/_modules/server/server-status/server-status.controller.spec.ts +255 -255
  323. package/src/_modules/server/server-status/server-status.controller.ts +272 -272
  324. package/src/_modules/socket/_enums/socket-security.enum.ts +11 -11
  325. package/src/_modules/socket/_models/socket-client-service-params.control-model.spec.ts +32 -32
  326. package/src/_modules/socket/_models/socket-client-service-params.control-model.ts +22 -22
  327. package/src/_modules/socket/_models/socket-presence.control-model.spec.ts +164 -164
  328. package/src/_modules/socket/_models/socket-presence.control-model.ts +210 -210
  329. package/src/_modules/socket/_models/socket-server-service-params.control-model.spec.ts +46 -46
  330. package/src/_modules/socket/_models/socket-server-service-params.control-model.ts +22 -22
  331. package/src/_modules/socket/_services/socket-client.service.spec.ts +15 -15
  332. package/src/_modules/socket/_services/socket-client.service.ts +260 -260
  333. package/src/_modules/socket/_services/socket-server.service.spec.ts +11 -11
  334. package/src/_modules/socket/app-extended.integration.spec.ts +85 -85
  335. package/src/_modules/socket/app-extended.server.ts +630 -630
  336. package/src/_modules/socket/index.ts +42 -42
  337. package/src/_modules/test/get-test-routing-module.util.spec.ts +28 -28
  338. package/src/_modules/test/get-test-routing-module.util.ts +23 -23
  339. package/src/_modules/test/index.ts +11 -11
  340. package/src/_modules/test/test.controller.spec.ts +72 -72
  341. package/src/_modules/test/test.controller.ts +115 -115
  342. package/src/_modules/usage/get-usage-routing-module.util.ts +22 -22
  343. package/src/_modules/usage/index.ts +15 -15
  344. package/src/_modules/usage/usage.controller.spec.ts +81 -81
  345. package/src/_modules/usage/usage.controller.ts +126 -126
  346. package/src/_modules/usage/usage.data-service.spec.ts +332 -332
  347. package/src/_modules/usage/usage.data-service.ts +185 -185
  348. package/src/_services/base/api.service-base.spec.ts +125 -125
  349. package/src/_services/base/api.service-base.ts +74 -74
  350. package/src/_services/base/archive-data.service.spec.ts +209 -209
  351. package/src/_services/base/archive-data.service.ts +224 -224
  352. package/src/_services/base/data.service.spec.ts +729 -729
  353. package/src/_services/base/data.service.ts +2744 -2744
  354. package/src/_services/base/db.service.spec.ts +160 -160
  355. package/src/_services/base/db.service.ts +1592 -1592
  356. package/src/_services/base/singleton.service-base.spec.ts +28 -28
  357. package/src/_services/base/singleton.service-base.ts +24 -24
  358. package/src/_services/base/singleton.service.spec.ts +114 -114
  359. package/src/_services/base/singleton.service.ts +38 -38
  360. package/src/_services/core/api.service.spec.ts +140 -140
  361. package/src/_services/core/auth.service.spec.ts +159 -159
  362. package/src/_services/core/auth.service.ts +174 -174
  363. package/src/_services/core/email.service.spec.ts +85 -85
  364. package/src/_services/core/email.service.ts +757 -757
  365. package/src/_services/core/global.service.spec.ts +292 -292
  366. package/src/_services/core/global.service.ts +487 -487
  367. package/src/_services/core/memory-guard.service.spec.ts +245 -245
  368. package/src/_services/core/memory-guard.service.ts +481 -481
  369. package/src/_services/core/service-collection.service.spec.ts +46 -46
  370. package/src/_services/core/service-collection.service.ts +6 -6
  371. package/src/_services/route/controller.service.spec.ts +53 -53
  372. package/src/_services/route/controller.service.ts +148 -148
  373. package/src/_services/route/routing-module.service.spec.ts +98 -98
  374. package/src/_services/route/routing-module.service.ts +330 -330
  375. package/src/_services/server/app.server.ts +1945 -1941
  376. package/src/_services/shared.static-service.spec.ts +99 -99
  377. package/src/_services/shared.static-service.ts +78 -78
  378. package/src/index.ts +101 -100
  379. package/tsconfig.app.json +12 -12
  380. package/tsconfig.json +42 -42
@@ -1,1592 +1,1592 @@
1
-
2
- import * as mongoose from 'mongoose';
3
- import { Schema } from 'mongoose';
4
-
5
- import {
6
- DyFM_AnyError,
7
- DyFM_BasicProperty_Type,
8
- DyFM_DataModel_Params,
9
- DyFM_DataProperties,
10
- DyFM_DataProperty_Params,
11
- DyFM_DBFilter, DyFM_DBFilterSimple, DyFM_DBSort,
12
- DyFM_Error,
13
- DyFM_Error_Settings, DyFM_ErrorLevel,
14
- DyFM_Log,
15
- DyFM_Metadata,
16
- DyFM_Object
17
- } from '@futdevpro/fsm-dynamo';
18
- import { DyNTS_archiveSuffix } from '../../_collections/archive.util';
19
- import { DyNTS_DBUpdate } from '../../_models/types/db-update.type';
20
- import { DyNTS_DBQueryOptions } from '../../_models/interfaces/db-query-options.interface';
21
- import { DyNTS_global_settings } from '../../_collections/global-settings.const';
22
-
23
- /**
24
- * DB Service for MongoDB
25
- */
26
- export class DyNTS_DBService<T extends DyFM_Metadata> {
27
-
28
- serviceName: string;
29
-
30
- dataModel/* : mongoose.Model<T> */; // = mongoose.model(this.dataParams.dataName, this.getSchema());
31
-
32
- /* private depDataName: string; */
33
- private readonly depKeys: string[] = [];
34
-
35
- defaultErrorUserMsg =
36
- `We encountered an unhandled DB Error, ` +
37
- `\nplease contact the responsible development team.`;
38
-
39
- /**
40
- * @param dataName name the model
41
- * @param typeSample sample data for scheme creation (dont include DyFM_Metadata!)
42
- * @param schemaSettings additional settings for specific parameters as unique, required, minlength or maxlength
43
- * schemaSettings also MUST contain specific types that differs from the listed above (Array, Date)
44
- */
45
- constructor(
46
- public dataParams: DyFM_DataModel_Params<T>
47
- ){
48
- try {
49
- this.serviceName = this.constructor?.name;
50
-
51
- if (!this.dataParams.dataName || typeof this.dataParams.dataName !== 'string') {
52
- throw new Error(
53
- `dbName not setted up for this db-service (${this.dataParams.dataName}) (NTS DB)`
54
- );
55
- }
56
-
57
- if (!this.dataParams.constructed?.()) {
58
- throw new DyFM_Error({
59
- error: new Error(
60
- `DataModelParams is not constructed properly! (${this.dataParams.dataName}) ` +
61
- `Use the DyFM_DataModel_Params.constructor to construct it properly! (NTS DB)`
62
- ),
63
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-C01`,
64
- additionalContent: { dataParams: this.dataParams },
65
- __localStack: this.dataParams.stackLocation,
66
- });
67
- }
68
-
69
- try {
70
- this.dataModel = mongoose.model(this.dataParams.dataName, this.getSchema());
71
- } catch (error) {
72
- if (mongoose.models[this.dataParams.dataName]) {
73
- this.dataModel = mongoose.models[this.dataParams.dataName];
74
- } else {
75
- throw error;
76
- }
77
- }
78
-
79
- this.lookForDependencyDataSettings();
80
- } catch (error) {
81
- throw new DyFM_Error({
82
- message:
83
- `DyNTS_DBService construction failed! "${dataParams.dataName}" - "${this.serviceName}"`,
84
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-C00`,
85
- level: DyFM_ErrorLevel.critical,
86
- additionalContent: { dataParams: this.dataParams },
87
- error,
88
- });
89
- }
90
- }
91
-
92
- /**
93
- * save new data
94
- * @param data data
95
- * @returns data
96
- */
97
- async createData(data: T, issuer: string): Promise<T> {
98
- data.__created = new Date();
99
- data.__lastModified = new Date();
100
- data.__createdBy = issuer;
101
- data.__lastModifiedBy = issuer;
102
-
103
- const dataModel = new this.dataModel(data);
104
- const newData: T = await dataModel.save().then((res): T => {
105
- if (res) {
106
- return res?.toObject() as T;
107
-
108
- } else {
109
- throw new DyFM_Error({
110
- ...this._getDefaultErrorSettings(
111
- 'createData',
112
- new Error(
113
- `createData failed, save "${this.dataParams.dataName}" result not found! (NTS DB)`
114
- ),
115
- issuer
116
- ),
117
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-CD1`,
118
- additionalContent: { data },
119
- issuer,
120
- });
121
- }
122
- }).catch((error): void => {
123
- if (error?.flag?.includes('DYNAMO')) {
124
- throw error;
125
-
126
- } else {
127
- throw new DyFM_Error({
128
- ...this._getDefaultErrorSettings('createData', error, issuer),
129
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-CD0`,
130
- additionalContent: {
131
- data: data,
132
- dataModel: this.dataModel,
133
- },
134
- message:
135
- `createData failed, Create new "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
136
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
137
- issuer,
138
- });
139
- }
140
- });
141
-
142
- return this.stringifyDataId(newData, 'createData');
143
- }
144
-
145
- /**
146
- * Find data by _id and update
147
- * @param data data
148
- * @returns data
149
- */
150
- async modifyData(data: T, issuer: string, dontUpdateModified?: boolean): Promise<T> {
151
- if (this.dataParams.forbidModify) {
152
- await this.modifyThrowMethod(data, issuer);
153
- }
154
-
155
- if (!dontUpdateModified) {
156
- data.__lastModified = new Date();
157
- data.__lastModifiedBy = issuer;
158
- }
159
-
160
- /**
161
- * EZ A SZAR TELJESEN SZAR, nem friss, nem a db-be mentett adatokat ad vissza,
162
- * átír random value-kat össze vissza, WTF
163
- * */
164
- /* let newData: T = */
165
- await this.dataModel.findByIdAndUpdate(data._id, data)/* .then((res) => {
166
- if (res) {
167
- //return res?.toObject() as T;
168
- } else {
169
- throw new DyFM_Error({
170
- ...this._getDefaultErrorSettings(
171
- 'modifyData',
172
- new Error(`modifyData failed, modify "${this.dataParams.dataName}" result not found! (NTS DB)`),
173
- issuer,
174
- ),
175
-
176
- status: 204,
177
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-FU1`,
178
- additionalContent: { data },
179
- issuer,
180
- });
181
- }
182
- }) */.catch((error): void => {
183
- throw new DyFM_Error({
184
- ...this._getDefaultErrorSettings('modifyData', error, issuer),
185
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-FU0`,
186
- additionalContent: { data },
187
- message:
188
- `modifyData "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
189
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
190
- issuer,
191
- });
192
- });
193
-
194
- return this.stringifyDataId(data, 'modifyData');
195
- }
196
-
197
- // TODO: Missing issuer
198
- /**
199
- * returns data by _id,
200
- * @param id id
201
- * @returns data
202
- */
203
- async getDataById(id: string): Promise<T> {
204
- if (!id) {
205
- throw new DyFM_Error({
206
- ...this._getDefaultErrorSettings('getDataById', new Error(`No ID provided! (NTS DB)`)),
207
-
208
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GI1`,
209
- message: `get "${this.dataParams.dataName}" by ID was unsuccessful (NTS DB)`,
210
- });
211
- }
212
-
213
- const data: T = await this.dataModel
214
- .findById(id)
215
- .then((res): T => res?.toObject() as T ?? null)
216
- .catch((error): void => {
217
- throw new DyFM_Error({
218
- ...this._getDefaultErrorSettings('getDataById', error),
219
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GI0`,
220
- additionalContent: { id },
221
- message:
222
- `get "${this.dataParams.dataName}" by ID was unsuccessful (NTS DB)` +
223
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
224
- });
225
- });
226
-
227
- return this.stringifyDataId(data, 'getDataById');
228
- }
229
-
230
- // TODO: Missing issuer
231
- /**
232
- * get data by dependency data id,
233
- * !!!: throws error if not found (errorCode on not found: NTS-DBS-GD2)
234
- *
235
- * @param dependencyIdsFilter id
236
- * @returns data
237
- */
238
- async getDataByDependencyId(dependencyIdsFilter: { [key: string]: string }): Promise<T> {
239
- if (!this.depKeys.length) {
240
- throw new DyFM_Error({
241
- ...this._getDefaultErrorSettings(
242
- 'getDataByDependencyId',
243
- new Error(
244
- `dependencyDataIdKey not setted up for this db-service (${this.dataParams.dataName}) (NTS DB)`
245
- )
246
- ),
247
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GD0`,
248
- });
249
- }
250
-
251
- const data: T = await this.dataModel
252
- .findOne(dependencyIdsFilter)
253
- .then((res): T => res?.toObject() as T ?? null)
254
- .catch((error): void => {
255
- throw new DyFM_Error({
256
- ...this._getDefaultErrorSettings('getDataByDependencyId', error),
257
-
258
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GD1`,
259
- additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
260
- message:
261
- `get "${this.dataParams.dataName}" by ` +
262
- `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
263
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
264
- });
265
- });
266
-
267
- return this.stringifyDataId(data, 'getDataByDependencyId');
268
- }
269
-
270
- // TODO: Missing issuer
271
- async getDataListByIds(ids: string[], findDeleted?: boolean): Promise<T[]> {
272
- const dataList: T[] = await this.dataModel
273
- .find({ _id: { $in: ids } })
274
- .then((res): T[] => res as T[] ?? [])
275
- .catch((error): void => {
276
- throw new DyFM_Error({
277
- ...this._getDefaultErrorSettings('getDataListByIds', error),
278
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GDL0`,
279
- additionalContent: { ids },
280
- message:
281
- `get "${this.dataParams.dataName}" by IDs was unsuccessful (NTS DB)` +
282
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
283
- });
284
- });
285
-
286
- if (!findDeleted) {
287
- return dataList.filter(
288
- (data: T): boolean => !data._deleted
289
- ).map(
290
- (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyId')
291
- );
292
- } else {
293
- return dataList.map(
294
- (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyId')
295
- );
296
- }
297
- }
298
-
299
- // TODO: Missing issuer
300
- /**
301
- * get data by dependency data id,
302
- * !!!: throws error if not found (errorCode on not found: NTS-DBS-GLD2)
303
- *
304
- * @param dependencyIdsFilter id
305
- * @returns dataList
306
- */
307
- async getDataListByDependencyId(dependencyIdsFilter: { [key: string]: string }, findDeleted?: boolean): Promise<T[]> {
308
- if (!this.depKeys.length) {
309
- throw new DyFM_Error({
310
- ...this._getDefaultErrorSettings(
311
- 'getDataListByDependencyId',
312
- new Error(
313
- `isDependencyHook not setted up for this dataModel (${this.dataParams.dataName}) (NTS DB)`
314
- )
315
- ),
316
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GLD0`,
317
- additionalContent: {
318
- dataModel: this.dataModel,
319
- },
320
- });
321
- }
322
-
323
- const dataList: T[] = await this.dataModel
324
- .find(dependencyIdsFilter)
325
- .then((res): T[] => res as T[] ?? [])
326
- .catch((error): void => {
327
- throw new DyFM_Error({
328
- ...this._getDefaultErrorSettings('getDataListByDependencyId', error),
329
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GLD1`,
330
- additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
331
- message:
332
- `get "${this.dataParams.dataName}" by ` +
333
- `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
334
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
335
- });
336
- });
337
-
338
- if (!findDeleted) {
339
- return dataList.filter(
340
- (data: T): boolean => !data._deleted
341
- ).map(
342
- (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyId')
343
- );
344
- } else {
345
- return dataList.map(
346
- (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyId')
347
- );
348
- }
349
- }
350
-
351
- // TODO: Missing issuer
352
- /**
353
- * get multiple data objects by a list of DependencyIDs,
354
- * !!!: throws error if not found (errorCode on not found: NTS-DBS-GLDS2)
355
- *
356
- * @param ids ids
357
- * @returns dataList
358
- */
359
- async getDataListByDependencyIds(dependencyKey: string, dependencyIds: string[], findDeleted?: boolean): Promise<T[]> {
360
- if (!this.depKeys.length) {
361
- throw new DyFM_Error({
362
- ...this._getDefaultErrorSettings(
363
- 'getDataListByDependencyIds',
364
- new Error(
365
- `getDataListByDependencyIds not setted up for this db-service ` +
366
- `(${this.dataParams.dataName}) (NTS DB)`
367
- )
368
- ),
369
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GLDS0`,
370
- });
371
- }
372
-
373
- if (!dependencyIds?.length) {
374
- return [];
375
- }
376
-
377
- if (!dependencyKey) {
378
- throw new DyFM_Error({
379
- ...this._getDefaultErrorSettings(
380
- 'getDataListByDependencyIds',
381
- new Error(`dependencyKey is missing! (${this.dataParams.dataName}) (NTS DB)`),
382
- ),
383
- });
384
- }
385
-
386
- if (!this.depKeys.includes(dependencyKey)) {
387
- throw new DyFM_Error({
388
- ...this._getDefaultErrorSettings(
389
- 'getDataListByDependencyIds',
390
- new Error(`dependencyKey is not valid! (${dependencyKey}) (NTS DB)`),
391
- ),
392
- });
393
- }
394
-
395
- const dataList: T[] = await this.dataModel
396
- .find({
397
- [dependencyKey]: { $in: dependencyIds },
398
- })
399
- .then((res): T[] => res as T[] ?? [])
400
- .catch((error): void => {
401
- throw new DyFM_Error({
402
- ...this._getDefaultErrorSettings('getDataListByDependencyIds', error),
403
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GLDS1`,
404
- additionalContent: { dependencyIds },
405
- message:
406
- `get "${this.dataParams.dataName}" by "${dependencyKey}" was unsuccessful (NTS DB)` +
407
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
408
- });
409
- });
410
-
411
- if (!findDeleted) {
412
- return dataList.filter(
413
- (data: T): boolean => !data._deleted
414
- ).map(
415
- (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyIds')
416
- );
417
- } else {
418
- return dataList.map(
419
- (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyIds')
420
- );
421
- }
422
- }
423
-
424
- // TODO: Missing issuer
425
- /**
426
- * returns all data from database,
427
- * !!!: throws error if not found (errorCode on not found: NTS-DBS-GA1)
428
- *
429
- * @returns dataList
430
- */
431
- async getAll(findDeleted?: boolean): Promise<T[]> {
432
- const dataList: T[] = await this.dataModel
433
- .find()
434
- .then((res): T[] => res as T[] ?? [])
435
- .catch((error): void => {
436
- throw new DyFM_Error({
437
- ...this._getDefaultErrorSettings('getAll', error),
438
-
439
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GA0`,
440
- message:
441
- `get all "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
442
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
443
- });
444
- });
445
-
446
- if (!findDeleted) {
447
- return dataList.filter(
448
- (data: T): boolean => !data._deleted
449
- ).map(
450
- (data: T): T => this.stringifyDataId(data, 'getAll')
451
- );
452
- } else {
453
- return dataList.map(
454
- (data: T): T => this.stringifyDataId(data, 'getAll')
455
- );
456
- }
457
- }
458
-
459
- async markDeletedById(id: string, issuer: string): Promise<void> {
460
- if (this.dataParams.forbidDelete) {
461
- await this.deleteThrowMethod(id, issuer);
462
- }
463
-
464
- await this.dataModel.findByIdAndUpdate(
465
- id,
466
- {
467
- _deleted: new Date(),
468
- _deletedBy: issuer,
469
- },
470
- /* issuer */
471
- ).catch(
472
- (error): void => {
473
- throw new DyFM_Error({
474
- ...this._getDefaultErrorSettings('markDeletedById', error, issuer),
475
-
476
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-MD0`,
477
- additionalContent: { id },
478
- message:
479
- `mark deleted "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
480
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
481
- issuer,
482
- });
483
- }
484
- );
485
- }
486
-
487
- async markDeletedByDependencyId(dependencyIdsFilter: { [key: string]: string }, issuer: string): Promise<void> {
488
- if (this.dataParams.forbidDelete) {
489
- await this.deleteThrowMethod(dependencyIdsFilter, issuer);
490
- }
491
-
492
- await this.dataModel.updateMany(
493
- dependencyIdsFilter,
494
- {
495
- _deleted: new Date(),
496
- _deletedBy: issuer,
497
- }
498
- ).catch((error): void => {
499
- throw new DyFM_Error({
500
- ...this._getDefaultErrorSettings('markDeletedByDependencyId', error, issuer),
501
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-MDD0`,
502
- additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
503
- message:
504
- `markDeleted "${this.dataParams.dataName}" by ` +
505
- `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
506
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
507
- issuer,
508
- });
509
- });
510
- }
511
-
512
- async restoreDeletedById(id: string, issuer: string): Promise<void> {
513
- await this.dataModel.findByIdAndUpdate(
514
- id,
515
- {
516
- _deleted: null,
517
- __lastModified: new Date(),
518
- __lastModifiedBy: issuer,
519
- },
520
- /* issuer */
521
- ).catch((error): void => {
522
- throw new DyFM_Error({
523
- ...this._getDefaultErrorSettings('restoreDeletedById', error, issuer),
524
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-RD0`,
525
- additionalContent: { id },
526
- message:
527
- `restoreDeleted "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
528
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
529
- issuer,
530
- });
531
- });
532
- }
533
-
534
- async restoreDeletedByDependencyId(
535
- dependencyIdsFilter: { [key: string]: string },
536
- issuer: string
537
- ): Promise<void> {
538
- await this.dataModel.updateMany(
539
- dependencyIdsFilter,
540
- {
541
- _deleted: null,
542
- __lastModified: new Date(),
543
- __lastModifiedBy: issuer,
544
- }
545
- ).catch((error): void => {
546
- throw new DyFM_Error({
547
- ...this._getDefaultErrorSettings('restoreDeletedByDependencyId', error, issuer),
548
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-RDD0`,
549
- additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
550
- message:
551
- `restoreDeleted "${this.dataParams.dataName}" by ` +
552
- `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
553
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
554
- issuer,
555
- });
556
- });
557
- }
558
-
559
- // TODO: Missing issuer
560
- async getDeletedDataList(): Promise<T[]> {
561
- const dataList: T[] = await this.dataModel
562
- .getAll()
563
- .then((res): T[] => res as T[] ?? [])
564
- .catch((error): void => {
565
- throw new DyFM_Error({
566
- ...this._getDefaultErrorSettings('getDeletedData', error),
567
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GDD0`,
568
- message:
569
- `get deleted "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
570
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
571
- });
572
- });
573
-
574
- return dataList.filter(
575
- (data: T): boolean => Boolean(data._deleted)
576
- ).map((data: T): T => this.stringifyDataId(data, 'getDeletedData'));
577
- }
578
-
579
- // TODO: Missing issuer
580
- /**
581
- * deleted data by id
582
- * @param id id
583
- */
584
- async trueDeleteDataById(id: string): Promise<void> {
585
- if (this.dataParams.forbidDelete) {
586
- await this.deleteThrowMethod(id/* , issuer */);
587
- }
588
-
589
- await this.dataModel
590
- .findByIdAndDelete(id)
591
- .catch((error): void => {
592
- throw new DyFM_Error({
593
- ...this._getDefaultErrorSettings('deleteDataById', error),
594
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-DD0`,
595
- additionalContent: { id },
596
- message:
597
- `delete "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
598
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
599
- });
600
- });
601
- }
602
- readonly deleteDataById = this.trueDeleteDataById;
603
-
604
- // TODO: Missing issuer
605
- /**
606
- * deleted data by id
607
- * @param dependencyId id
608
- */
609
- async trueDeleteDataByDependencyId(dependencyIdsFilter: { [key: string]: string }): Promise<void> {
610
- if (this.dataParams.forbidDelete) {
611
- await this.deleteThrowMethod(dependencyIdsFilter/* , issuer */);
612
- }
613
-
614
- if (!this.depKeys.length) {
615
- throw new DyFM_Error({
616
- ...this._getDefaultErrorSettings(
617
- 'deleteDataByDependencyId',
618
- new Error(
619
- `dependencyDataIdKey not setted up for this db-service (${this.dataParams.dataName}) (NTS DB)`
620
- )
621
- ),
622
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-DDD0`,
623
- });
624
- }
625
-
626
- await this.dataModel
627
- .deleteMany(dependencyIdsFilter)
628
- .catch((error): void => {
629
- throw new DyFM_Error({
630
- ...this._getDefaultErrorSettings('deleteDataByDependencyId', error),
631
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-DDD1`,
632
- additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
633
- message:
634
- `delete "${this.dataParams.dataName}" by ` +
635
- `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
636
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
637
- });
638
- });
639
- }
640
- readonly deleteDataByDependencyId = this.trueDeleteDataByDependencyId;
641
-
642
- // TODO: Missing issuer
643
- async trueDeleteAllData(): Promise<void> {
644
- if (this.dataParams.forbidDelete) {
645
- await this.deleteThrowMethod(null/* , issuer */);
646
- }
647
-
648
- await this.dataModel.deleteMany().catch((error): void => {
649
- throw new DyFM_Error({
650
- ...this._getDefaultErrorSettings('deleteAllData', error),
651
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-DAD0`,
652
- message:
653
- `delete all "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
654
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
655
- });
656
- });
657
- }
658
- readonly deleteAllData = this.trueDeleteAllData;
659
-
660
- // TODO: Missing issuer
661
- /**
662
- * returns search result for searchBy object params
663
- * can use lists or xRange values for searchBy obj properties
664
- *
665
- * @param filterBy filter
666
- * @param narrowByDependencyIds id
667
- * @returns dataList
668
- */
669
- async searchData(
670
- filterBy: DyFM_DBFilter<T>,
671
- narrowByDependencyIds?: string[],
672
- narrowByDependencyKey?: string,
673
- findDeleted?: boolean
674
- ): Promise<T[]> {
675
- const filter = {};
676
-
677
- if (0 < narrowByDependencyIds.length) {
678
- if (!this.depKeys.length) {
679
- throw new DyFM_Error({
680
- ...this._getDefaultErrorSettings(
681
- 'searchData',
682
- new Error(
683
- `dependencyDataIdKey not setted up for this db-service (${this.dataParams.dataName}) (NTS DB)`
684
- )
685
- ),
686
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-SD0`,
687
- });
688
- }
689
-
690
- if (!narrowByDependencyKey) {
691
- if (this.depKeys.length === 1) {
692
- narrowByDependencyKey = this.depKeys[0];
693
- } else {
694
- throw new DyFM_Error({
695
- ...this._getDefaultErrorSettings(
696
- 'searchData',
697
- new Error(`dependencyKey is missing! (${this.dataParams.dataName}) (NTS DB)`),
698
- ),
699
- });
700
- }
701
- }
702
-
703
- filter[narrowByDependencyKey] = { $in: narrowByDependencyIds };
704
- }
705
-
706
- Object.values(this.dataParams.properties).forEach(
707
- (modelParam: DyFM_DataProperty_Params<any, T>): void => {
708
- if (
709
- (filterBy[modelParam.key] !== null && filterBy[modelParam.key] !== undefined) ||
710
- filterBy[modelParam.key + 'Range']
711
- ) {
712
- if (modelParam.key.includes('Range') || modelParam.type.includes('[]')) {
713
- // inverz search filter (for Range and Array functions)
714
- if (modelParam.key.includes('Range')) {
715
- const searchParamKeyWithoutRange = modelParam.key.split('Range')[0];
716
-
717
- if (
718
- filterBy[searchParamKeyWithoutRange] !== null &&
719
- filterBy[searchParamKeyWithoutRange] !== undefined
720
- ) {
721
- filter[modelParam.key] = {
722
- from: { $lte: filterBy[searchParamKeyWithoutRange] },
723
- to: { $gte: filterBy[searchParamKeyWithoutRange] },
724
- };
725
- }
726
- } else {
727
- if (
728
- filterBy[modelParam.key] !== null &&
729
- filterBy[modelParam.key] !== undefined
730
- ) {
731
- filter[modelParam.key] = { $in: filterBy[modelParam.key] };
732
- }
733
- }
734
- } else {
735
- // basic search filter
736
- if (filterBy[modelParam.key + 'Range']) {
737
- if (
738
- filterBy[modelParam.key + 'Range'].from ||
739
- filterBy[modelParam.key + 'Range'].to
740
- ) {
741
- filter[modelParam.key] = {};
742
-
743
- if (filterBy[modelParam.key + 'Range'].from) {
744
- filter[modelParam.key].$gte = filterBy[modelParam.key + 'Range'].from;
745
- }
746
-
747
- if (filterBy[modelParam.key + 'Range'].to) {
748
- filter[modelParam.key].$lte = filterBy[modelParam.key + 'Range'].to;
749
- }
750
- }
751
- } else if (
752
- filterBy[modelParam.key] !== null &&
753
- filterBy[modelParam.key] !== undefined
754
- ) {
755
- if (filterBy[modelParam.key].lenght > 0) {
756
- filter[modelParam.key] = { $in: filterBy[modelParam.key] };
757
- }
758
- }
759
- }
760
- }
761
- }
762
- );
763
-
764
- let dataList: T[] = await this.dataModel
765
- .find(filter)
766
- .then((res): T[] => res as T[] ?? [])
767
- .catch((error): void => {
768
- throw new DyFM_Error({
769
- ...this._getDefaultErrorSettings('searchData', error),
770
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-SD1`,
771
- additionalContent: { filterBy, narrowByDependencyIds },
772
- message:
773
- `search "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
774
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
775
- });
776
- });
777
-
778
- if (!findDeleted && (filterBy as DyFM_DBFilterSimple<T>)._deleted === undefined) {
779
- dataList = dataList.filter((data: T): boolean => !data._deleted);
780
- }
781
-
782
- return dataList.map((data: T): T => this.stringifyDataId(data, 'searchData'));
783
- }
784
-
785
- // ----------------------------------------------------------------------------------
786
- // ----------------------------------------------------------------------------------
787
- // ----------------------------------------------------------------------------------
788
- // DIRECT Basic MONGOOSE FUNCTIONS (with error handlings)
789
-
790
- /**
791
- * Find the data first by any of its parameters,
792
- * !!!: throws error if not found (errorCode on not found: NTS-DBS-FO1)
793
- *
794
- * @param filterBy if you can, use unique parameters for find!
795
- *
796
- * @example
797
- * // by email:
798
- * { email: email }
799
- * //
800
- * @example
801
- * // or by id that is in list:
802
- * { userIds: { $in: this.userId } }
803
- * // or by userIds:
804
- * { userId: { $in: userIds } }
805
- * //
806
- * @example
807
- * // or by number or Date that is Greater Than AND Less Than:
808
- * { points: { $gt: 2, $lt: 14 } }
809
- * // further tools (syntax matches with $gt):
810
- * $eq: // Matches values that are EQual to a specified value.
811
- * $gte: // Matches values that are Greater Than OR Equal to a specified value.
812
- * $lte: // Matches values that are Less Than or Equal to a specified value.
813
- * $ne: // Matches all values that are Not Equal to a specified value.
814
- * $nin: // Matches None of the values specified IN an array.
815
- * //
816
- * @returns {T} data: T
817
- */
818
- async findOne(filterBy: DyFM_DBFilter<T>): Promise<T> {
819
- const data: T = await this.dataModel
820
- .findOne(filterBy)
821
- .then((res): T => res as T ?? null)
822
- .catch((error): void => {
823
- throw new DyFM_Error({
824
- ...this._getDefaultErrorSettings('findOne', error),
825
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-FO0`,
826
- additionalContent: { filterBy },
827
- message:
828
- `findOne "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
829
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
830
- });
831
- });
832
-
833
- return this.stringifyDataId(data, 'findOne');
834
- }
835
-
836
- /**
837
- * #MONGOOSE FUNCTION
838
- * Find the data first by any of its parameters,
839
- * !!!: throws error if not found (errorCode on not found: NTS-DBS-F1)
840
- *
841
- * @param filterBy if you can, use unique parameters for find!
842
- *
843
- * @example
844
- * // by email:
845
- * { email: email }
846
- * //
847
- * @example
848
- * // or by id that is in list:
849
- * { userIds: { $in: this.userId } }
850
- * // or by userIds:
851
- * { userId: { $in: userIds } }
852
- * //
853
- * @example
854
- * // or by number or Date that is Greater Than AND Less Than:
855
- * { points: { $gt: 2, $lt: 14 } }
856
- * // further tools (syntax matches with $gt):
857
- * $eq: // Matches values that are EQual to a specified value.
858
- * $gte: // Matches values that are Greater Than OR Equal to a specified value.
859
- * $lte: // Matches values that are Less Than or Equal to a specified value.
860
- * $ne: // Matches all values that are Not Equal to a specified value.
861
- * $nin: // Matches None of the values specified IN an array.
862
- * //
863
- * @param options BFR-008: opcionalis projection/limit/sort — DB-szinten szukit (a nagy mezok be sem toltodnek)
864
- * @returns {T[]} dataList: T[]
865
- */
866
- async find(filterBy: DyFM_DBFilter<T>, findDeleted?: boolean, options?: DyNTS_DBQueryOptions<T>): Promise<T[]> {
867
- // BFR-OVERSEER-008 — options megadasakor a soft-delete szures QUERY-szintre kerul: limit mellett a
868
- // memoriabeli post-filter hibas darabszamot adna, projekcio mellett (kihagyott `_deleted` mezovel)
869
- // hibasan atengedne a torolt dokumentumokat. A `_deleted` soft-delete-kor `new Date()`, egyebkent
870
- // HIANYZIK → a Mongo `_deleted: null` (missing VAGY null) a post-filter `!data._deleted` ekvivalense.
871
- const deletedGuardInQuery: boolean =
872
- !!options && !findDeleted && (filterBy as DyFM_DBFilterSimple<T>)._deleted === undefined;
873
- const effectiveFilter: DyFM_DBFilter<T> = deletedGuardInQuery
874
- ? { ...(filterBy as DyFM_DBFilterSimple<T>), _deleted: null } as unknown as DyFM_DBFilter<T>
875
- : filterBy;
876
-
877
- // A szukites (select/sort/limit) DB-szinten tortenik → a nagy mezok be sem toltodnek a heap-be.
878
- let query = this.dataModel.find(effectiveFilter);
879
- if (options?.projection) { query = query.select(options.projection); }
880
- if (options?.sort) { query = query.sort(options.sort); }
881
- if (options?.limit) { query = query.limit(options.limit); }
882
-
883
- let dataList: T[] = await query
884
- .then((res): T[] => res as T[] ?? [])
885
- .catch((error): void => {
886
- throw new DyFM_Error({
887
- ...this._getDefaultErrorSettings('find', error),
888
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-F0`,
889
- additionalContent: { filterBy },
890
- message:
891
- `find "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
892
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
893
- });
894
- });
895
-
896
- if (!findDeleted && !deletedGuardInQuery && (filterBy as DyFM_DBFilterSimple<T>)._deleted === undefined) {
897
- dataList = dataList.filter((data: T): boolean => !data._deleted);
898
- }
899
-
900
- return dataList.map((data: T): T => this.stringifyDataId(data, 'find'));
901
- }
902
-
903
- /**
904
- * #MONGOOSE FUNCTION
905
- * Find the data first by any of its parameters
906
- * WARNING: This function will not gives you back the total number of data in the database!
907
- *
908
- * @param filterBy if you can, use unique parameters for find!
909
- *
910
- * @example
911
- * // by email:
912
- * { email: email }
913
- * //
914
- * @example
915
- * // or by id that is in list:
916
- * { userIds: { $in: this.userId } }
917
- * // or by userIds:
918
- * { userId: { $in: userIds } }
919
- * //
920
- * @example
921
- * // or by number or Date that is Greater Than AND Less Than:
922
- * { points: { $gt: 2, $lt: 14 } }
923
- * // further tools (syntax matches with $gt):
924
- * $eq: // Matches values that are EQual to a specified value.
925
- * $gte: // Matches values that are Greater Than OR Equal to a specified value.
926
- * $lte: // Matches values that are Less Than or Equal to a specified value.
927
- * $ne: // Matches all values that are Not Equal to a specified value.
928
- * $nin: // Matches None of the values specified IN an array.
929
- * //
930
- * @param page page
931
- * @param pageSize pageSize
932
- * @param sort
933
- * @example
934
- * // by dateTime (this uses the basic sort function):
935
- * { dateTime: -1 }
936
- * //
937
- * @returns {T[]} dataList: T[]
938
- */
939
- async findWithPaging(
940
- filterBy: DyFM_DBFilter<T>,
941
- page: number,
942
- pageSize: number,
943
- sort?: DyFM_DBSort<T>
944
- ): Promise<T[]> {
945
- /* if (filterBy['_deleted'] === undefined) {
946
- filterBy['_deleted'] = null;
947
- } */
948
-
949
- const dataList: T[] = await this.dataModel
950
- .find(filterBy)
951
- .sort(sort)
952
- .skip(page * pageSize)
953
- .limit(pageSize)
954
- .then((res): T => res ?? [])
955
- .catch((error): void => {
956
- throw new DyFM_Error({
957
- ...this._getDefaultErrorSettings('findWithPaging', error),
958
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-WP0`,
959
- additionalContent: { filterBy, page, pageSize, sort },
960
- message:
961
- `findWithPaging "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
962
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
963
- });
964
- });
965
-
966
- /* if ((filterBy as DyFM_DBFilterSimple<T>)._deleted === undefined) {
967
- dataList = dataList.filter((data: T): boolean => !data._deleted);
968
- } */
969
-
970
- return dataList.map((data: T): T => this.stringifyDataId(data, 'find'));
971
- }
972
-
973
- /**
974
- * #MONGOOSE FUNCTION
975
- * Find data by _id and update
976
- *
977
- * @param id id
978
- * @param update update
979
- * @returns data
980
- */
981
- async findByIdAndUpdate(
982
- id: string,
983
- update: DyNTS_DBUpdate<T>,
984
- issuer: string,
985
- dontUpdateModified?: boolean
986
- ): Promise<T> {
987
- if (this.dataParams.forbidModify) {
988
- await this.modifyThrowMethod(update, issuer);
989
- }
990
-
991
- if (!dontUpdateModified) {
992
- update.__lastModified = new Date();
993
- update.__lastModifiedBy = issuer;
994
- }
995
-
996
- const data: T = await this.dataModel
997
- .findByIdAndUpdate(id, update)
998
- .then((res): T => res?.toObject() as T ?? null)
999
- .catch((error): void => {
1000
- throw new DyFM_Error({
1001
- ...this._getDefaultErrorSettings('findByIdAndUpdate', error, issuer),
1002
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-FIU0`,
1003
- additionalContent: { id, update },
1004
- message:
1005
- `findByIdAndUpdate "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
1006
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
1007
- issuer,
1008
- });
1009
- });
1010
-
1011
- return this.stringifyDataId(data, 'findByIdAndUpdate');
1012
- }
1013
-
1014
- /**
1015
- * #MONGOOSE FUNCTION
1016
- * Find the data first by any of its parameters
1017
- *
1018
- * @param filter This uses the basic Mongoose updateOne.
1019
- * If you can, use unique parameters for find!
1020
- * @example
1021
- * // by email:
1022
- * { email: email }
1023
- * //
1024
- * @example
1025
- * // or by id that is in list:
1026
- * { userIds: { $in: this.userId } }
1027
- * // or by userIds:
1028
- * { userId: { $in: userIds } }
1029
- * //
1030
- * @example
1031
- * // or by number or Date that is Greater Than AND Less Than:
1032
- * { points: { $gt: 2, $lt: 14 } }
1033
- * // further tools (syntax matches with $gt):
1034
- * $eq: // Matches values that are EQual to a specified value.
1035
- * $gte: // Matches values that are Greater Than OR Equal to a specified value.
1036
- * $lte: // Matches values that are Less Than or Equal to a specified value.
1037
- * $ne: // Matches all values that are Not Equal to a specified value.
1038
- * $nin: // Matches None of the values specified IN an array.
1039
- * //
1040
- *
1041
- * @param update this uses the basic Mongoose updateOne
1042
- * @example
1043
- * // increase a specific value (here by 15):
1044
- * { $inc: { popularity: 15 } }
1045
- * //
1046
- * @example
1047
- * // or add element to a list:
1048
- * { $push: { reactions: this.newReaction }
1049
- * // or add multiple elements to a list
1050
- * { $push: { schedule: {$each: [ monday, tuesday, wednesday ] } } }
1051
- * //
1052
- * @example
1053
- * // or all at once
1054
- * {
1055
- * $inc: { popularity: this.newVote.amount },
1056
- * emailVerified: true,
1057
- * $push: { reactions: this.newReaction }
1058
- * }
1059
- * // further tools (syntax matches with $inc):
1060
- * $currentDate: // Sets the value of a field to current date, either as a Date or a Timestamp.
1061
- * $min: // Only updates the field if the specified value is less than the existing field value.
1062
- * $max: // Only updates the field if the specified value is greater than the existing field value.
1063
- * $mul: // Multiplies the value of the field by the specified amount.
1064
- * $rename: // Renames a field.
1065
- * $unset: // Removes the specified field from a document. (set: "" to value)
1066
- * //
1067
- */
1068
- async updateOne(
1069
- filterBy: DyFM_DBFilter<T>,
1070
- update: DyNTS_DBUpdate<T>,
1071
- issuer: string,
1072
- dontUpdateModified?: boolean
1073
- ): Promise<void> {
1074
- if (this.dataParams.forbidModify) {
1075
- await this.modifyThrowMethod(update, issuer);
1076
- }
1077
-
1078
- if (!dontUpdateModified) {
1079
- update.__lastModified = new Date();
1080
- update.__lastModifiedBy = issuer;
1081
- }
1082
-
1083
- await this.dataModel
1084
- .updateOne(filterBy, update)
1085
- .catch((error): void => {
1086
- throw new DyFM_Error({
1087
- ...this._getDefaultErrorSettings('updateOne', error, issuer),
1088
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-UO0`,
1089
- additionalContent: { filterBy, update },
1090
- message:
1091
- `updateOne "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
1092
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
1093
- issuer,
1094
- });
1095
- });
1096
- }
1097
-
1098
- /**
1099
- * #MONGOOSE FUNCTION
1100
- * update one parameter by a specific
1101
- *
1102
- * @param filter This uses the basic Mongoose updateMany.
1103
- * @example
1104
- * // by email:
1105
- * { email: email }
1106
- * //
1107
- * @example
1108
- * // or by id that is in list:
1109
- * { userIds: { $in: this.userId } }
1110
- * // or by userIds:
1111
- * { userId: { $in: userIds } }
1112
- * //
1113
- * @example
1114
- * // or by number or Date that is Greater Than AND Less Than:
1115
- * { points: { $gt: 2, $lt: 14 } }
1116
- * // further tools (syntax matches with $gt):
1117
- * $eq: // Matches values that are EQual to a specified value.
1118
- * $gte: // Matches values that are Greater Than OR Equal to a specified value.
1119
- * $lte: // Matches values that are Less Than or Equal to a specified value.
1120
- * $ne: // Matches all values that are Not Equal to a specified value.
1121
- * $nin: // Matches None of the values specified IN an array.
1122
- * //
1123
- *
1124
- * @param update this uses the basic Mongoose updateOne
1125
- * @example
1126
- * // increase a specific value (here by 15):
1127
- * { $inc: { popularity: 15 } }
1128
- * //
1129
- * @example
1130
- * // or add element to a list:
1131
- * { $push: { reactions: this.newReaction }
1132
- * // or add multiple elements to a list
1133
- * { $push: { schedule: {$each: [ monday, tuesday, wednesday ] } } }
1134
- * //
1135
- * @example
1136
- * // or all at once
1137
- * {
1138
- * $inc: { popularity: this.newVote.amount },
1139
- * emailVerified: true,
1140
- * $push: { reactions: this.newReaction }
1141
- * }
1142
- * // further tools (syntax matches with $inc):
1143
- * $currentDate: // Sets the value of a field to current date, either as a Date or a Timestamp.
1144
- * $min: // Only updates the field if the specified value is less than the existing field value.
1145
- * $max: // Only updates the field if the specified value is greater than the existing field value.
1146
- * $mul: // Multiplies the value of the field by the specified amount.
1147
- * $rename: // Renames a field.
1148
- * $unset: // Removes the specified field from a document. (set: "" to value)
1149
- * //
1150
- */
1151
- async updateMany(
1152
- filterBy: DyFM_DBFilter<T>,
1153
- update: DyNTS_DBUpdate<T>,
1154
- issuer: string,
1155
- dontUpdateModified?: boolean
1156
- ): Promise<void> {
1157
- if (this.dataParams.forbidModify) {
1158
- await this.modifyThrowMethod(update, issuer);
1159
- }
1160
-
1161
- if (!dontUpdateModified) {
1162
- update.__lastModified = new Date();
1163
- update.__lastModifiedBy = issuer;
1164
- }
1165
-
1166
- await this.dataModel
1167
- .updateMany(filterBy, update)
1168
- .catch((error): void => {
1169
- throw new DyFM_Error({
1170
- ...this._getDefaultErrorSettings('updateMany', error, issuer),
1171
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-UM0`,
1172
- additionalContent: { filterBy, update },
1173
- message:
1174
- `updateMany "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
1175
- `\n error: ${DyFM_Error.getErrorMessage(error)}`,
1176
- issuer,
1177
- });
1178
- });
1179
- }
1180
-
1181
- /**
1182
- * {
1183
- "mappings": {
1184
- "dynamic": true,
1185
- "fields": {
1186
- "embedding": {
1187
- "type": "knnVector",
1188
- "dimensions": 768
1189
- }
1190
- }
1191
- }
1192
- }
1193
- */
1194
- /**
1195
- *
1196
- * @param set db.collection.aggregate([
1197
- {
1198
- $vectorSearch: {
1199
- index: "index_neve",
1200
- queryVector: [a keresett embedding],
1201
- path: "title.embedding",
1202
- numCandidates: 100,
1203
- limit: 5
1204
- }
1205
- },
1206
- {
1207
- $vectorSearch: {
1208
- index: "index_neve",
1209
- queryVector: [a keresett embedding],
1210
- path: "description.embedding",
1211
- numCandidates: 100,
1212
- limit: 5
1213
- }
1214
- }
1215
- ]);
1216
- * @returns
1217
- */
1218
- async aggregate(set: any) {
1219
- return this.dataModel.aggregate(set);
1220
- }
1221
-
1222
- // ----------------------------------------------------------------------------------
1223
- // ----------------------------------------------------------------------------------
1224
- // ----------------------------------------------------------------------------------
1225
- // PRIVATE FUNCTIONS
1226
-
1227
- private stringifyDataId(data: T, fnName: string): T {
1228
- if (data?._id && (typeof data._id !== 'string' || typeof data._id === 'object')) {
1229
- data._id = `${data._id}`;
1230
-
1231
- if (typeof data._id !== 'string' || typeof data._id === 'object') {
1232
- data = JSON.parse(JSON.stringify(data));
1233
-
1234
- if (typeof data._id !== 'string' || typeof data._id === 'object') {
1235
- DyFM_Log.error(
1236
- `data._id stringifying failed! Please notfiy the DynamoNTS developers! (${fnName})`,
1237
- new Error()
1238
- );
1239
- }
1240
- }
1241
- }
1242
-
1243
- return data;
1244
- }
1245
-
1246
- private _getDefaultErrorSettings(
1247
- fnName: string,
1248
- error: DyFM_AnyError,
1249
- issuer?: string
1250
- ): DyFM_Error_Settings {
1251
- return {
1252
- status: (error as DyFM_Error)?.___status ?? 500,
1253
- message: (error as Error)?.message ??
1254
- (error as DyFM_Error)?._message ??
1255
- `${fnName} was UNSUCCESSFUL (NTS-DB)`,
1256
- addECToUserMsg: !(error as DyFM_Error)?.__userMessage,
1257
- userMessage: (error as DyFM_Error)?.__userMessage ?? this.defaultErrorUserMsg,
1258
- issuer: issuer,
1259
- issuerService: this.serviceName,
1260
- error: error,
1261
- };
1262
- }
1263
-
1264
- // ----------------------------------------------------------------------------------
1265
- // PRIVATE BUILD FUNCTIONS
1266
-
1267
- /**
1268
- * builds and returns mongoose schema
1269
- * @returns schema
1270
- */
1271
- private getSchema(): mongoose.Schema {
1272
- this.dataParams.properties = this.addMetadataToProperties(this.dataParams.properties);
1273
-
1274
- if (this.dataParams.dataName.includes(DyNTS_archiveSuffix)) {
1275
- this.dataParams.properties = this.addArchiveMetadataToProperties(this.dataParams.properties);
1276
- }
1277
-
1278
- const schemaSettings: any = this.buildMongooseSchemaSettingsObjByModelParams(
1279
- this.dataParams.properties
1280
- );
1281
-
1282
- /* schema = this.addMetadataToSchema(schema); */
1283
-
1284
- /* if (this.dataParams.dataName.includes(DyNTS_archiveSuffix)) {
1285
- schema = this.addArchiveMetadataToSchema(schema);
1286
- } */
1287
-
1288
- if (schemaSettings['_id']) {
1289
- delete schemaSettings['_id'];
1290
- }
1291
-
1292
- return new Schema(schemaSettings);
1293
- }
1294
-
1295
- /**
1296
- * builds mongoose schema building settings object by dynamoDataModelParamsList
1297
- * @param properties DynamoNTSDataPropertyParams
1298
- * @returns mongoose schema object
1299
- */
1300
- private buildMongooseSchemaSettingsObjByModelParams(properties: DyFM_DataProperties<T>): any {
1301
- const schemaSettingsObj = {};
1302
-
1303
- /* if (!properties) {
1304
- properties = this.dataParams.properties;
1305
- } */
1306
-
1307
- Object.values(properties).forEach((property: DyFM_DataProperty_Params<any, T>): void => {
1308
- if (!property) {
1309
- DyFM_Log.warn(`property is undefined on "${this.dataParams.dataName}" (NTS DB)`);
1310
-
1311
- return;
1312
- }
1313
-
1314
- if (!property.key) {
1315
- const missingKeys = Object.keys(properties).filter((key: string) => !properties[key].key);
1316
-
1317
- throw new DyFM_Error({
1318
- ...this._getDefaultErrorSettings(
1319
- 'buildMongooseSchemaByModelParams',
1320
- new Error(
1321
- `property.key is undefined on "${this.dataParams.dataName}" (NTS DB) ` +
1322
- `(keys: ${Object.keys(properties).join(', ')}) ` +
1323
- `(missing keys: ${missingKeys.join(', ')})`
1324
- )
1325
- ),
1326
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-BMSBP0`,
1327
- additionalContent: {
1328
- property: property,
1329
- dataParams: this.dataParams,
1330
- missingKeys: missingKeys,
1331
- },
1332
- });
1333
- }
1334
-
1335
- if (property.forbidden) {
1336
- return;
1337
- }
1338
-
1339
- const beType = this.getBEType(property.type as DyFM_BasicProperty_Type);
1340
-
1341
- /* TODO if (beType === Array && property.archiveable && !property.archiveListAfter) {
1342
- property.archiveListAfter = DyNTS_global_settings.archiveListAfter;
1343
- } */
1344
-
1345
- if (
1346
- beType !== Object ||
1347
- !property?.subObjectParams ||
1348
- (property?.subObjectParams &&
1349
- Object.keys(property.subObjectParams).length == 0)
1350
- ) {
1351
- schemaSettingsObj[property.key] = {
1352
- type: beType,
1353
- };
1354
-
1355
- if (property.index) {
1356
- schemaSettingsObj[property.key].index = true;
1357
- }
1358
-
1359
- if (property.unique) {
1360
- schemaSettingsObj[property.key].unique = true;
1361
- }
1362
-
1363
- if (property.required) {
1364
- schemaSettingsObj[property.key].required = true;
1365
- }
1366
-
1367
- if (property.minlength) {
1368
- schemaSettingsObj[property.key].minlength = property.minlength;
1369
- }
1370
-
1371
- if (property.maxlength) {
1372
- schemaSettingsObj[property.key].maxlength = property.maxlength;
1373
- }
1374
- } else {
1375
- schemaSettingsObj[property.key] = this.buildMongooseSchemaSettingsObjByModelParams(
1376
- property.subObjectParams
1377
- );
1378
- }
1379
- });
1380
-
1381
- return schemaSettingsObj;
1382
- }
1383
-
1384
- private getBEType(
1385
- type: DyFM_BasicProperty_Type
1386
- ): string | number | boolean | object | Function | Array<any> | Date {
1387
- switch (type) {
1388
- case DyFM_BasicProperty_Type.string:
1389
- return String;
1390
-
1391
- case DyFM_BasicProperty_Type.number:
1392
- return Number;
1393
-
1394
- case DyFM_BasicProperty_Type.boolean:
1395
- return Boolean;
1396
-
1397
- case DyFM_BasicProperty_Type.date:
1398
- return Date;
1399
-
1400
- case DyFM_BasicProperty_Type.object:
1401
- return Object;
1402
-
1403
- case DyFM_BasicProperty_Type.array:
1404
- return Array;
1405
-
1406
- case DyFM_BasicProperty_Type.function:
1407
- return Function;
1408
-
1409
- default:
1410
- DyFM_Log.H_info('wtf', DyFM_Object.cleanObject(this.dataParams));
1411
-
1412
- throw new DyFM_Error({
1413
- error: new Error(
1414
- `Invalid property type: "${type}" (${this.dataParams.dataName})` +
1415
- (this.dataParams.constructed?.() ? '' : ('\nThe dataParams is not constructed properly! \n' +
1416
- 'Use the DyFM_DataModel_Params.constructor to construct it properly!'))
1417
- ),
1418
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GTP0`,
1419
- additionalContent: { type: type, dataParams: this.dataParams },
1420
- __localStack: this.dataParams.stackLocation,
1421
- });
1422
- }
1423
- /* switch (type.toLocaleLowerCase()) {
1424
- case DyFM_BasicProperty_Type.string:
1425
- case 'string':
1426
- return String;
1427
-
1428
- case DyFM_BasicProperty_Type.number:
1429
- case 'number':
1430
- return Number;
1431
-
1432
- case DyFM_BasicProperty_Type.boolean:
1433
- case 'boolean':
1434
- return Boolean;
1435
-
1436
- case DyFM_BasicProperty_Type.date:
1437
- case 'date':
1438
- return Date;
1439
-
1440
- case DyFM_BasicProperty_Type.object:
1441
- case 'object':
1442
- return Object;
1443
-
1444
- case DyFM_BasicProperty_Type.array:
1445
- case 'array':
1446
- return Array;
1447
-
1448
- default:
1449
- if (type.includes('[]') || type.includes('array')) {
1450
- return Array;
1451
- } else if (type.includes('=>') || type.includes('function')) {
1452
- return Function;
1453
- } else {
1454
- return Object;
1455
- }
1456
- } */
1457
- }
1458
-
1459
- /**
1460
- * adds dynamo metadata settings to any mongoose schema building settings object
1461
- * @param schema schema to update
1462
- * @returns updated schema
1463
- */
1464
- /* private addMetadataToSchema(schema: any): any {
1465
- schema.__created = { type: Date };
1466
- schema.__createdBy = { type: String };
1467
- schema.__lastModified = { type: Date };
1468
- schema.__lastModifiedBy = { type: String };
1469
-
1470
- schema._deleted = { type: Date };
1471
- schema._deletedBy = { type: String };
1472
-
1473
- return schema;
1474
- } */
1475
-
1476
- /**
1477
- * adds dynamo metadata settings to any mongoose schema building settings object
1478
- * @param properties properties to update
1479
- * @returns updated properties
1480
- */
1481
- private addMetadataToProperties(properties: DyFM_DataProperties<T>): DyFM_DataProperties<T> {
1482
- // TOD: ezek a kikommentelt "required: true"-k kellenek, csak félő, hogy gondokat okoznak a
1483
- // jelenlegi rendszerekben, ezért akkor kell majd visszarakni, ha lesz tesztelői ÉS fejlesztői kapacitás rá
1484
- if (!properties.__created) {
1485
- properties.__created = {
1486
- key: '__created', type: DyFM_BasicProperty_Type.date/* , required: true */,
1487
- };
1488
- }
1489
-
1490
- if (!properties.__createdBy) {
1491
- properties.__createdBy = {
1492
- key: '__createdBy', type: DyFM_BasicProperty_Type.string/* , required: true */,
1493
- };
1494
- }
1495
-
1496
- if (!properties.__lastModified) {
1497
- properties.__lastModified = {
1498
- key: '__lastModified', type: DyFM_BasicProperty_Type.date/* , required: true */,
1499
- };
1500
- }
1501
-
1502
- if (!properties.__lastModifiedBy) {
1503
- properties.__lastModifiedBy = {
1504
- key: '__lastModifiedBy', type: DyFM_BasicProperty_Type.string/* , required: true */,
1505
- };
1506
- }
1507
-
1508
- if (!properties._deleted) {
1509
- properties._deleted = {
1510
- key: '_deleted', type: DyFM_BasicProperty_Type.date,
1511
- };
1512
- }
1513
-
1514
- if (!properties._deletedBy) {
1515
- properties._deletedBy = {
1516
- key: '_deletedBy', type: DyFM_BasicProperty_Type.string,
1517
- };
1518
- }
1519
-
1520
- if (!properties._archived) {
1521
- properties._archived = {
1522
- key: '_archived', type: DyFM_BasicProperty_Type.date,
1523
- };
1524
- }
1525
-
1526
- return properties;
1527
- }
1528
-
1529
- /* private addArchiveMetadataToSchema(schema: any): any {
1530
- schema._originalId = { type: String, required: true, index: true, unique: true };
1531
- schema._archived = { type: Date, required: true };
1532
-
1533
- return schema;
1534
- } */
1535
-
1536
- private addArchiveMetadataToProperties(
1537
- properties: DyFM_DataProperties<T>
1538
- ): DyFM_DataProperties<T> {
1539
- if (!properties._originalId) {
1540
- properties._originalId = {
1541
- key: '_originalId', type: DyFM_BasicProperty_Type.string,
1542
- required: true, index: true, unique: true,
1543
- };
1544
- }
1545
-
1546
- if (!properties._archived) {
1547
- properties._archived = {
1548
- key: '_archived', type: DyFM_BasicProperty_Type.date,
1549
- required: true,
1550
- };
1551
- } else if (properties._archived.required === undefined) {
1552
- properties._archived.required = true;
1553
- }
1554
-
1555
- return properties;
1556
- }
1557
-
1558
- /**
1559
- * sets depDataKey
1560
- */
1561
- private lookForDependencyDataSettings(): void {
1562
- const dependencyParams: DyFM_DataProperty_Params<any, T>[] =
1563
- Object.values(this.dataParams.properties).filter(
1564
- (modelParams: DyFM_DataProperty_Params<any, T>): boolean =>
1565
- Boolean(modelParams.dependencyDataName)
1566
- );
1567
-
1568
- if (dependencyParams) {
1569
- this.depKeys.push(...dependencyParams.map(
1570
- (dependencyParam: DyFM_DataProperty_Params<any, T>): string => dependencyParam.key
1571
- ));
1572
- }
1573
- }
1574
-
1575
- private async deleteThrowMethod(data: any, issuer?: string): Promise<void> {
1576
- throw new DyFM_Error({
1577
- error: new Error(`Forbidden to delete any data! (${this.dataParams.dataName})`),
1578
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-CDAD`,
1579
- additionalContent: { dataParams: this.dataParams, data: data },
1580
- issuer: issuer,
1581
- });
1582
- };
1583
-
1584
- private async modifyThrowMethod(data: any, issuer?: string): Promise<void> {
1585
- throw new DyFM_Error({
1586
- error: new Error(`Forbidden to modify any data! (${this.dataParams.dataName})`),
1587
- errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-CDAD`,
1588
- additionalContent: { dataParams: this.dataParams, data: data },
1589
- issuer: issuer,
1590
- });
1591
- }
1592
- }
1
+
2
+ import * as mongoose from 'mongoose';
3
+ import { Schema } from 'mongoose';
4
+
5
+ import {
6
+ DyFM_AnyError,
7
+ DyFM_BasicProperty_Type,
8
+ DyFM_DataModel_Params,
9
+ DyFM_DataProperties,
10
+ DyFM_DataProperty_Params,
11
+ DyFM_DBFilter, DyFM_DBFilterSimple, DyFM_DBSort,
12
+ DyFM_Error,
13
+ DyFM_Error_Settings, DyFM_ErrorLevel,
14
+ DyFM_Log,
15
+ DyFM_Metadata,
16
+ DyFM_Object
17
+ } from '@futdevpro/fsm-dynamo';
18
+ import { DyNTS_archiveSuffix } from '../../_collections/archive.util';
19
+ import { DyNTS_DBUpdate } from '../../_models/types/db-update.type';
20
+ import { DyNTS_DBQueryOptions } from '../../_models/interfaces/db-query-options.interface';
21
+ import { DyNTS_global_settings } from '../../_collections/global-settings.const';
22
+
23
+ /**
24
+ * DB Service for MongoDB
25
+ */
26
+ export class DyNTS_DBService<T extends DyFM_Metadata> {
27
+
28
+ serviceName: string;
29
+
30
+ dataModel/* : mongoose.Model<T> */; // = mongoose.model(this.dataParams.dataName, this.getSchema());
31
+
32
+ /* private depDataName: string; */
33
+ private readonly depKeys: string[] = [];
34
+
35
+ defaultErrorUserMsg =
36
+ `We encountered an unhandled DB Error, ` +
37
+ `\nplease contact the responsible development team.`;
38
+
39
+ /**
40
+ * @param dataName name the model
41
+ * @param typeSample sample data for scheme creation (dont include DyFM_Metadata!)
42
+ * @param schemaSettings additional settings for specific parameters as unique, required, minlength or maxlength
43
+ * schemaSettings also MUST contain specific types that differs from the listed above (Array, Date)
44
+ */
45
+ constructor(
46
+ public dataParams: DyFM_DataModel_Params<T>
47
+ ){
48
+ try {
49
+ this.serviceName = this.constructor?.name;
50
+
51
+ if (!this.dataParams.dataName || typeof this.dataParams.dataName !== 'string') {
52
+ throw new Error(
53
+ `dbName not setted up for this db-service (${this.dataParams.dataName}) (NTS DB)`
54
+ );
55
+ }
56
+
57
+ if (!this.dataParams.constructed?.()) {
58
+ throw new DyFM_Error({
59
+ error: new Error(
60
+ `DataModelParams is not constructed properly! (${this.dataParams.dataName}) ` +
61
+ `Use the DyFM_DataModel_Params.constructor to construct it properly! (NTS DB)`
62
+ ),
63
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-C01`,
64
+ additionalContent: { dataParams: this.dataParams },
65
+ __localStack: this.dataParams.stackLocation,
66
+ });
67
+ }
68
+
69
+ try {
70
+ this.dataModel = mongoose.model(this.dataParams.dataName, this.getSchema());
71
+ } catch (error) {
72
+ if (mongoose.models[this.dataParams.dataName]) {
73
+ this.dataModel = mongoose.models[this.dataParams.dataName];
74
+ } else {
75
+ throw error;
76
+ }
77
+ }
78
+
79
+ this.lookForDependencyDataSettings();
80
+ } catch (error) {
81
+ throw new DyFM_Error({
82
+ message:
83
+ `DyNTS_DBService construction failed! "${dataParams.dataName}" - "${this.serviceName}"`,
84
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-C00`,
85
+ level: DyFM_ErrorLevel.critical,
86
+ additionalContent: { dataParams: this.dataParams },
87
+ error,
88
+ });
89
+ }
90
+ }
91
+
92
+ /**
93
+ * save new data
94
+ * @param data data
95
+ * @returns data
96
+ */
97
+ async createData(data: T, issuer: string): Promise<T> {
98
+ data.__created = new Date();
99
+ data.__lastModified = new Date();
100
+ data.__createdBy = issuer;
101
+ data.__lastModifiedBy = issuer;
102
+
103
+ const dataModel = new this.dataModel(data);
104
+ const newData: T = await dataModel.save().then((res): T => {
105
+ if (res) {
106
+ return res?.toObject() as T;
107
+
108
+ } else {
109
+ throw new DyFM_Error({
110
+ ...this._getDefaultErrorSettings(
111
+ 'createData',
112
+ new Error(
113
+ `createData failed, save "${this.dataParams.dataName}" result not found! (NTS DB)`
114
+ ),
115
+ issuer
116
+ ),
117
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-CD1`,
118
+ additionalContent: { data },
119
+ issuer,
120
+ });
121
+ }
122
+ }).catch((error): void => {
123
+ if (error?.flag?.includes('DYNAMO')) {
124
+ throw error;
125
+
126
+ } else {
127
+ throw new DyFM_Error({
128
+ ...this._getDefaultErrorSettings('createData', error, issuer),
129
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-CD0`,
130
+ additionalContent: {
131
+ data: data,
132
+ dataModel: this.dataModel,
133
+ },
134
+ message:
135
+ `createData failed, Create new "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
136
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
137
+ issuer,
138
+ });
139
+ }
140
+ });
141
+
142
+ return this.stringifyDataId(newData, 'createData');
143
+ }
144
+
145
+ /**
146
+ * Find data by _id and update
147
+ * @param data data
148
+ * @returns data
149
+ */
150
+ async modifyData(data: T, issuer: string, dontUpdateModified?: boolean): Promise<T> {
151
+ if (this.dataParams.forbidModify) {
152
+ await this.modifyThrowMethod(data, issuer);
153
+ }
154
+
155
+ if (!dontUpdateModified) {
156
+ data.__lastModified = new Date();
157
+ data.__lastModifiedBy = issuer;
158
+ }
159
+
160
+ /**
161
+ * EZ A SZAR TELJESEN SZAR, nem friss, nem a db-be mentett adatokat ad vissza,
162
+ * átír random value-kat össze vissza, WTF
163
+ * */
164
+ /* let newData: T = */
165
+ await this.dataModel.findByIdAndUpdate(data._id, data)/* .then((res) => {
166
+ if (res) {
167
+ //return res?.toObject() as T;
168
+ } else {
169
+ throw new DyFM_Error({
170
+ ...this._getDefaultErrorSettings(
171
+ 'modifyData',
172
+ new Error(`modifyData failed, modify "${this.dataParams.dataName}" result not found! (NTS DB)`),
173
+ issuer,
174
+ ),
175
+
176
+ status: 204,
177
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-FU1`,
178
+ additionalContent: { data },
179
+ issuer,
180
+ });
181
+ }
182
+ }) */.catch((error): void => {
183
+ throw new DyFM_Error({
184
+ ...this._getDefaultErrorSettings('modifyData', error, issuer),
185
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-FU0`,
186
+ additionalContent: { data },
187
+ message:
188
+ `modifyData "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
189
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
190
+ issuer,
191
+ });
192
+ });
193
+
194
+ return this.stringifyDataId(data, 'modifyData');
195
+ }
196
+
197
+ // TODO: Missing issuer
198
+ /**
199
+ * returns data by _id,
200
+ * @param id id
201
+ * @returns data
202
+ */
203
+ async getDataById(id: string): Promise<T> {
204
+ if (!id) {
205
+ throw new DyFM_Error({
206
+ ...this._getDefaultErrorSettings('getDataById', new Error(`No ID provided! (NTS DB)`)),
207
+
208
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GI1`,
209
+ message: `get "${this.dataParams.dataName}" by ID was unsuccessful (NTS DB)`,
210
+ });
211
+ }
212
+
213
+ const data: T = await this.dataModel
214
+ .findById(id)
215
+ .then((res): T => res?.toObject() as T ?? null)
216
+ .catch((error): void => {
217
+ throw new DyFM_Error({
218
+ ...this._getDefaultErrorSettings('getDataById', error),
219
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GI0`,
220
+ additionalContent: { id },
221
+ message:
222
+ `get "${this.dataParams.dataName}" by ID was unsuccessful (NTS DB)` +
223
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
224
+ });
225
+ });
226
+
227
+ return this.stringifyDataId(data, 'getDataById');
228
+ }
229
+
230
+ // TODO: Missing issuer
231
+ /**
232
+ * get data by dependency data id,
233
+ * !!!: throws error if not found (errorCode on not found: NTS-DBS-GD2)
234
+ *
235
+ * @param dependencyIdsFilter id
236
+ * @returns data
237
+ */
238
+ async getDataByDependencyId(dependencyIdsFilter: { [key: string]: string }): Promise<T> {
239
+ if (!this.depKeys.length) {
240
+ throw new DyFM_Error({
241
+ ...this._getDefaultErrorSettings(
242
+ 'getDataByDependencyId',
243
+ new Error(
244
+ `dependencyDataIdKey not setted up for this db-service (${this.dataParams.dataName}) (NTS DB)`
245
+ )
246
+ ),
247
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GD0`,
248
+ });
249
+ }
250
+
251
+ const data: T = await this.dataModel
252
+ .findOne(dependencyIdsFilter)
253
+ .then((res): T => res?.toObject() as T ?? null)
254
+ .catch((error): void => {
255
+ throw new DyFM_Error({
256
+ ...this._getDefaultErrorSettings('getDataByDependencyId', error),
257
+
258
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GD1`,
259
+ additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
260
+ message:
261
+ `get "${this.dataParams.dataName}" by ` +
262
+ `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
263
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
264
+ });
265
+ });
266
+
267
+ return this.stringifyDataId(data, 'getDataByDependencyId');
268
+ }
269
+
270
+ // TODO: Missing issuer
271
+ async getDataListByIds(ids: string[], findDeleted?: boolean): Promise<T[]> {
272
+ const dataList: T[] = await this.dataModel
273
+ .find({ _id: { $in: ids } })
274
+ .then((res): T[] => res as T[] ?? [])
275
+ .catch((error): void => {
276
+ throw new DyFM_Error({
277
+ ...this._getDefaultErrorSettings('getDataListByIds', error),
278
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GDL0`,
279
+ additionalContent: { ids },
280
+ message:
281
+ `get "${this.dataParams.dataName}" by IDs was unsuccessful (NTS DB)` +
282
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
283
+ });
284
+ });
285
+
286
+ if (!findDeleted) {
287
+ return dataList.filter(
288
+ (data: T): boolean => !data._deleted
289
+ ).map(
290
+ (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyId')
291
+ );
292
+ } else {
293
+ return dataList.map(
294
+ (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyId')
295
+ );
296
+ }
297
+ }
298
+
299
+ // TODO: Missing issuer
300
+ /**
301
+ * get data by dependency data id,
302
+ * !!!: throws error if not found (errorCode on not found: NTS-DBS-GLD2)
303
+ *
304
+ * @param dependencyIdsFilter id
305
+ * @returns dataList
306
+ */
307
+ async getDataListByDependencyId(dependencyIdsFilter: { [key: string]: string }, findDeleted?: boolean): Promise<T[]> {
308
+ if (!this.depKeys.length) {
309
+ throw new DyFM_Error({
310
+ ...this._getDefaultErrorSettings(
311
+ 'getDataListByDependencyId',
312
+ new Error(
313
+ `isDependencyHook not setted up for this dataModel (${this.dataParams.dataName}) (NTS DB)`
314
+ )
315
+ ),
316
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GLD0`,
317
+ additionalContent: {
318
+ dataModel: this.dataModel,
319
+ },
320
+ });
321
+ }
322
+
323
+ const dataList: T[] = await this.dataModel
324
+ .find(dependencyIdsFilter)
325
+ .then((res): T[] => res as T[] ?? [])
326
+ .catch((error): void => {
327
+ throw new DyFM_Error({
328
+ ...this._getDefaultErrorSettings('getDataListByDependencyId', error),
329
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GLD1`,
330
+ additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
331
+ message:
332
+ `get "${this.dataParams.dataName}" by ` +
333
+ `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
334
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
335
+ });
336
+ });
337
+
338
+ if (!findDeleted) {
339
+ return dataList.filter(
340
+ (data: T): boolean => !data._deleted
341
+ ).map(
342
+ (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyId')
343
+ );
344
+ } else {
345
+ return dataList.map(
346
+ (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyId')
347
+ );
348
+ }
349
+ }
350
+
351
+ // TODO: Missing issuer
352
+ /**
353
+ * get multiple data objects by a list of DependencyIDs,
354
+ * !!!: throws error if not found (errorCode on not found: NTS-DBS-GLDS2)
355
+ *
356
+ * @param ids ids
357
+ * @returns dataList
358
+ */
359
+ async getDataListByDependencyIds(dependencyKey: string, dependencyIds: string[], findDeleted?: boolean): Promise<T[]> {
360
+ if (!this.depKeys.length) {
361
+ throw new DyFM_Error({
362
+ ...this._getDefaultErrorSettings(
363
+ 'getDataListByDependencyIds',
364
+ new Error(
365
+ `getDataListByDependencyIds not setted up for this db-service ` +
366
+ `(${this.dataParams.dataName}) (NTS DB)`
367
+ )
368
+ ),
369
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GLDS0`,
370
+ });
371
+ }
372
+
373
+ if (!dependencyIds?.length) {
374
+ return [];
375
+ }
376
+
377
+ if (!dependencyKey) {
378
+ throw new DyFM_Error({
379
+ ...this._getDefaultErrorSettings(
380
+ 'getDataListByDependencyIds',
381
+ new Error(`dependencyKey is missing! (${this.dataParams.dataName}) (NTS DB)`),
382
+ ),
383
+ });
384
+ }
385
+
386
+ if (!this.depKeys.includes(dependencyKey)) {
387
+ throw new DyFM_Error({
388
+ ...this._getDefaultErrorSettings(
389
+ 'getDataListByDependencyIds',
390
+ new Error(`dependencyKey is not valid! (${dependencyKey}) (NTS DB)`),
391
+ ),
392
+ });
393
+ }
394
+
395
+ const dataList: T[] = await this.dataModel
396
+ .find({
397
+ [dependencyKey]: { $in: dependencyIds },
398
+ })
399
+ .then((res): T[] => res as T[] ?? [])
400
+ .catch((error): void => {
401
+ throw new DyFM_Error({
402
+ ...this._getDefaultErrorSettings('getDataListByDependencyIds', error),
403
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GLDS1`,
404
+ additionalContent: { dependencyIds },
405
+ message:
406
+ `get "${this.dataParams.dataName}" by "${dependencyKey}" was unsuccessful (NTS DB)` +
407
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
408
+ });
409
+ });
410
+
411
+ if (!findDeleted) {
412
+ return dataList.filter(
413
+ (data: T): boolean => !data._deleted
414
+ ).map(
415
+ (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyIds')
416
+ );
417
+ } else {
418
+ return dataList.map(
419
+ (data: T): T => this.stringifyDataId(data, 'getDataListByDependencyIds')
420
+ );
421
+ }
422
+ }
423
+
424
+ // TODO: Missing issuer
425
+ /**
426
+ * returns all data from database,
427
+ * !!!: throws error if not found (errorCode on not found: NTS-DBS-GA1)
428
+ *
429
+ * @returns dataList
430
+ */
431
+ async getAll(findDeleted?: boolean): Promise<T[]> {
432
+ const dataList: T[] = await this.dataModel
433
+ .find()
434
+ .then((res): T[] => res as T[] ?? [])
435
+ .catch((error): void => {
436
+ throw new DyFM_Error({
437
+ ...this._getDefaultErrorSettings('getAll', error),
438
+
439
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GA0`,
440
+ message:
441
+ `get all "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
442
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
443
+ });
444
+ });
445
+
446
+ if (!findDeleted) {
447
+ return dataList.filter(
448
+ (data: T): boolean => !data._deleted
449
+ ).map(
450
+ (data: T): T => this.stringifyDataId(data, 'getAll')
451
+ );
452
+ } else {
453
+ return dataList.map(
454
+ (data: T): T => this.stringifyDataId(data, 'getAll')
455
+ );
456
+ }
457
+ }
458
+
459
+ async markDeletedById(id: string, issuer: string): Promise<void> {
460
+ if (this.dataParams.forbidDelete) {
461
+ await this.deleteThrowMethod(id, issuer);
462
+ }
463
+
464
+ await this.dataModel.findByIdAndUpdate(
465
+ id,
466
+ {
467
+ _deleted: new Date(),
468
+ _deletedBy: issuer,
469
+ },
470
+ /* issuer */
471
+ ).catch(
472
+ (error): void => {
473
+ throw new DyFM_Error({
474
+ ...this._getDefaultErrorSettings('markDeletedById', error, issuer),
475
+
476
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-MD0`,
477
+ additionalContent: { id },
478
+ message:
479
+ `mark deleted "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
480
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
481
+ issuer,
482
+ });
483
+ }
484
+ );
485
+ }
486
+
487
+ async markDeletedByDependencyId(dependencyIdsFilter: { [key: string]: string }, issuer: string): Promise<void> {
488
+ if (this.dataParams.forbidDelete) {
489
+ await this.deleteThrowMethod(dependencyIdsFilter, issuer);
490
+ }
491
+
492
+ await this.dataModel.updateMany(
493
+ dependencyIdsFilter,
494
+ {
495
+ _deleted: new Date(),
496
+ _deletedBy: issuer,
497
+ }
498
+ ).catch((error): void => {
499
+ throw new DyFM_Error({
500
+ ...this._getDefaultErrorSettings('markDeletedByDependencyId', error, issuer),
501
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-MDD0`,
502
+ additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
503
+ message:
504
+ `markDeleted "${this.dataParams.dataName}" by ` +
505
+ `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
506
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
507
+ issuer,
508
+ });
509
+ });
510
+ }
511
+
512
+ async restoreDeletedById(id: string, issuer: string): Promise<void> {
513
+ await this.dataModel.findByIdAndUpdate(
514
+ id,
515
+ {
516
+ _deleted: null,
517
+ __lastModified: new Date(),
518
+ __lastModifiedBy: issuer,
519
+ },
520
+ /* issuer */
521
+ ).catch((error): void => {
522
+ throw new DyFM_Error({
523
+ ...this._getDefaultErrorSettings('restoreDeletedById', error, issuer),
524
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-RD0`,
525
+ additionalContent: { id },
526
+ message:
527
+ `restoreDeleted "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
528
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
529
+ issuer,
530
+ });
531
+ });
532
+ }
533
+
534
+ async restoreDeletedByDependencyId(
535
+ dependencyIdsFilter: { [key: string]: string },
536
+ issuer: string
537
+ ): Promise<void> {
538
+ await this.dataModel.updateMany(
539
+ dependencyIdsFilter,
540
+ {
541
+ _deleted: null,
542
+ __lastModified: new Date(),
543
+ __lastModifiedBy: issuer,
544
+ }
545
+ ).catch((error): void => {
546
+ throw new DyFM_Error({
547
+ ...this._getDefaultErrorSettings('restoreDeletedByDependencyId', error, issuer),
548
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-RDD0`,
549
+ additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
550
+ message:
551
+ `restoreDeleted "${this.dataParams.dataName}" by ` +
552
+ `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
553
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
554
+ issuer,
555
+ });
556
+ });
557
+ }
558
+
559
+ // TODO: Missing issuer
560
+ async getDeletedDataList(): Promise<T[]> {
561
+ const dataList: T[] = await this.dataModel
562
+ .getAll()
563
+ .then((res): T[] => res as T[] ?? [])
564
+ .catch((error): void => {
565
+ throw new DyFM_Error({
566
+ ...this._getDefaultErrorSettings('getDeletedData', error),
567
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GDD0`,
568
+ message:
569
+ `get deleted "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
570
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
571
+ });
572
+ });
573
+
574
+ return dataList.filter(
575
+ (data: T): boolean => Boolean(data._deleted)
576
+ ).map((data: T): T => this.stringifyDataId(data, 'getDeletedData'));
577
+ }
578
+
579
+ // TODO: Missing issuer
580
+ /**
581
+ * deleted data by id
582
+ * @param id id
583
+ */
584
+ async trueDeleteDataById(id: string): Promise<void> {
585
+ if (this.dataParams.forbidDelete) {
586
+ await this.deleteThrowMethod(id/* , issuer */);
587
+ }
588
+
589
+ await this.dataModel
590
+ .findByIdAndDelete(id)
591
+ .catch((error): void => {
592
+ throw new DyFM_Error({
593
+ ...this._getDefaultErrorSettings('deleteDataById', error),
594
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-DD0`,
595
+ additionalContent: { id },
596
+ message:
597
+ `delete "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
598
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
599
+ });
600
+ });
601
+ }
602
+ readonly deleteDataById = this.trueDeleteDataById;
603
+
604
+ // TODO: Missing issuer
605
+ /**
606
+ * deleted data by id
607
+ * @param dependencyId id
608
+ */
609
+ async trueDeleteDataByDependencyId(dependencyIdsFilter: { [key: string]: string }): Promise<void> {
610
+ if (this.dataParams.forbidDelete) {
611
+ await this.deleteThrowMethod(dependencyIdsFilter/* , issuer */);
612
+ }
613
+
614
+ if (!this.depKeys.length) {
615
+ throw new DyFM_Error({
616
+ ...this._getDefaultErrorSettings(
617
+ 'deleteDataByDependencyId',
618
+ new Error(
619
+ `dependencyDataIdKey not setted up for this db-service (${this.dataParams.dataName}) (NTS DB)`
620
+ )
621
+ ),
622
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-DDD0`,
623
+ });
624
+ }
625
+
626
+ await this.dataModel
627
+ .deleteMany(dependencyIdsFilter)
628
+ .catch((error): void => {
629
+ throw new DyFM_Error({
630
+ ...this._getDefaultErrorSettings('deleteDataByDependencyId', error),
631
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-DDD1`,
632
+ additionalContent: { dependencyIdsFilter: dependencyIdsFilter },
633
+ message:
634
+ `delete "${this.dataParams.dataName}" by ` +
635
+ `"${Object.keys(dependencyIdsFilter).join(', ')}" was unsuccessful (NTS DB)` +
636
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
637
+ });
638
+ });
639
+ }
640
+ readonly deleteDataByDependencyId = this.trueDeleteDataByDependencyId;
641
+
642
+ // TODO: Missing issuer
643
+ async trueDeleteAllData(): Promise<void> {
644
+ if (this.dataParams.forbidDelete) {
645
+ await this.deleteThrowMethod(null/* , issuer */);
646
+ }
647
+
648
+ await this.dataModel.deleteMany().catch((error): void => {
649
+ throw new DyFM_Error({
650
+ ...this._getDefaultErrorSettings('deleteAllData', error),
651
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-DAD0`,
652
+ message:
653
+ `delete all "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
654
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
655
+ });
656
+ });
657
+ }
658
+ readonly deleteAllData = this.trueDeleteAllData;
659
+
660
+ // TODO: Missing issuer
661
+ /**
662
+ * returns search result for searchBy object params
663
+ * can use lists or xRange values for searchBy obj properties
664
+ *
665
+ * @param filterBy filter
666
+ * @param narrowByDependencyIds id
667
+ * @returns dataList
668
+ */
669
+ async searchData(
670
+ filterBy: DyFM_DBFilter<T>,
671
+ narrowByDependencyIds?: string[],
672
+ narrowByDependencyKey?: string,
673
+ findDeleted?: boolean
674
+ ): Promise<T[]> {
675
+ const filter = {};
676
+
677
+ if (0 < narrowByDependencyIds.length) {
678
+ if (!this.depKeys.length) {
679
+ throw new DyFM_Error({
680
+ ...this._getDefaultErrorSettings(
681
+ 'searchData',
682
+ new Error(
683
+ `dependencyDataIdKey not setted up for this db-service (${this.dataParams.dataName}) (NTS DB)`
684
+ )
685
+ ),
686
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-SD0`,
687
+ });
688
+ }
689
+
690
+ if (!narrowByDependencyKey) {
691
+ if (this.depKeys.length === 1) {
692
+ narrowByDependencyKey = this.depKeys[0];
693
+ } else {
694
+ throw new DyFM_Error({
695
+ ...this._getDefaultErrorSettings(
696
+ 'searchData',
697
+ new Error(`dependencyKey is missing! (${this.dataParams.dataName}) (NTS DB)`),
698
+ ),
699
+ });
700
+ }
701
+ }
702
+
703
+ filter[narrowByDependencyKey] = { $in: narrowByDependencyIds };
704
+ }
705
+
706
+ Object.values(this.dataParams.properties).forEach(
707
+ (modelParam: DyFM_DataProperty_Params<any, T>): void => {
708
+ if (
709
+ (filterBy[modelParam.key] !== null && filterBy[modelParam.key] !== undefined) ||
710
+ filterBy[modelParam.key + 'Range']
711
+ ) {
712
+ if (modelParam.key.includes('Range') || modelParam.type.includes('[]')) {
713
+ // inverz search filter (for Range and Array functions)
714
+ if (modelParam.key.includes('Range')) {
715
+ const searchParamKeyWithoutRange = modelParam.key.split('Range')[0];
716
+
717
+ if (
718
+ filterBy[searchParamKeyWithoutRange] !== null &&
719
+ filterBy[searchParamKeyWithoutRange] !== undefined
720
+ ) {
721
+ filter[modelParam.key] = {
722
+ from: { $lte: filterBy[searchParamKeyWithoutRange] },
723
+ to: { $gte: filterBy[searchParamKeyWithoutRange] },
724
+ };
725
+ }
726
+ } else {
727
+ if (
728
+ filterBy[modelParam.key] !== null &&
729
+ filterBy[modelParam.key] !== undefined
730
+ ) {
731
+ filter[modelParam.key] = { $in: filterBy[modelParam.key] };
732
+ }
733
+ }
734
+ } else {
735
+ // basic search filter
736
+ if (filterBy[modelParam.key + 'Range']) {
737
+ if (
738
+ filterBy[modelParam.key + 'Range'].from ||
739
+ filterBy[modelParam.key + 'Range'].to
740
+ ) {
741
+ filter[modelParam.key] = {};
742
+
743
+ if (filterBy[modelParam.key + 'Range'].from) {
744
+ filter[modelParam.key].$gte = filterBy[modelParam.key + 'Range'].from;
745
+ }
746
+
747
+ if (filterBy[modelParam.key + 'Range'].to) {
748
+ filter[modelParam.key].$lte = filterBy[modelParam.key + 'Range'].to;
749
+ }
750
+ }
751
+ } else if (
752
+ filterBy[modelParam.key] !== null &&
753
+ filterBy[modelParam.key] !== undefined
754
+ ) {
755
+ if (filterBy[modelParam.key].lenght > 0) {
756
+ filter[modelParam.key] = { $in: filterBy[modelParam.key] };
757
+ }
758
+ }
759
+ }
760
+ }
761
+ }
762
+ );
763
+
764
+ let dataList: T[] = await this.dataModel
765
+ .find(filter)
766
+ .then((res): T[] => res as T[] ?? [])
767
+ .catch((error): void => {
768
+ throw new DyFM_Error({
769
+ ...this._getDefaultErrorSettings('searchData', error),
770
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-SD1`,
771
+ additionalContent: { filterBy, narrowByDependencyIds },
772
+ message:
773
+ `search "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
774
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
775
+ });
776
+ });
777
+
778
+ if (!findDeleted && (filterBy as DyFM_DBFilterSimple<T>)._deleted === undefined) {
779
+ dataList = dataList.filter((data: T): boolean => !data._deleted);
780
+ }
781
+
782
+ return dataList.map((data: T): T => this.stringifyDataId(data, 'searchData'));
783
+ }
784
+
785
+ // ----------------------------------------------------------------------------------
786
+ // ----------------------------------------------------------------------------------
787
+ // ----------------------------------------------------------------------------------
788
+ // DIRECT Basic MONGOOSE FUNCTIONS (with error handlings)
789
+
790
+ /**
791
+ * Find the data first by any of its parameters,
792
+ * !!!: throws error if not found (errorCode on not found: NTS-DBS-FO1)
793
+ *
794
+ * @param filterBy if you can, use unique parameters for find!
795
+ *
796
+ * @example
797
+ * // by email:
798
+ * { email: email }
799
+ * //
800
+ * @example
801
+ * // or by id that is in list:
802
+ * { userIds: { $in: this.userId } }
803
+ * // or by userIds:
804
+ * { userId: { $in: userIds } }
805
+ * //
806
+ * @example
807
+ * // or by number or Date that is Greater Than AND Less Than:
808
+ * { points: { $gt: 2, $lt: 14 } }
809
+ * // further tools (syntax matches with $gt):
810
+ * $eq: // Matches values that are EQual to a specified value.
811
+ * $gte: // Matches values that are Greater Than OR Equal to a specified value.
812
+ * $lte: // Matches values that are Less Than or Equal to a specified value.
813
+ * $ne: // Matches all values that are Not Equal to a specified value.
814
+ * $nin: // Matches None of the values specified IN an array.
815
+ * //
816
+ * @returns {T} data: T
817
+ */
818
+ async findOne(filterBy: DyFM_DBFilter<T>): Promise<T> {
819
+ const data: T = await this.dataModel
820
+ .findOne(filterBy)
821
+ .then((res): T => res as T ?? null)
822
+ .catch((error): void => {
823
+ throw new DyFM_Error({
824
+ ...this._getDefaultErrorSettings('findOne', error),
825
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-FO0`,
826
+ additionalContent: { filterBy },
827
+ message:
828
+ `findOne "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
829
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
830
+ });
831
+ });
832
+
833
+ return this.stringifyDataId(data, 'findOne');
834
+ }
835
+
836
+ /**
837
+ * #MONGOOSE FUNCTION
838
+ * Find the data first by any of its parameters,
839
+ * !!!: throws error if not found (errorCode on not found: NTS-DBS-F1)
840
+ *
841
+ * @param filterBy if you can, use unique parameters for find!
842
+ *
843
+ * @example
844
+ * // by email:
845
+ * { email: email }
846
+ * //
847
+ * @example
848
+ * // or by id that is in list:
849
+ * { userIds: { $in: this.userId } }
850
+ * // or by userIds:
851
+ * { userId: { $in: userIds } }
852
+ * //
853
+ * @example
854
+ * // or by number or Date that is Greater Than AND Less Than:
855
+ * { points: { $gt: 2, $lt: 14 } }
856
+ * // further tools (syntax matches with $gt):
857
+ * $eq: // Matches values that are EQual to a specified value.
858
+ * $gte: // Matches values that are Greater Than OR Equal to a specified value.
859
+ * $lte: // Matches values that are Less Than or Equal to a specified value.
860
+ * $ne: // Matches all values that are Not Equal to a specified value.
861
+ * $nin: // Matches None of the values specified IN an array.
862
+ * //
863
+ * @param options BFR-008: opcionalis projection/limit/sort — DB-szinten szukit (a nagy mezok be sem toltodnek)
864
+ * @returns {T[]} dataList: T[]
865
+ */
866
+ async find(filterBy: DyFM_DBFilter<T>, findDeleted?: boolean, options?: DyNTS_DBQueryOptions<T>): Promise<T[]> {
867
+ // BFR-OVERSEER-008 — options megadasakor a soft-delete szures QUERY-szintre kerul: limit mellett a
868
+ // memoriabeli post-filter hibas darabszamot adna, projekcio mellett (kihagyott `_deleted` mezovel)
869
+ // hibasan atengedne a torolt dokumentumokat. A `_deleted` soft-delete-kor `new Date()`, egyebkent
870
+ // HIANYZIK → a Mongo `_deleted: null` (missing VAGY null) a post-filter `!data._deleted` ekvivalense.
871
+ const deletedGuardInQuery: boolean =
872
+ !!options && !findDeleted && (filterBy as DyFM_DBFilterSimple<T>)._deleted === undefined;
873
+ const effectiveFilter: DyFM_DBFilter<T> = deletedGuardInQuery
874
+ ? { ...(filterBy as DyFM_DBFilterSimple<T>), _deleted: null } as unknown as DyFM_DBFilter<T>
875
+ : filterBy;
876
+
877
+ // A szukites (select/sort/limit) DB-szinten tortenik → a nagy mezok be sem toltodnek a heap-be.
878
+ let query = this.dataModel.find(effectiveFilter);
879
+ if (options?.projection) { query = query.select(options.projection); }
880
+ if (options?.sort) { query = query.sort(options.sort); }
881
+ if (options?.limit) { query = query.limit(options.limit); }
882
+
883
+ let dataList: T[] = await query
884
+ .then((res): T[] => res as T[] ?? [])
885
+ .catch((error): void => {
886
+ throw new DyFM_Error({
887
+ ...this._getDefaultErrorSettings('find', error),
888
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-F0`,
889
+ additionalContent: { filterBy },
890
+ message:
891
+ `find "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
892
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
893
+ });
894
+ });
895
+
896
+ if (!findDeleted && !deletedGuardInQuery && (filterBy as DyFM_DBFilterSimple<T>)._deleted === undefined) {
897
+ dataList = dataList.filter((data: T): boolean => !data._deleted);
898
+ }
899
+
900
+ return dataList.map((data: T): T => this.stringifyDataId(data, 'find'));
901
+ }
902
+
903
+ /**
904
+ * #MONGOOSE FUNCTION
905
+ * Find the data first by any of its parameters
906
+ * WARNING: This function will not gives you back the total number of data in the database!
907
+ *
908
+ * @param filterBy if you can, use unique parameters for find!
909
+ *
910
+ * @example
911
+ * // by email:
912
+ * { email: email }
913
+ * //
914
+ * @example
915
+ * // or by id that is in list:
916
+ * { userIds: { $in: this.userId } }
917
+ * // or by userIds:
918
+ * { userId: { $in: userIds } }
919
+ * //
920
+ * @example
921
+ * // or by number or Date that is Greater Than AND Less Than:
922
+ * { points: { $gt: 2, $lt: 14 } }
923
+ * // further tools (syntax matches with $gt):
924
+ * $eq: // Matches values that are EQual to a specified value.
925
+ * $gte: // Matches values that are Greater Than OR Equal to a specified value.
926
+ * $lte: // Matches values that are Less Than or Equal to a specified value.
927
+ * $ne: // Matches all values that are Not Equal to a specified value.
928
+ * $nin: // Matches None of the values specified IN an array.
929
+ * //
930
+ * @param page page
931
+ * @param pageSize pageSize
932
+ * @param sort
933
+ * @example
934
+ * // by dateTime (this uses the basic sort function):
935
+ * { dateTime: -1 }
936
+ * //
937
+ * @returns {T[]} dataList: T[]
938
+ */
939
+ async findWithPaging(
940
+ filterBy: DyFM_DBFilter<T>,
941
+ page: number,
942
+ pageSize: number,
943
+ sort?: DyFM_DBSort<T>
944
+ ): Promise<T[]> {
945
+ /* if (filterBy['_deleted'] === undefined) {
946
+ filterBy['_deleted'] = null;
947
+ } */
948
+
949
+ const dataList: T[] = await this.dataModel
950
+ .find(filterBy)
951
+ .sort(sort)
952
+ .skip(page * pageSize)
953
+ .limit(pageSize)
954
+ .then((res): T => res ?? [])
955
+ .catch((error): void => {
956
+ throw new DyFM_Error({
957
+ ...this._getDefaultErrorSettings('findWithPaging', error),
958
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-WP0`,
959
+ additionalContent: { filterBy, page, pageSize, sort },
960
+ message:
961
+ `findWithPaging "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
962
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
963
+ });
964
+ });
965
+
966
+ /* if ((filterBy as DyFM_DBFilterSimple<T>)._deleted === undefined) {
967
+ dataList = dataList.filter((data: T): boolean => !data._deleted);
968
+ } */
969
+
970
+ return dataList.map((data: T): T => this.stringifyDataId(data, 'find'));
971
+ }
972
+
973
+ /**
974
+ * #MONGOOSE FUNCTION
975
+ * Find data by _id and update
976
+ *
977
+ * @param id id
978
+ * @param update update
979
+ * @returns data
980
+ */
981
+ async findByIdAndUpdate(
982
+ id: string,
983
+ update: DyNTS_DBUpdate<T>,
984
+ issuer: string,
985
+ dontUpdateModified?: boolean
986
+ ): Promise<T> {
987
+ if (this.dataParams.forbidModify) {
988
+ await this.modifyThrowMethod(update, issuer);
989
+ }
990
+
991
+ if (!dontUpdateModified) {
992
+ update.__lastModified = new Date();
993
+ update.__lastModifiedBy = issuer;
994
+ }
995
+
996
+ const data: T = await this.dataModel
997
+ .findByIdAndUpdate(id, update)
998
+ .then((res): T => res?.toObject() as T ?? null)
999
+ .catch((error): void => {
1000
+ throw new DyFM_Error({
1001
+ ...this._getDefaultErrorSettings('findByIdAndUpdate', error, issuer),
1002
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-FIU0`,
1003
+ additionalContent: { id, update },
1004
+ message:
1005
+ `findByIdAndUpdate "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
1006
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
1007
+ issuer,
1008
+ });
1009
+ });
1010
+
1011
+ return this.stringifyDataId(data, 'findByIdAndUpdate');
1012
+ }
1013
+
1014
+ /**
1015
+ * #MONGOOSE FUNCTION
1016
+ * Find the data first by any of its parameters
1017
+ *
1018
+ * @param filter This uses the basic Mongoose updateOne.
1019
+ * If you can, use unique parameters for find!
1020
+ * @example
1021
+ * // by email:
1022
+ * { email: email }
1023
+ * //
1024
+ * @example
1025
+ * // or by id that is in list:
1026
+ * { userIds: { $in: this.userId } }
1027
+ * // or by userIds:
1028
+ * { userId: { $in: userIds } }
1029
+ * //
1030
+ * @example
1031
+ * // or by number or Date that is Greater Than AND Less Than:
1032
+ * { points: { $gt: 2, $lt: 14 } }
1033
+ * // further tools (syntax matches with $gt):
1034
+ * $eq: // Matches values that are EQual to a specified value.
1035
+ * $gte: // Matches values that are Greater Than OR Equal to a specified value.
1036
+ * $lte: // Matches values that are Less Than or Equal to a specified value.
1037
+ * $ne: // Matches all values that are Not Equal to a specified value.
1038
+ * $nin: // Matches None of the values specified IN an array.
1039
+ * //
1040
+ *
1041
+ * @param update this uses the basic Mongoose updateOne
1042
+ * @example
1043
+ * // increase a specific value (here by 15):
1044
+ * { $inc: { popularity: 15 } }
1045
+ * //
1046
+ * @example
1047
+ * // or add element to a list:
1048
+ * { $push: { reactions: this.newReaction }
1049
+ * // or add multiple elements to a list
1050
+ * { $push: { schedule: {$each: [ monday, tuesday, wednesday ] } } }
1051
+ * //
1052
+ * @example
1053
+ * // or all at once
1054
+ * {
1055
+ * $inc: { popularity: this.newVote.amount },
1056
+ * emailVerified: true,
1057
+ * $push: { reactions: this.newReaction }
1058
+ * }
1059
+ * // further tools (syntax matches with $inc):
1060
+ * $currentDate: // Sets the value of a field to current date, either as a Date or a Timestamp.
1061
+ * $min: // Only updates the field if the specified value is less than the existing field value.
1062
+ * $max: // Only updates the field if the specified value is greater than the existing field value.
1063
+ * $mul: // Multiplies the value of the field by the specified amount.
1064
+ * $rename: // Renames a field.
1065
+ * $unset: // Removes the specified field from a document. (set: "" to value)
1066
+ * //
1067
+ */
1068
+ async updateOne(
1069
+ filterBy: DyFM_DBFilter<T>,
1070
+ update: DyNTS_DBUpdate<T>,
1071
+ issuer: string,
1072
+ dontUpdateModified?: boolean
1073
+ ): Promise<void> {
1074
+ if (this.dataParams.forbidModify) {
1075
+ await this.modifyThrowMethod(update, issuer);
1076
+ }
1077
+
1078
+ if (!dontUpdateModified) {
1079
+ update.__lastModified = new Date();
1080
+ update.__lastModifiedBy = issuer;
1081
+ }
1082
+
1083
+ await this.dataModel
1084
+ .updateOne(filterBy, update)
1085
+ .catch((error): void => {
1086
+ throw new DyFM_Error({
1087
+ ...this._getDefaultErrorSettings('updateOne', error, issuer),
1088
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-UO0`,
1089
+ additionalContent: { filterBy, update },
1090
+ message:
1091
+ `updateOne "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
1092
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
1093
+ issuer,
1094
+ });
1095
+ });
1096
+ }
1097
+
1098
+ /**
1099
+ * #MONGOOSE FUNCTION
1100
+ * update one parameter by a specific
1101
+ *
1102
+ * @param filter This uses the basic Mongoose updateMany.
1103
+ * @example
1104
+ * // by email:
1105
+ * { email: email }
1106
+ * //
1107
+ * @example
1108
+ * // or by id that is in list:
1109
+ * { userIds: { $in: this.userId } }
1110
+ * // or by userIds:
1111
+ * { userId: { $in: userIds } }
1112
+ * //
1113
+ * @example
1114
+ * // or by number or Date that is Greater Than AND Less Than:
1115
+ * { points: { $gt: 2, $lt: 14 } }
1116
+ * // further tools (syntax matches with $gt):
1117
+ * $eq: // Matches values that are EQual to a specified value.
1118
+ * $gte: // Matches values that are Greater Than OR Equal to a specified value.
1119
+ * $lte: // Matches values that are Less Than or Equal to a specified value.
1120
+ * $ne: // Matches all values that are Not Equal to a specified value.
1121
+ * $nin: // Matches None of the values specified IN an array.
1122
+ * //
1123
+ *
1124
+ * @param update this uses the basic Mongoose updateOne
1125
+ * @example
1126
+ * // increase a specific value (here by 15):
1127
+ * { $inc: { popularity: 15 } }
1128
+ * //
1129
+ * @example
1130
+ * // or add element to a list:
1131
+ * { $push: { reactions: this.newReaction }
1132
+ * // or add multiple elements to a list
1133
+ * { $push: { schedule: {$each: [ monday, tuesday, wednesday ] } } }
1134
+ * //
1135
+ * @example
1136
+ * // or all at once
1137
+ * {
1138
+ * $inc: { popularity: this.newVote.amount },
1139
+ * emailVerified: true,
1140
+ * $push: { reactions: this.newReaction }
1141
+ * }
1142
+ * // further tools (syntax matches with $inc):
1143
+ * $currentDate: // Sets the value of a field to current date, either as a Date or a Timestamp.
1144
+ * $min: // Only updates the field if the specified value is less than the existing field value.
1145
+ * $max: // Only updates the field if the specified value is greater than the existing field value.
1146
+ * $mul: // Multiplies the value of the field by the specified amount.
1147
+ * $rename: // Renames a field.
1148
+ * $unset: // Removes the specified field from a document. (set: "" to value)
1149
+ * //
1150
+ */
1151
+ async updateMany(
1152
+ filterBy: DyFM_DBFilter<T>,
1153
+ update: DyNTS_DBUpdate<T>,
1154
+ issuer: string,
1155
+ dontUpdateModified?: boolean
1156
+ ): Promise<void> {
1157
+ if (this.dataParams.forbidModify) {
1158
+ await this.modifyThrowMethod(update, issuer);
1159
+ }
1160
+
1161
+ if (!dontUpdateModified) {
1162
+ update.__lastModified = new Date();
1163
+ update.__lastModifiedBy = issuer;
1164
+ }
1165
+
1166
+ await this.dataModel
1167
+ .updateMany(filterBy, update)
1168
+ .catch((error): void => {
1169
+ throw new DyFM_Error({
1170
+ ...this._getDefaultErrorSettings('updateMany', error, issuer),
1171
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-UM0`,
1172
+ additionalContent: { filterBy, update },
1173
+ message:
1174
+ `updateMany "${this.dataParams.dataName}" was unsuccessful (NTS DB)` +
1175
+ `\n error: ${DyFM_Error.getErrorMessage(error)}`,
1176
+ issuer,
1177
+ });
1178
+ });
1179
+ }
1180
+
1181
+ /**
1182
+ * {
1183
+ "mappings": {
1184
+ "dynamic": true,
1185
+ "fields": {
1186
+ "embedding": {
1187
+ "type": "knnVector",
1188
+ "dimensions": 768
1189
+ }
1190
+ }
1191
+ }
1192
+ }
1193
+ */
1194
+ /**
1195
+ *
1196
+ * @param set db.collection.aggregate([
1197
+ {
1198
+ $vectorSearch: {
1199
+ index: "index_neve",
1200
+ queryVector: [a keresett embedding],
1201
+ path: "title.embedding",
1202
+ numCandidates: 100,
1203
+ limit: 5
1204
+ }
1205
+ },
1206
+ {
1207
+ $vectorSearch: {
1208
+ index: "index_neve",
1209
+ queryVector: [a keresett embedding],
1210
+ path: "description.embedding",
1211
+ numCandidates: 100,
1212
+ limit: 5
1213
+ }
1214
+ }
1215
+ ]);
1216
+ * @returns
1217
+ */
1218
+ async aggregate(set: any) {
1219
+ return this.dataModel.aggregate(set);
1220
+ }
1221
+
1222
+ // ----------------------------------------------------------------------------------
1223
+ // ----------------------------------------------------------------------------------
1224
+ // ----------------------------------------------------------------------------------
1225
+ // PRIVATE FUNCTIONS
1226
+
1227
+ private stringifyDataId(data: T, fnName: string): T {
1228
+ if (data?._id && (typeof data._id !== 'string' || typeof data._id === 'object')) {
1229
+ data._id = `${data._id}`;
1230
+
1231
+ if (typeof data._id !== 'string' || typeof data._id === 'object') {
1232
+ data = JSON.parse(JSON.stringify(data));
1233
+
1234
+ if (typeof data._id !== 'string' || typeof data._id === 'object') {
1235
+ DyFM_Log.error(
1236
+ `data._id stringifying failed! Please notfiy the DynamoNTS developers! (${fnName})`,
1237
+ new Error()
1238
+ );
1239
+ }
1240
+ }
1241
+ }
1242
+
1243
+ return data;
1244
+ }
1245
+
1246
+ private _getDefaultErrorSettings(
1247
+ fnName: string,
1248
+ error: DyFM_AnyError,
1249
+ issuer?: string
1250
+ ): DyFM_Error_Settings {
1251
+ return {
1252
+ status: (error as DyFM_Error)?.___status ?? 500,
1253
+ message: (error as Error)?.message ??
1254
+ (error as DyFM_Error)?._message ??
1255
+ `${fnName} was UNSUCCESSFUL (NTS-DB)`,
1256
+ addECToUserMsg: !(error as DyFM_Error)?.__userMessage,
1257
+ userMessage: (error as DyFM_Error)?.__userMessage ?? this.defaultErrorUserMsg,
1258
+ issuer: issuer,
1259
+ issuerService: this.serviceName,
1260
+ error: error,
1261
+ };
1262
+ }
1263
+
1264
+ // ----------------------------------------------------------------------------------
1265
+ // PRIVATE BUILD FUNCTIONS
1266
+
1267
+ /**
1268
+ * builds and returns mongoose schema
1269
+ * @returns schema
1270
+ */
1271
+ private getSchema(): mongoose.Schema {
1272
+ this.dataParams.properties = this.addMetadataToProperties(this.dataParams.properties);
1273
+
1274
+ if (this.dataParams.dataName.includes(DyNTS_archiveSuffix)) {
1275
+ this.dataParams.properties = this.addArchiveMetadataToProperties(this.dataParams.properties);
1276
+ }
1277
+
1278
+ const schemaSettings: any = this.buildMongooseSchemaSettingsObjByModelParams(
1279
+ this.dataParams.properties
1280
+ );
1281
+
1282
+ /* schema = this.addMetadataToSchema(schema); */
1283
+
1284
+ /* if (this.dataParams.dataName.includes(DyNTS_archiveSuffix)) {
1285
+ schema = this.addArchiveMetadataToSchema(schema);
1286
+ } */
1287
+
1288
+ if (schemaSettings['_id']) {
1289
+ delete schemaSettings['_id'];
1290
+ }
1291
+
1292
+ return new Schema(schemaSettings);
1293
+ }
1294
+
1295
+ /**
1296
+ * builds mongoose schema building settings object by dynamoDataModelParamsList
1297
+ * @param properties DynamoNTSDataPropertyParams
1298
+ * @returns mongoose schema object
1299
+ */
1300
+ private buildMongooseSchemaSettingsObjByModelParams(properties: DyFM_DataProperties<T>): any {
1301
+ const schemaSettingsObj = {};
1302
+
1303
+ /* if (!properties) {
1304
+ properties = this.dataParams.properties;
1305
+ } */
1306
+
1307
+ Object.values(properties).forEach((property: DyFM_DataProperty_Params<any, T>): void => {
1308
+ if (!property) {
1309
+ DyFM_Log.warn(`property is undefined on "${this.dataParams.dataName}" (NTS DB)`);
1310
+
1311
+ return;
1312
+ }
1313
+
1314
+ if (!property.key) {
1315
+ const missingKeys = Object.keys(properties).filter((key: string) => !properties[key].key);
1316
+
1317
+ throw new DyFM_Error({
1318
+ ...this._getDefaultErrorSettings(
1319
+ 'buildMongooseSchemaByModelParams',
1320
+ new Error(
1321
+ `property.key is undefined on "${this.dataParams.dataName}" (NTS DB) ` +
1322
+ `(keys: ${Object.keys(properties).join(', ')}) ` +
1323
+ `(missing keys: ${missingKeys.join(', ')})`
1324
+ )
1325
+ ),
1326
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-BMSBP0`,
1327
+ additionalContent: {
1328
+ property: property,
1329
+ dataParams: this.dataParams,
1330
+ missingKeys: missingKeys,
1331
+ },
1332
+ });
1333
+ }
1334
+
1335
+ if (property.forbidden) {
1336
+ return;
1337
+ }
1338
+
1339
+ const beType = this.getBEType(property.type as DyFM_BasicProperty_Type);
1340
+
1341
+ /* TODO if (beType === Array && property.archiveable && !property.archiveListAfter) {
1342
+ property.archiveListAfter = DyNTS_global_settings.archiveListAfter;
1343
+ } */
1344
+
1345
+ if (
1346
+ beType !== Object ||
1347
+ !property?.subObjectParams ||
1348
+ (property?.subObjectParams &&
1349
+ Object.keys(property.subObjectParams).length == 0)
1350
+ ) {
1351
+ schemaSettingsObj[property.key] = {
1352
+ type: beType,
1353
+ };
1354
+
1355
+ if (property.index) {
1356
+ schemaSettingsObj[property.key].index = true;
1357
+ }
1358
+
1359
+ if (property.unique) {
1360
+ schemaSettingsObj[property.key].unique = true;
1361
+ }
1362
+
1363
+ if (property.required) {
1364
+ schemaSettingsObj[property.key].required = true;
1365
+ }
1366
+
1367
+ if (property.minlength) {
1368
+ schemaSettingsObj[property.key].minlength = property.minlength;
1369
+ }
1370
+
1371
+ if (property.maxlength) {
1372
+ schemaSettingsObj[property.key].maxlength = property.maxlength;
1373
+ }
1374
+ } else {
1375
+ schemaSettingsObj[property.key] = this.buildMongooseSchemaSettingsObjByModelParams(
1376
+ property.subObjectParams
1377
+ );
1378
+ }
1379
+ });
1380
+
1381
+ return schemaSettingsObj;
1382
+ }
1383
+
1384
+ private getBEType(
1385
+ type: DyFM_BasicProperty_Type
1386
+ ): string | number | boolean | object | Function | Array<any> | Date {
1387
+ switch (type) {
1388
+ case DyFM_BasicProperty_Type.string:
1389
+ return String;
1390
+
1391
+ case DyFM_BasicProperty_Type.number:
1392
+ return Number;
1393
+
1394
+ case DyFM_BasicProperty_Type.boolean:
1395
+ return Boolean;
1396
+
1397
+ case DyFM_BasicProperty_Type.date:
1398
+ return Date;
1399
+
1400
+ case DyFM_BasicProperty_Type.object:
1401
+ return Object;
1402
+
1403
+ case DyFM_BasicProperty_Type.array:
1404
+ return Array;
1405
+
1406
+ case DyFM_BasicProperty_Type.function:
1407
+ return Function;
1408
+
1409
+ default:
1410
+ DyFM_Log.H_info('wtf', DyFM_Object.cleanObject(this.dataParams));
1411
+
1412
+ throw new DyFM_Error({
1413
+ error: new Error(
1414
+ `Invalid property type: "${type}" (${this.dataParams.dataName})` +
1415
+ (this.dataParams.constructed?.() ? '' : ('\nThe dataParams is not constructed properly! \n' +
1416
+ 'Use the DyFM_DataModel_Params.constructor to construct it properly!'))
1417
+ ),
1418
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-GTP0`,
1419
+ additionalContent: { type: type, dataParams: this.dataParams },
1420
+ __localStack: this.dataParams.stackLocation,
1421
+ });
1422
+ }
1423
+ /* switch (type.toLocaleLowerCase()) {
1424
+ case DyFM_BasicProperty_Type.string:
1425
+ case 'string':
1426
+ return String;
1427
+
1428
+ case DyFM_BasicProperty_Type.number:
1429
+ case 'number':
1430
+ return Number;
1431
+
1432
+ case DyFM_BasicProperty_Type.boolean:
1433
+ case 'boolean':
1434
+ return Boolean;
1435
+
1436
+ case DyFM_BasicProperty_Type.date:
1437
+ case 'date':
1438
+ return Date;
1439
+
1440
+ case DyFM_BasicProperty_Type.object:
1441
+ case 'object':
1442
+ return Object;
1443
+
1444
+ case DyFM_BasicProperty_Type.array:
1445
+ case 'array':
1446
+ return Array;
1447
+
1448
+ default:
1449
+ if (type.includes('[]') || type.includes('array')) {
1450
+ return Array;
1451
+ } else if (type.includes('=>') || type.includes('function')) {
1452
+ return Function;
1453
+ } else {
1454
+ return Object;
1455
+ }
1456
+ } */
1457
+ }
1458
+
1459
+ /**
1460
+ * adds dynamo metadata settings to any mongoose schema building settings object
1461
+ * @param schema schema to update
1462
+ * @returns updated schema
1463
+ */
1464
+ /* private addMetadataToSchema(schema: any): any {
1465
+ schema.__created = { type: Date };
1466
+ schema.__createdBy = { type: String };
1467
+ schema.__lastModified = { type: Date };
1468
+ schema.__lastModifiedBy = { type: String };
1469
+
1470
+ schema._deleted = { type: Date };
1471
+ schema._deletedBy = { type: String };
1472
+
1473
+ return schema;
1474
+ } */
1475
+
1476
+ /**
1477
+ * adds dynamo metadata settings to any mongoose schema building settings object
1478
+ * @param properties properties to update
1479
+ * @returns updated properties
1480
+ */
1481
+ private addMetadataToProperties(properties: DyFM_DataProperties<T>): DyFM_DataProperties<T> {
1482
+ // TOD: ezek a kikommentelt "required: true"-k kellenek, csak félő, hogy gondokat okoznak a
1483
+ // jelenlegi rendszerekben, ezért akkor kell majd visszarakni, ha lesz tesztelői ÉS fejlesztői kapacitás rá
1484
+ if (!properties.__created) {
1485
+ properties.__created = {
1486
+ key: '__created', type: DyFM_BasicProperty_Type.date/* , required: true */,
1487
+ };
1488
+ }
1489
+
1490
+ if (!properties.__createdBy) {
1491
+ properties.__createdBy = {
1492
+ key: '__createdBy', type: DyFM_BasicProperty_Type.string/* , required: true */,
1493
+ };
1494
+ }
1495
+
1496
+ if (!properties.__lastModified) {
1497
+ properties.__lastModified = {
1498
+ key: '__lastModified', type: DyFM_BasicProperty_Type.date/* , required: true */,
1499
+ };
1500
+ }
1501
+
1502
+ if (!properties.__lastModifiedBy) {
1503
+ properties.__lastModifiedBy = {
1504
+ key: '__lastModifiedBy', type: DyFM_BasicProperty_Type.string/* , required: true */,
1505
+ };
1506
+ }
1507
+
1508
+ if (!properties._deleted) {
1509
+ properties._deleted = {
1510
+ key: '_deleted', type: DyFM_BasicProperty_Type.date,
1511
+ };
1512
+ }
1513
+
1514
+ if (!properties._deletedBy) {
1515
+ properties._deletedBy = {
1516
+ key: '_deletedBy', type: DyFM_BasicProperty_Type.string,
1517
+ };
1518
+ }
1519
+
1520
+ if (!properties._archived) {
1521
+ properties._archived = {
1522
+ key: '_archived', type: DyFM_BasicProperty_Type.date,
1523
+ };
1524
+ }
1525
+
1526
+ return properties;
1527
+ }
1528
+
1529
+ /* private addArchiveMetadataToSchema(schema: any): any {
1530
+ schema._originalId = { type: String, required: true, index: true, unique: true };
1531
+ schema._archived = { type: Date, required: true };
1532
+
1533
+ return schema;
1534
+ } */
1535
+
1536
+ private addArchiveMetadataToProperties(
1537
+ properties: DyFM_DataProperties<T>
1538
+ ): DyFM_DataProperties<T> {
1539
+ if (!properties._originalId) {
1540
+ properties._originalId = {
1541
+ key: '_originalId', type: DyFM_BasicProperty_Type.string,
1542
+ required: true, index: true, unique: true,
1543
+ };
1544
+ }
1545
+
1546
+ if (!properties._archived) {
1547
+ properties._archived = {
1548
+ key: '_archived', type: DyFM_BasicProperty_Type.date,
1549
+ required: true,
1550
+ };
1551
+ } else if (properties._archived.required === undefined) {
1552
+ properties._archived.required = true;
1553
+ }
1554
+
1555
+ return properties;
1556
+ }
1557
+
1558
+ /**
1559
+ * sets depDataKey
1560
+ */
1561
+ private lookForDependencyDataSettings(): void {
1562
+ const dependencyParams: DyFM_DataProperty_Params<any, T>[] =
1563
+ Object.values(this.dataParams.properties).filter(
1564
+ (modelParams: DyFM_DataProperty_Params<any, T>): boolean =>
1565
+ Boolean(modelParams.dependencyDataName)
1566
+ );
1567
+
1568
+ if (dependencyParams) {
1569
+ this.depKeys.push(...dependencyParams.map(
1570
+ (dependencyParam: DyFM_DataProperty_Params<any, T>): string => dependencyParam.key
1571
+ ));
1572
+ }
1573
+ }
1574
+
1575
+ private async deleteThrowMethod(data: any, issuer?: string): Promise<void> {
1576
+ throw new DyFM_Error({
1577
+ error: new Error(`Forbidden to delete any data! (${this.dataParams.dataName})`),
1578
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-CDAD`,
1579
+ additionalContent: { dataParams: this.dataParams, data: data },
1580
+ issuer: issuer,
1581
+ });
1582
+ };
1583
+
1584
+ private async modifyThrowMethod(data: any, issuer?: string): Promise<void> {
1585
+ throw new DyFM_Error({
1586
+ error: new Error(`Forbidden to modify any data! (${this.dataParams.dataName})`),
1587
+ errorCode: `${DyNTS_global_settings.systemShortCodeName}|DyNTS-DBS-CDAD`,
1588
+ additionalContent: { dataParams: this.dataParams, data: data },
1589
+ issuer: issuer,
1590
+ });
1591
+ }
1592
+ }