@hed-hog/core 0.0.390 → 0.0.393

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 (528) hide show
  1. package/README.md +39 -0
  2. package/dist/access-log/access-log.controller.d.ts.map +1 -1
  3. package/dist/access-log/access-log.controller.js +1 -1
  4. package/dist/access-log/access-log.controller.js.map +1 -1
  5. package/dist/access-log/access-log.interceptor.d.ts.map +1 -1
  6. package/dist/access-log/access-log.interceptor.js +8 -5
  7. package/dist/access-log/access-log.interceptor.js.map +1 -1
  8. package/dist/access-log/access-log.service.d.ts +4 -0
  9. package/dist/access-log/access-log.service.d.ts.map +1 -1
  10. package/dist/access-log/access-log.service.js +31 -4
  11. package/dist/access-log/access-log.service.js.map +1 -1
  12. package/dist/access-log/dto/query-access-log.dto.d.ts +2 -0
  13. package/dist/access-log/dto/query-access-log.dto.d.ts.map +1 -1
  14. package/dist/access-log/dto/query-access-log.dto.js +5 -0
  15. package/dist/access-log/dto/query-access-log.dto.js.map +1 -1
  16. package/dist/ai/ai.controller.d.ts +12 -8
  17. package/dist/ai/ai.controller.d.ts.map +1 -1
  18. package/dist/ai/ai.controller.js +17 -2
  19. package/dist/ai/ai.controller.js.map +1 -1
  20. package/dist/ai/ai.module.d.ts.map +1 -1
  21. package/dist/ai/ai.module.js +3 -2
  22. package/dist/ai/ai.module.js.map +1 -1
  23. package/dist/ai/ai.service.d.ts +30 -1
  24. package/dist/ai/ai.service.d.ts.map +1 -1
  25. package/dist/ai/ai.service.js +97 -3
  26. package/dist/ai/ai.service.js.map +1 -1
  27. package/dist/ai/dto/richtext-edit-html.dto.d.ts +5 -0
  28. package/dist/ai/dto/richtext-edit-html.dto.d.ts.map +1 -0
  29. package/dist/ai/dto/richtext-edit-html.dto.js +27 -0
  30. package/dist/ai/dto/richtext-edit-html.dto.js.map +1 -0
  31. package/dist/ai/richtext-ai.prompts.d.ts +5 -0
  32. package/dist/ai/richtext-ai.prompts.d.ts.map +1 -0
  33. package/dist/ai/richtext-ai.prompts.js +57 -0
  34. package/dist/ai/richtext-ai.prompts.js.map +1 -0
  35. package/dist/ai/richtext-ai.service.d.ts +34 -0
  36. package/dist/ai/richtext-ai.service.d.ts.map +1 -0
  37. package/dist/ai/richtext-ai.service.js +95 -0
  38. package/dist/ai/richtext-ai.service.js.map +1 -0
  39. package/dist/ai-instruction/ai-instruction.controller.d.ts +5 -5
  40. package/dist/auth/auth.controller.d.ts +66 -7
  41. package/dist/auth/auth.controller.d.ts.map +1 -1
  42. package/dist/auth/auth.controller.js +67 -23
  43. package/dist/auth/auth.controller.js.map +1 -1
  44. package/dist/auth/auth.module.d.ts.map +1 -1
  45. package/dist/auth/auth.module.js +2 -0
  46. package/dist/auth/auth.module.js.map +1 -1
  47. package/dist/auth/auth.service.d.ts +136 -4
  48. package/dist/auth/auth.service.d.ts.map +1 -1
  49. package/dist/auth/auth.service.js +246 -48
  50. package/dist/auth/auth.service.js.map +1 -1
  51. package/dist/auth/dto/confirm-email.dto.d.ts +4 -0
  52. package/dist/auth/dto/confirm-email.dto.d.ts.map +1 -0
  53. package/dist/auth/dto/confirm-email.dto.js +22 -0
  54. package/dist/auth/dto/confirm-email.dto.js.map +1 -0
  55. package/dist/auth/dto/resend-confirmation.dto.d.ts +8 -0
  56. package/dist/auth/dto/resend-confirmation.dto.d.ts.map +1 -0
  57. package/dist/auth/dto/resend-confirmation.dto.js +36 -0
  58. package/dist/auth/dto/resend-confirmation.dto.js.map +1 -0
  59. package/dist/authorize/authorize.controller.d.ts +1 -1
  60. package/dist/authorize/authorize.controller.d.ts.map +1 -1
  61. package/dist/authorize/authorize.controller.js +4 -2
  62. package/dist/authorize/authorize.controller.js.map +1 -1
  63. package/dist/authorize/authorize.service.d.ts +7 -0
  64. package/dist/authorize/authorize.service.d.ts.map +1 -1
  65. package/dist/authorize/authorize.service.js +1 -1
  66. package/dist/authorize/authorize.service.js.map +1 -1
  67. package/dist/challenge/challenge.service.d.ts +18 -5
  68. package/dist/challenge/challenge.service.d.ts.map +1 -1
  69. package/dist/challenge/challenge.service.js +50 -3
  70. package/dist/challenge/challenge.service.js.map +1 -1
  71. package/dist/core.module.d.ts.map +1 -1
  72. package/dist/core.module.js +17 -0
  73. package/dist/core.module.js.map +1 -1
  74. package/dist/dashboard/dashboard/dashboard.controller.d.ts +6 -6
  75. package/dist/dashboard/dashboard/dashboard.service.d.ts +6 -6
  76. package/dist/dashboard/dashboard-component/dashboard-component.controller.d.ts +4 -4
  77. package/dist/dashboard/dashboard-component/dashboard-component.service.d.ts +4 -4
  78. package/dist/dashboard/dashboard-component-role/dashboard-component-role.controller.d.ts +1 -1
  79. package/dist/dashboard/dashboard-component-role/dashboard-component-role.service.d.ts +1 -1
  80. package/dist/dashboard/dashboard-core/dashboard-core.controller.d.ts +2 -2
  81. package/dist/dashboard/dashboard-core/dashboard-core.service.d.ts +2 -2
  82. package/dist/dashboard/dashboard-item/dashboard-item.controller.d.ts +2 -2
  83. package/dist/dashboard/dashboard-item/dashboard-item.service.d.ts +2 -2
  84. package/dist/file/file.controller.d.ts +8 -1
  85. package/dist/file/file.controller.d.ts.map +1 -1
  86. package/dist/file/file.controller.js +45 -7
  87. package/dist/file/file.controller.js.map +1 -1
  88. package/dist/file/file.service.d.ts +128 -1
  89. package/dist/file/file.service.d.ts.map +1 -1
  90. package/dist/file/file.service.js +319 -8
  91. package/dist/file/file.service.js.map +1 -1
  92. package/dist/file/image-optimization.service.d.ts +43 -0
  93. package/dist/file/image-optimization.service.d.ts.map +1 -1
  94. package/dist/file/image-optimization.service.js +154 -0
  95. package/dist/file/image-optimization.service.js.map +1 -1
  96. package/dist/file/provider/abstract.provider.d.ts +16 -0
  97. package/dist/file/provider/abstract.provider.d.ts.map +1 -1
  98. package/dist/file/provider/abstract.provider.js +4 -0
  99. package/dist/file/provider/abstract.provider.js.map +1 -1
  100. package/dist/file/provider/gcs.provider.d.ts +2 -0
  101. package/dist/file/provider/gcs.provider.d.ts.map +1 -1
  102. package/dist/file/provider/gcs.provider.js +10 -0
  103. package/dist/file/provider/gcs.provider.js.map +1 -1
  104. package/dist/file/provider/local.provider.d.ts +1 -0
  105. package/dist/file/provider/local.provider.d.ts.map +1 -1
  106. package/dist/file/provider/local.provider.js +13 -0
  107. package/dist/file/provider/local.provider.js.map +1 -1
  108. package/dist/file/provider/s3.provider.d.ts +5 -0
  109. package/dist/file/provider/s3.provider.d.ts.map +1 -1
  110. package/dist/file/provider/s3.provider.js +15 -0
  111. package/dist/file/provider/s3.provider.js.map +1 -1
  112. package/dist/file/provider/spaces.provider.d.ts +5 -0
  113. package/dist/file/provider/spaces.provider.d.ts.map +1 -1
  114. package/dist/file/provider/spaces.provider.js +16 -0
  115. package/dist/file/provider/spaces.provider.js.map +1 -1
  116. package/dist/impersonation/dto/redeem-impersonation.dto.d.ts +4 -0
  117. package/dist/impersonation/dto/redeem-impersonation.dto.d.ts.map +1 -0
  118. package/dist/impersonation/dto/redeem-impersonation.dto.js +23 -0
  119. package/dist/impersonation/dto/redeem-impersonation.dto.js.map +1 -0
  120. package/dist/impersonation/dto/start-impersonation.dto.d.ts +7 -0
  121. package/dist/impersonation/dto/start-impersonation.dto.d.ts.map +1 -0
  122. package/dist/impersonation/dto/start-impersonation.dto.js +27 -0
  123. package/dist/impersonation/dto/start-impersonation.dto.js.map +1 -0
  124. package/dist/impersonation/impersonation-restrictions.d.ts +26 -0
  125. package/dist/impersonation/impersonation-restrictions.d.ts.map +1 -0
  126. package/dist/impersonation/impersonation-restrictions.js +76 -0
  127. package/dist/impersonation/impersonation-restrictions.js.map +1 -0
  128. package/dist/impersonation/impersonation.controller.d.ts +90 -0
  129. package/dist/impersonation/impersonation.controller.d.ts.map +1 -0
  130. package/dist/impersonation/impersonation.controller.js +135 -0
  131. package/dist/impersonation/impersonation.controller.js.map +1 -0
  132. package/dist/impersonation/impersonation.module.d.ts +8 -0
  133. package/dist/impersonation/impersonation.module.d.ts.map +1 -0
  134. package/dist/impersonation/impersonation.module.js +44 -0
  135. package/dist/impersonation/impersonation.module.js.map +1 -0
  136. package/dist/impersonation/impersonation.service.d.ts +164 -0
  137. package/dist/impersonation/impersonation.service.d.ts.map +1 -0
  138. package/dist/impersonation/impersonation.service.js +408 -0
  139. package/dist/impersonation/impersonation.service.js.map +1 -0
  140. package/dist/index.d.ts +17 -0
  141. package/dist/index.d.ts.map +1 -1
  142. package/dist/index.js +19 -0
  143. package/dist/index.js.map +1 -1
  144. package/dist/integration/services/outbox-polling.coordinator.d.ts +2 -0
  145. package/dist/integration/services/outbox-polling.coordinator.d.ts.map +1 -1
  146. package/dist/integration/services/outbox-polling.coordinator.js +50 -30
  147. package/dist/integration/services/outbox-polling.coordinator.js.map +1 -1
  148. package/dist/integration/services/outbox.service.d.ts.map +1 -1
  149. package/dist/integration/services/outbox.service.js +5 -1
  150. package/dist/integration/services/outbox.service.js.map +1 -1
  151. package/dist/integration-profile/integration-profile.secrets.d.ts.map +1 -1
  152. package/dist/integration-profile/integration-profile.secrets.js +3 -0
  153. package/dist/integration-profile/integration-profile.secrets.js.map +1 -1
  154. package/dist/integration-profile/integration-profile.utils.d.ts +14 -0
  155. package/dist/integration-profile/integration-profile.utils.d.ts.map +1 -1
  156. package/dist/integration-profile/integration-profile.utils.js +26 -0
  157. package/dist/integration-profile/integration-profile.utils.js.map +1 -1
  158. package/dist/integration-profile/testers/email.testers.d.ts.map +1 -1
  159. package/dist/integration-profile/testers/email.testers.js +28 -0
  160. package/dist/integration-profile/testers/email.testers.js.map +1 -1
  161. package/dist/language/en.json +11 -0
  162. package/dist/language/pt.json +11 -0
  163. package/dist/mail/dto/send.dto.d.ts +38 -1
  164. package/dist/mail/dto/send.dto.d.ts.map +1 -1
  165. package/dist/mail/dto/send.dto.js +10 -0
  166. package/dist/mail/dto/send.dto.js.map +1 -1
  167. package/dist/mail/mail.controller.d.ts +1 -0
  168. package/dist/mail/mail.controller.d.ts.map +1 -1
  169. package/dist/mail/mail.module.d.ts.map +1 -1
  170. package/dist/mail/mail.module.js +2 -0
  171. package/dist/mail/mail.module.js.map +1 -1
  172. package/dist/mail/mail.service.d.ts +48 -4
  173. package/dist/mail/mail.service.d.ts.map +1 -1
  174. package/dist/mail/mail.service.js +187 -35
  175. package/dist/mail/mail.service.js.map +1 -1
  176. package/dist/mail-delivery/mail-delivery-provision.service.d.ts +21 -0
  177. package/dist/mail-delivery/mail-delivery-provision.service.d.ts.map +1 -0
  178. package/dist/mail-delivery/mail-delivery-provision.service.js +64 -0
  179. package/dist/mail-delivery/mail-delivery-provision.service.js.map +1 -0
  180. package/dist/mail-delivery/mail-delivery.constants.d.ts +17 -0
  181. package/dist/mail-delivery/mail-delivery.constants.d.ts.map +1 -0
  182. package/dist/mail-delivery/mail-delivery.constants.js +31 -0
  183. package/dist/mail-delivery/mail-delivery.constants.js.map +1 -0
  184. package/dist/mail-delivery/mail-delivery.controller.d.ts +19 -0
  185. package/dist/mail-delivery/mail-delivery.controller.d.ts.map +1 -0
  186. package/dist/mail-delivery/mail-delivery.controller.js +53 -0
  187. package/dist/mail-delivery/mail-delivery.controller.js.map +1 -0
  188. package/dist/mail-delivery/mail-delivery.module.d.ts +7 -0
  189. package/dist/mail-delivery/mail-delivery.module.d.ts.map +1 -0
  190. package/dist/mail-delivery/mail-delivery.module.js +36 -0
  191. package/dist/mail-delivery/mail-delivery.module.js.map +1 -0
  192. package/dist/mail-delivery/mail-delivery.service.d.ts +38 -0
  193. package/dist/mail-delivery/mail-delivery.service.d.ts.map +1 -0
  194. package/dist/mail-delivery/mail-delivery.service.js +140 -0
  195. package/dist/mail-delivery/mail-delivery.service.js.map +1 -0
  196. package/dist/mail-delivery/ses-event.parser.d.ts +27 -0
  197. package/dist/mail-delivery/ses-event.parser.d.ts.map +1 -0
  198. package/dist/mail-delivery/ses-event.parser.js +131 -0
  199. package/dist/mail-delivery/ses-event.parser.js.map +1 -0
  200. package/dist/mail-delivery/ses-webhook.service.d.ts +58 -0
  201. package/dist/mail-delivery/ses-webhook.service.d.ts.map +1 -0
  202. package/dist/mail-delivery/ses-webhook.service.js +214 -0
  203. package/dist/mail-delivery/ses-webhook.service.js.map +1 -0
  204. package/dist/mail-delivery/sns-message.util.d.ts +38 -0
  205. package/dist/mail-delivery/sns-message.util.d.ts.map +1 -0
  206. package/dist/mail-delivery/sns-message.util.js +109 -0
  207. package/dist/mail-delivery/sns-message.util.js.map +1 -0
  208. package/dist/mail-sent/dto/query-mail-sent-list.dto.d.ts +5 -0
  209. package/dist/mail-sent/dto/query-mail-sent-list.dto.d.ts.map +1 -1
  210. package/dist/mail-sent/dto/query-mail-sent-list.dto.js +6 -0
  211. package/dist/mail-sent/dto/query-mail-sent-list.dto.js.map +1 -1
  212. package/dist/mail-sent/mail-sent.controller.d.ts +39 -0
  213. package/dist/mail-sent/mail-sent.controller.d.ts.map +1 -1
  214. package/dist/mail-sent/mail-sent.service.d.ts +39 -0
  215. package/dist/mail-sent/mail-sent.service.d.ts.map +1 -1
  216. package/dist/mail-sent/mail-sent.service.js +45 -4
  217. package/dist/mail-sent/mail-sent.service.js.map +1 -1
  218. package/dist/mailbox/mailbox-fetcher.registry.d.ts +100 -0
  219. package/dist/mailbox/mailbox-fetcher.registry.d.ts.map +1 -0
  220. package/dist/mailbox/mailbox-fetcher.registry.js +59 -0
  221. package/dist/mailbox/mailbox-fetcher.registry.js.map +1 -0
  222. package/dist/mailbox/mailbox.module.d.ts +8 -0
  223. package/dist/mailbox/mailbox.module.d.ts.map +1 -0
  224. package/dist/mailbox/mailbox.module.js +27 -0
  225. package/dist/mailbox/mailbox.module.js.map +1 -0
  226. package/dist/meeting/meeting-provider.registry.d.ts +155 -0
  227. package/dist/meeting/meeting-provider.registry.d.ts.map +1 -0
  228. package/dist/meeting/meeting-provider.registry.js +53 -0
  229. package/dist/meeting/meeting-provider.registry.js.map +1 -0
  230. package/dist/meeting/meeting.constants.d.ts +47 -0
  231. package/dist/meeting/meeting.constants.d.ts.map +1 -0
  232. package/dist/meeting/meeting.constants.js +21 -0
  233. package/dist/meeting/meeting.constants.js.map +1 -0
  234. package/dist/meeting/meeting.module.d.ts +7 -0
  235. package/dist/meeting/meeting.module.d.ts.map +1 -0
  236. package/dist/meeting/meeting.module.js +26 -0
  237. package/dist/meeting/meeting.module.js.map +1 -0
  238. package/dist/middlewares/locale-injection.middleware.d.ts +12 -0
  239. package/dist/middlewares/locale-injection.middleware.d.ts.map +1 -1
  240. package/dist/middlewares/locale-injection.middleware.js +20 -4
  241. package/dist/middlewares/locale-injection.middleware.js.map +1 -1
  242. package/dist/oauth/providers/google.provider.d.ts +7 -0
  243. package/dist/oauth/providers/google.provider.d.ts.map +1 -1
  244. package/dist/oauth/providers/google.provider.js +43 -13
  245. package/dist/oauth/providers/google.provider.js.map +1 -1
  246. package/dist/observability/monitored-cron.d.ts +34 -0
  247. package/dist/observability/monitored-cron.d.ts.map +1 -0
  248. package/dist/observability/monitored-cron.js +118 -0
  249. package/dist/observability/monitored-cron.js.map +1 -0
  250. package/dist/pairing/dto/approve-reverse-pairing.dto.d.ts +12 -0
  251. package/dist/pairing/dto/approve-reverse-pairing.dto.d.ts.map +1 -0
  252. package/dist/pairing/dto/approve-reverse-pairing.dto.js +30 -0
  253. package/dist/pairing/dto/approve-reverse-pairing.dto.js.map +1 -0
  254. package/dist/pairing/dto/claim-pairing.dto.d.ts +11 -0
  255. package/dist/pairing/dto/claim-pairing.dto.d.ts.map +1 -0
  256. package/dist/pairing/dto/claim-pairing.dto.js +35 -0
  257. package/dist/pairing/dto/claim-pairing.dto.js.map +1 -0
  258. package/dist/pairing/dto/confirm-pairing.dto.d.ts +10 -0
  259. package/dist/pairing/dto/confirm-pairing.dto.d.ts.map +1 -0
  260. package/dist/pairing/dto/confirm-pairing.dto.js +24 -0
  261. package/dist/pairing/dto/confirm-pairing.dto.js.map +1 -0
  262. package/dist/pairing/dto/poll-reverse-pairing.dto.d.ts +5 -0
  263. package/dist/pairing/dto/poll-reverse-pairing.dto.d.ts.map +1 -0
  264. package/dist/pairing/dto/poll-reverse-pairing.dto.js +24 -0
  265. package/dist/pairing/dto/poll-reverse-pairing.dto.js.map +1 -0
  266. package/dist/pairing/dto/start-pairing.dto.d.ts +11 -0
  267. package/dist/pairing/dto/start-pairing.dto.d.ts.map +1 -0
  268. package/dist/pairing/dto/start-pairing.dto.js +30 -0
  269. package/dist/pairing/dto/start-pairing.dto.js.map +1 -0
  270. package/dist/pairing/dto/start-reverse-pairing.dto.d.ts +24 -0
  271. package/dist/pairing/dto/start-reverse-pairing.dto.d.ts.map +1 -0
  272. package/dist/pairing/dto/start-reverse-pairing.dto.js +47 -0
  273. package/dist/pairing/dto/start-reverse-pairing.dto.js.map +1 -0
  274. package/dist/pairing/pairing.controller.d.ts +118 -0
  275. package/dist/pairing/pairing.controller.d.ts.map +1 -0
  276. package/dist/pairing/pairing.controller.js +296 -0
  277. package/dist/pairing/pairing.controller.js.map +1 -0
  278. package/dist/pairing/pairing.module.d.ts +10 -0
  279. package/dist/pairing/pairing.module.d.ts.map +1 -0
  280. package/dist/pairing/pairing.module.js +40 -0
  281. package/dist/pairing/pairing.module.js.map +1 -0
  282. package/dist/pairing/pairing.service.d.ts +238 -0
  283. package/dist/pairing/pairing.service.d.ts.map +1 -0
  284. package/dist/pairing/pairing.service.js +495 -0
  285. package/dist/pairing/pairing.service.js.map +1 -0
  286. package/dist/pdf/pdf.service.d.ts +3 -6
  287. package/dist/pdf/pdf.service.d.ts.map +1 -1
  288. package/dist/pdf/pdf.service.js +8 -20
  289. package/dist/pdf/pdf.service.js.map +1 -1
  290. package/dist/profile/profile.controller.d.ts +11 -0
  291. package/dist/profile/profile.controller.d.ts.map +1 -1
  292. package/dist/profile/profile.service.d.ts +11 -0
  293. package/dist/profile/profile.service.d.ts.map +1 -1
  294. package/dist/profile/profile.service.js +20 -11
  295. package/dist/profile/profile.service.js.map +1 -1
  296. package/dist/redis/redis-pubsub.d.ts.map +1 -1
  297. package/dist/redis/redis-pubsub.js +44 -0
  298. package/dist/redis/redis-pubsub.js.map +1 -1
  299. package/dist/role/guards/role.guard.d.ts +5 -0
  300. package/dist/role/guards/role.guard.d.ts.map +1 -1
  301. package/dist/role/guards/role.guard.js +41 -39
  302. package/dist/role/guards/role.guard.js.map +1 -1
  303. package/dist/session/session.controller.d.ts +2 -0
  304. package/dist/session/session.controller.d.ts.map +1 -1
  305. package/dist/session/session.service.d.ts +39 -0
  306. package/dist/session/session.service.d.ts.map +1 -1
  307. package/dist/session/session.service.js +91 -8
  308. package/dist/session/session.service.js.map +1 -1
  309. package/dist/setting/brand-asset.service.d.ts +48 -0
  310. package/dist/setting/brand-asset.service.d.ts.map +1 -0
  311. package/dist/setting/brand-asset.service.js +130 -0
  312. package/dist/setting/brand-asset.service.js.map +1 -0
  313. package/dist/setting/setting.module.d.ts.map +1 -1
  314. package/dist/setting/setting.module.js +3 -2
  315. package/dist/setting/setting.module.js.map +1 -1
  316. package/dist/setting/setting.service.d.ts +33 -0
  317. package/dist/setting/setting.service.d.ts.map +1 -1
  318. package/dist/setting/setting.service.js +88 -0
  319. package/dist/setting/setting.service.js.map +1 -1
  320. package/dist/token/token.service.d.ts +23 -2
  321. package/dist/token/token.service.d.ts.map +1 -1
  322. package/dist/token/token.service.js +39 -4
  323. package/dist/token/token.service.js.map +1 -1
  324. package/dist/user/user.controller.d.ts +8 -22
  325. package/dist/user/user.controller.d.ts.map +1 -1
  326. package/dist/user/user.service.d.ts +44 -24
  327. package/dist/user/user.service.d.ts.map +1 -1
  328. package/dist/user/user.service.js +89 -6
  329. package/dist/user/user.service.js.map +1 -1
  330. package/dist/user-device/user-device.controller.d.ts +54 -0
  331. package/dist/user-device/user-device.controller.d.ts.map +1 -0
  332. package/dist/user-device/user-device.controller.js +103 -0
  333. package/dist/user-device/user-device.controller.js.map +1 -0
  334. package/dist/user-device/user-device.module.d.ts +3 -0
  335. package/dist/user-device/user-device.module.d.ts.map +1 -0
  336. package/dist/user-device/user-device.module.js +26 -0
  337. package/dist/user-device/user-device.module.js.map +1 -0
  338. package/dist/user-device/user-device.service.d.ts +71 -0
  339. package/dist/user-device/user-device.service.d.ts.map +1 -0
  340. package/dist/user-device/user-device.service.js +158 -0
  341. package/dist/user-device/user-device.service.js.map +1 -0
  342. package/dist/utils/device-key.d.ts +23 -0
  343. package/dist/utils/device-key.d.ts.map +1 -0
  344. package/dist/utils/device-key.js +31 -0
  345. package/dist/utils/device-key.js.map +1 -0
  346. package/dist/utils/geo-ip.d.ts +38 -0
  347. package/dist/utils/geo-ip.d.ts.map +1 -0
  348. package/dist/utils/geo-ip.js +122 -0
  349. package/dist/utils/geo-ip.js.map +1 -0
  350. package/dist/utils/locale-context.d.ts +10 -7
  351. package/dist/utils/locale-context.d.ts.map +1 -1
  352. package/dist/utils/locale-context.js +14 -8
  353. package/dist/utils/locale-context.js.map +1 -1
  354. package/dist/utils/security-event-vars.d.ts +56 -0
  355. package/dist/utils/security-event-vars.d.ts.map +1 -0
  356. package/dist/utils/security-event-vars.js +109 -0
  357. package/dist/utils/security-event-vars.js.map +1 -0
  358. package/dist/utils/user-agent.d.ts +19 -0
  359. package/dist/utils/user-agent.d.ts.map +1 -0
  360. package/dist/utils/user-agent.js +36 -0
  361. package/dist/utils/user-agent.js.map +1 -0
  362. package/dist/webhook-integration/webhook-integration.service.d.ts +5 -0
  363. package/dist/webhook-integration/webhook-integration.service.d.ts.map +1 -1
  364. package/dist/webhook-integration/webhook-integration.service.js +50 -4
  365. package/dist/webhook-integration/webhook-integration.service.js.map +1 -1
  366. package/dist/webhook-integration/webhook-protocol.registry.d.ts +6 -0
  367. package/dist/webhook-integration/webhook-protocol.registry.d.ts.map +1 -1
  368. package/dist/webhook-integration/webhook-protocol.registry.js.map +1 -1
  369. package/hedhog/data/integration_provider.yaml +9 -0
  370. package/hedhog/data/mail.yaml +198 -62
  371. package/hedhog/data/mail_layout.yaml +43 -33
  372. package/hedhog/data/menu.yaml +2 -0
  373. package/hedhog/data/role.yaml +16 -0
  374. package/hedhog/data/route.yaml +172 -3
  375. package/hedhog/data/setting_group.yaml +178 -2
  376. package/hedhog/data/setting_subgroup.yaml +8 -0
  377. package/hedhog/frontend/app/_lib/hooks/use-core-access.test.tsx.ejs +125 -0
  378. package/hedhog/frontend/app/_lib/hooks/use-core-access.ts.ejs +29 -0
  379. package/hedhog/frontend/app/_lib/hooks/use-impersonation-access.test.ts.ejs +71 -0
  380. package/hedhog/frontend/app/_lib/hooks/use-impersonation-access.ts.ejs +32 -0
  381. package/hedhog/frontend/app/access-log/page.tsx.ejs +96 -22
  382. package/hedhog/frontend/app/account/components/active-sessions.tsx.ejs +17 -1
  383. package/hedhog/frontend/app/account/components/known-devices.tsx.ejs +89 -0
  384. package/hedhog/frontend/app/account/components/profile-form.tsx.ejs +2 -1
  385. package/hedhog/frontend/app/account/components/user-devices-list.tsx.ejs +186 -0
  386. package/hedhog/frontend/app/account/devices/page.tsx.ejs +5 -0
  387. package/hedhog/frontend/app/account/layout.tsx.ejs +2 -0
  388. package/hedhog/frontend/app/configurations/[slug]/components/setting-field.test.tsx.ejs +298 -0
  389. package/hedhog/frontend/app/configurations/[slug]/components/setting-field.tsx.ejs +376 -1236
  390. package/hedhog/frontend/app/mail/log/page.tsx.ejs +210 -3
  391. package/hedhog/frontend/app/mail/template/page.tsx.ejs +190 -132
  392. package/hedhog/frontend/app/users/active-session.tsx.ejs +58 -11
  393. package/hedhog/frontend/app/users/page.tsx.ejs +69 -10
  394. package/hedhog/frontend/app/users/simulate-access-dialog.test.tsx.ejs +202 -0
  395. package/hedhog/frontend/app/users/simulate-access-dialog.tsx.ejs +170 -0
  396. package/hedhog/frontend/app/users/user-activity-timeline.tsx.ejs +19 -0
  397. package/hedhog/frontend/app/users/user-devices.tsx.ejs +89 -0
  398. package/hedhog/frontend/app/users/user-logs.tsx.ejs +13 -1
  399. package/hedhog/frontend/app/users/user-sheet.tsx.ejs +46 -24
  400. package/hedhog/frontend/messages/en.json +146 -48
  401. package/hedhog/frontend/messages/pt.json +146 -48
  402. package/hedhog/table/access_log.yaml +7 -0
  403. package/hedhog/table/file.yaml +8 -0
  404. package/hedhog/table/mail_delivery_event.yaml +76 -0
  405. package/hedhog/table/mail_sent.yaml +23 -0
  406. package/hedhog/table/user_activity.yaml +9 -0
  407. package/hedhog/table/user_device.yaml +52 -0
  408. package/hedhog/table/user_session.yaml +20 -1
  409. package/package.json +6 -5
  410. package/src/access-log/access-log.controller.ts +1 -0
  411. package/src/access-log/access-log.interceptor.ts +5 -1
  412. package/src/access-log/access-log.service.spec.ts +33 -2
  413. package/src/access-log/access-log.service.ts +38 -0
  414. package/src/access-log/dto/query-access-log.dto.ts +5 -0
  415. package/src/ai/ai.controller.ts +9 -0
  416. package/src/ai/ai.module.ts +3 -2
  417. package/src/ai/ai.service.ts +150 -13
  418. package/src/ai/dto/richtext-edit-html.dto.ts +11 -0
  419. package/src/ai/richtext-ai.prompts.ts +57 -0
  420. package/src/ai/richtext-ai.service.ts +109 -0
  421. package/src/auth/auth.controller.ts +47 -8
  422. package/src/auth/auth.module.ts +2 -0
  423. package/src/auth/auth.service.spec.ts +383 -6
  424. package/src/auth/auth.service.ts +345 -56
  425. package/src/auth/dto/confirm-email.dto.ts +7 -0
  426. package/src/auth/dto/resend-confirmation.dto.ts +20 -0
  427. package/src/authorize/authorize.controller.ts +2 -0
  428. package/src/authorize/authorize.service.spec.ts +23 -0
  429. package/src/authorize/authorize.service.ts +8 -0
  430. package/src/challenge/challenge.service.spec.ts +73 -0
  431. package/src/challenge/challenge.service.ts +62 -3
  432. package/src/core.module.ts +19 -0
  433. package/src/file/file.controller.ts +54 -4
  434. package/src/file/file.service.spec.ts +275 -105
  435. package/src/file/file.service.ts +409 -14
  436. package/src/file/image-optimization.service.spec.ts +92 -0
  437. package/src/file/image-optimization.service.ts +202 -0
  438. package/src/file/provider/abstract.provider.ts +23 -0
  439. package/src/file/provider/gcs.provider.ts +17 -0
  440. package/src/file/provider/local.provider.ts +21 -0
  441. package/src/file/provider/s3.provider.ts +25 -0
  442. package/src/file/provider/spaces.provider.ts +26 -0
  443. package/src/impersonation/dto/redeem-impersonation.dto.ts +8 -0
  444. package/src/impersonation/dto/start-impersonation.dto.ts +13 -0
  445. package/src/impersonation/impersonation-restrictions.ts +84 -0
  446. package/src/impersonation/impersonation.controller.ts +109 -0
  447. package/src/impersonation/impersonation.module.ts +31 -0
  448. package/src/impersonation/impersonation.service.spec.ts +427 -0
  449. package/src/impersonation/impersonation.service.ts +577 -0
  450. package/src/index.ts +21 -0
  451. package/src/integration/services/outbox-polling.coordinator.spec.ts +90 -0
  452. package/src/integration/services/outbox-polling.coordinator.ts +62 -40
  453. package/src/integration/services/outbox.service.spec.ts +8 -0
  454. package/src/integration/services/outbox.service.ts +19 -13
  455. package/src/integration-profile/integration-profile.secrets.ts +3 -0
  456. package/src/integration-profile/integration-profile.utils.ts +38 -0
  457. package/src/integration-profile/testers/email.testers.ts +34 -1
  458. package/src/language/en.json +11 -0
  459. package/src/language/pt.json +11 -0
  460. package/src/mail/dto/send.dto.ts +46 -2
  461. package/src/mail/mail-template.spec.ts +79 -2
  462. package/src/mail/mail.module.ts +2 -0
  463. package/src/mail/mail.service.spec.ts +307 -6
  464. package/src/mail/mail.service.ts +227 -30
  465. package/src/mail-delivery/mail-delivery-provision.service.ts +66 -0
  466. package/src/mail-delivery/mail-delivery.constants.ts +31 -0
  467. package/src/mail-delivery/mail-delivery.controller.ts +38 -0
  468. package/src/mail-delivery/mail-delivery.module.ts +23 -0
  469. package/src/mail-delivery/mail-delivery.service.spec.ts +136 -0
  470. package/src/mail-delivery/mail-delivery.service.ts +152 -0
  471. package/src/mail-delivery/ses-event.parser.spec.ts +140 -0
  472. package/src/mail-delivery/ses-event.parser.ts +191 -0
  473. package/src/mail-delivery/ses-webhook.service.spec.ts +170 -0
  474. package/src/mail-delivery/ses-webhook.service.ts +240 -0
  475. package/src/mail-delivery/sns-message.util.spec.ts +163 -0
  476. package/src/mail-delivery/sns-message.util.ts +125 -0
  477. package/src/mail-sent/dto/query-mail-sent-list.dto.ts +15 -0
  478. package/src/mail-sent/mail-sent.service.ts +46 -2
  479. package/src/mailbox/mailbox-fetcher.registry.ts +132 -0
  480. package/src/mailbox/mailbox.module.ts +14 -0
  481. package/src/meeting/meeting-provider.registry.ts +193 -0
  482. package/src/meeting/meeting.constants.ts +53 -0
  483. package/src/meeting/meeting.module.ts +13 -0
  484. package/src/middlewares/locale-injection.middleware.ts +25 -6
  485. package/src/oauth/providers/google.provider.ts +49 -15
  486. package/src/observability/monitored-cron.spec.ts +102 -0
  487. package/src/observability/monitored-cron.ts +110 -0
  488. package/src/pairing/dto/approve-reverse-pairing.dto.ts +20 -0
  489. package/src/pairing/dto/claim-pairing.dto.ts +19 -0
  490. package/src/pairing/dto/confirm-pairing.dto.ts +14 -0
  491. package/src/pairing/dto/poll-reverse-pairing.dto.ts +9 -0
  492. package/src/pairing/dto/start-pairing.dto.ts +19 -0
  493. package/src/pairing/dto/start-reverse-pairing.dto.ts +45 -0
  494. package/src/pairing/pairing.controller.ts +246 -0
  495. package/src/pairing/pairing.module.ts +27 -0
  496. package/src/pairing/pairing.service.spec.ts +462 -0
  497. package/src/pairing/pairing.service.ts +614 -0
  498. package/src/pdf/pdf.service.ts +6 -24
  499. package/src/profile/profile.service.ts +26 -8
  500. package/src/redis/redis-pubsub.ts +11 -0
  501. package/src/role/guards/role.guard.spec.ts +75 -0
  502. package/src/role/guards/role.guard.ts +64 -46
  503. package/src/session/session.service.spec.ts +81 -0
  504. package/src/session/session.service.ts +93 -6
  505. package/src/setting/brand-asset.service.ts +137 -0
  506. package/src/setting/setting.module.ts +3 -2
  507. package/src/setting/setting.service.spec.ts +79 -1
  508. package/src/setting/setting.service.ts +109 -1
  509. package/src/token/token.service.spec.ts +62 -0
  510. package/src/token/token.service.ts +57 -3
  511. package/src/user/user.service.spec.ts +33 -2
  512. package/src/user/user.service.ts +108 -6
  513. package/src/user-device/user-device.controller.ts +77 -0
  514. package/src/user-device/user-device.module.ts +13 -0
  515. package/src/user-device/user-device.service.spec.ts +234 -0
  516. package/src/user-device/user-device.service.ts +168 -0
  517. package/src/utils/device-key.spec.ts +57 -0
  518. package/src/utils/device-key.ts +32 -0
  519. package/src/utils/geo-ip.spec.ts +134 -0
  520. package/src/utils/geo-ip.ts +93 -0
  521. package/src/utils/locale-context.spec.ts +27 -1
  522. package/src/utils/locale-context.ts +15 -12
  523. package/src/utils/security-event-vars.spec.ts +161 -0
  524. package/src/utils/security-event-vars.ts +153 -0
  525. package/src/utils/user-agent.spec.ts +37 -0
  526. package/src/utils/user-agent.ts +46 -0
  527. package/src/webhook-integration/webhook-integration.service.ts +57 -3
  528. package/src/webhook-integration/webhook-protocol.registry.ts +6 -0
