Note
DossierFacile.fr a été créé par le Ministère de la Transition écologique pour aider à la réalisation de dossiers de location.
The project is available at DossierFacile.fr.
The front-end code is also accessible in this repository.
You need to have JDK 21, maven and Docker installed.
In this project we use a Docker Compose to setup the dev environment. Several services are used:
- PostgreSQL => Database for all the applications
- NGINX => Reverse proxy for the BO to serve SSL
- RabbitMQ => Queue used by pdf-generator, api-tenant and api-watermark
Run:
docker-compose -f docker-compose.dev.yml up -dTo create a dedicated user and database for dossierfacile.
- Create the file
docker-compose.overwrite.yml - Add the following to it:
services: nginx: extra_hosts: - "host.docker.internal:host-gateway"
- Add it to the
./.git/info/excludefile to ignore it without modifying the shared.gitignore - Run the stack with
docker compose -f docker-compose.dev.yml -f docker-compose.overwrite.yml up -d
You may also need to add pgcrypt extension to your local database:
- Connect to the container database
docker exec -it <container_name_or_id> psql -U <username> -d <database_name> - Run this SQL query
CREATE EXTENSION IF NOT EXISTS "pgcrypto";
Follow those steps to use Keycloak in dev environment locally:
- Follow the README instructions on repo Dossier-Facile-Keycloak.
- Connect to your keycloak admin console (default: http://localhost:8085/auth)
- Create a new realm "dossier-facile"
- Inside the realm create a new Client scope:
- Name: dossier
- Type: Default
- Display on consent screen: On
- Include in token scope: On
- Inside the realm create a new client: "dossier-facile-frontend-localhost"
- Root: Url of the tenant webProject (default: http://localhost:8090)
- Home URL: Url of the tenant webProject (default: http://localhost:8090)
- valid redirect Uris:
* - Valid post logout Uris:
* - web Origins:
* - Client authentication: Off
- authentication flow: Standard flow and Direct access Grants
- Theme: df
- Client scopes: add dossier
- Create a new realm: "dossier-facile-owner"
- Inside the realm create a new Client scope:
- Name: dossier
- Type: Default
- Display on consent screen: On
- Include in token scope: On
- Inside the realm create a new client: "dossier-facile-owner-localhost"
- Root: Url of the tenant webProject (default: http://localhost:8090)
- Home URL: Url of the tenant webProject (default: http://localhost:8090)
- valid redirect Uris:
* - Valid post logout Uris:
* - web Origins:
* - Client authentication: Off
- authentication flow: Standard flow and Direct access Grants
- Theme: df
- Client scopes: add dossier
- Inside the realm Master create a new client: "dossier-facile-api"
- Root: empty
- Home URL: empty
- valid redirect Uris:
* - Valid post logout Uris:
* - web Origins:
* - Client authentication: On
- authentication flow: Standard flow / Direct access Grants / Service account roles
- In this client you need add a Service account roles
- In the tab "Service Account Roles" add the role "admin"
- Save and copy the dossier-facile-api credentials (Client Secret).
Create a new folder mock-storage to store files.
For development, use the LOCAL provider with mock storage. For production, you can use S3 (OVH Multi-AZ), OVH, or OUTSCALE providers.
Example configuration for the new S3 provider:
storage.provider.list=S3
s3.region=sbg
s3.endpoint.url=https://s3.sbg.io.cloud.ovh.net
s3.access.key=your-access-key
s3.secret.access.key=your-secret-key- Project: dossierfacile-api-owner
- Project: dossierfacile-api-tenant
- Project: dossierfacile-api-watermark
- Project: dossierfacile-bo
- Project: dossierfacile-pdf-generator
- Project: dossierfacile-process-file
- Project: dossierfacile-task-scheduler
Feature flags are backed by the feature_flag, user_feature_assignment, and user_feature_assignment_history tables.
Do not create feature flags manually in production: creation must go through a versioned Liquibase migration.
- Create a migration file in:
dossierfacile-common-library/src/main/resources/db/migration/following the usual naming convention (timestamp + description), for example:202603010000-add-my-feature-flag.xml. - Add a
changeSetthat inserts the row intofeature_flag. - Add an explicit rollback that removes this row.
- Register the migration in
dossierfacile-common-library/src/main/resources/db/changelog/databaseChangeLog.xml.
Minimal example:
<?xml version="1.0" encoding="UTF-8"?>
<databaseChangeLog
xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog
http://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-3.10.xsd">
<changeSet id="202603010001" author="team">
<insert tableName="feature_flag">
<column name="key" value="my_feature_key"/>
<column name="description" value="Business description of the feature"/>
<column name="active" valueBoolean="false"/>
<column name="only_for_new_user" valueBoolean="false"/>
<column name="rollout_pct" valueNumeric="0"/>
<column name="deployment_date" valueDate="2026-03-01T00:00:00"/>
<column name="created_at" valueDate="2026-03-01T00:00:00"/>
<column name="updated_at" valueDate="2026-03-01T00:00:00"/>
</insert>
<rollback>
<delete tableName="feature_flag">
<where>key = 'my_feature_key'</where>
</delete>
</rollback>
</changeSet>
</databaseChangeLog>Then add the include in databaseChangeLog.xml:
<include file="db/migration/202603010000-add-my-feature-flag.xml" />Use FeatureFlagService (from module dossierfacile-common-library) in the relevant business service/controller.
private final FeatureFlagService featureFlagService;
if (featureFlagService.isFeatureEnabledForUser(userId, "my_feature_key")) {
// New behavior
} else {
// Existing behavior
}Best practices:
- Keep the key stable (
my_feature_key) and explicit. - Check the feature flag close to the business decision point.
- Keep a fallback (
existing behavior) in theelsebranch. - Add/adapt unit tests for both paths (
enabled/disabled).
In BO, go to "Paramétrer les features flags":
- Enable/disable globally with
active. - Increase rollout (
rollout_pct) progressively (e.g.0 -> 5 -> 25 -> 50 -> 100). - Use
only_for_new_userwhen the feature must be limited to users created afterdeployment_date.
- Liquibase migration created with
insert+rollback - Migration included in
databaseChangeLog.xml - Key used in code via
FeatureFlagService - Business fallback preserved
- Unit tests updated
- Progressive activation plan defined in BO
- Feature flag removal (code + DB) planned once rollout reaches 100%
Run mvn clean install from the root folder. This will build every module.
In each application folder, run
mvn spring-boot:run -D spring-boot.run.profiles=dev,mockOvhPull requests are welcome. For major changes, please open an issue first to discuss what you would like to change.
Please make sure to update tests as appropriate.

