Retour à l'accueil

Configuration ClickHouse : mise en place production de config.xml et users.xml

Guide pratique pour configurer ClickHouse pour un environnement de production. Les principales sections de config.xml sont couvertes : logger avec rotation basée sur la taille (10 fichiers de 1 Go chacun), chemins des données et du swap, paramètres MergeTree (min_bytes_for_wide_part, parts_to_throw_insert=300). La structure de users.xml pour trois types d'utilisateurs est présentée : analystes (readonly=1, limites de mémoire et de temps), application (ressources limitées), administrateur (accès local). Paramètres de profil : max_memory_usage, max_execution_time, max_rows_to_read. Quotas sur le nombre de requêtes et de lignes lues. Compression LZ4 (vitesse) vs ZSTD (économie d'espace). TLS/SSL pour un accès sécurisé. Principe de configuration via config.d/ pour préserver les paramètres lors des mises à jour. Checklist de sécurité minimale : changer le mot de passe par défaut, fermer les ports via UFW/iptables, restreindre les réseaux dans users.xml, activer query_log.

ClickHouse : comment configurer la production sans perdre de données
Advertisement 728x90

Configuration de ClickHouse : Comment j'ai mis en place la production sans me tirer une balle dans le pied

L'histoire d'une faute de frappe : 300 Go de logs et un serveur planté

Par défaut, ClickHouse écrit les logs dans /var/log/clickhouse-server/ et ne les archive jamais. Deux semaines après le lancement, nous avons découvert que le fichier de log avait gonflé à 300 Go et rempli toute la partition racine. Le serveur a planté. Les analystes ne pouvaient pas exécuter de SELECT, la production était en panne.

La documentation de ClickHouse est immense, mais en production, vous n'avez vraiment besoin de modifier qu'environ 20 paramètres. Voici ma checklist issue de 5 ans d'exploitation de clusters allant de 1 à 12 nœuds.

1. config.xml : Le squelette d'une configuration de production

La configuration principale se trouve dans /etc/clickhouse-server/config.xml. Voici les sections que je touche dans chaque projet :

Google AdInline article slot
<clickhouse>
    <!-- Journalisation — ajouter une rotation pour éviter de répéter mon erreur -->
    <logger>
        <level>information</level>
        <log>/var/log/clickhouse-server/clickhouse-server.log</log>
        <errorlog>/var/log/clickhouse-server/clickhouse-server.err.log</errorlog>
        <size>1000M</size>
        <count>10</count>
        <!-- Cela sauvegarde les disques. 10 fichiers de 1 Go chacun — rotation basée sur la taille -->
    </logger>

    <!-- Ports — standard, mais je les change en production -->
    <tcp_port>9000</tcp_port>           <!-- Client natif -->
    <http_port>8123</http_port>         <!-- API HTTP -->
    <interserver_http_port>9009</interserver_http_port>  <!-- Réplication -->
    
    <!-- Interfaces d'écoute — en production, NE PAS mettre 0.0.0.0 sans pare-feu -->
    <listen_host>0.0.0.0</listen_host>  <!-- Toutes les interfaces — attention -->
    <!-- <listen_host>::</listen_host>   IPv6 -->
</clickhouse>

Pourquoi je déconseille d'utiliser aveuglément 0.0.0.0 : En production avec une IP publique, votre ClickHouse deviendra une cible pour le scan de ports. Mieux vaut utiliser un VPN ou des pare-feux.

2. Chemins de données : Où ClickHouse stocke tout

<path>/var/lib/clickhouse/</path>           <!-- Données principales -->
<tmp_path>/var/lib/clickhouse/tmp/</tmp_path>
<user_files_path>/var/lib/clickhouse/user_files/</user_files_path>
<format_schema_path>/var/lib/clickhouse/format_schemas/</format_schema_path>

Ce qui m'a brûlé : Le /tmp du système était monté en mémoire (tmpfs) avec seulement 2 Go. ClickHouse essayait d'écrire des fichiers temporaires pour les grosses requêtes GROUP BY et plantait avec une erreur. J'ai déplacé tmp_path vers un disque de 50 Go :

<tmp_path>/data/clickhouse_tmp/</tmp_path>

3. Paramètres MergeTree : Prévenir les catastrophes

Je définis ces paramètres sur tous les serveurs de production :

