Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
81 changes: 80 additions & 1 deletion .github/workflows/run-ci-cd.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -249,13 +249,73 @@ jobs:
permissions:
contents: read
runs-on: ubuntu-latest
services:
db:
image: pgvector/pgvector:pg16
env:
POSTGRES_DB: nest_db_e2e
POSTGRES_PASSWORD: nest_user_e2e_password
POSTGRES_USER: nest_user_e2e
options: >-
--health-cmd="pg_isready -U nest_user_e2e -d nest_db_e2e -h localhost -p 5432"
--health-interval=5s
--health-timeout=5s
--health-retries=5
ports:
- 5432:5432
cache:
image: redis:8.0.5-alpine3.21
options: >-
--health-cmd="redis-cli ping"
--health-interval=5s
--health-retries=5
--health-timeout=5s
ports:
- 6379:6379
steps:
- name: Check out repository
uses: actions/checkout@8e8c483db84b4bee98b60c0593521ed34d9990e8

- name: Set up Docker buildx
uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f

- name: Setup Backend environment
uses: ./.github/workflows/setup-backend-environment
with:
db_username: nest_user_e2e
db_name: nest_db_e2e

- name: Start Backend in the background
run: |
docker run -d --rm --name e2e-nest-backend \
--env-file backend/.env.e2e.example \
--network host \
-e DJANGO_DB_HOST=localhost \
-e DJANGO_REDIS_AUTH_ENABLED=False \
-e DJANGO_REDIS_HOST=localhost \
-p 9000:9000 \
owasp/nest:test-backend-latest \
sh -c '
python manage.py migrate &&
gunicorn wsgi:application --bind 0.0.0.0:9000
'

- name: Waiting for the backend to be ready
run: |
timeout 5m bash -c '
until wget --spider http://localhost:9000/a; do
echo "Waiting for backend..."
sleep 5
done
'
echo "Backend is up!"

- name: Load Postgres data
env:
PGPASSWORD: nest_user_e2e_password
run: |
pg_restore -h localhost -U nest_user_e2e -d nest_db_e2e < backend/data/nest.dump

- name: Build frontend end-to-end testing image
uses: docker/build-push-action@263435318d21b8e681c14492fe198d362a7d2c83
with:
Expand All @@ -270,7 +330,7 @@ jobs:

- name: Run frontend end-to-end tests
run: |
docker run --env-file frontend/.env.example owasp/nest:test-frontend-e2e-latest pnpm run test:e2e
docker run --env-file frontend/.env.e2e.example owasp/nest:test-frontend-e2e-latest pnpm run test:e2e
timeout-minutes: 10

run-frontend-a11y-tests:
Expand Down Expand Up @@ -324,6 +384,25 @@ jobs:
fi
timeout-minutes: 5

run-graphql-fuzz-tests:
name: Run GraphQL fuzz tests
needs:
- scan-code
- scan-ci-dependencies
uses: ./.github/workflows/run-fuzz-tests.yaml
with:
test-file: graphql_test.py

run-rest-fuzz-tests:
name: Run REST fuzz tests
needs:
- scan-code
- scan-ci-dependencies
uses: ./.github/workflows/run-fuzz-tests.yaml
with:
test-file: rest_test.py
rest-url: http://localhost:9500/api/v0

build-staging-images:
name: Build Staging Images
env:
Expand Down
118 changes: 118 additions & 0 deletions .github/workflows/run-fuzz-tests.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
name: Run fuzz tests

on:
workflow_call:
inputs:
test-file:
description: 'The test file to run fuzz tests on'
required: true
type: string
rest-url:
description: 'The REST API URL to test against'
required: false
type: string
default: 'http://localhost:9500/api/v0'

jobs:
run-fuzz-tests:
name: Run Fuzz Tests
runs-on: ubuntu-latest
timeout-minutes: 20
services:
db:
image: pgvector/pgvector:pg16
env:
POSTGRES_DB: nest_db_fuzz
POSTGRES_PASSWORD: nest_user_fuzz_password
POSTGRES_USER: nest_user_fuzz
options: >-
--health-cmd="pg_isready -U nest_user_fuzz -d nest_db_fuzz -h localhost -p 5432"
--health-interval=5s
--health-retries=5
--health-timeout=5s
ports:
- 5432:5432
cache:
image: redis:8.0.5-alpine3.21
options: >-
--health-cmd="redis-cli ping"
--health-interval=5s
--health-retries=5
--health-timeout=5s
ports:
- 6379:6379
steps:
- name: Check out repository
uses: actions/checkout@8e8c483db84b4bee98b60c0593521ed34d9990e8

- name: Set up Docker buildx
uses: docker/setup-buildx-action@8d2750c68a42422c14e847fe6c8ac0403b4cbd6f

- name: Setup Backend environment
uses: ./.github/workflows/setup-backend-environment
with:
db_username: nest_user_fuzz
db_name: nest_db_fuzz

- name: Run backend with fuzz environment variables
run: |
docker run -d --rm --name fuzz-nest-backend \
--env-file backend/.env.fuzz.example \
--network host \
-e DJANGO_DB_HOST=localhost \
-e DJANGO_REDIS_AUTH_ENABLED=False \
-e DJANGO_REDIS_HOST=localhost \
-p 9500:9500 \
owasp/nest:test-backend-latest \
sh -c '
python manage.py migrate &&
gunicorn wsgi:application --bind 0.0.0.0:9500
'

