@hed-hog/core 0.0.399 → 0.0.401

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 (815) hide show
  1. package/dist/ai/ai-agent.sort.d.ts +6 -0
  2. package/dist/ai/ai-agent.sort.d.ts.map +1 -0
  3. package/dist/ai/ai-agent.sort.js +21 -0
  4. package/dist/ai/ai-agent.sort.js.map +1 -0
  5. package/dist/ai/ai.controller.d.ts +6 -4
  6. package/dist/ai/ai.controller.d.ts.map +1 -1
  7. package/dist/ai/ai.service.d.ts +121 -6
  8. package/dist/ai/ai.service.d.ts.map +1 -1
  9. package/dist/ai/ai.service.js +355 -160
  10. package/dist/ai/ai.service.js.map +1 -1
  11. package/dist/ai-instruction/ai-instruction.service.d.ts.map +1 -1
  12. package/dist/ai-instruction/ai-instruction.service.js +26 -23
  13. package/dist/ai-instruction/ai-instruction.service.js.map +1 -1
  14. package/dist/ai-instruction/ai-instruction.sort.d.ts +16 -0
  15. package/dist/ai-instruction/ai-instruction.sort.d.ts.map +1 -0
  16. package/dist/ai-instruction/ai-instruction.sort.js +32 -0
  17. package/dist/ai-instruction/ai-instruction.sort.js.map +1 -0
  18. package/dist/ai-instruction/ai-prompt-resolver.service.d.ts +12 -0
  19. package/dist/ai-instruction/ai-prompt-resolver.service.d.ts.map +1 -1
  20. package/dist/ai-instruction/ai-prompt-resolver.service.js +26 -0
  21. package/dist/ai-instruction/ai-prompt-resolver.service.js.map +1 -1
  22. package/dist/auth/auth.controller.d.ts +24 -8
  23. package/dist/auth/auth.controller.d.ts.map +1 -1
  24. package/dist/auth/auth.module.d.ts.map +1 -1
  25. package/dist/auth/auth.module.js +8 -1
  26. package/dist/auth/auth.module.js.map +1 -1
  27. package/dist/auth/auth.service.d.ts +72 -25
  28. package/dist/auth/auth.service.d.ts.map +1 -1
  29. package/dist/auth/auth.service.js +41 -4
  30. package/dist/auth/auth.service.js.map +1 -1
  31. package/dist/auth/guards/auth.guard.d.ts +3 -1
  32. package/dist/auth/guards/auth.guard.d.ts.map +1 -1
  33. package/dist/auth/guards/auth.guard.js +12 -3
  34. package/dist/auth/guards/auth.guard.js.map +1 -1
  35. package/dist/authorize/authorize.controller.d.ts +29 -5
  36. package/dist/authorize/authorize.controller.d.ts.map +1 -1
  37. package/dist/authorize/authorize.controller.js +120 -13
  38. package/dist/authorize/authorize.controller.js.map +1 -1
  39. package/dist/authorize/authorize.errors.d.ts +34 -0
  40. package/dist/authorize/authorize.errors.d.ts.map +1 -0
  41. package/dist/authorize/authorize.errors.js +37 -0
  42. package/dist/authorize/authorize.errors.js.map +1 -0
  43. package/dist/authorize/authorize.module.d.ts.map +1 -1
  44. package/dist/authorize/authorize.module.js +6 -1
  45. package/dist/authorize/authorize.module.js.map +1 -1
  46. package/dist/authorize/authorize.service.d.ts +77 -3
  47. package/dist/authorize/authorize.service.d.ts.map +1 -1
  48. package/dist/authorize/authorize.service.js +212 -21
  49. package/dist/authorize/authorize.service.js.map +1 -1
  50. package/dist/authorize/dto/authorize-info.dto.d.ts +10 -1
  51. package/dist/authorize/dto/authorize-info.dto.d.ts.map +1 -1
  52. package/dist/authorize/dto/authorize-info.dto.js +16 -1
  53. package/dist/authorize/dto/authorize-info.dto.js.map +1 -1
  54. package/dist/authorize/dto/consent.dto.d.ts +10 -1
  55. package/dist/authorize/dto/consent.dto.d.ts.map +1 -1
  56. package/dist/authorize/dto/consent.dto.js +16 -1
  57. package/dist/authorize/dto/consent.dto.js.map +1 -1
  58. package/dist/authorize/dto/token.dto.d.ts +12 -0
  59. package/dist/authorize/dto/token.dto.d.ts.map +1 -1
  60. package/dist/authorize/dto/token.dto.js +21 -1
  61. package/dist/authorize/dto/token.dto.js.map +1 -1
  62. package/dist/authorize/oauth-exception.filter.d.ts +17 -0
  63. package/dist/authorize/oauth-exception.filter.d.ts.map +1 -0
  64. package/dist/authorize/oauth-exception.filter.js +54 -0
  65. package/dist/authorize/oauth-exception.filter.js.map +1 -0
  66. package/dist/authorize/oauth-metadata.service.d.ts +39 -0
  67. package/dist/authorize/oauth-metadata.service.d.ts.map +1 -0
  68. package/dist/authorize/oauth-metadata.service.js +81 -0
  69. package/dist/authorize/oauth-metadata.service.js.map +1 -0
  70. package/dist/authorize/well-known.controller.d.ts +67 -0
  71. package/dist/authorize/well-known.controller.d.ts.map +1 -0
  72. package/dist/authorize/well-known.controller.js +126 -0
  73. package/dist/authorize/well-known.controller.js.map +1 -0
  74. package/dist/captcha/captcha.service.d.ts +32 -2
  75. package/dist/captcha/captcha.service.d.ts.map +1 -1
  76. package/dist/captcha/captcha.service.js +85 -12
  77. package/dist/captcha/captcha.service.js.map +1 -1
  78. package/dist/challenge/challenge.service.d.ts +2 -2
  79. package/dist/core.module.d.ts.map +1 -1
  80. package/dist/core.module.js +9 -0
  81. package/dist/core.module.js.map +1 -1
  82. package/dist/dashboard/dashboard/dashboard.controller.d.ts +9 -9
  83. package/dist/dashboard/dashboard/dashboard.service.d.ts +9 -9
  84. package/dist/dashboard/dashboard-component/dashboard-component.controller.d.ts +3 -3
  85. package/dist/dashboard/dashboard-component/dashboard-component.service.d.ts +3 -3
  86. package/dist/dashboard/dashboard-component-role/dashboard-component-role.controller.d.ts +3 -3
  87. package/dist/dashboard/dashboard-component-role/dashboard-component-role.service.d.ts +3 -3
  88. package/dist/dashboard/dashboard-component-role/dashboard-component-role.service.d.ts.map +1 -1
  89. package/dist/dashboard/dashboard-component-role/dashboard-component-role.service.js +2 -4
  90. package/dist/dashboard/dashboard-component-role/dashboard-component-role.service.js.map +1 -1
  91. package/dist/dashboard/dashboard-component-role/dashboard-component-role.sort.d.ts +8 -0
  92. package/dist/dashboard/dashboard-component-role/dashboard-component-role.sort.d.ts.map +1 -0
  93. package/dist/dashboard/dashboard-component-role/dashboard-component-role.sort.js +18 -0
  94. package/dist/dashboard/dashboard-component-role/dashboard-component-role.sort.js.map +1 -0
  95. package/dist/dashboard/dashboard-item/dashboard-item.service.d.ts.map +1 -1
  96. package/dist/dashboard/dashboard-item/dashboard-item.service.js +2 -4
  97. package/dist/dashboard/dashboard-item/dashboard-item.service.js.map +1 -1
  98. package/dist/dashboard/dashboard-item/dashboard-item.sort.d.ts +9 -0
  99. package/dist/dashboard/dashboard-item/dashboard-item.sort.d.ts.map +1 -0
  100. package/dist/dashboard/dashboard-item/dashboard-item.sort.js +19 -0
  101. package/dist/dashboard/dashboard-item/dashboard-item.sort.js.map +1 -0
  102. package/dist/dashboard/dashboard-role/dashboard-role.controller.d.ts +3 -3
  103. package/dist/dashboard/dashboard-role/dashboard-role.service.d.ts +3 -3
  104. package/dist/dashboard/dashboard-role/dashboard-role.service.d.ts.map +1 -1
  105. package/dist/dashboard/dashboard-role/dashboard-role.service.js +2 -4
  106. package/dist/dashboard/dashboard-role/dashboard-role.service.js.map +1 -1
  107. package/dist/dashboard/dashboard-role/dashboard-role.sort.d.ts +8 -0
  108. package/dist/dashboard/dashboard-role/dashboard-role.sort.d.ts.map +1 -0
  109. package/dist/dashboard/dashboard-role/dashboard-role.sort.js +16 -0
  110. package/dist/dashboard/dashboard-role/dashboard-role.sort.js.map +1 -0
  111. package/dist/document-kit/document-kit.module.d.ts +3 -0
  112. package/dist/document-kit/document-kit.module.d.ts.map +1 -0
  113. package/dist/document-kit/document-kit.module.js +24 -0
  114. package/dist/document-kit/document-kit.module.js.map +1 -0
  115. package/dist/document-kit/document-kit.registry.d.ts +55 -0
  116. package/dist/document-kit/document-kit.registry.d.ts.map +1 -0
  117. package/dist/document-kit/document-kit.registry.js +91 -0
  118. package/dist/document-kit/document-kit.registry.js.map +1 -0
  119. package/dist/document-kit/document-kit.service.d.ts +49 -0
  120. package/dist/document-kit/document-kit.service.d.ts.map +1 -0
  121. package/dist/document-kit/document-kit.service.js +135 -0
  122. package/dist/document-kit/document-kit.service.js.map +1 -0
  123. package/dist/file/file-upload-ticket.service.d.ts +160 -0
  124. package/dist/file/file-upload-ticket.service.d.ts.map +1 -0
  125. package/dist/file/file-upload-ticket.service.js +382 -0
  126. package/dist/file/file-upload-ticket.service.js.map +1 -0
  127. package/dist/file/file.controller.d.ts +24 -1
  128. package/dist/file/file.controller.d.ts.map +1 -1
  129. package/dist/file/file.controller.js +63 -2
  130. package/dist/file/file.controller.js.map +1 -1
  131. package/dist/file/file.module.d.ts.map +1 -1
  132. package/dist/file/file.module.js +14 -2
  133. package/dist/file/file.module.js.map +1 -1
  134. package/dist/file/file.service.d.ts +197 -7
  135. package/dist/file/file.service.d.ts.map +1 -1
  136. package/dist/file/file.service.js +438 -78
  137. package/dist/file/file.service.js.map +1 -1
  138. package/dist/file/filename-encoding.util.d.ts +24 -0
  139. package/dist/file/filename-encoding.util.d.ts.map +1 -0
  140. package/dist/file/filename-encoding.util.js +63 -0
  141. package/dist/file/filename-encoding.util.js.map +1 -0
  142. package/dist/file/image-optimization.service.d.ts +27 -0
  143. package/dist/file/image-optimization.service.d.ts.map +1 -1
  144. package/dist/file/image-optimization.service.js +63 -14
  145. package/dist/file/image-optimization.service.js.map +1 -1
  146. package/dist/file/mcp-file-source.schema.d.ts +33 -0
  147. package/dist/file/mcp-file-source.schema.d.ts.map +1 -0
  148. package/dist/file/mcp-file-source.schema.js +78 -0
  149. package/dist/file/mcp-file-source.schema.js.map +1 -0
  150. package/dist/file/mcp-file-source.service.d.ts +124 -0
  151. package/dist/file/mcp-file-source.service.d.ts.map +1 -0
  152. package/dist/file/mcp-file-source.service.js +262 -0
  153. package/dist/file/mcp-file-source.service.js.map +1 -0
  154. package/dist/file/mimetype-sniff.util.d.ts +62 -0
  155. package/dist/file/mimetype-sniff.util.d.ts.map +1 -0
  156. package/dist/file/mimetype-sniff.util.js +226 -0
  157. package/dist/file/mimetype-sniff.util.js.map +1 -0
  158. package/dist/file/remote-fetch.util.d.ts +35 -0
  159. package/dist/file/remote-fetch.util.d.ts.map +1 -0
  160. package/dist/file/remote-fetch.util.js +236 -0
  161. package/dist/file/remote-fetch.util.js.map +1 -0
  162. package/dist/impersonation/dto/start-impersonation.dto.d.ts +4 -1
  163. package/dist/impersonation/dto/start-impersonation.dto.d.ts.map +1 -1
  164. package/dist/impersonation/dto/start-impersonation.dto.js +1 -1
  165. package/dist/impersonation/dto/start-impersonation.dto.js.map +1 -1
  166. package/dist/impersonation/impersonation.service.d.ts +8 -3
  167. package/dist/impersonation/impersonation.service.d.ts.map +1 -1
  168. package/dist/impersonation/impersonation.service.js +14 -4
  169. package/dist/impersonation/impersonation.service.js.map +1 -1
  170. package/dist/incident/incident.controller.d.ts +2 -1
  171. package/dist/incident/incident.controller.d.ts.map +1 -1
  172. package/dist/incident/incident.controller.js +10 -6
  173. package/dist/incident/incident.controller.js.map +1 -1
  174. package/dist/incident/incident.service.d.ts +2 -0
  175. package/dist/incident/incident.service.d.ts.map +1 -1
  176. package/dist/incident/incident.service.js +4 -0
  177. package/dist/incident/incident.service.js.map +1 -1
  178. package/dist/index.d.ts +22 -0
  179. package/dist/index.d.ts.map +1 -1
  180. package/dist/index.js +22 -0
  181. package/dist/index.js.map +1 -1
  182. package/dist/integration-profile/integration-profile.secrets.d.ts.map +1 -1
  183. package/dist/integration-profile/integration-profile.secrets.js +28 -0
  184. package/dist/integration-profile/integration-profile.secrets.js.map +1 -1
  185. package/dist/integration-profile/integration-profile.service.d.ts +0 -13
  186. package/dist/integration-profile/integration-profile.service.d.ts.map +1 -1
  187. package/dist/integration-profile/integration-profile.service.js +5 -40
  188. package/dist/integration-profile/integration-profile.service.js.map +1 -1
  189. package/dist/integration-profile/integration-profile.utils.js +5 -5
  190. package/dist/integration-profile/integration-profile.utils.js.map +1 -1
  191. package/dist/integration-profile/testers/ai.testers.d.ts.map +1 -1
  192. package/dist/integration-profile/testers/ai.testers.js +46 -8
  193. package/dist/integration-profile/testers/ai.testers.js.map +1 -1
  194. package/dist/integration-profile/testers/index.d.ts.map +1 -1
  195. package/dist/integration-profile/testers/index.js +2 -0
  196. package/dist/integration-profile/testers/index.js.map +1 -1
  197. package/dist/integration-profile/testers/shipping.testers.d.ts +3 -0
  198. package/dist/integration-profile/testers/shipping.testers.d.ts.map +1 -0
  199. package/dist/integration-profile/testers/shipping.testers.js +71 -0
  200. package/dist/integration-profile/testers/shipping.testers.js.map +1 -0
  201. package/dist/locale/locale.controller.d.ts +1 -1
  202. package/dist/locale/locale.service.d.ts +1 -1
  203. package/dist/mail/dto/send.dto.d.ts +6 -1
  204. package/dist/mail/dto/send.dto.d.ts.map +1 -1
  205. package/dist/mail/dto/send.dto.js.map +1 -1
  206. package/dist/mail/mail.service.d.ts +9 -0
  207. package/dist/mail/mail.service.d.ts.map +1 -1
  208. package/dist/mail/mail.service.js +34 -14
  209. package/dist/mail/mail.service.js.map +1 -1
  210. package/dist/mail-sent/mail-sent.controller.d.ts +1 -1
  211. package/dist/mail-sent/mail-sent.service.d.ts +1 -1
  212. package/dist/mail-sent/mail-sent.service.d.ts.map +1 -1
  213. package/dist/mail-sent/mail-sent.service.js +2 -1
  214. package/dist/mail-sent/mail-sent.service.js.map +1 -1
  215. package/dist/mail-sent/mail-sent.sort.d.ts +9 -0
  216. package/dist/mail-sent/mail-sent.sort.d.ts.map +1 -0
  217. package/dist/mail-sent/mail-sent.sort.js +19 -0
  218. package/dist/mail-sent/mail-sent.sort.js.map +1 -0
  219. package/dist/mcp/filters/mcp-challenge.filter.d.ts +20 -0
  220. package/dist/mcp/filters/mcp-challenge.filter.d.ts.map +1 -0
  221. package/dist/mcp/filters/mcp-challenge.filter.js +69 -0
  222. package/dist/mcp/filters/mcp-challenge.filter.js.map +1 -0
  223. package/dist/mcp/guards/mcp-auth.guard.d.ts +4 -1
  224. package/dist/mcp/guards/mcp-auth.guard.d.ts.map +1 -1
  225. package/dist/mcp/guards/mcp-auth.guard.js +19 -5
  226. package/dist/mcp/guards/mcp-auth.guard.js.map +1 -1
  227. package/dist/mcp/guards/mcp-permission.guard.d.ts +25 -3
  228. package/dist/mcp/guards/mcp-permission.guard.d.ts.map +1 -1
  229. package/dist/mcp/guards/mcp-permission.guard.js +46 -26
  230. package/dist/mcp/guards/mcp-permission.guard.js.map +1 -1
  231. package/dist/mcp/mcp-audit.service.d.ts +17 -0
  232. package/dist/mcp/mcp-audit.service.d.ts.map +1 -1
  233. package/dist/mcp/mcp-audit.service.js +32 -3
  234. package/dist/mcp/mcp-audit.service.js.map +1 -1
  235. package/dist/mcp/mcp-permission.service.d.ts +64 -0
  236. package/dist/mcp/mcp-permission.service.d.ts.map +1 -0
  237. package/dist/mcp/mcp-permission.service.js +178 -0
  238. package/dist/mcp/mcp-permission.service.js.map +1 -0
  239. package/dist/mcp/mcp-server.service.d.ts +3 -1
  240. package/dist/mcp/mcp-server.service.d.ts.map +1 -1
  241. package/dist/mcp/mcp-server.service.js +36 -15
  242. package/dist/mcp/mcp-server.service.js.map +1 -1
  243. package/dist/mcp/mcp.controller.d.ts.map +1 -1
  244. package/dist/mcp/mcp.controller.js +10 -2
  245. package/dist/mcp/mcp.controller.js.map +1 -1
  246. package/dist/mcp/mcp.module.d.ts.map +1 -1
  247. package/dist/mcp/mcp.module.js +7 -1
  248. package/dist/mcp/mcp.module.js.map +1 -1
  249. package/dist/mcp/tools/core-access-log.mcp-tools.d.ts +17 -0
  250. package/dist/mcp/tools/core-access-log.mcp-tools.d.ts.map +1 -0
  251. package/dist/mcp/tools/core-access-log.mcp-tools.js +74 -0
  252. package/dist/mcp/tools/core-access-log.mcp-tools.js.map +1 -0
  253. package/dist/mcp/tools/core-ai.mcp-tools.js +2 -9
  254. package/dist/mcp/tools/core-ai.mcp-tools.js.map +1 -1
  255. package/dist/mcp/tools/core-dashboard-items.mcp-tools.js +1 -1
  256. package/dist/mcp/tools/core-dashboard-items.mcp-tools.js.map +1 -1
  257. package/dist/mcp/tools/core-dashboard.mcp-tools.js +2 -9
  258. package/dist/mcp/tools/core-dashboard.mcp-tools.js.map +1 -1
  259. package/dist/mcp/tools/core-event-webhooks.mcp-tools.d.ts.map +1 -1
  260. package/dist/mcp/tools/core-event-webhooks.mcp-tools.js +2 -10
  261. package/dist/mcp/tools/core-event-webhooks.mcp-tools.js.map +1 -1
  262. package/dist/mcp/tools/core-files.mcp-tools.d.ts +17 -5
  263. package/dist/mcp/tools/core-files.mcp-tools.d.ts.map +1 -1
  264. package/dist/mcp/tools/core-files.mcp-tools.js +186 -24
  265. package/dist/mcp/tools/core-files.mcp-tools.js.map +1 -1
  266. package/dist/mcp/tools/core-integration-events.mcp-tools.js +2 -9
  267. package/dist/mcp/tools/core-integration-events.mcp-tools.js.map +1 -1
  268. package/dist/mcp/tools/core-mail-sent.mcp-tools.js +2 -14
  269. package/dist/mcp/tools/core-mail-sent.mcp-tools.js.map +1 -1
  270. package/dist/mcp/tools/core-mail.mcp-tools.js +2 -9
  271. package/dist/mcp/tools/core-mail.mcp-tools.js.map +1 -1
  272. package/dist/mcp/tools/core-menus.mcp-tools.d.ts.map +1 -1
  273. package/dist/mcp/tools/core-menus.mcp-tools.js +2 -10
  274. package/dist/mcp/tools/core-menus.mcp-tools.js.map +1 -1
  275. package/dist/mcp/tools/core-notifications.mcp-tools.d.ts.map +1 -1
  276. package/dist/mcp/tools/core-notifications.mcp-tools.js +0 -1
  277. package/dist/mcp/tools/core-notifications.mcp-tools.js.map +1 -1
  278. package/dist/mcp/tools/core-roles.mcp-tools.d.ts.map +1 -1
  279. package/dist/mcp/tools/core-roles.mcp-tools.js +2 -13
  280. package/dist/mcp/tools/core-roles.mcp-tools.js.map +1 -1
  281. package/dist/mcp/tools/core-routes.mcp-tools.d.ts.map +1 -1
  282. package/dist/mcp/tools/core-routes.mcp-tools.js +2 -11
  283. package/dist/mcp/tools/core-routes.mcp-tools.js.map +1 -1
  284. package/dist/mcp/tools/core-screens.mcp-tools.d.ts.map +1 -1
  285. package/dist/mcp/tools/core-screens.mcp-tools.js +2 -11
  286. package/dist/mcp/tools/core-screens.mcp-tools.js.map +1 -1
  287. package/dist/mcp/tools/core-sessions.mcp-tools.d.ts.map +1 -1
  288. package/dist/mcp/tools/core-sessions.mcp-tools.js +0 -2
  289. package/dist/mcp/tools/core-sessions.mcp-tools.js.map +1 -1
  290. package/dist/mcp/tools/core-settings.mcp-tools.d.ts.map +1 -1
  291. package/dist/mcp/tools/core-settings.mcp-tools.js +2 -10
  292. package/dist/mcp/tools/core-settings.mcp-tools.js.map +1 -1
  293. package/dist/mcp/tools/core-users.mcp-tools.js +2 -9
  294. package/dist/mcp/tools/core-users.mcp-tools.js.map +1 -1
  295. package/dist/mcp/tools/core-webhooks.mcp-tools.d.ts.map +1 -1
  296. package/dist/mcp/tools/core-webhooks.mcp-tools.js +2 -10
  297. package/dist/mcp/tools/core-webhooks.mcp-tools.js.map +1 -1
  298. package/dist/mcp/types/mcp-context.type.d.ts +9 -0
  299. package/dist/mcp/types/mcp-context.type.d.ts.map +1 -1
  300. package/dist/mcp-chat/mcp-chat.service.d.ts.map +1 -1
  301. package/dist/mcp-chat/mcp-chat.service.js +8 -0
  302. package/dist/mcp-chat/mcp-chat.service.js.map +1 -1
  303. package/dist/meeting/meeting-provider.registry.d.ts +187 -0
  304. package/dist/meeting/meeting-provider.registry.d.ts.map +1 -1
  305. package/dist/meeting/meeting-provider.registry.js.map +1 -1
  306. package/dist/meeting/meeting.constants.d.ts +70 -0
  307. package/dist/meeting/meeting.constants.d.ts.map +1 -1
  308. package/dist/meeting/meeting.constants.js +9 -1
  309. package/dist/meeting/meeting.constants.js.map +1 -1
  310. package/dist/menu/menu.service.d.ts.map +1 -1
  311. package/dist/menu/menu.service.js +29 -9
  312. package/dist/menu/menu.service.js.map +1 -1
  313. package/dist/message-template/dto/update-message-template.dto.d.ts +18 -0
  314. package/dist/message-template/dto/update-message-template.dto.d.ts.map +1 -0
  315. package/dist/message-template/dto/update-message-template.dto.js +38 -0
  316. package/dist/message-template/dto/update-message-template.dto.js.map +1 -0
  317. package/dist/message-template/message-template-admin.service.d.ts +70 -0
  318. package/dist/message-template/message-template-admin.service.d.ts.map +1 -0
  319. package/dist/message-template/message-template-admin.service.js +226 -0
  320. package/dist/message-template/message-template-admin.service.js.map +1 -0
  321. package/dist/message-template/message-template.controller.d.ts +29 -0
  322. package/dist/message-template/message-template.controller.d.ts.map +1 -0
  323. package/dist/message-template/message-template.controller.js +101 -0
  324. package/dist/message-template/message-template.controller.js.map +1 -0
  325. package/dist/message-template/message-template.module.d.ts +10 -0
  326. package/dist/message-template/message-template.module.d.ts.map +1 -0
  327. package/dist/message-template/message-template.module.js +33 -0
  328. package/dist/message-template/message-template.module.js.map +1 -0
  329. package/dist/message-template/message-template.registry.d.ts +55 -0
  330. package/dist/message-template/message-template.registry.d.ts.map +1 -0
  331. package/dist/message-template/message-template.registry.js +64 -0
  332. package/dist/message-template/message-template.registry.js.map +1 -0
  333. package/dist/message-template/message-template.service.d.ts +59 -0
  334. package/dist/message-template/message-template.service.d.ts.map +1 -0
  335. package/dist/message-template/message-template.service.js +166 -0
  336. package/dist/message-template/message-template.service.js.map +1 -0
  337. package/dist/notification/notification.constants.d.ts +11 -0
  338. package/dist/notification/notification.constants.d.ts.map +1 -0
  339. package/dist/notification/notification.constants.js +14 -0
  340. package/dist/notification/notification.constants.js.map +1 -0
  341. package/dist/notification/notification.controller.d.ts +20 -20
  342. package/dist/notification/notification.module.d.ts.map +1 -1
  343. package/dist/notification/notification.module.js +3 -0
  344. package/dist/notification/notification.module.js.map +1 -1
  345. package/dist/notification/notification.service.d.ts +33 -21
  346. package/dist/notification/notification.service.d.ts.map +1 -1
  347. package/dist/notification/notification.service.js +36 -2
  348. package/dist/notification/notification.service.js.map +1 -1
  349. package/dist/oauth/oauth-token-broker.service.d.ts +50 -1
  350. package/dist/oauth/oauth-token-broker.service.d.ts.map +1 -1
  351. package/dist/oauth/oauth-token-broker.service.js +105 -3
  352. package/dist/oauth/oauth-token-broker.service.js.map +1 -1
  353. package/dist/oauth/oauth.controller.d.ts +4 -6
  354. package/dist/oauth/oauth.controller.d.ts.map +1 -1
  355. package/dist/oauth/oauth.controller.js +0 -1
  356. package/dist/oauth/oauth.controller.js.map +1 -1
  357. package/dist/oauth/oauth.errors.d.ts +15 -1
  358. package/dist/oauth/oauth.errors.d.ts.map +1 -1
  359. package/dist/oauth/oauth.errors.js +9 -1
  360. package/dist/oauth/oauth.errors.js.map +1 -1
  361. package/dist/oauth/oauth.module.d.ts.map +1 -1
  362. package/dist/oauth/oauth.module.js +6 -1
  363. package/dist/oauth/oauth.module.js.map +1 -1
  364. package/dist/oauth/oauth.service.d.ts +25 -5
  365. package/dist/oauth/oauth.service.d.ts.map +1 -1
  366. package/dist/oauth/oauth.service.js +63 -27
  367. package/dist/oauth/oauth.service.js.map +1 -1
  368. package/dist/oauth/providers/abstract.provider.d.ts +10 -0
  369. package/dist/oauth/providers/abstract.provider.d.ts.map +1 -1
  370. package/dist/oauth/providers/abstract.provider.js +39 -12
  371. package/dist/oauth/providers/abstract.provider.js.map +1 -1
  372. package/dist/oauth/providers/github.provider.d.ts +1 -1
  373. package/dist/oauth/providers/github.provider.d.ts.map +1 -1
  374. package/dist/oauth/providers/github.provider.js +48 -22
  375. package/dist/oauth/providers/github.provider.js.map +1 -1
  376. package/dist/oauth/providers/microsoft-entra-id.provider.d.ts +6 -0
  377. package/dist/oauth/providers/microsoft-entra-id.provider.d.ts.map +1 -1
  378. package/dist/oauth/providers/microsoft-entra-id.provider.js +36 -4
  379. package/dist/oauth/providers/microsoft-entra-id.provider.js.map +1 -1
  380. package/dist/observability/monitored-cron.d.ts +29 -12
  381. package/dist/observability/monitored-cron.d.ts.map +1 -1
  382. package/dist/observability/monitored-cron.js +131 -46
  383. package/dist/observability/monitored-cron.js.map +1 -1
  384. package/dist/pairing/pairing.service.d.ts +6 -2
  385. package/dist/pairing/pairing.service.d.ts.map +1 -1
  386. package/dist/pdf/document/charts/chart-bar.d.ts +24 -0
  387. package/dist/pdf/document/charts/chart-bar.d.ts.map +1 -0
  388. package/dist/pdf/document/charts/chart-bar.js +117 -0
  389. package/dist/pdf/document/charts/chart-bar.js.map +1 -0
  390. package/dist/pdf/document/charts/chart-donut.d.ts +16 -0
  391. package/dist/pdf/document/charts/chart-donut.d.ts.map +1 -0
  392. package/dist/pdf/document/charts/chart-donut.js +89 -0
  393. package/dist/pdf/document/charts/chart-donut.js.map +1 -0
  394. package/dist/pdf/document/charts/chart-gauge.d.ts +15 -0
  395. package/dist/pdf/document/charts/chart-gauge.d.ts.map +1 -0
  396. package/dist/pdf/document/charts/chart-gauge.js +60 -0
  397. package/dist/pdf/document/charts/chart-gauge.js.map +1 -0
  398. package/dist/pdf/document/charts/chart-line.d.ts +29 -0
  399. package/dist/pdf/document/charts/chart-line.d.ts.map +1 -0
  400. package/dist/pdf/document/charts/chart-line.js +89 -0
  401. package/dist/pdf/document/charts/chart-line.js.map +1 -0
  402. package/dist/pdf/document/charts/chart-primitives.d.ts +64 -0
  403. package/dist/pdf/document/charts/chart-primitives.d.ts.map +1 -0
  404. package/dist/pdf/document/charts/chart-primitives.js +110 -0
  405. package/dist/pdf/document/charts/chart-primitives.js.map +1 -0
  406. package/dist/pdf/document/charts/chart-radar.d.ts +13 -0
  407. package/dist/pdf/document/charts/chart-radar.d.ts.map +1 -0
  408. package/dist/pdf/document/charts/chart-radar.js +83 -0
  409. package/dist/pdf/document/charts/chart-radar.js.map +1 -0
  410. package/dist/pdf/document/charts/chart-scale.d.ts +39 -0
  411. package/dist/pdf/document/charts/chart-scale.d.ts.map +1 -0
  412. package/dist/pdf/document/charts/chart-scale.js +118 -0
  413. package/dist/pdf/document/charts/chart-scale.js.map +1 -0
  414. package/dist/pdf/document/charts/index.d.ts +8 -0
  415. package/dist/pdf/document/charts/index.d.ts.map +1 -0
  416. package/dist/pdf/document/charts/index.js +24 -0
  417. package/dist/pdf/document/charts/index.js.map +1 -0
  418. package/dist/pdf/document/index.d.ts +8 -0
  419. package/dist/pdf/document/index.d.ts.map +1 -0
  420. package/dist/pdf/document/index.js +24 -0
  421. package/dist/pdf/document/index.js.map +1 -0
  422. package/dist/pdf/document/pdf-document.chrome.d.ts +20 -0
  423. package/dist/pdf/document/pdf-document.chrome.d.ts.map +1 -0
  424. package/dist/pdf/document/pdf-document.chrome.js +36 -0
  425. package/dist/pdf/document/pdf-document.chrome.js.map +1 -0
  426. package/dist/pdf/document/pdf-document.css.d.ts +20 -0
  427. package/dist/pdf/document/pdf-document.css.d.ts.map +1 -0
  428. package/dist/pdf/document/pdf-document.css.js +239 -0
  429. package/dist/pdf/document/pdf-document.css.js.map +1 -0
  430. package/dist/pdf/document/pdf-document.renderer.d.ts +10 -0
  431. package/dist/pdf/document/pdf-document.renderer.d.ts.map +1 -0
  432. package/dist/pdf/document/pdf-document.renderer.js +153 -0
  433. package/dist/pdf/document/pdf-document.renderer.js.map +1 -0
  434. package/dist/pdf/document/pdf-document.service.d.ts +27 -0
  435. package/dist/pdf/document/pdf-document.service.d.ts.map +1 -0
  436. package/dist/pdf/document/pdf-document.service.js +81 -0
  437. package/dist/pdf/document/pdf-document.service.js.map +1 -0
  438. package/dist/pdf/document/pdf-document.theme.d.ts +41 -0
  439. package/dist/pdf/document/pdf-document.theme.d.ts.map +1 -0
  440. package/dist/pdf/document/pdf-document.theme.js +105 -0
  441. package/dist/pdf/document/pdf-document.theme.js.map +1 -0
  442. package/dist/pdf/document/pdf-document.types.d.ts +108 -0
  443. package/dist/pdf/document/pdf-document.types.d.ts.map +1 -0
  444. package/dist/pdf/document/pdf-document.types.js +18 -0
  445. package/dist/pdf/document/pdf-document.types.js.map +1 -0
  446. package/dist/pdf/pdf.module.d.ts.map +1 -1
  447. package/dist/pdf/pdf.module.js +3 -2
  448. package/dist/pdf/pdf.module.js.map +1 -1
  449. package/dist/pdf/pdf.service.d.ts +69 -1
  450. package/dist/pdf/pdf.service.d.ts.map +1 -1
  451. package/dist/pdf/pdf.service.js +164 -63
  452. package/dist/pdf/pdf.service.js.map +1 -1
  453. package/dist/pdf/templates/commercial-proposal.template.d.ts +96 -0
  454. package/dist/pdf/templates/commercial-proposal.template.d.ts.map +1 -0
  455. package/dist/pdf/templates/commercial-proposal.template.js +276 -0
  456. package/dist/pdf/templates/commercial-proposal.template.js.map +1 -0
  457. package/dist/profile/dto/change-password.dto.d.ts.map +1 -1
  458. package/dist/profile/dto/change-password.dto.js +4 -6
  459. package/dist/profile/dto/change-password.dto.js.map +1 -1
  460. package/dist/profile/profile.controller.d.ts +1 -1
  461. package/dist/profile/profile.service.d.ts +1 -1
  462. package/dist/profile/profile.service.d.ts.map +1 -1
  463. package/dist/profile/profile.service.js +9 -3
  464. package/dist/profile/profile.service.js.map +1 -1
  465. package/dist/realtime/realtime-tick.coalescer.d.ts +34 -0
  466. package/dist/realtime/realtime-tick.coalescer.d.ts.map +1 -0
  467. package/dist/realtime/realtime-tick.coalescer.js +60 -0
  468. package/dist/realtime/realtime-tick.coalescer.js.map +1 -0
  469. package/dist/realtime/realtime.service.d.ts +2 -0
  470. package/dist/realtime/realtime.service.d.ts.map +1 -1
  471. package/dist/realtime/realtime.service.js +22 -2
  472. package/dist/realtime/realtime.service.js.map +1 -1
  473. package/dist/redis/redis-kv.service.d.ts +90 -0
  474. package/dist/redis/redis-kv.service.d.ts.map +1 -0
  475. package/dist/redis/redis-kv.service.js +247 -0
  476. package/dist/redis/redis-kv.service.js.map +1 -0
  477. package/dist/redis/redis-master.d.ts +29 -0
  478. package/dist/redis/redis-master.d.ts.map +1 -0
  479. package/dist/redis/redis-master.js +81 -0
  480. package/dist/redis/redis-master.js.map +1 -0
  481. package/dist/redis/redis-pubsub.d.ts +12 -0
  482. package/dist/redis/redis-pubsub.d.ts.map +1 -1
  483. package/dist/redis/redis-pubsub.js +25 -2
  484. package/dist/redis/redis-pubsub.js.map +1 -1
  485. package/dist/redis/redis.module.d.ts +11 -0
  486. package/dist/redis/redis.module.d.ts.map +1 -0
  487. package/dist/redis/redis.module.js +30 -0
  488. package/dist/redis/redis.module.js.map +1 -0
  489. package/dist/session/session.controller.d.ts +6 -2
  490. package/dist/session/session.controller.d.ts.map +1 -1
  491. package/dist/session/session.service.d.ts +118 -15
  492. package/dist/session/session.service.d.ts.map +1 -1
  493. package/dist/session/session.service.js +251 -77
  494. package/dist/session/session.service.js.map +1 -1
  495. package/dist/setting/favicon.controller.d.ts +26 -0
  496. package/dist/setting/favicon.controller.d.ts.map +1 -0
  497. package/dist/setting/favicon.controller.js +130 -0
  498. package/dist/setting/favicon.controller.js.map +1 -0
  499. package/dist/setting/setting.controller.d.ts +5 -0
  500. package/dist/setting/setting.controller.d.ts.map +1 -1
  501. package/dist/setting/setting.module.d.ts.map +1 -1
  502. package/dist/setting/setting.module.js +2 -1
  503. package/dist/setting/setting.module.js.map +1 -1
  504. package/dist/setting/setting.service.d.ts +7 -0
  505. package/dist/setting/setting.service.d.ts.map +1 -1
  506. package/dist/setting/setting.service.js +38 -3
  507. package/dist/setting/setting.service.js.map +1 -1
  508. package/dist/task/task.service.d.ts +17 -0
  509. package/dist/task/task.service.d.ts.map +1 -1
  510. package/dist/task/task.service.js +48 -13
  511. package/dist/task/task.service.js.map +1 -1
  512. package/dist/token/token.service.d.ts +19 -1
  513. package/dist/token/token.service.d.ts.map +1 -1
  514. package/dist/token/token.service.js +39 -2
  515. package/dist/token/token.service.js.map +1 -1
  516. package/dist/user/user-credential.util.d.ts +10 -0
  517. package/dist/user/user-credential.util.d.ts.map +1 -1
  518. package/dist/user/user-credential.util.js +14 -1
  519. package/dist/user/user-credential.util.js.map +1 -1
  520. package/dist/user/user.service.d.ts +12 -4
  521. package/dist/user/user.service.d.ts.map +1 -1
  522. package/dist/user/user.service.js +2 -11
  523. package/dist/user/user.service.js.map +1 -1
  524. package/dist/user/user.sort.d.ts +16 -0
  525. package/dist/user/user.sort.d.ts.map +1 -0
  526. package/dist/user/user.sort.js +25 -0
  527. package/dist/user/user.sort.js.map +1 -0
  528. package/dist/utils/abbreviate-name.d.ts +13 -0
  529. package/dist/utils/abbreviate-name.d.ts.map +1 -0
  530. package/dist/utils/abbreviate-name.js +42 -0
  531. package/dist/utils/abbreviate-name.js.map +1 -0
  532. package/dist/utils/date-range-query.dto.d.ts +11 -0
  533. package/dist/utils/date-range-query.dto.d.ts.map +1 -0
  534. package/dist/utils/date-range-query.dto.js +63 -0
  535. package/dist/utils/date-range-query.dto.js.map +1 -0
  536. package/dist/utils/date-range.d.ts +96 -0
  537. package/dist/utils/date-range.d.ts.map +1 -0
  538. package/dist/utils/date-range.js +172 -0
  539. package/dist/utils/date-range.js.map +1 -0
  540. package/dist/webhook-integration/webhook-utils.d.ts.map +1 -1
  541. package/dist/webhook-integration/webhook-utils.js +24 -0
  542. package/dist/webhook-integration/webhook-utils.js.map +1 -1
  543. package/dist/whatsapp-sender/whatsapp-recipients.d.ts +49 -0
  544. package/dist/whatsapp-sender/whatsapp-recipients.d.ts.map +1 -0
  545. package/dist/whatsapp-sender/whatsapp-recipients.js +66 -0
  546. package/dist/whatsapp-sender/whatsapp-recipients.js.map +1 -0
  547. package/dist/whatsapp-sender/whatsapp-sender.service.d.ts +25 -0
  548. package/dist/whatsapp-sender/whatsapp-sender.service.d.ts.map +1 -1
  549. package/dist/whatsapp-sender/whatsapp-sender.service.js +71 -7
  550. package/dist/whatsapp-sender/whatsapp-sender.service.js.map +1 -1
  551. package/hedhog/data/integration_provider.yaml +9 -0
  552. package/hedhog/data/integration_type.yaml +12 -0
  553. package/hedhog/data/locale.yaml +0 -1
  554. package/hedhog/data/mail.yaml +2 -2
  555. package/hedhog/data/mail_layout.yaml +6 -3
  556. package/hedhog/data/menu.yaml +25 -5
  557. package/hedhog/data/route.yaml +148 -0
  558. package/hedhog/data/setting_group.yaml +189 -3
  559. package/hedhog/frontend/app/access-log/page.tsx.ejs +47 -53
  560. package/hedhog/frontend/app/account/components/active-sessions.tsx.ejs +33 -8
  561. package/hedhog/frontend/app/account/components/mcp-tokens.tsx.ejs +54 -13
  562. package/hedhog/frontend/app/account/components/mfa-method-card.tsx.ejs +7 -1
  563. package/hedhog/frontend/app/account/components/recovery-codes-dialog.tsx.ejs +1 -0
  564. package/hedhog/frontend/app/account/components/tokens.tsx.ejs +47 -17
  565. package/hedhog/frontend/app/ai_agent/page.tsx.ejs +46 -5
  566. package/hedhog/frontend/app/ai_instruction/_components/ai-instruction-form.tsx.ejs +101 -30
  567. package/hedhog/frontend/app/ai_instruction/_components/ai-instruction-versions.tsx.ejs +24 -8
  568. package/hedhog/frontend/app/ai_instruction/page.tsx.ejs +80 -15
  569. package/hedhog/frontend/app/configurations/[slug]/components/image-optimization-action.tsx.ejs +166 -0
  570. package/hedhog/frontend/app/configurations/[slug]/components/setting-field.test.tsx.ejs +145 -45
  571. package/hedhog/frontend/app/configurations/[slug]/components/setting-field.tsx.ejs +99 -219
  572. package/hedhog/frontend/app/configurations/[slug]/page.tsx.ejs +19 -1
  573. package/hedhog/frontend/app/configurations/layout.tsx.ejs +19 -5
  574. package/hedhog/frontend/app/dashboard/[slug]/widget-renderer.tsx.ejs +2 -8
  575. package/hedhog/frontend/app/dashboard/components/dynamic-widget.tsx.ejs +3 -0
  576. package/hedhog/frontend/app/dashboard/components/widget-wrapper.tsx.ejs +4 -0
  577. package/hedhog/frontend/app/dashboard/dashboard-home-tabs.tsx.ejs +43 -44
  578. package/hedhog/frontend/app/dashboard/management/tabs/component-roles-tab.tsx.ejs +41 -3
  579. package/hedhog/frontend/app/dashboard/management/tabs/components-tab.tsx.ejs +42 -2
  580. package/hedhog/frontend/app/dashboard/management/tabs/dashboard-roles-tab.tsx.ejs +41 -3
  581. package/hedhog/frontend/app/dashboard/management/tabs/dashboards-tab.tsx.ejs +39 -4
  582. package/hedhog/frontend/app/dashboard/management/tabs/items-tab.tsx.ejs +42 -3
  583. package/hedhog/frontend/app/incidents/page.tsx.ejs +60 -31
  584. package/hedhog/frontend/app/integration/profiles/page.tsx.ejs +45 -5
  585. package/hedhog/frontend/app/integrations-webhooks/page.tsx.ejs +92 -15
  586. package/hedhog/frontend/app/mail/log/page.tsx.ejs +109 -61
  587. package/hedhog/frontend/app/mail/template/page.tsx.ejs +125 -23
  588. package/hedhog/frontend/app/mcp_chat/chat-components.tsx.ejs +13 -15
  589. package/hedhog/frontend/app/mcp_chat/page.tsx.ejs +116 -110
  590. package/hedhog/frontend/app/message-templates/_components/message-template-sheet.tsx.ejs +245 -0
  591. package/hedhog/frontend/app/message-templates/_lib/types.ts.ejs +24 -0
  592. package/hedhog/frontend/app/message-templates/page.tsx.ejs +182 -0
  593. package/hedhog/frontend/app/pages/_components/page-wizard-sheet.tsx.ejs +1 -0
  594. package/hedhog/frontend/app/pages/page.tsx.ejs +94 -9
  595. package/hedhog/frontend/app/roles/menus.tsx.ejs +4 -4
  596. package/hedhog/frontend/app/roles/routes.tsx.ejs +4 -4
  597. package/hedhog/frontend/app/roles/users.tsx.ejs +4 -4
  598. package/hedhog/frontend/app/setting-list/page.tsx.ejs +71 -9
  599. package/hedhog/frontend/app/users/page.tsx.ejs +77 -67
  600. package/hedhog/frontend/messages/en.json +237 -37
  601. package/hedhog/frontend/messages/pt.json +237 -37
  602. package/hedhog/table/cron_lock.yaml +17 -0
  603. package/hedhog/table/file.yaml +13 -1
  604. package/hedhog/table/file_upload_chunk.yaml +23 -0
  605. package/hedhog/table/file_upload_ticket.yaml +67 -0
  606. package/hedhog/table/mcp_tool_call_log.yaml +30 -22
  607. package/hedhog/table/message_template.yaml +33 -0
  608. package/hedhog/table/setting.yaml +8 -0
  609. package/hedhog/table/user_session.yaml +36 -1
  610. package/package.json +5 -3
  611. package/src/ai/ai-agent.sort.ts +21 -0
  612. package/src/ai/ai-attachment.fragments.spec.ts +56 -3
  613. package/src/ai/ai.service.responses.spec.ts +429 -0
  614. package/src/ai/ai.service.spec.ts +173 -1
  615. package/src/ai/ai.service.ts +473 -220
  616. package/src/ai-instruction/ai-instruction.service.ts +32 -28
  617. package/src/ai-instruction/ai-instruction.sort.ts +32 -0
  618. package/src/ai-instruction/ai-prompt-resolver.service.spec.ts +44 -0
  619. package/src/ai-instruction/ai-prompt-resolver.service.ts +29 -0
  620. package/src/auth/auth.module.ts +8 -1
  621. package/src/auth/auth.service.spec.ts +108 -1
  622. package/src/auth/auth.service.ts +59 -5
  623. package/src/auth/guards/auth.guard.ts +9 -1
  624. package/src/authorize/authorize.controller.ts +126 -11
  625. package/src/authorize/authorize.errors.ts +55 -0
  626. package/src/authorize/authorize.module.ts +6 -1
  627. package/src/authorize/authorize.service.spec.ts +379 -7
  628. package/src/authorize/authorize.service.ts +309 -23
  629. package/src/authorize/dto/authorize-info.dto.ts +21 -3
  630. package/src/authorize/dto/consent.dto.ts +21 -3
  631. package/src/authorize/dto/token.dto.ts +24 -2
  632. package/src/authorize/oauth-exception.filter.ts +58 -0
  633. package/src/authorize/oauth-metadata.service.ts +67 -0
  634. package/src/authorize/well-known.controller.spec.ts +84 -0
  635. package/src/authorize/well-known.controller.ts +96 -0
  636. package/src/captcha/captcha.service.spec.ts +211 -4
  637. package/src/captcha/captcha.service.ts +127 -10
  638. package/src/core.module.ts +9 -0
  639. package/src/dashboard/dashboard-component-role/dashboard-component-role.service.ts +2 -3
  640. package/src/dashboard/dashboard-component-role/dashboard-component-role.sort.ts +18 -0
  641. package/src/dashboard/dashboard-item/dashboard-item.service.ts +2 -3
  642. package/src/dashboard/dashboard-item/dashboard-item.sort.ts +19 -0
  643. package/src/dashboard/dashboard-role/dashboard-role.service.ts +2 -3
  644. package/src/dashboard/dashboard-role/dashboard-role.sort.ts +16 -0
  645. package/src/document-kit/document-kit.module.ts +12 -0
  646. package/src/document-kit/document-kit.registry.ts +125 -0
  647. package/src/document-kit/document-kit.service.spec.ts +156 -0
  648. package/src/document-kit/document-kit.service.ts +173 -0
  649. package/src/file/file-upload-ticket.service.spec.ts +422 -0
  650. package/src/file/file-upload-ticket.service.ts +513 -0
  651. package/src/file/file.controller.ts +65 -0
  652. package/src/file/file.module.ts +14 -2
  653. package/src/file/file.service.spec.ts +262 -1
  654. package/src/file/file.service.ts +505 -87
  655. package/src/file/filename-encoding.util.spec.ts +54 -0
  656. package/src/file/filename-encoding.util.ts +67 -0
  657. package/src/file/image-optimization.service.spec.ts +156 -19
  658. package/src/file/image-optimization.service.ts +106 -21
  659. package/src/file/mcp-file-source.schema.ts +86 -0
  660. package/src/file/mcp-file-source.service.spec.ts +473 -0
  661. package/src/file/mcp-file-source.service.ts +445 -0
  662. package/src/file/mimetype-sniff.util.spec.ts +126 -0
  663. package/src/file/mimetype-sniff.util.ts +265 -0
  664. package/src/file/remote-fetch.util.spec.ts +117 -0
  665. package/src/file/remote-fetch.util.ts +330 -0
  666. package/src/impersonation/dto/start-impersonation.dto.ts +5 -2
  667. package/src/impersonation/impersonation.service.spec.ts +24 -1
  668. package/src/impersonation/impersonation.service.ts +14 -4
  669. package/src/incident/incident.controller.ts +9 -1
  670. package/src/incident/incident.service.ts +7 -0
  671. package/src/index.ts +23 -1
  672. package/src/integration-profile/integration-profile.secrets.ts +28 -0
  673. package/src/integration-profile/integration-profile.service.ts +7 -64
  674. package/src/integration-profile/integration-profile.utils.spec.ts +9 -0
  675. package/src/integration-profile/integration-profile.utils.ts +5 -5
  676. package/src/integration-profile/testers/ai.testers.ts +70 -5
  677. package/src/integration-profile/testers/index.ts +2 -0
  678. package/src/integration-profile/testers/remaining.testers.spec.ts +144 -1
  679. package/src/integration-profile/testers/shipping.testers.ts +94 -0
  680. package/src/integration-profile/testers/tester-coverage.spec.ts +10 -0
  681. package/src/mail/dto/send.dto.ts +6 -1
  682. package/src/mail/mail-template.spec.ts +58 -1
  683. package/src/mail/mail.service.spec.ts +112 -0
  684. package/src/mail/mail.service.ts +42 -4
  685. package/src/mail-sent/mail-sent.service.ts +3 -0
  686. package/src/mail-sent/mail-sent.sort.ts +19 -0
  687. package/src/mcp/filters/mcp-challenge.filter.spec.ts +76 -0
  688. package/src/mcp/filters/mcp-challenge.filter.ts +70 -0
  689. package/src/mcp/guards/mcp-auth.guard.spec.ts +51 -2
  690. package/src/mcp/guards/mcp-auth.guard.ts +24 -1
  691. package/src/mcp/guards/mcp-permission.guard.spec.ts +109 -15
  692. package/src/mcp/guards/mcp-permission.guard.ts +76 -51
  693. package/src/mcp/mcp-audit.service.spec.ts +107 -0
  694. package/src/mcp/mcp-audit.service.ts +37 -1
  695. package/src/mcp/mcp-permission.service.spec.ts +197 -0
  696. package/src/mcp/mcp-permission.service.ts +184 -0
  697. package/src/mcp/mcp-server.service.spec.ts +84 -2
  698. package/src/mcp/mcp-server.service.ts +111 -87
  699. package/src/mcp/mcp.controller.ts +8 -1
  700. package/src/mcp/mcp.module.ts +7 -1
  701. package/src/mcp/tools/core-access-log.mcp-tools.ts +66 -0
  702. package/src/mcp/tools/core-ai.mcp-tools.ts +1 -1
  703. package/src/mcp/tools/core-dashboard-items.mcp-tools.ts +1 -1
  704. package/src/mcp/tools/core-dashboard.mcp-tools.ts +1 -1
  705. package/src/mcp/tools/core-event-webhooks.mcp-tools.ts +1 -2
  706. package/src/mcp/tools/core-files.mcp-tools.ts +202 -22
  707. package/src/mcp/tools/core-integration-events.mcp-tools.ts +1 -1
  708. package/src/mcp/tools/core-mail-sent.mcp-tools.ts +1 -1
  709. package/src/mcp/tools/core-mail.mcp-tools.ts +1 -1
  710. package/src/mcp/tools/core-menus.mcp-tools.ts +1 -2
  711. package/src/mcp/tools/core-notifications.mcp-tools.ts +0 -1
  712. package/src/mcp/tools/core-roles.mcp-tools.ts +1 -5
  713. package/src/mcp/tools/core-routes.mcp-tools.ts +1 -3
  714. package/src/mcp/tools/core-screens.mcp-tools.ts +1 -3
  715. package/src/mcp/tools/core-sessions.mcp-tools.ts +0 -2
  716. package/src/mcp/tools/core-settings.mcp-tools.ts +1 -2
  717. package/src/mcp/tools/core-users.mcp-tools.ts +1 -1
  718. package/src/mcp/tools/core-webhooks.mcp-tools.ts +1 -2
  719. package/src/mcp/types/mcp-context.type.ts +15 -6
  720. package/src/mcp-chat/mcp-chat.service.ts +8 -0
  721. package/src/meeting/meeting-provider.registry.ts +201 -0
  722. package/src/meeting/meeting.constants.ts +74 -0
  723. package/src/menu/menu.service.spec.ts +89 -0
  724. package/src/menu/menu.service.ts +29 -11
  725. package/src/message-template/dto/update-message-template.dto.ts +22 -0
  726. package/src/message-template/message-template-admin.service.spec.ts +163 -0
  727. package/src/message-template/message-template-admin.service.ts +239 -0
  728. package/src/message-template/message-template.controller.ts +52 -0
  729. package/src/message-template/message-template.module.ts +21 -0
  730. package/src/message-template/message-template.registry.spec.ts +62 -0
  731. package/src/message-template/message-template.registry.ts +125 -0
  732. package/src/message-template/message-template.service.spec.ts +149 -0
  733. package/src/message-template/message-template.service.ts +149 -0
  734. package/src/notification/notification.constants.ts +10 -0
  735. package/src/notification/notification.module.ts +3 -0
  736. package/src/notification/notification.service.spec.ts +75 -1
  737. package/src/notification/notification.service.ts +39 -1
  738. package/src/oauth/oauth-token-broker.service.spec.ts +108 -0
  739. package/src/oauth/oauth-token-broker.service.ts +129 -2
  740. package/src/oauth/oauth.controller.ts +0 -1
  741. package/src/oauth/oauth.errors.ts +7 -0
  742. package/src/oauth/oauth.module.ts +6 -1
  743. package/src/oauth/oauth.service.spec.ts +58 -7
  744. package/src/oauth/oauth.service.ts +71 -32
  745. package/src/oauth/providers/abstract.provider.spec.ts +192 -0
  746. package/src/oauth/providers/abstract.provider.ts +46 -14
  747. package/src/oauth/providers/github.provider.ts +57 -34
  748. package/src/oauth/providers/microsoft-entra-id.provider.spec.ts +133 -0
  749. package/src/oauth/providers/microsoft-entra-id.provider.ts +37 -3
  750. package/src/observability/monitored-cron.spec.ts +164 -31
  751. package/src/observability/monitored-cron.ts +154 -62
  752. package/src/pdf/document/charts/chart-bar.ts +217 -0
  753. package/src/pdf/document/charts/chart-donut.ts +163 -0
  754. package/src/pdf/document/charts/chart-gauge.ts +94 -0
  755. package/src/pdf/document/charts/chart-line.ts +159 -0
  756. package/src/pdf/document/charts/chart-primitives.ts +188 -0
  757. package/src/pdf/document/charts/chart-radar.ts +136 -0
  758. package/src/pdf/document/charts/chart-scale.spec.ts +93 -0
  759. package/src/pdf/document/charts/chart-scale.ts +141 -0
  760. package/src/pdf/document/charts/charts.spec.ts +157 -0
  761. package/src/pdf/document/charts/index.ts +7 -0
  762. package/src/pdf/document/index.ts +7 -0
  763. package/src/pdf/document/pdf-document.chrome.ts +38 -0
  764. package/src/pdf/document/pdf-document.css.ts +238 -0
  765. package/src/pdf/document/pdf-document.renderer.spec.ts +129 -0
  766. package/src/pdf/document/pdf-document.renderer.ts +215 -0
  767. package/src/pdf/document/pdf-document.service.ts +77 -0
  768. package/src/pdf/document/pdf-document.theme.ts +146 -0
  769. package/src/pdf/document/pdf-document.types.ts +97 -0
  770. package/src/pdf/pdf.module.ts +3 -2
  771. package/src/pdf/pdf.service.spec.ts +131 -0
  772. package/src/pdf/pdf.service.ts +245 -82
  773. package/src/pdf/templates/commercial-proposal.template.spec.ts +177 -0
  774. package/src/pdf/templates/commercial-proposal.template.ts +400 -0
  775. package/src/profile/dto/change-password.dto.ts +25 -7
  776. package/src/profile/profile.service.spec.ts +97 -0
  777. package/src/profile/profile.service.ts +9 -3
  778. package/src/realtime/realtime-tick.coalescer.spec.ts +92 -0
  779. package/src/realtime/realtime-tick.coalescer.ts +60 -0
  780. package/src/realtime/realtime.service.spec.ts +33 -0
  781. package/src/realtime/realtime.service.ts +28 -2
  782. package/src/redis/redis-kv.service.ts +261 -0
  783. package/src/redis/redis-master.spec.ts +111 -0
  784. package/src/redis/redis-master.ts +86 -0
  785. package/src/redis/redis-pubsub.ts +27 -3
  786. package/src/redis/redis.module.ts +17 -0
  787. package/src/session/session.service.spec.ts +121 -42
  788. package/src/session/session.service.ts +279 -82
  789. package/src/setting/favicon.controller.spec.ts +92 -0
  790. package/src/setting/favicon.controller.ts +135 -0
  791. package/src/setting/setting.module.ts +2 -1
  792. package/src/setting/setting.service.ts +44 -3
  793. package/src/task/task.service.spec.ts +41 -0
  794. package/src/task/task.service.ts +53 -13
  795. package/src/token/token.service.spec.ts +90 -0
  796. package/src/token/token.service.ts +48 -2
  797. package/src/user/user-credential.util.ts +14 -5
  798. package/src/user/user.service.ts +2 -12
  799. package/src/user/user.sort.ts +25 -0
  800. package/src/utils/abbreviate-name.spec.ts +50 -0
  801. package/src/utils/abbreviate-name.ts +44 -0
  802. package/src/utils/date-range-query.dto.ts +56 -0
  803. package/src/utils/date-range.spec.ts +175 -0
  804. package/src/utils/date-range.ts +246 -0
  805. package/src/webhook-integration/webhook-utils.spec.ts +67 -0
  806. package/src/webhook-integration/webhook-utils.ts +26 -0
  807. package/src/whatsapp-sender/whatsapp-recipients.spec.ts +89 -0
  808. package/src/whatsapp-sender/whatsapp-recipients.ts +83 -0
  809. package/src/whatsapp-sender/whatsapp-sender.service.spec.ts +185 -0
  810. package/src/whatsapp-sender/whatsapp-sender.service.ts +90 -7
  811. package/hedhog/query/device_pairing_request.sql +0 -46
  812. package/hedhog/query/impersonation_grant.sql +0 -71
  813. package/hedhog/query/oauth_authorize_pkce.sql +0 -58
  814. package/hedhog/query/oauth_mobile_state_token.sql +0 -30
  815. package/hedhog/query/oauth_web_ref_token.sql +0 -25
