Pool de connexions avec l' PgBouncer

PgBouncer est un gestionnaire de pool de connexions léger pour l' PostgreSQL. Il maintient un nombre réduit de connexions à la base de données et les partage entre de nombreux clients d'application, ce qui vous aide à respecter la limite de connexions imposée et évite la surcharge liée à l'ouverture d'une nouvelle connexion pour chaque client.

IBM Cloud® Databases for PostgreSQL Les déploiements incluent une prise en charge intégrée de l'authentification PgBouncer'sauth_query. Chaque déploiement fournit une public.pgbouncer_lookup fonction et un pgbouncer_auth rôle; ainsi, une instance de PgBouncer que vous exécutez peut valider directement les utilisateurs de la base de données par rapport à votre déploiement. Vous ne gérez pas de liste de mots de passe locale pour les utilisateurs de votre base de données, et les modifications de mot de passe prennent effet immédiatement, sans redémarrage ni rechargement d' PgBouncer.

Databases for PostgreSQL n'héberge ni n'exploite PgBouncer. Vous installez, exécutez, sécurisez et mettez à jour PgBouncer sur votre propre infrastructure, telle qu’un serveur virtuel, un cluster Kubernetes ou un sidecar d’application. Pour plus d'informations sur la gestion des connexions, consultez la section Gestion des connexions.

Avant de commencer

Vous avez besoin des éléments suivants :

  • Déploiement d' Databases for PostgreSQL avec le mot de passe administrateur défini.
  • Un utilisateur de base de données pour votre application, créé via l'interface utilisateur, la ligne de commande ou l'API.
  • PgBouncer 1.11.0 ou une version ultérieure, prenant en charge l'authentification SCRAM, installée sur une infrastructure que vous contrôlez. Si vous prévoyez d'utiliser des instructions préparées au niveau du protocole en mode de mise en commun des transactions, utilisez la version PgBouncer 1.21.0 ou une version ultérieure.
  • Un client psql.
  • Vos informations de connexion pour le déploiement :
    • Nom d'hôte et port, issus des [chaînes de connexion]...
    • Certificat CA, récupéré avec ibmcloud cdb deployment-cacert.

La prise en charge de pgbouncer_lookup est en cours de déploiement sur l'ensemble des environnements. Pour vérifier que votre déploiement dispose de cette fonctionnalité, connectez-vous en tant psql que admin et exécutez \df public.pgbouncer_lookup. Si le résultat est vide, votre déploiement recevra la fonction lors d'une prochaine mise à jour de maintenance.

Création d'un utilisateur d'authentification dédié

PgBouncer fonctionne auth_query sous un rôle d'authentification spécifique, son auth_user. Créez un rôle dédié exclusivement à cette fin. Un rôle dédié qui ne gère aucune donnée et n'exécute aucune autre tâche constitue le choix offrant le moins de privilèges.

Connectez-vous en psql tant qu'utilisateur admin, puis créez le rôle et attribuez-lui pgbouncer_auth:

CREATE ROLE pool_auth WITH LOGIN PASSWORD '<POOL_AUTH_PASSWORD>';
GRANT pgbouncer_auth TO pool_auth;

Ce rôle pgbouncer_auth ne confère qu'un seul privilège : l'autorisation d'exécuter la fonction pgbouncer_lookup. L'utilisateur admin dispose pgbouncer_auth de l'option d'administrateur; vous pouvez donc attribuer et révoquer vous-même les droits d'accès. Vous pouvez également créer l'utilisateur avec si ibmcloud cdb user-create vous souhaitez qu'il apparaisse dans vos identifiants de service, mais les utilisateurs créés de cette manière sont membres de ibm-cloud-base-user et peuvent créer des utilisateurs et des bases de données, ce qui dépasse les besoins de l'utilisateur d'authentification.

N'accorder l'accès pgbouncer_auth qu'à l'utilisateur disposant d'une autorisation dédiée. Tout membre de ce rôle peut consulter les vérificateurs de mot de passe enregistrés des autres utilisateurs de votre base de données; ainsi, chaque membre supplémentaire amplifie l'impact d'une compromission des identifiants.

Pour désactiver un utilisateur authentifié, révoquez son adhésion :

REVOKE pgbouncer_auth FROM pool_auth;

Configuration d' PgBouncer

Les paramètres d' PgBouncer s suivants sont requis lors de la connexion à un déploiement Databases for PostgreSQL:

  • auth_type = scram-sha-256, car les déploiements stockent des vérificateurs de mot de passe d' SCRAM-SHA-256.
  • auth_query = SELECT * FROM public.pgbouncer_lookup($1), car le fichier PgBouncer's par défaut auth_query s'affiche directement pg_authid et vos utilisateurs de la base de données ne peuvent pas le lire.
  • TLS côté serveur, car les déploiements n'acceptent que les connexions TLS. Définissez server_tls_sslmode = verify-full, puis enregistrez le certificat que vous avez récupéré avec ibmcloud cdb deployment-cacert à l'emplacement que vous avez défini dans server_tls_ca_file.

PgBouncer lit ses propres identifiants à auth_user partir de auth_file, donc dans cette configuration, userlist.txt ne contient que les identifiants auth_user. Un utilisateur sur deux effectue la résolution via auth_query. Limitez les droits d'accès au fichier au propriétaire du processus PgBouncer, par exemple avec le mode 0600.

"pool_auth" "<POOL_AUTH_PASSWORD>"

