ci: merge main to release (#8262)
This commit is contained in:
commit
7f65171c1a
132
.github/workflows/build-base-app.yml
vendored
132
.github/workflows/build-base-app.yml
vendored
|
@ -1,66 +1,66 @@
|
||||||
name: Build Base App Docker Image
|
name: Build Base App Docker Image
|
||||||
|
|
||||||
on:
|
on:
|
||||||
push:
|
push:
|
||||||
branches:
|
branches:
|
||||||
- 'main'
|
- 'main'
|
||||||
paths:
|
paths:
|
||||||
- 'docker/base.Dockerfile'
|
- 'docker/base.Dockerfile'
|
||||||
- 'requirements.txt'
|
- 'requirements.txt'
|
||||||
|
|
||||||
workflow_dispatch:
|
workflow_dispatch:
|
||||||
|
|
||||||
jobs:
|
jobs:
|
||||||
publish:
|
publish:
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
permissions:
|
permissions:
|
||||||
contents: write
|
contents: write
|
||||||
packages: write
|
packages: write
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v4
|
- uses: actions/checkout@v4
|
||||||
with:
|
with:
|
||||||
token: ${{ secrets.GH_COMMON_TOKEN }}
|
token: ${{ secrets.GH_COMMON_TOKEN }}
|
||||||
|
|
||||||
- name: Set Version
|
- name: Set Version
|
||||||
run: |
|
run: |
|
||||||
printf -v CURDATE '%(%Y%m%dT%H%M)T' -1
|
printf -v CURDATE '%(%Y%m%dT%H%M)T' -1
|
||||||
echo "IMGVERSION=$CURDATE" >> $GITHUB_ENV
|
echo "IMGVERSION=$CURDATE" >> $GITHUB_ENV
|
||||||
|
|
||||||
- name: Set up QEMU
|
- name: Set up QEMU
|
||||||
uses: docker/setup-qemu-action@v3
|
uses: docker/setup-qemu-action@v3
|
||||||
|
|
||||||
- name: Set up Docker Buildx
|
- name: Set up Docker Buildx
|
||||||
uses: docker/setup-buildx-action@v3
|
uses: docker/setup-buildx-action@v3
|
||||||
|
|
||||||
- name: Login to GitHub Container Registry
|
- name: Login to GitHub Container Registry
|
||||||
uses: docker/login-action@v3
|
uses: docker/login-action@v3
|
||||||
with:
|
with:
|
||||||
registry: ghcr.io
|
registry: ghcr.io
|
||||||
username: ${{ github.actor }}
|
username: ${{ github.actor }}
|
||||||
password: ${{ secrets.GITHUB_TOKEN }}
|
password: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
|
||||||
- name: Docker Build & Push
|
- name: Docker Build & Push
|
||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
env:
|
env:
|
||||||
DOCKER_BUILD_NO_SUMMARY: true
|
DOCKER_BUILD_NO_SUMMARY: true
|
||||||
with:
|
with:
|
||||||
context: .
|
context: .
|
||||||
file: docker/base.Dockerfile
|
file: docker/base.Dockerfile
|
||||||
platforms: linux/amd64,linux/arm64
|
platforms: linux/amd64,linux/arm64
|
||||||
push: true
|
push: true
|
||||||
tags: |
|
tags: |
|
||||||
ghcr.io/ietf-tools/datatracker-app-base:${{ env.IMGVERSION }}
|
ghcr.io/ietf-tools/datatracker-app-base:${{ env.IMGVERSION }}
|
||||||
ghcr.io/ietf-tools/datatracker-app-base:latest
|
ghcr.io/ietf-tools/datatracker-app-base:latest
|
||||||
|
|
||||||
- name: Update version references
|
- name: Update version references
|
||||||
run: |
|
run: |
|
||||||
sed -i "1s/.*/FROM ghcr.io\/ietf-tools\/datatracker-app-base:${{ env.IMGVERSION }}/" dev/build/Dockerfile
|
sed -i "1s/.*/FROM ghcr.io\/ietf-tools\/datatracker-app-base:${{ env.IMGVERSION }}/" dev/build/Dockerfile
|
||||||
echo "${{ env.IMGVERSION }}" > dev/build/TARGET_BASE
|
echo "${{ env.IMGVERSION }}" > dev/build/TARGET_BASE
|
||||||
|
|
||||||
- name: Commit CHANGELOG.md
|
- name: Commit CHANGELOG.md
|
||||||
uses: stefanzweifel/git-auto-commit-action@v5
|
uses: stefanzweifel/git-auto-commit-action@v5
|
||||||
with:
|
with:
|
||||||
branch: main
|
branch: main
|
||||||
commit_message: 'ci: update base image target version to ${{ env.IMGVERSION }}'
|
commit_message: 'ci: update base image target version to ${{ env.IMGVERSION }}'
|
||||||
file_pattern: dev/build/Dockerfile dev/build/TARGET_BASE
|
file_pattern: dev/build/Dockerfile dev/build/TARGET_BASE
|
||||||
|
|
8
.github/workflows/build.yml
vendored
8
.github/workflows/build.yml
vendored
|
@ -256,6 +256,10 @@ jobs:
|
||||||
username: ${{ github.actor }}
|
username: ${{ github.actor }}
|
||||||
password: ${{ secrets.GITHUB_TOKEN }}
|
password: ${{ secrets.GITHUB_TOKEN }}
|
||||||
|
|
||||||
|
- name: Add feature-latest tag
|
||||||
|
if: ${{ startsWith(github.ref_name, 'feat/') }}
|
||||||
|
run: echo "FEATURE_LATEST_TAG=$(echo $GITHUB_REF_NAME | tr / -)" >> $GITHUB_ENV
|
||||||
|
|
||||||
- name: Build Images
|
- name: Build Images
|
||||||
uses: docker/build-push-action@v6
|
uses: docker/build-push-action@v6
|
||||||
env:
|
env:
|
||||||
|
@ -265,7 +269,9 @@ jobs:
|
||||||
file: dev/build/Dockerfile
|
file: dev/build/Dockerfile
|
||||||
platforms: ${{ github.event.inputs.skiparm == 'true' && 'linux/amd64' || 'linux/amd64,linux/arm64' }}
|
platforms: ${{ github.event.inputs.skiparm == 'true' && 'linux/amd64' || 'linux/amd64,linux/arm64' }}
|
||||||
push: true
|
push: true
|
||||||
tags: ghcr.io/ietf-tools/datatracker:${{ env.PKG_VERSION }}
|
tags: |
|
||||||
|
ghcr.io/ietf-tools/datatracker:${{ env.PKG_VERSION }}
|
||||||
|
${{ env.FEATURE_LATEST_TAG && format('ghcr.io/ietf-tools/datatracker:{0}-latest', env.FEATURE_LATEST_TAG) || null }}
|
||||||
cache-from: type=gha
|
cache-from: type=gha
|
||||||
cache-to: type=gha,mode=max
|
cache-to: type=gha,mode=max
|
||||||
|
|
||||||
|
|
374
.github/workflows/tests.yml
vendored
374
.github/workflows/tests.yml
vendored
|
@ -1,187 +1,187 @@
|
||||||
name: Reusable Tests Workflow
|
name: Reusable Tests Workflow
|
||||||
|
|
||||||
on:
|
on:
|
||||||
workflow_call:
|
workflow_call:
|
||||||
inputs:
|
inputs:
|
||||||
ignoreLowerCoverage:
|
ignoreLowerCoverage:
|
||||||
description: 'Ignore Lower Coverage'
|
description: 'Ignore Lower Coverage'
|
||||||
default: false
|
default: false
|
||||||
required: true
|
required: true
|
||||||
type: boolean
|
type: boolean
|
||||||
skipSelenium:
|
skipSelenium:
|
||||||
description: 'Skip Selenium Tests'
|
description: 'Skip Selenium Tests'
|
||||||
default: false
|
default: false
|
||||||
required: false
|
required: false
|
||||||
type: boolean
|
type: boolean
|
||||||
targetBaseVersion:
|
targetBaseVersion:
|
||||||
description: 'Target Base Image Version'
|
description: 'Target Base Image Version'
|
||||||
default: latest
|
default: latest
|
||||||
required: false
|
required: false
|
||||||
type: string
|
type: string
|
||||||
|
|
||||||
jobs:
|
jobs:
|
||||||
tests-python:
|
tests-python:
|
||||||
name: Python Tests
|
name: Python Tests
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
container: ghcr.io/ietf-tools/datatracker-app-base:${{ inputs.targetBaseVersion }}
|
container: ghcr.io/ietf-tools/datatracker-app-base:${{ inputs.targetBaseVersion }}
|
||||||
|
|
||||||
services:
|
services:
|
||||||
db:
|
db:
|
||||||
image: ghcr.io/ietf-tools/datatracker-db:latest
|
image: ghcr.io/ietf-tools/datatracker-db:latest
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v4
|
- uses: actions/checkout@v4
|
||||||
|
|
||||||
- name: Prepare for tests
|
- name: Prepare for tests
|
||||||
run: |
|
run: |
|
||||||
chmod +x ./dev/tests/prepare.sh
|
chmod +x ./dev/tests/prepare.sh
|
||||||
sh ./dev/tests/prepare.sh
|
sh ./dev/tests/prepare.sh
|
||||||
|
|
||||||
- name: Ensure DB is ready
|
- name: Ensure DB is ready
|
||||||
run: |
|
run: |
|
||||||
/usr/local/bin/wait-for db:5432 -- echo "DB ready"
|
/usr/local/bin/wait-for db:5432 -- echo "DB ready"
|
||||||
|
|
||||||
- name: Run all tests
|
- name: Run all tests
|
||||||
shell: bash
|
shell: bash
|
||||||
run: |
|
run: |
|
||||||
echo "Running checks..."
|
echo "Running checks..."
|
||||||
./ietf/manage.py check
|
./ietf/manage.py check
|
||||||
./ietf/manage.py migrate --fake-initial
|
./ietf/manage.py migrate --fake-initial
|
||||||
echo "Validating migrations..."
|
echo "Validating migrations..."
|
||||||
if ! ( ietf/manage.py makemigrations --dry-run --check --verbosity 3 ) ; then
|
if ! ( ietf/manage.py makemigrations --dry-run --check --verbosity 3 ) ; then
|
||||||
echo "Model changes without migrations found."
|
echo "Model changes without migrations found."
|
||||||
exit 1
|
exit 1
|
||||||
fi
|
fi
|
||||||
if [[ "x${{ inputs.skipSelenium }}" == "xtrue" ]]; then
|
if [[ "x${{ inputs.skipSelenium }}" == "xtrue" ]]; then
|
||||||
echo "Disable selenium tests..."
|
echo "Disable selenium tests..."
|
||||||
rm /usr/bin/geckodriver
|
rm /usr/bin/geckodriver
|
||||||
fi
|
fi
|
||||||
echo "Running tests..."
|
echo "Running tests..."
|
||||||
if [[ "x${{ inputs.ignoreLowerCoverage }}" == "xtrue" ]]; then
|
if [[ "x${{ inputs.ignoreLowerCoverage }}" == "xtrue" ]]; then
|
||||||
echo "Lower coverage failures will be ignored."
|
echo "Lower coverage failures will be ignored."
|
||||||
HOME=/root ./ietf/manage.py test -v2 --validate-html-harder --settings=settings_test --ignore-lower-coverage
|
HOME=/root ./ietf/manage.py test -v2 --validate-html-harder --settings=settings_test --ignore-lower-coverage
|
||||||
else
|
else
|
||||||
HOME=/root ./ietf/manage.py test -v2 --validate-html-harder --settings=settings_test
|
HOME=/root ./ietf/manage.py test -v2 --validate-html-harder --settings=settings_test
|
||||||
fi
|
fi
|
||||||
coverage xml
|
coverage xml
|
||||||
|
|
||||||
- name: Upload geckodriver.log
|
- name: Upload geckodriver.log
|
||||||
uses: actions/upload-artifact@v4
|
uses: actions/upload-artifact@v4
|
||||||
if: ${{ failure() }}
|
if: ${{ failure() }}
|
||||||
with:
|
with:
|
||||||
name: geckodriverlog
|
name: geckodriverlog
|
||||||
path: geckodriver.log
|
path: geckodriver.log
|
||||||
|
|
||||||
- name: Upload Coverage Results to Codecov
|
- name: Upload Coverage Results to Codecov
|
||||||
uses: codecov/codecov-action@v5
|
uses: codecov/codecov-action@v5
|
||||||
with:
|
with:
|
||||||
disable_search: true
|
disable_search: true
|
||||||
files: coverage.xml
|
files: coverage.xml
|
||||||
token: ${{ secrets.CODECOV_TOKEN }}
|
token: ${{ secrets.CODECOV_TOKEN }}
|
||||||
|
|
||||||
- name: Convert Coverage Results
|
- name: Convert Coverage Results
|
||||||
if: ${{ always() }}
|
if: ${{ always() }}
|
||||||
run: |
|
run: |
|
||||||
mv latest-coverage.json coverage.json
|
mv latest-coverage.json coverage.json
|
||||||
|
|
||||||
- name: Upload Coverage Results as Build Artifact
|
- name: Upload Coverage Results as Build Artifact
|
||||||
uses: actions/upload-artifact@v4
|
uses: actions/upload-artifact@v4
|
||||||
if: ${{ always() }}
|
if: ${{ always() }}
|
||||||
with:
|
with:
|
||||||
name: coverage
|
name: coverage
|
||||||
path: coverage.json
|
path: coverage.json
|
||||||
|
|
||||||
tests-playwright:
|
tests-playwright:
|
||||||
name: Playwright Tests
|
name: Playwright Tests
|
||||||
runs-on: macos-latest
|
runs-on: macos-latest
|
||||||
strategy:
|
strategy:
|
||||||
fail-fast: false
|
fail-fast: false
|
||||||
matrix:
|
matrix:
|
||||||
project: [chromium, firefox]
|
project: [chromium, firefox]
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v4
|
- uses: actions/checkout@v4
|
||||||
|
|
||||||
- uses: actions/setup-node@v4
|
- uses: actions/setup-node@v4
|
||||||
with:
|
with:
|
||||||
node-version: '18'
|
node-version: '18'
|
||||||
|
|
||||||
- name: Run all tests
|
- name: Run all tests
|
||||||
run: |
|
run: |
|
||||||
echo "Installing dependencies..."
|
echo "Installing dependencies..."
|
||||||
yarn
|
yarn
|
||||||
echo "Installing Playwright..."
|
echo "Installing Playwright..."
|
||||||
cd playwright
|
cd playwright
|
||||||
mkdir test-results
|
mkdir test-results
|
||||||
npm ci
|
npm ci
|
||||||
npx playwright install --with-deps ${{ matrix.project }}
|
npx playwright install --with-deps ${{ matrix.project }}
|
||||||
echo "Running tests..."
|
echo "Running tests..."
|
||||||
npx playwright test --project=${{ matrix.project }}
|
npx playwright test --project=${{ matrix.project }}
|
||||||
|
|
||||||
- name: Upload Report
|
- name: Upload Report
|
||||||
uses: actions/upload-artifact@v4
|
uses: actions/upload-artifact@v4
|
||||||
if: ${{ always() }}
|
if: ${{ always() }}
|
||||||
continue-on-error: true
|
continue-on-error: true
|
||||||
with:
|
with:
|
||||||
name: playwright-results-${{ matrix.project }}
|
name: playwright-results-${{ matrix.project }}
|
||||||
path: playwright/test-results/
|
path: playwright/test-results/
|
||||||
if-no-files-found: ignore
|
if-no-files-found: ignore
|
||||||
|
|
||||||
tests-playwright-legacy:
|
tests-playwright-legacy:
|
||||||
name: Playwright Legacy Tests
|
name: Playwright Legacy Tests
|
||||||
runs-on: ubuntu-latest
|
runs-on: ubuntu-latest
|
||||||
container: ghcr.io/ietf-tools/datatracker-app-base:${{ inputs.targetBaseVersion }}
|
container: ghcr.io/ietf-tools/datatracker-app-base:${{ inputs.targetBaseVersion }}
|
||||||
strategy:
|
strategy:
|
||||||
fail-fast: false
|
fail-fast: false
|
||||||
matrix:
|
matrix:
|
||||||
project: [chromium, firefox]
|
project: [chromium, firefox]
|
||||||
|
|
||||||
services:
|
services:
|
||||||
db:
|
db:
|
||||||
image: ghcr.io/ietf-tools/datatracker-db:latest
|
image: ghcr.io/ietf-tools/datatracker-db:latest
|
||||||
|
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v4
|
- uses: actions/checkout@v4
|
||||||
|
|
||||||
- name: Prepare for tests
|
- name: Prepare for tests
|
||||||
run: |
|
run: |
|
||||||
chmod +x ./dev/tests/prepare.sh
|
chmod +x ./dev/tests/prepare.sh
|
||||||
sh ./dev/tests/prepare.sh
|
sh ./dev/tests/prepare.sh
|
||||||
|
|
||||||
- name: Ensure DB is ready
|
- name: Ensure DB is ready
|
||||||
run: |
|
run: |
|
||||||
/usr/local/bin/wait-for db:5432 -- echo "DB ready"
|
/usr/local/bin/wait-for db:5432 -- echo "DB ready"
|
||||||
|
|
||||||
- name: Start Datatracker
|
- name: Start Datatracker
|
||||||
run: |
|
run: |
|
||||||
echo "Running checks..."
|
echo "Running checks..."
|
||||||
./ietf/manage.py check
|
./ietf/manage.py check
|
||||||
./ietf/manage.py migrate --fake-initial
|
./ietf/manage.py migrate --fake-initial
|
||||||
echo "Starting datatracker..."
|
echo "Starting datatracker..."
|
||||||
./ietf/manage.py runserver 0.0.0.0:8000 --settings=settings_local &
|
./ietf/manage.py runserver 0.0.0.0:8000 --settings=settings_local &
|
||||||
echo "Waiting for datatracker to be ready..."
|
echo "Waiting for datatracker to be ready..."
|
||||||
/usr/local/bin/wait-for localhost:8000 -- echo "Datatracker ready"
|
/usr/local/bin/wait-for localhost:8000 -- echo "Datatracker ready"
|
||||||
|
|
||||||
- name: Run all tests
|
- name: Run all tests
|
||||||
env:
|
env:
|
||||||
# Required to get firefox to run as root:
|
# Required to get firefox to run as root:
|
||||||
HOME: ""
|
HOME: ""
|
||||||
run: |
|
run: |
|
||||||
echo "Installing dependencies..."
|
echo "Installing dependencies..."
|
||||||
yarn
|
yarn
|
||||||
echo "Installing Playwright..."
|
echo "Installing Playwright..."
|
||||||
cd playwright
|
cd playwright
|
||||||
mkdir test-results
|
mkdir test-results
|
||||||
npm ci
|
npm ci
|
||||||
npx playwright install --with-deps ${{ matrix.project }}
|
npx playwright install --with-deps ${{ matrix.project }}
|
||||||
echo "Running tests..."
|
echo "Running tests..."
|
||||||
npx playwright test --project=${{ matrix.project }} -c playwright-legacy.config.js
|
npx playwright test --project=${{ matrix.project }} -c playwright-legacy.config.js
|
||||||
|
|
||||||
- name: Upload Report
|
- name: Upload Report
|
||||||
uses: actions/upload-artifact@v4
|
uses: actions/upload-artifact@v4
|
||||||
if: ${{ always() }}
|
if: ${{ always() }}
|
||||||
continue-on-error: true
|
continue-on-error: true
|
||||||
with:
|
with:
|
||||||
name: playwright-legacy-results-${{ matrix.project }}
|
name: playwright-legacy-results-${{ matrix.project }}
|
||||||
path: playwright/test-results/
|
path: playwright/test-results/
|
||||||
if-no-files-found: ignore
|
if-no-files-found: ignore
|
||||||
|
|
|
@ -56,6 +56,7 @@ from django.utils import timezone
|
||||||
from django.utils.html import strip_tags
|
from django.utils.html import strip_tags
|
||||||
from django.utils.cache import _generate_cache_key # type: ignore
|
from django.utils.cache import _generate_cache_key # type: ignore
|
||||||
from django.utils.text import slugify
|
from django.utils.text import slugify
|
||||||
|
from django.views.decorators.csrf import ensure_csrf_cookie
|
||||||
from django_stubs_ext import QuerySetAny
|
from django_stubs_ext import QuerySetAny
|
||||||
|
|
||||||
import debug # pyflakes:ignore
|
import debug # pyflakes:ignore
|
||||||
|
@ -283,6 +284,7 @@ def retrieve_search_results(form, all_types=False):
|
||||||
return docs
|
return docs
|
||||||
|
|
||||||
|
|
||||||
|
@ensure_csrf_cookie
|
||||||
def search(request):
|
def search(request):
|
||||||
"""Search for a draft"""
|
"""Search for a draft"""
|
||||||
# defaults for results / meta
|
# defaults for results / meta
|
||||||
|
@ -335,6 +337,7 @@ def search(request):
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@ensure_csrf_cookie
|
||||||
def frontpage(request):
|
def frontpage(request):
|
||||||
form = SearchForm()
|
form = SearchForm()
|
||||||
return render(request, 'doc/frontpage.html', {'form':form})
|
return render(request, 'doc/frontpage.html', {'form':form})
|
||||||
|
|
|
@ -82,6 +82,10 @@ class SecrMeetingTestCase(TestCase):
|
||||||
[cn.slug for cn in new_meeting.group_conflict_types.all()],
|
[cn.slug for cn in new_meeting.group_conflict_types.all()],
|
||||||
post_data['group_conflict_types'],
|
post_data['group_conflict_types'],
|
||||||
)
|
)
|
||||||
|
self.assertEqual(
|
||||||
|
new_meeting.session_request_lock_message,
|
||||||
|
"Session requests for this meeting have not yet opened.",
|
||||||
|
)
|
||||||
|
|
||||||
def test_add_meeting_default_conflict_types(self):
|
def test_add_meeting_default_conflict_types(self):
|
||||||
"""Add meeting should default to same conflict types as previous meeting"""
|
"""Add meeting should default to same conflict types as previous meeting"""
|
||||||
|
|
|
@ -17,7 +17,7 @@ import debug # pyflakes:ignore
|
||||||
from ietf.ietfauth.utils import role_required
|
from ietf.ietfauth.utils import role_required
|
||||||
from ietf.utils.mail import send_mail
|
from ietf.utils.mail import send_mail
|
||||||
from ietf.meeting.forms import duration_string
|
from ietf.meeting.forms import duration_string
|
||||||
from ietf.meeting.helpers import get_meeting, make_materials_directories, populate_important_dates
|
from ietf.meeting.helpers import make_materials_directories, populate_important_dates
|
||||||
from ietf.meeting.models import Meeting, Session, Room, TimeSlot, SchedTimeSessAssignment, Schedule, SchedulingEvent
|
from ietf.meeting.models import Meeting, Session, Room, TimeSlot, SchedTimeSessAssignment, Schedule, SchedulingEvent
|
||||||
from ietf.meeting.utils import add_event_info_to_session_qs
|
from ietf.meeting.utils import add_event_info_to_session_qs
|
||||||
from ietf.name.models import SessionStatusName
|
from ietf.name.models import SessionStatusName
|
||||||
|
@ -223,9 +223,8 @@ def add(request):
|
||||||
)
|
)
|
||||||
meeting.schedule = schedule
|
meeting.schedule = schedule
|
||||||
|
|
||||||
# we want to carry session request lock status over from previous meeting
|
# Create meeting with session requests locked
|
||||||
previous_meeting = get_meeting( int(meeting.number) - 1 )
|
meeting.session_request_lock_message = "Session requests for this meeting have not yet opened."
|
||||||
meeting.session_request_lock_message = previous_meeting.session_request_lock_message
|
|
||||||
meeting.save()
|
meeting.save()
|
||||||
|
|
||||||
populate_important_dates(meeting)
|
populate_important_dates(meeting)
|
||||||
|
|
Loading…
Reference in a new issue