@@ -0,0 +1,135 @@
1
+ import { Public } from '@hed-hog/api';
2
+ import { Controller, Get, Logger, NotFoundException, Res } from '@nestjs/common';
3
+ import { Response } from 'express';
4
+ import { BrandAssetService } from './brand-asset.service';
5
+ import { SettingService } from './setting.service';
6
+
7
+ /** Timeout do fetch da imagem configurada. */
8
+ const FETCH_TIMEOUT_MS = 5_000;
9
+
10
+ /** Quanto tempo o binario baixado fica em memoria antes de buscar de novo. */
11
+ const CACHE_TTL_MS = 10 * 60_000;
12
+
13
+ type CachedIcon = {
14
+ url: string;
15
+ body: Buffer;
16
+ contentType: string;
17
+ expiresAt: number;
18
+ };
19
+
20
+ /**
21
+ * `GET /favicon.ico` no host da API, com o icone do Branding (`icon-url`).
22
+ *
23
+ * Quem procura o favicon no dominio da API sao os clientes que so conhecem esse
24
+ * endereco - o conector MCP no claude.ai, por exemplo, mostra o icone do dominio
25
+ * do servidor ao lado do nome. Sem esta rota a resposta era o 404 JSON do Nest e
26
+ * o conector caia na letra inicial.
27
+ *
28
+ * O arquivo e servido daqui (e nao por redirect) porque nem todo coletor de
29
+ * favicon segue redirecionamento. O Content-Type e o da origem, entao um SVG
30
+ * configurado no Branding chega como SVG.
31
+ */
32
+ @Controller()
33
+ export class FaviconController {
34
+ private readonly logger = new Logger(FaviconController.name);
35
+ private cache: CachedIcon | null = null;
36
+
37
+ constructor(
38
+ private readonly setting: SettingService,
39
+ private readonly brandAsset: BrandAssetService,
40
+ ) {}
41
+
42
+ @Public()
43
+ @Get('favicon.ico')
44
+ async favicon(@Res() res: Response) {
45
+ const icon = await this.loadIcon();
46
+
47
+ if (!icon) {
48
+ throw new NotFoundException();
49
+ }
50
+
51
+ res.setHeader('Content-Type', icon.contentType);
52
+ res.setHeader('Cache-Control', 'public, max-age=3600');
53
+ res.send(icon.body);
54
+ }
55
+
56
+ private async loadIcon(): Promise<CachedIcon | null> {
57
+ const settings = await this.setting.getSettingValues([
58
+ 'icon-url',
59
+ 'image-url',
60
+ ]);
61
+ const value =
62
+ String(settings['icon-url'] ?? '').trim() ||
63
+ String(settings['image-url'] ?? '').trim();
64
+ const url = await this.brandAsset.resolveAssetUrl(value);
65
+
66
+ if (!url) {
67
+ return null;
68
+ }
69
+
70
+ if (
71
+ this.cache &&
72
+ this.cache.url === url &&
73
+ this.cache.expiresAt > Date.now()
74
+ ) {
75
+ return this.cache;
76
+ }
77
+
78
+ const icon = await this.download(url);
79
+
80
+ if (icon) {
81
+ this.cache = icon;
82
+ return icon;
83
+ }
84
+
85
+ // Origem fora do ar: melhor o icone anterior do que nenhum.
86
+ return this.cache?.url === url ? this.cache : null;
87
+ }
88
+
89
+ private async download(url: string): Promise<CachedIcon | null> {
90
+ const dataUri = /^data:([^;,]+)(;base64)?,([\s\S]*)$/i.exec(url);
91
+
92
+ if (dataUri) {
93
+ const [, contentType, base64, payload] = dataUri;
94
+ return {
95
+ url,
96
+ contentType,
97
+ body: base64
98
+ ? Buffer.from(payload, 'base64')
99
+ : Buffer.from(decodeURIComponent(payload)),
100
+ expiresAt: Date.now() + CACHE_TTL_MS,
101
+ };
102
+ }
103
+
104
+ try {
105
+ const controller = new AbortController();
106
+ const timeout = setTimeout(() => controller.abort(), FETCH_TIMEOUT_MS);
107
+ const response = await globalThis
108
+ .fetch(url, { signal: controller.signal })
109
+ .finally(() => clearTimeout(timeout));
110
+
111
+ const contentType = response.headers.get('content-type') ?? '';
112
+
113
+ if (!response.ok || !contentType.startsWith('image/')) {
114
+ this.logger.warn(
115
+ `Favicon source ${url} answered ${response.status} ${contentType || '(no content-type)'}`,
116
+ );
117
+ return null;
118
+ }
119
+
120
+ return {
121
+ url,
122
+ contentType,
123
+ body: Buffer.from(await response.arrayBuffer()),
124
+ expiresAt: Date.now() + CACHE_TTL_MS,
125
+ };
126
+ } catch (error) {
127
+ this.logger.warn(
128
+ `Could not fetch favicon source ${url}: ${
129
+ error instanceof Error ? error.message : String(error)
130
+ }`,
131
+ );
132
+ return null;
133
+ }
134
+ }
135
+ }
@@ -5,6 +5,7 @@ import { Global, Module, forwardRef } from '@nestjs/common';
5
5
  import { AuthModule } from '../auth/auth.module';
