zitadel/CONTRIBUTING.md

23 KiB

Contributing to ZITADEL

Introduction

Thank you for your interest about how to contribute! As you might know there is more than code to contribute. You can find all information needed to start contributing here.

Please give us and our community the chance to get rid of security vulnerabilities by responsibly disclose this kind of issues by contacting security@zitadel.com.

The strongest part of a community is the possibility to share thoughts. That's why we try to react as soon as possible to your ideas, thoughts and feedback. We love to discuss as much as possible in an open space like in the issues and discussions section here or in our chat, but we understand your doubts and provide further contact options here.

If you want to give an answer or be part of discussions please be kind. Treat others like you want to be treated. Read more about our code of conduct here.

What can I contribute?

For people who are new to ZITADEL: We flag issues which are a good starting point to start contributing. You find them here

Make ZITADEL more popular and give it a

Help shaping the future of ZITADEL:

Contribute

Follow @zitadel on twitter

How to contribute

We strongly recommend to talk to us before you start contributing to streamline our and your work.

We accept contributions through pull requests. You need a github account for that. If you are unfamiliar with git have a look at Github's documentation on creating forks and creating pull requests. Please draft the pull request as soon as possible. Go through the following checklist before you submit the final pull request:

Submit a Pull Request (PR)

  1. Fork the zitadel/zitadel repository on GitHub

  2. On your fork, commit your changes to a new branch

    git checkout -b my-fix-branch main

  3. Make your changes following the guidelines in this guide. Make sure that all tests pass.

  4. Commit the changes on the new branch

    git commit --all

  5. Merge the latest commit of the main-branch

  6. Push the changes to your branch on Github

    git push origin my-fix-branch

  7. Use Semantic Release commit messages to simplify creation of release notes. In the title of the pull request correct tagging is required and will be requested by the reviewers.

  8. On GitHub, send a pull request to zitadel:main. Request review from one of the maintainers.

Reviewing a Pull Request

The reviewers will provide you feedback and approve your changes as soon as they are satisfied. If we ask you for changes in the code, you can follow the GitHub Guide to incorporate feedback in your pull request.

Commit Messages

Make sure you use semantic release messages format.

<type>(<scope>): <short summary>

Type

Must be one of the following:

  • feat: New Feature
  • fix: Bug Fix
  • docs: Documentation

Scope

This is optional to indicate which component is affected. In doubt, leave blank (<type>: <short summary>)

Short Summary

Provide a brief description of the change.

Contribute

The code consists of the following parts:

name description language where to find
backend Service that serves the grpc(-web) and RESTful API go API implementation
console Frontend the user interacts with after he is logged in Angular, Typescript ./console
login Server side rendered frontend the user interacts with during login go, go templates ./internal/api/ui/login
API definitions Specifications of the API Protobuf ./proto/zitadel
docs Project documentation made with docusaurus Docusaurus ./docs

Please validate and test the code before you contribute.

We add the label "good first issue" for problems we think are a good starting point to contribute to ZITADEL.

Backend / Login

By executing the commands from this section, you run everything you need to develop the ZITADEL backend locally. Using Docker Compose, you run a CockroachDB on your local machine. With goreleaser, you build a debuggable ZITADEL binary and run it using delve. Then, you test your changes via the console your binary is serving at http://localhost:8080 and by verifying the database. Once you are happy with your changes, you run end-to-end tests and tear everything down.

ZITADEL uses golangci-lint for code quality checks. Please use this configuration when running golangci-lint. We recommend to set golangci-lint as linter in your IDE.

The commands in this section are tested against the following software versions:

Make some changes to the source code, then run the database locally.

# You just need the db service to develop the backend against.
docker compose --file ./e2e/docker-compose.yaml up --detach db

Build the binary. This takes some minutes, but you can speed up rebuilds.

# You just need goreleasers build part (--snapshot) and you just need to target your current platform (--single-target)
goreleaser build --id dev --snapshot --single-target --rm-dist --output .artifacts/zitadel/zitadel

Note: With this command, several steps are executed. For speeding up rebuilds, you can reexecute only specific steps you think are necessary based on your changes.
Generating gRPC stubs: DOCKER_BUILDKIT=1 docker build -f build/zitadel/Dockerfile . --target go-copy -o .
Running unit tests: DOCKER_BUILDKIT=1 docker build -f build/zitadel/Dockerfile . --target go-codecov
Generating the console: DOCKER_BUILDKIT=1 docker build -f build/console/Dockerfile . --target angular-export -o internal/api/ui/console/static/
Build the binary: goreleaser build --id dev --snapshot --single-target --rm-dist --output .artifacts/zitadel/zitadel --skip-before

You can now run and debug the binary in .artifacts/zitadel/zitadel using your favourite IDE, for example GoLand. You can test if ZITADEL does what you expect by using the UI at http://localhost:8080/ui/console. Also, you can verify the data by running cockroach sql --database zitadel --insecure and running SQL queries.

As soon as you are ready to battle test your changes, run the end-to-end tests.

