CONTRIBUTING.md
June 8, 2026 ยท View on GitHub
Thank you for your contribution to Flora! We need you to read and understand this document when you open your PR or your ticket:
Project Setup
We need you to read and acknowledge our Code of Conduct document.
The compiler version used is described in the cabal.project file.
cabal-install version 3.8 or higher is needed.
The following Haskell command-line tools will have to be installed:
fourmolu: To style the code base. Version is 0.17.0.0hlintv3.10 &apply-refact: To enforce certain patterns in the code base ("lint")cabal-gildandnixfmt: To style the cabal and nix filesghcid: To automatically reload the Haskell code base upon source changesghc-tags: To generate ctags or etags for the project
Outside of the flora root directory run:
cabal install hlint cabal-gild ghcid ghc-tags --semaphore -j
(Some of the above packages could have incompatible dependencies, so consider installing them separately with cabal install)
gperftools: This gives ustcmalloc, an alternative malloc implementation that helps against memory fragmentation in long-running serverslibsodium-1.0.18: The system library that powers most of the cryptography happening in florayarn: The tool that handles the JavaScript code basesesbuild: The tool that handles asset bundlingchangelog-dv1.0: https://codeberg.org/fgaz/changelog-d/releases/tag/v1.0
Notes on MacOS
cabal.project.freezeis not portable, so make sure to delete it before runningmake build, if not using the Docker-based setup.
Questions
Open a thread in the Questions discussion board. You'll get help from everyone in the community.
Issues & Bugs
Open a Ticket and tell us what you can about your problem.
Pull Requests
You need to
- Read this document
- Have a ticket that you can relate the PR to, so that we can have some context for your change
- Provide screenshots of before/after if you change the UI.
- Put
[FLORA-XXXX]where XXXX is the ticket this PR is related to, or [NO-ISSUE] if no tickets are related, in the PR title and commit message:
[NO-ISSUE] Update dependencies for Storybook.js
- Insert a changelog entry in the
changelog.ddirectory, based on this template:
synopsis: Add feature xyz
prs: #102
issues: #100 #101
significance: significant -- Only if this is important enough to be put at the top of the changelog.
description: {
- Detail number 1
- Detail number 2
}
Feature request
Open a thread in the Feature Request discussion board. Be certain to search if it has already been suggested!
Making a release
Here is the procedure to follow when making a release:
-
Create a PR to prepare the release of the next version targeting
development. It must include:- Bump the version in the flora.cabal file
- Generate the changelog with ./scripts/generate-changelog.sh
- Write down the date in the CHANGELOG
- Remove the changelog.d entries
-
Once the PR is merged into
development, mergedevelopmentintomain -
Create a new release.
Profiling
If you are about to run flora-cli or flora-server with profiling, please first read
https://well-typed.com/blog/2021/01/first-look-at-hi-profiling-mode/.
Here are the steps:
$ cabal build flora-server -f prof(orflora-cli)$ cabal run -- flora-server +RTS -l -hT -i0.5 -RTS$ eventlog2html flora-server.eventlog
Also consider capturing live eventlogs during developement.
Installation and Configuration
Step 1. Read The above "Project Setup" section. Step 2. Keep reading from here.
Flora server
The configuration is handled through environment variables. They are all prefixed by FLORA_ to avoid conflict, and the
server will tell you which ones are missing.
To start in the best of conditions, create a file called environment.local.sh with the following content:
source environment.sh
This will get all the variables from environment.sh and allow you to override them locally.
If you use direnv, you are advised to create a symbolic link from environment.local.sh to .envrc.
You can then build the server with make build. Do not simply run cabal build.
A very useful command to run is
$ make start-tmux
To start a tmux session with code reloading for frontend and backend:
To explore the other possible Make rules, type:
$ make help
Database
The Flora server uses PostgreSQL 14. Please install it.
Side-Quest: First installation
If this is your first time with PostgreSQL, here is what you should do:
- Locate the
pg_hba.conffile. If a search engine cannot help you, you can find it easily withsudo find / -type f -name pg_hba.confon UNIX systems. - Go to the bottom of the file and perform the following changes:
local all all peer
# IPv4 local connections:
- host all all 127.0.0.1/32 md5
+ host all all 127.0.0.1/32 scram-sha-256
# IPv6 local connections:
- host all all ::1/128 md5
+ host all all ::1/128 scram-sha-256
-
Restart the database engine (using
systemctlon Linux, orbrew services restart postgresql@14if you have installed PostgreSQL withbrew) -
Connect (via sudo) to the
rootuser
user $ sudo -s
[sudo] password: [type your user's password]
Then as root, connect to the postgres account, and open a psql shell.
root # su -l postgres
postgres $ psql
psql (14.7 (Ubuntu 14.7-1.pgdg18.04+1))
Type "help" for help.
Now, set the password for user postgres to the character string 'postgres'
postgres=# alter role postgres with password 'postgres';
And you are good to go.
Setup project
To create the database and apply the migrations, type:
$ make db-setup
you can also use db-create and db-drop to create and delete the database in the PostgreSQL instance.
Docker Workflow
A docker-based workflow is provided. The idea is to develop from within a container that brings with it all dependencies, and communicates with another container for the PostgreSQL database.
# Start the containers for the database and the server
$ make docker-up
# Once the containers are running, you can enter the development environment and start hacking
$ make docker-enter
# You'll be in the docker container. Environment variables are automatically set
# so you should be able to start Flora
(docker)$ make start-tmux
# You'll be in a tmux session, everything should be launched
# Visit localhost:8084 from your web browser to see if it all works.
If you need to rebuild the container, run the following command:
$ make docker-build
Provisioning the database
After everything is set up, (locally or via Docker), you can start populating the database:
$ make db-setup
$ make db-provision
$ cabal run -- flora-cli create-user --admin --can-login --username "admin" \
--email "admin@localhost" --password "password123"
$ make db-provision-packages
Importing a package index
The previous paragraph shows how to import test packages, but you may want to import a whole package index, for shit and giggles.
You can do so with:
$ cabal run flora-cli -- import-index ~/.cabal/packages/hackage.haskell.org/01-index.tar.gz \
--repository hackage.haskell.org
Similarly if you have the cardano packages index configured, run:
$ cabal run flora-cli -- import-index ~/.cabal/packages/cardano/01-index.tar.gz \
--repository "cardano"
Live Eventlogs
To enable capturing live events from Flora server running locally:
- Ensure
FLORA_EVENTLOG_SOCKETis being present in your local environment config script. - Run:
$ source environment.local.sh
$ cabal run -- flora-server +RTS -l -hT --eventlog-flush-interval=1 -RTS
- After that, run separately:
$ source environment.local.sh
$ docker compose -f docker-compose.live-eventlog.yml up
- Open
http://localhost:3000and login withadminusername and password. Ensure JavaScript enabled in your browser.
To disable live events, unset FLORA_EVENTLOG_SOCKET.
Nix
Nix is an alternative way to interact with the Flora codebase.
Flora provides a nix setup to make provisioning a development environment and creating reproducible and simple
builds. To show all available flake attributes, run
nix flake show -Lv --allow-import-from-derivation --fallback
Using nix as provider for a development environment
Obtaining a devShell which contains all tools for develop flora, including correct compiler and haskell tooling
is as simple as running
nix -Lv develop
We recommend using our proposed nix config settings, including the extra binary cache, but ultimately it's up to you
whether you trust those settings by reacting with y on the prompt after running a nix command.
Warning accepting binary caches from a flake requires elevated rights for
nix, only allow it, if you know what you're doing
Using nix with direnv
Direnv can drastically reduce development cycles by reducing the amount of times nix evaluates the expressions for
this repository, which is a drastic improvement, especially with IFD (which this repo uses due to callCabal2nix).
Devshell startup times will be instant if you didn't change anything in the configuration and as long as usual if you
need to re-evaluate the nix-expressions (i.e. on cabal config changes or nix changes).
Find out how to install direnv on your machine by visiting their github.o
After installing, add a .envrc file to the root of the project containing:
use flake -Lv --fallback
and run
direnv allow
To reload the direnv environment, run
direnv reload
Formatting and Linting with nix and pre-commit-hooks
After starting up a devShell with nix develop or direnv, a shellHook will run that installs two things
- a script, called
pre-commit - a pre-commit hook for git
The former can be invoked to run the formatters and linters on the entire project, to check everything, run
pre-commit run -a
to check a single check run
pre-commit run <check>
Note The available hooks can be found in
./nix/pre-commit-config.nix
The latter is invoked when calling git commit, it will abort the commit, if the linting and formatting does not succeed.
If you want to commit although they do not succeed, pass --no-verify to the git commit command.
Warning Be careful that this does not mean you get around linting and formatting, as they're checked in
CI
Using nix to build and run flora
To verify, that the haskell code builds, the tests pass and the formatting and linting are correct, as well as the nix code working, run
nix flake check -Lv --allow-import-from-derivation
To build flora, invoke
nix build -Lv
To run the cli, run
nix run .#cli
To run the server, run
nix run .#server
Contributing to our nix infrastructure
Contributions to our nix infrastructures are always appreciated, however, there are a couple of guidelines
- don't forget to run formatting and linting (see above for
pre-commit-hooks) - prefer cached derivations, that means:
- prefer upstream haskell packages over custom versions-
- prefer frameworks that have reliable and trusted binary caches
- prefer versions with less IFD:
- prefer realized
nixderivations overcallHackageovercallCabal2nix - don't use custom packages if not absolutely necessary
- prefer realized
- locking happens in the
nixflakenixprovides a native locking mechanism with flakes, we only use that mechanism- if we need a source of a package, we add it as a flake input with
flake = false; - we don't use any fetcher, if not absolutely needed (e.g. if you need a tarball which is not unpacked, it might sometimes be necessary)