Une configuration minimale complète, où et <HOSTNAME> <PORT> proviennent de vos chaînes de connexion:

[databases]
ibmclouddb = host=<HOSTNAME> port=<PORT> dbname=ibmclouddb
[pgbouncer]
listen_addr = 127.0.0.1
listen_port = 6432
auth_type = scram-sha-256
auth_file = /etc/pgbouncer/userlist.txt
auth_user = pool_auth
auth_query = SELECT * FROM public.pgbouncer_lookup($1)
server_tls_sslmode = verify-full
server_tls_ca_file = /etc/pgbouncer/ca-certificate.crt
pool_mode = session
max_client_conn = 200
default_pool_size = 20

Ne pas définir auth_dbname = postgres. La fonction de recherche n'est pas installée dans la base postgres de données. Laissez ce paramètre non auth_dbname défini afin que la requête d'authentification s'exécute dans la base de données à laquelle le client se connecte. Les bases de données que vous créerez par la suite intégreront automatiquement cette fonctionnalité.

Pour obtenir la description de chaque paramètre, consultez le guide de configuration d' PgBouncer.

Vérification de l'installation

  1. Vérifiez que la recherche aboutit à l'un de vos utilisateurs de la base de données. Connectez-vous avec en psql tant que admin et exécutez :

    SELECT usename, passwd IS NOT NULL AS can_authenticate
      FROM public.pgbouncer_lookup('<APP_USERNAME>');
    

    Le résultat est une ligne contenant can_authenticate = t. La requête est rédigée de manière à ce que le vérificateur de mot de passe ne s'affiche pas. Les utilisateurs réservés au service, y compris admin, ne renvoient aucune ligne.

  2. Connectez-vous via PgBouncer en tant qu'utilisateur de la base de données :

    psql "host=127.0.0.1 port=6432 dbname=ibmclouddb user=<APP_USERNAME>"
    

    Si la connexion aboutit, PgBouncer authentifie correctement les utilisateurs via auth_query.

  3. Changez le mot de passe de l'utilisateur de la base de données, puis reconnectez-vous via PgBouncer avec le nouveau mot de passe :

    ibmcloud cdb user-password <DEPLOYMENT_NAME_OR_CRN> <APP_USERNAME> <NEW_PASSWORD>
    

    Le nouveau mot de passe est immédiatement opérationnel. Aucun redémarrage, rechargement ou userlist.txt modification d' PgBouncer n'est nécessaire.

Fonctionnement du modèle de sécurité

La fonction pgbouncer_lookup ne divulgue que les informations nécessaires à l'authentification par PgBouncer.

  • La fonction s'exécute avec SECURITY DEFINER et un épinglé search_path, et lit pg_catalog.pg_authid en votre nom. L'accès direct à et pg_authid reste pg_shadow bloqué.
  • Il renvoie des identifiants SCRAM hachés, jamais de mots de passe en clair.
  • Seuls les rôles autorisés à se connecter peuvent résoudre le problème. Les utilisateurs réservés aux services, tels que admin et les utilisateurs internes chargés de la réplication et des opérations, ne sont jamais résolus.
  • Si l'horodatage VALID UNTIL d'un rôle est antérieur à la date actuelle, la fonction renvoie un mot de passe NULL; l'authentification échoue donc et l'expiration du mot de passe reste appliquée.
  • L'autorisation d'exécuter la fonction est révoquée pour et PUBLIC n'est accordée qu'à admin et aux membres de pgbouncer_auth.

PgBouncer's La auth_query lecture par défaut s'effectue directement pg_authid, ce que vos utilisateurs de bases de données ne peuvent pas faire. Dans ce cas, la recommande PgBouncer documentation d'appeler une fonction SECURITY DEFINER via un utilisateur non super-utilisateur à la place. La fonction pgbouncer_lookup consiste à exclure les utilisateurs réservés du service.

Contraintes et considérations

  • PgBouncer n'affecte pas le déploiement max_connections. Dimensionnez default_pool_size de manière à ce que le nombre total de connexions serveur provenant de toutes vos instances d' PgBouncer e reste dans les limites autorisées. Si vous atteignez la limite, consultez la section Augmenter le nombre maximal de connexions.
  • L'utilisateur admin ne peut pas s'authentifier via auth_query. Pour les tâches d'administration, connectez-vous directement admin au déploiement, et non via PgBouncer.
  • La base postgres de données ne dispose pas de fonction de recherche; ne définissez donc jamais auth_dbname = postgres.
  • En mode de regroupement des transactions (pool_mode = transaction), l'état de la session, tel que les variables SET, les tables temporaires, les verrous consultatifs et les canaux LISTEN, n'est pas conservé d'une transaction à l'autre. Les instructions préparées au niveau du protocole nécessitent max_prepared_statements et PgBouncer 1.21.0 ou une version ultérieure. Pour plus d'informations, consultez la rubrique Fonctionnalités d' PgBouncer.
  • Lors d'une mise à niveau majeure sur site, votre déploiement subit une brève période d'indisponibilité et les connexions ouvertes sont interrompues (SQLSTATE 57P01). PgBouncer Il rétablit automatiquement ses connexions au serveur, mais vos applications doivent réessayer les transactions interrompues et préparer à nouveau les instructions.
  • Les utilisateurs en lecture seule ne peuvent pas se connecter au point de terminaison principal. Pour regrouper leurs connexions, ajoutez une entrée [databases] distincte pointant vers votreréplique en lecture seule.

Etapes suivantes