Git & Branch Standards
Branch Naming
All branches must follow this format. Use kebab-case (lowercase, hyphens) and always include the ticket/issue number when one exists.
# Pattern
<prefix>/<ticket>-<description>
# Examples
feature/HE2-142-add-team-invite-flow
bugfix/HE2-305-fix-thread-pagination
hotfix/HE2-410-patch-auth-redirect
chore/HE2-99-upgrade-nextjs
refactor/HE2-200-simplify-billing-service
| Prefix | Use When |
|---|---|
feature/ | Adding new functionality |
bugfix/ | Fixing a bug |
hotfix/ | Urgent production fix |
release/ | Preparing a release |
chore/ | Maintenance, dependency updates |
docs/ | Documentation changes only |
refactor/ | Code restructuring without behavior change |
myfix # No prefix, no ticket
Feature/add-stuff # Wrong case
feature/addTeamInviteFlow # camelCase not allowed
fix_something_quick # Underscores not allowed
john/testing # Developer names are not prefixes
Main Branch
main
main — always go through a PR
Branch Cleanup
Branches are deleted immediately after PR merge — no exceptions. Enable "Delete branch after merge" in your GitHub settings. Branches inactive for more than 2 weeks without an open PR will be deleted automatically.
main and create a fresh branch
Commit Message Standards
All commits must follow the Conventional Commits format.
<type>(<scope>): <subject>
Rules
auth, billing, agent, frontend)
Allowed Types
| Type | When to Use |
|---|---|
feat | New feature or functionality |
fix | Bug fix |
docs | Documentation only |
refactor | Code change that neither fixes a bug nor adds a feature |
test | Adding or updating tests |
chore | Build process, tooling, dependency updates |
ci | CI/CD pipeline changes |
perf | Performance improvement |
Examples
feat(agent): add retry logic for failed sandbox executions
fix(billing): prevent duplicate Stripe webhook processing
refactor(knowledge-base): extract chunking into dedicated service
test(auth): add integration tests for phone auth flow
chore(deps): upgrade @tanstack/react-query to v5
ci(deploy): add staging environment to GitHub Actions
perf(redis): batch cache invalidation for thread updates
fixed stuff # No type, vague description
feat: Add New Feature. # Trailing period, wrong case
update # No type, no scope, no description
WIP # Never commit WIP to shared branches
Do not add Co-Authored-By lines for Anthropic or Claude in commit messages.
Pull Request Standards
PR Size Limits
If your PR is growing large, split it into logical, independently reviewable chunks. Each chunk should be functional on its own.
PR Title
Follow the same Conventional Commits format as commit messages:
feat(agent): add retry logic for failed sandbox executions
PR Description (Required)
Every PR must include the following sections:
## Summary
<!-- 2-3 bullet points explaining WHAT changed and WHY -->
- Added retry logic for sandbox execution failures
- Implements exponential backoff with max 3 retries
- Addresses intermittent timeout issues reported in #142
## Related Issue
Fixes #142
## Type of Change
- [ ] New feature
- [ ] Bug fix
- [ ] Refactor
- [ ] Documentation
- [ ] CI/CD
- [ ] Other (describe)
## Testing
- [ ] Unit tests added/updated
- [ ] Integration tests added/updated
- [ ] Manual testing performed (describe steps)
- [ ] Feature flag verified in staging
## Self-Review Checklist
- [ ] Code follows project conventions
- [ ] No secrets, API keys, or tokens committed
- [ ] No console.log or debug statements left in
- [ ] No any types in TypeScript
- [ ] Feature flag wraps new functionality
- [ ] Database migrations are backward-compatible
- [ ] Error handling follows project patterns
- [ ] Accessibility checked (if UI change)
PR Review Rules
Feature Flags
Every new feature, UI change, or behavioral modification must be wrapped in a feature flag. This allows safe rollback without redeployment, gradual rollout, A/B testing, and decoupling deployment from release.
Implementation
// Use the feature flag hook
const { isEnabled } = useFeatureFlag('new-thread-ui');
if (isEnabled) {
return <NewThreadUI />;
}
return <LegacyThreadUI />;
from utils.feature_flags import is_feature_enabled
async def process_request(team_id: str):
if await is_feature_enabled("new-billing-logic", team_id):
return await new_billing_flow()
return await legacy_billing_flow()
Feature Flag Lifecycle
Naming Convention
<domain>-<feature-description>
# Examples
agent-retry-logic
billing-new-checkout
thread-markdown-preview
Security & Secrets
Committing secrets (API keys, tokens, passwords, credentials) is a terminable offense in regulated environments. This policy has no exceptions.
Banned from Source Code
.env or .env.local file contentsWhere Secrets Belong
| Environment | Method |
|---|---|
| Local development | .env / .env.local files (already in .gitignore) |
| CI/CD | GitHub Actions secrets or environment variables |
| Staging/Production | AWS Secrets Manager / environment variables |
Pre-Commit Checks
--no-verify
Frontend Security
NEXT_PUBLIC_ prefixdangerouslySetInnerHTML without DOMPurify sanitizationHttpOnly, Secure, SameSite=StrictBackend Security
secrets module for OTP/token generation — never randomhmac.compare_digest for comparisons — never ==Environment & Tooling
Tool Versions
All developers must use the versions specified in mise.toml. Use mise to manage tool versions automatically.
Running Commands in the Right Directory
Running npm install from the project root will create a rogue node_modules/ and package-lock.json in the root — this breaks the build and pollutes the repo.
| Command | Run From | Not From |
|---|---|---|
npm install | frontend/ | Never from project root |
npm run dev | frontend/ | Never from project root |
npm run build | frontend/ | Never from project root |
uv sync | backend/ | Never from project root |
uv run api.py | backend/ | Never from project root |
uv run pytest | backend/ | Never from project root |
docker compose up | he2-beta/ (root) | Not from subdirectories |
python setup.py | he2-beta/ (root) | Not from subdirectories |
Local Development Setup
# 1. Clone and enter the repo
git clone <repo-url> && cd he2-beta
# 2. Run the setup wizard
python setup.py
# 3. Install frontend dependencies
cd frontend && npm install
# 4. Install backend dependencies
cd ../backend && uv sync
# 5. Start Redis (required for backend)
docker compose up redis
# 6. Start backend (new terminal, from backend/)
cd backend && source .venv/bin/activate && uv run api.py
# 7. Start frontend (new terminal, from frontend/)
cd frontend && npm run dev
Environment Variables
Backend (.env in backend/):
REDIS_HOST — use localhost for local dev, redis inside DockerANTHROPIC_API_KEY, GEMINI_API_KEY — LLM provider keysDAYTONA_API_KEY — sandbox providerTAVILY_API_KEY — web searchFrontend (.env.local in frontend/):
NEXT_PUBLIC_BACKEND_URL — defaults to http://localhost:8000/apiNEXT_PUBLIC_ENV_MODE — environment mode flagFrontend Standards
TypeScript
any types — use proper typing or unknown if truly neededComponents
components/ui/ — never raw HTML elements (<button>, <input>, <select>, etc.)<i className="ri-icon-name-line"> — never import from react-iconsState Management
| What | Tool |
|---|---|
| Server state (API data) | React Query (@tanstack/react-query) |
| Global client state | Zustand stores (stores/) |
| Local component state | useState / useReducer |
| Form state | React Hook Form |
Styling
style={{}} attributes unless absolutely necessaryCode Quality
console.log in committed code — use proper logging or removenpm run lint and npm run format:check before pushingBackend Standards
Python
async/await for all I/O operations (database, API calls, file I/O)Follow the domain-driven structure:
domain/
<feature>/
api/ # Routes
service/ # Business logic
repository/ # Data access
models/ # Data models
Database
backend/supabase/migrations/ as SQL filesError Handling
LLM Integration
infrastructure/llm/)Testing Standards
Backend
PRs that drop coverage below 70% will be blocked. Write tests for all new business logic.
| Marker | When to Use |
|---|---|
@pytest.mark.unit | No external dependencies needed |
@pytest.mark.integration | Requires DB, Redis, or external services |
@pytest.mark.property | Hypothesis property-based tests |
@pytest.mark.slow | Tests that take >5 seconds |
# Run unit tests before pushing
uv run pytest -m "not integration"
Frontend
# Run tests before pushing
npm test
Code Review Checklist
Use this checklist when reviewing (or self-reviewing) a PR. Every item must be checked before approving.
General
Code Quality
Security
Architecture
Testing
Quick Reference Card
Everything you need at a glance. Bookmark this section.
feature/HE2-123-add-widget
feat(widget): add interactive widget to dashboard
feat(widget): add interactive widget to dashboard
< 400 lines
.env only, never in code
Run from frontend/, NEVER from root
Run from backend/
All new features behind feature flags
Deleted after merge
Required, 70% coverage minimum
No `any` in TypeScript, type all Python functions
SOC 2 Type 2 + GDPR — check compliance/policies/ when in doubt