6
6
  import { MailModule } from '../mail/mail.module';
7
7
  import { BrandAssetService } from './brand-asset.service';
8
+ import { FaviconController } from './favicon.controller';
8
9
  import { SettingsController } from './setting.controller';
9
10
  import { SettingService } from './setting.service';
10
11
 
@@ -17,7 +18,7 @@ import { SettingService } from './setting.service';
17
18
  forwardRef(() => LocaleModule),
18
19
  forwardRef(() => MailModule),
19
20
  ],
20
- controllers: [SettingsController],
21
+ controllers: [SettingsController, FaviconController],
21
22
  providers: [SettingService, BrandAssetService],
22
23
  exports: [SettingService, BrandAssetService],
23
24
  })
@@ -67,6 +67,15 @@ export class SettingService implements OnModuleInit, OnModuleDestroy {
67
67
  );
68
68
  private lastRedisSubscriberErrorLogAt = 0;
69
69
  private lastRedisPublisherErrorLogAt = 0;
70
+ // A `reconnectStrategy` que nunca devolve `false` faz `client.connect()` ficar
71
+ // retentando pra sempre quando o Redis está indisponível: a Promise nunca
72
+ // resolve nem rejeita, e `onModuleInit` trava o boot inteiro da API esperando
73
+ // por ela. Este teto bound só a tentativa inicial; a reconexão de um cliente
74
+ // já conectado continua indefinida.
75
+ private readonly redisConnectTimeoutMs = Math.max(
76
+ 1000,
77
+ Number(process.env.REDIS_CONNECT_TIMEOUT_MS || 3000),
78
+ );
70
79
 
