Policy for Choosing Languages and Frameworks
General
Languages are allowed only if they meet all of the following criteria:
- Null safety
- C++ is not allowed; use Rust instead.
- Java is not allowed; use Kotlin instead.
- Type safety
- For Python, type hints with a strict type checker are mandatory.
- Use TypeScript instead of JavaScript.
- Concurrency support
- Event-driven, async models only.
- Thread-based models are not allowed.
Never mix backend and frontend runtime code. Doing so can lead to serious security vulnerabilities.
Choose technologies that align with the business idea and available resources to enable rapid validation.
Using linters, formatters, and CI is strongly recommended.
Put CI workflows in top-level .gitea directory and use the self-hosted machine.
Containers
Use Podman instead of Docker. Podman is commercially free and vendor-neutral. Use Containerfile, compose.yaml, and .containerignore filenames instead of Dockerfile, docker-compose.yml, and .dockerignore.
Backend
Containerization is mandatory for all backend services.
For Python, always use uv, ruff, and ty for code quality.
Frontend
A no-framework approach is mandatory. Always focus on web standards. Web components composed of pure HTML, CSS, and JavaScript must be used. Third-party frameworks do not guarantee long-term security, stability, or continued adoption.
By using only web components, we achieve:
- A central UI component library with design consistency
- Improved security
- Better end-user performance
- Long-term maintainability
- Direct DOM debugging capabilities
This means banned options include, but are not limited to:
- React
- Tailwind
- Vue
- Svelte
- Angular
- Solid
Currently approved options are:
- Lit
- Raw TypeScript
For all TypeScript projects, always prefer Deno over Node. Deno provides built-in support for type-checking, linting, formatting, and bundling.