@prosopo/provider 3.1.3 → 3.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (227) hide show
  1. package/CHANGELOG.md +54 -0
  2. package/dist/api/admin/apiAdminRoutesProvider.js +26 -21
  3. package/dist/api/admin/apiRegisterSiteKeyEndpoint.js +21 -20
  4. package/dist/api/admin/apiRemoveDetectorKeyEndpoint.js +27 -27
  5. package/dist/api/admin/apiUpdateDetectorKeyEndpoint.js +33 -33
  6. package/dist/api/admin/createApiAdminRoutesProvider.js +8 -5
  7. package/dist/api/blacklistRequestInspector.js +116 -98
  8. package/dist/api/block.js +13 -8
  9. package/dist/api/captcha.js +519 -356
  10. package/dist/api/domainMiddleware.js +75 -68
  11. package/dist/api/headerCheckMiddleware.js +26 -25
  12. package/dist/api/ignoreMiddleware.js +12 -10
  13. package/dist/api/ja4Middleware.js +75 -80
  14. package/dist/api/public.js +26 -23
  15. package/dist/api/robotsMiddleware.js +11 -9
  16. package/dist/api/validateAddress.js +20 -18
  17. package/dist/api/verify.js +133 -95
  18. package/dist/cjs/api/blacklistRequestInspector.cjs +4 -6
  19. package/dist/cjs/api/captcha.cjs +45 -36
  20. package/dist/cjs/api/ja4Middleware.cjs +4 -1
  21. package/dist/cjs/tasks/captchaManager.cjs +24 -10
  22. package/dist/cjs/tasks/frictionless/frictionlessTasks.cjs +0 -3
  23. package/dist/cjs/tasks/powCaptcha/powTasksUtils.cjs +1 -1
  24. package/dist/index.js +38 -15
  25. package/dist/rules/lang.js +14 -14
  26. package/dist/schedulers/captchaScheduler.js +28 -23
  27. package/dist/schedulers/getClientList.js +29 -24
  28. package/dist/tasks/captchaManager.js +109 -85
  29. package/dist/tasks/client/clientTasks.js +265 -204
  30. package/dist/tasks/dataset/datasetTasks.js +27 -16
  31. package/dist/tasks/dataset/datasetTasksUtils.js +31 -31
  32. package/dist/tasks/detection/decodePayload.js +378 -208
  33. package/dist/tasks/detection/getBotScore.js +12 -10
  34. package/dist/tasks/frictionless/frictionlessTasks.js +117 -119
  35. package/dist/tasks/frictionless/frictionlessTasksUtils.js +10 -5
  36. package/dist/tasks/imgCaptcha/imgCaptchaTasks.js +360 -271
  37. package/dist/tasks/imgCaptcha/imgCaptchaTasksUtils.js +23 -16
  38. package/dist/tasks/index.js +4 -2
  39. package/dist/tasks/powCaptcha/powTasks.js +157 -97
  40. package/dist/tasks/powCaptcha/powTasksUtils.js +24 -20
  41. package/dist/tasks/tasks.js +53 -29
  42. package/dist/util.js +98 -88
  43. package/package.json +31 -27
  44. package/vite.cjs.config.ts +4 -1
  45. package/vite.esm.config.ts +20 -0
  46. package/vite.test.config.ts +15 -3
  47. package/dist/api/admin/apiAdminRoutesProvider.d.ts +0 -9
  48. package/dist/api/admin/apiAdminRoutesProvider.d.ts.map +0 -1
  49. package/dist/api/admin/apiAdminRoutesProvider.js.map +0 -1
  50. package/dist/api/admin/apiRegisterSiteKeyEndpoint.d.ts +0 -14
  51. package/dist/api/admin/apiRegisterSiteKeyEndpoint.d.ts.map +0 -1
  52. package/dist/api/admin/apiRegisterSiteKeyEndpoint.js.map +0 -1
  53. package/dist/api/admin/apiRemoveDetectorKeyEndpoint.d.ts +0 -14
  54. package/dist/api/admin/apiRemoveDetectorKeyEndpoint.d.ts.map +0 -1
  55. package/dist/api/admin/apiRemoveDetectorKeyEndpoint.js.map +0 -1
  56. package/dist/api/admin/apiUpdateDetectorKeyEndpoint.d.ts +0 -14
  57. package/dist/api/admin/apiUpdateDetectorKeyEndpoint.d.ts.map +0 -1
  58. package/dist/api/admin/apiUpdateDetectorKeyEndpoint.js.map +0 -1
  59. package/dist/api/admin/createApiAdminRoutesProvider.d.ts +0 -4
  60. package/dist/api/admin/createApiAdminRoutesProvider.d.ts.map +0 -1
  61. package/dist/api/admin/createApiAdminRoutesProvider.js.map +0 -1
  62. package/dist/api/blacklistRequestInspector.d.ts +0 -44
  63. package/dist/api/blacklistRequestInspector.d.ts.map +0 -1
  64. package/dist/api/blacklistRequestInspector.js.map +0 -1
  65. package/dist/api/block.d.ts +0 -3
  66. package/dist/api/block.d.ts.map +0 -1
  67. package/dist/api/block.js.map +0 -1
  68. package/dist/api/captcha.d.ts +0 -4
  69. package/dist/api/captcha.d.ts.map +0 -1
  70. package/dist/api/captcha.js.map +0 -1
  71. package/dist/api/domainMiddleware.d.ts +0 -4
  72. package/dist/api/domainMiddleware.d.ts.map +0 -1
  73. package/dist/api/domainMiddleware.js.map +0 -1
  74. package/dist/api/headerCheckMiddleware.d.ts +0 -4
  75. package/dist/api/headerCheckMiddleware.d.ts.map +0 -1
  76. package/dist/api/headerCheckMiddleware.js.map +0 -1
  77. package/dist/api/ignoreMiddleware.d.ts +0 -3
  78. package/dist/api/ignoreMiddleware.d.ts.map +0 -1
  79. package/dist/api/ignoreMiddleware.js.map +0 -1
  80. package/dist/api/ja4Middleware.d.ts +0 -10
  81. package/dist/api/ja4Middleware.d.ts.map +0 -1
  82. package/dist/api/ja4Middleware.js.map +0 -1
  83. package/dist/api/public.d.ts +0 -3
  84. package/dist/api/public.d.ts.map +0 -1
  85. package/dist/api/public.js.map +0 -1
  86. package/dist/api/robotsMiddleware.d.ts +0 -3
  87. package/dist/api/robotsMiddleware.d.ts.map +0 -1
  88. package/dist/api/robotsMiddleware.js.map +0 -1
  89. package/dist/api/validateAddress.d.ts +0 -5
  90. package/dist/api/validateAddress.d.ts.map +0 -1
  91. package/dist/api/validateAddress.js.map +0 -1
  92. package/dist/api/verify.d.ts +0 -4
  93. package/dist/api/verify.d.ts.map +0 -1
  94. package/dist/api/verify.js.map +0 -1
  95. package/dist/index.d.ts +0 -15
  96. package/dist/index.d.ts.map +0 -1
  97. package/dist/index.js.map +0 -1
  98. package/dist/rules/lang.d.ts +0 -3
  99. package/dist/rules/lang.d.ts.map +0 -1
  100. package/dist/rules/lang.js.map +0 -1
  101. package/dist/schedulers/captchaScheduler.d.ts +0 -4
  102. package/dist/schedulers/captchaScheduler.d.ts.map +0 -1
  103. package/dist/schedulers/captchaScheduler.js.map +0 -1
  104. package/dist/schedulers/getClientList.d.ts +0 -4
  105. package/dist/schedulers/getClientList.d.ts.map +0 -1
  106. package/dist/schedulers/getClientList.js.map +0 -1
  107. package/dist/tasks/captchaManager.d.ts +0 -48
  108. package/dist/tasks/captchaManager.d.ts.map +0 -1
  109. package/dist/tasks/captchaManager.js.map +0 -1
  110. package/dist/tasks/client/clientTasks.d.ts +0 -21
  111. package/dist/tasks/client/clientTasks.d.ts.map +0 -1
  112. package/dist/tasks/client/clientTasks.js.map +0 -1
  113. package/dist/tasks/dataset/datasetTasks.d.ts +0 -13
  114. package/dist/tasks/dataset/datasetTasks.d.ts.map +0 -1
  115. package/dist/tasks/dataset/datasetTasks.js.map +0 -1
  116. package/dist/tasks/dataset/datasetTasksUtils.d.ts +0 -3
  117. package/dist/tasks/dataset/datasetTasksUtils.d.ts.map +0 -1
  118. package/dist/tasks/dataset/datasetTasksUtils.js.map +0 -1
  119. package/dist/tasks/detection/decodePayload.d.ts +0 -5
  120. package/dist/tasks/detection/decodePayload.d.ts.map +0 -1
  121. package/dist/tasks/detection/decodePayload.js.map +0 -1
  122. package/dist/tasks/detection/getBotScore.d.ts +0 -5
  123. package/dist/tasks/detection/getBotScore.d.ts.map +0 -1
  124. package/dist/tasks/detection/getBotScore.js.map +0 -1
  125. package/dist/tasks/frictionless/frictionlessTasks.d.ts +0 -23
  126. package/dist/tasks/frictionless/frictionlessTasks.d.ts.map +0 -1
  127. package/dist/tasks/frictionless/frictionlessTasks.js.map +0 -1
  128. package/dist/tasks/frictionless/frictionlessTasksUtils.d.ts +0 -5
  129. package/dist/tasks/frictionless/frictionlessTasksUtils.d.ts.map +0 -1
  130. package/dist/tasks/frictionless/frictionlessTasksUtils.js.map +0 -1
  131. package/dist/tasks/imgCaptcha/imgCaptchaTasks.d.ts +0 -29
  132. package/dist/tasks/imgCaptcha/imgCaptchaTasks.d.ts.map +0 -1
  133. package/dist/tasks/imgCaptcha/imgCaptchaTasks.js.map +0 -1
  134. package/dist/tasks/imgCaptcha/imgCaptchaTasksUtils.d.ts +0 -7
  135. package/dist/tasks/imgCaptcha/imgCaptchaTasksUtils.d.ts.map +0 -1
  136. package/dist/tasks/imgCaptcha/imgCaptchaTasksUtils.js.map +0 -1
  137. package/dist/tasks/index.d.ts +0 -2
  138. package/dist/tasks/index.d.ts.map +0 -1
  139. package/dist/tasks/index.js.map +0 -1
  140. package/dist/tasks/powCaptcha/powTasks.d.ts +0 -16
  141. package/dist/tasks/powCaptcha/powTasks.d.ts.map +0 -1
  142. package/dist/tasks/powCaptcha/powTasks.js.map +0 -1
  143. package/dist/tasks/powCaptcha/powTasksUtils.d.ts +0 -3
  144. package/dist/tasks/powCaptcha/powTasksUtils.d.ts.map +0 -1
  145. package/dist/tasks/powCaptcha/powTasksUtils.js.map +0 -1
  146. package/dist/tasks/tasks.d.ts +0 -25
  147. package/dist/tasks/tasks.d.ts.map +0 -1
  148. package/dist/tasks/tasks.js.map +0 -1
  149. package/dist/tests/index.d.ts +0 -2
  150. package/dist/tests/index.d.ts.map +0 -1
  151. package/dist/tests/index.js +0 -2
  152. package/dist/tests/index.js.map +0 -1
  153. package/dist/tests/integration/imgCaptcha.integration.test.d.ts +0 -2
  154. package/dist/tests/integration/imgCaptcha.integration.test.d.ts.map +0 -1
  155. package/dist/tests/integration/imgCaptcha.integration.test.js +0 -261
  156. package/dist/tests/integration/imgCaptcha.integration.test.js.map +0 -1
  157. package/dist/tests/integration/mocks/solvedTestCaptchas.d.ts +0 -32
  158. package/dist/tests/integration/mocks/solvedTestCaptchas.d.ts.map +0 -1
  159. package/dist/tests/integration/mocks/solvedTestCaptchas.js +0 -1046
  160. package/dist/tests/integration/mocks/solvedTestCaptchas.js.map +0 -1
  161. package/dist/tests/integration/powCaptcha.integration.test.d.ts +0 -2
  162. package/dist/tests/integration/powCaptcha.integration.test.d.ts.map +0 -1
  163. package/dist/tests/integration/powCaptcha.integration.test.js +0 -299
  164. package/dist/tests/integration/powCaptcha.integration.test.js.map +0 -1
  165. package/dist/tests/integration/registerSitekey.d.ts +0 -3
  166. package/dist/tests/integration/registerSitekey.d.ts.map +0 -1
  167. package/dist/tests/integration/registerSitekey.js +0 -39
  168. package/dist/tests/integration/registerSitekey.js.map +0 -1
  169. package/dist/tests/unit/api/ignoreMiddleware.unit.test.d.ts +0 -2
  170. package/dist/tests/unit/api/ignoreMiddleware.unit.test.d.ts.map +0 -1
  171. package/dist/tests/unit/api/ignoreMiddleware.unit.test.js +0 -43
  172. package/dist/tests/unit/api/ignoreMiddleware.unit.test.js.map +0 -1
  173. package/dist/tests/unit/api/ja4Middleware.unit.test.d.ts +0 -2
  174. package/dist/tests/unit/api/ja4Middleware.unit.test.d.ts.map +0 -1
  175. package/dist/tests/unit/api/ja4Middleware.unit.test.js +0 -71
  176. package/dist/tests/unit/api/ja4Middleware.unit.test.js.map +0 -1
  177. package/dist/tests/unit/schedulers/captchaScheduler.unit.test.d.ts +0 -2
  178. package/dist/tests/unit/schedulers/captchaScheduler.unit.test.d.ts.map +0 -1
  179. package/dist/tests/unit/schedulers/captchaScheduler.unit.test.js +0 -75
  180. package/dist/tests/unit/schedulers/captchaScheduler.unit.test.js.map +0 -1
  181. package/dist/tests/unit/tasks/captchaManager.unit.test.d.ts +0 -2
  182. package/dist/tests/unit/tasks/captchaManager.unit.test.d.ts.map +0 -1
  183. package/dist/tests/unit/tasks/captchaManager.unit.test.js +0 -236
  184. package/dist/tests/unit/tasks/captchaManager.unit.test.js.map +0 -1
  185. package/dist/tests/unit/tasks/client/clientTasks.unit.test.d.ts +0 -2
  186. package/dist/tests/unit/tasks/client/clientTasks.unit.test.d.ts.map +0 -1
  187. package/dist/tests/unit/tasks/client/clientTasks.unit.test.js +0 -277
  188. package/dist/tests/unit/tasks/client/clientTasks.unit.test.js.map +0 -1
  189. package/dist/tests/unit/tasks/dataset/datasetTasks.unit.test.d.ts +0 -2
  190. package/dist/tests/unit/tasks/dataset/datasetTasks.unit.test.d.ts.map +0 -1
  191. package/dist/tests/unit/tasks/dataset/datasetTasks.unit.test.js +0 -93
  192. package/dist/tests/unit/tasks/dataset/datasetTasks.unit.test.js.map +0 -1
  193. package/dist/tests/unit/tasks/dataset/datasetTasksUtils.unit.test.d.ts +0 -2
  194. package/dist/tests/unit/tasks/dataset/datasetTasksUtils.unit.test.d.ts.map +0 -1
  195. package/dist/tests/unit/tasks/dataset/datasetTasksUtils.unit.test.js +0 -75
  196. package/dist/tests/unit/tasks/dataset/datasetTasksUtils.unit.test.js.map +0 -1
  197. package/dist/tests/unit/tasks/frictionless/frictionlessTasks.unit.test.d.ts +0 -2
  198. package/dist/tests/unit/tasks/frictionless/frictionlessTasks.unit.test.d.ts.map +0 -1
  199. package/dist/tests/unit/tasks/frictionless/frictionlessTasks.unit.test.js +0 -68
  200. package/dist/tests/unit/tasks/frictionless/frictionlessTasks.unit.test.js.map +0 -1
  201. package/dist/tests/unit/tasks/frictionless/frictionlessTasksUtils.unit.test.d.ts +0 -2
  202. package/dist/tests/unit/tasks/frictionless/frictionlessTasksUtils.unit.test.d.ts.map +0 -1
  203. package/dist/tests/unit/tasks/frictionless/frictionlessTasksUtils.unit.test.js +0 -37
  204. package/dist/tests/unit/tasks/frictionless/frictionlessTasksUtils.unit.test.js.map +0 -1
  205. package/dist/tests/unit/tasks/imgCaptcha/imgCaptchaTasks.unit.test.d.ts +0 -2
  206. package/dist/tests/unit/tasks/imgCaptcha/imgCaptchaTasks.unit.test.d.ts.map +0 -1
  207. package/dist/tests/unit/tasks/imgCaptcha/imgCaptchaTasks.unit.test.js +0 -402
  208. package/dist/tests/unit/tasks/imgCaptcha/imgCaptchaTasks.unit.test.js.map +0 -1
  209. package/dist/tests/unit/tasks/imgCaptcha/imgCaptchaTasksUtils.unit.test.d.ts +0 -2
  210. package/dist/tests/unit/tasks/imgCaptcha/imgCaptchaTasksUtils.unit.test.d.ts.map +0 -1
  211. package/dist/tests/unit/tasks/imgCaptcha/imgCaptchaTasksUtils.unit.test.js +0 -46
  212. package/dist/tests/unit/tasks/imgCaptcha/imgCaptchaTasksUtils.unit.test.js.map +0 -1
  213. package/dist/tests/unit/tasks/powCaptcha/powTasks.unit.test.d.ts +0 -2
  214. package/dist/tests/unit/tasks/powCaptcha/powTasks.unit.test.d.ts.map +0 -1
  215. package/dist/tests/unit/tasks/powCaptcha/powTasks.unit.test.js +0 -228
  216. package/dist/tests/unit/tasks/powCaptcha/powTasks.unit.test.js.map +0 -1
  217. package/dist/tests/unit/tasks/powCaptcha/powTasksUtils.unit.test.d.ts +0 -2
  218. package/dist/tests/unit/tasks/powCaptcha/powTasksUtils.unit.test.d.ts.map +0 -1
  219. package/dist/tests/unit/tasks/powCaptcha/powTasksUtils.unit.test.js +0 -68
  220. package/dist/tests/unit/tasks/powCaptcha/powTasksUtils.unit.test.js.map +0 -1
  221. package/dist/tests/unit/util.unit.test.d.ts +0 -2
  222. package/dist/tests/unit/util.unit.test.d.ts.map +0 -1
  223. package/dist/tests/unit/util.unit.test.js +0 -148
  224. package/dist/tests/unit/util.unit.test.js.map +0 -1
  225. package/dist/util.d.ts +0 -13
  226. package/dist/util.d.ts.map +0 -1
  227. package/dist/util.js.map +0 -1