71
80
  constructor(
72
81
  @Inject(forwardRef(() => PrismaService))
@@ -140,6 +149,23 @@ export class SettingService implements OnModuleInit, OnModuleDestroy {
140
149
  return String(error);
141
150
  }
142
151
 
152
+ private async withConnectTimeout<T>(promise: Promise<T>, timeoutMs: number): Promise<T> {
153
+ let timer: NodeJS.Timeout;
154
+ try {
155
+ return await Promise.race([
156
+ promise,
157
+ new Promise<never>((_, reject) => {
158
+ timer = setTimeout(
159
+ () => reject(new Error(`Redis connection timed out after ${timeoutMs}ms`)),
160
+ timeoutMs,
161
+ );
162
+ }),
163
+ ]);
164
+ } finally {
165
+ clearTimeout(timer!);
166
+ }
167
+ }
168
+
143
169
  private async initializeRedisSync() {
144
170
  if (!this.redisUrl) {
145
171
  this.logger.log(
@@ -169,8 +195,8 @@ export class SettingService implements OnModuleInit, OnModuleDestroy {
169
195
  this.logRedisClientError('publisher', error);
170
196
  });
171
197
 
172
- await this.redisSubscriber.connect();
173
- await this.redisPublisher.connect();
198
+ await this.withConnectTimeout(this.redisSubscriber.connect(), this.redisConnectTimeoutMs);
199
+ await this.withConnectTimeout(this.redisPublisher.connect(), this.redisConnectTimeoutMs);
174
200
  await this.redisSubscriber.subscribe(this.redisChannel, async (message) => {
175
201
  await this.handleRedisSettingsVersionMessage(message);
176
202
  });
@@ -529,7 +555,22 @@ export class SettingService implements OnModuleInit, OnModuleDestroy {
529
555
  'lms-video-frame-capture-interval-seconds',
530
556
  'lms-error-modal-enabled',
531
557
  'url',
532
- 'app-urls'
558
+ 'app-urls',
559
+ // Hcode Store: liga/desliga a venda no frontend (o backend também
560
+ // recusa o checkout — isto é só para a UI mostrar "Em breve" cedo).
561
+ 'commerce-store-sales-enabled',
562
+ // A loja lê esta para decidir se dispara o beacon de navegação. A irmã
563
+ // `-persist` NÃO entra aqui de propósito: é decisão de servidor (grava ou
564
+ // não IP e origem) e não tem por que chegar ao navegador.
565
+ 'commerce-store-visitor-tracking',
566
+ // A partir de quantas unidades a loja mostra "Última unidade"/"Restam N".
567
+ // Só afeta o aviso na vitrine — a trava de quantidade é do backend e não
568
+ // depende deste valor chegar ao navegador.
569
+ 'commerce-store-low-stock-threshold',
570
+ // Se a loja abre o stream de estoque ao vivo. Desligada, o frontend nem
571
+ // conecta — que é o ponto: sem isto aqui, cada visitante abriria uma
572
+ // conexão de longa duração para um recurso que está fora de uso.
573
+ 'commerce-store-realtime-stock-enabled'
533
574
  ];
534
575
  const setting = await this.getSettingValues(slugs);
535
576
  return { locales, setting };
@@ -44,4 +44,45 @@ describe('TasksService', () => {
44
44
  expect(values).toContain(500);
45
45
  });
46
46
  });
47
+
48
+ describe('clearOldAccessLogs', () => {
49
+ it('repete lotes ate drenar o acumulo', async () => {
50
+ // O bug: um unico lote por execucao diaria contra uma ingestao uma ordem
51
+ // de grandeza maior deixava a retencao inalcancavel.
52
+ const { service, deps } = makeService();
53
+ deps.settingService.getSettingValues.mockResolvedValue({
54
+ 'cleanup-batch-limit': 100,
55
+ });
56
+ deps.prismaService.$executeRaw
57
+ .mockResolvedValueOnce(100)
58
+ .mockResolvedValueOnce(100)
59
+ .mockResolvedValueOnce(42);
60
+
61
+ await (service as any).clearOldAccessLogs();
62
+
63
+ expect(deps.prismaService.$executeRaw).toHaveBeenCalledTimes(3);
64
+ });
65
+
66
+ it('para no primeiro lote incompleto', async () => {
67
+ const { service, deps } = makeService();
68
+ deps.settingService.getSettingValues.mockResolvedValue({
69
+ 'cleanup-batch-limit': 100,
70
+ });
71
+ deps.prismaService.$executeRaw.mockResolvedValue(0);
72
+
73
+ await (service as any).clearOldAccessLogs();
74
+
75
+ expect(deps.prismaService.$executeRaw).toHaveBeenCalledTimes(1);
76
+ });
77
+
78
+ it('usa os defaults de retencao e de lote quando as settings faltam', async () => {
79
+ const { service, deps } = makeService();
80
+ deps.settingService.getSettingValues.mockResolvedValue({});
81
+
82
+ await (service as any).clearOldAccessLogs();
83
+
84
+ const values = deps.prismaService.$executeRaw.mock.calls[0].slice(1);
85
+ expect(values).toContain(20000);
86
+ });
87
+ });
47
88
  });
