Compare commits
15 Commits
claude/add
...
main
| Author | SHA1 | Date | |
|---|---|---|---|
| 506ac612bc | |||
| 30edc307af | |||
| 20adae3675 | |||
| cd7d529b86 | |||
| 15504ecba3 | |||
| e98ef96b2e | |||
| 98eb1083eb | |||
| 3aa2a2583d | |||
| 5b441b3698 | |||
| e45a94f260 | |||
| c088f1003b | |||
| e0e4092218 | |||
| 893274ca6a | |||
| 0601d9e6a0 | |||
| 91f5f4ba7c |
47
.github/workflows/deploy-coolify.yml
vendored
Normal file
47
.github/workflows/deploy-coolify.yml
vendored
Normal file
@@ -0,0 +1,47 @@
|
||||
name: "Deploy to Coolify"
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
deploy:
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
steps:
|
||||
- name: Check out repository
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
submodules: recursive
|
||||
|
||||
- name: Login to Gitea Container Registry
|
||||
uses: docker/login-action@v4
|
||||
with:
|
||||
registry: gitea.bchen.dev
|
||||
username: ${{ github.actor }}
|
||||
password: ${{ secrets.PAT }}
|
||||
|
||||
- name: Set up Docker Buildx
|
||||
uses: docker/setup-buildx-action@v4
|
||||
|
||||
- name: Build and push
|
||||
uses: docker/build-push-action@v7
|
||||
with:
|
||||
context: .
|
||||
push: true
|
||||
tags: gitea.bchen.dev/${{ github.actor }}/project-inter-server:latest
|
||||
|
||||
- name: Set up Tailscale
|
||||
uses: tailscale/github-action@v4
|
||||
with:
|
||||
oauth-client-id: ${{ secrets.TS_OAUTH_CLIENT_ID }}
|
||||
oauth-secret: ${{ secrets.TS_OAUTH_SECRET }}
|
||||
tags: tag:ci
|
||||
use-cache: false
|
||||
tailscaled-args: --tun=userspace-networking --socks5-server=localhost:1055 --outbound-http-proxy-listen=localhost:1055
|
||||
|
||||
- name: Deploy to Coolify
|
||||
run: |
|
||||
curl --request POST '${{ secrets.COOLIFY_WEBHOOK }}' --header 'Authorization: Bearer ${{ secrets.COOLIFY_TOKEN }}'
|
||||
60
.github/workflows/deploy.yml
vendored
60
.github/workflows/deploy.yml
vendored
@@ -1,60 +0,0 @@
|
||||
name: "Deploy to birb co."
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
deploy:
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
steps:
|
||||
- name: Check out repository
|
||||
uses: actions/checkout@v3
|
||||
|
||||
# See documentation: https://github.com/tailscale/github-action?tab=readme-ov-file
|
||||
- name: Connect to Tailscale
|
||||
uses: tailscale/github-action@v4
|
||||
with:
|
||||
oauth-client-id: ${{ secrets.TS_OAUTH_CLIENT_ID }}
|
||||
oauth-secret: ${{ secrets.TS_OAUTH_CLIENT_SECRET }}
|
||||
tags: tag:ci
|
||||
|
||||
- name: Set up SSH key
|
||||
run: |
|
||||
mkdir -p ~/.ssh
|
||||
echo "${{ secrets.SSH_PRIVATE_KEY }}" > ~/.ssh/id_ed25519
|
||||
chmod 600 ~/.ssh/id_ed25519
|
||||
ssh-keyscan ${{ vars.HOST }} >> ~/.ssh/known_hosts
|
||||
|
||||
- name: Remove directory from server
|
||||
run: |
|
||||
ssh -i ~/.ssh/id_ed25519 ${{ vars.USERNAME }}@${{ vars.HOST }} << 'EOF'
|
||||
rm -rf ~/${{ vars.DIRECTORY_NAME }}
|
||||
EOF
|
||||
|
||||
# Avoid needing to set up SSH access to GitHub for this user
|
||||
- name: Transfer repository files to server
|
||||
run: |
|
||||
scp -i ~/.ssh/id_ed25519 -r ./* ${{ vars.USERNAME }}@${{ vars.HOST }}:~/${{ vars.DIRECTORY_NAME }}
|
||||
|
||||
- name: Deploy on server with Docker
|
||||
run: |
|
||||
ssh -i ~/.ssh/id_ed25519 ${{ vars.USERNAME }}@${{ vars.HOST }} << 'EOF'
|
||||
cd ~/${{ vars.DIRECTORY_NAME }}
|
||||
export APNS_IS_PRODUCTION=${{ secrets.APNS_IS_PRODUCTION }}
|
||||
export APNS_BUNDLE_ID=${{ secrets.APNS_BUNDLE_ID }}
|
||||
export APNS_TEAM_ID=${{ secrets.APNS_TEAM_ID }}
|
||||
export APNS_KEY_ID=${{ secrets.APNS_KEY_ID }}
|
||||
export APNS_PRIVATE_KEY=${{ secrets.APNS_PRIVATE_KEY }}
|
||||
export PARKING_LOGGING_INTERVAL_MS=${{ secrets.PARKING_LOGGING_INTERVAL_MS }}
|
||||
export RATE_LIMITS_DISABLED=${{ secrets.RATE_LIMITS_DISABLED }}
|
||||
export RATE_LIMIT_WINDOW_MS=${{ secrets.RATE_LIMIT_WINDOW_MS }}
|
||||
export RATE_LIMIT_DELAY_AFTER_REQUESTS=${{ secrets.RATE_LIMIT_DELAY_AFTER_REQUESTS }}
|
||||
export RATE_LIMIT_DELAY_MULTIPLIER_MS=${{ secrets.RATE_LIMIT_DELAY_MULTIPLIER_MS }}
|
||||
export DOCKER_HOST=unix://$XDG_RUNTIME_DIR/docker.sock
|
||||
docker compose -f docker-compose.prod.yml down --remove-orphans
|
||||
docker compose -f docker-compose.prod.yml up -d --build
|
||||
EOF
|
||||
103
AGENTS.md
Normal file
103
AGENTS.md
Normal file
@@ -0,0 +1,103 @@
|
||||
# CLAUDE.md
|
||||
|
||||
This file provides guidance to all agents when working with code in this repository.
|
||||
|
||||
## Development Commands
|
||||
|
||||
### Core Development
|
||||
|
||||
```bash
|
||||
# Start development server with hot reloading
|
||||
docker compose run dev
|
||||
|
||||
# Run comprehensive test suite
|
||||
docker compose run test
|
||||
|
||||
# Generate GraphQL TypeScript types
|
||||
npm run generate
|
||||
|
||||
# Build for development (install, codegen, tsc)
|
||||
npm run build:dev
|
||||
```
|
||||
|
||||
Only use Docker Compose for running tests, and only use `docker compose run test`
|
||||
to run tests; don't try to run tests for individual files.
|
||||
|
||||
## Architecture Overview
|
||||
|
||||
Project Inter Server is a GraphQL-based backend for college transit tracking with real-time shuttle data, parking availability, and push notifications.
|
||||
|
||||
- InterchangeSystem: Central orchestrator for shuttles, parking, and notifications
|
||||
- Use `InterchangeSystem.build()` in production
|
||||
- Use `InterchangeSystem.buildForTesting()` in tests
|
||||
|
||||
- Repository Pattern (data access abstraction)
|
||||
- Shuttle: `UnoptimizedInMemoryShuttleRepository`
|
||||
- Parking: `InMemoryParkingRepository`
|
||||
- Notifications: `RedisNotificationRepository` (prod) / `InMemoryNotificationRepository` (test)
|
||||
|
||||
- Data Loaders (external API integration)
|
||||
- `ApiBasedShuttleRepositoryLoader` – Passio GO! API
|
||||
- `ChapmanApiBasedParkingRepositoryLoader` – Parking data
|
||||
- `TimedApiBasedRepositoryLoader` – Periodic refresh wrapper
|
||||
|
||||
- Notification System
|
||||
- `ETANotificationScheduler` – Shuttle arrival notifications
|
||||
- `AppleNotificationSender` – APNS integration
|
||||
|
||||
## GraphQL
|
||||
|
||||
- Schema definition: `schema.graphqls`
|
||||
- Generated types: `src/generated/`
|
||||
- Resolvers: `src/resolvers/`
|
||||
- Resolver merge: `src/MergedResolvers.ts`
|
||||
|
||||
## Directory Structure
|
||||
|
||||
- `src/entities/` – Core business logic
|
||||
- `src/repositories/` – Data access layer
|
||||
- `src/loaders/` – External API integrations
|
||||
- `src/notifications/` – Push notification system
|
||||
- `src/resolvers/` – GraphQL resolvers and tests
|
||||
- `testHelpers/` – Test utilities and mock data
|
||||
|
||||
## Docker Services
|
||||
|
||||
- `dev` – Development server with hot reload
|
||||
- `test` – Unit/integration tests
|
||||
- `redis` – Persistent Redis
|
||||
- `redis-no-persistence` – Ephemeral Redis for tests
|
||||
|
||||
## Testing Patterns
|
||||
|
||||
- Prefer `buildForTesting()` to construct systems in tests.
|
||||
- Mock external APIs using JSON snapshots under `testHelpers/jsonSnapshots`.
|
||||
- Use in-memory repositories for speed where possible.
|
||||
- When adding features that affect API output, add focused resolver tests in the corresponding `src/resolvers/__tests__` file.
|
||||
- Separate unit tests from integration tests where practical to keep feedback fast and failures well-scoped.
|
||||
|
||||
## Development Guidelines
|
||||
|
||||
### General Guidelines
|
||||
|
||||
- Use test-driven development where possible. Write tests before implementation and run them before and after changes.
|
||||
- Use Docker Compose for tests. Run `docker compose run test` so you can see full output.
|
||||
|
||||
### Git Workflow
|
||||
|
||||
- Name pull requests after their branch name.
|
||||
|
||||
### Code Style
|
||||
|
||||
- Prefer arrow functions, especially within classes.
|
||||
- Keep changes minimal and focused; avoid unrelated refactors. Mention incidental issues separately.
|
||||
- Respect existing interfaces and types; use non-destructive edits.
|
||||
|
||||
### Agent Tips
|
||||
|
||||
- Write or update tests alongside changes; validate with `docker compose run test`.
|
||||
- When touching GraphQL resolvers, co-locate new tests in `src/resolvers/__tests__`.
|
||||
|
||||
## Multi-tenant Support
|
||||
|
||||
Currently supports Chapman University (Passio System ID: `263`). Each university system uses isolated repositories and configuration. New systems should be added via `InterchangeSystem` configuration and appropriate loaders.
|
||||
94
CLAUDE.md
94
CLAUDE.md
@@ -1,93 +1 @@
|
||||
# CLAUDE.md
|
||||
|
||||
This file provides guidance to Claude Code when working with code in this repository.
|
||||
|
||||
## Development Commands
|
||||
|
||||
### Core Development
|
||||
```bash
|
||||
# Start development server with hot reloading
|
||||
docker compose run dev
|
||||
|
||||
# Run comprehensive test suite
|
||||
docker compose run test
|
||||
|
||||
# Generate GraphQL TypeScript types
|
||||
npm run generate
|
||||
|
||||
# Build for development (install, codegen, tsc)
|
||||
npm run build:dev
|
||||
```
|
||||
|
||||
Only use Docker Compose for running tests, and only use `docker compose run test`
|
||||
to run tests; don't try to run tests for individual files.
|
||||
|
||||
## Architecture Overview
|
||||
|
||||
Project Inter Server is a GraphQL-based backend for college transit tracking with real-time shuttle data, parking availability, and push notifications.
|
||||
|
||||
- InterchangeSystem: Central orchestrator for shuttles, parking, and notifications
|
||||
- Use `InterchangeSystem.build()` in production
|
||||
- Use `InterchangeSystem.buildForTesting()` in tests
|
||||
|
||||
- Repository Pattern (data access abstraction)
|
||||
- Shuttle: `UnoptimizedInMemoryShuttleRepository`
|
||||
- Parking: `InMemoryParkingRepository`
|
||||
- Notifications: `RedisNotificationRepository` (prod) / `InMemoryNotificationRepository` (test)
|
||||
|
||||
- Data Loaders (external API integration)
|
||||
- `ApiBasedShuttleRepositoryLoader` – Passio GO! API
|
||||
- `ChapmanApiBasedParkingRepositoryLoader` – Parking data
|
||||
- `TimedApiBasedRepositoryLoader` – Periodic refresh wrapper
|
||||
|
||||
- Notification System
|
||||
- `ETANotificationScheduler` – Shuttle arrival notifications
|
||||
- `AppleNotificationSender` – APNS integration
|
||||
|
||||
## GraphQL
|
||||
- Schema definition: `schema.graphqls`
|
||||
- Generated types: `src/generated/`
|
||||
- Resolvers: `src/resolvers/`
|
||||
- Resolver merge: `src/MergedResolvers.ts`
|
||||
|
||||
## Directory Structure
|
||||
- `src/entities/` – Core business logic
|
||||
- `src/repositories/` – Data access layer
|
||||
- `src/loaders/` – External API integrations
|
||||
- `src/notifications/` – Push notification system
|
||||
- `src/resolvers/` – GraphQL resolvers and tests
|
||||
- `testHelpers/` – Test utilities and mock data
|
||||
|
||||
## Docker Services
|
||||
- `dev` – Development server with hot reload
|
||||
- `test` – Unit/integration tests
|
||||
- `redis` – Persistent Redis
|
||||
- `redis-no-persistence` – Ephemeral Redis for tests
|
||||
|
||||
## Testing Patterns
|
||||
- Prefer `buildForTesting()` to construct systems in tests.
|
||||
- Mock external APIs using JSON snapshots under `testHelpers/jsonSnapshots`.
|
||||
- Use in-memory repositories for speed where possible.
|
||||
- When adding features that affect API output, add focused resolver tests in the corresponding `src/resolvers/__tests__` file.
|
||||
- Separate unit tests from integration tests where practical to keep feedback fast and failures well-scoped.
|
||||
|
||||
## Development Guidelines
|
||||
|
||||
### General Guidelines
|
||||
- Use test-driven development where possible. Write tests before implementation and run them before and after changes.
|
||||
- Use Docker Compose for tests. Run `docker compose run test` so you can see full output.
|
||||
|
||||
### Git Workflow
|
||||
- Name pull requests after their branch name.
|
||||
|
||||
### Code Style
|
||||
- Prefer arrow functions, especially within classes.
|
||||
- Keep changes minimal and focused; avoid unrelated refactors. Mention incidental issues separately.
|
||||
- Respect existing interfaces and types; use non-destructive edits.
|
||||
|
||||
### Agent Tips
|
||||
- Write or update tests alongside changes; validate with `docker compose run test`.
|
||||
- When touching GraphQL resolvers, co-locate new tests in `src/resolvers/__tests__`.
|
||||
|
||||
## Multi-tenant Support
|
||||
Currently supports Chapman University (Passio System ID: `263`). Each university system uses isolated repositories and configuration. New systems should be added via `InterchangeSystem` configuration and appropriate loaders.
|
||||
See AGENTS.md
|
||||
@@ -1,4 +1,7 @@
|
||||
FROM node:22-alpine
|
||||
WORKDIR /usr/src/app
|
||||
COPY . .
|
||||
RUN npm run build
|
||||
EXPOSE 4000
|
||||
|
||||
CMD ["npm", "run", "start"]
|
||||
|
||||
1121
package-lock.json
generated
1121
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@@ -7,7 +7,7 @@
|
||||
"build:dev": "npm install --include=dev && npm run generate && tsc --project tsconfig.build.json",
|
||||
"build": "npm install --include=dev && npm run generate && tsc --project tsconfig.build.json && npm prune --omit=dev",
|
||||
"start:dev": "npm run build:dev && node ./dist/index.js",
|
||||
"start": "npm run build && node ./dist/index.js",
|
||||
"start": "node ./dist/index.js",
|
||||
"generate": "graphql-codegen --config codegen.ts",
|
||||
"test": "npm run build:dev && jest --runInBand"
|
||||
},
|
||||
@@ -26,12 +26,12 @@
|
||||
},
|
||||
"private": true,
|
||||
"dependencies": {
|
||||
"@apollo/server": "^4.11.2",
|
||||
"@apollo/server": "^5.0.0",
|
||||
"@as-integrations/express5": "^1.1.2",
|
||||
"express": "^5.1.0",
|
||||
"express-rate-limit": "^8.0.1",
|
||||
"express-slow-down": "^3.0.0",
|
||||
"graphql": "^16.10.0",
|
||||
"graphql": "^16.11.0",
|
||||
"jsonwebtoken": "^9.0.2",
|
||||
"redis": "^4.7.0"
|
||||
},
|
||||
|
||||
Reference in New Issue
Block a user