@prosopo/database 4.0.26 → 4.0.28

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 (47) hide show
  1. package/.turbo/turbo-build$colon$cjs.log +9 -9
  2. package/.turbo/turbo-build$colon$tsc.log +16 -16
  3. package/.turbo/turbo-build.log +9 -9
  4. package/CHANGELOG.md +108 -0
  5. package/dist/base/mongo.d.ts +7 -1
  6. package/dist/base/mongo.d.ts.map +1 -1
  7. package/dist/base/mongo.js +14 -2
  8. package/dist/base/mongo.js.map +1 -1
  9. package/dist/cjs/base/mongo.cjs +14 -2
  10. package/dist/cjs/databases/captcha.cjs +2 -2
  11. package/dist/cjs/databases/centralDbStreamer.cjs +10 -1
  12. package/dist/cjs/databases/provider.cjs +10 -30
  13. package/dist/cjs/index.cjs +3 -3
  14. package/dist/cjs/mongooseOptions.cjs +20 -3
  15. package/dist/databases/captcha.d.ts +4 -4
  16. package/dist/databases/captcha.d.ts.map +1 -1
  17. package/dist/databases/captcha.js +2 -2
  18. package/dist/databases/captcha.js.map +1 -1
  19. package/dist/databases/centralDbStreamer.d.ts +2 -0
  20. package/dist/databases/centralDbStreamer.d.ts.map +1 -1
  21. package/dist/databases/centralDbStreamer.js +10 -1
  22. package/dist/databases/centralDbStreamer.js.map +1 -1
  23. package/dist/databases/provider.d.ts +2 -4
  24. package/dist/databases/provider.d.ts.map +1 -1
  25. package/dist/databases/provider.js +11 -31
  26. package/dist/databases/provider.js.map +1 -1
  27. package/dist/index.js +4 -4
  28. package/dist/index.js.map +1 -1
  29. package/dist/mongooseOptions.d.ts +4 -0
  30. package/dist/mongooseOptions.d.ts.map +1 -1
  31. package/dist/mongooseOptions.js +19 -4
  32. package/dist/mongooseOptions.js.map +1 -1
  33. package/dist/tests/integration/commitmentUpsertNoMutation.integration.test.d.ts +2 -0
  34. package/dist/tests/integration/commitmentUpsertNoMutation.integration.test.d.ts.map +1 -0
  35. package/dist/tests/integration/commitmentUpsertNoMutation.integration.test.js +51 -0
  36. package/dist/tests/integration/commitmentUpsertNoMutation.integration.test.js.map +1 -0
  37. package/dist/tests/integration/providedIpPipelineCast.integration.test.js +2 -2
  38. package/dist/tests/integration/providedIpPipelineCast.integration.test.js.map +1 -1
  39. package/dist/tests/integration/puzzleCentralStreaming.integration.test.js +4 -4
  40. package/dist/tests/integration/puzzleCentralStreaming.integration.test.js.map +1 -1
  41. package/dist/tests/mongooseOptions.unit.test.js +19 -1
  42. package/dist/tests/mongooseOptions.unit.test.js.map +1 -1
  43. package/dist/tests/unit/base/mongo.unit.test.d.ts +2 -0
  44. package/dist/tests/unit/base/mongo.unit.test.d.ts.map +1 -0
  45. package/dist/tests/unit/base/mongo.unit.test.js +58 -0
  46. package/dist/tests/unit/base/mongo.unit.test.js.map +1 -0
  47. package/package.json +15 -15
@@ -1,5 +1,5 @@
1
1
 
2
- > @prosopo/database@4.0.26 build:cjs
2
+ > @prosopo/database@4.0.28 build:cjs
3
3
  > NODE_ENV=${NODE_ENV:-development}; vite build --config vite.cjs.config.ts --mode $NODE_ENV
4
4
 
5
5
  ViteCommonJSConfig: .
@@ -25,6 +25,7 @@ ViteCommonJSConfig: .
25
25
  '@prosopo/logger',
26
26
  '@prosopo/util',
27
27
  '@prosopo/types',
28
+ The plugin "vite-tsconfig-paths" is detected. Vite now supports tsconfig paths resolution natively via the resolve.tsconfigPaths option. You can remove the plugin and set resolve.tsconfigPaths: true in your Vite config instead.
28
29
  '@prosopo/util-crypto',
29
30
  '@prosopo/types-database',
30
31
  '@prosopo/user-access-policy',
@@ -33,7 +34,6 @@ ViteCommonJSConfig: .
33
34
  '@prosopo/api'
34
35
  ]
35
36
  }
36
- The plugin "vite-tsconfig-paths" is detected. Vite now supports tsconfig paths resolution natively via the resolve.tsconfigPaths option. You can remove the plugin and set resolve.tsconfigPaths: true in your Vite config instead.
37
37
  vite v8.1.5 building ssr environment for production...
38
38
  Bundle build started
39
39
  
@@ -45,12 +45,12 @@ dist/cjs/base/mongoMemory.cjs 0.66 kB │ gzip: 0.32 kB
45
45
  dist/cjs/_virtual/_rolldown/runtime.cjs 1.00 kB │ gzip: 0.50 kB
46
46
  dist/cjs/databases/index.cjs 1.14 kB │ gzip: 0.32 kB
47
47
  dist/cjs/databases/client.cjs 1.57 kB │ gzip: 0.69 kB
48
- dist/cjs/index.cjs 1.57 kB │ gzip: 0.48 kB
49
- dist/cjs/mongooseOptions.cjs 2.65 kB │ gzip: 1.15 kB
50
- dist/cjs/base/mongo.cjs 3.77 kB │ gzip: 1.29 kB
51
- dist/cjs/databases/centralDbStreamer.cjs 5.29 kB │ gzip: 1.30 kB
52
- dist/cjs/databases/captcha.cjs 7.36 kB │ gzip: 2.17 kB
48
+ dist/cjs/index.cjs 1.66 kB │ gzip: 0.49 kB
49
+ dist/cjs/mongooseOptions.cjs 3.74 kB │ gzip: 1.56 kB
50
+ dist/cjs/base/mongo.cjs 4.27 kB │ gzip: 1.41 kB
51
+ dist/cjs/databases/centralDbStreamer.cjs 5.53 kB │ gzip: 1.37 kB
52
+ dist/cjs/databases/captcha.cjs 7.38 kB │ gzip: 2.18 kB
53
53
  dist/cjs/redisCache.cjs 15.77 kB │ gzip: 4.54 kB
54
- dist/cjs/databases/provider.cjs 59.70 kB │ gzip: 12.01 kB
54
+ dist/cjs/databases/provider.cjs 59.03 kB │ gzip: 11.78 kB
55
55
 
56
- ✓ built in 72ms
56
+ ✓ built in 124ms
@@ -1,8 +1,8 @@
1
1
 
2
- > @prosopo/database@4.0.26 build:tsc
2
+ > @prosopo/database@4.0.28 build:tsc
3
3
  > tsc --build --verbose
4
4
 
5
- 1:56:34 PM - Projects in this build:
5
+ 1:15:41 PM - Projects in this build:
6
6
  * ../../dev/config/tsconfig.json
7
7
  * ../locale/tsconfig.json
8
8
  * ../util/tsconfig.json
@@ -17,31 +17,31 @@
17
17
  * ../types-database/tsconfig.json
18
18
  * tsconfig.json
19
19
 
20
- 1:56:34 PM - Project '../../dev/config/tsconfig.json' is up to date because newest input '../../dev/config/src/webpack/webpack.config.ts' is older than output '../../dev/config/tsconfig.tsbuildinfo'
20
+ 1:15:41 PM - Project '../../dev/config/tsconfig.json' is up to date because newest input '../../dev/config/src/webpack/webpack.config.ts' is older than output '../../dev/config/tsconfig.tsbuildinfo'
21
21
 