@@ -3,6 +3,13 @@ import { Injectable, Logger } from '@nestjs/common';
3
3
  import { Cron, CronExpression } from '@nestjs/schedule';
4
4
  import { SettingService } from '../setting/setting.service';
5
5
 
6
+ /**
7
+ * Teto de tempo da limpeza do `access_log`. Existe para o caso da entrada
8
+ * superar a saída de novo: o laço para e devolve o resto para a execução
9
+ * seguinte, em vez de varrer a madrugada inteira disputando o banco.
10
+ */
11
+ const ACCESS_LOG_CLEANUP_BUDGET_MS = 10 * 60 * 1000;
12
+
6
13
  @Injectable()
7
14
  export class TasksService {
8
15
  private readonly logger = new Logger(TasksService.name);
@@ -270,6 +277,23 @@ export class TasksService {
270
277
  );
271
278
  }
272
279
 
280
+ /**
281
+ * Apaga os logs de acesso fora da janela de `access-log-retention-days`.
282
+ *
283
+ * Roda em lotes até drenar, e não em um lote só. O `access_log` recebe um
284
+ * INSERT por requisição — em produção, de 200 a 540 mil por dia — enquanto a
285
+ * limpeza apagava `cleanup-batch-limit` registros por execução diária. Com a
286
+ * entrada uma ordem de grandeza acima da saída, a retenção nunca era
287
+ * alcançada: a tabela chegou a 18,6 milhões de linhas e 4 GB, com 11,8
288
+ * milhões já vencidos e registros três meses mais velhos que a retenção de 30
289
+ * dias configurada.
290
+ *
291
+ * O `cleanup-batch-limit` passa a ser o tamanho de CADA lote — o papel que a
292
+ * própria descrição da setting sempre anunciou ("valores menores evitam locks
293
+ * prolongados mas aumentam a duração da limpeza"). O teto agora é de tempo,
294
+ * não de linhas: o laço para ao drenar a fila ou ao estourar o orçamento,
295
+ * para que a limpeza não avance madrugada adentro competindo com o tráfego.
296
+ */
273
297
  private async clearOldAccessLogs(): Promise<void> {
274
298
  const settings = await this.settingService.getSettingValues([
275
299
  'cleanup-batch-limit',
@@ -280,21 +304,37 @@ export class TasksService {
280
304
  this.logger.verbose('Starting cleanup of old access logs');
281
305
  const startAt = Date.now();
282
306
 
283
- await this.prismaService.$executeRaw`
284
- WITH del AS (
285
- SELECT id
286
- FROM access_log
287
- WHERE created_at < (now() - ${Prisma.sql`INTERVAL '${Prisma.raw(String(retentionDays))} days'`})
288
- ORDER BY id
289
- LIMIT ${batchLimit}
290
- )
291
- DELETE FROM access_log al
292
- USING del
293
- WHERE al.id = del.id
294
- `;
307
+ let deleted = 0;
308
+ let batches = 0;
309
+ for (;;) {
310
+ const removed = await this.prismaService.$executeRaw`
311
+ WITH del AS (
312
+ SELECT id
313
+ FROM access_log
314
+ WHERE created_at < (now() - ${Prisma.sql`INTERVAL '${Prisma.raw(String(retentionDays))} days'`})
315
+ ORDER BY id
316
+ LIMIT ${batchLimit}
317
+ )
318
+ DELETE FROM access_log al
319
+ USING del
320
+ WHERE al.id = del.id
321
+ `;
322
+
323
+ deleted += removed;
324
+ batches += 1;
325
+
326
+ if (removed < batchLimit) break;
327
+
328
+ if (Date.now() - startAt >= ACCESS_LOG_CLEANUP_BUDGET_MS) {
329
+ this.logger.warn(
330
+ `Access log cleanup hit the ${ACCESS_LOG_CLEANUP_BUDGET_MS}ms budget after ${deleted} rows; the remainder goes on the next run.`,
331
+ );
332
+ break;
333
+ }
334
+ }
295
335
 
296
336
  this.logger.verbose(
297
- `Old access logs cleaned up in ${Date.now() - startAt}ms`,
337
+ `Old access logs cleaned up in ${Date.now() - startAt}ms (${deleted} rows in ${batches} batches)`,
298
338
  );
299
339
  }
300
340
 
@@ -410,4 +410,94 @@ describe('TokenService', () => {
410
410
  );
411
411
  });
412
412
  });