@@ -0,0 +1 @@
1
+ {"version":3,"file":"user-device.controller.js","sourceRoot":"","sources":["../../src/user-device/user-device.controller.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;AAAA,sCAA0C;AAC1C,4DAAoE;AACpE,2CAOwB;AACxB,+DAA0D;AAInD,IAAM,oBAAoB,GAA1B,MAAM,oBAAoB;IAC/B,YAA6B,iBAAoC;QAApC,sBAAiB,GAAjB,iBAAiB,CAAmB;IAAG,CAAC;IAErE;;;;;;;OAOG;IAEG,AAAN,KAAK,CAAC,IAAI,CACM,gBAA+B,EACrC,EAAE,EAAE,EAAE,EACS,SAAiB,EACf,SAAiB;QAE1C,OAAO,IAAI,CAAC,iBAAiB,CAAC,IAAI,CAAC,gBAAgB,EAAE,EAAE,EAAE;YACvD,SAAS,EAAE,SAAS,IAAI,IAAI;YAC5B,SAAS,EAAE,SAAS,IAAI,IAAI;SAC7B,CAAC,CAAC;IACL,CAAC;IAED;;;;;OAKG;IAEG,AAAN,KAAK,CAAC,MAAM,CACF,EAAE,EAAE,EAAE,EACmB,QAAgB;QAEjD,OAAO,IAAI,CAAC,iBAAiB,CAAC,MAAM,CAAC,EAAE,EAAE,QAAQ,CAAC,CAAC;IACrD,CAAC;IAED;;;;OAIG;IAEG,AAAN,KAAK,CAAC,WAAW,CACD,gBAA+B,EACd,MAAc;QAE7C,OAAO,IAAI,CAAC,iBAAiB,CAAC,IAAI,CAAC,gBAAgB,EAAE,MAAM,CAAC,CAAC;IAC/D,CAAC;IAED;;;OAGG;IAEG,AAAN,KAAK,CAAC,aAAa,CACc,MAAc,EACZ,QAAgB;QAEjD,OAAO,IAAI,CAAC,iBAAiB,CAAC,MAAM,CAAC,MAAM,EAAE,QAAQ,CAAC,CAAC;IACzD,CAAC;CACF,CAAA;AA9DY,oDAAoB;AAYzB;IADL,IAAA,YAAG,GAAE;IAEH,WAAA,IAAA,2BAAU,GAAE,CAAA;IACZ,WAAA,IAAA,UAAI,GAAE,CAAA;IACN,WAAA,IAAA,gBAAO,EAAC,YAAY,CAAC,CAAA;IACrB,WAAA,IAAA,gBAAO,EAAC,cAAc,CAAC,CAAA;;qCAHQ,8BAAa;;gDAS9C;AASK;IADL,IAAA,eAAM,EAAC,WAAW,CAAC;IAEjB,WAAA,IAAA,UAAI,GAAE,CAAA;IACN,WAAA,IAAA,cAAK,EAAC,UAAU,EAAE,qBAAY,CAAC,CAAA;;;;kDAGjC;AAQK;IADL,IAAA,YAAG,EAAC,cAAc,CAAC;IAEjB,WAAA,IAAA,2BAAU,GAAE,CAAA;IACZ,WAAA,IAAA,cAAK,EAAC,QAAQ,EAAE,qBAAY,CAAC,CAAA;;qCADE,8BAAa;;uDAI9C;AAOK;IADL,IAAA,eAAM,EAAC,wBAAwB,CAAC;IAE9B,WAAA,IAAA,cAAK,EAAC,QAAQ,EAAE,qBAAY,CAAC,CAAA;IAC7B,WAAA,IAAA,cAAK,EAAC,UAAU,EAAE,qBAAY,CAAC,CAAA;;;;yDAGjC;+BA7DU,oBAAoB;IAFhC,IAAA,UAAI,GAAE;IACN,IAAA,mBAAU,EAAC,aAAa,CAAC;qCAEwB,uCAAiB;GADtD,oBAAoB,CA8DhC"}
@@ -0,0 +1,3 @@
1
+ export declare class UserDeviceModule {
2
+ }
3
+ //# sourceMappingURL=user-device.module.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"user-device.module.d.ts","sourceRoot":"","sources":["../../src/user-device/user-device.module.ts"],"names":[],"mappings":"AAMA,qBAMa,gBAAgB;CAAG"}
@@ -0,0 +1,26 @@
1
+ "use strict";
2
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
7
+ };
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ exports.UserDeviceModule = void 0;
10
+ const api_pagination_1 = require("@hed-hog/api-pagination");
11
+ const api_prisma_1 = require("@hed-hog/api-prisma");
12
+ const common_1 = require("@nestjs/common");
13
+ const user_device_controller_1 = require("./user-device.controller");
14
+ const user_device_service_1 = require("./user-device.service");
15
+ let UserDeviceModule = class UserDeviceModule {
16
+ };
17
+ exports.UserDeviceModule = UserDeviceModule;
18
+ exports.UserDeviceModule = UserDeviceModule = __decorate([
19
+ (0, common_1.Module)({
20
+ imports: [(0, common_1.forwardRef)(() => api_prisma_1.PrismaModule), (0, common_1.forwardRef)(() => api_pagination_1.PaginationModule)],
21
+ controllers: [user_device_controller_1.UserDeviceController],
22
+ providers: [user_device_service_1.UserDeviceService],
23
+ exports: [user_device_service_1.UserDeviceService],
24
+ })
25
+ ], UserDeviceModule);
26
+ //# sourceMappingURL=user-device.module.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"user-device.module.js","sourceRoot":"","sources":["../../src/user-device/user-device.module.ts"],"names":[],"mappings":";;;;;;;;;AAAA,4DAA2D;AAC3D,oDAAmD;AACnD,2CAAoD;AACpD,qEAAgE;AAChE,+DAA0D;AAQnD,IAAM,gBAAgB,GAAtB,MAAM,gBAAgB;CAAG,CAAA;AAAnB,4CAAgB;2BAAhB,gBAAgB;IAN5B,IAAA,eAAM,EAAC;QACN,OAAO,EAAE,CAAC,IAAA,mBAAU,EAAC,GAAG,EAAE,CAAC,yBAAY,CAAC,EAAE,IAAA,mBAAU,EAAC,GAAG,EAAE,CAAC,iCAAgB,CAAC,CAAC;QAC7E,WAAW,EAAE,CAAC,6CAAoB,CAAC;QACnC,SAAS,EAAE,CAAC,uCAAiB,CAAC;QAC9B,OAAO,EAAE,CAAC,uCAAiB,CAAC;KAC7B,CAAC;GACW,gBAAgB,CAAG"}
@@ -0,0 +1,71 @@
1
+ import { PaginationDTO, PaginationService } from '@hed-hog/api-pagination';
2
+ import { PrismaService } from '@hed-hog/api-prisma';
3
+ export interface DeviceFingerprint {
4
+ userAgent?: string | null;
5
+ browserId?: string | null;
6
+ ipAddress?: string | null;
7
+ }
8
+ /**
9
+ * Dispositivos ja vistos por usuario.
10
+ *
11
+ * Substitui a heuristica anterior, que procurava no historico de `user_session`
12
+ * para decidir se um login vinha de um dispositivo novo. Aquilo dependia de
13
+ * dados que a rotina de limpeza apaga: `clearExpiredSessions` remove sessoes
14
+ * expiradas com mais de `session-retention-days`, entao um dispositivo parado
15
+ * alguns meses saia do historico e era anunciado como novo de novo.
16
+ */
17
+ export declare class UserDeviceService {
18
+ private readonly prisma;
19
+ private readonly paginationService;
20
+ private readonly logger;
21
+ constructor(prisma: PrismaService, paginationService: PaginationService);
22
+ /**
23
+ * `true` quando o usuario ja tem dispositivos registrados e nenhum deles e
24
+ * este.
25
+ *
26
+ * O primeiro login da conta nunca conta como dispositivo novo: nao ha com o
27
+ * que comparar, e quem acabou de se cadastrar ja recebeu as boas-vindas.
28
+ *
29
+ * Tem que rodar ANTES de `remember`, que passa a conhecer o dispositivo atual.
30
+ */
31
+ isNewDevice(userId: number, userAgent?: string | null, browserId?: string | null): Promise<boolean>;
32
+ /**
33
+ * Registra o dispositivo ou atualiza o ultimo uso.
34
+ *
35
+ * Nunca lanca: isto roda dentro do fluxo de login, e falhar em anotar um
36
+ * dispositivo nao pode impedir alguem de entrar. O custo de engolir o erro e
37
+ * um alerta repetido no proximo login, nao um login perdido.
38
+ */
39
+ remember(userId: number, { userAgent, browserId, ipAddress }: DeviceFingerprint): Promise<void>;
40
+ /**
41
+ * Dispositivos de um usuario, do mais recente para o mais antigo.
42
+ *
43
+ * Paginado como a lista de sessoes: uma conta antiga acumula dezenas de
44
+ * dispositivos, e devolver tudo de uma vez entrega uma parede de linhas.
45
+ *
46
+ * A `device_key` e lida para marcar qual linha e o aparelho que fez esta
47
+ * chamada (`current`), mas nunca sai daqui: e derivada do browser_id, entao
48
+ * devolve-la seria entregar de graca o valor que identifica o dispositivo nas
49
+ * requisicoes. Sem `fingerprint` — o caso do admin olhando a lista de outra
50
+ * pessoa — nenhuma linha e a atual.
51
+ */
52
+ list(paginationParams: PaginationDTO, userId: number, fingerprint?: DeviceFingerprint): Promise<{
53
+ data: any;
54
+ total: any;
55
+ lastPage: number;
56
+ page: number;
57
+ pageSize: number;
58
+ }>;
59
+ /**
60
+ * Esquece um dispositivo. O proximo login vindo dele volta a disparar o
61
+ * alerta de dispositivo desconhecido — que e a reacao certa para "esse ai nao
62
+ * fui eu".
63
+ *
64
+ * O `user_id` entra no where junto com o id: sem ele, qualquer usuario
65
+ * autenticado apagaria o dispositivo de qualquer outro so por adivinhar o id.
66
+ */
67
+ forget(userId: number, deviceId: number): Promise<{
68
+ deleted: boolean;
69
+ }>;
70
+ }
71
+ //# sourceMappingURL=user-device.service.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"user-device.service.d.ts","sourceRoot":"","sources":["../../src/user-device/user-device.service.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,iBAAiB,EAAE,MAAM,yBAAyB,CAAC;AAC3E,OAAO,EAAE,aAAa,EAAE,MAAM,qBAAqB,CAAC;AAKpD,MAAM,WAAW,iBAAiB;IAChC,SAAS,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,SAAS,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1B,SAAS,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CAC3B;AAED;;;;;;;;GAQG;AACH,qBACa,iBAAiB;IAI1B,OAAO,CAAC,QAAQ,CAAC,MAAM;IAEvB,OAAO,CAAC,QAAQ,CAAC,iBAAiB;IALpC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAsC;gBAG1C,MAAM,EAAE,aAAa,EAErB,iBAAiB,EAAE,iBAAiB;IAGvD;;;;;;;;OAQG;IACG,WAAW,CACf,MAAM,EAAE,MAAM,EACd,SAAS,CAAC,EAAE,MAAM,GAAG,IAAI,EACzB,SAAS,CAAC,EAAE,MAAM,GAAG,IAAI,GACxB,OAAO,CAAC,OAAO,CAAC;IAiBnB;;;;;;OAMG;IACG,QAAQ,CACZ,MAAM,EAAE,MAAM,EACd,EAAE,SAAS,EAAE,SAAS,EAAE,SAAS,EAAE,EAAE,iBAAiB,GACrD,OAAO,CAAC,IAAI,CAAC;IA4BhB;;;;;;;;;;;OAWG;IACG,IAAI,CACR,gBAAgB,EAAE,aAAa,EAC/B,MAAM,EAAE,MAAM,EACd,WAAW,CAAC,EAAE,iBAAiB;;;;;;;IAsCjC;;;;;;;OAOG;IACG,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC;QAAE,OAAO,EAAE,OAAO,CAAA;KAAE,CAAC;CAO9E"}
@@ -0,0 +1,158 @@
1
+ "use strict";
2
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
7
+ };
8
+ var __metadata = (this && this.__metadata) || function (k, v) {
9
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
10
+ };
11
+ var __param = (this && this.__param) || function (paramIndex, decorator) {
12
+ return function (target, key) { decorator(target, key, paramIndex); }
13
+ };
14
+ var __rest = (this && this.__rest) || function (s, e) {
15
+ var t = {};
16
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
17
+ t[p] = s[p];
18
+ if (s != null && typeof Object.getOwnPropertySymbols === "function")
19
+ for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
20
+ if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
21
+ t[p[i]] = s[p[i]];
22
+ }
23
+ return t;
24
+ };
25
+ var UserDeviceService_1;
26
+ Object.defineProperty(exports, "__esModule", { value: true });
27
+ exports.UserDeviceService = void 0;
28
+ const api_pagination_1 = require("@hed-hog/api-pagination");
29
+ const api_prisma_1 = require("@hed-hog/api-prisma");
30
+ const common_1 = require("@nestjs/common");
31
+ const device_key_1 = require("../utils/device-key");
32
+ const user_agent_1 = require("../utils/user-agent");
33
+ /**
34
+ * Dispositivos ja vistos por usuario.
35
+ *
36
+ * Substitui a heuristica anterior, que procurava no historico de `user_session`
37
+ * para decidir se um login vinha de um dispositivo novo. Aquilo dependia de
38
+ * dados que a rotina de limpeza apaga: `clearExpiredSessions` remove sessoes
39
+ * expiradas com mais de `session-retention-days`, entao um dispositivo parado
40
+ * alguns meses saia do historico e era anunciado como novo de novo.
41
+ */
42
+ let UserDeviceService = UserDeviceService_1 = class UserDeviceService {
43
+ constructor(prisma, paginationService) {
44
+ this.prisma = prisma;
45
+ this.paginationService = paginationService;
46
+ this.logger = new common_1.Logger(UserDeviceService_1.name);
47
+ }
48
+ /**
49
+ * `true` quando o usuario ja tem dispositivos registrados e nenhum deles e
50
+ * este.
51
+ *
52
+ * O primeiro login da conta nunca conta como dispositivo novo: nao ha com o
53
+ * que comparar, e quem acabou de se cadastrar ja recebeu as boas-vindas.
54
+ *
55
+ * Tem que rodar ANTES de `remember`, que passa a conhecer o dispositivo atual.
56
+ */
57
+ async isNewDevice(userId, userAgent, browserId) {
58
+ const device_key = (0, device_key_1.buildDeviceKey)(userAgent, browserId);
59
+ const [anyDevice, knownDevice] = await Promise.all([
60
+ this.prisma.user_device.findFirst({
61
+ where: { user_id: userId },
62
+ select: { id: true },
63
+ }),
64
+ this.prisma.user_device.findUnique({
65
+ where: { user_id_device_key: { user_id: userId, device_key } },
66
+ select: { id: true },
67
+ }),
68
+ ]);
69
+ return Boolean(anyDevice) && !knownDevice;
70
+ }
71
+ /**
72
+ * Registra o dispositivo ou atualiza o ultimo uso.
73
+ *
74
+ * Nunca lanca: isto roda dentro do fluxo de login, e falhar em anotar um
75
+ * dispositivo nao pode impedir alguem de entrar. O custo de engolir o erro e
76
+ * um alerta repetido no proximo login, nao um login perdido.
77
+ */
78
+ async remember(userId, { userAgent, browserId, ipAddress }) {
79
+ var _a, _b;
80
+ const device_key = (0, device_key_1.buildDeviceKey)(userAgent, browserId);
81
+ const ua = (0, user_agent_1.parseUserAgent)(userAgent);
82
+ const seen = {
83
+ browser_id: (browserId !== null && browserId !== void 0 ? browserId : '').trim() || null,
84
+ user_agent: (userAgent !== null && userAgent !== void 0 ? userAgent : '').trim() || null,
85
+ browser_name: (_a = ua === null || ua === void 0 ? void 0 : ua.browser_name) !== null && _a !== void 0 ? _a : null,
86
+ os_name: (_b = ua === null || ua === void 0 ? void 0 : ua.os_name) !== null && _b !== void 0 ? _b : null,
87
+ last_ip: (ipAddress !== null && ipAddress !== void 0 ? ipAddress : '').trim() || null,
88
+ last_seen_at: new Date(),
89
+ };
90
+ try {
91
+ await this.prisma.user_device.upsert({
92
+ where: { user_id_device_key: { user_id: userId, device_key } },
93
+ create: Object.assign({ user_id: userId, device_key }, seen),
94
+ update: seen,
95
+ });
96
+ }
97
+ catch (error) {
98
+ this.logger.error(`Falha ao registrar dispositivo userId=${userId}: ${error instanceof Error ? error.message : String(error)}`);
99
+ }
100
+ }
101
+ /**
102
+ * Dispositivos de um usuario, do mais recente para o mais antigo.
103
+ *
104
+ * Paginado como a lista de sessoes: uma conta antiga acumula dezenas de
105
+ * dispositivos, e devolver tudo de uma vez entrega uma parede de linhas.
106
+ *
107
+ * A `device_key` e lida para marcar qual linha e o aparelho que fez esta
108
+ * chamada (`current`), mas nunca sai daqui: e derivada do browser_id, entao
109
+ * devolve-la seria entregar de graca o valor que identifica o dispositivo nas
110
+ * requisicoes. Sem `fingerprint` — o caso do admin olhando a lista de outra
111
+ * pessoa — nenhuma linha e a atual.
112
+ */
113
+ async list(paginationParams, userId, fingerprint) {
114
+ var _a;
115
+ const currentKey = fingerprint
116
+ ? (0, device_key_1.buildDeviceKey)(fingerprint.userAgent, fingerprint.browserId)
117
+ : null;
118
+ const paginate = await this.paginationService.paginatePrismaModel(this.prisma.user_device, Object.assign(Object.assign({}, paginationParams), { where: { user_id: userId }, select: {
119
+ id: true,
120
+ device_key: true,
121
+ browser_name: true,
122
+ os_name: true,
123
+ user_agent: true,
124
+ last_ip: true,
125
+ last_seen_at: true,
126
+ created_at: true,
127
+ },
128
+ // Explicito: sem isto a paginacao ordena crescente e a primeira pagina
129
+ // mostra os dispositivos mais antigos.
130
+ orderBy: { last_seen_at: 'desc' } }));
131
+ return Object.assign(Object.assign({}, paginate), { data: ((_a = paginate.data) !== null && _a !== void 0 ? _a : []).map((_a) => {
132
+ var { device_key } = _a, device = __rest(_a, ["device_key"]);
133
+ return (Object.assign(Object.assign({}, device), { current: Boolean(currentKey) && device_key === currentKey }));
134
+ }) });
135
+ }
136
+ /**
137
+ * Esquece um dispositivo. O proximo login vindo dele volta a disparar o
138
+ * alerta de dispositivo desconhecido — que e a reacao certa para "esse ai nao
139
+ * fui eu".
140
+ *
141
+ * O `user_id` entra no where junto com o id: sem ele, qualquer usuario
142
+ * autenticado apagaria o dispositivo de qualquer outro so por adivinhar o id.
143
+ */
144
+ async forget(userId, deviceId) {
145
+ const { count } = await this.prisma.user_device.deleteMany({
146
+ where: { id: deviceId, user_id: userId },
147
+ });
148
+ return { deleted: count > 0 };
149
+ }
150
+ };
151
+ exports.UserDeviceService = UserDeviceService;
152
+ exports.UserDeviceService = UserDeviceService = UserDeviceService_1 = __decorate([
153
+ (0, common_1.Injectable)(),
154
+ __param(1, (0, common_1.Inject)((0, common_1.forwardRef)(() => api_pagination_1.PaginationService))),
155
+ __metadata("design:paramtypes", [api_prisma_1.PrismaService,
156
+ api_pagination_1.PaginationService])
157
+ ], UserDeviceService);
158
+ //# sourceMappingURL=user-device.service.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"user-device.service.js","sourceRoot":"","sources":["../../src/user-device/user-device.service.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,4DAA2E;AAC3E,oDAAoD;AACpD,2CAAwE;AACxE,oDAAqD;AACrD,oDAAqD;AAQrD;;;;;;;;GAQG;AAEI,IAAM,iBAAiB,yBAAvB,MAAM,iBAAiB;IAG5B,YACmB,MAAqB,EAEtC,iBAAqD;QAFpC,WAAM,GAAN,MAAM,CAAe;QAErB,sBAAiB,GAAjB,iBAAiB,CAAmB;QALtC,WAAM,GAAG,IAAI,eAAM,CAAC,mBAAiB,CAAC,IAAI,CAAC,CAAC;IAM1D,CAAC;IAEJ;;;;;;;;OAQG;IACH,KAAK,CAAC,WAAW,CACf,MAAc,EACd,SAAyB,EACzB,SAAyB;QAEzB,MAAM,UAAU,GAAG,IAAA,2BAAc,EAAC,SAAS,EAAE,SAAS,CAAC,CAAC;QAExD,MAAM,CAAC,SAAS,EAAE,WAAW,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC;YACjD,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,SAAS,CAAC;gBAChC,KAAK,EAAE,EAAE,OAAO,EAAE,MAAM,EAAE;gBAC1B,MAAM,EAAE,EAAE,EAAE,EAAE,IAAI,EAAE;aACrB,CAAC;YACF,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,UAAU,CAAC;gBACjC,KAAK,EAAE,EAAE,kBAAkB,EAAE,EAAE,OAAO,EAAE,MAAM,EAAE,UAAU,EAAE,EAAE;gBAC9D,MAAM,EAAE,EAAE,EAAE,EAAE,IAAI,EAAE;aACrB,CAAC;SACH,CAAC,CAAC;QAEH,OAAO,OAAO,CAAC,SAAS,CAAC,IAAI,CAAC,WAAW,CAAC;IAC5C,CAAC;IAED;;;;;;OAMG;IACH,KAAK,CAAC,QAAQ,CACZ,MAAc,EACd,EAAE,SAAS,EAAE,SAAS,EAAE,SAAS,EAAqB;;QAEtD,MAAM,UAAU,GAAG,IAAA,2BAAc,EAAC,SAAS,EAAE,SAAS,CAAC,CAAC;QACxD,MAAM,EAAE,GAAG,IAAA,2BAAc,EAAC,SAAS,CAAC,CAAC;QAErC,MAAM,IAAI,GAAG;YACX,UAAU,EAAE,CAAC,SAAS,aAAT,SAAS,cAAT,SAAS,GAAI,EAAE,CAAC,CAAC,IAAI,EAAE,IAAI,IAAI;YAC5C,UAAU,EAAE,CAAC,SAAS,aAAT,SAAS,cAAT,SAAS,GAAI,EAAE,CAAC,CAAC,IAAI,EAAE,IAAI,IAAI;YAC5C,YAAY,EAAE,MAAA,EAAE,aAAF,EAAE,uBAAF,EAAE,CAAE,YAAY,mCAAI,IAAI;YACtC,OAAO,EAAE,MAAA,EAAE,aAAF,EAAE,uBAAF,EAAE,CAAE,OAAO,mCAAI,IAAI;YAC5B,OAAO,EAAE,CAAC,SAAS,aAAT,SAAS,cAAT,SAAS,GAAI,EAAE,CAAC,CAAC,IAAI,EAAE,IAAI,IAAI;YACzC,YAAY,EAAE,IAAI,IAAI,EAAE;SACzB,CAAC;QAEF,IAAI,CAAC;YACH,MAAM,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,MAAM,CAAC;gBACnC,KAAK,EAAE,EAAE,kBAAkB,EAAE,EAAE,OAAO,EAAE,MAAM,EAAE,UAAU,EAAE,EAAE;gBAC9D,MAAM,kBAAI,OAAO,EAAE,MAAM,EAAE,UAAU,IAAK,IAAI,CAAE;gBAChD,MAAM,EAAE,IAAI;aACb,CAAC,CAAC;QACL,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,CAAC,MAAM,CAAC,KAAK,CACf,yCAAyC,MAAM,KAC7C,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CACvD,EAAE,CACH,CAAC;QACJ,CAAC;IACH,CAAC;IAED;;;;;;;;;;;OAWG;IACH,KAAK,CAAC,IAAI,CACR,gBAA+B,EAC/B,MAAc,EACd,WAA+B;;QAE/B,MAAM,UAAU,GAAG,WAAW;YAC5B,CAAC,CAAC,IAAA,2BAAc,EAAC,WAAW,CAAC,SAAS,EAAE,WAAW,CAAC,SAAS,CAAC;YAC9D,CAAC,CAAC,IAAI,CAAC;QAET,MAAM,QAAQ,GAAG,MAAM,IAAI,CAAC,iBAAiB,CAAC,mBAAmB,CAC/D,IAAI,CAAC,MAAM,CAAC,WAAW,kCAElB,gBAAgB,KACnB,KAAK,EAAE,EAAE,OAAO,EAAE,MAAM,EAAE,EAC1B,MAAM,EAAE;gBACN,EAAE,EAAE,IAAI;gBACR,UAAU,EAAE,IAAI;gBAChB,YAAY,EAAE,IAAI;gBAClB,OAAO,EAAE,IAAI;gBACb,UAAU,EAAE,IAAI;gBAChB,OAAO,EAAE,IAAI;gBACb,YAAY,EAAE,IAAI;gBAClB,UAAU,EAAE,IAAI;aACjB;YACD,uEAAuE;YACvE,uCAAuC;YACvC,OAAO,EAAE,EAAE,YAAY,EAAE,MAAM,EAAE,IAEpC,CAAC;QAEF,uCACK,QAAQ,KACX,IAAI,EAAE,CAAC,MAAA,QAAQ,CAAC,IAAI,mCAAI,EAAE,CAAC,CAAC,GAAG,CAC7B,CAAC,EAAiD,EAAE,EAAE;oBAArD,EAAE,UAAU,OAAqC,EAAhC,MAAM,cAAvB,cAAyB,CAAF;gBAA+B,OAAA,iCAClD,MAAM,KACT,OAAO,EAAE,OAAO,CAAC,UAAU,CAAC,IAAI,UAAU,KAAK,UAAU,IACzD,CAAA;aAAA,CACH,IACD;IACJ,CAAC;IAED;;;;;;;OAOG;IACH,KAAK,CAAC,MAAM,CAAC,MAAc,EAAE,QAAgB;QAC3C,MAAM,EAAE,KAAK,EAAE,GAAG,MAAM,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC,UAAU,CAAC;YACzD,KAAK,EAAE,EAAE,EAAE,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,EAAE;SACzC,CAAC,CAAC;QAEH,OAAO,EAAE,OAAO,EAAE,KAAK,GAAG,CAAC,EAAE,CAAC;IAChC,CAAC;CACF,CAAA;AAjJY,8CAAiB;4BAAjB,iBAAiB;IAD7B,IAAA,mBAAU,GAAE;IAMR,WAAA,IAAA,eAAM,EAAC,IAAA,mBAAU,EAAC,GAAG,EAAE,CAAC,kCAAiB,CAAC,CAAC,CAAA;qCADnB,0BAAa;QAEF,kCAAiB;GAN5C,iBAAiB,CAiJ7B"}
@@ -0,0 +1,23 @@
1
+ /**
2
+ * Identidade estavel de um dispositivo para um usuario.
3
+ *
4
+ * O `browser_id` (UUID em localStorage, header X-Browser-ID) e o sinal forte e
5
+ * tem precedencia. Sem ele — app desktop, integracoes, clientes que nao mandam
6
+ * o header — cai no User-Agent, que erra para menos (nao distingue dois
7
+ * dispositivos com o mesmo UA) e nunca para mais.
8
+ *
9
+ * O resultado e um sha256 hex de largura fixa, e nao o valor cru, para caber
10
+ * num indice unico junto com o user_id sem depender do tamanho do UA. O
11
+ * `browser_id` e o `user_agent` continuam gravados em colunas proprias de
12
+ * `user_device`, entao nada de diagnostico se perde no hash.
13
+ *
14
+ * O prefixo `b:`/`u:` impede que um User-Agent que por acaso seja igual a um
15
+ * browser_id colida com ele.
16
+ *
17
+ * IMPORTANTE: a migration 20260808140000_core_user_device reproduz esta mesma
18
+ * expressao em SQL para popular a tabela a partir do historico de sessoes. Ao
19
+ * mudar a normalizacao aqui, as chaves ja gravadas deixam de casar e todo
20
+ * dispositivo conhecido vira "novo" — o que dispara um alerta para cada usuario.
21
+ */
22
+ export declare function buildDeviceKey(userAgent?: string | null, browserId?: string | null): string;
23
+ //# sourceMappingURL=device-key.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"device-key.d.ts","sourceRoot":"","sources":["../../src/utils/device-key.ts"],"names":[],"mappings":"AAEA;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,wBAAgB,cAAc,CAC5B,SAAS,CAAC,EAAE,MAAM,GAAG,IAAI,EACzB,SAAS,CAAC,EAAE,MAAM,GAAG,IAAI,GACxB,MAAM,CAKR"}
@@ -0,0 +1,31 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.buildDeviceKey = buildDeviceKey;
4
+ const crypto_1 = require("crypto");
5
+ /**
6
+ * Identidade estavel de um dispositivo para um usuario.
7
+ *
8
+ * O `browser_id` (UUID em localStorage, header X-Browser-ID) e o sinal forte e
9
+ * tem precedencia. Sem ele — app desktop, integracoes, clientes que nao mandam
10
+ * o header — cai no User-Agent, que erra para menos (nao distingue dois
11
+ * dispositivos com o mesmo UA) e nunca para mais.
12
+ *
13
+ * O resultado e um sha256 hex de largura fixa, e nao o valor cru, para caber
14
+ * num indice unico junto com o user_id sem depender do tamanho do UA. O
15
+ * `browser_id` e o `user_agent` continuam gravados em colunas proprias de
16
+ * `user_device`, entao nada de diagnostico se perde no hash.
17
+ *
18
+ * O prefixo `b:`/`u:` impede que um User-Agent que por acaso seja igual a um
19
+ * browser_id colida com ele.
20
+ *
21
+ * IMPORTANTE: a migration 20260808140000_core_user_device reproduz esta mesma
22
+ * expressao em SQL para popular a tabela a partir do historico de sessoes. Ao
23
+ * mudar a normalizacao aqui, as chaves ja gravadas deixam de casar e todo
24
+ * dispositivo conhecido vira "novo" — o que dispara um alerta para cada usuario.
25
+ */
26
+ function buildDeviceKey(userAgent, browserId) {
27
+ const browser = (browserId !== null && browserId !== void 0 ? browserId : '').trim();
28
+ const source = browser ? `b:${browser}` : `u:${(userAgent !== null && userAgent !== void 0 ? userAgent : '').trim()}`;
29
+ return (0, crypto_1.createHash)('sha256').update(source, 'utf8').digest('hex');
30
+ }
31
+ //# sourceMappingURL=device-key.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"device-key.js","sourceRoot":"","sources":["../../src/utils/device-key.ts"],"names":[],"mappings":";;AAuBA,wCAQC;AA/BD,mCAAoC;AAEpC;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,SAAgB,cAAc,CAC5B,SAAyB,EACzB,SAAyB;IAEzB,MAAM,OAAO,GAAG,CAAC,SAAS,aAAT,SAAS,cAAT,SAAS,GAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;IACzC,MAAM,MAAM,GAAG,OAAO,CAAC,CAAC,CAAC,KAAK,OAAO,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,SAAS,aAAT,SAAS,cAAT,SAAS,GAAI,EAAE,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC;IAE1E,OAAO,IAAA,mBAAU,EAAC,QAAQ,CAAC,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;AACnE,CAAC"}
@@ -0,0 +1,38 @@
1
+ export interface GeoLocation {
2
+ /** ISO 3166-1 alpha-2, e.g. 'BR'. */
3
+ country: string | null;
4
+ /** Subdivision code, e.g. 'SP'. */
5
+ region: string | null;
6
+ city: string | null;
7
+ /** IANA timezone, e.g. 'America/Sao_Paulo'. */
8
+ timezone: string | null;
9
+ }
10
+ /**
11
+ * Strips the IPv4-mapped IPv6 prefix and any trailing port, and unwraps the
12
+ * bracket notation used for IPv6 hosts.
13
+ *
14
+ * Without this, `::ffff:189.1.2.3` — what a dual-stack socket reports — is
15
+ * looked up in the IPv6 database and always misses.
16
+ */
17
+ export declare function normalizeIp(ip?: string | null): string | null;
18
+ /**
19
+ * Loopback, private, link-local and CGNAT ranges — plus the placeholders the
20
+ * callers use when they could not resolve anything.
21
+ *
22
+ * The cluster pod CIDR (10.244.x.x) falls here, which is exactly what every
23
+ * ticket created before the client IP started being forwarded has stored.
24
+ *
25
+ * Careful with 172: only 172.16.0.0/12 is private, so the second octet has to
26
+ * be between 16 and 31. Blocking the whole `172.` prefix — as the copy in
27
+ * lms/platforma/handlers/lesson-heartbeat.handler.ts does — silently discards
28
+ * public addresses such as 172.32.5.9.
29
+ */
30
+ export declare function isPrivateIp(ip?: string | null): boolean;
31
+ /**
32
+ * Offline lookup against the MaxMind-lite database bundled with geoip-lite.
33
+ *
34
+ * Returns null for empty, private or unknown addresses — never an invented
35
+ * country, which is what makes it safe to render the result directly.
36
+ */
37
+ export declare function lookupGeo(ip?: string | null): GeoLocation | null;
38
+ //# sourceMappingURL=geo-ip.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"geo-ip.d.ts","sourceRoot":"","sources":["../../src/utils/geo-ip.ts"],"names":[],"mappings":"AAEA,MAAM,WAAW,WAAW;IAC1B,qCAAqC;IACrC,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IACvB,mCAAmC;IACnC,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;IACpB,+CAA+C;IAC/C,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;CACzB;AAED;;;;;;GAMG;AACH,wBAAgB,WAAW,CAAC,EAAE,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,MAAM,GAAG,IAAI,CAc7D;AAED;;;;;;;;;;;GAWG;AACH,wBAAgB,WAAW,CAAC,EAAE,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,OAAO,CAwBvD;AAED;;;;;GAKG;AACH,wBAAgB,SAAS,CAAC,EAAE,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,WAAW,GAAG,IAAI,CAahE"}
@@ -0,0 +1,122 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ exports.normalizeIp = normalizeIp;
37
+ exports.isPrivateIp = isPrivateIp;
38
+ exports.lookupGeo = lookupGeo;
39
+ const geoip = __importStar(require("geoip-lite"));
40
+ /**
41
+ * Strips the IPv4-mapped IPv6 prefix and any trailing port, and unwraps the
42
+ * bracket notation used for IPv6 hosts.
43
+ *
44
+ * Without this, `::ffff:189.1.2.3` — what a dual-stack socket reports — is
45
+ * looked up in the IPv6 database and always misses.
46
+ */
47
+ function normalizeIp(ip) {
48
+ const raw = (ip !== null && ip !== void 0 ? ip : '').trim();
49
+ if (!raw)
50
+ return null;
51
+ // `[2001:db8::1]:443` -> `2001:db8::1`
52
+ const bracketed = raw.match(/^\[(.+)\](?::\d+)?$/);
53
+ const value = bracketed ? bracketed[1] : raw;
54
+ const unmapped = value.replace(/^::ffff:/i, '');
55
+ // `189.1.2.3:51000` -> `189.1.2.3` (only for IPv4; a bare IPv6 has many colons)
56
+ const withoutPort = unmapped.match(/^(\d{1,3}(?:\.\d{1,3}){3}):\d+$/);
57
+ return (withoutPort ? withoutPort[1] : unmapped) || null;
58
+ }
59
+ /**
60
+ * Loopback, private, link-local and CGNAT ranges — plus the placeholders the
61
+ * callers use when they could not resolve anything.
62
+ *
63
+ * The cluster pod CIDR (10.244.x.x) falls here, which is exactly what every
64
+ * ticket created before the client IP started being forwarded has stored.
65
+ *
66
+ * Careful with 172: only 172.16.0.0/12 is private, so the second octet has to
67
+ * be between 16 and 31. Blocking the whole `172.` prefix — as the copy in
68
+ * lms/platforma/handlers/lesson-heartbeat.handler.ts does — silently discards
69
+ * public addresses such as 172.32.5.9.
70
+ */
71
+ function isPrivateIp(ip) {
72
+ const value = normalizeIp(ip);
73
+ if (!value)
74
+ return true;
75
+ const lower = value.toLowerCase();
76
+ if (lower === 'unknown' || lower === '::' || lower === '0.0.0.0')
77
+ return true;
78
+ // IPv6: loopback, unique local (fc00::/7) and link-local (fe80::/10).
79
+ if (lower === '::1')
80
+ return true;
81
+ if (/^f[cd]/.test(lower) && lower.includes(':'))
82
+ return true;
83
+ if (/^fe[89ab]/.test(lower) && lower.includes(':'))
84
+ return true;
85
+ const v4 = lower.match(/^(\d{1,3})\.(\d{1,3})\.(\d{1,3})\.(\d{1,3})$/);
86
+ if (!v4)
87
+ return false;
88
+ const [a, b] = [Number(v4[1]), Number(v4[2])];
89
+ if (a === 0 || a === 10 || a === 127)
90
+ return true;
91
+ if (a === 172 && b >= 16 && b <= 31)
92
+ return true;
93
+ if (a === 192 && b === 168)
94
+ return true;
95
+ if (a === 169 && b === 254)
96
+ return true;
97
+ // CGNAT 100.64.0.0/10
98
+ if (a === 100 && b >= 64 && b <= 127)
99
+ return true;
100
+ return false;
101
+ }
102
+ /**
103
+ * Offline lookup against the MaxMind-lite database bundled with geoip-lite.
104
+ *
105
+ * Returns null for empty, private or unknown addresses — never an invented
106
+ * country, which is what makes it safe to render the result directly.
107
+ */
108
+ function lookupGeo(ip) {
109
+ const value = normalizeIp(ip);
110
+ if (!value || isPrivateIp(value))
111
+ return null;
112
+ const geo = geoip.lookup(value);
113
+ if (!geo)
114
+ return null;
115
+ return {
116
+ country: geo.country || null,
117
+ region: geo.region || null,
118
+ city: geo.city || null,
119
+ timezone: geo.timezone || null,
120
+ };
121
+ }
122
+ //# sourceMappingURL=geo-ip.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"geo-ip.js","sourceRoot":"","sources":["../../src/utils/geo-ip.ts"],"names":[],"mappings":"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"}
@@ -1,8 +1,11 @@
1
- import { AsyncLocalStorage } from 'async_hooks';
2
- interface LocaleContext {
3
- locale: string;
4
- }
5
- export declare const localeStorage: AsyncLocalStorage<LocaleContext>;
6
- export declare function getLocaleFromContext(): string;
7
- export {};
1
+ /**
2
+ * O contexto de locale mora em `@hed-hog/api-locale`, junto do middleware que o
3
+ * popula. Este arquivo continua existindo como reexport porque `@hed-hog/core`
4
+ * e a fachada que as outras libraries importam (`operations`, validators).
5
+ *
6
+ * Manter uma copia do `AsyncLocalStorage` aqui criaria DOIS storages: o
7
+ * middleware escreveria num e `getLocaleFromContext()` leria o outro, sempre
8
+ * vazio.
9
+ */
10
+ export { getLocaleFromContext, isLocaleDetectedFromContext, localeStorage, type LocaleContext, } from '@hed-hog/api-locale';
8
11
  //# sourceMappingURL=locale-context.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"locale-context.d.ts","sourceRoot":"","sources":["../../src/utils/locale-context.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAEhD,UAAU,aAAa;IACrB,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,eAAO,MAAM,aAAa,kCAAyC,CAAC;AAEpE,wBAAgB,oBAAoB,IAAI,MAAM,CAG7C"}
