Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
32 commits
Select commit Hold shift + click to select a range
045375e
add management command for importing an existing installation
joshuadavidthomas Nov 16, 2024
73a5c52
add integration tests for management command and adjust command
joshuadavidthomas Nov 17, 2024
e63764f
remove abc from typevar
joshuadavidthomas Nov 17, 2024
59fbb5b
add types for cli
joshuadavidthomas Nov 17, 2024
6eeb9c9
add test stubs for new method
joshuadavidthomas Nov 17, 2024
e0008d3
tweak documentation
joshuadavidthomas Nov 17, 2024
392f023
adjust documentation
joshuadavidthomas Nov 17, 2024
d113549
fix command
joshuadavidthomas Nov 17, 2024
35bad1b
tweakssss
joshuadavidthomas Nov 17, 2024
3fe4ec0
expand
joshuadavidthomas Nov 17, 2024
5744201
add integration test job
joshuadavidthomas Nov 17, 2024
1819a4f
add note about ci
joshuadavidthomas Nov 17, 2024
83c7224
add check for secret
joshuadavidthomas Nov 17, 2024
6e122f6
remove check
joshuadavidthomas Nov 17, 2024
85f46e7
add tests for refresh and adjust fail floor for coverage
joshuadavidthomas Nov 18, 2024
dc577f0
add test for calling management command
joshuadavidthomas Nov 18, 2024
1009534
start import section in README
joshuadavidthomas Nov 18, 2024
a5cd7cb
remove titel
joshuadavidthomas Nov 18, 2024
b45f261
add new model method to docs
joshuadavidthomas Nov 18, 2024
76edb95
swap for coverage
joshuadavidthomas Nov 18, 2024
3649cdc
pare back endpoints to ones actually used
joshuadavidthomas Nov 18, 2024
02b6800
fix types by switching account type to enum
joshuadavidthomas Nov 18, 2024
06a81fe
adjust installation instructions in README
joshuadavidthomas Nov 18, 2024
f8bffe5
adjust formatting
joshuadavidthomas Nov 18, 2024
264792e
change to subsections
joshuadavidthomas Nov 18, 2024
c849fe3
update changelog
joshuadavidthomas Nov 18, 2024
6d9355d
update changelog
joshuadavidthomas Nov 18, 2024
8c28224
update docs
joshuadavidthomas Nov 18, 2024
37883b7
update docs
joshuadavidthomas Nov 18, 2024
26839f8
adjust
joshuadavidthomas Nov 18, 2024
1c98f04
adjust wording
joshuadavidthomas Nov 18, 2024
ae0cf21
explicit name of command
joshuadavidthomas Nov 18, 2024
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
8 changes: 8 additions & 0 deletions .env.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
TEST_ACCOUNT_NAME=
TEST_ACCOUNT_TYPE=
TEST_APP_ID=
TEST_CLIENT_ID=
TEST_INSTALLATION_ID=
TEST_NAME=
TEST_PRIVATE_KEY=""
TEST_WEBHOOK_SECRET=""
25 changes: 25 additions & 0 deletions .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,31 @@ jobs:
if: ${{ contains(needs.*.result, 'failure') }}
run: exit 1

integration:
runs-on: ubuntu-latest
environment: integration
steps:
- uses: actions/checkout@v4

- name: Install uv
uses: astral-sh/setup-uv@v3
with:
enable-cache: true
version: ${{ env.UV_VERSION }}

- name: Run tests with integration tests enabled
env:
TEST_ACCOUNT_NAME: ${{ vars.TEST_ACCOUNT_NAME }}
TEST_ACCOUNT_TYPE: ${{ vars.TEST_ACCOUNT_TYPE }}
TEST_APP_ID: ${{ vars.TEST_APP_ID }}
TEST_CLIENT_ID: ${{ vars.TEST_CLIENT_ID }}
TEST_INSTALLATION_ID: ${{ vars.TEST_INSTALLATION_ID }}
TEST_NAME: ${{ vars.TEST_NAME }}
TEST_PRIVATE_KEY: ${{ secrets.TEST_PRIVATE_KEY }}
TEST_WEBHOOK_SECRET: ${{ secrets.TEST_WEBHOOK_SECRET }}
run: |
uv run nox --session "coverage" -- --integration