413
+
414
+ describe('verify - audiencia (audience binding)', () => {
415
+ const RESOURCE = 'https://hub-api.example.com/mcp';
416
+ const activeSession = {
417
+ revoked_at: null,
418
+ expires_at: new Date(Date.now() + 60_000),
419
+ };
420
+
421
+ // ESTE e o teste central do audience binding: sem ele, o token entregue ao
422
+ // conector do Claude valeria na API REST inteira.
423
+ it('recusa token COM aud numa rota que nao declara recurso', async () => {
424
+ const { service, deps } = makeService();
425
+ deps.jwt.verifyAsync.mockResolvedValue({ sub: 1, sessionId: 9, aud: RESOURCE });
426
+
427
+ await expect(service.verify('en', 'tok')).rejects.toThrow(
428
+ UnauthorizedException,
429
+ );
430
+ // Nem chega a consultar a sessao: a recusa e antes.
431
+ expect(deps.prisma.user_session.findUnique).not.toHaveBeenCalled();
432
+ });
433
+
434
+ it('recusa token cujo aud e de OUTRO recurso', async () => {
435
+ const { service, deps } = makeService();
436
+ deps.jwt.verifyAsync.mockResolvedValue({
437
+ sub: 1,
438
+ sessionId: 9,
439
+ aud: 'https://outro.example.com/mcp',
440
+ });
441
+
442
+ await expect(service.verify('en', 'tok', RESOURCE)).rejects.toThrow(
443
+ UnauthorizedException,
444
+ );
445
+ });
446
+
447
+ it('aceita token cujo aud casa exatamente com o recurso', async () => {
448
+ const { service, deps } = makeService();
449
+ deps.jwt.verifyAsync.mockResolvedValue({ sub: 1, sessionId: 9, aud: RESOURCE });
450
+ deps.prisma.user_session.findUnique.mockResolvedValue(activeSession);
451
+
452
+ await expect(service.verify('en', 'tok', RESOURCE)).resolves.toMatchObject({
453
+ sub: 1,
454
+ aud: RESOURCE,
455
+ });
456
+ });
457
+
458
+ // Comparacao por igualdade exata: barra final e outro recurso.
459
+ it('nao normaliza barra final ao comparar', async () => {
460
+ const { service, deps } = makeService();
461
+ deps.jwt.verifyAsync.mockResolvedValue({
462
+ sub: 1,
463
+ sessionId: 9,
464
+ aud: RESOURCE + '/',
465
+ });
466
+
467
+ await expect(service.verify('en', 'tok', RESOURCE)).rejects.toThrow(
468
+ UnauthorizedException,
469
+ );
470
+ });
471
+
472
+ // O login normal nao pode mudar de comportamento por causa disso.
473
+ it('aceita token SEM aud, com ou sem recurso declarado', async () => {
474
+ const { service, deps } = makeService();
475
+ deps.jwt.verifyAsync.mockResolvedValue({ sub: 1, sessionId: 9 });
476
+ deps.prisma.user_session.findUnique.mockResolvedValue(activeSession);
477
+
478
+ await expect(service.verify('en', 'tok')).resolves.toMatchObject({ sub: 1 });
479
+ await expect(service.verify('en', 'tok', RESOURCE)).resolves.toMatchObject({
480
+ sub: 1,
481
+ });
482
+ });
483
+
484
+ it('falha fechado em erro de banco quando o token e de recurso', async () => {
485
+ const { service, deps } = makeService();
486
+ deps.jwt.verifyAsync.mockResolvedValue({ sub: 1, sessionId: 9, aud: RESOURCE });
487
+ deps.prisma.user_session.findUnique.mockRejectedValue(new Error('db down'));
488
+
489
+ await expect(service.verify('en', 'tok', RESOURCE)).rejects.toThrow(
490
+ UnauthorizedException,
491
+ );
492
+ });
493
+
494
+ it('segue aberto em erro de banco para a sessao de login', async () => {
495
+ const { service, deps } = makeService();
496
+ deps.jwt.verifyAsync.mockResolvedValue({ sub: 1, sessionId: 9 });
497
+ deps.prisma.user_session.findUnique.mockRejectedValue(new Error('db down'));
498
+
499
+ await expect(service.verify('en', 'tok')).resolves.toMatchObject({ sub: 1 });
500
+ });
501
+ });
502
+
413
503
  });