22
- 1:56:34 PM - Project '../locale/tsconfig.json' is up to date because newest input '../locale/src/translationKey.ts' is older than output '../locale/tsconfig.tsbuildinfo'
22
+ 1:15:41 PM - Project '../locale/tsconfig.json' is up to date because newest input '../locale/src/translationKey.ts' is older than output '../locale/tsconfig.tsbuildinfo'
23
23
 
24
- 1:56:34 PM - Project '../util/tsconfig.json' is up to date because newest input '../util/src/url.ts' is older than output '../util/tsconfig.tsbuildinfo'
24
+ 1:15:41 PM - Project '../util/tsconfig.json' is up to date because newest input '../util/src/url.ts' is older than output '../util/tsconfig.tsbuildinfo'
25
25
 
26
- 1:56:34 PM - Project '../logger/tsconfig.json' is up to date because newest input '../logger/src/index.ts' is older than output '../logger/tsconfig.tsbuildinfo'
26
+ 1:15:41 PM - Project '../logger/tsconfig.json' is up to date because newest input '../logger/src/index.ts' is older than output '../logger/tsconfig.tsbuildinfo'
27
27
 
28
- 1:56:34 PM - Project '../util-crypto/tsconfig.json' is up to date because newest input '../util-crypto/src/types.ts' is older than output '../util-crypto/tsconfig.tsbuildinfo'
28
+ 1:15:41 PM - Project '../util-crypto/tsconfig.json' is up to date because newest input '../util-crypto/src/types.ts' is older than output '../util-crypto/tsconfig.tsbuildinfo'
29
29
 
30
- 1:56:35 PM - Project '../types/tsconfig.json' is up to date because newest input '../types/src/index.ts' is older than output '../types/tsconfig.tsbuildinfo'
30
+ 1:15:41 PM - Project '../types/tsconfig.json' is up to date because newest input '../types/src/types.test-d.ts' is older than output '../types/tsconfig.tsbuildinfo'
31
31
 
32
- 1:56:35 PM - Project '../common/tsconfig.json' is up to date because newest input '../common/src/index.ts' is older than output '../common/tsconfig.tsbuildinfo'
32
+ 1:15:41 PM - Project '../common/tsconfig.json' is up to date because newest input '../common/src/utils/batches.ts' is older than output '../common/tsconfig.tsbuildinfo'
33
33
 
34
- 1:56:35 PM - Project '../api-route/tsconfig.json' is up to date because newest input '../api-route/src/index.ts' is older than output '../api-route/tsconfig.tsbuildinfo'
34
+ 1:15:41 PM - Project '../api-route/tsconfig.json' is up to date because newest input '../api-route/src/apiRoutes.ts' is older than output '../api-route/tsconfig.tsbuildinfo'
35
35
 
36
- 1:56:35 PM - Project '../redis-client/tsconfig.json' is up to date because newest input '../redis-client/src/index.ts' is older than output '../redis-client/tsconfig.tsbuildinfo'
36
+ 1:15:41 PM - Project '../redis-client/tsconfig.json' is up to date because newest input '../redis-client/src/index.ts' is older than output '../redis-client/tsconfig.tsbuildinfo'
37
37
 
38
- 1:56:35 PM - Project '../api/tsconfig.json' is up to date because newest input '../api/src/index.ts' is older than output '../api/tsconfig.tsbuildinfo'
38
+ 1:15:41 PM - Project '../api/tsconfig.json' is up to date because newest input '../api/src/tests/apiHarness.ts' is older than output '../api/tsconfig.tsbuildinfo'
39
39
 
40
- 1:56:35 PM - Project '../user-access-policy/tsconfig.json' is up to date because newest input '../user-access-policy/src/rule.ts' is older than output '../user-access-policy/tsconfig.tsbuildinfo'
40
+ 1:15:41 PM - Project '../user-access-policy/tsconfig.json' is up to date because newest input '../user-access-policy/src/transformRule.ts' is older than output '../user-access-policy/tsconfig.tsbuildinfo'
41
41
 
42
- 1:56:35 PM - Project '../types-database/tsconfig.json' is up to date because newest input '../types-database/src/index.ts' is older than output '../types-database/tsconfig.tsbuildinfo'
42
+ 1:15:41 PM - Project '../types-database/tsconfig.json' is up to date because newest input '../types-database/src/types.test-d.ts' is older than output '../types-database/tsconfig.tsbuildinfo'
43
43
 
44
- 1:56:35 PM - Project 'tsconfig.json' is out of date because output file 'tsconfig.tsbuildinfo' does not exist
44
+ 1:15:41 PM - Project 'tsconfig.json' is out of date because output file 'tsconfig.tsbuildinfo' does not exist
45
45
 
46
- 1:56:35 PM - Building project '/home/runner/work/captcha/captcha/packages/database/tsconfig.json'...
46
+ 1:15:41 PM - Building project '/home/runner/work/captcha/captcha/packages/database/tsconfig.json'...
47
47
 
@@ -1,9 +1,9 @@
1
1
 
2
- > @prosopo/database@4.0.26 build
2
+ > @prosopo/database@4.0.28 build
3
3
  > npm run build:cross-env -- --mode ${NODE_ENV:-development}
4
4
 
5
5
 
6
- > @prosopo/database@4.0.26 build:cross-env
6
+ > @prosopo/database@4.0.28 build:cross-env
7
7
  > vite build --config vite.esm.config.ts --mode production
8
8
 
9
9
  ViteEsmConfig: .
@@ -48,13 +48,13 @@ dist/_virtual/_rolldown/runtime.js 0.04 kB │ gzip: 0.06 kB
48
48
  dist/base/index.js 0.14 kB │ gzip: 0.08 kB
49
49
  dist/base/mongoMemory.js 0.60 kB │ gzip: 0.30 kB
50
50
  dist/databases/index.js 0.77 kB │ gzip: 0.27 kB
51
- dist/index.js 0.92 kB │ gzip: 0.34 kB
51
+ dist/index.js 1.07 kB │ gzip: 0.38 kB
52
52
  dist/databases/client.js 1.47 kB │ gzip: 0.68 kB
53
- dist/mongooseOptions.js 2.56 kB │ gzip: 1.12 kB
54
- dist/base/mongo.js 3.52 kB │ gzip: 1.20 kB
55
- dist/databases/centralDbStreamer.js 5.23 kB │ gzip: 1.28 kB
56
- dist/databases/captcha.js 7.28 kB │ gzip: 2.16 kB
53
+ dist/mongooseOptions.js 3.58 kB │ gzip: 1.53 kB
54
+ dist/base/mongo.js 4.01 kB │ gzip: 1.32 kB
55
+ dist/databases/centralDbStreamer.js 5.47 kB │ gzip: 1.35 kB
56
+ dist/databases/captcha.js 7.30 kB │ gzip: 2.17 kB
57
57
  dist/redisCache.js 15.71 kB │ gzip: 4.53 kB
58
- dist/databases/provider.js 58.41 kB │ gzip: 12.04 kB
58
+ dist/databases/provider.js 57.73 kB │ gzip: 11.80 kB
59
59
 
60
- ✓ built in 95ms
60
+ ✓ built in 82ms
package/CHANGELOG.md CHANGED
@@ -1,5 +1,113 @@
1
1
  # @prosopo/database
2
2
 