Google AdInline article slot
<merge_tree>
    <!-- Une partie ne fusionnera pas tant qu'elle n'aura pas accumulé 10 Go — réduit la charge en arrière-plan -->
    <min_bytes_for_wide_part>10000000000</min_bytes_for_wide_part>
    
    <!-- Taille maximale de partie pour la fusion (100 Go) -->
    <max_bytes_to_merge_at_max_space_in_pool>107374182400</max_bytes_to_merge_at_max_space_in_pool>
    
    <!-- Si les parties dépassent 300, les nouveaux INSERT seront rejetés -->
    <parts_to_throw_insert>300</parts_to_throw_insert>
    
    <!-- Avertissement à 200 parties -->
    <parts_to_delay_insert>200</parts_to_delay_insert>
    
    <!-- Nombre maximal de parties dans une partition -->
    <max_parts_in_total>10000</max_parts_in_total>
</merge_tree>

Pourquoi parts_to_throw_insert = 300 : Si vous avez 300+ parties, les SELECT ralentissent, et les INSERT ne font qu'empirer les choses. Mieux vaut rejeter l'insert et enquêter.

4. users.xml : Utilisateurs, profils, quotas

Le fichier /etc/clickhouse-server/users.xml est le contrôle d'accès. Je crée trois utilisateurs :

<clickhouse>
    <!-- 1. Utilisateur pour les analystes (lecture seule) -->
    <analyst>
        <password>analyst_secure_password</password>
        <networks>
            <ip>10.0.0.0/8</ip>   <!-- Réseau interne uniquement -->
        </networks>
        <profile>readonly_profile</profile>
        <quota>analyst_quota</quota>
    </analyst>

    <!-- 2. Application (ressources limitées) -->
    <app_user>
        <password>${CLICKHOUSE_APP_PASSWORD}</password>  <!-- Depuis une variable d'environnement -->
        <networks>
            <ip>::/0</ip>  <!-- Attention ici, mieux vaut utiliser des sous-réseaux spécifiques -->
        </networks>
        <profile>app_profile</profile>
    </app_user>

    <!-- 3. Administrateur (accès complet) -->
    <admin>
        <password>admin_strong_password</password>
        <networks>
            <host>localhost</host>
            <host>10.0.0.50</host>  <!-- Hôte bastion uniquement -->
        </networks>
        <profile>admin_profile</profile>
    </admin>
</clickhouse>

Nuance importante : Le mot de passe de l'utilisateur par défaut est vide par défaut. C'est la première chose que je change après l'installation.

Google AdInline article slot

5. Profils de paramètres : Protection contre les requêtes folles

Les profils sont des ensembles de contraintes qui sauvent le cluster de SELECT * FROM huge_table CROSS JOIN.

<profiles>
    <!-- Analystes : peuvent exécuter des requêtes lourdes mais avec des limites -->
    <readonly_profile>
        <readonly>1</readonly>   <!-- SELECT uniquement -->
        <max_memory_usage>10000000000</max_memory_usage>  <!-- 10 Go -->
        <max_execution_time>300</max_execution_time>      <!-- 5 minutes -->
        <max_rows_to_read>50000000000</max_rows_to_read>  <!-- 50 milliards de lignes -->
        <max_bytes_to_read>107374182400</max_bytes_to_read> <!-- 100 Go -->
        <prefer_global_in_and_join>1</prefer_global_in_and_join>
    </readonly_profile>

    <!-- Application : requêtes rapides, petites limites -->
    <app_profile>
        <readonly>0</readonly>
        <max_memory_usage>1000000000</max_memory_usage>   <!-- 1 Go -->
        <max_execution_time>10</max_execution_time>        <!-- 10 secondes -->
        <max_rows_to_read>100000000</max_rows_to_read>     <!-- 100 millions -->
        <timeout_before_checking_execution_speed>0</timeout_before_checking_execution_speed>
    </app_profile>

    <!-- Admin : presque aucune limite (mais attention) -->
    <admin_profile>
        <readonly>0</readonly>
        <max_memory_usage>0</max_memory_usage>  <!-- pas de limite -->
        <max_execution_time>0</max_execution_time>
    </admin_profile>
</profiles>

Quotas — pour qu'un analyste ne tue pas tout le monde :

<quotas>
    <analyst_quota>
        <interval>
            <duration>3600</duration>      <!-- par heure -->
            <queries>100</queries>         <!-- pas plus de 100 requêtes -->
            <errors>0</errors>             <!-- aucune erreur -->
            <result_rows>100000000</result_rows>  <!-- 100 millions de lignes de résultat -->
            <read_rows>10000000000</read_rows>    <!-- 10 milliards lues -->
        </interval>
    </analyst_quota>
</quotas>

6. Paramètres de compression par défaut

ClickHouse compresse les données avec LZ4 (rapide) ou ZSTD (plus fort). Je choisis en fonction du type de données :