@@ -2,81 +2,88 @@ import { handleErrors } from "@prosopo/api-express-router";
2
2
  import { ProsopoApiError } from "@prosopo/common";
3
3
  import { validateAddress } from "@prosopo/util-crypto";
4
4
  import { ZodError } from "zod";
5
- import { Tasks } from "../tasks/index.js";
6
- export const domainMiddleware = (env) => {
7
- const tasks = new Tasks(env);
8
- return async (req, res, next) => {
9
- try {
10
- const dapp = req.headers["prosopo-site-key"];
11
- if (!dapp)
12
- throw siteKeyNotRegisteredError(req.i18n, "No sitekey provided", req.logger);
13
- try {
14
- validateAddress(dapp, false, 42);
15
- }
16
- catch (err) {
17
- throw invalidSiteKeyError(req.i18n, dapp, req.logger);
18
- }
19
- const clientSettings = await tasks.db.getClientRecord(dapp);
20
- if (!clientSettings)
21
- throw siteKeyNotRegisteredError(req.i18n, dapp, req.logger);
22
- const allowedDomains = clientSettings.settings?.domains;
23
- if (!allowedDomains)
24
- throw siteKeyInvalidDomainError(req.i18n, dapp, req.hostname, req.logger);
25
- const origin = req.headers.origin;
26
- if (!origin)
27
- throw unauthorizedOriginError(req.i18n, undefined, req.logger);
28
- for (const domain of allowedDomains) {
29
- if (tasks.clientTaskManager.isSubdomainOrExactMatch(origin, domain)) {
30
- next();
31
- return;
32
- }
33
- }
34
- throw unauthorizedOriginError(req.i18n, origin, req.logger);
5
+ import "../tasks/index.js";
6
+ import { Tasks } from "../tasks/tasks.js";
7
+ const domainMiddleware = (env) => {
8
+ const tasks = new Tasks(env);
9
+ return async (req, res, next) => {
10
+ try {
11
+ const dapp = req.headers["prosopo-site-key"];
12
+ if (!dapp)
13
+ throw siteKeyNotRegisteredError(
14
+ req.i18n,
15
+ "No sitekey provided",
16
+ req.logger
17
+ );
18
+ try {
19
+ validateAddress(dapp, false, 42);
20
+ } catch (err) {
21
+ throw invalidSiteKeyError(req.i18n, dapp, req.logger);
22
+ }
23
+ const clientSettings = await tasks.db.getClientRecord(dapp);
24
+ if (!clientSettings)
25
+ throw siteKeyNotRegisteredError(req.i18n, dapp, req.logger);
26
+ const allowedDomains = clientSettings.settings?.domains;
27
+ if (!allowedDomains)
28
+ throw siteKeyInvalidDomainError(
29
+ req.i18n,
30
+ dapp,
31
+ req.hostname,
32
+ req.logger
33
+ );
34
+ const origin = req.headers.origin;
35
+ if (!origin)
36
+ throw unauthorizedOriginError(req.i18n, void 0, req.logger);
37
+ for (const domain of allowedDomains) {
38
+ if (tasks.clientTaskManager.isSubdomainOrExactMatch(origin, domain)) {
39
+ next();
40
+ return;
35
41
  }
36
- catch (err) {
37
- if (err instanceof ProsopoApiError ||
38
- err instanceof ZodError ||
39
- err instanceof SyntaxError) {
40
- handleErrors(err, req, res, next);
41
- }
42
- else {
43
- res.status(401).json({ error: "Unauthorized", message: err });
44
- return;
45
- }
46
- }
47
- };
42
+ }
43
+ throw unauthorizedOriginError(req.i18n, origin, req.logger);
44
+ } catch (err) {
45
+ if (err instanceof ProsopoApiError || err instanceof ZodError || err instanceof SyntaxError) {
46
+ handleErrors(err, req, res, next);
47
+ } else {
48
+ res.status(401).json({ error: "Unauthorized", message: err });
49
+ return;
50
+ }
51
+ }
52
+ };
48
53
  };
49
54
  const siteKeyNotRegisteredError = (i18n, dapp, logger) => {
50
- return new ProsopoApiError("API.SITE_KEY_NOT_REGISTERED", {
51
- context: { code: 400, siteKey: dapp },
52
- i18n,
53
- logger,
54
- });
55
+ return new ProsopoApiError("API.SITE_KEY_NOT_REGISTERED", {
56
+ context: { code: 400, siteKey: dapp },
57
+ i18n,
58
+ logger
59
+ });
55
60
  };
56
61
  const invalidSiteKeyError = (i18n, siteKey, logger) => {
57
- return new ProsopoApiError("API.INVALID_SITE_KEY", {
58
- context: { code: 400, siteKey: siteKey },
59
- i18n,
60
- logger,
61
- });
62
+ return new ProsopoApiError("API.INVALID_SITE_KEY", {
63
+ context: { code: 400, siteKey },
64
+ i18n,
65
+ logger
66
+ });
62
67
  };
63
68
  const unauthorizedOriginError = (i18n, origin, logger) => {
64
- return new ProsopoApiError("API.UNAUTHORIZED_ORIGIN_URL", {
65
- context: { code: 400, origin },
66
- i18n,
67
- logger,
68
- });
69
+ return new ProsopoApiError("API.UNAUTHORIZED_ORIGIN_URL", {
70
+ context: { code: 400, origin },
71
+ i18n,
72
+ logger
73
+ });
69
74
  };
70
75
  const siteKeyInvalidDomainError = (i18n, dapp, domain, logger) => {
71
- return new ProsopoApiError("API.UNAUTHORIZED_ORIGIN_URL", {
72
- context: {
73
- code: 400,
74
- message: "No domains are allowed for this site key. Please fix in the Procaptcha Portal",
75
- siteKey: dapp,
76
- domain,
77
- },
78
- i18n,
79
- logger,
80
- });
76
+ return new ProsopoApiError("API.UNAUTHORIZED_ORIGIN_URL", {
77
+ context: {
78
+ code: 400,
79
+ message: "No domains are allowed for this site key. Please fix in the Procaptcha Portal",
80
+ siteKey: dapp,
81
+ domain
82
+ },
83
+ i18n,
84
+ logger
85
+ });
86
+ };
87
+ export {
88
+ domainMiddleware
81
89
  };
82
- //# sourceMappingURL=domainMiddleware.js.map
@@ -1,28 +1,29 @@
1
1
  import { handleErrors } from "@prosopo/api-express-router";
2
- import { validateAddr, validateSiteKey } from "./validateAddress.js";
3
- export const headerCheckMiddleware = (env) => {
4
- return async (req, res, next) => {
5
- try {
6
- const user = req.headers["prosopo-user"];
7
- const siteKey = req.headers["prosopo-site-key"];
8
- if (!user) {
9
- unauthorised(res);
10
- return;
11
- }
12
- if (!siteKey) {
13
- unauthorised(res);
14
- return;
15
- }
16
- validateSiteKey(siteKey, req.logger);
17
- validateAddr(user, undefined, req.logger);
18
- req.user = user;
19
- req.siteKey = siteKey;
20
- next();
21
- }
22
- catch (err) {
23
- return handleErrors(err, req, res, next);
24
- }
25
- };
2
+ import { validateSiteKey, validateAddr } from "./validateAddress.js";
3
+ const headerCheckMiddleware = (env) => {
4
+ return async (req, res, next) => {
5
+ try {
6
+ const user = req.headers["prosopo-user"];
7
+ const siteKey = req.headers["prosopo-site-key"];
8
+ if (!user) {
9
+ unauthorised(res);
10
+ return;
11
+ }
12
+ if (!siteKey) {
13
+ unauthorised(res);
14
+ return;
15
+ }
16
+ validateSiteKey(siteKey, req.logger);
17
+ validateAddr(user, void 0, req.logger);
18
+ req.user = user;
19
+ req.siteKey = siteKey;
20
+ next();
21
+ } catch (err) {
22
+ return handleErrors(err, req, res, next);
23
+ }
24
+ };
26
25
  };
27
26
  const unauthorised = (res) => res.status(401).json({ error: "Unauthorized", message: "Unauthorized" });
28
- //# sourceMappingURL=headerCheckMiddleware.js.map
27
+ export {
28
+ headerCheckMiddleware
29
+ };
@@ -1,12 +1,14 @@
1
1
  import { ApiPrefix } from "@prosopo/types";
2
- export function ignoreMiddleware() {
3
- return (req, res, next) => {
4
- if (req.originalUrl.indexOf(ApiPrefix) === -1) {
5
- res.statusCode = 404;
6
- res.send("Not Found");
7
- return;
8
- }
9
- next();
10
- };
2
+ function ignoreMiddleware() {
3
+ return (req, res, next) => {
4
+ if (req.originalUrl.indexOf(ApiPrefix) === -1) {
5
+ res.statusCode = 404;
6
+ res.send("Not Found");
7
+ return;
8
+ }
9
+ next();
10
+ };
11
11
  }
12
- //# sourceMappingURL=ignoreMiddleware.js.map
12
+ export {
13
+ ignoreMiddleware
14
+ };
@@ -2,89 +2,84 @@ import { createHash } from "node:crypto";
2
2
  import { Readable } from "node:stream";
3
3
  import { handleErrors } from "@prosopo/api-express-router";
4
4
  import { getLogger } from "@prosopo/common";
5
+ import { randomAsHex } from "@prosopo/util-crypto";
5
6
  import { readTlsClientHello } from "read-tls-client-hello";
6
- export const DEFAULT_JA4 = "ja4";
7
- export const getJA4 = async (headers, logger) => {
8
- logger = logger || getLogger("info", import.meta.url);
9
- if (process.env.NODE_ENV === "development") {
10
- return { ja4PlusFingerprint: DEFAULT_JA4 };
7
+ const DEFAULT_JA4 = "ja4";
8
+ const getJA4 = async (headers, logger) => {
9
+ logger = logger || getLogger("info", import.meta.url);
10
+ if (process.env.NODE_ENV === "development") {
11
+ return {
12
+ ja4PlusFingerprint: `${DEFAULT_JA4}${randomAsHex().slice(28, 32)}`
13
+ };
14
+ }
15
+ try {
16
+ const xTlsClientHello = (headers["x-tls-clienthello"] || "").toString();
17
+ const xTlsVersion = (headers["x-tls-version"] || "").toString().toLowerCase();
18
+ const xTlsServerName = (headers["x-tls-server-name"] || "").toString();
19
+ const clientHelloBuffer = Buffer.from(xTlsClientHello, "base64");
20
+ logger.debug(() => ({
21
+ msg: "ClientHello First Bytes:",
22
+ data: { hex: clientHelloBuffer.subarray(0, 5).toString("hex") }
23
+ }));
24
+ if (clientHelloBuffer[5] !== 1) {
25
+ logger.debug(() => ({
26
+ msg: "Invalid ClientHello message: First byte is not 0x01"
27
+ }));
28
+ return { ja4PlusFingerprint: DEFAULT_JA4 };
11
29
  }
30
+ logger.debug(() => ({
31
+ msg: "Headers TLS Version:",
32
+ data: { xTlsVersion }
33
+ }));
34
+ const tlsVersion = xTlsVersion.replace(/(tls)|\./g, "");
35
+ const readableStream = new Readable({
36
+ read() {
37
+ this.push(clientHelloBuffer);
38
+ }
39
+ });
40
+ const clientHello = await readTlsClientHello(readableStream);
41
+ const { alpnProtocols } = clientHello;
42
+ const [_tlsVersion, cipherSuites, extensions] = clientHello.fingerprintData;
43
+ const transport = "t";
44
+ const sniIndicator = xTlsServerName ? "d" : "i";
45
+ const validCipherSuites = cipherSuites.filter(
46
+ (cs) => (cs & 3855) !== 2570
47
+ );
48
+ const cipherCount = validCipherSuites.length;
49
+ const validExtensions = extensions.filter(
50
+ (ext) => (ext & 3855) !== 2570
51
+ );
52
+ const extensionCount = validExtensions.length;
53
+ const alpn = alpnProtocols?.length ? alpnProtocols[0] : "";
54
+ const alpnLabel = alpn ? `${alpn[0]}${alpn[alpn.length - 1]}` : "00";
55
+ const sortedCiphers = validCipherSuites.map((cs) => cs.toString(16).padStart(4, "0")).sort().join(",");
56
+ const cipherHash = createHash("sha256").update(sortedCiphers).digest("hex").slice(0, 12);
57
+ const decimalString = extensions.sort((a, b) => a - b).map((ext) => ext.toString(10)).join("-");
58
+ const extensionHash = createHash("sha256").update(decimalString).digest("hex").slice(0, 12);
59
+ const ja4PlusFingerprint = `${transport}${tlsVersion}${sniIndicator}${cipherCount}${extensionCount}${alpnLabel}_${cipherHash}_${extensionHash}`;
60
+ return { ja4PlusFingerprint };
61
+ } catch (e) {
62
+ logger.error(() => ({
63
+ msg: "Error generating JA4+ fingerprint:",
64
+ err: e instanceof Error ? e : new Error(String(e))
65
+ }));
66
+ return { ja4PlusFingerprint: DEFAULT_JA4 };
67
+ }
68
+ };
69
+ const ja4Middleware = (env) => {
70
+ return async (req, res, next) => {
12
71
  try {
13
- const xTlsClientHello = (headers["x-tls-clienthello"] || "").toString();
14
- const xTlsVersion = (headers["x-tls-version"] || "")
15
- .toString()
16
- .toLowerCase();
17
- const xTlsServerName = (headers["x-tls-server-name"] || "").toString();
18
- const clientHelloBuffer = Buffer.from(xTlsClientHello, "base64");
19
- logger.debug(() => ({
20
- msg: "ClientHello First Bytes:",
21
- data: { hex: clientHelloBuffer.subarray(0, 5).toString("hex") },
22
- }));
23
- if (clientHelloBuffer[5] !== 0x01) {
24
- logger.debug(() => ({
25
- msg: "Invalid ClientHello message: First byte is not 0x01",
26
- }));
27
- return { ja4PlusFingerprint: DEFAULT_JA4 };
28
- }
29
- logger.debug(() => ({
30
- msg: "Headers TLS Version:",
31
- data: { xTlsVersion },
32
- }));
33
- const tlsVersion = xTlsVersion.replace(/(tls)|\./g, "");
34
- const readableStream = new Readable({
35
- read() {
36
- this.push(clientHelloBuffer);
37
- },
38
- });
39
- const clientHello = await readTlsClientHello(readableStream);
40
- const { alpnProtocols } = clientHello;
41
- const [_tlsVersion, cipherSuites, extensions] = clientHello.fingerprintData;
42
- const transport = "t";
43
- const sniIndicator = xTlsServerName ? "d" : "i";
44
- const validCipherSuites = cipherSuites.filter((cs) => (cs & 0x0f0f) !== 0x0a0a);
45
- const cipherCount = validCipherSuites.length;
46
- const validExtensions = extensions.filter((ext) => (ext & 0x0f0f) !== 0x0a0a);
47
- const extensionCount = validExtensions.length;
48
- const alpn = alpnProtocols?.length ? alpnProtocols[0] : "";
49
- const alpnLabel = alpn ? `${alpn[0]}${alpn[alpn.length - 1]}` : "00";
50
- const sortedCiphers = validCipherSuites
51
- .map((cs) => cs.toString(16).padStart(4, "0"))
52
- .sort()
53
- .join(",");
54
- const cipherHash = createHash("sha256")
55
- .update(sortedCiphers)
56
- .digest("hex")
57
- .slice(0, 12);
58
- const decimalString = extensions
59
- .sort((a, b) => a - b)
60
- .map((ext) => ext.toString(10))
61
- .join("-");
62
- const extensionHash = createHash("sha256")
63
- .update(decimalString)
64
- .digest("hex")
65
- .slice(0, 12);
66
- const ja4PlusFingerprint = `${transport}${tlsVersion}${sniIndicator}${cipherCount}${extensionCount}${alpnLabel}_${cipherHash}_${extensionHash}`;
67
- return { ja4PlusFingerprint };
68
- }
69
- catch (e) {
70
- logger.error(() => ({
71
- msg: "Error generating JA4+ fingerprint:",
72
- err: e instanceof Error ? e : new Error(String(e)),
73
- }));
74
- return { ja4PlusFingerprint: DEFAULT_JA4 };
72
+ req.logger.debug(() => ({ data: { url: req.url } }));
73
+ const ja4 = await getJA4(req.headers, req.logger);
74
+ req.ja4 = ja4.ja4PlusFingerprint || "";
75
+ next();
76
+ } catch (err) {
77
+ return handleErrors(err, req, res, next);
75
78
  }
79
+ };
76
80
  };
77
- export const ja4Middleware = (env) => {
78
- return async (req, res, next) => {
79
- try {
80
- req.logger.debug(() => ({ data: { url: req.url } }));
81
- const ja4 = await getJA4(req.headers, req.logger);
82
- req.ja4 = ja4.ja4PlusFingerprint || "";
83
- next();
84
- }
85
- catch (err) {
86
- return handleErrors(err, req, res, next);
87
- }
88
- };
81
+ export {
82
+ DEFAULT_JA4,
83
+ getJA4,
84
+ ja4Middleware
89
85
  };
90
- //# sourceMappingURL=ja4Middleware.js.map
@@ -3,27 +3,30 @@ import { ProsopoApiError } from "@prosopo/common";
3
3
  import { PublicApiPaths } from "@prosopo/types";
4
4
  import { version } from "@prosopo/util";
5
5
  import express from "express";
6
- export function publicRouter() {
7
- const router = express.Router();
8
- router.get(PublicApiPaths.Healthz, (req, res) => {
9
- res.status(200).send("OK");
10
- });
11
- router.get(PublicApiPaths.GetProviderDetails, async (req, res, next) => {
12
- try {
13
- return res.json({ version, ...{ message: "Provider online" } });
14
- }
15
- catch (err) {
16
- req.logger.error(() => ({
17
- err,
18
- data: { reqParams: req.params },
19
- msg: "Error getting provider details",
20
- }));
21
- return next(new ProsopoApiError("API.BAD_REQUEST", {
22
- context: { code: 500 },
23
- }));
24
- }
25
- });
26
- router.use(handleErrors);
27
- return router;
6
+ function publicRouter() {
7
+ const router = express.Router();
8
+ router.get(PublicApiPaths.Healthz, (req, res) => {
9
+ res.status(200).send("OK");
10
+ });
11
+ router.get(PublicApiPaths.GetProviderDetails, async (req, res, next) => {
12
+ try {
13
+ return res.json({ version, ...{ message: "Provider online" } });
14
+ } catch (err) {
15
+ req.logger.error(() => ({
16
+ err,
17
+ data: { reqParams: req.params },
18
+ msg: "Error getting provider details"
19
+ }));
20
+ return next(
21
+ new ProsopoApiError("API.BAD_REQUEST", {
22
+ context: { code: 500 }
23
+ })
24
+ );
25
+ }
26
+ });
27
+ router.use(handleErrors);
28
+ return router;
28
29
  }
29
- //# sourceMappingURL=public.js.map
30
+ export {
31
+ publicRouter
32
+ };
@@ -1,10 +1,12 @@
1
- export function robotsMiddleware() {
2
- return (_req, res, next) => {
3
- res.setHeader("Strict-Transport-Security", "max-age=31536000;");
4
- res.setHeader("X-XSS-Protection", "1; mode=block");
5
- res.setHeader("X-Frame-Options", "DENY");
6
- res.setHeader("X-Robots-Tag", "none");
7
- next();
8
- };
1
+ function robotsMiddleware() {
2
+ return (_req, res, next) => {
3
+ res.setHeader("Strict-Transport-Security", "max-age=31536000;");
4
+ res.setHeader("X-XSS-Protection", "1; mode=block");
5
+ res.setHeader("X-Frame-Options", "DENY");
6
+ res.setHeader("X-Robots-Tag", "none");
7
+ next();
8
+ };
9
9
  }
10
- //# sourceMappingURL=robotsMiddleware.js.map
10
+ export {
11
+ robotsMiddleware
12
+ };
@@ -1,23 +1,25 @@
1
1
  import { ProsopoApiError } from "@prosopo/common";
2
2
  import { validateAddress } from "@prosopo/util-crypto";
3
- export const validateSiteKey = (siteKey, logger) => {
4
- return validateAddr(siteKey, "API.INVALID_SITE_KEY", logger);
3
+ const validateSiteKey = (siteKey, logger) => {
4
+ return validateAddr(siteKey, "API.INVALID_SITE_KEY", logger);
5
5
  };
6
- export const validateAddr = (address, translationKey = "CONTRACT.INVALID_ADDRESS", logger) => {
7
- try {
8
- const valid = validateAddress(address, false, 42);
9
- if (!valid) {
10
- throw new ProsopoApiError(translationKey, {
11
- context: { code: 400, siteKey: address },
12
- logger,
13
- });
14
- }
15
- }
16
- catch (err) {
17
- throw new ProsopoApiError(translationKey, {
18
- context: { code: 400, siteKey: address },
19
- logger,
20
- });
6
+ const validateAddr = (address, translationKey = "CONTRACT.INVALID_ADDRESS", logger) => {
7
+ try {
8
+ const valid = validateAddress(address, false, 42);
9
+ if (!valid) {
10
+ throw new ProsopoApiError(translationKey, {
11
+ context: { code: 400, siteKey: address },
12
+ logger
13
+ });
21
14
  }
15
+ } catch (err) {
16
+ throw new ProsopoApiError(translationKey, {
17
+ context: { code: 400, siteKey: address },
18
+ logger
19
+ });
20
+ }
21
+ };
22
+ export {
23
+ validateAddr,
24
+ validateSiteKey
22
25
  };
23
- //# sourceMappingURL=validateAddress.js.map