1
+ {"version":3,"file":"locale-context.d.ts","sourceRoot":"","sources":["../../src/utils/locale-context.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AACH,OAAO,EACL,oBAAoB,EACpB,2BAA2B,EAC3B,aAAa,EACb,KAAK,aAAa,GACnB,MAAM,qBAAqB,CAAC"}
@@ -1,11 +1,17 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.localeStorage = void 0;
4
- exports.getLocaleFromContext = getLocaleFromContext;
5
- const async_hooks_1 = require("async_hooks");
6
- exports.localeStorage = new async_hooks_1.AsyncLocalStorage();
7
- function getLocaleFromContext() {
8
- const context = exports.localeStorage.getStore();
9
- return (context === null || context === void 0 ? void 0 : context.locale) || 'en';
10
- }
3
+ exports.localeStorage = exports.isLocaleDetectedFromContext = exports.getLocaleFromContext = void 0;
4
+ /**
5
+ * O contexto de locale mora em `@hed-hog/api-locale`, junto do middleware que o
6
+ * popula. Este arquivo continua existindo como reexport porque `@hed-hog/core`
7
+ * e a fachada que as outras libraries importam (`operations`, validators).
8
+ *
9
+ * Manter uma copia do `AsyncLocalStorage` aqui criaria DOIS storages: o
10
+ * middleware escreveria num e `getLocaleFromContext()` leria o outro, sempre
11
+ * vazio.
12
+ */
13
+ var api_locale_1 = require("@hed-hog/api-locale");
14
+ Object.defineProperty(exports, "getLocaleFromContext", { enumerable: true, get: function () { return api_locale_1.getLocaleFromContext; } });
15
+ Object.defineProperty(exports, "isLocaleDetectedFromContext", { enumerable: true, get: function () { return api_locale_1.isLocaleDetectedFromContext; } });
16
+ Object.defineProperty(exports, "localeStorage", { enumerable: true, get: function () { return api_locale_1.localeStorage; } });
11
17
  //# sourceMappingURL=locale-context.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"locale-context.js","sourceRoot":"","sources":["../../src/utils/locale-context.ts"],"names":[],"mappings":";;;AAQA,oDAGC;AAXD,6CAAgD;AAMnC,QAAA,aAAa,GAAG,IAAI,+BAAiB,EAAiB,CAAC;AAEpE,SAAgB,oBAAoB;IAClC,MAAM,OAAO,GAAG,qBAAa,CAAC,QAAQ,EAAE,CAAC;IACzC,OAAO,CAAA,OAAO,aAAP,OAAO,uBAAP,OAAO,CAAE,MAAM,KAAI,IAAI,CAAC;AACjC,CAAC"}
1
+ {"version":3,"file":"locale-context.js","sourceRoot":"","sources":["../../src/utils/locale-context.ts"],"names":[],"mappings":";;;AAAA;;;;;;;;GAQG;AACH,kDAK6B;AAJ3B,kHAAA,oBAAoB,OAAA;AACpB,yHAAA,2BAA2B,OAAA;AAC3B,2GAAA,aAAa,OAAA"}
@@ -0,0 +1,56 @@
1
+ export interface SecurityEventContext {
2
+ ipAddress?: string | null;
3
+ userAgent?: string | null;
4
+ /** Codigo da tabela `locale` ('pt' | 'en' | 'es'), como chega do LocaleMiddleware. */
5
+ locale?: string | null;
6
+ /** Momento do evento. Default: agora. */
7
+ at?: Date;
8
+ /** Fuso quando o geoip nao resolve. Default: DEFAULT_TIME_ZONE. */
9
+ fallbackTimeZone?: string;
10
+ }
11
+ /**
12
+ * Variaveis prontas para os templates de e-mail de seguranca
13
+ * (`auth-login-new-device`, `auth-change-password-notification`).
14
+ *
15
+ * Todo campo e string, nunca null: `sendTemplatedMail` recebe um
16
+ * Record<string, string> e os templates usam `{{#if}}` para esconder a linha
17
+ * do cartao — string vazia e o que faz a linha sumir.
18
+ */
19
+ export interface SecurityEventVars {
20
+ ipAddress: string;
21
+ /** UA cru; o template so imprime quando nao conseguiu identificar navegador nem SO. */
22
+ userAgent: string;
23
+ /** "Chrome 151" */
24
+ browser: string;
25
+ /** "Windows 10" */
26
+ os: string;
27
+ /** "Sao Paulo, Brasil" */
28
+ location: string;
29
+ /** "🇧🇷" */
30
+ countryFlag: string;
31
+ /** "8 de agosto de 2026 as 12:04" */
32
+ datetime: string;
33
+ }
34
+ /**
35
+ * Par de regional indicators para um ISO 3166-1 alpha-2.
36
+ *
37
+ * Mesma conta do countryFlag() em apps/admin/src/components/browser-os-icon.tsx,
38
+ * reimplementada aqui porque aquele arquivo e 'use client' e vive no app.
39
+ *
40
+ * Emoji e a unica forma de bandeira que renderiza nos tres clientes que
41
+ * importam: o Gmail remove <svg> inline e bloqueia data: URI, e o Outlook
42
+ * desktop nao renderiza SVG de jeito nenhum.
43
+ */
44
+ export declare function countryFlagEmoji(code?: string | null): string;
45
+ export declare function formatEventDateTime(at: Date, locale?: string | null, timeZone?: string | null): string;
46
+ /**
47
+ * Traduz IP + User-Agent crus nas variaveis que o template de seguranca
48
+ * imprime, resolvendo geolocalizacao e navegador/SO pelos utilitarios que o
49
+ * access-log ja usa.
50
+ *
51
+ * O que nao foi possivel resolver volta como string vazia, e nao como um
52
+ * "Unknown" literal: o template esconde a linha inteira em vez de anunciar
53
+ * que o sistema nao sabe.
54
+ */
55
+ export declare function buildSecurityEventVars(ctx: SecurityEventContext): SecurityEventVars;
56
+ //# sourceMappingURL=security-event-vars.d.ts.map