<compression>
    <!-- LZ4 pour les données récentes (vitesse) -->
    <case>
        <last_level>1</last_level>  <!-- Niveau de compression -->
        <method>LZ4</method>
    </case>
    
    <!-- ZSTD pour les partitions de plus de 30 jours (économie d'espace) -->
    <case>
        <min_part_size>10737418240</min_part_size>  <!-- 10 Go -->
        <method>ZSTD</method>
        <level>3</level>
    </case>
</compression>

Mon choix en production : LZ4 pour toutes les données. ZSTD économise 20 à 30 % d'espace mais perd jusqu'à 10 % de vitesse sur les requêtes.

7. TLS/SSL — Si vous n'êtes pas dans un réseau isolé

<https_port>8443</https_port>
<tcp_port_secure>9440</tcp_port_secure>

<openSSL>
    <server>
        <certificateFile>/etc/clickhouse-server/ssl/server.crt</certificateFile>
        <privateKeyFile>/etc/clickhouse-server/ssl/server.key</privateKeyFile>
        <verificationMode>none</verificationMode>
        <caConfig>/etc/clickhouse-server/ssl/CA.pem</caConfig>
        <cacheSessions>true</cacheSessions>
        <disableProtocols>sslv2,sslv3,tlsv1,tlsv1_1</disableProtocols>
        <preferServerCiphers>true</preferServerCiphers>
    </server>
</openSSL>

Ce qui m'a brûlé : Un certificat auto-signé sans vérification n'est sûr que dans un réseau de confiance. Pour un accès externe, utilisez Let's Encrypt ou un certificat payant.

8. config.d/ — Surcharges sans douleur

Ne modifiez jamais config.xml directement. Mettez toutes les modifications dans /etc/clickhouse-server/config.d/.

Fichier config.d/memory.xml :

<clickhouse>
    <max_server_memory_usage>0.75</max_server_memory_usage>  <!-- 75 % de la RAM totale -->
    <max_concurrent_queries>100</max_concurrent_queries>
</clickhouse>

Fichier config.d/networks.xml :

<clickhouse>
    <listen_host>0.0.0.0</listen_host>
    <max_connections>4096</max_connections>
</clickhouse>

Avantages : Lors de la mise à jour de ClickHouse, votre config.xml ne sera pas écrasé et les surcharges restent. J'ai appris cela à mes dépens après avoir perdu ma configuration lors d'une mise à niveau de 22.x à 23.x.

9. Checklist de sécurité pour une plateforme de paris

Avant d'ouvrir l'accès à ClickHouse au monde extérieur, je vérifie :

✅ Changer le mot de passe utilisateur par défaut

clickhouse-client --password
ALTER USER default IDENTIFIED BY 'new_strong_password';

✅ Supprimer ou restreindre l'utilisateur par défaut

<!-- Dans users.xml, commentez la section default -->
<!-- <default>
    <password></password>
</default> -->

✅ Fermer les ports de l'accès externe (UFW)

sudo ufw default deny incoming
sudo ufw allow from 10.0.0.0/8 to any port 9000 proto tcp  # réseau interne uniquement
sudo ufw allow from 10.0.0.0/8 to any port 8123 proto tcp
sudo ufw allow ssh

✅ Activer le pare-feu au niveau de l'hôte

sudo iptables -A INPUT -p tcp --dport 9000 -s 10.0.0.0/8 -j ACCEPT
sudo iptables -A INPUT -p tcp --dport 9000 -j DROP

✅ Définir max_memory_usage pour qu'une seule requête ne tue pas le serveur

<max_memory_usage>10000000000</max_memory_usage>  <!-- 10 Go -->

✅ Désactiver les fonctionnalités expérimentales (si non nécessaires)

<allow_experimental_geo_types>0</allow_experimental_geo_types>
<allow_experimental_window_functions>1</allow_experimental_window_functions> <!-- 23.8+ -->

✅ Activer query_log et slow_log pour la surveillance

<query_log>
    <database>system</database>
    <table>query_log</table>
    <partition_by>toYYYYMM(event_date)</partition_by>
    <flush_interval_milliseconds>7500</flush_interval_milliseconds>
</query_log>

<query_thread_log>
    <database>system</database>
    <table>query_thread_log</table>
</query_thread_log>

✅ Restreindre l'accès par IP (liste blanche)

<analyst>
    <networks>
        <ip>10.0.0.100</ip>   <!-- IP analyste spécifique uniquement -->
        <ip>10.0.0.101</ip>
        <ip>192.168.1.0/24</ip>
    </networks>
</analyst>

Prochaine étape

Maintenant, votre ClickHouse est configuré pour la bataille. Le prochain article concerne la surveillance et les sauvegardes en production.


Précédente: Suivante: ReplacingMergeTree : Comment Vaincre les Doublons dans ClickHouse Sans Douleur

— Editorial Team

Advertisement 728x90

Lire ensuite