diff --git a/.github/workflows/codespell.yml b/.github/workflows/codespell.yml index 45fc51e80..1d9616fcc 100644 --- a/.github/workflows/codespell.yml +++ b/.github/workflows/codespell.yml @@ -3,9 +3,9 @@ name: Codespell on: push: - branches: [milgram] + branches: [nightingale] pull_request: - branches: [milgram] + branches: [nightingale] permissions: contents: read diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml new file mode 100644 index 000000000..421e75984 --- /dev/null +++ b/.github/workflows/tests.yml @@ -0,0 +1,67 @@ +name: Tests + +on: + push: + branches: [nightingale] + pull_request: + branches: [nightingale] + +# Cancel superseded runs on the same ref to save runner minutes. +concurrency: + group: ${{ github.workflow }}-${{ github.ref }} + cancel-in-progress: true + +jobs: + test: + name: pytest (${{ matrix.os }}, py${{ matrix.python-version }}) + runs-on: ${{ matrix.os }} + timeout-minutes: 15 + strategy: + fail-fast: false + matrix: + os: [ubuntu-latest, macos-latest] + python-version: ["3.10", "3.13"] + + env: + QT_QPA_PLATFORM: offscreen + SDL_VIDEODRIVER: dummy + + steps: + - uses: actions/checkout@v4 + + - uses: actions/setup-python@v5 + with: + python-version: ${{ matrix.python-version }} + cache: pip + + # PyQt6 wheels need EGL/GL system libraries on headless Linux runners. + # Runner DNS intermittently fails for *.ubuntu.com, so apt sources + # are repointed to mirrors.kernel.org before updating/installing. + - name: Install Qt system dependencies (Linux) + if: runner.os == 'Linux' + run: | + . /etc/os-release + sudo mv /etc/apt/sources.list.d/*.sources /etc/apt/sources.list.d/*.list /tmp/ 2>/dev/null || true + sudo rm -f /etc/apt/sources.list + for pocket in "" -updates -security; do + echo "deb https://mirrors.kernel.org/ubuntu $VERSION_CODENAME$pocket main restricted universe multiverse" | sudo tee -a /etc/apt/sources.list + done + for attempt in 1 2 3; do + if sudo apt-get update && sudo apt-get install -y --no-install-recommends \ + libegl1 libgl1 libxkbcommon0 libdbus-1-3 libfontconfig1; then + exit 0 + fi + echo "apt attempt $attempt failed; retrying in 15s..." + sleep 15 + done + exit 1 + + # conftest.py puts the repo root on sys.path, so tests exercise the + # source tree; opensesame-core provides the third-party dependencies. + - name: Install dependencies + run: | + python -m pip install --upgrade pip + pip install opensesame-core pytest pygame imageio imageio-ffmpeg + + - name: Run tests + run: python -m pytest tests/ -q diff --git a/.gitignore b/.gitignore new file mode 100644 index 000000000..1e79a571f --- /dev/null +++ b/.gitignore @@ -0,0 +1,121 @@ +# Byte-compiled / optimized / DLL files +__pycache__/ +*.py[cod] +*$py.class + +# Virtual environments +.venv/ +venv/ +env/ +ENV/ + +# Distribution / packaging +.Python +build/ +develop-eggs/ +dist/ +downloads/ +eggs/ +.eggs/ +lib64/ +parts/ +sdist/ +var/ +wheels/ +*.egg-info/ +.installed.cfg +*.egg + +# PyInstaller +*.manifest +*.spec + +# Installer logs +pip-log.txt +pip-delete-this-directory.txt + +# Unit test / coverage reports +htmlcov/ +.tox/ +.nox/ +.coverage +.coverage.* +.cache +nosetests.xml +coverage.xml +*.cover +*.py,cover +.hypothesis/ +.pytest_cache/ + +# Translations +*.mo +*.pot + +# Django stuff: +*.log +local_settings.py +db.sqlite3 + +# Flask stuff: +instance/ +.webassets-cache + +# Scrapy stuff: +.scrapy + +# Sphinx documentation +docs/_build/ + +# PyBuilder +target/ + +# Jupyter Notebook +.ipynb_checkpoints + +# pyenv +.python-version + +# pipenv +Pipfile.lock + +# UV +uv.lock + +# poetry +poetry.lock + +# macOS +.DS_Store +.AppleDouble +.LSOverride +Icon? +._* +.Spotlight-V100 +.Trashes + +# Windows +Thumbs.db +ehthumbs.db +Desktop.ini +$RECYCLE.BIN/ + +# Linux +*~ +.fuse_hidden* + +# Editor / IDE +.idea/ +.vscode/ +*.swp +*.swo +*~ +.project +.pydevproject +.settings/ + +# OpenSesame test artifacts (tests drop outputs in the repo root) +/tmp.osexp +/test_*.png +/test_*.csv +/test_*.xlsx