3
+ ## 4.0.28
4
+ ### Patch Changes
5
+
6
+ - f8a41fe: Stop leaking a mongoose connection pool on every failed database connect.
7
+
8
+ `MongoDatabase.connect()` assigns `this.connection` only once the connection
9
+ opens, so a connection that fails to open is unreachable from the instance and
10
+ `close()` can never reach it — while mongoose keeps its topology monitor, its
11
+ `minPoolSize: 5` pool and its entry in `mongoose.connections` alive and
12
+ retrying forever. `onError` now destroys that connection. `destroy` rather than
13
+ `close` because only `destroy` drops the `mongoose.connections` entry, which
14
+ would otherwise retain the object on its own. The teardown is guarded so that a
15
+ runtime `error` on an already-open connection is not mistaken for a failed
16
+ connect and does not tear down a working pool; the `error` listener stays
17
+ registered after `open` because an `EventEmitter` `error` with no listener
18
+ would take the process down.
19
+
20
+ Observed on a provider whose connects to the central DB were timing out: 524
21
+ failed connects an hour accumulated 5,819 ESTABLISHED sockets to the central
22
+ DB and 5,859 TLS sockets, and the resulting flood of driver DNS lookups
23
+ saturated libuv's four-thread pool — 8,812 `getaddrinfo` calls queued — so
24
+ every unrelated outbound lookup in the process backed up behind them. That
25
+ provider burned 3.45x the CPU of a healthy peer while serving 2.5x less
26
+ traffic, with event-loop p99 at 240ms against the peer's 27ms.
27
+
28
+ `getMongoConnectionOptions` also gains `connectTimeoutMS` and
29
+ `serverSelectionTimeoutMS` overrides, and `CentralDbStreamer` passes 45s for
30
+ both. The 10s default is sized for a database that is local or on the same
31
+ continent; the central DB is long-haul for every provider and genuinely distant
32
+ for some, where the TLS handshake alone measures 2-30s. Under the old ceiling
33
+ those providers could never connect at all, so the streamer burned a connect
34
+ attempt every cooldown forever and streamed no records — which is what fed the
35
+ leak above.
36
+ - 6f57ee9: chore(deps): bump make-dir from 3.1.0 to 5.1.0
37
+ - 6f57ee9: chore(deps): bump the npm-minor-and-patch group across 1 directory with 3 updates
38
+ - Updated dependencies [6f57ee9]
39
+ - Updated dependencies [6f57ee9]
40
+ - Updated dependencies [e22d5fb]
41
+ - Updated dependencies [b6918c0]
42
+ - Updated dependencies [d288371]
43
+ - @prosopo/user-access-policy@3.13.0
44
+ - @prosopo/types@5.7.0
45
+ - @prosopo/util@3.3.9
46
+ - @prosopo/types-database@5.4.1
47
+ - @prosopo/common@3.1.54
48
+ - @prosopo/logger@2.0.9
49
+ - @prosopo/redis-client@1.0.35
50
+
51
+ ## 4.0.27
52
+ ### Patch Changes
53
+
54
+ - 89dd38a: chore(deps): batch the outstanding dependabot bumps into one upgrade
55
+
56
+ Rolls up dependabot PRs #3112, #3127-#3134 and #3159. Majors: `mongoose`
57
+ 8 -> 9, `bson` 6 -> 7, `@noble/curves` 1 -> 2, `@polkadot/util-crypto`
58
+ 13 -> 14, `@typegoose/auto-increment` 4 -> 5, `@babel/preset-env` 7 -> 8,
59
+ `@types/jsdom` 21 -> 30, `@types/bcrypt` 5 -> 6, `@actions/github` 6 -> 9,
60
+ `testcontainers` 11 -> 12. The rest are minor/patch.
61
+
62
+ Code changes the majors forced:
63
+ - `@noble/curves` v2 requires `.js` specifiers and renamed the point API,
64
+ so `secp256k1.ProjectivePoint.fromHex(...).toRawBytes()` becomes
65
+ `secp256k1.Point.fromBytes(...).toBytes()`, `RistrettoPoint` becomes
66
+ `ristretto255.Point`, and `abstract/utils` moves to `utils.js`.
67
+ - mongoose 9 drops `RootFilterQuery` (now `QueryFilter`), no longer sets
68
+ `background: true` on schema indexes by default, and no longer declares
69
+ `id` on `Document`, which un-hid a mismatch between
70
+ `updateDappUserCommitment`'s `Hash` parameter and the `string` `id` it
71
+ filters on.
72
+ - mongoose 9 rejects an aggregation-pipeline update (an array) unless the
73
+ call passes `updatePipeline: true`, so the six pipeline writes in
74
+ `ProviderDatabase` now opt in explicitly.
75
+ - mongoose 9's `castUpdate` throws on a `$setOnInsert` key inside `$set`.
76
+ `storeUserImageCaptchaSolution` passed its record straight in as the
77
+ update, and mongoose's `moveImmutableProperties` mutates that object on
78
+ an upsert -- adding the very `$setOnInsert` key the record then carried
79
+ into `CentralDbStreamer.streamImageRecord`. Image records stopped
80
+ reaching the central DB (the streamer is fire-and-forget, so it only
81
+ logged) and signup verification returned 500. The update is now an
82
+ explicit `$set` over a shallow copy.
83
+ - `@prosopo/database` moves from mongodb 6.20 to 7.5 to match the driver
84
+ mongoose 9 pulls, so bson 7 is the only copy resolvable in the package.
85
+ - `vitest`/`@vitest/coverage-v8` go to 4.1.11 alongside dependabot's
86
+ `@vitest/spy` bump; leaving them at 4.1.10 installed a second copy of
87
+ `@vitest/spy` and broke type inference in the provider test utils.
88
+ - 8a670d3: Remove the provider-side context validation path.
89
+
90
+ The provider read a per-context baseline out of `clientcontextentropies` on the frictionless path and compared a session's head hash against it. The task that wrote that collection was removed from the provider on 2026-08-21, so the read has returned `undefined` ever since and the branch has been dead in every deployment since then. Computing and applying the baseline now happens off-provider.
91
+
92
+ Removed: `contextAwareValidation.ts`, the decision-machine branch that used it, `getClientContextEntropy` on the provider and its database method, the `clientContextEntropy` table registration, the unused `getRoundsFromSimScore` helper, and the `contextAwareEnabled` parameter threaded into image verification — which logged and then did nothing, its return commented out.
93
+
94
+ Also removes the per-site `settings.contextAware` block that configured it, along with `ContextAwareSchema`, `IContextAware`, `IContexts`, `ContextConfigSchema`, `contextAwareThresholdDefault` and `expandContexts`, the legacy `default`/`webview` context keys and their helpers, and `FrictionlessReason.CONTEXT_AWARE_VALIDATION_FAILED`. The site-key registration CLI no longer writes a `contextAware` default into new sites.
95
+
96
+ `ContextType`, `contextTypeFromSession` and `deviceContextTypes` stay — the off-provider work keys on them. `ClientContextEntropyRecord` and its schema stay for the same reason; only the provider's use of them goes.
97
+
98
+ No behaviour change: every path removed here was already inert.
99
+ - Updated dependencies [7fd6eb2]
100
+ - Updated dependencies [89dd38a]
101
+ - Updated dependencies [80f73c1]
102
+ - Updated dependencies [8a670d3]
103
+ - @prosopo/user-access-policy@3.12.33
104
+ - @prosopo/common@3.1.53
105
+ - @prosopo/logger@2.0.8
106
+ - @prosopo/redis-client@1.0.34
107
+ - @prosopo/types@5.6.0
108
+ - @prosopo/types-database@5.4.0
109
+ - @prosopo/util@3.3.8
110
+
3
111
  ## 4.0.26
4
112
  ### Patch Changes
5
113
 
@@ -1,6 +1,10 @@
1
1
  import { type Logger } from "@prosopo/logger";
