Skip to content

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

3 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

gitpay-worker

Git-backed storage worker for Gitpay Payment Requests.

Each payment request gets an isolated Git repository under the creator user. Every file change is committed and automatically tagged as a sequential release (v1, v2, …). Only the authenticated creator can access their repositories.

API (local) http://localhost:3001
Swagger UI http://localhost:3001/docs
ReDoc http://localhost:3001/redoc
OpenAPI http://localhost:3001/openapi.json
Human docs (Jekyll) docs/ → GitHub Pages

Features

  • Per payment request Git repos — full history, not a blind blob store
  • Automatic release tagsv1, v2, … on every successful commit
  • ZIP & file download — export the whole tree or a single file at HEAD or a release tag
  • User-scoped authentication — service token + X-User-Id, or per-user API keys; ownership enforced
  • Stripe-style documentation — guides + API reference (Jekyll / GitHub Pages) linked to live OpenAPI
  • Postman + cURL examples — importable collection under examples/
  • Test coverage ≥ 80% — enforced via pytest-cov (--cov-fail-under=80)

Quick start

Requirements

  • Python 3.11+
  • Git available on PATH

Install

python -m venv .venv
source .venv/bin/activate   # Windows: .venv\Scripts\activate
pip install -r requirements.txt
cp .env.example .env        # edit tokens and storage path

Configure (.env)

PORT=3001
INTERNAL_API_TOKEN=dev-secret
USER_API_KEYS={"user-1":"user-1-secret-key","user-2":"user-2-secret-key"}
GITPAY_REPO_STORAGE_ROOT=./storage/git-repos
GIT_AUTHOR_NAME=Gitpay
GIT_AUTHOR_EMAIL=noreply@gitpay.me
Variable Purpose
INTERNAL_API_TOKEN Shared secret for service-to-service calls
USER_API_KEYS JSON map user_id → api_key for direct user auth
GITPAY_REPO_STORAGE_ROOT Root directory for on-disk repos
GIT_AUTHOR_* Commit author identity written into each repo

Run

uvicorn app.main:app --host 0.0.0.0 --port 3001 --reload

Authentication

Two modes; both require that the authenticated user matches creator_user_id.

1. Service (backend → worker)

Authorization: Bearer <INTERNAL_API_TOKEN>
X-User-Id: <creator_user_id>

2. User API key

Authorization: Bearer <user_api_key>

If another user tries to access a repo, the worker returns 403.

Details: docs/guides/authentication.md


API overview

Method Path Description
GET /health Health check
POST /repositories/init Create repo + tag v1
PUT /repositories/file Create/update file + next tag
POST /repositories/files List tracked files
POST /repositories/read-file Read at HEAD / commit / tag (JSON)
DELETE /repositories/file Delete file + next tag
POST /repositories/versions List release tags
POST /repositories/zip Download repo as ZIP (optional tag/commit)
POST /repositories/download-file Download one file as attachment

Mutating responses include commit_sha and version_tag.
Download endpoints return binary bodies with Content-Disposition: attachment and X-Commit-Sha / X-Version-Tag headers.

Interactive reference: run the server and open /docs.
Curated docs: docs/api/.

Minimal cURL

export BASE=http://localhost:3001
export TOKEN=dev-secret
export USER_ID=user-1

curl -sS -X POST "$BASE/repositories/init" \
  -H "Authorization: Bearer $TOKEN" \
  -H "X-User-Id: $USER_ID" \
  -H "Content-Type: application/json" \
  -d '{"creator_user_id":"user-1","payment_request_id":"pr-100"}'

Full script: examples/curl/full-flow.sh


Postman

  1. Import examples/postman/gitpay-worker.postman_collection.json
  2. Optionally import examples/postman/gitpay-worker.postman_environment.json
  3. Set baseUrl, token, userId, paymentRequestId
  4. Run Health → Init → Save → List → Read → Versions → Zip → Download file → Delete

You can also import OpenAPI from http://localhost:3001/openapi.json.


Versioning (release tags)

Every successful commit is tagged:

init  → v1
save  → v2
save  → v3
delete → v4

Read a historical snapshot with version_tag on /repositories/read-file, or list tags via /repositories/versions.

Guide: docs/guides/versioning.md


Storage layout

$GITPAY_REPO_STORAGE_ROOT/
  users/<creator_user_id>/payment-requests/<payment_request_id>/repo/

Documentation (Jekyll / GitHub Pages)

Human docs live in docs/ (Stripe-style Guides + API Reference, cross-linked).

Preview locally

cd docs
bundle install
bundle exec jekyll serve
# open http://127.0.0.1:4000/gitpay-worker/

Publish

GitHub Actions workflow .github/workflows/docs.yml builds the Jekyll site and deploys to GitHub Pages on pushes to main that touch docs/.

Enable Settings → Pages → Source: GitHub Actions on the repository.

If the repo name is not gitpay-worker, update baseurl in docs/_config.yml.

Docs layer Location
How it works / auth / tags docs/guides/
Endpoint reference docs/api/
Auto-generated OpenAPI live /openapi.json, /docs, /redoc

Development

Tests & coverage

pytest
# or: pytest -q --cov=app --cov-report=term-missing

Coverage is required to stay ≥ 80% (pytest.ini--cov-fail-under=80). CI runs the same checks (.github/workflows/ci.yml).

Project layout

app/
  main.py                 # FastAPI app + OpenAPI security schemes
  core/                   # auth, config, paths, locks, schemas
  routes/repositories.py  # HTTP endpoints
  services/               # git_service, repo_service
docs/                     # Jekyll site (GitHub Pages)
examples/
  curl/full-flow.sh
  postman/                # Collection + environment
tests/                    # pytest suite

License

See LICENSE.

Releases

Packages

Contributors

Languages