Running the tests with docker

Running the tests with docker doesn't require you to take care of other dependencies than docker and goreleaser.

# Build the production binary (unit tests are executed, too)
goreleaser build --id prod --snapshot --single-target --rm-dist --output .artifacts/zitadel/zitadel

# Pack the binary into a docker image
DOCKER_BUILDKIT=1 docker build --file build/Dockerfile .artifacts/zitadel -t zitadel:local

# If you made changes in the e2e directory, make sure you reformat the files
(cd ./e2e && npm run lint:fix)

# Run the tests
ZITADEL_IMAGE=zitadel:local docker compose --file ./e2e/config/host.docker.internal/docker-compose.yaml run --service-ports e2e

When you are happy with your changes, you can cleanup your environment.

# Stop and remove the docker containers for zitadel and the database
docker compose --file ./e2e/config/host.docker.internal/docker-compose.yaml down

Running the tests without docker

If you also make changes to the console, you can run the test suite against your locally built backend code and frontend server. But you will have to install the relevant node dependencies.

# Install dependencies
(cd ./e2e && npm install)

# Run the tests interactively
(cd ./e2e && npm run open:golangangular)

# Run the tests non-interactively
(cd ./e2e && npm run e2e:golangangular)

When you are happy with your changes, you can cleanup your environment.

# Stop and remove the docker containers for zitadel and the database
docker compose --file ./e2e/config/host.docker.internal/docker-compose.yaml down

Integration tests

In order to run the integrations tests for the gRPC API, PostgreSQL and CockroachDB must be started and initialized:

export INTEGRATION_DB_FLAVOR="cockroach" ZITADEL_MASTERKEY="MasterkeyNeedsToHave32Characters"
docker compose -f internal/integration/config/docker-compose.yaml up --wait ${INTEGRATION_DB_FLAVOR}
go run main.go init --config internal/integration/config/zitadel.yaml --config internal/integration/config/${INTEGRATION_DB_FLAVOR}.yaml
go run main.go setup --masterkeyFromEnv --config internal/integration/config/zitadel.yaml --config internal/integration/config/${INTEGRATION_DB_FLAVOR}.yaml
go test -tags=integration -race -parallel 1 ./internal/integration ./internal/api/grpc/...
docker compose -f internal/integration/config/docker-compose.yaml down

The above can be repeated with INTEGRATION_DB_FLAVOR="postgres".

Console

By executing the commands from this section, you run everything you need to develop the console locally. Using Docker Compose, you run CockroachDB and the latest release of ZITADEL on your local machine. You use the ZITADEL container as backend for your console. The console is run in your Node environment using a local development server for Angular, so you have fast feedback about your changes.

We use angular-eslint/Prettier for linting/formatting, so please run npm run lint:fix before committing. (VSCode users, check out this ESLint extension and this Prettier extension to fix lint and formatting issues in development)

Once you are happy with your changes, you run end-to-end tests and tear everything down.

The commands in this section are tested against the following software versions:

Note for WSL2 on Windows 10 Following the suggestions here subsequently here may need to XLaunch and configure your DISPLAY variable. Use at your own risk.
  1. Install VcXsrv Windows X Server
  2. Set the target of your shortcut to "C:\Program Files\VcXsrv\xlaunch.exe" -ac
  3. In WSL2 run export DISPLAY=$(cat /etc/resolv.conf | grep nameserver | awk '{print $2}'):0 to set your DISPLAY variable
  4. When starting XLaunch, make sure to disable access control

Run the database and the latest backend locally.

# Change to the console directory
cd ./console

# You just need the db and the zitadel services to develop the console against.
docker compose --file ../e2e/docker-compose.yaml up --detach zitadel

When the backend is ready, you have the latest zitadel exposed at http://localhost:8080. You can now run a local development server with live code reloading at http://localhost:4200. To allow console access via http://localhost:4200, you have to configure the ZITADEL backend.

  1. Navigate to http://localhost:8080/ui/console/projects.
  2. When prompted, login with zitadel-admin@zitadel.localhost and Password1!
  3. Select the ZITADEL project.
  4. Select the Console application.
  5. Select Redirect Settings
  6. Add http://localhost:4200/auth/callback to the Redirect URIs
  7. Add http://localhost:4200/signedout to the Post Logout URIs
  8. Select the Save button

You can run the local console development server now.

# Console loads its target environment from the file console/src/assets/environment.json.
# Load it from the backend.
curl http://localhost:8080/ui/console/assets/environment.json > ./src/assets/environment.json

# Generate source files from Protos
npm run generate

# Install npm dependencies
npm install

# Start the server
npm start

Navigate to http://localhost:4200/. Make some changes to the source code and see how the browser is automatically updated. After making changes to the code, you should run the end-to-end-tests. Open another shell.

# Reformat your console code
npm run lint:fix

# Change to the e2e directory
cd .. && cd e2e/

# If you made changes in the e2e directory, make sure you reformat the files here too
npm run lint:fix

# Install npm dependencies
npm install