@@ -22,13 +22,46 @@ export class TokenService {
22
22
  private readonly setting: SettingService,
23
23
  ) { }
24
24
 
25
- async verify(locale: string, token: string) {
25
+ /**
26
+ * `allowedAudience` declara qual recurso ESTA rota atende. A regra e de mao
27
+ * unica, e e essa assimetria que faz o modelo funcionar:
28
+ *
29
+ * - token SEM `aud` (o login normal) vale em qualquer lugar, com ou sem o
30
+ * parametro — nada muda para quem ja existe;
31
+ * - token COM `aud` so vale onde aquele exato recurso foi declarado. Em
32
+ * qualquer outra rota, 401.
33
+ *
34
+ * O AuthGuard global chama este metodo SEM o terceiro argumento, entao toda
35
+ * rota que ninguem marcou como recurso ja recusa um token de conector — por
36
+ * construcao, inclusive nas rotas que ainda nem foram escritas. Nao ha
37
+ * allowlist para alguem esquecer de atualizar.
38
+ *
39
+ * A comparacao e feita aqui, na mao, e nao pela opcao `audience` do
40
+ * jsonwebtoken: quando aquela opcao esta ausente, a lib simplesmente NAO OLHA o
41
+ * claim. E exatamente essa omissao que precisa virar rejeicao.
42
+ */
43
+ async verify(locale: string, token: string, allowedAudience?: string) {
26
44
  try {
27
45
 
28
46
  const payload = await this.jwt.verifyAsync(token, {
29
47
  secret: this.security.getJwtSecret(),
30
48
  });
31
49
 
50
+ const audience = payload.aud;
51
+ const isResourceToken = audience !== undefined;
52
+
53
+ // Igualdade exata de string, sem parsear URL — normalizar abriria as mesmas
54
+ // brechas que a allowlist de redirect_uri ja evita (barra final, case do
55
+ // host, porta default).
56
+ if (isResourceToken && audience !== allowedAudience) {
57
+ this.logger.warn(
58
+ `[TokenVerify] sessionId=${payload.sessionId} userId=${payload.sub} token with aud=${audience} used outside its resource`,
59
+ );
60
+ throw new UnauthorizedException(
61
+ getLocaleText('accessDenied', locale, 'Access denied.'),
62
+ );
63
+ }
64
+
32
65
  // Verify session is not revoked (only if prisma is available)
33
66
  if (payload.sessionId && this.prisma) {
34
67
  try {
@@ -62,8 +95,21 @@ export class TokenService {
62
95
  if (sessionError instanceof UnauthorizedException) {
63
96
  throw sessionError;
64
97
  }
65
- // DB error: log but allow auth to continue to avoid blocking on transient DB issues
66
98
  this.logger.error(`[TokenVerify] DB error validating sessionId=${payload.sessionId} userId=${payload.sub}: ${(sessionError as any)?.message}`);
99
+
100
+ // Token de recurso nao ganha o beneficio da duvida. Para a sessao de
101
+ // login, seguir em frente numa falha transitoria de banco e a troca
102
+ // certa — derrubar todo mundo logado e pior que aceitar uma revogacao
103
+ // com atraso. Para um token entregue a um cliente externo, user_session
104
+ // e o UNICO jeito de revogar: continuar aqui faria uma revogacao valer
105
+ // so no vencimento do JWT. A decisao segue a natureza do TOKEN, nao a
106
+ // da rota.
107
+ if (isResourceToken) {
108
+ throw new UnauthorizedException(
109
+ getLocaleText('accessDenied', locale, 'Access denied.'),
110
+ );
111
+ }
112
+ // DB error: log but allow auth to continue to avoid blocking on transient DB issues
67
113
  }
68
114
  }
69
115
 
@@ -21,15 +21,24 @@ export function hasPendingPasswordReset(user: any): boolean {
21
21
  );
22
22
  }
23
23
 
24
+ /**
25
+ * Credencial de senha que ainda vale: do tipo password e não revogada.
26
+ *
27
+ * Existe para quem já tem as credenciais em memória e precisa do mesmo critério
28
+ * que as consultas de Prisma expressam com `revoked_at: null`. O login e a troca
29
+ * de e-mail filtravam só por `type`, então uma credencial revogada continuava
30
+ * autenticando — e a revogação é justamente o que o convite de acesso enterprise
31
+ * usa para transformar "autorize o acesso" em "crie sua conta e defina a senha".
32
+ */
33
+ export function isActivePasswordCredential(credential: any): boolean {
34
+ return credential?.type === 'password' && !credential?.revoked_at;
35
+ }
36
+
24
37
  /**
25
38
  * Usuários criados/autenticados apenas via provedor externo (ex: Microsoft
26
39
  * Entra ID) nunca têm uma credencial de senha ativa — não faz sentido
27
40
  * oferecer o fluxo de "esqueci a senha" para eles.
28
41
  */
29
42
  export function hasPasswordCredential(user: any): boolean {
30
- return Boolean(
31
- user?.user_credential?.some(
32
- (credential) => credential?.type === 'password' && !credential?.revoked_at,
33
- ),
34
- );
43
+ return Boolean(user?.user_credential?.some(isActivePasswordCredential));
35
44
  }
@@ -25,6 +25,7 @@ import {
25
25
  PENDING_PASSWORD_RESET_WHERE,
26
26
  hasPendingPasswordReset,
27
27
  } from './user-credential.util';
28
+ import { USER_SORT } from './user.sort';
28
29
 
29
30
  // Constants
30
31
  const IDENTIFIER_TYPE = {
@@ -48,17 +49,6 @@ const PASSWORD_CHARSETS = {
48
49
  symbols: '@#$%&*!?-_+',
49
50
  } as const;
50
51
 
51
- const USER_SORT_FIELDS = [
52
- 'id',
53
- 'name',
54
- 'photo_id',
55
- 'suspended_until',
56
- 'suspended_reason',
57
- 'deactivated_at',
58
- 'created_at',
59
- 'updated_at',
60
- ] as const;
61
-
62
52
  type UserChangeLog = user_change_log;
63
53
  type UserChangeLogActor = Prisma.userGetPayload<{
64
54
  select: {
@@ -164,7 +154,7 @@ export class UserService {
164
154
  this.prismaService.user,
165
155
  {
166
156
  ...paginationParams,
167
- validSortFields: USER_SORT_FIELDS,
157
+ sort: USER_SORT,
168
158
  where: this.buildUserListWhere(filter, paginationParams?.search),
169
159
  include: this.getUserIncludeClause(),
170
160
  }
@@ -0,0 +1,25 @@
1
+ import { defineSortable } from '@hed-hog/api-pagination';
2
+
3
+ /**
4
+ * Campos ordenáveis de `user`.
5
+ *
6
+ * `email` fica de fora: mora em `user_identifier` (relação to-many filtrada
7
+ * por `type = 'email'`), sem coluna própria em `user` para o Prisma ordenar —
8
+ * mesma limitação documentada em `libraries/lms/src/instructor/instructor.sort.ts`
9
+ * para o e-mail do instrutor.
10
+ *
11
+ * `passwordReset` também fica de fora: é booleano calculado no service
12
+ * (`hasPendingPasswordReset`), não uma coluna.
13
+ *
14
+ * Sem ninguém pedir ordenação, o resultado continua igual ao de antes
15
+ * (`id` desc, o fallback do `paginatePrismaModel` quando não há `sortField`).
16
+ */
17
+ export const USER_SORT = defineSortable(
18
+ {
19
+ name: true,
20
+ suspended_until: true,
21
+ last_login_at: true,
22
+ id: { initialOrder: 'desc' },
23
+ },
24
+ { default: 'id', defaultOrder: 'desc' },
25
+ );
@@ -0,0 +1,50 @@
1
+ import { describe, it, expect } from '@jest/globals';
2
+ import { abbreviateName } from './abbreviate-name';
3
+
4
+ describe('abbreviateName', () => {
5
+ it('mantém primeiro nome e último sobrenome', () => {
6
+ expect(abbreviateName('João Henrique Cunha Rangel')).toBe('João Rangel');
7
+ });
8
+
9
+ it('ignora partículas (de/da/do/das/dos/e) ao escolher o último sobrenome', () => {
10
+ expect(abbreviateName('Maria de Souza')).toBe('Maria Souza');
11
+ expect(abbreviateName('Ana da Silva')).toBe('Ana Silva');
12
+ expect(abbreviateName('Pedro dos Santos')).toBe('Pedro Santos');
13
+ expect(abbreviateName('Carlos do Nascimento')).toBe('Carlos Nascimento');
14
+ expect(abbreviateName('José das Neves')).toBe('José Neves');
15
+ expect(abbreviateName('Silva e Souza Junior')).toBe('Silva Junior');
16
+ });
17
+
18
+ it('nome com duas palavras não muda', () => {
19
+ expect(abbreviateName('Ana Paula')).toBe('Ana Paula');
20
+ });
21
+
22
+ it('nome com uma palavra só passa como está', () => {
23
+ expect(abbreviateName('Madonna')).toBe('Madonna');
24
+ });
25
+
26
+ it('nome vazio ou só espaço devolve vazio', () => {
27
+ expect(abbreviateName('')).toBe('');
28
+ expect(abbreviateName(' ')).toBe('');
29
+ });
30
+
31
+ it('nome nulo/indefinido devolve vazio', () => {
32
+ expect(abbreviateName(null)).toBe('');
33
+ expect(abbreviateName(undefined)).toBe('');
34
+ });
35
+
36
+ it('normaliza espaços múltiplos entre palavras', () => {
37
+ expect(abbreviateName(' João Henrique Rangel ')).toBe('João Rangel');
38
+ });
39
+
40
+ it('cai no primeiro nome quando só sobra partícula depois dele', () => {
41
+ // Dado maltratado (ex.: sobrenome vazio salvo como "de") — não deve
42
+ // repetir o primeiro nome nem devolver a partícula sozinha.
43
+ expect(abbreviateName('João de')).toBe('João');
44
+ });
45
+
46
+ it('fallback "Alguém"/"Someone" (sem atribuidor) passa direto, sem quebrar', () => {
47
+ expect(abbreviateName('Alguém')).toBe('Alguém');
48
+ expect(abbreviateName('Someone')).toBe('Someone');
49
+ });
50
+ });