We take security seriously. If you discover a security vulnerability, please report it privately to us via GitHub Private Vulnerability Reporting.
Do not disclose vulnerabilities publicly before we have a chance to address them.
- Submit your report through GitHub's Private Vulnerability Reporting
- Include details about the vulnerability, reproduction steps, and affected versions
- We will acknowledge your report within 7 days when possible
- We will work with you to validate and fix the issue
- Once a fix is released, we will credit you in the advisory unless you prefer anonymity
This is a volunteer-run project, so we cannot provide guaranteed SLAs. We do our best to:
- Acknowledge reports within 7 days when possible
- Provide an initial assessment within 14 days
- Release a fix for critical vulnerabilities within 30 days (depending on severity and volunteer availability)
Response times may vary based on severity, volunteer availability, and complexity of the issue.
VoteCatcher is currently in pre-1.0 development. Only the latest release receives security updates.
| Version | Supported |
|---|---|
| Latest (pre-1.0) | ✅ Yes |
| All older versions | ❌ No |
Recommendation: Always upgrade to the latest release for security fixes.
We follow coordinated disclosure:
- Vulnerabilities are fixed before public disclosure
- A security advisory is published alongside the fix release
- Reporters are credited in the advisory unless they prefer anonymity
- Public disclosure happens only after a fix is available
If you're self-hosting VoteCatcher, follow these security practices:
- Never commit API keys or secrets to version control
- Use environment variables for all sensitive configuration
- Copy
.env.examplefiles to.envand fill in your values - See
backend/.env.exampleandfrontend/.env.examplefor all required secrets
Required secrets:
DATABASE_URL— database connection stringBETTER_AUTH_SECRET— session encryption keyOCR_PROVIDER_API_KEY— LLM/OCR provider key (unless using simulation mode)SUPABASE_SERVICE_KEY— Supabase admin key (if using Supabase)
- Use PostgreSQL in production, not SQLite
- Create a dedicated database user with strong credentials
- Restrict database access to the application server only
- Use environment variables for database credentials, not config files
- Enable SSL for database connections in production
- Use separate anon and service keys
- Store the service key securely — it has full database access
- Never expose the service key to client-side code
- Use Row Level Security (RLS) policies for data access control
- Always use HTTPS in production
- Use a reverse proxy (nginx, Caddy) with SSL/TLS termination
- Keep dependencies updated:
just security-scan - Monitor GitHub Dependabot alerts and code scanning results
- Review logs regularly for suspicious activity
Before deploying to production:
# Run security scans
just security-scan
# Check for known vulnerabilities
just scaVerify:
- Environment variables are set and not committed
- HTTPS is enabled
- Database credentials are strong
- OCR provider API key is restricted
- Dependencies are up to date
- Application code in
backend/andfrontend/ - Dependencies (Python and Node.js packages)
- Authentication and authorization mechanisms
- Input validation and sanitization
- API security
- Database access controls
- Configuration management
- Social engineering attacks
- Denial of service attacks against self-hosted instances
- Issues in third-party services (e.g., Supabase, OpenAI)
- Issues requiring physical access to infrastructure
- Issues already disclosed publicly (without coordination)
VoteCatcher uses these security tools:
| Tool | Purpose | Usage |
|---|---|---|
just security-scan |
Run all security scans | Pre-deployment |
| Dependabot | Automated dependency updates | GitHub integration |
| GitHub Code Scanning | SAST via CodeQL | CI pipeline |
| Bandit | Python security linter | CI pipeline |
uv audit |
Python dependency vulnerabilities | CI pipeline |
bun audit |
Node.js dependency vulnerabilities | CI pipeline |
See CONTRIBUTING.md for CI security checks.