# Run all e2e tests
npm run e2e:angular -- --headed

You can also open the test suite interactively for fast feedback on specific tests.

# Run tests interactively
npm run open:angular

If you also make changes to the backend code, you can run the test against your locally built backend code and frontend server

npm run open:golangangular
npm run e2e:golangangular

When you are happy with your changes, you can format your code and cleanup your environment

# Stop and remove the docker containers for zitadel and the database
docker compose down

Contribute Docs

Project documentation is made with docusaurus and is located under ./docs.

Local Testing

Please refer to the README for more information and local testing.

Style Guide

  • Code with variables: Make sure that code snippets can be used by setting environment variables, instead of manually replacing a placeholder.
  • Embedded files: When embedding mdx files, make sure the template ist prefixed by "_" (lowdash). The content will be rendered inside the parent page, but is not accessible individually (eg, by search).
  • Don't repeat yourself: When using the same content in multiple places, save and manage the content as separate file and make use of embedded files to import it into other docs pages.
  • Embedded code: You can embed code snippets from a repository. See the plugin for usage.

Docs Pull Request

When making a pull request use docs(<scope>): <short summary> as title for the semantic release. Scope can be left empty (omit the brackets) or refer to the top navigation sections.

Contribute Internationalization

ZITADEL loads translations from four files:

You may edit the texts in these files or create a new file for additional language support. Make sure you set the locale (ISO 639-1 code) as the name of the new language file.

Want to start ZITADEL?

You can find an installation guide for all the different environments here: https://zitadel.com/docs/self-hosting/deploy/overview

Did you find a security flaw?

Product Management

The ZITADEL Team works with an agile product management methodology. You can find all the issues prioritized and ordered in the product board.

Sprint

We want to deliver a new release every second week. So we plan everything in two-week sprints. Each Tuesday we estimate new issues and on Wednesday the last sprint will be reviewed and the next one will be planned. After a sprint ends a new version of ZITADEL will be released, and publish to ZITADEL Cloud the following Monday.

If there are some critical or urgent issues we will have a look at it earlier, than the two weeks. To show the community the needed information, each issue gets attributes and labels.

About the attributes

You can find the attributes on the project "Product Management".

State

The state should reflect the progress of the issue and what is going on right now.

  • No status: Issue just got added and has to be looked at.
  • 🧐 Investigating: We are currently investigating to find out what the problem is, which priority it should have and what has to be implemented. Or we need some more information from the author.
  • 📨 Product Backlog: If an issue is in the backlog, it is not currently being worked on. These are recorded so that they can be worked on in the future. Issues with this state do not have to be completely defined yet.
  • 📝 Prioritized Product Backlog: An issue with the state "Prioritized Backlog" is ready for the refinement from the perspective of the product owner (PO) to implement. This means the developer can find all the relevant information and acceptance criteria in the issue.
  • 🔖 Ready: The issue is ready to take into a sprint. Difference to "prioritized..." is that the complexity is defined by the team.
  • 📋 Sprint Backlog: The issue is scheduled for the current sprint.
  • 🏗 In progress: Someone is working on this issue right now. The issue will get an assignee as soon as it is in progress.
  • 👀 In review: The issue is in review. Please add someone to review your issue or let us know that it is ready to review with a comment on your pull request.
  • Done: The issue is implemented and merged to main.

Priority

Priority shows you the priority the ZITADEL team has given this issue. In general the higher the demand from customers and community for the feature, the higher the priority.

  • 🌋 Critical: This is a security issue or something that has to be fixed urgently, because the software is not usable or highly vulnerable.
  • 🏔 High: These are the issues the ZITADEL team is currently focusing on and will be implemented as soon as possible.
  • 🏕 Medium: After all the high issues are done these will be next.
  • 🏝 Low: This is low in priority and will probably not be implemented in the next time or just if someone has some time in between.

Complexity

This should give you an indication how complex the issue is. It's not about the hours or effort it takes. Everything that is higher than 8 should be split in smaller parts.

1, 2, 3, 5, 8, 13

About the Labels

There are a few general labels that don't belong to a specific category.

  • good first issue: This label shows contributors, that it is an easy entry point to start developing on ZITADEL.
  • help wanted: The author is seeking help on this topic, this may be from an internal ZITADEL team member or external contributors.

Category

The category shows which part of ZITADEL is affected.

  • category: backend: The backend includes the APIs, event store, command and query side. This is developed in golang.
  • category: ci: ci is all about continues integration and pipelines.
  • category: design: All about the ux/ui of ZITADEL
  • category: docs: Adjustments or new documentations, this can be found in the docs folder.
  • category: frontend: The frontend concerns on the one hand the ZITADEL management console (Angular) and on the other hand the login (gohtml)
  • category: infra: Infrastructure does include many different parts. E.g Terraform-provider, docker, metrics, etc.
  • category: translation: Everything concerning translations or new languages

Language

The language shows you in which programming language the affected part is written

  • lang: angular
  • lang: go
  • lang: javascript