Authentification OpenID Connect avec Symfony (2/3)
Tags: php, symfony, openid, keycloak
Published: 2021-04-20 11:03:55

> Cet article fait partie d'une série d'articles :
* [Introduction](https://dev.to/gbtux/authentification-openid-connect-avec-symfony-3m5h)
* Mettre en place un serveur OpenID Connect avec Keycloak (cet article)
* Symfony et Keycloak

Après cette (longue) introduction, on va enfin rentrer dans le vif du sujet. 
Aujourd'hui c'est Keycloak!
On va l'installer en mode "standalone", avec une base Mysql (ou MariaDB, suivant votre choix).
On mettra enfin un serveur Apache devant, configuré en SSL et en reverse proxy.

Vous êtes prêts ? C'est parti !
>Notes: Comme dit précédemment, Keycloak sera installé sur une VM. On va imaginer un serveur sur le domaine "gbtux.org".

# Installation de Keycloak

Connectez-vous à votre VM, en root, et allez dans le répertoire /opt.

## Installation de Java
Keycloak nécessite Java pour fonctionner.
On va donc l'installer.
Mettez donc votre liste de paquets à jour :
```
apt-get update
```
Puis installez le JDK:
```
apt install default-jdk -y
```
Contrôlez la bonne exécution de Java via :
```
java -version
```

## Téléchargement

Téléchargez le sources de keycloak avec wget :
```
wget https://github.com/keycloak/keycloak/releases/download/12.0.4/keycloak-12.0.4.tar.gz
```
Puis, décompressez l'archive avec :
```
tar zxvf keycloak-12.0.4.tar.gz
```
Vous avez maintenant un répertoire /opt/keycloak-12.0.4

## Création d'un utilisateur
Pour faire ça bien, on va créer un utilisateur et un groupe associé.

```
groupadd keycloak
useradd -r -g keycloak -d /opt/keycloak -s /sbin/nologin keycloak
```

## Changement des permissions sur le répertoire Keycloak

```
$ sudo chown -R keycloak: keycloak
$ sudo chmod o+x /opt/keycloak/bin/
```
## Keycloak en tant que service (avec System D)

### Fichier de config

D'abord, on va créer un répertoire qui va accueillir  notre fichier de configuration

```
mkdir /etc/keycloak
```

Puis on va copier le fichier contenu dans la distribution de keycloak.
```
cp /opt/keycloak-12.0.4/docs/contrib/scripts/systemd/wildfly.conf keycloak.conf
``` 
Pas besoin de l'adapter, on va laisser les valeurs par défaut (fichier de configuration XML, mode et adresse d'écoute)

### Script de démarrage 
De la même façon, on va se servir d'un fichier de la distribution de Keycloak:
```
cd /opt/keycloak-12.0.4/bin
cp ../docs/contrib/scripts/systemd/launch.sh .
```

Editez le nouveau fichier pour modifier la variable WILDFLY_HOME comme suit :

![Fichier launch](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/h52x8hz47iu2eifwvjhc.png)

### Fichier de service
Maintenant qu'on s'est occupé du fichier de configuration et du script de démarrage, mettons tout cela en musique pour pouvoir démarrer Keycloak comme un véritable service.

Pour cela, encore une fois, la distribution de Keycloak nous fournit tout ce qu'il faut.

```
cp /opt/keycloak-12.0.4/docs/contrib/scripts/systemd/wildfly.service /etc/systemd/system/keycloak.service
```

Maintenant, éditez le fichier copié (/etc/systemd/system/keycloak.service) et adaptez-le comme suit:
![keycloak.service](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/oxr6ycg88rdkx1qaigtp.png)

Tout est maintenant en place pour prendre les modifications en compte par systemd:

```
systemctl daemon-reload
systemctl enable keycloak
```
et lancer notre nouveau service
```
systemctl start keycloak
```
Contrôlez son démarrage avec un simple:
```
systemctl status keycloak
```
![status keycloak](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/q9ysyfgqc9jg0u4oeo35.png)

Contrôlez aussi l'accès à l'interface d'admin de Keycloak à l'adresse http://<nom_machine_public_de_la_vm:8080/auth/ (dans notre exemple : http://gbtux.org:8080/auth/)

![capture keycloak](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/blefu3lu3cfonw9f1xqe.png)

## Keycloak en SSL