- name: Waiting for the backend to be ready
run: |
timeout 5m bash -c '
until wget --spider http://localhost:9500/a; do
echo "Waiting for backend..."
sleep 5
done
'
echo "Backend is up!"

- name: Load Postgres data
env:
PGPASSWORD: nest_user_fuzz_password
run: |
set -euo pipefail
if ! pg_restore -h localhost -U nest_user_fuzz -d nest_db_fuzz < backend/data/nest.dump; then
echo "Data loading failed"
exit 1
fi
echo "Data loading completed."

- name: Build Fuzz-testing image
uses: docker/build-push-action@263435318d21b8e681c14492fe198d362a7d2c83
with:
cache-from: |
type=gha
type=registry,ref=owasp/nest:test-fuzz-backend-cache
cache-to: |
type=gha,compression=zstd
context: backend
file: docker/backend/Dockerfile.fuzz
load: true
platforms: linux/amd64
tags: owasp/nest:test-fuzz-backend-latest

- name: Run fuzz tests
env:
TEST_FILE: ${{ inputs.test-file }}
REST_URL: ${{ inputs.rest-url }}
run: |
docker run \
--network host \
-e BASE_URL=http://localhost:9500 \
-e CI=true \
-e REST_URL="$REST_URL" \
-e TEST_FILE="$TEST_FILE" \
owasp/nest:test-fuzz-backend-latest
44 changes: 44 additions & 0 deletions .github/workflows/setup-backend-environment/action.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
name: Set up Backend environment

description: Sets up the Backend environment testing.

inputs:
db_username:
description: 'Database username'
required: true
db_name:
description: 'Database name'
required: true

runs:
using: composite
steps:
- name: Wait for database to be ready
env:
DB_USERNAME: ${{ inputs.db_username }}
DB_NAME: ${{ inputs.db_name }}
run: |
timeout 5m bash -c '
until docker exec ${{ job.services.db.id }} pg_isready -U $DB_USERNAME -d $DB_NAME; do
echo "Waiting for database..."
sleep 5
done
'
shell: bash

- name: Install PostgreSQL client
run: sudo apt-get install -y postgresql-client
shell: bash

- name: Build backend image
uses: docker/build-push-action@263435318d21b8e681c14492fe198d362a7d2c83
with:
cache-from: |
type=gha
cache-to: |
type=gha,compression=zstd
context: backend
file: docker/backend/Dockerfile
load: true
platforms: linux/amd64
tags: owasp/nest:test-backend-latest
13 changes: 13 additions & 0 deletions .github/workflows/update-nest-test-images.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -74,4 +74,17 @@ jobs:
platforms: linux/amd64
push: true
tags: owasp/nest:test-frontend-e2e-latest

- name: Build and push fuzz-test-backend image
uses: docker/build-push-action@263435318d21b8e681c14492fe198d362a7d2c83
with:
cache-from: type=registry,ref=owasp/nest:test-fuzz-backend-cache
cache-to: |
type=gha,compression=zstd
type=registry,ref=owasp/nest:test-fuzz-backend-cache
context: backend
file: docker/backend/Dockerfile.fuzz
platforms: linux/amd64
push: true
tags: owasp/nest:test-fuzz-backend-latest
timeout-minutes: 15
6 changes: 6 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,12 @@ __pycache__
.cache
.coverage
.cursor/rules/snyk_rules.mdc
backend/fuzzing_results/
.DS_Store
.env*
!.env.example
!.env.e2e.example
!.env.fuzz.example
.github/instructions/snyk_rules.instructions.md
.idea
.lighthouseci/
Expand Down Expand Up @@ -44,3 +47,6 @@ logs
node_modules/
TODO
venv/

# Snyk Security Extension - AI Rules (auto-generated)
.cursor/rules/snyk_rules.mdc
56 changes: 56 additions & 0 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -275,6 +275,8 @@ Ensure that all `.env` files are saved in **UTF-8 format without BOM (Byte Order

1. **Load Initial Data**:

- Make sure you have `gzip` installed on your machine.

- Open a new terminal session and run the following command to populate the database with initial data from fixtures:

```bash
Expand Down Expand Up @@ -404,6 +406,60 @@ make test
This command runs tests and checks that coverage threshold requirements are satisfied for both backend and frontend.
**Please note your PR won't be merged if it fails the code tests checks.**

### Running e2e Tests

Run the frontend e2e tests with the following command:

```bash
make test-frontend-e2e
```

This command automatically:

- Starts the database and backend containers
- Runs migrations and loads test data
- Executes the e2e tests
- Cleans up containers when done

For debugging, you can run the e2e backend separately:

```bash
make run-backend-e2e
```

Then load data manually in another terminal:

```bash
make load-data-e2e
```

### Running Fuzz Tests

Run the fuzz tests with the following command:

```bash
make test-fuzz
```

This command automatically:

- Starts the database and backend containers
- Runs migrations and loads test data
- Executes the fuzz tests
- Cleans up containers when done

For debugging, you can run the fuzz backend separately:

```bash
make run-backend-fuzz
```

Then load data manually in another terminal:

```bash
make load-data-fuzz
```

### Test Coverage

- There is a **minimum test coverage requirement** for the **backend** code -- see [pyproject.toml](https://github.com/OWASP/Nest/blob/main/backend/pyproject.toml).
Expand Down
Loading
Loading