2
2
  import type { IDatabase } from "@prosopo/types-database";
3
3
  import mongoose, { type Connection } from "mongoose";
4
+ export interface MongoConnectionTimeouts {
5
+ connectTimeoutMS?: number;
6
+ serverSelectionTimeoutMS?: number;
7
+ }
4
8
  export declare class MongoDatabase implements IDatabase {
5
9
  protected readonly _url: string;
6
10
  safeURL: string;
@@ -9,7 +13,9 @@ export declare class MongoDatabase implements IDatabase {
9
13
  logger: Logger;
10
14
  connected: boolean;
11
15
  private connecting?;
12
- constructor(url: string, dbname?: string, authSource?: string, logger?: Logger);
16
+ protected readonly connectTimeoutMS?: number;
17
+ protected readonly serverSelectionTimeoutMS?: number;
18
+ constructor(url: string, dbname?: string, authSource?: string, logger?: Logger, timeouts?: MongoConnectionTimeouts);
13
19
  get url(): string;
14
20
  getConnection(): mongoose.Connection;
15
21
  connect(): Promise<void>;
@@ -1 +1 @@
1
- {"version":3,"file":"mongo.d.ts","sourceRoot":"","sources":["../../src/base/mongo.ts"],"names":[],"mappings":"AAeA,OAAO,EAAE,KAAK,MAAM,EAAa,MAAM,iBAAiB,CAAC;AACzD,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yBAAyB,CAAC;AACzD,OAAO,QAAQ,EAAE,EAAE,KAAK,UAAU,EAAE,MAAM,UAAU,CAAC;AAcrD,qBAAa,aAAc,YAAW,SAAS;IAC9C,SAAS,CAAC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IAChC,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,MAAM,CAAC;IACf,UAAU,CAAC,EAAE,UAAU,CAAC;IACxB,MAAM,EAAE,MAAM,CAAC;IACf,SAAS,UAAS;IAClB,OAAO,CAAC,UAAU,CAAC,CAAgB;gBAGlC,GAAG,EAAE,MAAM,EACX,MAAM,CAAC,EAAE,MAAM,EACf,UAAU,CAAC,EAAE,MAAM,EACnB,MAAM,CAAC,EAAE,MAAM;IAkBhB,IAAI,GAAG,IAAI,MAAM,CAEhB;IAED,aAAa,IAAI,QAAQ,CAAC,UAAU;IAa9B,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAoGxB,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;CAM5B"}
1
+ {"version":3,"file":"mongo.d.ts","sourceRoot":"","sources":["../../src/base/mongo.ts"],"names":[],"mappings":"AAeA,OAAO,EAAE,KAAK,MAAM,EAAa,MAAM,iBAAiB,CAAC;AACzD,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,yBAAyB,CAAC;AACzD,OAAO,QAAQ,EAAE,EAAE,KAAK,UAAU,EAAE,MAAM,UAAU,CAAC;AAYrD,MAAM,WAAW,uBAAuB;IACvC,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,wBAAwB,CAAC,EAAE,MAAM,CAAC;CAClC;AAQD,qBAAa,aAAc,YAAW,SAAS;IAC9C,SAAS,CAAC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IAChC,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,MAAM,CAAC;IACf,UAAU,CAAC,EAAE,UAAU,CAAC;IACxB,MAAM,EAAE,MAAM,CAAC;IACf,SAAS,UAAS;IAClB,OAAO,CAAC,UAAU,CAAC,CAAgB;IACnC,SAAS,CAAC,QAAQ,CAAC,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC7C,SAAS,CAAC,QAAQ,CAAC,wBAAwB,CAAC,EAAE,MAAM,CAAC;gBAGpD,GAAG,EAAE,MAAM,EACX,MAAM,CAAC,EAAE,MAAM,EACf,UAAU,CAAC,EAAE,MAAM,EACnB,MAAM,CAAC,EAAE,MAAM,EACf,QAAQ,CAAC,EAAE,uBAAuB;IAoBnC,IAAI,GAAG,IAAI,MAAM,CAEhB;IAED,aAAa,IAAI,QAAQ,CAAC,UAAU;IAa9B,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAyIxB,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;CAM5B"}
@@ -13,8 +13,10 @@ var DEFAULT_ENDPOINT = "mongodb://127.0.0.1:27017";
13
13
  * @return {MongoDatabase} Database layer
14
14
  */
15
15
  var MongoDatabase = class {
16
- constructor(url, dbname, authSource, logger) {
16
+ constructor(url, dbname, authSource, logger, timeouts) {
17
17
  this.connected = false;
18
+ this.connectTimeoutMS = timeouts?.connectTimeoutMS;
19
+ this.serverSelectionTimeoutMS = timeouts?.serverSelectionTimeoutMS;
18
20
  const parsedUrl = new URL(url || DEFAULT_ENDPOINT);
19
21
  if (dbname) parsedUrl.pathname = dbname;
20
22
  if (authSource) parsedUrl.searchParams.set("authSource", authSource);
@@ -54,9 +56,13 @@ var MongoDatabase = class {
54
56
  appName,
55
57
  dbName: this.dbname,
56
58
  maxPoolSize: 50,
57
- minPoolSize: 5
59
+ minPoolSize: 5,
60
+ connectTimeoutMS: this.connectTimeoutMS,
61
+ serverSelectionTimeoutMS: this.serverSelectionTimeoutMS
58
62
  }));
63
+ let opened = false;
59
64
  const onConnected = () => {
65
+ opened = true;
60
66
  this.logger.debug(() => ({ msg: "Database connection opened" }));
61
67
  this.connected = true;
62
68
  this.connection = connection;
@@ -70,6 +76,12 @@ var MongoDatabase = class {
70
76
  }));
71
77
  this.connected = false;
72
78
  this.connecting = void 0;
79
+ if (!opened) connection.destroy(true).catch((destroyErr) => {
80
+ this.logger.error(() => ({
81
+ err: destroyErr,
82
+ msg: "Failed to destroy unconnected database connection"
83
+ }));
84
+ });
73
85
  reject(err);
74
86
  };
75
87
  connection.once("open", onConnected);
@@ -1 +1 @@
1
- {"version":3,"file":"mongo.js","sourceRoot":"","sources":["../../src/base/mongo.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"mongo.js","sourceRoot":"","sources":["../../src/base/mongo.ts"],"names":[],"mappings":"AAaA,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AACzC,OAAO,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AACjD,OAAO,EAAe,SAAS,EAAE,MAAM,iBAAiB,CAAC;AAEzD,OAAO,QAA6B,MAAM,UAAU,CAAC;AACrD,OAAO,EAAE,yBAAyB,EAAE,MAAM,uBAAuB,CAAC;AAElE,QAAQ,CAAC,GAAG,CAAC,aAAa,EAAE,KAAK,CAAC,CAAC;AAGnC,MAAM,gBAAgB,GAAG,2BAA2B,CAAC;AAiBrD,MAAM,OAAO,aAAa;IAWzB,YACC,GAAW,EACX,MAAe,EACf,UAAmB,EACnB,MAAe,EACf,QAAkC;QAVnC,cAAS,GAAG,KAAK,CAAC;QAYjB,IAAI,CAAC,gBAAgB,GAAG,QAAQ,EAAE,gBAAgB,CAAC;QACnD,IAAI,CAAC,wBAAwB,GAAG,QAAQ,EAAE,wBAAwB,CAAC;QACnE,MAAM,YAAY,GAAG,GAAG,IAAI,gBAAgB,CAAC;QAC7C,MAAM,SAAS,GAAG,IAAI,GAAG,CAAC,YAAY,CAAC,CAAC;QACxC,IAAI,MAAM,EAAE,CAAC;YACZ,SAAS,CAAC,QAAQ,GAAG,MAAM,CAAC;QAC7B,CAAC;QACD,IAAI,UAAU,EAAE,CAAC;YAChB,SAAS,CAAC,YAAY,CAAC,GAAG,CAAC,YAAY,EAAE,UAAU,CAAC,CAAC;QACtD,CAAC;QACD,IAAI,CAAC,IAAI,GAAG,SAAS,CAAC,QAAQ,EAAE,CAAC;QACjC,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC,GAAG,CAAC,OAAO,CAAC,SAAS,EAAE,eAAe,CAAC,CAAC;QAC5D,IAAI,CAAC,MAAM,GAAG,MAAM,IAAI,SAAS,CAAC,QAAQ,CAAC,OAAO,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC;QAC5D,IAAI,CAAC,MAAM,GAAG,CAAC,MAAM,IAAI,SAAS,CAAC,MAAM,EAAE,gBAAgB,CAAC,CAAC,CAAC,IAAI,CAAC;YAClE,QAAQ,EAAE,IAAI,CAAC,OAAO;SACtB,CAAC,CAAC;IACJ,CAAC;IAED,IAAI,GAAG;QACN,OAAO,IAAI,CAAC,IAAI,CAAC;IAClB,CAAC;IAED,aAAa;QACZ,IAAI,CAAC,IAAI,CAAC,UAAU,EAAE,CAAC;YACtB,MAAM,IAAI,cAAc,CAAC,+BAA+B,EAAE;gBACzD,OAAO,EAAE,EAAE,cAAc,EAAE,IAAI,CAAC,aAAa,CAAC,IAAI,EAAE;gBACpD,MAAM,EAAE,IAAI,CAAC,MAAM;aACnB,CAAC,CAAC;QACJ,CAAC;QACD,OAAO,IAAI,CAAC,UAAU,CAAC;IACxB,CAAC;IAKD,KAAK,CAAC,OAAO;QACZ,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;YACxB,GAAG,EAAE,wBAAwB;SAC7B,CAAC,CAAC,CAAC;QACJ,IAAI,CAAC;YAEJ,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC;gBACpB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;oBACxB,GAAG,EAAE,kCAAkC;iBACvC,CAAC,CAAC,CAAC;gBACJ,OAAO;YACR,CAAC;YAGD,IAAI,IAAI,CAAC,UAAU,EAAE,CAAC;gBACrB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;oBACxB,GAAG,EAAE,2DAA2D;iBAChE,CAAC,CAAC,CAAC;gBACJ,OAAO,IAAI,CAAC,UAAU,CAAC;YACxB,CAAC;YAGD,IAAI,CAAC,UAAU,GAAG,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,MAAM,EAAE,EAAE;gBACjD,MAAM,OAAO,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;gBAE/C,MAAM,UAAU,GAAG,QAAQ,CAAC,gBAAgB,CAC3C,IAAI,CAAC,GAAG,EACR,yBAAyB,CAAC;oBACzB,GAAG,EAAE,IAAI,CAAC,GAAG;oBACb,OAAO;oBACP,MAAM,EAAE,IAAI,CAAC,MAAM;oBACnB,WAAW,EAAE,EAAE;oBACf,WAAW,EAAE,CAAC;oBACd,gBAAgB,EAAE,IAAI,CAAC,gBAAgB;oBACvC,wBAAwB,EAAE,IAAI,CAAC,wBAAwB;iBACvD,CAAC,CACF,CAAC;gBAQF,IAAI,MAAM,GAAG,KAAK,CAAC;gBAEnB,MAAM,WAAW,GAAG,GAAG,EAAE;oBACxB,MAAM,GAAG,IAAI,CAAC;oBACd,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;wBACxB,GAAG,EAAE,4BAA4B;qBACjC,CAAC,CAAC,CAAC;oBACJ,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC;oBACtB,IAAI,CAAC,UAAU,GAAG,UAAU,CAAC;oBAC7B,IAAI,CAAC,UAAU,GAAG,SAAS,CAAC;oBAC5B,OAAO,EAAE,CAAC;gBACX,CAAC,CAAC;gBAEF,MAAM,OAAO,GAAG,CAAC,GAAY,EAAE,EAAE;oBAChC,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;wBACxB,GAAG;wBACH,GAAG,EAAE,gBAAgB;qBACrB,CAAC,CAAC,CAAC;oBACJ,IAAI,CAAC,SAAS,GAAG,KAAK,CAAC;oBACvB,IAAI,CAAC,UAAU,GAAG,SAAS,CAAC;oBAE5B,IAAI,CAAC,MAAM,EAAE,CAAC;wBAiBb,UAAU,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,KAAK,CAAC,CAAC,UAAmB,EAAE,EAAE;4BACtD,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;gCACxB,GAAG,EAAE,UAAU;gCACf,GAAG,EAAE,mDAAmD;6BACxD,CAAC,CAAC,CAAC;wBACL,CAAC,CAAC,CAAC;oBACJ,CAAC;oBAED,MAAM,CAAC,GAAG,CAAC,CAAC;gBACb,CAAC,CAAC;gBAEF,UAAU,CAAC,IAAI,CAAC,MAAM,EAAE,WAAW,CAAC,CAAC;gBACrC,UAAU,CAAC,IAAI,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;gBAGlC,UAAU,CAAC,EAAE,CAAC,cAAc,EAAE,GAAG,EAAE;oBAClC,IAAI,CAAC,SAAS,GAAG,KAAK,CAAC;oBACvB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;wBACxB,GAAG,EAAE,uBAAuB;qBAC5B,CAAC,CAAC,CAAC;gBACL,CAAC,CAAC,CAAC;gBAEH,UAAU,CAAC,EAAE,CAAC,aAAa,EAAE,GAAG,EAAE;oBACjC,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC;oBACtB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;wBACxB,GAAG,EAAE,sBAAsB;qBAC3B,CAAC,CAAC,CAAC;gBACL,CAAC,CAAC,CAAC;gBAEH,UAAU,CAAC,EAAE,CAAC,OAAO,EAAE,GAAG,EAAE;oBAC3B,IAAI,CAAC,SAAS,GAAG,KAAK,CAAC;oBACvB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;wBACxB,GAAG,EAAE,4BAA4B;qBACjC,CAAC,CAAC,CAAC;gBACL,CAAC,CAAC,CAAC;gBAEH,UAAU,CAAC,EAAE,CAAC,WAAW,EAAE,GAAG,EAAE;oBAC/B,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC;oBACtB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;wBACxB,GAAG,EAAE,oCAAoC;qBACzC,CAAC,CAAC,CAAC;gBACL,CAAC,CAAC,CAAC;YACJ,CAAC,CAAC,CAAC;YAEH,OAAO,IAAI,CAAC,UAAU,CAAC;QACxB,CAAC;QAAC,OAAO,CAAC,EAAE,CAAC;YACZ,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;gBACxB,GAAG,EAAE,CAAC;gBACN,GAAG,EAAE,2BAA2B;aAChC,CAAC,CAAC,CAAC;YACJ,MAAM,CAAC,CAAC;QACT,CAAC;IACF,CAAC;IAGD,KAAK,CAAC,KAAK;QACV,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,CAAC;YACxB,GAAG,EAAE,oBAAoB;SACzB,CAAC,CAAC,CAAC;QACJ,MAAM,IAAI,CAAC,UAAU,EAAE,KAAK,EAAE,CAAC;IAChC,CAAC;CACD"}
@@ -15,8 +15,10 @@ var DEFAULT_ENDPOINT = "mongodb://127.0.0.1:27017";
15
15
  * @return {MongoDatabase} Database layer
16
16
  */
17
17
  var MongoDatabase = class {
18
- constructor(url, dbname, authSource, logger) {
18
+ constructor(url, dbname, authSource, logger, timeouts) {
19
19
  this.connected = false;
20
+ this.connectTimeoutMS = timeouts?.connectTimeoutMS;
21
+ this.serverSelectionTimeoutMS = timeouts?.serverSelectionTimeoutMS;
20
22
  const parsedUrl = new URL(url || DEFAULT_ENDPOINT);
21
23
  if (dbname) parsedUrl.pathname = dbname;
22
24
  if (authSource) parsedUrl.searchParams.set("authSource", authSource);
@@ -56,9 +58,13 @@ var MongoDatabase = class {
56
58
  appName,
57
59
  dbName: this.dbname,
58
60
  maxPoolSize: 50,
59
- minPoolSize: 5
61
+ minPoolSize: 5,
62
+ connectTimeoutMS: this.connectTimeoutMS,
63
+ serverSelectionTimeoutMS: this.serverSelectionTimeoutMS
60
64
  }));
65
+ let opened = false;
61
66
  const onConnected = () => {
67
+ opened = true;
62
68
  this.logger.debug(() => ({ msg: "Database connection opened" }));
63
69
  this.connected = true;
64
70
  this.connection = connection;
@@ -72,6 +78,12 @@ var MongoDatabase = class {
72
78
  }));
73
79
  this.connected = false;
74
80
  this.connecting = void 0;
81
+ if (!opened) connection.destroy(true).catch((destroyErr) => {
82
+ this.logger.error(() => ({
83
+ err: destroyErr,
84
+ msg: "Failed to destroy unconnected database connection"
85
+ }));
86
+ });
75
87
  reject(err);
76
88
  };
77
89
  connection.once("open", onConnected);
@@ -29,8 +29,8 @@ var CAPTCHA_TABLES = [
29
29
  }
30
30
  ];
31
31
  var CaptchaDatabase = class CaptchaDatabase extends require_mongo.MongoDatabase {
32
- constructor(url, dbname, authSource, logger) {
33
- super(url, dbname, authSource, logger);
32
+ constructor(url, dbname, authSource, logger, timeouts) {
33
+ super(url, dbname, authSource, logger, timeouts);
34
34
  this.indexesEnsured = false;
35
35
  this.tables = {};
36
36
  }
@@ -17,10 +17,19 @@ var CentralDbStreamer = class CentralDbStreamer {
17
17
  static {
18
18
  this.RECONNECT_COOLDOWN_MS = 5e3;
19
19
  }
20
+ static {
21
+ this.CONNECT_TIMEOUT_MS = 45e3;
22
+ }
23
+ static {
24
+ this.SERVER_SELECTION_TIMEOUT_MS = 45e3;
25
+ }
20
26
  constructor(mongoCaptchaUri, logger) {
21
27
  this.lastFailureTime = 0;
22
28
  this.logger = logger || (0, _prosopo_logger.getLogger)("info", "CentralDbStreamer");
23
- this.db = new require_captcha.CaptchaDatabase(mongoCaptchaUri, void 0, void 0, this.logger);
29
+ this.db = new require_captcha.CaptchaDatabase(mongoCaptchaUri, void 0, void 0, this.logger, {
30
+ connectTimeoutMS: CentralDbStreamer.CONNECT_TIMEOUT_MS,
31
+ serverSelectionTimeoutMS: CentralDbStreamer.SERVER_SELECTION_TIMEOUT_MS
32
+ });
24
33
  }
25
34
  ensureConnected() {
26
35
  if (this.connectPromise && !this.db.connected) this.connectPromise = void 0;
@@ -63,11 +63,6 @@ var PROVIDER_TABLES = [
63
63
  modelName: "DecisionMachine",
64
64
  schema: _prosopo_types_database.DecisionMachineArtifactRecordSchema
65
65
  },
66
- {
67
- collectionName: "clientContextEntropy",
68
- modelName: "ClientContextEntropy",
69
- schema: _prosopo_types_database.ClientContextEntropyRecordSchema
70
- },
71
66
  {
72
67
  collectionName: "spamEmailDomain",
73
68
  modelName: "SpamEmailDomain",
@@ -406,7 +401,7 @@ var ProviderDatabase = class ProviderDatabase extends require_mongo.MongoDatabas
406
401
  });
407
402
  if (captchas.length) {
408
403
  const filter = { id: commit.id };
409
- await this.tables?.commitment.updateOne(filter, commitmentRecord, { upsert: true });
404
+ await this.tables?.commitment.updateOne(filter, { $set: { ...commitmentRecord } }, { upsert: true });
410
405
  const ops = captchas.map((captcha) => ({ updateOne: {
411
406
  filter: {
412
407
  commitmentId: commit.id,
@@ -588,7 +583,7 @@ var ProviderDatabase = class ProviderDatabase extends require_mongo.MongoDatabas
588
583
  if (userSubmitted) setStage.submittedAtTimestamp = { $ifNull: ["$submittedAtTimestamp", timestamp] };
589
584
  if (isDisapproved) setStage.failedAtTimestamp = { $ifNull: ["$failedAtTimestamp", timestamp] };
590
585
  try {
591
- if ((await tables.powcaptcha.updateOne({ challenge }, [{ $set: setStage }])).matchedCount === 0) {
586
+ if ((await tables.powcaptcha.updateOne({ challenge }, [{ $set: setStage }], { updatePipeline: true })).matchedCount === 0) {
592
587
  const err = new _prosopo_common.ProsopoDBError("DATABASE.CAPTCHA_GET_FAILED", {
593
588
  context: {
594
589
  challenge,
@@ -921,7 +916,7 @@ var ProviderDatabase = class ProviderDatabase extends require_mongo.MongoDatabas
921
916
  lastUpdatedTimestamp: timestamp,
922
917
  pendingStage: true,
923
918
  verifiedAtTimestamp: { $ifNull: ["$verifiedAtTimestamp", timestamp] }
924
- } }]);
919
+ } }], { updatePipeline: true });
925
920
  }
926
921
  /** @description Update an image captcha commitment
927
922
  */
@@ -944,7 +939,7 @@ var ProviderDatabase = class ProviderDatabase extends require_mongo.MongoDatabas
944
939
  await this.tables?.commitment.updateOne(filter, [{ $set: {
945
940
  ...baseSet,
946
941
  ...pipelineExprs
947
- } }]);
942
+ } }], { updatePipeline: true });
948
943
  }
949
944
  /**
950
945
  * Counts server-checked captcha records across image (`commitment`),
@@ -1005,7 +1000,10 @@ var ProviderDatabase = class ProviderDatabase extends require_mongo.MongoDatabas
1005
1000
  lastUpdatedTimestamp: timestamp,
1006
1001
  pendingStage: true,
1007
1002
  verifiedAtTimestamp: { $ifNull: ["$verifiedAtTimestamp", timestamp] }
1008
- } }], { upsert: false });
1003
+ } }], {
1004
+ upsert: false,
1005
+ updatePipeline: true
1006
+ });
1009
1007
  }
1010
1008
  /**
1011
1009
  * Store a new session record
@@ -1175,7 +1173,7 @@ var ProviderDatabase = class ProviderDatabase extends require_mongo.MongoDatabas
1175
1173
  simdReadingsStage: { $ifNull: ["$simdReadingsStage", stage] },
1176
1174
  lastUpdatedTimestamp: /* @__PURE__ */ new Date(),
1177
1175
  pendingStage: true
1178
- } }]);
1176
+ } }], { updatePipeline: true });
1179
1177
  } catch (err) {
1180
1178
  throw new _prosopo_common.ProsopoDBError("DATABASE.SESSION_GET_FAILED", {
1181
1179
  context: {
@@ -1208,7 +1206,7 @@ var ProviderDatabase = class ProviderDatabase extends require_mongo.MongoDatabas
1208
1206
  if (fields.peerIp !== void 0) setStage["dnsEvent.peerIp"] = fields.peerIp;
1209
1207
  if (fields.pathValid !== void 0) setStage["dnsEvent.pathValid"] = fields.pathValid;
1210
1208
  try {
1211
- return (await this.tables.session.updateOne({ sessionId }, [{ $set: setStage }])).matchedCount > 0;
1209
+ return (await this.tables.session.updateOne({ sessionId }, [{ $set: setStage }], { updatePipeline: true })).matchedCount > 0;
1212
1210
  } catch (err) {
1213
1211
  throw new _prosopo_common.ProsopoDBError("DATABASE.SESSION_GET_FAILED", {
1214
1212
  context: {
@@ -1731,24 +1729,6 @@ var ProviderDatabase = class ProviderDatabase extends require_mongo.MongoDatabas
1731
1729
  async removeAllDecisionMachineArtifacts() {
1732
1730
  return (await this.tables?.decisionMachine.deleteMany({}))?.deletedCount ?? 0;
1733
1731
  }
1734
- /**
1735
- * @description get client context-specific entropy
1736
- *
1737
- * Read-only. The `clientcontextentropies` collection is populated
1738
- * externally by the job-runner sweep — the provider used to compute
1739
- * entropy locally via `sampleContextEntropy` + `setClientContextEntropy`
1740
- * on a scheduled task, but that path was pulled 2026-08-21 (the sweep
1741
- * aggregation was ~36 minutes of DB time per 6h, and the same
1742
- * computation now runs off-provider across the full record set).
1743
- */
1744
- async getClientContextEntropy(account, contextType) {
1745
- const filter = {
1746
- account,
1747
- contextType
1748
- };
1749
- const doc = await this.tables?.clientContextEntropy.findOne(filter).lean();
1750
- return doc ? doc.entropy : void 0;
1751
- }
1752
1732
  async getSpamEmailDomain(domain) {
1753
1733
  if (!this.tables?.spamEmailDomain) throw new _prosopo_common.ProsopoDBError("DATABASE.DATABASE_IMPORT_ERROR", { context: { failedFuncName: this.getSpamEmailDomain.name } });
1754
1734
  const suffixCandidates = (0, _prosopo_util.buildDomainSuffixCandidates)(domain).slice(0, MAX_DOMAIN_SUFFIX_CANDIDATES);
@@ -1,5 +1,4 @@
1
1
  Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
2
- const require_runtime = require("./_virtual/_rolldown/runtime.cjs");
3
2
  const require_mongooseOptions = require("./mongooseOptions.cjs");
4
3
  const require_mongo = require("./base/mongo.cjs");
5
4
  const require_mongoMemory = require("./base/mongoMemory.cjs");
@@ -10,13 +9,14 @@ const require_centralDbStreamer = require("./databases/centralDbStreamer.cjs");
10
9
  const require_index = require("./databases/index.cjs");
11
10
  const require_redisCache = require("./redisCache.cjs");
12
11
  let make_dir = require("make-dir");
13
- make_dir = require_runtime.__toESM(make_dir, 1);
14
12
  //#region src/index.ts
15
- console.debug(make_dir.default);
13
+ console.debug(make_dir.makeDirectory);
16
14
  //#endregion
17
15
  exports.CaptchaDatabase = require_captcha.CaptchaDatabase;
18
16
  exports.CentralDbStreamer = require_centralDbStreamer.CentralDbStreamer;
19
17
  exports.ClientDatabase = require_client.ClientDatabase;
18
+ exports.DEFAULT_CONNECT_TIMEOUT_MS = require_mongooseOptions.DEFAULT_CONNECT_TIMEOUT_MS;
19
+ exports.DEFAULT_SERVER_SELECTION_TIMEOUT_MS = require_mongooseOptions.DEFAULT_SERVER_SELECTION_TIMEOUT_MS;
20
20
  exports.DETECTOR_BUNDLE_TTL_SECONDS = require_redisCache.DETECTOR_BUNDLE_TTL_SECONDS;
21
21
  exports.Databases = require_index.Databases;
22
22
  exports.MongoDatabase = require_mongo.MongoDatabase;
@@ -25,6 +25,19 @@ var getMongoCompressors = (url, compressors = DEFAULT_COMPRESSORS) => {
25
25
  }
26
26
  };
27
27
  /**
28
+ * Default connect / server-selection timeouts.
29
+ *
30
+ * These are sized for a database that is local to the process or at least on
31
+ * the same continent, where a connect that has not completed in 10s is a real
32
+ * fault worth failing fast on. They are *not* safe as a universal ceiling: a
33
+ * connection to a remote database can need far longer for the TLS handshake
34
+ * alone — pronode17 measures 2-30s to mongo1 — and every connect that trips
35
+ * the ceiling is a wasted attempt that will simply be retried. Callers that
36
+ * own a known long-haul connection pass their own values instead.
37
+ */
38
+ var DEFAULT_CONNECT_TIMEOUT_MS = 1e4;
39
+ var DEFAULT_SERVER_SELECTION_TIMEOUT_MS = 2e4;
40
+ /**
28
41
  * Returns default mongoose connection options with the ability to override specific values.
29
42
  *
30
43
  * @param options - Configuration options
@@ -33,10 +46,12 @@ var getMongoCompressors = (url, compressors = DEFAULT_COMPRESSORS) => {
33
46
  * @param options.maxPoolSize - Maximum pool size (default: 10)
34
47
  * @param options.minPoolSize - Minimum pool size (default: 0)
35
48
  * @param options.dbName - Optional database name
49
+ * @param options.connectTimeoutMS - Max time to establish a connection (default: 10000)
50
+ * @param options.serverSelectionTimeoutMS - Max time to select a server (default: 20000)
36
51
  * @returns Mongoose connection options object
37
52
  */
38
53
  var getMongoConnectionOptions = (options) => {
39
- const { url, appName, maxPoolSize = 10, minPoolSize = 0, dbName } = options;
54
+ const { url, appName, maxPoolSize = 10, minPoolSize = 0, dbName, connectTimeoutMS = DEFAULT_CONNECT_TIMEOUT_MS, serverSelectionTimeoutMS = DEFAULT_SERVER_SELECTION_TIMEOUT_MS } = options;
40
55
  if (!url || url.trim() === "") throw new Error("MongoDB connection URL is required and cannot be empty or whitespace-only");
41
56
  const compressors = getMongoCompressors(url);
42
57
  const connectionOptions = {
@@ -48,16 +63,18 @@ var getMongoConnectionOptions = (options) => {
48
63
  maxPoolSize,
49
64
  minPoolSize,
50
65
  maxConnecting: 2,
51
- connectTimeoutMS: 1e4,
66
+ connectTimeoutMS,
52
67
  socketTimeoutMS: 3e4,
53
68
  maxIdleTimeMS: 3e5,
54
69
  appName,
55
- serverSelectionTimeoutMS: 2e4,
70
+ serverSelectionTimeoutMS,
56
71
  compressors
57
72
  };
58
73
  if (dbName) connectionOptions.dbName = dbName;
59
74
  return connectionOptions;
60
75
  };
61
76
  //#endregion
77
+ exports.DEFAULT_CONNECT_TIMEOUT_MS = DEFAULT_CONNECT_TIMEOUT_MS;
78
+ exports.DEFAULT_SERVER_SELECTION_TIMEOUT_MS = DEFAULT_SERVER_SELECTION_TIMEOUT_MS;
62
79
  exports.getMongoCompressors = getMongoCompressors;
63
80
  exports.getMongoConnectionOptions = getMongoConnectionOptions;
@@ -1,7 +1,7 @@
1
1
  import { type Logger } from "@prosopo/logger";
2
2
  import { type CaptchaProperties, type ICaptchaDatabase, type PoWCaptchaRecord, type PuzzleCaptchaRecord, type StoredSession, type Tables, type UserCommitmentRecord } from "@prosopo/types-database";
3
- import type { RootFilterQuery } from "mongoose";
4
- import { MongoDatabase } from "../base/index.js";
3
+ import type { QueryFilter } from "mongoose";
4
+ import { type MongoConnectionTimeouts, MongoDatabase } from "../base/index.js";
5
5
  declare enum TableNames {
6
6
  frictionlessToken = "frictionlessToken",
7
7
  session = "session",
@@ -12,14 +12,14 @@ declare enum TableNames {
12
12
  export declare class CaptchaDatabase extends MongoDatabase implements ICaptchaDatabase {
13
13
  tables: Tables<TableNames>;
14
14
  private indexesEnsured;
15
- constructor(url: string, dbname?: string, authSource?: string, logger?: Logger);
15
+ constructor(url: string, dbname?: string, authSource?: string, logger?: Logger, timeouts?: MongoConnectionTimeouts);
16
16
  connect(): Promise<void>;
17
17
  getTables(): Tables<TableNames>;
18
18
  ensureIndexes(): Promise<void>;
19
19
  private static normaliseCompositeIp;
20
20
  private static normaliseDocCompositeIps;
21
21
  saveCaptchas(sessionEvents: StoredSession[], imageCaptchaEvents: UserCommitmentRecord[], powCaptchaEvents: PoWCaptchaRecord[], puzzleCaptchaEvents?: PuzzleCaptchaRecord[]): Promise<void>;
22
- getCaptchas(filter?: RootFilterQuery<CaptchaProperties>, limit?: number): Promise<{
22
+ getCaptchas(filter?: QueryFilter<CaptchaProperties>, limit?: number): Promise<{
23
23
  userCommitmentRecords: UserCommitmentRecord[];
24
24
  powCaptchaRecords: PoWCaptchaRecord[];
25
25
  puzzleCaptchaRecords: PuzzleCaptchaRecord[];
@@ -1 +1 @@
1
- {"version":3,"file":"captcha.d.ts","sourceRoot":"","sources":["../../src/databases/captcha.ts"],"names":[],"mappings":"AAeA,OAAO,EAAE,KAAK,MAAM,EAAa,MAAM,iBAAiB,CAAC;AACzD,OAAO,EACN,KAAK,iBAAiB,EACtB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,mBAAmB,EAGxB,KAAK,aAAa,EAGlB,KAAK,MAAM,EACX,KAAK,oBAAoB,EACzB,MAAM,yBAAyB,CAAC;AAajC,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,UAAU,CAAC;AAChD,OAAO,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AAIjD,aAAK,UAAU;IACd,iBAAiB,sBAAsB;IACvC,OAAO,YAAY;IACnB,UAAU,eAAe;IACzB,UAAU,eAAe;IACzB,aAAa,kBAAkB;CAC/B;AAyBD,qBAAa,eAAgB,SAAQ,aAAc,YAAW,gBAAgB;IAC7E,MAAM,EAAE,MAAM,CAAC,UAAU,CAAC,CAAC;IAC3B,OAAO,CAAC,cAAc,CAAS;gBAG9B,GAAG,EAAE,MAAM,EACX,MAAM,CAAC,EAAE,MAAM,EACf,UAAU,CAAC,EAAE,MAAM,EACnB,MAAM,CAAC,EAAE,MAAM;IAMD,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAUvC,SAAS,IAAI,MAAM,CAAC,UAAU,CAAC;IAUzB,aAAa,IAAI,OAAO,CAAC,IAAI,CAAC;IAqDpC,OAAO,CAAC,MAAM,CAAC,oBAAoB;IAoBnC,OAAO,CAAC,MAAM,CAAC,wBAAwB;IAajC,YAAY,CACjB,aAAa,EAAE,aAAa,EAAE,EAC9B,kBAAkB,EAAE,oBAAoB,EAAE,EAC1C,gBAAgB,EAAE,gBAAgB,EAAE,EACpC,mBAAmB,GAAE,mBAAmB,EAAO;IAmI1C,WAAW,CAChB,MAAM,GAAE,eAAe,CAAC,iBAAiB,CAAM,EAC/C,KAAK,SAAM,GACT,OAAO,CAAC;QACV,qBAAqB,EAAE,oBAAoB,EAAE,CAAC;QAC9C,iBAAiB,EAAE,gBAAgB,EAAE,CAAC;QACtC,oBAAoB,EAAE,mBAAmB,EAAE,CAAC;KAC5C,CAAC;CAsCF"}
1
+ {"version":3,"file":"captcha.d.ts","sourceRoot":"","sources":["../../src/databases/captcha.ts"],"names":[],"mappings":"AAeA,OAAO,EAAE,KAAK,MAAM,EAAa,MAAM,iBAAiB,CAAC;AACzD,OAAO,EACN,KAAK,iBAAiB,EACtB,KAAK,gBAAgB,EACrB,KAAK,gBAAgB,EACrB,KAAK,mBAAmB,EAGxB,KAAK,aAAa,EAGlB,KAAK,MAAM,EACX,KAAK,oBAAoB,EACzB,MAAM,yBAAyB,CAAC;AAajC,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AAC5C,OAAO,EAAE,KAAK,uBAAuB,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AAI/E,aAAK,UAAU;IACd,iBAAiB,sBAAsB;IACvC,OAAO,YAAY;IACnB,UAAU,eAAe;IACzB,UAAU,eAAe;IACzB,aAAa,kBAAkB;CAC/B;AAyBD,qBAAa,eAAgB,SAAQ,aAAc,YAAW,gBAAgB;IAC7E,MAAM,EAAE,MAAM,CAAC,UAAU,CAAC,CAAC;IAC3B,OAAO,CAAC,cAAc,CAAS;gBAG9B,GAAG,EAAE,MAAM,EACX,MAAM,CAAC,EAAE,MAAM,EACf,UAAU,CAAC,EAAE,MAAM,EACnB,MAAM,CAAC,EAAE,MAAM,EACf,QAAQ,CAAC,EAAE,uBAAuB;IAMpB,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC;IAUvC,SAAS,IAAI,MAAM,CAAC,UAAU,CAAC;IAUzB,aAAa,IAAI,OAAO,CAAC,IAAI,CAAC;IAqDpC,OAAO,CAAC,MAAM,CAAC,oBAAoB;IAoBnC,OAAO,CAAC,MAAM,CAAC,wBAAwB;IAajC,YAAY,CACjB,aAAa,EAAE,aAAa,EAAE,EAC9B,kBAAkB,EAAE,oBAAoB,EAAE,EAC1C,gBAAgB,EAAE,gBAAgB,EAAE,EACpC,mBAAmB,GAAE,mBAAmB,EAAO;IAmI1C,WAAW,CAChB,MAAM,GAAE,WAAW,CAAC,iBAAiB,CAAM,EAC3C,KAAK,SAAM,GACT,OAAO,CAAC;QACV,qBAAqB,EAAE,oBAAoB,EAAE,CAAC;QAC9C,iBAAiB,EAAE,gBAAgB,EAAE,CAAC;QACtC,oBAAoB,EAAE,mBAAmB,EAAE,CAAC;KAC5C,CAAC;CAsCF"}