Pour mettre notre serveur Keycloak en SSL (httpS ;) ), il nous faut un certificat.
On va utiliser *certbot*, l'outil de [Let's Encrypt](https://letsencrypt.org/fr/) qui permet de créer des certificats automatiquement.

Installons-le :
```
apt install certbot
```

Puis créons notre certificat :

> Attention: certbot a besoin du port 80 pour fonctionner. Or, notre serveur Apache tourne sur ce port. Arrêtez-le temporairement avec un simple *systemctl stop apache2*

```
certbot certonly --standalone -d gbtux.org
```

Vous pouvez constater que certbot a créé toute une arborescence dans */etc/letsencrypt*, et notamment un répertoire /etc/letsencrypt/live/<votre_domaine>. 

>On va aussi utiliser tous ces fichiers *.pem dans notre configuration Apache.

Maintenant que nous avons notre certificat, on va l'importer dans le *keystore* (littéralement *magasin de clés*) de Keycloak.

Allons dans le répertoire de configuration où se trouve notre keystore:
```
cd /opt/keycloak-12.0.4/standalone/configuration
```
Dans ce répertoire se trouve un fichier *application.keystore*. 

Importons notre certificat (évidemment, remplacez tous les "gbtux.org" par votre nom de domaine):
```
openssl pkcs12 -export -inkey /etc/letsencrypt/live/gbtux.org/privkey.pem -in /etc/letsencrypt/live/gbtux.org/fullchain.pem -out application.keystore -name gbtux.org
```

>RETENEZ BIEN LE MOT DE PASSE QUE VOUS ALLEZ CREER !

Vérifions l'import (le mot de passe demandé est évidemment celui que vous venez de créer):
```
keytool -list -v -keystore application.keystore 
```

Configurons Keycloak pour utiliser ce nouveau certificat ajouté dans le keystore.
Dans le même répertoire, éditez le fichier *standalone.xml*.

Repérez l'entrée "security-realms" puis celle concernat "ApplicationRealm" (aux alentours de la ligne 46) et modifiez les valeurs de configuration tel que:
![ssl realm](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0463x7irn1we9pwdgwyk.png)

Redémarrez Keycloak pour prendre en compte la configuration
```
systemctl restart keycloak
systemctl status keycloak
```
Et admirez le résultat ;) : [https://votre_domaine:8443/auth/](https://votre_domaine:8443/auth/)

## Créer un utilisateur d'admin

Maintenant qu'on a accès à la console, créez un utilisateur d'admin/

Placez-vous dans le répertoire bin de Keycloak:
```
cd /opt/keycloak-12.0.4/bin
```
Puis créez votre utilisateur (et redémarrez Keycloak):
```
./add-user-keycloak.sh -r master -u <username> -p <password>
systemctl restart keycloak
```

Cliquez sur le lien "Administration Console" sur la page d'accueil de votre Keycloak, et testez votre login !

# Apache

Maintenant que notre Keycloak marche en SSL, on va mettre un serveur Apache devant en reverse proxy. Pourquoi me direz-vous ? ben ...parce que c'est mieux de ne pas directement exposer son serveur d'application. 
La bonne pratique c'est bien de mettre un Apache en frontal qui relaie les requêtes externes vers un serveur d'application qui lui n'écoute que sur une adresse "locale". Cela vous permettrais de filtrer l'accès à la partie admin de Keycloak par exemple

>Notez qu'ici je vous fais faire les 2 (port 443 via Apache, port 8443 en *direct*) pour éviter de complexifier la configuration. Pour *faire ça bien*, il faut modifier le fichier de configuration de Keycloak (/etc/keycloak/keycloak.conf et changer le paramètre WILDFLY_BIND pour 127.0.0.1). Ainsi, le Keycloak n'est plus accessible que via Apache (i.e le port 8443 n'est plus accessible depuis une IP publique).


## Installation
Installons Apache HTTPD:
 
```
apt install apache2
```

## Activer les modules nécessaires

Pour faire un reverse proxy, Apache a besoin de quelques modules activés
```
a2enmod proxy proxy_http ssl headers
```
Pour les prendre en compte, redémarrez Apache:
```
systemctl restart apache2
```

## Création d'un VirtualHost

On va créer un VirtualHost dédié à notre Keycloak, pour y mettre un *reverse proxy*.

Créez un fichier de configuration dans la configuration Apache :
```
/etc/apache2/sites-available/keycloak.conf
```
Puis déclarons notre configuration à l'intérieur:
```
<IfModule mod_ssl.c>
	<VirtualHost _default_:443>

		ErrorLog ${APACHE_LOG_DIR}/keycloak-error.log
		CustomLog ${APACHE_LOG_DIR}/keycloak-access.log combined

		SSLEngine on
		SSLCertificateFile	/etc/letsencrypt/live/gbtux.org/cert.pem
		SSLCertificateKeyFile /etc/letsencrypt/live/gbtux.org/privkey.pem
		SSLCertificateChainFile /etc/letsencrypt/live/gbtux.org/chain.pem

		ProxyPreserveHost On
    		SSLProxyEngine On
    		SSLProxyCheckPeerCN on
    		SSLProxyCheckPeerExpire on
    		RequestHeader set X-Forwarded-Proto "https"
    		RequestHeader set X-Forwarded-Port "443"
    		ProxyPass / https://127.0.0.1:8443/
    		ProxyPassReverse / https://127.0.0.1:8443/
	</VirtualHost>
</IfModule>

```

Activez maintenant ce nouveau VirtualHost :
```
systemctl restart apache2
```

Puis testez si ça marche dans votre navigateur à l'adresse [https://votre_domaine/auth/](https://votre_domaine/auth/) 
 (https://gbtux.org/auth/ pour mon exemple).


# Conclusion

Une grosse étape a été franchie. Notre serveur d'authentification est installé et configuré proprement.

Dans le prochain épisode, on fait du Symfony !