Skip to content

Mettre en place une base de données

Le site web du livre d'or de la conférence permet de recueillir des commentaires pendant les conférences. Nous avons besoin de stocker ces commentaires dans un stockage persistant.

Un commentaire est mieux décrit par une structure de données fixe : un nom, un email, le texte du commentaire et une photo facultative. Ce type de données se stocke facilement dans un moteur de base de données relationnelle traditionnel.

PostgreSQL est le moteur de base de données que nous allons utiliser.

Ajouter PostgreSQL à Docker Compose

Sur notre machine locale, nous avons décidé d'utiliser Docker pour gérer nos services. Le fichier docker-compose.yaml généré contient déjà PostgreSQL en tant que service :

docker-compose.yml
1
2
3
4
5
6
7
8
9
10
11
12
13
###> doctrine/doctrine-bundle ###
database:
    image: postgres:${POSTGRES_VERSION:-13}-alpine
    environment:
    POSTGRES_DB: ${POSTGRES_DB:-app}
    # You should definitely change the password in production
    POSTGRES_PASSWORD: ${POSTGRES_PASSWORD:-ChangeMe}
    POSTGRES_USER: ${POSTGRES_USER:-symfony}
volumes:
    - db-data:/var/lib/postgresql/data:rw
    # You may use a bind-mounted host directory instead, so that it is harder to accidentally remove the volume and lose all your data!
    # - ./docker/db/data:/var/lib/postgresql/data:rw
###< doctrine/doctrine-bundle ###

Un serveur PostgreSQL sera alors installé et certaines variables d'environnement, qui contrôlent le nom de la base de données et ses identifiants, seront configurées. Les valeurs n'ont pas vraiment d'importance.

Nous exposons également le port PostgreSQL (5432) du conteneur à l'hôte local. Cela nous aidera à accéder à la base de données à partir de notre machine :

docker-compose.override.yml
1
2
3
4
5
###> doctrine/doctrine-bundle ###
database:
    ports:
    - "5432"
###< doctrine/doctrine-bundle ###

Note

L'extension pdo_pgsql a déjà dû être installée précédemment lors de l'installation de PHP.

Démarrer Docker Compose

Lancez Docker Compose en arrière-plan (-d) :

1
$ docker-compose up -d

Attendez un peu pour laisser démarrer la base de données, puis vérifiez que tout fonctionne bien :

1
2
3
4
5
$ docker-compose ps

        Name                      Command              State            Ports
---------------------------------------------------------------------------------------
guestbook_database_1   docker-entrypoint.sh postgres   Up      0.0.0.0:32780->5432/tcp

S'il n'y a pas de conteneurs en cours d'exécution ou si la colonne State n'indique pas Up, vérifiez les logs de Docker Compose :

1
$ docker-compose logs

Accéder à la base de données locale

L'utilitaire en ligne de commande psql peut parfois s'avérer utile. Mais vous devez vous rappelez des informations d'identification et du nom de la base de données. Encore moins évident, vous devez aussi connaître le port local sur lequel la base de données tourne sur l'hôte. Docker choisit un port aléatoire pour que vous puissiez travailler sur plus d'un projet en utilisant PostgreSQL en même temps (le port local fait partie de la sortie de docker-compose ps).

Si vous utilisez psql avec la commande symfony, vous n'avez pas besoin de vous souvenir de quoi que ce soit.

La commande symfony détecte automatiquement les services Docker en cours d'exécution pour le projet et expose les variables d'environnement dont psql a besoin pour se connecter à la base de données.

Grâce à ces conventions, accéder à la base de données avec symfony run est beaucoup plus facile :

1
$ symfony run psql

Note

Si vous n'avez pas le binaire psql sur votre hôte local, vous pouvez également l'exécuter avec docker-compose :

1
$ docker-compose exec database psql main main

Sauvegarder et restaurer les données de la base

Utilisez pg_dump pour sauvegarder les données de la base :

1
$ symfony run pg_dump --data-only > dump.sql

Et restaurer les données :

1
$ symfony run psql < dump.sql

Ajouter PostgreSQL à Platform.sh

Pour l'infrastructure de production sur Platform.sh, l'ajout d'un service comme PostgreSQL doit se faire dans le fichier .platform/services.yaml, ce qui a déjà été fait par la recette du paquet webapp :

.platform/services.yaml
1
2
3
database:
    type: postgresql:13
    disk: 1024

Le service database est une base de données PostgreSQL (même version que pour Docker) que nous voulons provisionner avec 1 Go d'espace disque.

Nous devons également "lier" la BDD au conteneur de l'application, qui est décrit dans .platform.app.yaml :

.platform.app.yaml
1
2
relationships:
    database: "database:postgresql"

Le service database de type postgresql est référencé comme database sur le conteneur d'application.

Vérifiez que l'extension pdo_pgsql est bien installée pour PHP :

.platform.app.yaml
1
2
3
4
5
runtime:
    extensions:
        # other extensions
        - pdo_pgsql
        # other extensions

Accéder à la base de données de Platform.sh

PostgreSQL fonctionne maintenant localement via Docker et en production sur Platform.sh.

Comme nous venons de le voir, exécutersymfony run psql permet de se connecter automatiquement à la base de données hébergée avec Docker grâce aux variables d'environnement exposées par symfony run.

Si vous souhaitez vous connecter au PostgreSQL hébergé dans les conteneurs de production, vous pouvez ouvrir un tunnel SSH entre la machine locale et l'infrastructure Platform.sh :

1
2
$ symfony cloud:tunnel:open
$ symfony var:expose-from-tunnel

Par défaut, les services Platform.sh ne sont pas exposés comme variables d'environnement sur la machine locale. Vous devez le faire explicitement en utilisant l'option var:expose-from-tunnel. Pourquoi ? La connexion à la base de données de production est une opération dangereuse et vous risquez de compromettre de vraies données.

Comme précédemment, connectez-vous à la base de données PostgreSQL distante avec symfony run psql :

1
$ symfony run psql

Quand vous avez terminé, n'oubliez pas de fermer le tunnel :

1
$ symfony cloud:tunnel:close

Tip

Au lieu d'ouvrir un shell, vous pouvez également utiliser la commande symfony sql pour exécuter des requêtes SQL sur la base de données de production.

Exposer des variables d'environnement

Docker Compose et Platform.sh fonctionnent en harmonie avec Symfony grâce aux variables d'environnement.

Vérifier toutes les variables d'environnement exposées par symfony en exécutant symfony var:export :

1
2
3
4
5
6
7
8
$ symfony var:export

PGHOST=127.0.0.1
PGPORT=32781
PGDATABASE=main
PGUSER=main
PGPASSWORD=main
# ...

Les variables d'environnement commençant par PG sont utilisées par l'utilitaire psql. Et les autres ?

Lorsqu'un tunnel est ouvert vers Platform.sh avec l'option --expose-env-vars, la commande var:export retourne les variables d'environnement distantes :

1
2
3
4
$ symfony cloud:tunnel:open
$ symfony var:expose-from-tunnel
$ symfony var:export
$ symfony cloud:tunnel:close

Décrire votre infrastructure

Vous ne vous en êtes peut-être pas encore rendu compte, mais le fait que l'infrastructure soit stockée dans des fichiers à côté du code aide beaucoup. Docker et Platform.sh utilisent des fichiers de configuration pour décrire l'infrastructure du projet. Lorsqu'une nouvelle fonctionnalité nécessite un service supplémentaire, le code et les modifications de l'infrastructure font partie du même patch.

This work, including the code samples, is licensed under a Creative Commons BY-NC-SA 4.0 license.
TOC
    Version