types:
runs-on: ubuntu-latest
steps:
Expand Down
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,9 @@ and this project attempts to adhere to [Semantic Versioning](https://semver.org/
- `aget_repos`/`get_repos` for retrieving all repositories accessible to an app installation.
- Added `get_gh_client` model method to `Installation` model.
- Added `aget_repos`/`get_repos` model method to `installation`
- Added `arefresh_from_gh`/`refresh_from_gh` model methods to `Installation` model for syncing local data with GitHub.
- Created a new management command namespace, `python manage.py github`, for all django-github-app management commands.
- Added a new management command to `github` namespace, `python manage.py github import-app`, for importing an existing GitHub App and installation.

## [0.1.0]

Expand Down
106 changes: 96 additions & 10 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ We adhere to Django's Code of Conduct in all interactions and expect all contrib

### `Justfile`

The repository includes a `Justfile` that provides all common development tasks with a consistent interface. Running `just` without arguments shows all available commands and their descriptions:
The repository includes a `Justfile` that provides all common development tasks with a consistent interface. Running `just` without arguments shows all available commands and their descriptions.

<!-- [[[cog
import subprocess
Expand Down Expand Up @@ -70,16 +70,17 @@ The following instructions will use `uv` and assume a Unix-like operating system

Windows users will need to adjust commands accordingly, though the core workflow remains the same.

Alternatively, any Python package manager that supports installing from `pyproject.toml` ([PEP 621](https://peps.python.org/pep-0621/)) can be used. If not using `uv`, ensure you have Python installed from [python.org](https://www.python.org/).
Alternatively, any Python package manager that supports installing from `pyproject.toml` ([PEP 621](https://peps.python.org/pep-0621/)) can be used. If not using `uv`, ensure you have Python installed from [python.org](https://www.python.org/) or another source such as [`pyenv`](https://github.com/pyenv/pyenv).

1. Fork the repository and clone it locally.
2. Use `uv` too bootstrap your development environment:

```bash
uv python install
uv sync --locked
# just bootstrap
```
2. Use `uv` to bootstrap your development environment.

```bash
uv python install
uv sync --locked
# just bootstrap
```

This will install the correct Python version, create and configure a virtual environment, and install all dependencies.

Expand All @@ -101,7 +102,7 @@ uv run nox --session tests
# just testall
```

Both can be passed additional arguments that will be provided to `pytest`:
Both can be passed additional arguments that will be provided to `pytest`.

```bash
uv run nox --session test -- -v --last-failed
Expand All @@ -123,6 +124,91 @@ uv run nox --session coverage

All pull requests must include tests to maintain 100% coverage. Coverage configuration can be found in the `[tools.coverage.*]` sections of [`pyproject.toml`](pyproject.toml).

### Integration Tests

Integration tests in [`tests/integration`](tests/integration) verify actual interactions with GitHub's API and webhooks. These tests are skipped by default and require:

- A GitHub App in your account
- Environment variables configured with the App's credentials

To enable integration tests, pass `--integration` to any test command:

```bash
uv run nox --session test -- --integration
# just test --integration
```

#### Setting up a Test GitHub App

1. Create a new GitHub App.

- Go to GitHub Developer Settings > GitHub Apps > New GitHub App
- Name: `@<username> - django-github-app tests` (must be unique on GitHub, max 34 characters)
- Homepage URL: Your fork's URL (e.g., `https://github.com/<username>/django-github-app`)
- Webhooks: Disable by unchecking "Active" (no webhook tests currently implemented)
- Permissions:
- Repository: Metadata (Read-only)
- Installation: "Only on this account"

2. After creation, collect these values:

- App ID (from app settings)
- Client ID (from app settings)
- Private key (generate and download)
- Installation ID (from URL after installing: `https://github.com/settings/installations/<ID>`)

3. Configure environment variables.

Using direnv (recommended):

```bash
cp .env.example .env
```

Edit the new `.env` file with the values collected above.

Or manually export:

```bash
export TEST_ACCOUNT_NAME="<username>"
# etc...
```

See [`.env.example`](.env.example) for all required variables.

#### Setting up CI Integration Tests

If you want integration tests to run in CI on your fork:

1. Go to your fork's repository settings on GitHub

2. Under "Environments", create a new environment named `integration`

3. Add the following secrets and variables to the environment:

- Secrets
- `TEST_PRIVATE_KEY`
- `TEST_WEBHOOK_SECRET`
- Variables
- `TEST_ACCOUNT_NAME`
- `TEST_ACCOUNT_TYPE`
- `TEST_APP_ID`
- `TEST_CLIENT_ID`
- `TEST_INSTALLATION_ID`
- `TEST_NAME`

> [!NOTE]
> Integration tests in CI will only run with access to these environment secrets. This is a security feature - fork PRs cannot access these secrets unless explicitly granted by repository maintainers.

#### Security Considerations

The integration test setup is designed to be secure:

- The test GitHub App requires minimal permissions (read-only metadata access)
- It's installed only on your personal account
- In CI, tests run in a protected GitHub Environment with restricted secret access
- Fork PRs cannot access integration test secrets (managed automatically by GitHub Actions)

## Linting and Formatting

This project enforces code quality standards using [`pre-commit`](https://github.com/pre-commit/pre-commit).
Expand Down Expand Up @@ -155,7 +241,7 @@ Configuration for these tools can be found in:

## Continuous Integration

This project uses GitHub Actions for CI/CD. The workflows can be found in [`.github/workflows/`](.github/workflows/):
This project uses GitHub Actions for CI/CD. The workflows can be found in [`.github/workflows/`](.github/workflows/).

- [`test.yml`](.github/workflows/test.yml) - Runs on pushes to the `main` branch and on all PRs
- Tests across Python/Django version matrix
Expand Down
21 changes: 19 additions & 2 deletions Justfile
Original file line number Diff line number Diff line change
Expand Up @@ -24,15 +24,32 @@ bootstrap:
uv python install
uv sync --locked

coverage:
@just nox coverage
coverage *ARGS:
@just nox coverage {{ ARGS }}

lint:
@just nox lint

lock *ARGS:
uv lock {{ ARGS }}

manage *COMMAND:
#!/usr/bin/env python
import sys

try:
from django.conf import settings
from django.core.management import execute_from_command_line
except ImportError as exc:
raise ImportError(
"Couldn't import Django. Are you sure it's installed and "
"available on your PYTHONPATH environment variable? Did you "
"forget to activate a virtual environment?"
) from exc

settings.configure(INSTALLED_APPS=["django_github_app"])
execute_from_command_line(sys.argv + "{{ COMMAND }}".split(" "))

test *ARGS:
@just nox test {{ ARGS }}

Expand Down
Loading