feat: 670 per reviewer skip - #893
Conversation
* test(ncmec): add field coverage and submission tests Add XML field-coverage regression tests for NCMEC report builders, including XSD-order locks for the ipCaptureEvent ordering regression class. Add a submitReport integration test using a stubbed fetchHTTP seam against real Postgres, plus a fixture helper for NCMEC org settings. Canonicalise webhook-sourced ipCaptureEvent objects before XML rendering so webhook key order cannot produce out-of-order CyberTip XML. Co-Authored-By: pi * fix(ncmec): correct fileDetails ipCaptureEvent XSD ordering; harden tests buildFileDetailsObject emits <ipCaptureEvent> in the wrong position relative to <industryClassification>/<originalFileHash>. PR #869 moved it BEFORE industryClassification, claiming NCMEC's live validator required that — but a probe against exttest.cybertip.org proves the opposite: - Variant A (#869 order, ipCaptureEvent BEFORE industryClassification): REJECTED — cvc-complex-type.2.4.a: Invalid content was found starting with element 'industryClassification'. One of '{deviceId, details, additionalInfo}' is expected. - Variant B (canonical XSD order, ipCaptureEvent AFTER industryClassification/originalFileHash): ACCEPTED, responseCode=0. #869 misread the original #856 error (which fires when an element lands in the trailing deviceId/details/additionalInfo slot) and moved ipCaptureEvent backwards to a position NCMEC actually rejects. #869's own PR description admits the live re-test was never run before merge. This commit restores the canonical XSD order, which the live validator accepts. Reorders buildFileDetailsObject and the FileDetails type so ipCaptureEvent follows industryClassification and originalFileHash, and updates the ncmecReporting.builders.test.ts 'preserves XSD insertion order (Appendix C)' assertion to anchor the correct order (the test had been updated in #869 to anchor the wrong one). Also includes test-hygiene improvements to the NCMEC #843 test work: - fieldCoverage.test.ts: strengthen the renderXml assertion from a bare length>0 check to per-scenario structural XML markers (present/absent), so the js2xml serialization path is actually exercised. Remove the dead XSD.fileDetails array (buildSubmitReportObject's <report> envelope never contains <fileDetails>; its ordering is locked in ncmecReporting.builders.test.ts). - ncmec-submission.integ.test.ts: extract a shared RecordedCall type, replace submitCall! non-null assertions with an early-fail type guard, and type the stub generic against the real FetchHTTP/CoopRequestQuery contract (removing the as-never param, inline cast, and final broad as-unknown-as-FetchHTTP). Requires exporting HandleResponseBody from networkingService (additive type-only export). Co-Authored-By: pi
* fix: Support non-standard scylla ports in DB Migrator * better compat * whitespace
|
Important Review skippedAuto reviews are disabled on base/target branches other than the default branch. 🗂️ Base branches to auto review (1)
Please check the settings in the CodeRabbit UI or the ⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: CHILL Plan: Pro Plus Run ID: You can disable this status message by setting the Use the checkbox below for a quick retry:
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
Co-authored-by: Pi <pi@earendil.works>
* ci: stop logging every DB query in test runs Set DATABASE_PRINT_LOGS=false in .env.githubci (used by the docker-compose `test` service for unit/integration tests) and comment it out in server/.env.example (copied to server/.env by the e2e workflow) so the default is off. Kysely still logs query errors regardless, so failures remain visible; this only suppresses the per-query SQL/params/duration spam that made CI logs unreadable. Co-Authored-By: pi <pi@earendil-works> * ci: drop redundant comment in server/.env.example Co-Authored-By: pi <pi@earendil-works> --------- Co-authored-by: pi <pi@earendil-works> Co-authored-by: Cassidy James <cassidyjames@roost.tools>
* fix: close express-session store on api shutdown connect-pg-simple keeps a recurring pruneSessions timer that calls pool.query on its pool. makeApiServer created the store with the shared KyselyPgPool but never closed it, so the timer kept running after shutdown. In tests this leaked a setInterval per makeMockedServer() call that fired pool.query on the harness's already-closed pinned connection after each test, logging "Failed to prune sessions: Client was closed and is not queryable" indefinitely and hanging the test worker — the loop that forced the manual cancellation of CI run 27951870325. Hold a reference to the store instance and call its close() in the shutdown path. ownsPg is false (we pass in our own pool), so close() only stops the prune timer and won't end the shared pool. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> * test: migrate DB-backed tests to transactional harness Move the remaining DB-backed server tests onto the transaction-rollback harness from #732 so they get per-test isolation with no hand-written cleanup. - Convert the makeMockedServer/getBottle-based tests to makeTransactionalTestWithFixture, dropping manual org/user/queue/action deletes and KyselyPg.destroy() teardown: userKyselyPersistenceFindByEmailAndOrg, resolveSamlUser, and the MRT module tests (CommentOperations, JobRouting, QueueOperations, ReporterInvalidation). - Rewrite moderationConfigService and manualReviewToolService so every test is self-contained: each creates its own fresh org (rolled back automatically) rather than sharing a suite-scoped org. This removes the cross-test ordering/accumulator dependency in moderationConfigService and the hardcoded staging-seed-data dependency in manualReviewToolService. Scylla-touching tests (itemInvestigationService) keep uid-based isolation, since the Postgres-only harness can't roll those back. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * test: migrate UserReportSweep and userStrikeService to transactional harness Two DB-backed test suites were missed by the initial migration commit: - manualReviewToolService/modules/UserReportSweep.test.ts: a sibling of the four MRT module tests already migrated (CommentOperations, JobRouting, QueueOperations, ReporterInvalidation). It used makeTestWithFixture + getBottle with hand-written cleanup (createOrg/createUser/createMrtQueue teardown + KyselyPg/KyselyPgReadReplica.destroy()). Converted to makeTransactionalTestWithFixture; cleanup is now automatic rollback. - userStrikeService/userStrikeService.test.ts: used beforeAll/afterAll with a shared getBottle container and uid-based isolation. Converted to makeTransactionalTestWithFixture for true per-test rollback isolation. Also fixes a copy-paste describe block name ('Item Investigation Service' -> 'User Strike Service'). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix: resolve typecheck errors in migrated test files Two files migrated by the prior commit had TypeScript errors that broke `tsc` (and therefore `check_api_server` and the e2e server start): - manualReviewToolService.test.ts: the 'records an AUTOMATIC_CLOSE decision with no human reviewer' test was left as a bare `it(...)` referencing an out-of-scope `mrtService` and hardcoded staging `orgId`/'queueId' ('e7c89ce7729'/'1') — the very seed-data dependency the migration was meant to remove. Convert it to `testWithQueue()` like its siblings, using the fixture's `mrtService`/`org.id`/`queue.id`. - moderationConfigService.test.ts: the 'should return actions for a rule scoped to the caller org' snapshot read `it.id` from `getActionsForRuleId`, which returns `{ action, parameters }[]` — should be `it.action.id` (as on main). Also add the now-present `email` field role to the #createUserType inline snapshot. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix: create real user in migrated JobRouting fixture The transactional JobRouting fixture accidentally replaced the pre-migration createUser() call with a bare uid(). createManualReviewQueue validates queue users, so setup failed after creating org/item-type rows but before the fixture returned. Because makeTestWithFixture cannot run cleanup when setup throws, the outer transaction stayed idle-in-transaction and later tests blocked on the item_type_versions materialized-view refresh, timing out check_api_server. Keep the transactional harness, but create a real user and pass user.id to the queue setup. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * fix: restore QueueOperations org-scoping tests The rebase conflict resolution for QueueOperations.test.ts accidentally kept the pre-#872 branch side and dropped the two-org org-scoping regression tests that now exist on main. Restore testWithTwoOrgs and its cross-org access tests, using the transactional harness. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * test: configure decision-reason settings through service API Replace the decision-reason test helpers' direct writes to manual_review_tool_settings with a behavior-shaped helper that uses the ManualReviewToolService update API. The tests still exercise persisted org settings through submitDecision, but no longer couple setup to table and column names. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> * style: remove api shutdown explanatory comments Remove the comments added around the express-session store shutdown while keeping the shutdown behavior unchanged. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
* test: add MRT video playback e2e coverage Co-Authored-By: Pi <pi@users.noreply.github.com> * test: use Playwright base URL for media fixtures Co-Authored-By: Pi <pi@users.noreply.github.com> --------- Co-authored-by: Pi <pi@users.noreply.github.com>
| ); | ||
| selectedRelatedActionsSetter(actions); | ||
| }; | ||
| const setSelectedRelatedActions = useCallback( |
There was a problem hiding this comment.
are you adding useCallback in response to an observed performance issue, or is it hypothetical?
| ); | ||
| selectedRelatedActionsSetter(actions); | ||
| }, | ||
| [actionStore], |
There was a problem hiding this comment.
should we not have selectedRelatedActionsSetter in the dependency array, too?
| setSelectedRelatedActions([]); | ||
| setDecisionReason(undefined); | ||
| }; | ||
| }, [setSelectedRelatedActions]); |
There was a problem hiding this comment.
why does this dependency array only have one of the functions?
|
|
||
| **Full Changelog**: https://github.com/roostorg/coop/compare/1.0.2...main | ||
|
|
||
| ## Review Console |
There was a problem hiding this comment.
(as in another PR) we should probably decide how we want to handle the changelog, i.e. writing to it per-PR or manually writing it all once in a while
| return null; | ||
| } | ||
|
|
||
| static readonly REVIEWER_SKIP_TTL_MS = 30 * 60 * 1000; |
There was a problem hiding this comment.
hmm, how come we only skip for 30 minutes?
i guess in general -- what's the user story we imagine when someone skips a job? is it "i am not qualified to review this", "this is a hard job and i don't wanna deal with it / lower my average handling time by taking it", or something else? cc @julietshen
…tore it as null in decision log (#913) * fix(mrt): store null for unparseable item createdAt in decision log Submitting a decision failed with a 500 ("Job submission failed. Please try again.") for any job whose item carries a truthy but unparseable createdAt value. `#logDecision` passed `new Date(itemCreatedAtField)` straight into the `item_created_at` timestamptz column; an unparseable value yields an Invalid Date, which the pg driver serializes to a NaN string that Postgres rejects (22007), failing the whole decision insert. The decision is never recorded and the job is never removed, so the task is stuck in the queue. Normal item submissions can't reach this state because the DATETIME field handler validates dates at intake. A bad value only arrives via a path that skips that validation (e.g. system-generated reports, or a createdAt role mapped to a non-DATETIME field). Normalize at the write boundary: parse the value and store null when it is not a valid date. The column is already nullable, so the decision records and the task clears. Adds a unit regression test for the normalization helper. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CEU6YHFiBYfTqjgM5Vyt9n * docs(changelog): note the unparseable createdAt decision fix Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CEU6YHFiBYfTqjgM5Vyt9n * fix(mrt): preserve epoch 0 in parseItemCreatedAt Address review: `!value` treated a numeric 0 (a valid 1970-01-01 epoch) as empty. Guard only null/undefined/empty-string instead, and cover epoch 0 in the test. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CEU6YHFiBYfTqjgM5Vyt9n * fix(mrt): record unparseable item createdAt values Address review: surface invalid createdAt values instead of silently nulling them. When a present createdAt can't be parsed, emit a tracer span (job id, org id, the raw value) so the bad data is diagnosable and can be backfilled. The decision still saves with a null item_created_at. new Date() returns an Invalid Date rather than throwing, so this detects the invalid parse rather than wrapping in try/catch. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CEU6YHFiBYfTqjgM5Vyt9n --------- Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…nal (#918) * Make Scylla-backed features (item investigation, user strikes) optional * Address review: extract shared flag helper, use @ts-expect-error Resolve CodeRabbit nitpicks on PR #918: - Extract the ITEM_INVESTIGATION_AND_STRIKES_ENABLED parsing into a single exported helper (itemInvestigationAndStrikesEnabled) in noOpScylla.ts; the iocContainer factory and the unit test now share it instead of keeping two copies in sync (DRY). - Keep the helper a pure function of its argument (env is read at the call site) so the default-enabled test is independent of the ambient environment. - Replace the 'as unknown as' cast in NoOpScylla.insert() with a scoped @ts-expect-error and justifying comment, per repo guidelines. Co-Authored-By: Rovo Dev <rovodev@atlassian.com> * Fixed formatting * ci: re-trigger E2E (investigate investigation.spec flake vs regression) * Gate user strike logic behind ITEM_INVESTIGATION_AND_STRIKES_ENABLED flag When the flag is false, applyUserStrikeFromPublishedActions early-returns to avoid running strike threshold checks against always-zero counts from the NoOpScylla, which would cause escalation actions to fire unexpectedly. --------- Co-authored-by: Rovo Dev <rovodev@atlassian.com> Co-authored-by: Juan Mrad <juansmrad@gmail.com>
Add paths filter so the GitHub Actions security scan only triggers when .github/workflows/ files are modified, instead of on every PR.
#909) getOldestJobCreatedAtForExistingQueue fetched the first waiting/delayed job with queue.getJobs([state], 0, 0), but BullMQ's getJobs defaults to descending order, so index 0 is the most recently added job. The MRT queues dashboard's Oldest Task Age column therefore showed the newest task's age. Switch to BullMQ's getWaiting/getDelayed getters, which return jobs oldest-first. Adds a regression test that enqueues an older job then a newer one and asserts the older createdAt is returned; it fails against the previous implementation. The dummy-job payload builder it needs was previously copied per test file, so it is extracted into a shared test/fixtureHelpers/makeDummyMrtJobPayload.ts fixture (using instantiateOpaqueType instead of eslint-disabled type assertions). Co-authored-by: Claude Fable 5 <noreply@anthropic.com> Co-authored-by: Juan Mrad <juansmrad@gmail.com>
…Created At (#916) * fix(mrt): guard client date rendering against unparseable createdAt Unguarded date-fns format/formatDistanceToNow calls threw RangeError: Invalid time value on an unparseable createdAt, unmounting the task detail and queue preview into the "Something Went Wrong" error boundary. Add safeFormat/safeFormatDistanceToNow helpers that fall back to "Unknown" for invalid dates, and use them on the MRT render path. Client-side counterpart to the server-side decision-log fix in #913. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01AKvvCLkcC7LM1znjzvDjDA * add guard on more functions to prevent errors on invalid timezone formats. --------- Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com> Co-authored-by: Juan Mrad <juansmrad@gmail.com>
The testOrgs allowlist (['4def6a77d6a','acc701627cb']) hard-coded two org IDs that were silently suppressed with PERMANENT_ERROR before any network call. Hard-coded org IDs in source don't belong here; the NCMEC_ENV-based sandbox/production routing already handles test vs. prod submissions. Co-Authored-By: pi
Bumps the db-prod-security group with 1 update in the /db directory: [fast-uri](https://github.com/fastify/fast-uri). Updates `fast-uri` from 3.1.2 to 3.1.4 - [Release notes](https://github.com/fastify/fast-uri/releases) - [Commits](fastify/fast-uri@v3.1.2...v3.1.4) --- updated-dependencies: - dependency-name: fast-uri dependency-version: 3.1.4 dependency-type: indirect dependency-group: db-prod-security ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Bumps the migrator-prod-security group with 1 update in the /migrator directory: [fast-uri](https://github.com/fastify/fast-uri). Updates `fast-uri` from 3.1.2 to 3.1.4 - [Release notes](https://github.com/fastify/fast-uri/releases) - [Commits](fastify/fast-uri@v3.1.2...v3.1.4) --- updated-dependencies: - dependency-name: fast-uri dependency-version: 3.1.4 dependency-type: indirect dependency-group: migrator-prod-security ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Bumps [undici](https://github.com/nodejs/undici) from 7.27.1 to 7.29.0. - [Release notes](https://github.com/nodejs/undici/releases) - [Commits](nodejs/undici@v7.27.1...v7.29.0) --- updated-dependencies: - dependency-name: undici dependency-version: 7.29.0 dependency-type: indirect ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Bumps [immutable](https://github.com/immutable-js/immutable-js) from 5.1.5 to 5.1.9. - [Release notes](https://github.com/immutable-js/immutable-js/releases) - [Changelog](https://github.com/immutable-js/immutable-js/blob/main/CHANGELOG.md) - [Commits](immutable-js/immutable-js@v5.1.5...v5.1.9) --- updated-dependencies: - dependency-name: immutable dependency-version: 5.1.9 dependency-type: indirect ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
* build(deps-dev): bump js-yaml from 4.3.0 to 5.2.2 in /server Bumps [js-yaml](https://github.com/nodeca/js-yaml) from 4.3.0 to 5.2.2. - [Changelog](https://github.com/nodeca/js-yaml/blob/master/CHANGELOG.md) - [Commits](nodeca/js-yaml@4.3.0...5.2.2) --- updated-dependencies: - dependency-name: js-yaml dependency-version: 5.2.2 dependency-type: direct:development ... Signed-off-by: dependabot[bot] <support@github.com> * fix: use js-yaml named export Co-Authored-By: Codex <noreply@openai.com> --------- Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Tao Bojlén <git@btao.org> Co-authored-by: Codex <noreply@openai.com>
…ith 2 updates (#943) Bumps the server-prod-security group with 2 updates in the /server directory: [body-parser](https://github.com/expressjs/body-parser) and [fast-uri](https://github.com/fastify/fast-uri). Updates `body-parser` from 2.2.2 to 2.3.0 - [Release notes](https://github.com/expressjs/body-parser/releases) - [Changelog](https://github.com/expressjs/body-parser/blob/master/HISTORY.md) - [Commits](expressjs/body-parser@v2.2.2...v2.3.0) Updates `fast-uri` from 3.1.2 to 3.1.4 - [Release notes](https://github.com/fastify/fast-uri/releases) - [Commits](fastify/fast-uri@v3.1.2...v3.1.4) --- updated-dependencies: - dependency-name: body-parser dependency-version: 2.3.0 dependency-type: indirect dependency-group: server-prod-security - dependency-name: fast-uri dependency-version: 3.1.4 dependency-type: indirect dependency-group: server-prod-security ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
…ctory with 2 updates (#941) Bumps the nodejs-instrumentation-prod group with 2 updates in the /nodejs-instrumentation directory: [@opentelemetry/semantic-conventions](https://github.com/open-telemetry/opentelemetry-js) and [@opentelemetry/winston-transport](https://github.com/open-telemetry/opentelemetry-js-contrib/tree/HEAD/packages/winston-transport). Updates `@opentelemetry/semantic-conventions` from 1.41.1 to 1.43.0 - [Release notes](https://github.com/open-telemetry/opentelemetry-js/releases) - [Changelog](https://github.com/open-telemetry/opentelemetry-js/blob/main/CHANGELOG.md) - [Commits](open-telemetry/opentelemetry-js@semconv/v1.41.1...semconv/v1.43.0) Updates `@opentelemetry/winston-transport` from 0.29.0 to 0.30.0 - [Release notes](https://github.com/open-telemetry/opentelemetry-js-contrib/releases) - [Changelog](https://github.com/open-telemetry/opentelemetry-js-contrib/blob/main/packages/winston-transport/CHANGELOG.md) - [Commits](https://github.com/open-telemetry/opentelemetry-js-contrib/commits/host-metrics-v0.30.0/packages/winston-transport) --- updated-dependencies: - dependency-name: "@opentelemetry/semantic-conventions" dependency-version: 1.43.0 dependency-type: direct:production update-type: version-update:semver-minor dependency-group: nodejs-instrumentation-prod - dependency-name: "@opentelemetry/winston-transport" dependency-version: 0.30.0 dependency-type: direct:production update-type: version-update:semver-minor dependency-group: nodejs-instrumentation-prod ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Bumps [postcss](https://github.com/postcss/postcss) from 8.5.12 to 8.5.23. - [Release notes](https://github.com/postcss/postcss/releases) - [Changelog](https://github.com/postcss/postcss/blob/main/CHANGELOG.md) - [Commits](postcss/postcss@8.5.12...8.5.23) --- updated-dependencies: - dependency-name: postcss dependency-version: 8.5.23 dependency-type: direct:development ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
* Replace dotenv with Node's built-in --env-file-if-exists Node 24 (this repo's runtime) has a built-in flag that loads a .env file when present and silently no-ops when absent - exactly the behavior dotenv/config provided. Remove the dotenv package from server and db, and switch all invocations to . Key details: - (not ) preserves the silent no-op when .env is absent, matching dotenv/config. CI/prod get env from the docker-compose directive, so .env is not present there. - is NOT allowed in NODE_OPTIONS, so the test scripts were restructured to invoke directly while keeping the ts-node loader in NODE_OPTIONS. - Removed from 4 test/e2e fixture files; env is now loaded by the node flag before any module reads process.env. - Removed dotenv from db/knip.json ignoreDependencies (no longer needed). - Updated db/src/index.ts shebang and db/README.md. uuid was NOT removed: the server uses v1 (timestamp) UUIDs in 23 files, and crypto.randomUUID() only generates v4 - there is no Node built-in replacement for v1. Co-Authored-By: pi * Remove redundant env-loading comments The comments restated the env-loading mechanism; removing them keeps the files clean. Behavior unchanged. Co-Authored-By: pi * Load env in test:e2e via --env-file-if-exists The e2e suite boots the IoC container (via the coop.ts fixture), which reads env vars like UI_URL at module load. Removing the `import 'dotenv/config'` from the fixture left nothing to load server/.env when playwright runs, so CI failed with "Missing env var UI_URL". Invoke playwright through `node --env-file-if-exists=.env` (the same pattern used for jest) so env loads before any test module imports the container. CI gets server/.env from the workflow's `cp server/.env.example server/.env` step; the -if-exists variant no-ops if it's absent. Co-Authored-By: pi
… updates (#949) * build(deps-dev): bump the client-dev group across 1 directory with 19 updates Bumps the client-dev group with 18 updates in the /client directory: | Package | From | To | | --- | --- | --- | | [@eslint/compat](https://github.com/eslint/rewrite/tree/HEAD/packages/compat) | `2.0.3` | `2.1.0` | | [@eslint/eslintrc](https://github.com/eslint/eslintrc) | `3.3.5` | `3.3.6` | | [@testing-library/jest-dom](https://github.com/testing-library/jest-dom) | `5.16.5` | `5.17.0` | | [@types/google.maps](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/google.maps) | `3.51.0` | `3.65.2` | | [@types/latlon-geohash](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/latlon-geohash) | `2.0.0` | `2.0.4` | | [@types/lodash](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/lodash) | `4.14.191` | `4.17.24` | | [@types/react-beautiful-dnd](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/react-beautiful-dnd) | `13.1.4` | `13.1.8` | | [@types/react-csv](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/react-csv) | `1.1.3` | `1.1.10` | | [@types/react-table](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/react-table) | `7.7.14` | `7.7.20` | | [@typescript-eslint/eslint-plugin](https://github.com/typescript-eslint/typescript-eslint/tree/HEAD/packages/eslint-plugin) | `8.57.2` | `8.64.0` | | [@vitejs/plugin-react](https://github.com/vitejs/vite-plugin-react/tree/HEAD/packages/plugin-react) | `5.1.4` | `5.2.0` | | [autoprefixer](https://github.com/postcss/autoprefixer) | `10.4.13` | `10.5.4` | | [eslint](https://github.com/eslint/eslint) | `9.39.4` | `9.39.5` | | [eslint-plugin-react-hooks](https://github.com/facebook/react/tree/HEAD/packages/eslint-plugin-react-hooks) | `7.0.1` | `7.1.1` | | [knip](https://github.com/webpro-nl/knip/tree/HEAD/packages/knip) | `6.16.1` | `6.27.0` | | [typescript](https://github.com/microsoft/TypeScript) | `5.3.2` | `5.9.3` | | [vite](https://github.com/vitejs/vite/tree/HEAD/packages/vite) | `7.3.5` | `7.3.6` | | [vitest](https://github.com/vitest-dev/vitest/tree/HEAD/packages/vitest) | `4.1.0` | `4.1.10` | Updates `@eslint/compat` from 2.0.3 to 2.1.0 - [Release notes](https://github.com/eslint/rewrite/releases) - [Changelog](https://github.com/eslint/rewrite/blob/main/packages/compat/CHANGELOG.md) - [Commits](https://github.com/eslint/rewrite/commits/compat-v2.1.0/packages/compat) Updates `@eslint/eslintrc` from 3.3.5 to 3.3.6 - [Release notes](https://github.com/eslint/eslintrc/releases) - [Changelog](https://github.com/eslint/eslintrc/blob/main/CHANGELOG.md) - [Commits](eslint/eslintrc@eslintrc-v3.3.5...eslintrc-v3.3.6) Updates `@testing-library/jest-dom` from 5.16.5 to 5.17.0 - [Release notes](https://github.com/testing-library/jest-dom/releases) - [Changelog](https://github.com/testing-library/jest-dom/blob/main/CHANGELOG.md) - [Commits](testing-library/jest-dom@v5.16.5...v5.17.0) Updates `@types/google.maps` from 3.51.0 to 3.65.2 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/google.maps) Updates `@types/latlon-geohash` from 2.0.0 to 2.0.4 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/latlon-geohash) Updates `@types/lodash` from 4.14.191 to 4.17.24 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/lodash) Updates `@types/react-beautiful-dnd` from 13.1.4 to 13.1.8 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/react-beautiful-dnd) Updates `@types/react-csv` from 1.1.3 to 1.1.10 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/react-csv) Updates `@types/react-table` from 7.7.14 to 7.7.20 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/react-table) Updates `@typescript-eslint/eslint-plugin` from 8.57.2 to 8.64.0 - [Release notes](https://github.com/typescript-eslint/typescript-eslint/releases) - [Changelog](https://github.com/typescript-eslint/typescript-eslint/blob/main/packages/eslint-plugin/CHANGELOG.md) - [Commits](https://github.com/typescript-eslint/typescript-eslint/commits/v8.64.0/packages/eslint-plugin) Updates `@typescript-eslint/parser` from 8.57.2 to 8.65.0 - [Release notes](https://github.com/typescript-eslint/typescript-eslint/releases) - [Changelog](https://github.com/typescript-eslint/typescript-eslint/blob/main/packages/parser/CHANGELOG.md) - [Commits](https://github.com/typescript-eslint/typescript-eslint/commits/v8.65.0/packages/parser) Updates `@vitejs/plugin-react` from 5.1.4 to 5.2.0 - [Release notes](https://github.com/vitejs/vite-plugin-react/releases) - [Changelog](https://github.com/vitejs/vite-plugin-react/blob/plugin-react@5.2.0/packages/plugin-react/CHANGELOG.md) - [Commits](https://github.com/vitejs/vite-plugin-react/commits/plugin-react@5.2.0/packages/plugin-react) Updates `autoprefixer` from 10.4.13 to 10.5.4 - [Release notes](https://github.com/postcss/autoprefixer/releases) - [Changelog](https://github.com/postcss/autoprefixer/blob/main/CHANGELOG.md) - [Commits](postcss/autoprefixer@10.4.13...10.5.4) Updates `eslint` from 9.39.4 to 9.39.5 - [Release notes](https://github.com/eslint/eslint/releases) - [Commits](eslint/eslint@v9.39.4...v9.39.5) Updates `eslint-plugin-react-hooks` from 7.0.1 to 7.1.1 - [Release notes](https://github.com/facebook/react/releases) - [Changelog](https://github.com/react/react/blob/main/packages/eslint-plugin-react-hooks/CHANGELOG.md) - [Commits](https://github.com/facebook/react/commits/eslint-plugin-react-hooks@7.1.1/packages/eslint-plugin-react-hooks) Updates `knip` from 6.16.1 to 6.27.0 - [Release notes](https://github.com/webpro-nl/knip/releases) - [Commits](https://github.com/webpro-nl/knip/commits/knip@6.27.0/packages/knip) Updates `typescript` from 5.3.2 to 5.9.3 - [Release notes](https://github.com/microsoft/TypeScript/releases) - [Commits](microsoft/TypeScript@v5.3.2...v5.9.3) Updates `vite` from 7.3.5 to 7.3.6 - [Release notes](https://github.com/vitejs/vite/releases) - [Changelog](https://github.com/vitejs/vite/blob/v7.3.6/packages/vite/CHANGELOG.md) - [Commits](https://github.com/vitejs/vite/commits/v7.3.6/packages/vite) Updates `vitest` from 4.1.0 to 4.1.10 - [Release notes](https://github.com/vitest-dev/vitest/releases) - [Changelog](https://github.com/vitest-dev/vitest/blob/main/docs/releases.md) - [Commits](https://github.com/vitest-dev/vitest/commits/v4.1.10/packages/vitest) --- updated-dependencies: - dependency-name: "@eslint/compat" dependency-version: 2.1.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: "@eslint/eslintrc" dependency-version: 3.3.6 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: client-dev - dependency-name: "@testing-library/jest-dom" dependency-version: 5.17.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: "@types/google.maps" dependency-version: 3.65.2 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: "@types/latlon-geohash" dependency-version: 2.0.4 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: client-dev - dependency-name: "@types/lodash" dependency-version: 4.17.24 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: "@types/react-beautiful-dnd" dependency-version: 13.1.8 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: client-dev - dependency-name: "@types/react-csv" dependency-version: 1.1.10 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: client-dev - dependency-name: "@types/react-table" dependency-version: 7.7.20 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: client-dev - dependency-name: "@typescript-eslint/eslint-plugin" dependency-version: 8.64.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: "@typescript-eslint/parser" dependency-version: 8.65.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: "@vitejs/plugin-react" dependency-version: 5.2.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: autoprefixer dependency-version: 10.5.4 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: eslint dependency-version: 9.39.5 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: client-dev - dependency-name: eslint-plugin-react-hooks dependency-version: 7.1.1 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: knip dependency-version: 6.27.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: typescript dependency-version: 5.9.3 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: client-dev - dependency-name: vite dependency-version: 7.3.6 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: client-dev - dependency-name: vitest dependency-version: 4.1.10 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: client-dev ... Signed-off-by: dependabot[bot] <support@github.com> * Fix client checks after dependency updates Co-Authored-By: Codex <noreply@openai.com> --------- Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Tao Bojlén <git@btao.org> Co-authored-by: Codex <noreply@openai.com>
… updates (#948) * build(deps-dev): bump the server-dev group across 1 directory with 25 updates Bumps the server-dev group with 24 updates in the /server directory: | Package | From | To | | --- | --- | --- | | [@eslint/compat](https://github.com/eslint/rewrite/tree/HEAD/packages/compat) | `2.0.3` | `2.1.0` | | [@eslint/eslintrc](https://github.com/eslint/eslintrc) | `3.3.5` | `3.3.6` | | [@eslint/js](https://github.com/eslint/eslint/tree/HEAD/packages/js) | `9.39.4` | `9.39.5` | | [@playwright/test](https://github.com/microsoft/playwright) | `1.61.0` | `1.61.1` | | [@types/cookie-parser](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/cookie-parser) | `1.4.3` | `1.4.10` | | [@types/debug](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/debug) | `4.1.12` | `4.1.13` | | [@types/express-serve-static-core](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/express-serve-static-core) | `5.1.1` | `5.1.2` | | [@types/js-yaml](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/js-yaml) | `4.0.5` | `4.0.9` | | [@types/lodash](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/lodash) | `4.14.198` | `4.17.24` | | [@types/morgan](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/morgan) | `1.9.4` | `1.9.10` | | [@types/node](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/node) | `18.17.3` | `18.19.130` | | [@types/validator](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/validator) | `13.9.0` | `13.15.10` | | [@typescript-eslint/eslint-plugin](https://github.com/typescript-eslint/typescript-eslint/tree/HEAD/packages/eslint-plugin) | `8.59.0` | `8.65.0` | | [eslint](https://github.com/eslint/eslint) | `9.39.4` | `9.39.5` | | [eslint-import-resolver-typescript](https://github.com/import-js/eslint-import-resolver-typescript) | `3.6.0` | `3.10.1` | | [eslint-plugin-functional](https://github.com/eslint-functional/eslint-plugin-functional) | `9.0.4` | `9.0.5` | | [eslint-plugin-jsdoc](https://github.com/gajus/eslint-plugin-jsdoc) | `62.5.4` | `62.9.0` | | [eslint-plugin-promise](https://github.com/eslint-community/eslint-plugin-promise) | `7.2.1` | `7.3.0` | | [eslint-plugin-switch-statement](https://github.com/ethanresnick/eslint-plugin-exhaustive-switch) | `0.0.11` | `0.0.12` | | [jest-light-runner](https://github.com/nicolo-ribaudo/jest-light-runner) | `0.4.1` | `0.8.1` | | [knip](https://github.com/webpro-nl/knip/tree/HEAD/packages/knip) | `6.16.1` | `6.27.0` | | [ts-node](https://github.com/TypeStrong/ts-node) | `10.9.1` | `10.9.2` | | [typescript](https://github.com/microsoft/TypeScript) | `5.5.2` | `5.9.3` | | [typescript-eslint](https://github.com/typescript-eslint/typescript-eslint/tree/HEAD/packages/typescript-eslint) | `8.57.2` | `8.65.0` | Updates `@eslint/compat` from 2.0.3 to 2.1.0 - [Release notes](https://github.com/eslint/rewrite/releases) - [Changelog](https://github.com/eslint/rewrite/blob/main/packages/compat/CHANGELOG.md) - [Commits](https://github.com/eslint/rewrite/commits/compat-v2.1.0/packages/compat) Updates `@eslint/eslintrc` from 3.3.5 to 3.3.6 - [Release notes](https://github.com/eslint/eslintrc/releases) - [Changelog](https://github.com/eslint/eslintrc/blob/main/CHANGELOG.md) - [Commits](eslint/eslintrc@eslintrc-v3.3.5...eslintrc-v3.3.6) Updates `@eslint/js` from 9.39.4 to 9.39.5 - [Release notes](https://github.com/eslint/eslint/releases) - [Commits](https://github.com/eslint/eslint/commits/v9.39.5/packages/js) Updates `@playwright/test` from 1.61.0 to 1.61.1 - [Release notes](https://github.com/microsoft/playwright/releases) - [Commits](microsoft/playwright@v1.61.0...v1.61.1) Updates `@types/cookie-parser` from 1.4.3 to 1.4.10 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/cookie-parser) Updates `@types/debug` from 4.1.12 to 4.1.13 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/debug) Updates `@types/express-serve-static-core` from 5.1.1 to 5.1.2 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/express-serve-static-core) Updates `@types/js-yaml` from 4.0.5 to 4.0.9 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/js-yaml) Updates `@types/lodash` from 4.14.198 to 4.17.24 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/lodash) Updates `@types/morgan` from 1.9.4 to 1.9.10 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/morgan) Updates `@types/node` from 18.17.3 to 18.19.130 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/node) Updates `@types/validator` from 13.9.0 to 13.15.10 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/validator) Updates `@typescript-eslint/eslint-plugin` from 8.59.0 to 8.65.0 - [Release notes](https://github.com/typescript-eslint/typescript-eslint/releases) - [Changelog](https://github.com/typescript-eslint/typescript-eslint/blob/main/packages/eslint-plugin/CHANGELOG.md) - [Commits](https://github.com/typescript-eslint/typescript-eslint/commits/v8.65.0/packages/eslint-plugin) Updates `@typescript-eslint/parser` from 8.59.0 to 8.65.0 - [Release notes](https://github.com/typescript-eslint/typescript-eslint/releases) - [Changelog](https://github.com/typescript-eslint/typescript-eslint/blob/main/packages/parser/CHANGELOG.md) - [Commits](https://github.com/typescript-eslint/typescript-eslint/commits/v8.65.0/packages/parser) Updates `eslint` from 9.39.4 to 9.39.5 - [Release notes](https://github.com/eslint/eslint/releases) - [Commits](eslint/eslint@v9.39.4...v9.39.5) Updates `eslint-import-resolver-typescript` from 3.6.0 to 3.10.1 - [Release notes](https://github.com/import-js/eslint-import-resolver-typescript/releases) - [Changelog](https://github.com/import-js/eslint-import-resolver-typescript/blob/v3.10.1/CHANGELOG.md) - [Commits](import-js/eslint-import-resolver-typescript@v3.6.0...v3.10.1) Updates `eslint-plugin-functional` from 9.0.4 to 9.0.5 - [Release notes](https://github.com/eslint-functional/eslint-plugin-functional/releases) - [Changelog](https://github.com/eslint-functional/eslint-plugin-functional/blob/main/CHANGELOG.md) - [Commits](eslint-functional/eslint-plugin-functional@v9.0.4...v9.0.5) Updates `eslint-plugin-jsdoc` from 62.5.4 to 62.9.0 - [Release notes](https://github.com/gajus/eslint-plugin-jsdoc/releases) - [Commits](gajus/eslint-plugin-jsdoc@v62.5.4...v62.9.0) Updates `eslint-plugin-promise` from 7.2.1 to 7.3.0 - [Release notes](https://github.com/eslint-community/eslint-plugin-promise/releases) - [Changelog](https://github.com/eslint-community/eslint-plugin-promise/blob/main/CHANGELOG.md) - [Commits](eslint-community/eslint-plugin-promise@v7.2.1...v7.3.0) Updates `eslint-plugin-switch-statement` from 0.0.11 to 0.0.12 - [Commits](https://github.com/ethanresnick/eslint-plugin-exhaustive-switch/commits) Updates `jest-light-runner` from 0.4.1 to 0.8.1 - [Release notes](https://github.com/nicolo-ribaudo/jest-light-runner/releases) - [Commits](nicolo-ribaudo/jest-light-runner@v0.4.1...v0.8.1) Updates `knip` from 6.16.1 to 6.27.0 - [Release notes](https://github.com/webpro-nl/knip/releases) - [Commits](https://github.com/webpro-nl/knip/commits/knip@6.27.0/packages/knip) Updates `ts-node` from 10.9.1 to 10.9.2 - [Release notes](https://github.com/TypeStrong/ts-node/releases) - [Changelog](https://github.com/TypeStrong/ts-node/blob/main/development-docs/release-template.md) - [Commits](TypeStrong/ts-node@v10.9.1...v10.9.2) Updates `typescript` from 5.5.2 to 5.9.3 - [Release notes](https://github.com/microsoft/TypeScript/releases) - [Commits](microsoft/TypeScript@v5.5.2...v5.9.3) Updates `typescript-eslint` from 8.57.2 to 8.65.0 - [Release notes](https://github.com/typescript-eslint/typescript-eslint/releases) - [Changelog](https://github.com/typescript-eslint/typescript-eslint/blob/main/packages/typescript-eslint/CHANGELOG.md) - [Commits](https://github.com/typescript-eslint/typescript-eslint/commits/v8.65.0/packages/typescript-eslint) --- updated-dependencies: - dependency-name: "@eslint/compat" dependency-version: 2.1.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: "@eslint/eslintrc" dependency-version: 3.3.6 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: "@eslint/js" dependency-version: 9.39.5 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: "@playwright/test" dependency-version: 1.61.1 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: "@types/cookie-parser" dependency-version: 1.4.10 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: "@types/debug" dependency-version: 4.1.13 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: "@types/express-serve-static-core" dependency-version: 5.1.2 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: "@types/js-yaml" dependency-version: 4.0.9 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: "@types/lodash" dependency-version: 4.17.24 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: "@types/morgan" dependency-version: 1.9.10 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: "@types/node" dependency-version: 18.19.130 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: "@types/validator" dependency-version: 13.15.10 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: "@typescript-eslint/eslint-plugin" dependency-version: 8.64.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: "@typescript-eslint/parser" dependency-version: 8.65.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: eslint dependency-version: 9.39.5 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: eslint-import-resolver-typescript dependency-version: 3.10.1 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: eslint-plugin-functional dependency-version: 9.0.5 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: eslint-plugin-jsdoc dependency-version: 62.9.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: eslint-plugin-promise dependency-version: 7.3.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: eslint-plugin-switch-statement dependency-version: 0.0.12 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: jest-light-runner dependency-version: 0.8.1 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: knip dependency-version: 6.27.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: ts-node dependency-version: 10.9.2 dependency-type: direct:development update-type: version-update:semver-patch dependency-group: server-dev - dependency-name: typescript dependency-version: 5.9.3 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev - dependency-name: typescript-eslint dependency-version: 8.64.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: server-dev ... Signed-off-by: dependabot[bot] <support@github.com> * Fix server checks after dependency updates Co-Authored-By: Codex <noreply@openai.com> --------- Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Tao Bojlén <git@btao.org> Co-authored-by: Codex <noreply@openai.com>
…dates (#942) * build(deps-dev): bump the root-dev group across 1 directory with 3 updates Bumps the root-dev group with 3 updates in the / directory: [@types/node](https://github.com/DefinitelyTyped/DefinitelyTyped/tree/HEAD/types/node), [prettier](https://github.com/prettier/prettier) and [@parcel/watcher](https://github.com/parcel-bundler/watcher). Updates `@types/node` from 24.12.2 to 24.13.3 - [Release notes](https://github.com/DefinitelyTyped/DefinitelyTyped/releases) - [Commits](https://github.com/DefinitelyTyped/DefinitelyTyped/commits/HEAD/types/node) Updates `prettier` from 3.8.3 to 3.9.6 - [Release notes](https://github.com/prettier/prettier/releases) - [Changelog](https://github.com/prettier/prettier/blob/main/CHANGELOG.md) - [Commits](prettier/prettier@3.8.3...3.9.6) Updates `@parcel/watcher` from 2.5.6 to 2.6.0 - [Release notes](https://github.com/parcel-bundler/watcher/releases) - [Commits](parcel-bundler/watcher@v2.5.6...v2.6.0) --- updated-dependencies: - dependency-name: "@parcel/watcher" dependency-version: 2.6.0 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: root-dev - dependency-name: "@types/node" dependency-version: 24.13.3 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: root-dev - dependency-name: prettier dependency-version: 3.9.5 dependency-type: direct:development update-type: version-update:semver-minor dependency-group: root-dev ... Signed-off-by: dependabot[bot] <support@github.com> * Format code with Prettier 3.9 Co-Authored-By: Codex <noreply@openai.com> --------- Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Tao Bojlén <git@btao.org> Co-authored-by: Codex <noreply@openai.com>
* feat(mrt): add memoized CollapsibleText component (#870) Co-Authored-By: pi * feat(mrt): collapse long STRING fields with Read more (#870) Co-Authored-By: pi * fix(mrt): drop horizontal scroll for text containers (#870) Co-Authored-By: pi * fix(mrt): remove page-wide horizontal scroll from review view (#870) Co-Authored-By: pi * test(mrt): strengthen CollapsibleText grapheme test, fix stale comment (#870) Co-Authored-By: pi * fix(mrt): allow string field flex item to shrink for text wrapping (#870) The FieldComponent wrapper sat inside FieldsComponent's flex flex-wrap container with the default min-width: auto, so a flex item containing a long unbroken string expanded to the string's intrinsic width instead of wrapping. break-words and WebkitLineClamp only take effect when the element has a bounded content width, so the CollapsibleText Read more toggle appeared but did nothing on huge unbroken tokens. Adding min-w-0 lets the flex item shrink below its content width so wrapping and the line clamp take effect. Co-Authored-By: pi * fix(mrt): short-circuit grapheme count, reset expanded on text change (#870) Address review feedback on CollapsibleText: - countGraphemes → exceedsGraphemeThreshold: stop iterating once the count is known to exceed maxGraphemes, so a 1MB string segments at most maxGraphemes+1 graphemes instead of all of them. - Reset the expanded state when the text prop changes. When navigating between review jobs that reuse the same field name, React reuses the CollapsibleText instance; without the reset, a newly loaded long value inherited the previous job's expanded state. - The custom-thresholds test now asserts the maxLines prop lands on the clamped div's WebkitLineClamp style, independently verifying the line-count constraint (previously maxLines was passed but untested). - New test: expanding one long value then rerendering with a different long value restores the collapsed state. Co-Authored-By: pi * test(mrt): strengthen collapsible text thresholds (#870) Co-Authored-By: pi
Reconcile the client and server lockfiles against current main, then apply the non-breaking fixes available through npm audit fix. Client updates include the Babel 7.29.7 security release and patched brace-expansion versions. Server updates include js-yaml 3.15.0, protobufjs 7.6.5, patched brace-expansion versions, and compatible Cassandra dependency resolution. Remaining audit findings require breaking upgrades across React Router, ESLint/Storybook, Cassandra, or Jest. Keep those separately scoped; the existing dev-only piscina risk remains accepted here. Co-Authored-By: pi-coding-agent Co-Authored-By: Codex
* Eliminate manual review history item refetches Co-Authored-By: Codex <codex@openai.com> * Remove manual review history regression test Co-Authored-By: Codex <codex@openai.com> --------- Co-authored-by: Codex <codex@openai.com>
Co-authored-by: Codex <codex@openai.com>
* test: add regression test for RetryFailedNcmecDecisionsJob NCMEC_ENV * fix: RetryFailedNcmecDecisionsJob honors NCMEC_ENV The retry worker hardcoded isTest=false, so retries in dev/staging (NCMEC_ENV unset or non-production) submitted to the real NCMEC endpoint (report.cybertip.org) instead of the test endpoint (exttest.cybertip.org). It also published post-submit actions unconditionally, unlike the sibling call sites which gate on !isTest. Compute isTest from NCMEC_ENV the same way as the other two submit sites (iocContainer onRecordDecision path and retryNcmecSubmission), pass it to submitReport, and gate publishActions on !isTest. Co-Authored-By: pi * refactor: drop redundant NCMEC_ENV comment in RetryFailedNcmecDecisionsJob Co-Authored-By: pi
* Clarify approval requirements for routine commands Co-Authored-By: OpenAI Codex <codex@openai.com> * Refine routine command approval guidance Co-Authored-By: OpenAI Codex <codex@openai.com> --------- Co-authored-by: OpenAI Codex <codex@openai.com>
* [Fix] Refuse queue deletion when routing rules still reference it Fixes issue #738 (design #1). Changes the FK constraints on routing_rules.destination_queue_id and appeals_routing_rules.destination_queue_id from ON DELETE CASCADE to ON DELETE RESTRICT. The service now catches the resulting FK violation and throws QueueHasDependentRoutingRulesError, naming the blocking rules, instead of silently cascade-deleting them and breaking routing. The client's previously silent onError handler is replaced with a modal that surfaces the server's error message so the user knows which rules to update before retrying. Regression tests cover both routing_rules and appeals_routing_rules. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * [Queue Delete behavior] Put blocking rules on their own line, indent, and link to rules page * Remove accidentally included test code * [Fix] Update test helper to delete routing rules before queue deletion deleteManualReviewQueueForTestsDO_NOT_USE was written when routing_rules had CASCADE FKs on destination_queue_id. Now that the FK is RESTRICT, the helper must explicitly delete referencing routing rules and appeals routing rules before removing the queue, or the DB rejects the delete. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * [Fix] Address PR reviewer feedback on queue delete behavior - Move queue.obliterate() after DB transaction so Redis jobs aren't destroyed if deletion is blocked by FK constraints - Gate FK error mapping on specific constraint names to avoid swallowing unrelated 23503 errors from future RESTRICT FKs - Add org_id filter to routing rule deletes in test helper - Validate JSON.parse result is string[] before assigning to ruleNames - Use index as React key to avoid collisions on duplicate rule names Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * [Fix] Resolve CI failures after rebase on main Rename the routing-rules migration to a fresh timestamp since main gained a later migration (add_sepia) during the rebase, and dedupe the two new QueueOperations.test.ts cases behind a shared helper to get the file back under the 500-line lint limit. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> * [Fix] Address CodeRabbit feedback: log obliterate() failures after commit If queue.obliterate() throws after the DB delete has already committed, a retry would see numDeletedRows === 0n, skip obliterate() entirely, and silently leave orphaned Bull/Redis data behind. Wrap it in try/catch and surface the failure to the active tracing span, matching the best-effort cleanup pattern used elsewhere (e.g. UserApi.logout). Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> * address code review * make lint happy --------- Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com> Co-authored-by: Juan Mrad <juansmrad@gmail.com>
* Add self-harm/intent and self-harm/instructions signals Round out the omni-moderation self-harm coverage that the prior commit left lopsided. OpenAI scores both subcategories for text *and* image inputs; we had neither. New signal classes (4): - OpenAiSelfHarmIntentTextSignal / OpenAiSelfHarmIntentImageSignal - OpenAiSelfHarmInstructionsTextSignal / OpenAiSelfHarmInstructionsImageSignal Plus matching SignalType enum entries, integrationForSignalType cases, SignalArgsByType / RuntimeSignalArgsByType entries, IoC registration, and the two new category names in OpenAiModelName + OpenAiImageModelName. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * Expose self-harm/intent + instructions signals to GraphQL + client Same shape as the previous fix on PR #534: the four new self-harm subcategory signal types need to round-trip through both hand-maintained mirrors or the dashboard can't see them. - server/graphql/modules/signal.ts: add the four OPEN_AI_SELF_HARM_{INTENT,INSTRUCTIONS}_{TEXT,IMAGE}_MODEL types to the SDL enum. - client/src/models/signal.ts: add the same four to the OpenAi case in integrationForSignalType. - Regenerate codegen. The coverage test added in PR #534 catches this regression class on new SignalType additions; it now exercises 33 enum values (was 29). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * Add docstrings to self-harm/intent + instructions signal classes Matches the docstring style applied to the base PR's image signals. Raises this PR's docstring coverage above CodeRabbit's 80% pre-merge threshold by documenting each of the four new signal classes (self-harm/intent text+image, self-harm/instructions text+image) and their run() methods. No behavior change. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * Apply factory pattern to self-harm subcategory signals Mirrors the cleanup from PR #534: the 4 self-harm subcategory signal classes (2 text + 2 image) collapse to ~20-line factory calls instead of ~110-line class definitions each. - Adds `makeOpenAiTextModerationSignal` alongside the existing image factory introduced in #534. - Both factories now share a single internal `makeOpenAiModerationSignal` parameterized by input scalar + run impl, so the class body lives in one place (was duplicated twice in #534's first cut). - Factories moved into `openAiModerationSignalFactory.ts` — keeps `openAIModerationUtils.ts` under the 500-line lint limit (the second factory pushed it to 510) and organizes the file boundary cleanly: utils = lib functions, factory = class generator. The 4 self-harm subcategory signal files (text + image variants for `self-harm/intent` and `self-harm/instructions`) now just import the appropriate factory and pass a config object. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * fix bad import --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com> Co-authored-by: Juan Mrad <juansmrad@gmail.com>
There was a problem hiding this comment.
Pull request overview
This PR updates the manual review “skip” flow so skipping is handled as a single server-side operation and so dequeueing can transparently step past jobs a given reviewer recently skipped (without hiding those jobs from other reviewers).
Changes:
- Added per-reviewer skip tracking in Redis and updated dequeue to hold skipped jobs aside under the reviewer’s lock, then release them back to the shared pool.
- Updated dequeue behavior to avoid long-poll hangs by using
block: falsewhen calling BullMQgetNextJob. - Simplified the client skip flow to a single
logSkipmutation and improved UX when no reviewable job remains.
Reviewed changes
Copilot reviewed 6 out of 6 changed files in this pull request and generated 4 comments.
Show a summary per file
| File | Description |
|---|---|
| server/services/manualReviewToolService/modules/QueueOperations.ts | Implements per-reviewer skip filtering/hold-aside behavior and Redis skip-set helpers; updates getNextJob usage. |
| server/services/manualReviewToolService/modules/QueueOperations.reviewerSkips.test.ts | Adds coverage for skip-set recording/expiry and per-reviewer dequeue filtering behavior. |
| server/services/manualReviewToolService/manualReviewToolService.ts | Makes logSkip also record the per-reviewer skip and release the lock server-side. |
| client/src/webpages/dashboard/mrt/manual_review_job/ManualReviewJobReview.tsx | Removes separate ReleaseJobLock mutation and updates skip UX/redirect behavior. |
| client/src/graphql/generated.ts | Removes the generated ReleaseJobLock operation artifacts. |
| CHANGELOG.md | Adds an unreleased “Review Console” changelog entry for the new skip behavior (needs scope correction). |
| const skipToNextJob = async () => { | ||
| // First, release the lock on the current job and log the skip | ||
| // Skipping is one server-side operation: it logs the skip, hides the job | ||
| // from this reviewer for the skip window, and releases the lock so the | ||
| // job returns to the shared pool for everyone else. | ||
| if (queueId && job?.id && lockToken) { | ||
| await Promise.all([ | ||
| logSkip(), | ||
| releaseJobLock({ | ||
| variables: { | ||
| input: { | ||
| queueId, | ||
| jobId: job.id, | ||
| lockToken, | ||
| }, | ||
| }, | ||
| }), | ||
| ]); | ||
| const result = await logSkip(); | ||
| if (result.data?.logSkip !== true) { | ||
| // Nothing was released or hidden; stay on the current job so the | ||
| // reviewer can retry (or decide) instead of advancing past it. | ||
| setModalInfo({ | ||
| visible: true, | ||
| modalBody: 'Failed to skip this job. Please try again.', | ||
| footer: [{ title: 'Ok', type: 'primary', onClick: hideModal }], | ||
| }); | ||
| return; | ||
| } | ||
| } |
| // Release the held-aside jobs so other reviewers can pick them up | ||
| // immediately. This reviewer stays excluded via the skip set. | ||
| for (const held of heldAside) { | ||
| await this.releaseJobLock({ | ||
| orgId, | ||
| queueId, | ||
| jobId: held.data.id, |
| if (decision !== undefined) { | ||
| await this.removeJob({ | ||
| orgId, | ||
| queueId, | ||
| lockToken, | ||
| jobId: convertedJob.data.id, | ||
| }).catch(() => {}); | ||
| // then continue while loop | ||
| } else { | ||
| // this is the most likely case, where there is a job |
| ## Review Console | ||
|
|
||
| - Added per-queue job sort modes for manual review: FIFO (default, unchanged), most-reported-first, and custom weighted — ordering is computed at enqueue via BullMQ job priority, so the locked dequeue path is unchanged (#718) | ||
| - Added org-configurable job priority weights (Settings → Job Priorities) for weighted queues; changing weights or a queue's sort mode re-sorts already-queued jobs in a background sweep (#892) | ||
| - Skip is now per-reviewer: a skipped job is hidden from that reviewer for 30 minutes while returning to the shared pool immediately; entering a drained or fully-skipped queue redirects to the queue list (#893) |
…r-skip # Conflicts: # CHANGELOG.md # client/src/graphql/generated.ts # server/services/manualReviewToolService/modules/QueueOperations.ts

Context & Requests for Reviewers
Part 3 of 3 for #670. Previously, skipping a job just released the lock. The job came right back to the same reviewer, and skip was two separate client calls (
logSkip+releaseJobLock) that could partially fail.logSkipatomically logs the skip, records the job in a per-reviewer Redis skip set (sorted set scored by expiry, with a TTL backstop), and releases the lock. The client's separateReleaseJobLockcall is removed.finally, so they return to the shared pool immediately for everyone else.getNextJobnow usesblock: false, so a drained queue returns null immediately instead of long-polling and hanging the reviewer's request.Review focus: the held-aside-then-release pattern in
dequeueNextJobWithLock, particularly lock-token semantics (the token is the reviewer's userId) and what happens if the release infinallypartially fails.Tests
QueueOperations.reviewerSkips.test.ts— skip set recording/expiry, dequeue filtering per reviewer, held-aside jobs released for other reviewers.Checklist
Did you update the CHANGELOG.md and related docs?