diff --git a/.github/dependabot.yml b/.github/dependabot.yml
index 38975fd5..367ce0d0 100644
--- a/.github/dependabot.yml
+++ b/.github/dependabot.yml
@@ -36,6 +36,10 @@ updates:
labels:
- portfolio-maintenance
- needs-runtime-smoke
+ ignore:
+ - dependency-name: typescript
+ update-types:
+ - version-update:semver-major
groups:
frontend-platform:
patterns:
diff --git a/.github/workflows/ai-eval.yml b/.github/workflows/ai-eval.yml
index c287c3aa..ae672881 100644
--- a/.github/workflows/ai-eval.yml
+++ b/.github/workflows/ai-eval.yml
@@ -16,7 +16,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Validate compose file
run: docker compose config --quiet
@@ -27,7 +27,7 @@ jobs:
- name: Upload AI eval report
if: always()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: ai-eval-summary
path: reports/ai/eval-summary.json
@@ -39,7 +39,7 @@ jobs:
- name: Store compose logs
if: failure()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: compose-ai-eval-log
path: compose-ai-eval.log
diff --git a/.github/workflows/api-smoke.yml b/.github/workflows/api-smoke.yml
index 6cf1a719..55d5d85b 100644
--- a/.github/workflows/api-smoke.yml
+++ b/.github/workflows/api-smoke.yml
@@ -15,7 +15,7 @@ jobs:
timeout-minutes: 35
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Validate compose file
run: docker compose config --quiet
@@ -30,7 +30,7 @@ jobs:
- name: Store compose logs
if: failure()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: compose-api-smoke-log
path: compose-api-smoke.log
diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index 364d1be1..64f88811 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -19,7 +19,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Set up Java 21
uses: actions/setup-java@v5
@@ -77,7 +77,7 @@ jobs:
- name: Upload test reports on failure
if: failure()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: test-reports
path: |
diff --git a/.github/workflows/codeql.yml b/.github/workflows/codeql.yml
index 19fb5a20..ede4fa27 100644
--- a/.github/workflows/codeql.yml
+++ b/.github/workflows/codeql.yml
@@ -29,7 +29,7 @@ jobs:
- javascript-typescript
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Set up Java 21
if: matrix.language == 'java-kotlin'
diff --git a/.github/workflows/dependabot-curation.yml b/.github/workflows/dependabot-curation.yml
index 560a5bf4..b8061b8d 100644
--- a/.github/workflows/dependabot-curation.yml
+++ b/.github/workflows/dependabot-curation.yml
@@ -25,7 +25,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Run curation
shell: pwsh
@@ -55,7 +55,7 @@ jobs:
- name: Upload curation reports
if: always()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: dependabot-curation-reports
path: |
diff --git a/.github/workflows/dependency-maintenance.yml b/.github/workflows/dependency-maintenance.yml
index c0c8db8e..f6006d0f 100644
--- a/.github/workflows/dependency-maintenance.yml
+++ b/.github/workflows/dependency-maintenance.yml
@@ -17,7 +17,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Generate inventory
shell: pwsh
@@ -26,7 +26,7 @@ jobs:
run: ./scripts/dependabot-inventory.ps1
- name: Upload inventory
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: dependabot-inventory
path: reports/dependabot/
diff --git a/.github/workflows/docker.yml b/.github/workflows/docker.yml
index 35e4c363..4bb44ba3 100644
--- a/.github/workflows/docker.yml
+++ b/.github/workflows/docker.yml
@@ -36,7 +36,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v4
diff --git a/.github/workflows/docs.yml b/.github/workflows/docs.yml
index ec0dc452..834bc24f 100644
--- a/.github/workflows/docs.yml
+++ b/.github/workflows/docs.yml
@@ -20,7 +20,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Validate portfolio documentation
shell: pwsh
diff --git a/.github/workflows/e2e.yml b/.github/workflows/e2e.yml
index 67c184fb..95e16ce3 100644
--- a/.github/workflows/e2e.yml
+++ b/.github/workflows/e2e.yml
@@ -21,7 +21,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Set up Node.js
uses: actions/setup-node@v6
@@ -54,7 +54,7 @@ jobs:
- name: Upload Playwright preview report
if: always()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: playwright-preview-report
path: |
@@ -70,7 +70,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Set up Node.js
uses: actions/setup-node@v6
@@ -93,7 +93,7 @@ jobs:
- name: Upload Playwright report
if: always()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: playwright-report
path: frontend/playwright-report
diff --git a/.github/workflows/performance.yml b/.github/workflows/performance.yml
index 4e71dd9c..2f565e6b 100644
--- a/.github/workflows/performance.yml
+++ b/.github/workflows/performance.yml
@@ -28,7 +28,7 @@ jobs:
timeout-minutes: 40
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Start stack and validate business flow
shell: pwsh
@@ -45,7 +45,7 @@ jobs:
- name: Upload k6 summary
if: always()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: k6-role-based-suite-summary
path: reports/k6/role-based-suite-summary.json
@@ -57,7 +57,7 @@ jobs:
- name: Store compose logs
if: failure()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: compose-performance-smoke-log
path: compose-performance-smoke.log
diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml
index 3ea1726e..950238a1 100644
--- a/.github/workflows/release.yml
+++ b/.github/workflows/release.yml
@@ -44,7 +44,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v4
@@ -168,7 +168,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Create release from notes
env:
diff --git a/.github/workflows/repository-governance.yml b/.github/workflows/repository-governance.yml
index ded743e2..fd3800bd 100644
--- a/.github/workflows/repository-governance.yml
+++ b/.github/workflows/repository-governance.yml
@@ -27,7 +27,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Dry-run repository governance
if: ${{ inputs.mode == 'dry-run' }}
@@ -92,7 +92,7 @@ jobs:
- name: Upload governance reports
if: always()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: repository-governance-reports
path: |
diff --git a/.github/workflows/scorecard.yml b/.github/workflows/scorecard.yml
index b4003cb2..c601727c 100644
--- a/.github/workflows/scorecard.yml
+++ b/.github/workflows/scorecard.yml
@@ -22,7 +22,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
with:
persist-credentials: false
@@ -30,7 +30,7 @@ jobs:
run: mkdir -p security-reports
- name: Run OpenSSF Scorecard
- uses: ossf/scorecard-action@v2.4.0
+ uses: ossf/scorecard-action@v2.4.3
with:
results_file: security-reports/scorecard.sarif
results_format: sarif
@@ -38,7 +38,7 @@ jobs:
- name: Upload Scorecard report
if: always()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: openssf-scorecard-report
path: security-reports/scorecard.sarif
diff --git a/.github/workflows/security.yml b/.github/workflows/security.yml
index 3552b836..36eb7406 100644
--- a/.github/workflows/security.yml
+++ b/.github/workflows/security.yml
@@ -22,12 +22,12 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
with:
fetch-depth: 0
- name: Scan repository for secrets
- uses: gitleaks/gitleaks-action@v2
+ uses: gitleaks/gitleaks-action@v3
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
GITLEAKS_CONFIG: .gitleaks.toml
@@ -37,7 +37,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Prepare reports directory
run: mkdir -p security-reports
@@ -56,7 +56,7 @@ jobs:
- name: Upload Trivy filesystem report
if: always()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: trivy-filesystem-report
path: security-reports/trivy-fs.txt
@@ -70,7 +70,7 @@ jobs:
actions: read
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Prepare reports directory
run: mkdir -p security-reports
@@ -83,7 +83,7 @@ jobs:
output-file: security-reports/devhire-cloud-sbom.cdx.json
- name: Upload SBOM
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: devhire-cloud-sbom
path: security-reports/devhire-cloud-sbom.cdx.json
@@ -94,7 +94,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Review dependency changes
uses: actions/dependency-review-action@v5
@@ -116,7 +116,7 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Set up Java 21
uses: actions/setup-java@v5
@@ -150,7 +150,7 @@ jobs:
- frontend
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v4
@@ -206,7 +206,7 @@ jobs:
- name: Upload image scan report
if: always()
- uses: actions/upload-artifact@v6
+ uses: actions/upload-artifact@v7
with:
name: trivy-image-${{ matrix.service }}
path: security-reports/trivy-image-${{ matrix.service }}.txt
diff --git a/.github/workflows/terraform.yml b/.github/workflows/terraform.yml
index bb999498..86c080f8 100644
--- a/.github/workflows/terraform.yml
+++ b/.github/workflows/terraform.yml
@@ -56,7 +56,7 @@ jobs:
steps:
- name: Checkout
- uses: actions/checkout@v6
+ uses: actions/checkout@v7
- name: Terraform fmt validate lint and config scan
shell: pwsh
diff --git a/README.md b/README.md
index e60bb0c4..5908ac04 100644
--- a/README.md
+++ b/README.md
@@ -7,7 +7,7 @@
[](https://github.com/JasonTM17/DevHire_Cloud_Spring_Microservices/actions/workflows/terraform.yml)
[](https://github.com/JasonTM17/DevHire_Cloud_Spring_Microservices/actions/workflows/docs.yml)
-DevHire Cloud is a production-engineering portfolio for a recruitment platform: Java 21, Spring Boot 3.5, Next.js, Kafka, OpenSearch, PostgreSQL, Redis, Docker, Kubernetes, Terraform, and a controlled Claude Haiku AI assistant. The repository is written for senior review: it emphasizes service boundaries, owned data, event reliability, observability, security, CI/CD, cloud readiness, and evidence that can be checked without trusting the README.
+DevHire Cloud is a Java, systems, and DevOps learning project for a recruitment platform: Java 21, Spring Boot 4.0, Next.js, Kafka, OpenSearch, PostgreSQL, Redis, Docker, Kubernetes, Terraform, and a controlled Claude Haiku AI assistant. The repository documents service boundaries, owned data, event reliability, observability, security, CI/CD, and cloud-readiness evidence so reviewers can verify each claim against the code and supporting records.
## 30-Second Reviewer Brief
@@ -26,7 +26,7 @@ DevHire Cloud is a production-engineering portfolio for a recruitment platform:
| Current development cycle | `0.6.0-SNAPSHOT` release cut; next snapshot bump is a post-release maintenance step |
| v0.6 Stitch app | Merged into `master`; Code Assessment Studio is the flagship candidate grading, employer review, and admin health workflow |
| Default branch | `master`, protected and PR-governed |
-| Dependabot queue | 0 open Dependabot PRs after the 2026-05-14 zero-noise apply; 20 stale/behind/risky PRs were commented, closed, and their remote branches pruned; no dependency PR was force-merged into the release |
+| Dependency updates | [View the current Dependabot queue](https://github.com/JasonTM17/DevHire_Cloud_Spring_Microservices/pulls?q=is%3Apr+is%3Aopen+author%3Aapp%2Fdependabot); maintenance policy is documented in [docs/dependency-maintenance.md](docs/dependency-maintenance.md). |
| v1 status | Roadmap and acceptance checklist only, not a released tag |
## Reviewer Quick Links
@@ -48,6 +48,29 @@ DevHire Cloud is a production-engineering portfolio for a recruitment platform:
| Cloud readiness | [docs/cloud-readiness-review.md](docs/cloud-readiness-review.md) |
| Production scorecard | [docs/production-engineering-scorecard.md](docs/production-engineering-scorecard.md) |
+### Simplified system topology
+
+This reviewer map groups related services for readability; it is not a complete protocol or event-edge diagram.
+
+```mermaid
+flowchart LR
+ UI["Next.js frontend"] --> GW["Spring Cloud Gateway"]
+ GW --> ID["Auth + User"]
+ GW --> HIRE["Company + Job + Application"]
+ GW --> OPS["Notification + Audit"]
+ GW --> AI["Claude AI service"]
+ HIRE --> RUNNER["Assessment runner"]
+ HIRE <--> KAFKA[("Kafka + outbox")]
+ ID --> PG[("Service-owned PostgreSQL")]
+ HIRE --> PG
+ OPS --> PG
+ AI --> PG
+ HIRE --> SEARCH[("OpenSearch")]
+ ID --> REDIS[("Redis")]
+```
+
+[Review the detailed service boundaries and event flows](docs/architecture.md).
+
## Architecture and Operations Proof
| Layer | Proof in this repository |
@@ -182,4 +205,4 @@ The full visual evidence set is machine-checked in [docs/evidence-manifest.json]
## Honest Scope
-DevHire Cloud is a production-engineering portfolio, not a claim of live customer traffic. It does not claim external penetration testing, a production AWS account, or real customer data. Secrets are not committed; cloud apply remains a separate, credentialed operation.
+DevHire Cloud is a learning project that practices production-engineering patterns, not a claim of live customer traffic. It does not claim external penetration testing, a production AWS account, or real customer data. Secrets are not committed; cloud apply remains a separate, credentialed operation.
diff --git a/ai-service/Dockerfile b/ai-service/Dockerfile
index 29e8aefb..aa9b59bf 100644
--- a/ai-service/Dockerfile
+++ b/ai-service/Dockerfile
@@ -1,4 +1,4 @@
-FROM maven:3.9.12-eclipse-temurin-21 AS build
+FROM maven:3.9.14-eclipse-temurin-25 AS build
WORKDIR /workspace
ARG SERVICE_NAME=ai-service
COPY pom.xml .
@@ -17,7 +17,7 @@ COPY common-lib/src common-lib/src
COPY ${SERVICE_NAME}/src ${SERVICE_NAME}/src
RUN mvn -B -T1 -pl ${SERVICE_NAME} -am package -DskipTests
-FROM eclipse-temurin:21-jre-alpine
+FROM eclipse-temurin:25-jre-alpine
ARG SERVICE_NAME=ai-service
ARG BUILD_VERSION=0.4.0-SNAPSHOT
ARG VCS_REF=local
diff --git a/ai-service/pom.xml b/ai-service/pom.xml
index 651fdcf3..676119a1 100644
--- a/ai-service/pom.xml
+++ b/ai-service/pom.xml
@@ -42,12 +42,12 @@
spring-boot-starter-jdbc
- org.springframework.kafka
- spring-kafka
+ org.springframework.boot
+ spring-boot-starter-kafka
- org.flywaydb
- flyway-core
+ org.springframework.boot
+ spring-boot-starter-flyway
org.flywaydb
@@ -84,14 +84,24 @@
spring-boot-starter-test
test
+
+ org.springframework.boot
+ spring-boot-starter-jdbc-test
+ test
+
+
+ org.springframework.boot
+ spring-boot-starter-flyway-test
+ test
+
org.testcontainers
- postgresql
+ testcontainers-postgresql
test
org.testcontainers
- junit-jupiter
+ testcontainers-junit-jupiter
test
diff --git a/ai-service/src/test/java/com/devhire/ai/repository/AiConversationRepositoryIT.java b/ai-service/src/test/java/com/devhire/ai/repository/AiConversationRepositoryIT.java
index 103b57ba..ea60d2c6 100644
--- a/ai-service/src/test/java/com/devhire/ai/repository/AiConversationRepositoryIT.java
+++ b/ai-service/src/test/java/com/devhire/ai/repository/AiConversationRepositoryIT.java
@@ -6,13 +6,13 @@
import com.fasterxml.jackson.databind.ObjectMapper;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
-import org.springframework.boot.test.autoconfigure.jdbc.JdbcTest;
+import org.springframework.boot.jdbc.test.autoconfigure.AutoConfigureTestDatabase;
+import org.springframework.boot.jdbc.test.autoconfigure.JdbcTest;
import org.springframework.context.annotation.Import;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.test.context.DynamicPropertyRegistry;
import org.springframework.test.context.DynamicPropertySource;
-import org.testcontainers.containers.PostgreSQLContainer;
+import org.testcontainers.postgresql.PostgreSQLContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
@@ -26,7 +26,7 @@
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
class AiConversationRepositoryIT {
@Container
- static final PostgreSQLContainer> POSTGRES = new PostgreSQLContainer<>("postgres:17-alpine");
+ static final PostgreSQLContainer POSTGRES = new PostgreSQLContainer("postgres:17-alpine");
@DynamicPropertySource
static void datasource(DynamicPropertyRegistry registry) {
diff --git a/api-gateway/Dockerfile b/api-gateway/Dockerfile
index 0064b1f2..10fade39 100644
--- a/api-gateway/Dockerfile
+++ b/api-gateway/Dockerfile
@@ -1,4 +1,4 @@
-FROM maven:3.9.12-eclipse-temurin-21 AS build
+FROM maven:3.9.14-eclipse-temurin-25 AS build
WORKDIR /workspace
ARG SERVICE_NAME=api-gateway
COPY pom.xml .
@@ -17,7 +17,7 @@ COPY common-lib/src common-lib/src
COPY ${SERVICE_NAME}/src ${SERVICE_NAME}/src
RUN mvn -B -T1 -pl ${SERVICE_NAME} -am package -DskipTests
-FROM eclipse-temurin:21-jre-alpine
+FROM eclipse-temurin:25-jre-alpine
ARG SERVICE_NAME=api-gateway
ARG BUILD_VERSION=0.4.0-SNAPSHOT
ARG VCS_REF=local
diff --git a/api-gateway/src/main/java/com/devhire/gateway/error/GatewayExceptionHandler.java b/api-gateway/src/main/java/com/devhire/gateway/error/GatewayExceptionHandler.java
index bf0fca13..93d6d63a 100644
--- a/api-gateway/src/main/java/com/devhire/gateway/error/GatewayExceptionHandler.java
+++ b/api-gateway/src/main/java/com/devhire/gateway/error/GatewayExceptionHandler.java
@@ -1,7 +1,7 @@
package com.devhire.gateway.error;
import com.devhire.common.error.ErrorCode;
-import org.springframework.boot.web.reactive.error.ErrorWebExceptionHandler;
+import org.springframework.boot.webflux.error.ErrorWebExceptionHandler;
import org.springframework.core.annotation.Order;
import org.springframework.http.HttpStatus;
import org.springframework.stereotype.Component;
diff --git a/api-gateway/src/test/java/com/devhire/gateway/security/JwtAuthenticationGatewayFilterTest.java b/api-gateway/src/test/java/com/devhire/gateway/security/JwtAuthenticationGatewayFilterTest.java
index 6ded9ec9..e2bc8345 100644
--- a/api-gateway/src/test/java/com/devhire/gateway/security/JwtAuthenticationGatewayFilterTest.java
+++ b/api-gateway/src/test/java/com/devhire/gateway/security/JwtAuthenticationGatewayFilterTest.java
@@ -85,7 +85,7 @@ void publicAuthRouteStripsSpoofedIdentityHeaders() {
filter.filter(exchange, chain).block();
- assertThat(downstreamExchange.get().getRequest().getHeaders()).doesNotContainKey(AppHeaders.USER_ID);
+ assertThat(downstreamExchange.get().getRequest().getHeaders().containsHeader(AppHeaders.USER_ID)).isFalse();
verifyNoInteractions(redisTemplate);
}
@@ -108,8 +108,8 @@ void publicCompanyReadsDoNotRequireJwtButStripSpoofedIdentityHeaders() {
filter.filter(exchange, chain).block();
- assertThat(downstreamExchange.get().getRequest().getHeaders()).doesNotContainKey(AppHeaders.USER_ID);
- assertThat(downstreamExchange.get().getRequest().getHeaders()).doesNotContainKey(AppHeaders.USER_ROLE);
+ assertThat(downstreamExchange.get().getRequest().getHeaders().containsHeader(AppHeaders.USER_ID)).isFalse();
+ assertThat(downstreamExchange.get().getRequest().getHeaders().containsHeader(AppHeaders.USER_ROLE)).isFalse();
}
verifyNoInteractions(redisTemplate);
}
diff --git a/application-service/Dockerfile b/application-service/Dockerfile
index f11918d3..9e47d128 100644
--- a/application-service/Dockerfile
+++ b/application-service/Dockerfile
@@ -1,4 +1,4 @@
-FROM maven:3.9.12-eclipse-temurin-21 AS build
+FROM maven:3.9.14-eclipse-temurin-25 AS build
WORKDIR /workspace
ARG SERVICE_NAME=application-service
COPY pom.xml .
@@ -17,7 +17,7 @@ COPY common-lib/src common-lib/src
COPY ${SERVICE_NAME}/src ${SERVICE_NAME}/src
RUN mvn -B -T1 -pl ${SERVICE_NAME} -am package -DskipTests
-FROM eclipse-temurin:21-jre-alpine
+FROM eclipse-temurin:25-jre-alpine
ARG SERVICE_NAME=application-service
ARG BUILD_VERSION=0.4.0-SNAPSHOT
ARG VCS_REF=local
diff --git a/application-service/pom.xml b/application-service/pom.xml
index 2f6bc716..3a42e57a 100644
--- a/application-service/pom.xml
+++ b/application-service/pom.xml
@@ -17,8 +17,8 @@
org.springframework.bootspring-boot-starter-data-jpa
org.springframework.bootspring-boot-starter-actuator
org.springframework.cloudspring-cloud-starter-openfeign
- org.springframework.kafkaspring-kafka
- org.flywaydbflyway-core
+ org.springframework.bootspring-boot-starter-kafka
+ org.springframework.bootspring-boot-starter-flyway
org.flywaydbflyway-database-postgresql
org.postgresqlpostgresqlruntime
org.springdocspringdoc-openapi-starter-webmvc-ui${springdoc.version}
@@ -26,8 +26,10 @@
io.micrometermicrometer-tracing-bridge-otel
io.opentelemetryopentelemetry-exporter-otlp
org.springframework.bootspring-boot-starter-testtest
- org.testcontainerspostgresqltest
- org.testcontainersjunit-jupitertest
+ org.springframework.bootspring-boot-starter-data-jpa-testtest
+ org.springframework.bootspring-boot-starter-flyway-testtest
+ org.testcontainerstestcontainers-postgresqltest
+ org.testcontainerstestcontainers-junit-jupitertest
org.springframework.bootspring-boot-maven-plugin
diff --git a/application-service/src/test/java/com/devhire/application/repository/ApplicationRepositoryIT.java b/application-service/src/test/java/com/devhire/application/repository/ApplicationRepositoryIT.java
index d2eca8b9..b42772e3 100644
--- a/application-service/src/test/java/com/devhire/application/repository/ApplicationRepositoryIT.java
+++ b/application-service/src/test/java/com/devhire/application/repository/ApplicationRepositoryIT.java
@@ -5,8 +5,8 @@
import com.devhire.application.entity.JobApplication;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
-import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
+import org.springframework.boot.data.jpa.test.autoconfigure.DataJpaTest;
+import org.springframework.boot.jdbc.test.autoconfigure.AutoConfigureTestDatabase;
import org.springframework.dao.DataIntegrityViolationException;
import org.springframework.data.domain.PageRequest;
import org.springframework.jdbc.core.JdbcTemplate;
@@ -14,7 +14,7 @@
import org.springframework.test.context.DynamicPropertySource;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
-import org.testcontainers.containers.PostgreSQLContainer;
+import org.testcontainers.postgresql.PostgreSQLContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
@@ -28,7 +28,7 @@
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
class ApplicationRepositoryIT {
@Container
- static final PostgreSQLContainer> POSTGRES = new PostgreSQLContainer<>("postgres:17-alpine");
+ static final PostgreSQLContainer POSTGRES = new PostgreSQLContainer("postgres:17-alpine");
@DynamicPropertySource
static void datasource(DynamicPropertyRegistry registry) {
diff --git a/audit-service/Dockerfile b/audit-service/Dockerfile
index d729c982..3ed11681 100644
--- a/audit-service/Dockerfile
+++ b/audit-service/Dockerfile
@@ -1,4 +1,4 @@
-FROM maven:3.9.12-eclipse-temurin-21 AS build
+FROM maven:3.9.14-eclipse-temurin-25 AS build
WORKDIR /workspace
ARG SERVICE_NAME=audit-service
COPY pom.xml .
@@ -17,7 +17,7 @@ COPY common-lib/src common-lib/src
COPY ${SERVICE_NAME}/src ${SERVICE_NAME}/src
RUN mvn -B -T1 -pl ${SERVICE_NAME} -am package -DskipTests
-FROM eclipse-temurin:21-jre-alpine
+FROM eclipse-temurin:25-jre-alpine
ARG SERVICE_NAME=audit-service
ARG BUILD_VERSION=0.4.0-SNAPSHOT
ARG VCS_REF=local
diff --git a/audit-service/pom.xml b/audit-service/pom.xml
index d4ae8494..4cb94e2e 100644
--- a/audit-service/pom.xml
+++ b/audit-service/pom.xml
@@ -16,8 +16,8 @@
org.springframework.bootspring-boot-starter-validation
org.springframework.bootspring-boot-starter-data-jpa
org.springframework.bootspring-boot-starter-actuator
- org.springframework.kafkaspring-kafka
- org.flywaydbflyway-core
+ org.springframework.bootspring-boot-starter-kafka
+ org.springframework.bootspring-boot-starter-flyway
org.flywaydbflyway-database-postgresql
org.postgresqlpostgresqlruntime
org.springdocspringdoc-openapi-starter-webmvc-ui${springdoc.version}
@@ -25,8 +25,10 @@
io.micrometermicrometer-tracing-bridge-otel
io.opentelemetryopentelemetry-exporter-otlp
org.springframework.bootspring-boot-starter-testtest
- org.testcontainerspostgresqltest
- org.testcontainersjunit-jupitertest
+ org.springframework.bootspring-boot-starter-data-jpa-testtest
+ org.springframework.bootspring-boot-starter-flyway-testtest
+ org.testcontainerstestcontainers-postgresqltest
+ org.testcontainerstestcontainers-junit-jupitertest
org.springframework.bootspring-boot-maven-plugin
diff --git a/audit-service/src/main/java/com/devhire/audit/repository/AuditLogSpecifications.java b/audit-service/src/main/java/com/devhire/audit/repository/AuditLogSpecifications.java
index 8d453fd0..d6fb8ea5 100644
--- a/audit-service/src/main/java/com/devhire/audit/repository/AuditLogSpecifications.java
+++ b/audit-service/src/main/java/com/devhire/audit/repository/AuditLogSpecifications.java
@@ -12,13 +12,13 @@ private AuditLogSpecifications() {
}
public static Specification actorId(UUID actorId) {
- return actorId == null ? null : (root, query, criteriaBuilder) ->
+ return actorId == null ? Specification.unrestricted() : (root, query, criteriaBuilder) ->
criteriaBuilder.equal(root.get("actorId"), actorId);
}
public static Specification action(String action) {
if (action == null || action.isBlank()) {
- return null;
+ return Specification.unrestricted();
}
String normalized = action.toLowerCase(Locale.ROOT);
return (root, query, criteriaBuilder) ->
@@ -26,12 +26,12 @@ public static Specification action(String action) {
}
public static Specification occurredFrom(Instant from) {
- return from == null ? null : (root, query, criteriaBuilder) ->
+ return from == null ? Specification.unrestricted() : (root, query, criteriaBuilder) ->
criteriaBuilder.greaterThanOrEqualTo(root.get("occurredAt"), from);
}
public static Specification occurredTo(Instant to) {
- return to == null ? null : (root, query, criteriaBuilder) ->
+ return to == null ? Specification.unrestricted() : (root, query, criteriaBuilder) ->
criteriaBuilder.lessThanOrEqualTo(root.get("occurredAt"), to);
}
}
diff --git a/audit-service/src/test/java/com/devhire/audit/repository/AuditLogRepositoryIT.java b/audit-service/src/test/java/com/devhire/audit/repository/AuditLogRepositoryIT.java
index c25c1bea..e36583ef 100644
--- a/audit-service/src/test/java/com/devhire/audit/repository/AuditLogRepositoryIT.java
+++ b/audit-service/src/test/java/com/devhire/audit/repository/AuditLogRepositoryIT.java
@@ -3,12 +3,12 @@
import com.devhire.audit.entity.AuditLog;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
-import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
+import org.springframework.boot.data.jpa.test.autoconfigure.DataJpaTest;
+import org.springframework.boot.jdbc.test.autoconfigure.AutoConfigureTestDatabase;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.test.context.DynamicPropertyRegistry;
import org.springframework.test.context.DynamicPropertySource;
-import org.testcontainers.containers.PostgreSQLContainer;
+import org.testcontainers.postgresql.PostgreSQLContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
@@ -22,7 +22,7 @@
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
class AuditLogRepositoryIT {
@Container
- static final PostgreSQLContainer> POSTGRES = new PostgreSQLContainer<>("postgres:17-alpine");
+ static final PostgreSQLContainer POSTGRES = new PostgreSQLContainer("postgres:17-alpine");
@DynamicPropertySource
static void datasource(DynamicPropertyRegistry registry) {
diff --git a/auth-service/Dockerfile b/auth-service/Dockerfile
index 54b23d1a..1e741e6f 100644
--- a/auth-service/Dockerfile
+++ b/auth-service/Dockerfile
@@ -1,4 +1,4 @@
-FROM maven:3.9.12-eclipse-temurin-21 AS build
+FROM maven:3.9.14-eclipse-temurin-25 AS build
WORKDIR /workspace
ARG SERVICE_NAME=auth-service
COPY pom.xml .
@@ -17,7 +17,7 @@ COPY common-lib/src common-lib/src
COPY ${SERVICE_NAME}/src ${SERVICE_NAME}/src
RUN mvn -B -T1 -pl ${SERVICE_NAME} -am package -DskipTests
-FROM eclipse-temurin:21-jre-alpine
+FROM eclipse-temurin:25-jre-alpine
ARG SERVICE_NAME=auth-service
ARG BUILD_VERSION=0.4.0-SNAPSHOT
ARG VCS_REF=local
diff --git a/auth-service/pom.xml b/auth-service/pom.xml
index 1477a7f1..61ff45bf 100644
--- a/auth-service/pom.xml
+++ b/auth-service/pom.xml
@@ -36,12 +36,12 @@
spring-boot-starter-data-redis
- org.springframework.kafka
- spring-kafka
+ org.springframework.boot
+ spring-boot-starter-kafka
- org.flywaydb
- flyway-core
+ org.springframework.boot
+ spring-boot-starter-flyway
org.flywaydb
@@ -95,6 +95,16 @@
spring-boot-starter-test
test
+
+ org.springframework.boot
+ spring-boot-starter-data-jpa-test
+ test
+
+
+ org.springframework.boot
+ spring-boot-starter-flyway-test
+ test
+
org.springframework.security
spring-security-test
@@ -102,12 +112,12 @@
org.testcontainers
- postgresql
+ testcontainers-postgresql
test
org.testcontainers
- junit-jupiter
+ testcontainers-junit-jupiter
test
diff --git a/auth-service/src/test/java/com/devhire/auth/repository/AuthRepositoryIT.java b/auth-service/src/test/java/com/devhire/auth/repository/AuthRepositoryIT.java
index 2f78b9d1..3d3747a0 100644
--- a/auth-service/src/test/java/com/devhire/auth/repository/AuthRepositoryIT.java
+++ b/auth-service/src/test/java/com/devhire/auth/repository/AuthRepositoryIT.java
@@ -5,14 +5,14 @@
import com.devhire.common.security.UserRole;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
-import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
+import org.springframework.boot.data.jpa.test.autoconfigure.DataJpaTest;
+import org.springframework.boot.jdbc.test.autoconfigure.AutoConfigureTestDatabase;
import org.springframework.dao.DataIntegrityViolationException;
import org.springframework.test.context.DynamicPropertyRegistry;
import org.springframework.test.context.DynamicPropertySource;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
-import org.testcontainers.containers.PostgreSQLContainer;
+import org.testcontainers.postgresql.PostgreSQLContainer;
import java.time.Instant;
import java.util.UUID;
@@ -25,7 +25,7 @@
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
class AuthRepositoryIT {
@Container
- static final PostgreSQLContainer> POSTGRES = new PostgreSQLContainer<>("postgres:17-alpine");
+ static final PostgreSQLContainer POSTGRES = new PostgreSQLContainer("postgres:17-alpine");
@DynamicPropertySource
static void datasource(DynamicPropertyRegistry registry) {
diff --git a/common-lib/pom.xml b/common-lib/pom.xml
index 401cebfd..042923a8 100644
--- a/common-lib/pom.xml
+++ b/common-lib/pom.xml
@@ -51,10 +51,13 @@
com.fasterxml.jackson.core
jackson-databind
+
+ org.springframework.boot
+ spring-boot-jackson2
+
com.fasterxml.jackson.datatype
jackson-datatype-jsr310
- test
org.springframework.boot
diff --git a/company-service/Dockerfile b/company-service/Dockerfile
index 8f78e2af..7ccbf57c 100644
--- a/company-service/Dockerfile
+++ b/company-service/Dockerfile
@@ -1,4 +1,4 @@
-FROM maven:3.9.12-eclipse-temurin-21 AS build
+FROM maven:3.9.14-eclipse-temurin-25 AS build
WORKDIR /workspace
ARG SERVICE_NAME=company-service
COPY pom.xml .
@@ -17,7 +17,7 @@ COPY common-lib/src common-lib/src
COPY ${SERVICE_NAME}/src ${SERVICE_NAME}/src
RUN mvn -B -T1 -pl ${SERVICE_NAME} -am package -DskipTests
-FROM eclipse-temurin:21-jre-alpine
+FROM eclipse-temurin:25-jre-alpine
ARG SERVICE_NAME=company-service
ARG BUILD_VERSION=0.4.0-SNAPSHOT
ARG VCS_REF=local
diff --git a/company-service/pom.xml b/company-service/pom.xml
index 20385742..c819cc1b 100644
--- a/company-service/pom.xml
+++ b/company-service/pom.xml
@@ -16,8 +16,8 @@
org.springframework.bootspring-boot-starter-validation
org.springframework.bootspring-boot-starter-data-jpa
org.springframework.bootspring-boot-starter-actuator
- org.springframework.kafkaspring-kafka
- org.flywaydbflyway-core
+ org.springframework.bootspring-boot-starter-kafka
+ org.springframework.bootspring-boot-starter-flyway
org.flywaydbflyway-database-postgresql
org.postgresqlpostgresqlruntime
org.springdocspringdoc-openapi-starter-webmvc-ui${springdoc.version}
@@ -25,8 +25,10 @@
io.micrometermicrometer-tracing-bridge-otel
io.opentelemetryopentelemetry-exporter-otlp
org.springframework.bootspring-boot-starter-testtest
- org.testcontainerspostgresqltest
- org.testcontainersjunit-jupitertest
+ org.springframework.bootspring-boot-starter-data-jpa-testtest
+ org.springframework.bootspring-boot-starter-flyway-testtest
+ org.testcontainerstestcontainers-postgresqltest
+ org.testcontainerstestcontainers-junit-jupitertest
org.springframework.bootspring-boot-maven-plugin
diff --git a/company-service/src/test/java/com/devhire/company/repository/CompanyRepositoryIT.java b/company-service/src/test/java/com/devhire/company/repository/CompanyRepositoryIT.java
index ca38bf3c..644019de 100644
--- a/company-service/src/test/java/com/devhire/company/repository/CompanyRepositoryIT.java
+++ b/company-service/src/test/java/com/devhire/company/repository/CompanyRepositoryIT.java
@@ -4,13 +4,13 @@
import com.devhire.company.entity.CompanyStatus;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
-import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
+import org.springframework.boot.data.jpa.test.autoconfigure.DataJpaTest;
+import org.springframework.boot.jdbc.test.autoconfigure.AutoConfigureTestDatabase;
import org.springframework.dao.DataIntegrityViolationException;
import org.springframework.data.domain.PageRequest;
import org.springframework.test.context.DynamicPropertyRegistry;
import org.springframework.test.context.DynamicPropertySource;
-import org.testcontainers.containers.PostgreSQLContainer;
+import org.testcontainers.postgresql.PostgreSQLContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
@@ -24,7 +24,7 @@
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
class CompanyRepositoryIT {
@Container
- static final PostgreSQLContainer> POSTGRES = new PostgreSQLContainer<>("postgres:17-alpine");
+ static final PostgreSQLContainer POSTGRES = new PostgreSQLContainer("postgres:17-alpine");
@DynamicPropertySource
static void datasource(DynamicPropertyRegistry registry) {
diff --git a/deploy/terraform/aws/environments/dev/versions.tf b/deploy/terraform/aws/environments/dev/versions.tf
index c64e13ef..8c119a6c 100644
--- a/deploy/terraform/aws/environments/dev/versions.tf
+++ b/deploy/terraform/aws/environments/dev/versions.tf
@@ -4,7 +4,7 @@ terraform {
required_providers {
aws = {
source = "hashicorp/aws"
- version = "~> 5.84"
+ version = "~> 6.45"
}
}
}
diff --git a/deploy/terraform/aws/environments/prod/versions.tf b/deploy/terraform/aws/environments/prod/versions.tf
index c64e13ef..8c119a6c 100644
--- a/deploy/terraform/aws/environments/prod/versions.tf
+++ b/deploy/terraform/aws/environments/prod/versions.tf
@@ -4,7 +4,7 @@ terraform {
required_providers {
aws = {
source = "hashicorp/aws"
- version = "~> 5.84"
+ version = "~> 6.45"
}
}
}
diff --git a/deploy/terraform/aws/environments/staging/versions.tf b/deploy/terraform/aws/environments/staging/versions.tf
index c64e13ef..8c119a6c 100644
--- a/deploy/terraform/aws/environments/staging/versions.tf
+++ b/deploy/terraform/aws/environments/staging/versions.tf
@@ -4,7 +4,7 @@ terraform {
required_providers {
aws = {
source = "hashicorp/aws"
- version = "~> 5.84"
+ version = "~> 6.45"
}
}
}
diff --git a/deploy/terraform/aws/modules/container/versions.tf b/deploy/terraform/aws/modules/container/versions.tf
index eba66bdc..5c6a897f 100644
--- a/deploy/terraform/aws/modules/container/versions.tf
+++ b/deploy/terraform/aws/modules/container/versions.tf
@@ -4,7 +4,7 @@ terraform {
required_providers {
aws = {
source = "hashicorp/aws"
- version = "~> 5.84"
+ version = "~> 6.45"
}
}
}
diff --git a/deploy/terraform/aws/modules/data/versions.tf b/deploy/terraform/aws/modules/data/versions.tf
index eba66bdc..5c6a897f 100644
--- a/deploy/terraform/aws/modules/data/versions.tf
+++ b/deploy/terraform/aws/modules/data/versions.tf
@@ -4,7 +4,7 @@ terraform {
required_providers {
aws = {
source = "hashicorp/aws"
- version = "~> 5.84"
+ version = "~> 6.45"
}
}
}
diff --git a/deploy/terraform/aws/modules/eks/versions.tf b/deploy/terraform/aws/modules/eks/versions.tf
index eba66bdc..5c6a897f 100644
--- a/deploy/terraform/aws/modules/eks/versions.tf
+++ b/deploy/terraform/aws/modules/eks/versions.tf
@@ -4,7 +4,7 @@ terraform {
required_providers {
aws = {
source = "hashicorp/aws"
- version = "~> 5.84"
+ version = "~> 6.45"
}
}
}
diff --git a/deploy/terraform/aws/modules/network/versions.tf b/deploy/terraform/aws/modules/network/versions.tf
index eba66bdc..5c6a897f 100644
--- a/deploy/terraform/aws/modules/network/versions.tf
+++ b/deploy/terraform/aws/modules/network/versions.tf
@@ -4,7 +4,7 @@ terraform {
required_providers {
aws = {
source = "hashicorp/aws"
- version = "~> 5.84"
+ version = "~> 6.45"
}
}
}
diff --git a/deploy/terraform/aws/modules/secrets/versions.tf b/deploy/terraform/aws/modules/secrets/versions.tf
index eba66bdc..5c6a897f 100644
--- a/deploy/terraform/aws/modules/secrets/versions.tf
+++ b/deploy/terraform/aws/modules/secrets/versions.tf
@@ -4,7 +4,7 @@ terraform {
required_providers {
aws = {
source = "hashicorp/aws"
- version = "~> 5.84"
+ version = "~> 6.45"
}
}
}
diff --git a/docs/README_EN.md b/docs/README_EN.md
index f1e36b60..d061efa0 100644
--- a/docs/README_EN.md
+++ b/docs/README_EN.md
@@ -1,6 +1,6 @@
# DevHire Cloud - Microservices Recruitment Platform
-DevHire Cloud is a production-engineering portfolio for a recruitment platform: Java 21, Spring Boot 3.5, Next.js, Kafka, OpenSearch, PostgreSQL, Redis, Docker, Kubernetes, Terraform, and a controlled Claude Haiku AI assistant. The repository is written for senior review: it emphasizes service boundaries, owned data, event reliability, observability, security, CI/CD, cloud readiness, and evidence that can be checked without trusting the README.
+DevHire Cloud is a production-engineering portfolio for a recruitment platform: Java 21, Spring Boot 4.0, Next.js, Kafka, OpenSearch, PostgreSQL, Redis, Docker, Kubernetes, Terraform, and a controlled Claude Haiku AI assistant. The repository is written for senior review: it emphasizes service boundaries, owned data, event reliability, observability, security, CI/CD, cloud readiness, and evidence that can be checked without trusting the README.
## 30-Second Reviewer Brief
diff --git a/docs/README_JA.md b/docs/README_JA.md
index 9db91fec..cf4bb7f4 100644
--- a/docs/README_JA.md
+++ b/docs/README_JA.md
@@ -1,6 +1,6 @@
# DevHire Cloud - Microservices Recruitment Platform
-DevHire Cloud は、Java 21 / Spring Boot 3.5 で構築した採用プラットフォームの production engineering portfolio です。小規模な ITviec / LinkedIn Jobs のようなドメインを使い、明確な service boundary、service-owned database、Kafka/outbox、OpenSearch、observability、Docker/Kubernetes/Terraform、CI/CD、security evidence、Claude Haiku AI assistant を示します。
+DevHire Cloud は、Java 21 / Spring Boot 4.0 で構築した採用プラットフォームの production engineering portfolio です。小規模な ITviec / LinkedIn Jobs のようなドメインを使い、明確な service boundary、service-owned database、Kafka/outbox、OpenSearch、observability、Docker/Kubernetes/Terraform、CI/CD、security evidence、Claude Haiku AI assistant を示します。
## Public Repository Status
diff --git a/docs/demo-script.md b/docs/demo-script.md
index 0c2d6ab2..3181475c 100644
--- a/docs/demo-script.md
+++ b/docs/demo-script.md
@@ -100,7 +100,7 @@ Show these files:
Final message for recruiter:
-DevHire Cloud demonstrates Java 21, Spring Boot 3.5, Spring Cloud Gateway, JWT security, service-owned databases, Flyway, Kafka/outbox, OpenSearch, Claude Haiku RAG assistant, Gmail SMTP hardening, observability, CI/CD, Docker, Kubernetes/Helm/GitOps, tests, and real frontend E2E smoke coverage.
+DevHire Cloud demonstrates Java 21, Spring Boot 4.0, Spring Cloud Gateway, JWT security, service-owned databases, Flyway, Kafka/outbox, OpenSearch, Claude Haiku RAG assistant, Gmail SMTP hardening, observability, CI/CD, Docker, Kubernetes/Helm/GitOps, tests, and real frontend E2E smoke coverage.
Cleanup after a recruiter demo:
diff --git a/docs/dependency-maintenance.md b/docs/dependency-maintenance.md
index f79c104d..91a6f1ae 100644
--- a/docs/dependency-maintenance.md
+++ b/docs/dependency-maintenance.md
@@ -10,11 +10,18 @@ DevHire Cloud keeps Dependabot enabled because dependency hygiene is part of the
| Docker base images patch/minor | Batch by runtime family | Keeps image drift small without forcing many tiny releases. |
| Maven patch/minor | Accept when tests and smoke gates pass | Backend dependency changes can affect contracts and runtime behavior. |
| npm patch/minor | Accept with typecheck, build, and Playwright smoke | Frontend runtime changes are visible and should be screenshot-checked. |
+| TypeScript major | Defer until the Next.js production build and compiler API are compatible | A standalone `tsc` pass is insufficient when the framework also loads the TypeScript compiler API. |
| Terraform provider major | Defer until migration review | AWS provider major upgrades can change resources and state behavior. |
| Node major | Defer until Docker/frontend compatibility review | Runtime major upgrades can affect Next.js build and image behavior. |
| Spring platform major | Defer until compatibility matrix review | Spring Boot/Spring Cloud compatibility is a hard production constraint. |
-## Current v0.6 Release-Readiness State
+## 2026-07-15 Coordinated Integration Batch
+
+This maintenance window consolidates 23 remote branches into one reviewable change: 1 README correction and 22 Dependabot updates spanning GitHub Actions, Docker images, Maven, npm, and Terraform. Major platform changes were reviewed together because Spring Boot 4, Testcontainers 2, Node 26, and the AWS provider 6 line require compatibility fixes beyond a mechanical version bump.
+
+Local validation covered the full 12-module Maven reactor, 417 frontend tests, 22 property tests at 500 runs each, 52 Playwright scenarios across desktop and Pixel 7 projects, all three Terraform environments, documentation and repository audits, and an npm audit with zero known vulnerabilities. TypeScript remains on 6.0.3 because the current Next.js production build does not yet load the TypeScript 7 compiler API correctly; Dependabot ignores that major line until the framework boundary is compatible. Pull-request CI remains the final gate for the complete Docker matrix, CodeQL, secret scanning, SBOM generation, and filesystem scanning.
+
+## 2026-05 Release-Readiness Baseline
The 2026-05-14 live GitHub scan originally found 20 Dependabot pull requests: 9 Docker, 1 GitHub Actions, 2 Maven, 4 npm/frontend, 3 Terraform, and 1 other. `scripts/dependabot-zero-noise.ps1 -Apply` was then run from an owner-authenticated shell. It found 0 clean merge candidates, commented on each PR, closed/deferred all 20 stale/behind/risky updates, and the remote Dependabot branches were pruned. No dependency PR was force-merged into the release.
diff --git a/docs/production-checklist.md b/docs/production-checklist.md
index 7a2fef0d..d8dfa8a7 100644
--- a/docs/production-checklist.md
+++ b/docs/production-checklist.md
@@ -1,6 +1,6 @@
# Production Portfolio Checklist
-- Java 21 and Spring Boot 3.5.x multi-module build.
+- Java 21 and Spring Boot 4.0.x multi-module build.
- Spring Cloud Gateway with JWT validation, CORS, route security, and Redis rate limit.
- Role-based authorization for Admin, Employer, and Candidate.
- BCrypt password hashing.
diff --git a/frontend/Dockerfile b/frontend/Dockerfile
index 17b25c8c..64f0439a 100644
--- a/frontend/Dockerfile
+++ b/frontend/Dockerfile
@@ -1,9 +1,9 @@
-FROM node:24-alpine AS deps
+FROM node:26-alpine AS deps
WORKDIR /app
COPY frontend/package*.json ./
RUN npm ci
-FROM node:24-alpine AS builder
+FROM node:26-alpine AS builder
WORKDIR /app
ARG NEXT_PUBLIC_API_BASE_URL=http://localhost:8080
ENV NEXT_TELEMETRY_DISABLED=1
@@ -12,7 +12,7 @@ COPY --from=deps /app/node_modules ./node_modules
COPY frontend ./
RUN npm run build
-FROM node:24-alpine AS runner
+FROM node:26-alpine AS runner
WORKDIR /app
ARG SERVICE_NAME=frontend
ARG BUILD_VERSION=0.4.0
diff --git a/frontend/e2e/code-assessment-flow.spec.ts b/frontend/e2e/code-assessment-flow.spec.ts
index 89591e67..e64d1493 100644
--- a/frontend/e2e/code-assessment-flow.spec.ts
+++ b/frontend/e2e/code-assessment-flow.spec.ts
@@ -660,6 +660,10 @@ async function routeAdminApi(page: Page) {
}
test.describe("LeetCode-style code assessment E2E", () => {
+ test.beforeEach(async ({ page }) => {
+ await page.clock.setFixedTime(new Date(NOW));
+ });
+
test("candidate runs custom visible input, submits Java, and never sees hidden payloads", async ({ page }) => {
await routeCandidateCodeAssessmentApi(page);
await login(page, "candidate");
diff --git a/frontend/package-lock.json b/frontend/package-lock.json
index 2e77e36a..1ff3216c 100644
--- a/frontend/package-lock.json
+++ b/frontend/package-lock.json
@@ -11,62 +11,100 @@
"@monaco-editor/react": "^4.7.0",
"@stomp/stompjs": "^7.3.0",
"lucide-react": "1.14.0",
- "next": "16.2.6",
- "react": "19.2.5",
- "react-dom": "19.2.5",
+ "next": "16.2.10",
+ "react": "19.2.7",
+ "react-dom": "19.2.7",
"sockjs-client": "^1.6.1"
},
"devDependencies": {
"@axe-core/playwright": "^4.10.0",
"@next/bundle-analyzer": "^16.2.6",
- "@playwright/test": "1.57.0",
+ "@playwright/test": "1.60.0",
"@testing-library/dom": "^10.4.0",
"@testing-library/react": "^16.3.0",
"@types/jsdom": "^28.0.3",
"@types/node": "24.10.2",
- "@types/react": "19.2.14",
+ "@types/react": "19.2.17",
"@types/react-dom": "19.2.3",
"@types/sockjs-client": "^1.5.4",
- "fast-check": "^3.23.0",
- "jsdom": "^25.0.1",
+ "fast-check": "^4.8.0",
+ "jsdom": "^29.1.1",
+ "playwright-core": "1.60.0",
"typescript": "6.0.3"
}
},
"node_modules/@asamuzakjp/css-color": {
- "version": "3.2.0",
- "resolved": "https://registry.npmjs.org/@asamuzakjp/css-color/-/css-color-3.2.0.tgz",
- "integrity": "sha512-K1A6z8tS3XsmCMM86xoWdn7Fkdn9m6RSVtocUrJYIwZnFVkng/PvkEoWtOWmP+Scc6saYWHWZYbndEEXxl24jw==",
+ "version": "5.1.11",
+ "resolved": "https://registry.npmjs.org/@asamuzakjp/css-color/-/css-color-5.1.11.tgz",
+ "integrity": "sha512-KVw6qIiCTUQhByfTd78h2yD1/00waTmm9uy/R7Ck/ctUyAPj+AEDLkQIdJW0T8+qGgj3j5bpNKK7Q3G+LedJWg==",
"dev": true,
"license": "MIT",
"dependencies": {
- "@csstools/css-calc": "^2.1.3",
- "@csstools/css-color-parser": "^3.0.9",
- "@csstools/css-parser-algorithms": "^3.0.4",
- "@csstools/css-tokenizer": "^3.0.3",
- "lru-cache": "^10.4.3"
+ "@asamuzakjp/generational-cache": "^1.0.1",
+ "@csstools/css-calc": "^3.2.0",
+ "@csstools/css-color-parser": "^4.1.0",
+ "@csstools/css-parser-algorithms": "^4.0.0",
+ "@csstools/css-tokenizer": "^4.0.0"
+ },
+ "engines": {
+ "node": "^20.19.0 || ^22.12.0 || >=24.0.0"
+ }
+ },
+ "node_modules/@asamuzakjp/dom-selector": {
+ "version": "7.1.1",
+ "resolved": "https://registry.npmjs.org/@asamuzakjp/dom-selector/-/dom-selector-7.1.1.tgz",
+ "integrity": "sha512-67RZDnYRc8H/8MLDgQCDE//zoqVFwajkepHZgmXrbwybzXOEwOWGPYGmALYl9J2DOLfFPPs6kKCqmbzV895hTQ==",
+ "dev": true,
+ "license": "MIT",
+ "dependencies": {
+ "@asamuzakjp/generational-cache": "^1.0.1",
+ "@asamuzakjp/nwsapi": "^2.3.9",
+ "bidi-js": "^1.0.3",
+ "css-tree": "^3.2.1",
+ "is-potential-custom-element-name": "^1.0.1"
+ },
+ "engines": {
+ "node": "^20.19.0 || ^22.12.0 || >=24.0.0"
}
},
+ "node_modules/@asamuzakjp/generational-cache": {
+ "version": "1.0.1",
+ "resolved": "https://registry.npmjs.org/@asamuzakjp/generational-cache/-/generational-cache-1.0.1.tgz",
+ "integrity": "sha512-wajfB8KqzMCN2KGNFdLkReeHncd0AslUSrvHVvvYWuU8ghncRJoA50kT3zP9MVL0+9g4/67H+cdvBskj9THPzg==",
+ "dev": true,
+ "license": "MIT",
+ "engines": {
+ "node": "^20.19.0 || ^22.12.0 || >=24.0.0"
+ }
+ },
+ "node_modules/@asamuzakjp/nwsapi": {
+ "version": "2.3.9",
+ "resolved": "https://registry.npmjs.org/@asamuzakjp/nwsapi/-/nwsapi-2.3.9.tgz",
+ "integrity": "sha512-n8GuYSrI9bF7FFZ/SjhwevlHc8xaVlb/7HmHelnc/PZXBD2ZR49NnN9sMMuDdEGPeeRQ5d0hqlSlEpgCX3Wl0Q==",
+ "dev": true,
+ "license": "MIT"
+ },
"node_modules/@axe-core/playwright": {
- "version": "4.11.3",
- "resolved": "https://registry.npmjs.org/@axe-core/playwright/-/playwright-4.11.3.tgz",
- "integrity": "sha512-h/kfksv4F0cVIDlKpT4700OehdRgpvuVskuQ2nb7/JmtWUXpe9ftHAPtwyXGvVSsa6SJ64A9ER7Zrzc/sIvC4w==",
+ "version": "4.12.1",
+ "resolved": "https://registry.npmjs.org/@axe-core/playwright/-/playwright-4.12.1.tgz",
+ "integrity": "sha512-rMd7xriptqKpP+w5265i4Hdkv2X5kbu6uiBi/B2I7uf3hieRBM3qDCfaKPtxfiYb2mKXfF+yLODJwIx+Jv1GDw==",
"dev": true,
"license": "MPL-2.0",
"dependencies": {
- "axe-core": "~4.11.4"
+ "axe-core": "~4.12.1"
},
"peerDependencies": {
"playwright-core": ">= 1.0.0"
}
},
"node_modules/@babel/code-frame": {
- "version": "7.29.0",
- "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.29.0.tgz",
- "integrity": "sha512-9NhCeYjq9+3uxgdtp20LSiJXJvN0FeCtNGpJxuMFZ1Kv3cWUNb6DOhJwUvcVCzKGR66cw4njwM6hrJLqgOwbcw==",
+ "version": "7.29.7",
+ "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.29.7.tgz",
+ "integrity": "sha512-Aup7aUOfpbAUg2ROOJN6Iw5f9DMBlzu0mIkm/malLQFN/YQgO48wCj0Kxa3sEHJvPVFg7siR+qRInwXd2qhQKw==",
"dev": true,
"license": "MIT",
"dependencies": {
- "@babel/helper-validator-identifier": "^7.28.5",
+ "@babel/helper-validator-identifier": "^7.29.7",
"js-tokens": "^4.0.0",
"picocolors": "^1.1.1"
},
@@ -75,9 +113,9 @@
}
},
"node_modules/@babel/helper-validator-identifier": {
- "version": "7.28.5",
- "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.28.5.tgz",
- "integrity": "sha512-qSs4ifwzKJSV39ucNjsvc6WVHs6b7S03sOh2OcHF9UHfVPqWWALUsNUVzhSBiItjRZoLHx7nIarVjqKVusUZ1Q==",
+ "version": "7.29.7",
+ "resolved": "https://registry.npmjs.org/@babel/helper-validator-identifier/-/helper-validator-identifier-7.29.7.tgz",
+ "integrity": "sha512-qehxGkRj55h/ff8EMaJ+cYhyaKlHIxqYDn682wQD7RNp9UujOQsHog2uS0r2vzr4pW+sXf90NeeayjcNaX3fFg==",
"dev": true,
"license": "MIT",
"engines": {
@@ -85,19 +123,32 @@
}
},
"node_modules/@babel/runtime": {
- "version": "7.29.2",
- "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.29.2.tgz",
- "integrity": "sha512-JiDShH45zKHWyGe4ZNVRrCjBz8Nh9TMmZG1kh4QTK8hCBTWBi8Da+i7s1fJw7/lYpM4ccepSNfqzZ/QvABBi5g==",
+ "version": "7.29.7",
+ "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.29.7.tgz",
+ "integrity": "sha512-Nq8OhGWiZIZGV6hLHoyAKLLcJihP/xFeBMGJoUrxTX2psI8dCifzLhZISFb+VWS3wFMRDmCGw5R+dOySCqPLhw==",
"dev": true,
"license": "MIT",
"engines": {
"node": ">=6.9.0"
}
},
+ "node_modules/@bramus/specificity": {
+ "version": "2.4.2",
+ "resolved": "https://registry.npmjs.org/@bramus/specificity/-/specificity-2.4.2.tgz",
+ "integrity": "sha512-ctxtJ/eA+t+6q2++vj5j7FYX3nRu311q1wfYH3xjlLOsczhlhxAg2FWNUXhpGvAw3BWo1xBcvOV6/YLc2r5FJw==",
+ "dev": true,
+ "license": "MIT",
+ "dependencies": {
+ "css-tree": "^3.0.0"
+ },
+ "bin": {
+ "specificity": "bin/cli.js"
+ }
+ },
"node_modules/@csstools/color-helpers": {
- "version": "5.1.0",
- "resolved": "https://registry.npmjs.org/@csstools/color-helpers/-/color-helpers-5.1.0.tgz",
- "integrity": "sha512-S11EXWJyy0Mz5SYvRmY8nJYTFFd1LCNV+7cXyAgQtOOuzb4EsgfqDufL+9esx72/eLhsRdGZwaldu/h+E4t4BA==",
+ "version": "6.1.0",
+ "resolved": "https://registry.npmjs.org/@csstools/color-helpers/-/color-helpers-6.1.0.tgz",
+ "integrity": "sha512-064IFJdjTfUqnjpCVpMOdbr8FLQBhinbZj6yRv2An2E41O/pLEXqfFRWqGq/SxlE5PEUYTlvWsG2r8MswAVvkg==",
"dev": true,
"funding": [
{
@@ -111,13 +162,13 @@
],
"license": "MIT-0",
"engines": {
- "node": ">=18"
+ "node": ">=20.19.0"
}
},
"node_modules/@csstools/css-calc": {
- "version": "2.1.4",
- "resolved": "https://registry.npmjs.org/@csstools/css-calc/-/css-calc-2.1.4.tgz",
- "integrity": "sha512-3N8oaj+0juUw/1H3YwmDDJXCgTB1gKU6Hc/bB502u9zR0q2vd786XJH9QfrKIEgFlZmhZiq6epXl4rHqhzsIgQ==",
+ "version": "3.2.1",
+ "resolved": "https://registry.npmjs.org/@csstools/css-calc/-/css-calc-3.2.1.tgz",
+ "integrity": "sha512-DtdHlgXh5ZkA43cwBcAm+huzgJiwx3ZTWVjBs94kwz2xKqSimDA3lBgCjphYgwgVUMWatSM0pDd8TILB1yrVVg==",
"dev": true,
"funding": [
{
@@ -131,17 +182,17 @@
],
"license": "MIT",
"engines": {
- "node": ">=18"
+ "node": ">=20.19.0"
},
"peerDependencies": {
- "@csstools/css-parser-algorithms": "^3.0.5",
- "@csstools/css-tokenizer": "^3.0.4"
+ "@csstools/css-parser-algorithms": "^4.0.0",
+ "@csstools/css-tokenizer": "^4.0.0"
}
},
"node_modules/@csstools/css-color-parser": {
- "version": "3.1.0",
- "resolved": "https://registry.npmjs.org/@csstools/css-color-parser/-/css-color-parser-3.1.0.tgz",
- "integrity": "sha512-nbtKwh3a6xNVIp/VRuXV64yTKnb1IjTAEEh3irzS+HkKjAOYLTGNb9pmVNntZ8iVBHcWDA2Dof0QtPgFI1BaTA==",
+ "version": "4.1.9",
+ "resolved": "https://registry.npmjs.org/@csstools/css-color-parser/-/css-color-parser-4.1.9.tgz",
+ "integrity": "sha512-paQcIaOO53Rk5+YrBaBjm/SgrV4INImjo2BT1DtQRYr+XeTRbeAYlS+jxXp9drqvKmtFnWRJKIalDLhZZDu42A==",
"dev": true,
"funding": [
{
@@ -155,21 +206,21 @@
],
"license": "MIT",
"dependencies": {
- "@csstools/color-helpers": "^5.1.0",
- "@csstools/css-calc": "^2.1.4"
+ "@csstools/color-helpers": "^6.1.0",
+ "@csstools/css-calc": "^3.2.1"
},
"engines": {
- "node": ">=18"
+ "node": ">=20.19.0"
},
"peerDependencies": {
- "@csstools/css-parser-algorithms": "^3.0.5",
- "@csstools/css-tokenizer": "^3.0.4"
+ "@csstools/css-parser-algorithms": "^4.0.0",
+ "@csstools/css-tokenizer": "^4.0.0"
}
},
"node_modules/@csstools/css-parser-algorithms": {
- "version": "3.0.5",
- "resolved": "https://registry.npmjs.org/@csstools/css-parser-algorithms/-/css-parser-algorithms-3.0.5.tgz",
- "integrity": "sha512-DaDeUkXZKjdGhgYaHNJTV9pV7Y9B3b644jCLs9Upc3VeNGg6LWARAT6O+Q+/COo+2gg/bM5rhpMAtf70WqfBdQ==",
+ "version": "4.0.0",
+ "resolved": "https://registry.npmjs.org/@csstools/css-parser-algorithms/-/css-parser-algorithms-4.0.0.tgz",
+ "integrity": "sha512-+B87qS7fIG3L5h3qwJ/IFbjoVoOe/bpOdh9hAjXbvx0o8ImEmUsGXN0inFOnk2ChCFgqkkGFQ+TpM5rbhkKe4w==",
"dev": true,
"funding": [
{
@@ -184,16 +235,41 @@
"license": "MIT",
"peer": true,
"engines": {
- "node": ">=18"
+ "node": ">=20.19.0"
},
"peerDependencies": {
- "@csstools/css-tokenizer": "^3.0.4"
+ "@csstools/css-tokenizer": "^4.0.0"
+ }
+ },
+ "node_modules/@csstools/css-syntax-patches-for-csstree": {
+ "version": "1.1.6",
+ "resolved": "https://registry.npmjs.org/@csstools/css-syntax-patches-for-csstree/-/css-syntax-patches-for-csstree-1.1.6.tgz",
+ "integrity": "sha512-TcJCWFbXLPpJYq6z7bfOyjWYJDiDg2/I4gyUC9pqPNqHFRIey0EB0q0L5cSnQDfWJg8Jd6VadakxdIez/3zkqQ==",
+ "dev": true,
+ "funding": [
+ {
+ "type": "github",
+ "url": "https://github.com/sponsors/csstools"
+ },
+ {
+ "type": "opencollective",
+ "url": "https://opencollective.com/csstools"
+ }
+ ],
+ "license": "MIT-0",
+ "peerDependencies": {
+ "css-tree": "^3.2.1"
+ },
+ "peerDependenciesMeta": {
+ "css-tree": {
+ "optional": true
+ }
}
},
"node_modules/@csstools/css-tokenizer": {
- "version": "3.0.4",
- "resolved": "https://registry.npmjs.org/@csstools/css-tokenizer/-/css-tokenizer-3.0.4.tgz",
- "integrity": "sha512-Vd/9EVDiu6PPJt9yAh6roZP6El1xHrdvIVGjyBsHR0RYwNHgL7FJPyIIW4fANJNG6FtyZfvlRPpFI4ZM/lubvw==",
+ "version": "4.0.0",
+ "resolved": "https://registry.npmjs.org/@csstools/css-tokenizer/-/css-tokenizer-4.0.0.tgz",
+ "integrity": "sha512-QxULHAm7cNu72w97JUNCBFODFaXpbDg+dP8b/oWFAZ2MTRppA3U00Y2L1HqaS4J6yBqxwa/Y3nMBaxVKbB/NsA==",
"dev": true,
"funding": [
{
@@ -208,7 +284,7 @@
"license": "MIT",
"peer": true,
"engines": {
- "node": ">=18"
+ "node": ">=20.19.0"
}
},
"node_modules/@discoveryjs/json-ext": {
@@ -222,15 +298,33 @@
}
},
"node_modules/@emnapi/runtime": {
- "version": "1.10.0",
- "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.10.0.tgz",
- "integrity": "sha512-ewvYlk86xUoGI0zQRNq/mC+16R1QeDlKQy21Ki3oSYXNgLb45GV1P6A0M+/s6nyCuNDqe5VpaY84BzXGwVbwFA==",
+ "version": "1.11.2",
+ "resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.11.2.tgz",
+ "integrity": "sha512-kyOl3X0DuTiT1h2ft8r2fYO8JYtU9a9Xis/zBSiGArNaagCOWx90N1k2wxp18czFDH+OgcWGb5ZP/XMt3dcyPA==",
"license": "MIT",
"optional": true,
"dependencies": {
"tslib": "^2.4.0"
}
},
+ "node_modules/@exodus/bytes": {
+ "version": "1.15.1",
+ "resolved": "https://registry.npmjs.org/@exodus/bytes/-/bytes-1.15.1.tgz",
+ "integrity": "sha512-S6mL0yNB/Abt9Ei4tq8gDhcczc4S3+vQ4ra7vxnAf+YHC02srtqxKKZghx2Dq6p0e66THKwR6r8N6P95wEty7Q==",
+ "dev": true,
+ "license": "MIT",
+ "engines": {
+ "node": "^20.19.0 || ^22.12.0 || >=24.0.0"
+ },
+ "peerDependencies": {
+ "@noble/hashes": "^1.8.0 || ^2.0.0"
+ },
+ "peerDependenciesMeta": {
+ "@noble/hashes": {
+ "optional": true
+ }
+ }
+ },
"node_modules/@img/colour": {
"version": "1.1.0",
"resolved": "https://registry.npmjs.org/@img/colour/-/colour-1.1.0.tgz",
@@ -721,9 +815,9 @@
}
},
"node_modules/@next/bundle-analyzer": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/bundle-analyzer/-/bundle-analyzer-16.2.6.tgz",
- "integrity": "sha512-amPkVtHCTJAdBwyhhl5+qztHk24O4JlASgrWqh15AmnYi74apfZR46NGC0u4pM6BMAU1mYld4WdzD3cRBP3dOA==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/bundle-analyzer/-/bundle-analyzer-16.2.10.tgz",
+ "integrity": "sha512-KcepWhb3IVniZgm00GSSCQDEUQqZXuXtuXRh8J6e3Un342TcQ77iK4DedeEkct+fcx7yFEDL2J6z4Jeho5JDAw==",
"dev": true,
"license": "MIT",
"dependencies": {
@@ -731,15 +825,15 @@
}
},
"node_modules/@next/env": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/env/-/env-16.2.6.tgz",
- "integrity": "sha512-gd8HoHN4ufj73WmR3JmVolrpJR47ILK6LouP5xElPglaVxir6e1a7VzvTvDWkOoPXT9rkkTzyCxBu4yeZfZwcw==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/env/-/env-16.2.10.tgz",
+ "integrity": "sha512-zLPxg9M0MEHmygpj5OuxjQ+vHMiy/K7cSp74G8ecYolmgUWw0RwN02tF56npup/+qaI8JB97hQgS/r2Hb6QwVA==",
"license": "MIT"
},
"node_modules/@next/swc-darwin-arm64": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-16.2.6.tgz",
- "integrity": "sha512-ZJGkkcNfYgrrMkqOdZ7zoLa1TOy0qpcMfk/z4Mh/FKUz40gVO+HNQWqmLxf67Z5WB64DRp0dhEbyHfel+6sJUg==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/swc-darwin-arm64/-/swc-darwin-arm64-16.2.10.tgz",
+ "integrity": "sha512-v9IdJCa0H0mbo+8z5zwUpOk1Vj7RjkcI5uNYf5Ws1y6szf/p3Mzl9hLaST8SCt6L9h8NGnruZcd2+o0NTNwDhA==",
"cpu": [
"arm64"
],
@@ -753,9 +847,9 @@
}
},
"node_modules/@next/swc-darwin-x64": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-16.2.6.tgz",
- "integrity": "sha512-v/YLBHIY132Ced3puBJ7YJKw1lqsCrgcNo2aRJlCEyQrrCeRJlvGlnmxhPxNQI3KE3N1DN5r9TPNPvka3nq5RQ==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/swc-darwin-x64/-/swc-darwin-x64-16.2.10.tgz",
+ "integrity": "sha512-17IS0jJRViROGmA9uGdNR8VPJpfbnaVG7E9qhso5jDLkmyd0lSDORWxbcKINzcFqzZqGwGtMSnrFRxBpuUYjLQ==",
"cpu": [
"x64"
],
@@ -769,9 +863,9 @@
}
},
"node_modules/@next/swc-linux-arm64-gnu": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-16.2.6.tgz",
- "integrity": "sha512-RPOvqlYBbcQjkz9VQQDZ2T2bARIjXZV1KFlt+V2Mr6SW/e4I9fcKsaA0hdyf2FHoTlsV2xnBd5Y912rP/1Ce6w==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-gnu/-/swc-linux-arm64-gnu-16.2.10.tgz",
+ "integrity": "sha512-GRQRsRtuciNJvB54AvvuQTiq0oZtFwa1owQqtZD8wwnGpM2L39MV22kpI72YSXLKIyY40LC66EiLFv4PiicXxg==",
"cpu": [
"arm64"
],
@@ -785,9 +879,9 @@
}
},
"node_modules/@next/swc-linux-arm64-musl": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-16.2.6.tgz",
- "integrity": "sha512-URUTu1+dMkxJsPFgm+OeEvq9wf5sujw0EvgYy80TDGHTSLTnIHeqb0Eu8A3sC95IRgjejQL+kC4mw+4yPxiAXA==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/swc-linux-arm64-musl/-/swc-linux-arm64-musl-16.2.10.tgz",
+ "integrity": "sha512-zkN9MQYS7UQBro+FnISUq1itaQjXI9xqISzuQ+2bc921NcJ1x4yPCqrn77tVN6/dOOXaaWVX3k6/bR07pPwK+A==",
"cpu": [
"arm64"
],
@@ -801,9 +895,9 @@
}
},
"node_modules/@next/swc-linux-x64-gnu": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-16.2.6.tgz",
- "integrity": "sha512-DOj182mPV8G3UkrayLoREM5YEYI+Dk5wv7Ox9xl1fFibAELEsFD0lDPfHIeILlutMMfdyhlzYPELG3peuKaurw==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-gnu/-/swc-linux-x64-gnu-16.2.10.tgz",
+ "integrity": "sha512-iCVJnwvrPYECvA6WM/7+oo+OiTvedIKLxtCLAZP4xZR3nXa1zmzZyLPbYCmWvpd4CvMYF1EMTafd0ii3DygLvA==",
"cpu": [
"x64"
],
@@ -817,9 +911,9 @@
}
},
"node_modules/@next/swc-linux-x64-musl": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-16.2.6.tgz",
- "integrity": "sha512-HKQ5SP/V/ub73UvF7n/zeJlxk2kLmtL7Wzrg4WfmkjmNos5onJ2tKu7yZOPdL18A6Svfn3max29ym+ry7NkK4g==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/swc-linux-x64-musl/-/swc-linux-x64-musl-16.2.10.tgz",
+ "integrity": "sha512-ov2g4H0dHY9bPoOU83m91hWT7Iq5qy13bUnyyshLU3HGR1Ownn0X9QpmDPc5iIUaahTp7f7LeGAhV4DSFtackw==",
"cpu": [
"x64"
],
@@ -833,9 +927,9 @@
}
},
"node_modules/@next/swc-win32-arm64-msvc": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-16.2.6.tgz",
- "integrity": "sha512-LZXpTlPyS5v7HhSmnvsLGP3iIYgYOBnc8r8ArlT55sGHV89bR2HlDdBjWQ+PY6SJMmk8TuVGFuxalnP3k/0Dwg==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/swc-win32-arm64-msvc/-/swc-win32-arm64-msvc-16.2.10.tgz",
+ "integrity": "sha512-DwAnhLX76HQiFFQNgWlcK+JzlnD1rZ+UK/WY0ZMI/deXpvgnesjNYrqcfo1JzBuz4Kf7o3brIBL0glI1junatA==",
"cpu": [
"arm64"
],
@@ -849,9 +943,9 @@
}
},
"node_modules/@next/swc-win32-x64-msvc": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-16.2.6.tgz",
- "integrity": "sha512-F0+4i0h9J6C4eE3EAPWsoCk7UW/dbzOjyzxY0qnDUOYFu6FFmdZ6l97/XdV3/Nz3VYyO7UWjyEJUXkGqcoXfMA==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/@next/swc-win32-x64-msvc/-/swc-win32-x64-msvc-16.2.10.tgz",
+ "integrity": "sha512-0JXq3b85Jk9Jg4ntLUbXSPvoDw3gpZou7twuKdoFG2jOw635v7+IiXfTaa0TxVMyx78pUjnrVYwLgjKfX4e6/A==",
"cpu": [
"x64"
],
@@ -865,14 +959,14 @@
}
},
"node_modules/@playwright/test": {
- "version": "1.57.0",
- "resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.57.0.tgz",
- "integrity": "sha512-6TyEnHgd6SArQO8UO2OMTxshln3QMWBtPGrOCgs3wVEmQmwyuNtB10IZMfmYDE0riwNR1cu4q+pPcxMVtaG3TA==",
+ "version": "1.60.0",
+ "resolved": "https://registry.npmjs.org/@playwright/test/-/test-1.60.0.tgz",
+ "integrity": "sha512-O71yZIbAh/PxDMNGns37GHBIfrVkEVyn+AXyIa5dOTfb4/xNvRWV+Vv/NMbNCtODB/pO7vLlF2OTmMVLhmr7Ag==",
"devOptional": true,
"license": "Apache-2.0",
"peer": true,
"dependencies": {
- "playwright": "1.57.0"
+ "playwright": "1.60.0"
},
"bin": {
"playwright": "cli.js"
@@ -972,39 +1066,6 @@
"undici-types": "^7.21.0"
}
},
- "node_modules/@types/jsdom/node_modules/entities": {
- "version": "8.0.0",
- "resolved": "https://registry.npmjs.org/entities/-/entities-8.0.0.tgz",
- "integrity": "sha512-zwfzJecQ/Uej6tusMqwAqU/6KL2XaB2VZ2Jg54Je6ahNBGNH6Ek6g3jjNCF0fG9EWQKGZNddNjU5F1ZQn/sBnA==",
- "dev": true,
- "license": "BSD-2-Clause",
- "engines": {
- "node": ">=20.19.0"
- },
- "funding": {
- "url": "https://github.com/fb55/entities?sponsor=1"
- }
- },
- "node_modules/@types/jsdom/node_modules/parse5": {
- "version": "8.0.1",
- "resolved": "https://registry.npmjs.org/parse5/-/parse5-8.0.1.tgz",
- "integrity": "sha512-z1e/HMG90obSGeidlli3hj7cbocou0/wa5HacvI3ASx34PecNjNQeaHNo5WIZpWofN9kgkqV1q5YvXe3F0FoPw==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "entities": "^8.0.0"
- },
- "funding": {
- "url": "https://github.com/inikulin/parse5?sponsor=1"
- }
- },
- "node_modules/@types/jsdom/node_modules/undici-types": {
- "version": "7.25.0",
- "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.25.0.tgz",
- "integrity": "sha512-AXNgS1Byr27fTI+2bsPEkV9CxkT8H6xNyRI68b3TatlZo3RkzlqQBLL+w7SmGPVpokjHbcuNVQUWE7FRTg+LRA==",
- "dev": true,
- "license": "MIT"
- },
"node_modules/@types/node": {
"version": "24.10.2",
"resolved": "https://registry.npmjs.org/@types/node/-/node-24.10.2.tgz",
@@ -1015,10 +1076,17 @@
"undici-types": "~7.16.0"
}
},
+ "node_modules/@types/node/node_modules/undici-types": {
+ "version": "7.16.0",
+ "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.16.0.tgz",
+ "integrity": "sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw==",
+ "dev": true,
+ "license": "MIT"
+ },
"node_modules/@types/react": {
- "version": "19.2.14",
- "resolved": "https://registry.npmjs.org/@types/react/-/react-19.2.14.tgz",
- "integrity": "sha512-ilcTH/UniCkMdtexkoCN0bI7pMcJDvmQFPvuPvmEaYA/NSfFTAgdUSLAoVjaRJm7+6PvcM+q1zYOwS4wTYMF9w==",
+ "version": "19.2.17",
+ "resolved": "https://registry.npmjs.org/@types/react/-/react-19.2.17.tgz",
+ "integrity": "sha512-MXfmqaVPEVgkBT/aY0aGCkRWWtByiYQXo3xdQ8r5RzuFrPiRn8Gar2tQdXSUQ2GKV3bkXckek89V8wQBY2Q/Aw==",
"dev": true,
"license": "MIT",
"peer": true,
@@ -1059,9 +1127,9 @@
"optional": true
},
"node_modules/acorn": {
- "version": "8.16.0",
- "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.16.0.tgz",
- "integrity": "sha512-UVJyE9MttOsBQIDKw1skb9nAwQuR5wuGD3+82K6JgJlm/Y+KI92oNsMNGZCYdDsVtRHSak0pcV5Dno5+4jh9sw==",
+ "version": "8.17.0",
+ "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.17.0.tgz",
+ "integrity": "sha512-xRQbDb9BnwDafYNn6Vwl839DYVjqXYb1XVGtWAZ1kcDc6iwAL4hg3B1dZlRiuENFeO2H53gFG3in621AdERVAg==",
"dev": true,
"license": "MIT",
"bin": {
@@ -1084,16 +1152,6 @@
"node": ">=0.4.0"
}
},
- "node_modules/agent-base": {
- "version": "7.1.4",
- "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.4.tgz",
- "integrity": "sha512-MnA+YT8fwfJPgBx3m60MNqakm30XOkyIoH1y6huTQvC0PwZG7ki8NacLBcrPbNoo8vEZy7Jpuk7+jMO+CUovTQ==",
- "dev": true,
- "license": "MIT",
- "engines": {
- "node": ">= 14"
- }
- },
"node_modules/ansi-regex": {
"version": "5.0.1",
"resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-5.0.1.tgz",
@@ -1127,17 +1185,10 @@
"dequal": "^2.0.3"
}
},
- "node_modules/asynckit": {
- "version": "0.4.0",
- "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz",
- "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==",
- "dev": true,
- "license": "MIT"
- },
"node_modules/axe-core": {
- "version": "4.11.4",
- "resolved": "https://registry.npmjs.org/axe-core/-/axe-core-4.11.4.tgz",
- "integrity": "sha512-KunSNx+TVpkAw/6ULfhnx+HWRecjqZGTOyquAoWHYLRSdK1tB5Ihce1ZW+UY3fj33bYAFWPu7W/GRSmmrCGuxA==",
+ "version": "4.12.1",
+ "resolved": "https://registry.npmjs.org/axe-core/-/axe-core-4.12.1.tgz",
+ "integrity": "sha512-s7iGf5GaVMxEG0ENN9x+xTr7GFZCb1ZP/1uATUpCEK2X78nDB3RwbtFCo9pGAf9ru+VwoQ464DkaLEeRM08wJA==",
"dev": true,
"license": "MPL-2.0",
"engines": {
@@ -1145,9 +1196,9 @@
}
},
"node_modules/baseline-browser-mapping": {
- "version": "2.10.25",
- "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.10.25.tgz",
- "integrity": "sha512-QO/VHsXCQdnzADMfmkeOPvHdIAkoB7i0/rGjINPJEetLx75hNttVWGQ/jycHUDP9zZ9rupbm60WRxcwViB0MiA==",
+ "version": "2.10.43",
+ "resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.10.43.tgz",
+ "integrity": "sha512-AjYpR78kDWAY3Efj+cDTFH9t9SCoL7OoTp1BOb0mQV7S+6CiLwnWM3FyxhJtdPufDFKzmCSFoUncKjWgJEZTCQ==",
"license": "Apache-2.0",
"bin": {
"baseline-browser-mapping": "dist/cli.cjs"
@@ -1156,24 +1207,20 @@
"node": ">=6.0.0"
}
},
- "node_modules/call-bind-apply-helpers": {
- "version": "1.0.2",
- "resolved": "https://registry.npmjs.org/call-bind-apply-helpers/-/call-bind-apply-helpers-1.0.2.tgz",
- "integrity": "sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==",
+ "node_modules/bidi-js": {
+ "version": "1.0.3",
+ "resolved": "https://registry.npmjs.org/bidi-js/-/bidi-js-1.0.3.tgz",
+ "integrity": "sha512-RKshQI1R3YQ+n9YJz2QQ147P66ELpa1FQEg20Dk8oW9t2KgLbpDLLp9aGZ7y8WHSshDknG0bknqGw5/tyCs5tw==",
"dev": true,
"license": "MIT",
"dependencies": {
- "es-errors": "^1.3.0",
- "function-bind": "^1.1.2"
- },
- "engines": {
- "node": ">= 0.4"
+ "require-from-string": "^2.0.2"
}
},
"node_modules/caniuse-lite": {
- "version": "1.0.30001791",
- "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001791.tgz",
- "integrity": "sha512-yk0l/YSrOnFZk3UROpDLQD9+kC1l4meK/wed583AXrzoarMGJcbRi2Q4RaUYbKxYAsZ8sWmaSa/DsLmdBeI1vQ==",
+ "version": "1.0.30001805",
+ "resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001805.tgz",
+ "integrity": "sha512-52noaS3DubycKSXaU30TwPGIp+POyQSUVa5jBEq3vkRkY0kjyb3LQgvhU6WGyCcyXqVLWO0Cw0Q6BSdD0kUfVA==",
"funding": [
{
"type": "opencollective",
@@ -1196,19 +1243,6 @@
"integrity": "sha512-IV3Ou0jSMzZrd3pZ48nLkT9DA7Ag1pnPzaiQhpW7c3RbcqqzvzzVu+L8gfqMp/8IM2MQtSiqaCxrrcfu8I8rMA==",
"license": "MIT"
},
- "node_modules/combined-stream": {
- "version": "1.0.8",
- "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz",
- "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "delayed-stream": "~1.0.0"
- },
- "engines": {
- "node": ">= 0.8"
- }
- },
"node_modules/commander": {
"version": "7.2.0",
"resolved": "https://registry.npmjs.org/commander/-/commander-7.2.0.tgz",
@@ -1219,27 +1253,20 @@
"node": ">= 10"
}
},
- "node_modules/cssstyle": {
- "version": "4.6.0",
- "resolved": "https://registry.npmjs.org/cssstyle/-/cssstyle-4.6.0.tgz",
- "integrity": "sha512-2z+rWdzbbSZv6/rhtvzvqeZQHrBaqgogqt85sqFNbabZOuFbCVFb8kPeEtZjiKkbrm395irpNKiYeFeLiQnFPg==",
+ "node_modules/css-tree": {
+ "version": "3.2.1",
+ "resolved": "https://registry.npmjs.org/css-tree/-/css-tree-3.2.1.tgz",
+ "integrity": "sha512-X7sjQzceUhu1u7Y/ylrRZFU2FS6LRiFVp6rKLPg23y3x3c3DOKAwuXGDp+PAGjh6CSnCjYeAul8pcT8bAl+lSA==",
"dev": true,
"license": "MIT",
"dependencies": {
- "@asamuzakjp/css-color": "^3.2.0",
- "rrweb-cssom": "^0.8.0"
+ "mdn-data": "2.27.1",
+ "source-map-js": "^1.2.1"
},
"engines": {
- "node": ">=18"
+ "node": "^10 || ^12.20.0 || ^14.13.0 || >=15.0.0"
}
},
- "node_modules/cssstyle/node_modules/rrweb-cssom": {
- "version": "0.8.0",
- "resolved": "https://registry.npmjs.org/rrweb-cssom/-/rrweb-cssom-0.8.0.tgz",
- "integrity": "sha512-guoltQEx+9aMf2gDZ0s62EcV8lsXR+0w8915TC3ITdn2YueuNjdAYh/levpU9nFaoChh9RUS5ZdQMrKfVEN9tw==",
- "dev": true,
- "license": "MIT"
- },
"node_modules/csstype": {
"version": "3.2.3",
"resolved": "https://registry.npmjs.org/csstype/-/csstype-3.2.3.tgz",
@@ -1248,17 +1275,17 @@
"license": "MIT"
},
"node_modules/data-urls": {
- "version": "5.0.0",
- "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-5.0.0.tgz",
- "integrity": "sha512-ZYP5VBHshaDAiVZxjbRVcFJpc+4xGgT0bK3vzy1HLN8jTO975HEbuYzZJcHoQEY5K1a0z8YayJkyVETa08eNTg==",
+ "version": "7.0.0",
+ "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-7.0.0.tgz",
+ "integrity": "sha512-23XHcCF+coGYevirZceTVD7NdJOqVn+49IHyxgszm+JIiHLoB2TkmPtsYkNWT1pvRSGkc35L6NHs0yHkN2SumA==",
"dev": true,
"license": "MIT",
"dependencies": {
- "whatwg-mimetype": "^4.0.0",
- "whatwg-url": "^14.0.0"
+ "whatwg-mimetype": "^5.0.0",
+ "whatwg-url": "^16.0.0"
},
"engines": {
- "node": ">=18"
+ "node": "^20.19.0 || ^22.12.0 || >=24.0.0"
}
},
"node_modules/debounce": {
@@ -1269,21 +1296,12 @@
"license": "MIT"
},
"node_modules/debug": {
- "version": "4.4.3",
- "resolved": "https://registry.npmjs.org/debug/-/debug-4.4.3.tgz",
- "integrity": "sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==",
- "dev": true,
+ "version": "3.2.7",
+ "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz",
+ "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==",
"license": "MIT",
"dependencies": {
- "ms": "^2.1.3"
- },
- "engines": {
- "node": ">=6.0"
- },
- "peerDependenciesMeta": {
- "supports-color": {
- "optional": true
- }
+ "ms": "^2.1.1"
}
},
"node_modules/decimal.js": {
@@ -1293,16 +1311,6 @@
"dev": true,
"license": "MIT"
},
- "node_modules/delayed-stream": {
- "version": "1.0.0",
- "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz",
- "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==",
- "dev": true,
- "license": "MIT",
- "engines": {
- "node": ">=0.4.0"
- }
- },
"node_modules/dequal": {
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz",
@@ -1331,29 +1339,14 @@
"license": "MIT"
},
"node_modules/dompurify": {
- "version": "3.4.2",
- "resolved": "https://registry.npmjs.org/dompurify/-/dompurify-3.4.2.tgz",
- "integrity": "sha512-lHeS9SA/IKeIFFyYciHBr2n0v1VMPlSj843HdLOwjb2OxNwdq9Xykxqhk+FE42MzAdHvInbAolSE4mhahPpjXA==",
+ "version": "3.4.12",
+ "resolved": "https://registry.npmjs.org/dompurify/-/dompurify-3.4.12.tgz",
+ "integrity": "sha512-zQvGet8Z2sWbQhCmfFz/T5QWH2oBmjnqK3qvOjaqaNLrLEF912WamU+ohnTp0TCep/MFVHpdJuCZEdFOdTnEFg==",
"license": "(MPL-2.0 OR Apache-2.0)",
"optionalDependencies": {
"@types/trusted-types": "^2.0.7"
}
},
- "node_modules/dunder-proto": {
- "version": "1.0.1",
- "resolved": "https://registry.npmjs.org/dunder-proto/-/dunder-proto-1.0.1.tgz",
- "integrity": "sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "call-bind-apply-helpers": "^1.0.1",
- "es-errors": "^1.3.0",
- "gopd": "^1.2.0"
- },
- "engines": {
- "node": ">= 0.4"
- }
- },
"node_modules/duplexer": {
"version": "0.1.2",
"resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.2.tgz",
@@ -1362,67 +1355,18 @@
"license": "MIT"
},
"node_modules/entities": {
- "version": "6.0.1",
- "resolved": "https://registry.npmjs.org/entities/-/entities-6.0.1.tgz",
- "integrity": "sha512-aN97NXWF6AWBTahfVOIrB/NShkzi5H7F9r1s9mD3cDj4Ko5f2qhhVoYMibXF7GlLveb/D2ioWay8lxI97Ven3g==",
+ "version": "8.0.0",
+ "resolved": "https://registry.npmjs.org/entities/-/entities-8.0.0.tgz",
+ "integrity": "sha512-zwfzJecQ/Uej6tusMqwAqU/6KL2XaB2VZ2Jg54Je6ahNBGNH6Ek6g3jjNCF0fG9EWQKGZNddNjU5F1ZQn/sBnA==",
"dev": true,
"license": "BSD-2-Clause",
"engines": {
- "node": ">=0.12"
+ "node": ">=20.19.0"
},
"funding": {
"url": "https://github.com/fb55/entities?sponsor=1"
}
},
- "node_modules/es-define-property": {
- "version": "1.0.1",
- "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.1.tgz",
- "integrity": "sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==",
- "dev": true,
- "license": "MIT",
- "engines": {
- "node": ">= 0.4"
- }
- },
- "node_modules/es-errors": {
- "version": "1.3.0",
- "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz",
- "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==",
- "dev": true,
- "license": "MIT",
- "engines": {
- "node": ">= 0.4"
- }
- },
- "node_modules/es-object-atoms": {
- "version": "1.1.1",
- "resolved": "https://registry.npmjs.org/es-object-atoms/-/es-object-atoms-1.1.1.tgz",
- "integrity": "sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "es-errors": "^1.3.0"
- },
- "engines": {
- "node": ">= 0.4"
- }
- },
- "node_modules/es-set-tostringtag": {
- "version": "2.1.0",
- "resolved": "https://registry.npmjs.org/es-set-tostringtag/-/es-set-tostringtag-2.1.0.tgz",
- "integrity": "sha512-j6vWzfrGVfyXxge+O0x5sh6cvxAog0a/4Rdd2K36zCMV5eJ+/+tOAngRO8cODMNWbVRdVlmGZQL2YS3yR8bIUA==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "es-errors": "^1.3.0",
- "get-intrinsic": "^1.2.6",
- "has-tostringtag": "^1.0.2",
- "hasown": "^2.0.2"
- },
- "engines": {
- "node": ">= 0.4"
- }
- },
"node_modules/escape-string-regexp": {
"version": "4.0.0",
"resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz",
@@ -1446,9 +1390,9 @@
}
},
"node_modules/fast-check": {
- "version": "3.23.2",
- "resolved": "https://registry.npmjs.org/fast-check/-/fast-check-3.23.2.tgz",
- "integrity": "sha512-h5+1OzzfCC3Ef7VbtKdcv7zsstUQwUDlYpUTvjeUsJAssPgLn7QzbboPtL5ro04Mq0rPOsMzl7q5hIbRs2wD1A==",
+ "version": "4.9.0",
+ "resolved": "https://registry.npmjs.org/fast-check/-/fast-check-4.9.0.tgz",
+ "integrity": "sha512-7ms6T7SybUev/PQITciI0yLM2pOSFy5zpG8Ty7tQofcVaQUvrMXp6CBwqF6fThLCLOrfBtuHAtwq6Yu4XPCllg==",
"dev": true,
"funding": [
{
@@ -1462,10 +1406,10 @@
],
"license": "MIT",
"dependencies": {
- "pure-rand": "^6.1.0"
+ "pure-rand": "^8.0.0"
},
"engines": {
- "node": ">=8.0.0"
+ "node": ">=12.17.0"
}
},
"node_modules/faye-websocket": {
@@ -1480,23 +1424,6 @@
"node": ">=0.8.0"
}
},
- "node_modules/form-data": {
- "version": "4.0.5",
- "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.5.tgz",
- "integrity": "sha512-8RipRLol37bNs2bhoV67fiTEvdTrbMUYcFTiy3+wuuOnUog2QBHCZWXDRijWQfAkhBj2Uf5UnVaiWwA5vdd82w==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "asynckit": "^0.4.0",
- "combined-stream": "^1.0.8",
- "es-set-tostringtag": "^2.1.0",
- "hasown": "^2.0.2",
- "mime-types": "^2.1.12"
- },
- "engines": {
- "node": ">= 6"
- }
- },
"node_modules/fsevents": {
"version": "2.3.2",
"resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.2.tgz",
@@ -1512,68 +1439,6 @@
"node": "^8.16.0 || ^10.6.0 || >=11.0.0"
}
},
- "node_modules/function-bind": {
- "version": "1.1.2",
- "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz",
- "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==",
- "dev": true,
- "license": "MIT",
- "funding": {
- "url": "https://github.com/sponsors/ljharb"
- }
- },
- "node_modules/get-intrinsic": {
- "version": "1.3.0",
- "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.3.0.tgz",
- "integrity": "sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "call-bind-apply-helpers": "^1.0.2",
- "es-define-property": "^1.0.1",
- "es-errors": "^1.3.0",
- "es-object-atoms": "^1.1.1",
- "function-bind": "^1.1.2",
- "get-proto": "^1.0.1",
- "gopd": "^1.2.0",
- "has-symbols": "^1.1.0",
- "hasown": "^2.0.2",
- "math-intrinsics": "^1.1.0"
- },
- "engines": {
- "node": ">= 0.4"
- },
- "funding": {
- "url": "https://github.com/sponsors/ljharb"
- }
- },
- "node_modules/get-proto": {
- "version": "1.0.1",
- "resolved": "https://registry.npmjs.org/get-proto/-/get-proto-1.0.1.tgz",
- "integrity": "sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "dunder-proto": "^1.0.1",
- "es-object-atoms": "^1.0.0"
- },
- "engines": {
- "node": ">= 0.4"
- }
- },
- "node_modules/gopd": {
- "version": "1.2.0",
- "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.2.0.tgz",
- "integrity": "sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==",
- "dev": true,
- "license": "MIT",
- "engines": {
- "node": ">= 0.4"
- },
- "funding": {
- "url": "https://github.com/sponsors/ljharb"
- }
- },
"node_modules/gzip-size": {
"version": "6.0.0",
"resolved": "https://registry.npmjs.org/gzip-size/-/gzip-size-6.0.0.tgz",
@@ -1590,59 +1455,17 @@
"url": "https://github.com/sponsors/sindresorhus"
}
},
- "node_modules/has-symbols": {
- "version": "1.1.0",
- "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.1.0.tgz",
- "integrity": "sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==",
- "dev": true,
- "license": "MIT",
- "engines": {
- "node": ">= 0.4"
- },
- "funding": {
- "url": "https://github.com/sponsors/ljharb"
- }
- },
- "node_modules/has-tostringtag": {
- "version": "1.0.2",
- "resolved": "https://registry.npmjs.org/has-tostringtag/-/has-tostringtag-1.0.2.tgz",
- "integrity": "sha512-NqADB8VjPFLM2V0VvHUewwwsw0ZWBaIdgo+ieHtK3hasLz4qeCRjYcqfB6AQrBggRKppKF8L52/VqdVsO47Dlw==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "has-symbols": "^1.0.3"
- },
- "engines": {
- "node": ">= 0.4"
- },
- "funding": {
- "url": "https://github.com/sponsors/ljharb"
- }
- },
- "node_modules/hasown": {
- "version": "2.0.3",
- "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.3.tgz",
- "integrity": "sha512-ej4AhfhfL2Q2zpMmLo7U1Uv9+PyhIZpgQLGT1F9miIGmiCJIoCgSmczFdrc97mWT4kVY72KA+WnnhJ5pghSvSg==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "function-bind": "^1.1.2"
- },
- "engines": {
- "node": ">= 0.4"
- }
- },
"node_modules/html-encoding-sniffer": {
- "version": "4.0.0",
- "resolved": "https://registry.npmjs.org/html-encoding-sniffer/-/html-encoding-sniffer-4.0.0.tgz",
- "integrity": "sha512-Y22oTqIU4uuPgEemfz7NDJz6OeKf12Lsu+QC+s3BVpda64lTiMYCyGwg5ki4vFxkMwQdeZDl2adZoqUgdFuTgQ==",
+ "version": "6.0.0",
+ "resolved": "https://registry.npmjs.org/html-encoding-sniffer/-/html-encoding-sniffer-6.0.0.tgz",
+ "integrity": "sha512-CV9TW3Y3f8/wT0BRFc1/KAVQ3TUHiXmaAb6VW9vtiMFf7SLoMd1PdAc4W3KFOFETBJUb90KatHqlsZMWV+R9Gg==",
"dev": true,
"license": "MIT",
"dependencies": {
- "whatwg-encoding": "^3.1.1"
+ "@exodus/bytes": "^1.6.0"
},
"engines": {
- "node": ">=18"
+ "node": "^20.19.0 || ^22.12.0 || >=24.0.0"
}
},
"node_modules/html-escaper": {
@@ -1658,47 +1481,6 @@
"integrity": "sha512-Pysuw9XpUq5dVc/2SMHpuTY01RFl8fttgcyunjL7eEMhGM3cI4eOmiCycJDVCo/7O7ClfQD3SaI6ftDzqOXYMA==",
"license": "MIT"
},
- "node_modules/http-proxy-agent": {
- "version": "7.0.2",
- "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-7.0.2.tgz",
- "integrity": "sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "agent-base": "^7.1.0",
- "debug": "^4.3.4"
- },
- "engines": {
- "node": ">= 14"
- }
- },
- "node_modules/https-proxy-agent": {
- "version": "7.0.6",
- "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.6.tgz",
- "integrity": "sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "agent-base": "^7.1.2",
- "debug": "4"
- },
- "engines": {
- "node": ">= 14"
- }
- },
- "node_modules/iconv-lite": {
- "version": "0.6.3",
- "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz",
- "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "safer-buffer": ">= 2.1.2 < 3.0.0"
- },
- "engines": {
- "node": ">=0.10.0"
- }
- },
"node_modules/inherits": {
"version": "2.0.4",
"resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz",
@@ -1730,39 +1512,39 @@
"license": "MIT"
},
"node_modules/jsdom": {
- "version": "25.0.1",
- "resolved": "https://registry.npmjs.org/jsdom/-/jsdom-25.0.1.tgz",
- "integrity": "sha512-8i7LzZj7BF8uplX+ZyOlIz86V6TAsSs+np6m1kpW9u0JWi4z/1t+FzcK1aek+ybTnAC4KhBL4uXCNT0wcUIeCw==",
+ "version": "29.1.1",
+ "resolved": "https://registry.npmjs.org/jsdom/-/jsdom-29.1.1.tgz",
+ "integrity": "sha512-ECi4Fi2f7BdJtUKTflYRTiaMxIB0O6zfR1fX0GXpUrf6flp8QIYn1UT20YQqdSOfk2dfkCwS8LAFoJDEppNK5Q==",
"dev": true,
"license": "MIT",
"dependencies": {
- "cssstyle": "^4.1.0",
- "data-urls": "^5.0.0",
- "decimal.js": "^10.4.3",
- "form-data": "^4.0.0",
- "html-encoding-sniffer": "^4.0.0",
- "http-proxy-agent": "^7.0.2",
- "https-proxy-agent": "^7.0.5",
+ "@asamuzakjp/css-color": "^5.1.11",
+ "@asamuzakjp/dom-selector": "^7.1.1",
+ "@bramus/specificity": "^2.4.2",
+ "@csstools/css-syntax-patches-for-csstree": "^1.1.3",
+ "@exodus/bytes": "^1.15.0",
+ "css-tree": "^3.2.1",
+ "data-urls": "^7.0.0",
+ "decimal.js": "^10.6.0",
+ "html-encoding-sniffer": "^6.0.0",
"is-potential-custom-element-name": "^1.0.1",
- "nwsapi": "^2.2.12",
- "parse5": "^7.1.2",
- "rrweb-cssom": "^0.7.1",
+ "lru-cache": "^11.3.5",
+ "parse5": "^8.0.1",
"saxes": "^6.0.0",
"symbol-tree": "^3.2.4",
- "tough-cookie": "^5.0.0",
+ "tough-cookie": "^6.0.1",
+ "undici": "^7.25.0",
"w3c-xmlserializer": "^5.0.0",
- "webidl-conversions": "^7.0.0",
- "whatwg-encoding": "^3.1.1",
- "whatwg-mimetype": "^4.0.0",
- "whatwg-url": "^14.0.0",
- "ws": "^8.18.0",
+ "webidl-conversions": "^8.0.1",
+ "whatwg-mimetype": "^5.0.0",
+ "whatwg-url": "^16.0.1",
"xml-name-validator": "^5.0.0"
},
"engines": {
- "node": ">=18"
+ "node": "^20.19.0 || ^22.13.0 || >=24.0.0"
},
"peerDependencies": {
- "canvas": "^2.11.2"
+ "canvas": "^3.0.0"
},
"peerDependenciesMeta": {
"canvas": {
@@ -1771,11 +1553,14 @@
}
},
"node_modules/lru-cache": {
- "version": "10.4.3",
- "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-10.4.3.tgz",
- "integrity": "sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==",
+ "version": "11.5.2",
+ "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-11.5.2.tgz",
+ "integrity": "sha512-4pfM1Ff0x50o0tQwb5ucw/RzNyD0/YJME6IVcStalZuMWxdt3sR3huStTtxz4PUmvZfRguvDejasvQ2kifR11g==",
"dev": true,
- "license": "ISC"
+ "license": "BlueOak-1.0.0",
+ "engines": {
+ "node": "20 || >=22"
+ }
},
"node_modules/lucide-react": {
"version": "1.14.0",
@@ -1808,38 +1593,12 @@
"node": ">= 18"
}
},
- "node_modules/math-intrinsics": {
- "version": "1.1.0",
- "resolved": "https://registry.npmjs.org/math-intrinsics/-/math-intrinsics-1.1.0.tgz",
- "integrity": "sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==",
+ "node_modules/mdn-data": {
+ "version": "2.27.1",
+ "resolved": "https://registry.npmjs.org/mdn-data/-/mdn-data-2.27.1.tgz",
+ "integrity": "sha512-9Yubnt3e8A0OKwxYSXyhLymGW4sCufcLG6VdiDdUGVkPhpqLxlvP5vl1983gQjJl3tqbrM731mjaZaP68AgosQ==",
"dev": true,
- "license": "MIT",
- "engines": {
- "node": ">= 0.4"
- }
- },
- "node_modules/mime-db": {
- "version": "1.52.0",
- "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz",
- "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==",
- "dev": true,
- "license": "MIT",
- "engines": {
- "node": ">= 0.6"
- }
- },
- "node_modules/mime-types": {
- "version": "2.1.35",
- "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz",
- "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "mime-db": "1.52.0"
- },
- "engines": {
- "node": ">= 0.6"
- }
+ "license": "CC0-1.0"
},
"node_modules/monaco-editor": {
"version": "0.55.1",
@@ -1869,9 +1628,9 @@
"license": "MIT"
},
"node_modules/nanoid": {
- "version": "3.3.12",
- "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.12.tgz",
- "integrity": "sha512-ZB9RH/39qpq5Vu6Y+NmUaFhQR6pp+M2Xt76XBnEwDaGcVAqhlvxrl3B2bKS5D3NH3QR76v3aSrKaF/Kiy7lEtQ==",
+ "version": "3.3.16",
+ "resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.16.tgz",
+ "integrity": "sha512-bzlKTyNJ7+LdGIIwy8ijFpIqEQIvafahV7eYykJ8Cvh42EdJeODoJ6gUJXpQJvej1BddH8OqTXZNE/KfbWAu8Q==",
"funding": [
{
"type": "github",
@@ -1887,12 +1646,12 @@
}
},
"node_modules/next": {
- "version": "16.2.6",
- "resolved": "https://registry.npmjs.org/next/-/next-16.2.6.tgz",
- "integrity": "sha512-qOVgKJg1+At15NpeUP+eJgCHvTCgXsogweq87Ri/Ix7PkqQHg4sdaXmSFqKlgaIXE4kW0g25LE68W87UANlHtw==",
+ "version": "16.2.10",
+ "resolved": "https://registry.npmjs.org/next/-/next-16.2.10.tgz",
+ "integrity": "sha512-2som5AVXb3kE6Yjine3/mNbBayYF58eguBWIVVUdr1y/L426xyVEgYxgBG+1QC34P2x5E+tcDup6XkuOAX3dCA==",
"license": "MIT",
"dependencies": {
- "@next/env": "16.2.6",
+ "@next/env": "16.2.10",
"@swc/helpers": "0.5.15",
"baseline-browser-mapping": "^2.9.19",
"caniuse-lite": "^1.0.30001579",
@@ -1906,14 +1665,14 @@
"node": ">=20.9.0"
},
"optionalDependencies": {
- "@next/swc-darwin-arm64": "16.2.6",
- "@next/swc-darwin-x64": "16.2.6",
- "@next/swc-linux-arm64-gnu": "16.2.6",
- "@next/swc-linux-arm64-musl": "16.2.6",
- "@next/swc-linux-x64-gnu": "16.2.6",
- "@next/swc-linux-x64-musl": "16.2.6",
- "@next/swc-win32-arm64-msvc": "16.2.6",
- "@next/swc-win32-x64-msvc": "16.2.6",
+ "@next/swc-darwin-arm64": "16.2.10",
+ "@next/swc-darwin-x64": "16.2.10",
+ "@next/swc-linux-arm64-gnu": "16.2.10",
+ "@next/swc-linux-arm64-musl": "16.2.10",
+ "@next/swc-linux-x64-gnu": "16.2.10",
+ "@next/swc-linux-x64-musl": "16.2.10",
+ "@next/swc-win32-arm64-msvc": "16.2.10",
+ "@next/swc-win32-x64-msvc": "16.2.10",
"sharp": "^0.34.5"
},
"peerDependencies": {
@@ -1939,13 +1698,6 @@
}
}
},
- "node_modules/nwsapi": {
- "version": "2.2.23",
- "resolved": "https://registry.npmjs.org/nwsapi/-/nwsapi-2.2.23.tgz",
- "integrity": "sha512-7wfH4sLbt4M0gCDzGE6vzQBo0bfTKjU7Sfpqy/7gs1qBfYz2vEJH6vXcBKpO3+6Yu1telwd0t9HpyOoLEQQbIQ==",
- "dev": true,
- "license": "MIT"
- },
"node_modules/opener": {
"version": "1.5.2",
"resolved": "https://registry.npmjs.org/opener/-/opener-1.5.2.tgz",
@@ -1957,13 +1709,13 @@
}
},
"node_modules/parse5": {
- "version": "7.3.0",
- "resolved": "https://registry.npmjs.org/parse5/-/parse5-7.3.0.tgz",
- "integrity": "sha512-IInvU7fabl34qmi9gY8XOVxhYyMyuH2xUNpb2q8/Y+7552KlejkRvqvD19nMoUW/uQGGbqNpA6Tufu5FL5BZgw==",
+ "version": "8.0.1",
+ "resolved": "https://registry.npmjs.org/parse5/-/parse5-8.0.1.tgz",
+ "integrity": "sha512-z1e/HMG90obSGeidlli3hj7cbocou0/wa5HacvI3ASx34PecNjNQeaHNo5WIZpWofN9kgkqV1q5YvXe3F0FoPw==",
"dev": true,
"license": "MIT",
"dependencies": {
- "entities": "^6.0.0"
+ "entities": "^8.0.0"
},
"funding": {
"url": "https://github.com/inikulin/parse5?sponsor=1"
@@ -1976,13 +1728,13 @@
"license": "ISC"
},
"node_modules/playwright": {
- "version": "1.57.0",
- "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.57.0.tgz",
- "integrity": "sha512-ilYQj1s8sr2ppEJ2YVadYBN0Mb3mdo9J0wQ+UuDhzYqURwSoW4n1Xs5vs7ORwgDGmyEh33tRMeS8KhdkMoLXQw==",
+ "version": "1.60.0",
+ "resolved": "https://registry.npmjs.org/playwright/-/playwright-1.60.0.tgz",
+ "integrity": "sha512-hheHdokM8cdqCb0lcE3s+zT4t4W+vvjpGxsZlDnikarzx8tSzMebh3UiFtgqwFwnTnjYQcsyMF8ei2mCO/tpeA==",
"devOptional": true,
"license": "Apache-2.0",
"dependencies": {
- "playwright-core": "1.57.0"
+ "playwright-core": "1.60.0"
},
"bin": {
"playwright": "cli.js"
@@ -1995,9 +1747,9 @@
}
},
"node_modules/playwright-core": {
- "version": "1.57.0",
- "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.57.0.tgz",
- "integrity": "sha512-agTcKlMw/mjBWOnD6kFZttAAGHgi/Nw0CZ2o6JqWSbMlI219lAFLZZCyqByTsvVAJq5XA5H8cA6PrvBRpBWEuQ==",
+ "version": "1.60.0",
+ "resolved": "https://registry.npmjs.org/playwright-core/-/playwright-core-1.60.0.tgz",
+ "integrity": "sha512-9bW6zvX/m0lEbgTKJ6YppOKx8H3VOPBMOCFh2irXFOT4BbHgrx5hPjwJYLT40Lu+4qtD36qKc/Hn56StUW57IA==",
"devOptional": true,
"license": "Apache-2.0",
"peer": true,
@@ -2062,9 +1814,9 @@
}
},
"node_modules/pure-rand": {
- "version": "6.1.0",
- "resolved": "https://registry.npmjs.org/pure-rand/-/pure-rand-6.1.0.tgz",
- "integrity": "sha512-bVWawvoZoBYpp6yIoQtQXHZjmz35RSVHnUOTefl8Vcjr8snTPY1wnpSPMWekcFwbxI6gtmT7rSYPFvz71ldiOA==",
+ "version": "8.4.2",
+ "resolved": "https://registry.npmjs.org/pure-rand/-/pure-rand-8.4.2.tgz",
+ "integrity": "sha512-vvuOGgcuPJAirlHvuQw1TrOiw7ptaIXXmIbNuiNOY6lNGJJH49PQ1Kj4nd783nPdQhQdicgOjVI2yI/9BD6/Ng==",
"dev": true,
"funding": [
{
@@ -2085,9 +1837,9 @@
"license": "MIT"
},
"node_modules/react": {
- "version": "19.2.5",
- "resolved": "https://registry.npmjs.org/react/-/react-19.2.5.tgz",
- "integrity": "sha512-llUJLzz1zTUBrskt2pwZgLq59AemifIftw4aB7JxOqf1HY2FDaGDxgwpAPVzHU1kdWabH7FauP4i1oEeer2WCA==",
+ "version": "19.2.7",
+ "resolved": "https://registry.npmjs.org/react/-/react-19.2.7.tgz",
+ "integrity": "sha512-HNe9WslTbXmFK8o8cmwgAeJFSBvt1bPdHCVKtaaV+WlAN36mpT4hcRpwbf3fY56ar2oIXzsBpOAiIRHAdY0OlQ==",
"license": "MIT",
"peer": true,
"engines": {
@@ -2095,16 +1847,16 @@
}
},
"node_modules/react-dom": {
- "version": "19.2.5",
- "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.5.tgz",
- "integrity": "sha512-J5bAZz+DXMMwW/wV3xzKke59Af6CHY7G4uYLN1OvBcKEsWOs4pQExj86BBKamxl/Ik5bx9whOrvBlSDfWzgSag==",
+ "version": "19.2.7",
+ "resolved": "https://registry.npmjs.org/react-dom/-/react-dom-19.2.7.tgz",
+ "integrity": "sha512-t0BRVXvbiE/o20Hfw669rLbMCDWtYZLvmJigy2f0MxsXF+71pxhR3xOkspmsO8h3ZlNzyibAmtCa3l4lYKk6gQ==",
"license": "MIT",
"peer": true,
"dependencies": {
"scheduler": "^0.27.0"
},
"peerDependencies": {
- "react": "^19.2.5"
+ "react": "^19.2.7"
}
},
"node_modules/react-is": {
@@ -2114,19 +1866,22 @@
"dev": true,
"license": "MIT"
},
+ "node_modules/require-from-string": {
+ "version": "2.0.2",
+ "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz",
+ "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==",
+ "dev": true,
+ "license": "MIT",
+ "engines": {
+ "node": ">=0.10.0"
+ }
+ },
"node_modules/requires-port": {
"version": "1.0.0",
"resolved": "https://registry.npmjs.org/requires-port/-/requires-port-1.0.0.tgz",
"integrity": "sha512-KigOCHcocU3XODJxsu8i/j8T9tzT4adHiecwORRQ0ZZFcp7ahwXuRU1m+yuO90C5ZUyGeGfocHDI14M3L3yDAQ==",
"license": "MIT"
},
- "node_modules/rrweb-cssom": {
- "version": "0.7.1",
- "resolved": "https://registry.npmjs.org/rrweb-cssom/-/rrweb-cssom-0.7.1.tgz",
- "integrity": "sha512-TrEMa7JGdVm0UThDJSx7ddw5nVm3UJS9o9CCIZ72B1vSyEZoziDqBYP3XIoi/12lKrJR8rE3jeFHMok2F/Mnsg==",
- "dev": true,
- "license": "MIT"
- },
"node_modules/safe-buffer": {
"version": "5.2.1",
"resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz",
@@ -2147,13 +1902,6 @@
],
"license": "MIT"
},
- "node_modules/safer-buffer": {
- "version": "2.1.2",
- "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
- "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==",
- "dev": true,
- "license": "MIT"
- },
"node_modules/saxes": {
"version": "6.0.0",
"resolved": "https://registry.npmjs.org/saxes/-/saxes-6.0.0.tgz",
@@ -2174,9 +1922,9 @@
"license": "MIT"
},
"node_modules/semver": {
- "version": "7.7.4",
- "resolved": "https://registry.npmjs.org/semver/-/semver-7.7.4.tgz",
- "integrity": "sha512-vFKC2IEtQnVhpT78h1Yp8wzwrf8CM+MzKMHGJZfBtzhZNycRFnXsHk6E5TxIkkMsgNS7mdX3AGB7x2QM2di4lA==",
+ "version": "7.8.5",
+ "resolved": "https://registry.npmjs.org/semver/-/semver-7.8.5.tgz",
+ "integrity": "sha512-Y7/KDsb8LjooZpwaqGyulO6DQlksgCncchHGk+sZIY4SBvUocMBEFH5Ur1fI4dV+Jvl0w6cjvucaIi40puRioA==",
"license": "ISC",
"optional": true,
"bin": {
@@ -2265,15 +2013,6 @@
"url": "https://tidelift.com/funding/github/npm/sockjs-client"
}
},
- "node_modules/sockjs-client/node_modules/debug": {
- "version": "3.2.7",
- "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.7.tgz",
- "integrity": "sha512-CFjzYYAi4ThfiQvizrFQevTTXHtnCqWfe7x1AhgEscTz6ZbLbfoLRLPugTQyBth6f8ZERVUSyWHFD/7Wu4t1XQ==",
- "license": "MIT",
- "dependencies": {
- "ms": "^2.1.1"
- }
- },
"node_modules/source-map-js": {
"version": "1.2.1",
"resolved": "https://registry.npmjs.org/source-map-js/-/source-map-js-1.2.1.tgz",
@@ -2320,22 +2059,22 @@
"license": "MIT"
},
"node_modules/tldts": {
- "version": "6.1.86",
- "resolved": "https://registry.npmjs.org/tldts/-/tldts-6.1.86.tgz",
- "integrity": "sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==",
+ "version": "7.4.8",
+ "resolved": "https://registry.npmjs.org/tldts/-/tldts-7.4.8.tgz",
+ "integrity": "sha512-htwgN/8KRB3z3vnC0BOETVh2m499g5GmyTK9Wq5JBLX3FNz6tSBveAd+fQhzy9hkjif8vy2jwDMR1sGhLtZl2A==",
"dev": true,
"license": "MIT",
"dependencies": {
- "tldts-core": "^6.1.86"
+ "tldts-core": "^7.4.8"
},
"bin": {
"tldts": "bin/cli.js"
}
},
"node_modules/tldts-core": {
- "version": "6.1.86",
- "resolved": "https://registry.npmjs.org/tldts-core/-/tldts-core-6.1.86.tgz",
- "integrity": "sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==",
+ "version": "7.4.8",
+ "resolved": "https://registry.npmjs.org/tldts-core/-/tldts-core-7.4.8.tgz",
+ "integrity": "sha512-c1P7u0EhACHj7lPy4MJm8iTFEU8+nB0LCtddH0fhP7noaVoXAqafMtOOeX+ulpuPBqnrRgRhw494RICT3mbhnw==",
"dev": true,
"license": "MIT"
},
@@ -2350,29 +2089,29 @@
}
},
"node_modules/tough-cookie": {
- "version": "5.1.2",
- "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-5.1.2.tgz",
- "integrity": "sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==",
+ "version": "6.0.2",
+ "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-6.0.2.tgz",
+ "integrity": "sha512-exgYmnmL/sJpR3upZfXG5PoatXQii55xAiXGXzY+sROLZ/Y+SLcp9PgJNI9Vz37HpQ74WvDcLT8eqm+kV3FzrA==",
"dev": true,
"license": "BSD-3-Clause",
"dependencies": {
- "tldts": "^6.1.32"
+ "tldts": "^7.0.5"
},
"engines": {
"node": ">=16"
}
},
"node_modules/tr46": {
- "version": "5.1.1",
- "resolved": "https://registry.npmjs.org/tr46/-/tr46-5.1.1.tgz",
- "integrity": "sha512-hdF5ZgjTqgAntKkklYw0R03MG2x/bSzTtkxmIRw/sTNV8YXsCJ1tfLAX23lhxhHJlEf3CRCOCGGWw3vI3GaSPw==",
+ "version": "6.0.0",
+ "resolved": "https://registry.npmjs.org/tr46/-/tr46-6.0.0.tgz",
+ "integrity": "sha512-bLVMLPtstlZ4iMQHpFHTR7GAGj2jxi8Dg0s2h2MafAE4uSWF98FC/3MomU51iQAMf8/qDUbKWf5GxuvvVcXEhw==",
"dev": true,
"license": "MIT",
"dependencies": {
"punycode": "^2.3.1"
},
"engines": {
- "node": ">=18"
+ "node": ">=20"
}
},
"node_modules/tslib": {
@@ -2395,10 +2134,20 @@
"node": ">=14.17"
}
},
+ "node_modules/undici": {
+ "version": "7.28.0",
+ "resolved": "https://registry.npmjs.org/undici/-/undici-7.28.0.tgz",
+ "integrity": "sha512-cRZYrTDwWznlnRiPjggAGxZXanty6M8RV1ff8Wm4LWXBp7/IG8v5DnOm74DtUBp9OONpK75YlPnIjQqX0dBDtA==",
+ "dev": true,
+ "license": "MIT",
+ "engines": {
+ "node": ">=20.18.1"
+ }
+ },
"node_modules/undici-types": {
- "version": "7.16.0",
- "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.16.0.tgz",
- "integrity": "sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw==",
+ "version": "7.28.0",
+ "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-7.28.0.tgz",
+ "integrity": "sha512-LJAfY+2w6HGeT8d8J1wNQsUGUEGio6NWWpwdwurQe4f6oojzCFuGLizl1KSve4irsTxyLly1QhEeE6iapdaIvQ==",
"dev": true,
"license": "MIT"
},
@@ -2426,13 +2175,13 @@
}
},
"node_modules/webidl-conversions": {
- "version": "7.0.0",
- "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-7.0.0.tgz",
- "integrity": "sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==",
+ "version": "8.0.1",
+ "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-8.0.1.tgz",
+ "integrity": "sha512-BMhLD/Sw+GbJC21C/UgyaZX41nPt8bUTg+jWyDeg7e7YN4xOM05YPSIXceACnXVtqyEw/LMClUQMtMZ+PGGpqQ==",
"dev": true,
"license": "BSD-2-Clause",
"engines": {
- "node": ">=12"
+ "node": ">=20"
}
},
"node_modules/webpack-bundle-analyzer": {
@@ -2463,32 +2212,10 @@
"node": ">= 10.13.0"
}
},
- "node_modules/webpack-bundle-analyzer/node_modules/ws": {
- "version": "7.5.10",
- "resolved": "https://registry.npmjs.org/ws/-/ws-7.5.10.tgz",
- "integrity": "sha512-+dbF1tHwZpXcbOJdVOkzLDxZP1ailvSxM6ZweXTegylPny803bFhA+vqBYw4s31NSAk4S2Qz+AKXK9a4wkdjcQ==",
- "dev": true,
- "license": "MIT",
- "engines": {
- "node": ">=8.3.0"
- },
- "peerDependencies": {
- "bufferutil": "^4.0.1",
- "utf-8-validate": "^5.0.2"
- },
- "peerDependenciesMeta": {
- "bufferutil": {
- "optional": true
- },
- "utf-8-validate": {
- "optional": true
- }
- }
- },
"node_modules/websocket-driver": {
- "version": "0.7.4",
- "resolved": "https://registry.npmjs.org/websocket-driver/-/websocket-driver-0.7.4.tgz",
- "integrity": "sha512-b17KeDIQVjvb0ssuSDF2cYXSg2iztliJ4B9WdsuB6J952qCPKmnVq4DyW5motImXHDC1cBT/1UezrJVsKw5zjg==",
+ "version": "0.7.5",
+ "resolved": "https://registry.npmjs.org/websocket-driver/-/websocket-driver-0.7.5.tgz",
+ "integrity": "sha512-ZL2+3c7kMBdIRCMz6l8jQMHyGVxj+UL+xVk74Ombiciboca8rHa15L86B19E5oh1pL9Ii/uj54gtsIrZGMo6zA==",
"license": "Apache-2.0",
"dependencies": {
"http-parser-js": ">=0.5.1",
@@ -2508,56 +2235,43 @@
"node": ">=0.8.0"
}
},
- "node_modules/whatwg-encoding": {
- "version": "3.1.1",
- "resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-3.1.1.tgz",
- "integrity": "sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==",
- "deprecated": "Use @exodus/bytes instead for a more spec-conformant and faster implementation",
- "dev": true,
- "license": "MIT",
- "dependencies": {
- "iconv-lite": "0.6.3"
- },
- "engines": {
- "node": ">=18"
- }
- },
"node_modules/whatwg-mimetype": {
- "version": "4.0.0",
- "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-4.0.0.tgz",
- "integrity": "sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==",
+ "version": "5.0.0",
+ "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-5.0.0.tgz",
+ "integrity": "sha512-sXcNcHOC51uPGF0P/D4NVtrkjSU2fNsm9iog4ZvZJsL3rjoDAzXZhkm2MWt1y+PUdggKAYVoMAIYcs78wJ51Cw==",
"dev": true,
"license": "MIT",
"engines": {
- "node": ">=18"
+ "node": ">=20"
}
},
"node_modules/whatwg-url": {
- "version": "14.2.0",
- "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-14.2.0.tgz",
- "integrity": "sha512-De72GdQZzNTUBBChsXueQUnPKDkg/5A5zp7pFDuQAj5UFoENpiACU0wlCvzpAGnTkj++ihpKwKyYewn/XNUbKw==",
+ "version": "16.0.1",
+ "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-16.0.1.tgz",
+ "integrity": "sha512-1to4zXBxmXHV3IiSSEInrreIlu02vUOvrhxJJH5vcxYTBDAx51cqZiKdyTxlecdKNSjj8EcxGBxNf6Vg+945gw==",
"dev": true,
"license": "MIT",
"dependencies": {
- "tr46": "^5.1.0",
- "webidl-conversions": "^7.0.0"
+ "@exodus/bytes": "^1.11.0",
+ "tr46": "^6.0.0",
+ "webidl-conversions": "^8.0.1"
},
"engines": {
- "node": ">=18"
+ "node": "^20.19.0 || ^22.12.0 || >=24.0.0"
}
},
"node_modules/ws": {
- "version": "8.20.1",
- "resolved": "https://registry.npmjs.org/ws/-/ws-8.20.1.tgz",
- "integrity": "sha512-It4dO0K5v//JtTXuPkfEOaI3uUN87iYPnqo/ZzqCoG3g8uhA66QUMs/SrM0YK7/NAu+r4LMh/9dq2A7k+rHs+w==",
+ "version": "7.5.12",
+ "resolved": "https://registry.npmjs.org/ws/-/ws-7.5.12.tgz",
+ "integrity": "sha512-1xGnbYN3zbog9CwuNDQULNRrTCLIn46/WmpR1f0w6PsCYQHkylZr5vkd6kfMZYV6pRnQkcPNRyiA8LsrNKyhpg==",
"dev": true,
"license": "MIT",
"engines": {
- "node": ">=10.0.0"
+ "node": ">=8.3.0"
},
"peerDependencies": {
"bufferutil": "^4.0.1",
- "utf-8-validate": ">=5.0.2"
+ "utf-8-validate": "^5.0.2"
},
"peerDependenciesMeta": {
"bufferutil": {
diff --git a/frontend/package.json b/frontend/package.json
index ad5654d8..8d34e47a 100644
--- a/frontend/package.json
+++ b/frontend/package.json
@@ -30,28 +30,29 @@
"@monaco-editor/react": "^4.7.0",
"@stomp/stompjs": "^7.3.0",
"lucide-react": "1.14.0",
- "next": "16.2.6",
- "react": "19.2.5",
- "react-dom": "19.2.5",
+ "next": "16.2.10",
+ "react": "19.2.7",
+ "react-dom": "19.2.7",
"sockjs-client": "^1.6.1"
},
"devDependencies": {
"@axe-core/playwright": "^4.10.0",
"@next/bundle-analyzer": "^16.2.6",
- "@playwright/test": "1.57.0",
+ "@playwright/test": "1.60.0",
"@testing-library/dom": "^10.4.0",
"@testing-library/react": "^16.3.0",
"@types/jsdom": "^28.0.3",
"@types/node": "24.10.2",
- "@types/react": "19.2.14",
+ "@types/react": "19.2.17",
"@types/react-dom": "19.2.3",
"@types/sockjs-client": "^1.5.4",
- "fast-check": "^3.23.0",
- "jsdom": "^25.0.1",
+ "fast-check": "^4.8.0",
+ "jsdom": "^29.1.1",
+ "playwright-core": "1.60.0",
"typescript": "6.0.3"
},
"overrides": {
- "dompurify": "3.4.2",
+ "dompurify": "3.4.12",
"postcss": "8.5.10"
}
}
diff --git a/frontend/src/__tests__/hooks/useFocusTrap.test.ts b/frontend/src/__tests__/hooks/useFocusTrap.test.ts
index 58025b00..110f9ab5 100644
--- a/frontend/src/__tests__/hooks/useFocusTrap.test.ts
+++ b/frontend/src/__tests__/hooks/useFocusTrap.test.ts
@@ -44,10 +44,10 @@ describe('useFocusTrap - DOM behavior', () => {
// Should find: btn1, input1, link1, div1 (4 elements)
// Should NOT find: btn-disabled, div-neg
assert.equal(focusable.length, 4);
- assert.equal((focusable[0] as HTMLElement).id, 'btn1');
- assert.equal((focusable[1] as HTMLElement).id, 'input1');
- assert.equal((focusable[2] as HTMLElement).id, 'link1');
- assert.equal((focusable[3] as HTMLElement).id, 'div1');
+ assert.deepEqual(
+ new Set(focusable.map((element) => (element as HTMLElement).id)),
+ new Set(['btn1', 'input1', 'link1', 'div1'])
+ );
});
it('Tab on last element should cycle to first (simulated keydown logic)', () => {
diff --git a/frontend/src/__tests__/properties/eventSerialization.property.test.ts b/frontend/src/__tests__/properties/eventSerialization.property.test.ts
index f76e710d..e8cd3972 100644
--- a/frontend/src/__tests__/properties/eventSerialization.property.test.ts
+++ b/frontend/src/__tests__/properties/eventSerialization.property.test.ts
@@ -28,7 +28,11 @@ const arbNotificationEvent = fc.record({
type: arbNotificationType,
title: fc.string({ minLength: 1, maxLength: 100 }),
body: fc.string({ minLength: 1, maxLength: 500 }),
- createdAt: fc.date({ min: new Date("2020-01-01"), max: new Date("2030-01-01") })
+ createdAt: fc.date({
+ min: new Date("2020-01-01"),
+ max: new Date("2030-01-01"),
+ noInvalidDate: true,
+ })
.map((d) => d.toISOString()),
read: fc.boolean(),
sequenceNumber: fc.nat(),
diff --git a/job-service/Dockerfile b/job-service/Dockerfile
index a6fdefd4..4c79a368 100644
--- a/job-service/Dockerfile
+++ b/job-service/Dockerfile
@@ -1,4 +1,4 @@
-FROM maven:3.9.12-eclipse-temurin-21 AS build
+FROM maven:3.9.14-eclipse-temurin-25 AS build
WORKDIR /workspace
ARG SERVICE_NAME=job-service
COPY pom.xml .
@@ -17,7 +17,7 @@ COPY common-lib/src common-lib/src
COPY ${SERVICE_NAME}/src ${SERVICE_NAME}/src
RUN mvn -B -T1 -pl ${SERVICE_NAME} -am package -DskipTests
-FROM eclipse-temurin:21-jre-alpine
+FROM eclipse-temurin:25-jre-alpine
ARG SERVICE_NAME=job-service
ARG BUILD_VERSION=0.4.0-SNAPSHOT
ARG VCS_REF=local
diff --git a/job-service/pom.xml b/job-service/pom.xml
index 5dd2aa45..491a5417 100644
--- a/job-service/pom.xml
+++ b/job-service/pom.xml
@@ -17,8 +17,8 @@
org.springframework.bootspring-boot-starter-data-jpa
org.springframework.bootspring-boot-starter-actuator
org.springframework.cloudspring-cloud-starter-openfeign
- org.springframework.kafkaspring-kafka
- org.flywaydbflyway-core
+ org.springframework.bootspring-boot-starter-kafka
+ org.springframework.bootspring-boot-starter-flyway
org.flywaydbflyway-database-postgresql
org.postgresqlpostgresqlruntime
org.springdocspringdoc-openapi-starter-webmvc-ui${springdoc.version}
@@ -26,8 +26,10 @@
io.micrometermicrometer-tracing-bridge-otel
io.opentelemetryopentelemetry-exporter-otlp
org.springframework.bootspring-boot-starter-testtest
- org.testcontainerspostgresqltest
- org.testcontainersjunit-jupitertest
+ org.springframework.bootspring-boot-starter-data-jpa-testtest
+ org.springframework.bootspring-boot-starter-flyway-testtest
+ org.testcontainerstestcontainers-postgresqltest
+ org.testcontainerstestcontainers-junit-jupitertest
org.springframework.bootspring-boot-maven-plugin
diff --git a/job-service/src/test/java/com/devhire/job/repository/JobRepositoryIT.java b/job-service/src/test/java/com/devhire/job/repository/JobRepositoryIT.java
index b75eaffe..d155bd2b 100644
--- a/job-service/src/test/java/com/devhire/job/repository/JobRepositoryIT.java
+++ b/job-service/src/test/java/com/devhire/job/repository/JobRepositoryIT.java
@@ -4,13 +4,13 @@
import com.devhire.job.entity.JobStatus;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
-import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
+import org.springframework.boot.data.jpa.test.autoconfigure.DataJpaTest;
+import org.springframework.boot.jdbc.test.autoconfigure.AutoConfigureTestDatabase;
import org.springframework.dao.DataIntegrityViolationException;
import org.springframework.data.domain.PageRequest;
import org.springframework.test.context.DynamicPropertyRegistry;
import org.springframework.test.context.DynamicPropertySource;
-import org.testcontainers.containers.PostgreSQLContainer;
+import org.testcontainers.postgresql.PostgreSQLContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
@@ -28,7 +28,7 @@
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
class JobRepositoryIT {
@Container
- static final PostgreSQLContainer> postgres = new PostgreSQLContainer<>("postgres:17-alpine");
+ static final PostgreSQLContainer postgres = new PostgreSQLContainer("postgres:17-alpine");
@Autowired
private JobRepository jobRepository;
diff --git a/notification-service/Dockerfile b/notification-service/Dockerfile
index 3c2d53b1..35ab27ad 100644
--- a/notification-service/Dockerfile
+++ b/notification-service/Dockerfile
@@ -1,4 +1,4 @@
-FROM maven:3.9.12-eclipse-temurin-21 AS build
+FROM maven:3.9.14-eclipse-temurin-25 AS build
WORKDIR /workspace
ARG SERVICE_NAME=notification-service
COPY pom.xml .
@@ -17,7 +17,7 @@ COPY common-lib/src common-lib/src
COPY ${SERVICE_NAME}/src ${SERVICE_NAME}/src
RUN mvn -B -T1 -pl ${SERVICE_NAME} -am package -DskipTests
-FROM eclipse-temurin:21-jre-alpine
+FROM eclipse-temurin:25-jre-alpine
ARG SERVICE_NAME=notification-service
ARG BUILD_VERSION=0.4.0-SNAPSHOT
ARG VCS_REF=local
diff --git a/notification-service/pom.xml b/notification-service/pom.xml
index 53679553..189f746c 100644
--- a/notification-service/pom.xml
+++ b/notification-service/pom.xml
@@ -1,4 +1,4 @@
-
+
@@ -19,8 +19,8 @@
org.springframework.bootspring-boot-starter-actuator
org.springframework.bootspring-boot-starter-mail
org.springframework.cloudspring-cloud-starter-openfeign
- org.springframework.kafkaspring-kafka
- org.flywaydbflyway-core
+ org.springframework.bootspring-boot-starter-kafka
+ org.springframework.bootspring-boot-starter-flyway
org.flywaydbflyway-database-postgresql
org.postgresqlpostgresqlruntime
org.springdocspringdoc-openapi-starter-webmvc-ui${springdoc.version}
@@ -32,12 +32,14 @@
io.jsonwebtokenjjwt-jackson${jjwt.version}runtime
org.springframework.bootspring-boot-starter-data-redis
org.springframework.bootspring-boot-starter-testtest
- org.testcontainerspostgresqltest
- org.testcontainersjunit-jupitertest
- org.testcontainerskafkatest
+ org.springframework.bootspring-boot-starter-data-jpa-testtest
+ org.springframework.bootspring-boot-starter-flyway-testtest
+ org.testcontainerstestcontainers-postgresqltest
+ org.testcontainerstestcontainers-junit-jupitertest
+ org.testcontainerstestcontainers-kafkatest
org.springframework.kafkaspring-kafka-testtest
org.awaitilityawaitilitytest
- net.jqwikjqwik1.9.2test
+ net.jqwikjqwik1.10.1test
org.springframework.bootspring-boot-maven-plugin
diff --git a/notification-service/src/test/java/com/devhire/notification/integration/CacheInvalidationIntegrationTest.java b/notification-service/src/test/java/com/devhire/notification/integration/CacheInvalidationIntegrationTest.java
index 2f931e7a..7b72a8b9 100644
--- a/notification-service/src/test/java/com/devhire/notification/integration/CacheInvalidationIntegrationTest.java
+++ b/notification-service/src/test/java/com/devhire/notification/integration/CacheInvalidationIntegrationTest.java
@@ -12,7 +12,7 @@
import org.springframework.data.redis.connection.lettuce.LettuceConnectionFactory;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.testcontainers.containers.GenericContainer;
-import org.testcontainers.containers.KafkaContainer;
+import org.testcontainers.kafka.ConfluentKafkaContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
import org.testcontainers.utility.DockerImageName;
@@ -43,7 +43,7 @@ class CacheInvalidationIntegrationTest {
.withExposedPorts(6379);
@Container
- static final KafkaContainer KAFKA = new KafkaContainer(
+ static final ConfluentKafkaContainer KAFKA = new ConfluentKafkaContainer(
DockerImageName.parse("confluentinc/cp-kafka:7.6.0"));
private LettuceConnectionFactory connectionFactory;
diff --git a/notification-service/src/test/java/com/devhire/notification/integration/KafkaNotificationPipelineIntegrationTest.java b/notification-service/src/test/java/com/devhire/notification/integration/KafkaNotificationPipelineIntegrationTest.java
index aa325988..a36b171a 100644
--- a/notification-service/src/test/java/com/devhire/notification/integration/KafkaNotificationPipelineIntegrationTest.java
+++ b/notification-service/src/test/java/com/devhire/notification/integration/KafkaNotificationPipelineIntegrationTest.java
@@ -16,8 +16,8 @@
import org.springframework.data.redis.listener.ChannelTopic;
import org.springframework.data.redis.listener.RedisMessageListenerContainer;
import org.testcontainers.containers.GenericContainer;
-import org.testcontainers.containers.KafkaContainer;
-import org.testcontainers.containers.PostgreSQLContainer;
+import org.testcontainers.kafka.ConfluentKafkaContainer;
+import org.testcontainers.postgresql.PostgreSQLContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
import org.testcontainers.utility.DockerImageName;
@@ -47,11 +47,11 @@ class KafkaNotificationPipelineIntegrationTest {
.withExposedPorts(6379);
@Container
- static final KafkaContainer KAFKA = new KafkaContainer(
+ static final ConfluentKafkaContainer KAFKA = new ConfluentKafkaContainer(
DockerImageName.parse("confluentinc/cp-kafka:7.6.0"));
@Container
- static final PostgreSQLContainer> POSTGRES = new PostgreSQLContainer<>(
+ static final PostgreSQLContainer POSTGRES = new PostgreSQLContainer(
DockerImageName.parse("postgres:17-alpine"))
.withDatabaseName("notification_test")
.withUsername("test")
diff --git a/notification-service/src/test/java/com/devhire/notification/repository/NotificationRepositoryIT.java b/notification-service/src/test/java/com/devhire/notification/repository/NotificationRepositoryIT.java
index d8ec7ae8..95017e06 100644
--- a/notification-service/src/test/java/com/devhire/notification/repository/NotificationRepositoryIT.java
+++ b/notification-service/src/test/java/com/devhire/notification/repository/NotificationRepositoryIT.java
@@ -3,12 +3,12 @@
import com.devhire.notification.entity.Notification;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
-import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
+import org.springframework.boot.data.jpa.test.autoconfigure.DataJpaTest;
+import org.springframework.boot.jdbc.test.autoconfigure.AutoConfigureTestDatabase;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.test.context.DynamicPropertyRegistry;
import org.springframework.test.context.DynamicPropertySource;
-import org.testcontainers.containers.PostgreSQLContainer;
+import org.testcontainers.postgresql.PostgreSQLContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
@@ -22,7 +22,7 @@
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
class NotificationRepositoryIT {
@Container
- static final PostgreSQLContainer> POSTGRES = new PostgreSQLContainer<>("postgres:17-alpine");
+ static final PostgreSQLContainer POSTGRES = new PostgreSQLContainer("postgres:17-alpine");
@DynamicPropertySource
static void datasource(DynamicPropertyRegistry registry) {
diff --git a/pom.xml b/pom.xml
index 16306a98..9de1f1ed 100644
--- a/pom.xml
+++ b/pom.xml
@@ -1,4 +1,4 @@
-
+
@@ -7,7 +7,7 @@
org.springframework.boot
spring-boot-starter-parent
- 3.5.14
+ 4.0.6
@@ -35,14 +35,18 @@
21
21
- 2025.0.2
- 4.1.133.Final
- 10.1.54
+ 2025.1.1
+ 2.21.4
+ 3.1.4
+ 4.2.15.Final
+ 11.0.22
+ 4.0.6
+ 1.6.0
42.7.11
- 1.84
+ 1.85
0.12.6
- 2.8.9
- 1.20.6
+ 3.0.3
+ 2.0.5
1.6.3
1.4.1
0.35
@@ -71,6 +75,11 @@
bcprov-jdk18on
${bouncycastle.version}
+
+ commons-fileupload
+ commons-fileupload
+ ${commons-fileupload.version}
+
@@ -112,7 +121,7 @@
org.jacoco
jacoco-maven-plugin
- 0.8.14
+ 0.8.15
diff --git a/user-service/Dockerfile b/user-service/Dockerfile
index 90818cf1..833f5639 100644
--- a/user-service/Dockerfile
+++ b/user-service/Dockerfile
@@ -1,4 +1,4 @@
-FROM maven:3.9.12-eclipse-temurin-21 AS build
+FROM maven:3.9.14-eclipse-temurin-25 AS build
WORKDIR /workspace
ARG SERVICE_NAME=user-service
COPY pom.xml .
@@ -17,7 +17,7 @@ COPY common-lib/src common-lib/src
COPY ${SERVICE_NAME}/src ${SERVICE_NAME}/src
RUN mvn -B -T1 -pl ${SERVICE_NAME} -am package -DskipTests
-FROM eclipse-temurin:21-jre-alpine
+FROM eclipse-temurin:25-jre-alpine
ARG SERVICE_NAME=user-service
ARG BUILD_VERSION=0.4.0-SNAPSHOT
ARG VCS_REF=local
diff --git a/user-service/pom.xml b/user-service/pom.xml
index 8e21ac67..dbaba63a 100644
--- a/user-service/pom.xml
+++ b/user-service/pom.xml
@@ -16,8 +16,8 @@
org.springframework.bootspring-boot-starter-validation
org.springframework.bootspring-boot-starter-data-jpa
org.springframework.bootspring-boot-starter-actuator
- org.springframework.kafkaspring-kafka
- org.flywaydbflyway-core
+ org.springframework.bootspring-boot-starter-kafka
+ org.springframework.bootspring-boot-starter-flyway
org.flywaydbflyway-database-postgresql
org.postgresqlpostgresqlruntime
org.springdocspringdoc-openapi-starter-webmvc-ui${springdoc.version}
@@ -25,8 +25,10 @@
io.micrometermicrometer-tracing-bridge-otel
io.opentelemetryopentelemetry-exporter-otlp
org.springframework.bootspring-boot-starter-testtest
- org.testcontainerspostgresqltest
- org.testcontainersjunit-jupitertest
+ org.springframework.bootspring-boot-starter-data-jpa-testtest
+ org.springframework.bootspring-boot-starter-flyway-testtest
+ org.testcontainerstestcontainers-postgresqltest
+ org.testcontainerstestcontainers-junit-jupitertest
org.springframework.bootspring-boot-maven-plugin
diff --git a/user-service/src/test/java/com/devhire/user/repository/UserProfileRepositoryIT.java b/user-service/src/test/java/com/devhire/user/repository/UserProfileRepositoryIT.java
index 949f01e3..ebb5c3f1 100644
--- a/user-service/src/test/java/com/devhire/user/repository/UserProfileRepositoryIT.java
+++ b/user-service/src/test/java/com/devhire/user/repository/UserProfileRepositoryIT.java
@@ -4,12 +4,12 @@
import com.devhire.user.entity.UserProfile;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.boot.test.autoconfigure.jdbc.AutoConfigureTestDatabase;
-import org.springframework.boot.test.autoconfigure.orm.jpa.DataJpaTest;
+import org.springframework.boot.data.jpa.test.autoconfigure.DataJpaTest;
+import org.springframework.boot.jdbc.test.autoconfigure.AutoConfigureTestDatabase;
import org.springframework.dao.DataIntegrityViolationException;
import org.springframework.test.context.DynamicPropertyRegistry;
import org.springframework.test.context.DynamicPropertySource;
-import org.testcontainers.containers.PostgreSQLContainer;
+import org.testcontainers.postgresql.PostgreSQLContainer;
import org.testcontainers.junit.jupiter.Container;
import org.testcontainers.junit.jupiter.Testcontainers;
@@ -23,7 +23,7 @@
@AutoConfigureTestDatabase(replace = AutoConfigureTestDatabase.Replace.NONE)
class UserProfileRepositoryIT {
@Container
- static final PostgreSQLContainer> POSTGRES = new PostgreSQLContainer<>("postgres:17-alpine");
+ static final PostgreSQLContainer POSTGRES = new PostgreSQLContainer("postgres:17-alpine");
@DynamicPropertySource
static void datasource(DynamicPropertyRegistry registry) {