Skip to content

ldap2pg ignores SASL_MECH configuration #770

@s40547698

Description

@s40547698

Hi, I'm having a problem using ldap2pg 6.5.1 on a Ubuntu 24.04 server which is joined to a FreeIPA domain.

I run the following command:

ldap2pg --verbose --config /etc/ldap2pg/ldap2pg.yml

At the end I get the error: err="unhandled SASL_MECH"

Variable SASL_MECH is always being read from /etc/ldap/ldap.conf. This variabile is defined by FreeIPA and I have not found a working way to override it with the ldap2pg YAML file.

The only way to make the command run successfully is to comment SASL_MECH in /etc/ldap/ldap.conf, but as this value is set by FreeIPA it may be important to keep.

Expectations

  • What you expected from ldap2pg ?
    I expect ldap2pg to override SASL_MECH by using the value in the YAML file passed via --config flag.

  • What ldap2pg did wrong ?
    ldap2pg ignores SASL_MECH overrides from my files and instead always reads it from /etc/ldap/ldap.conf, but this is wrong.

Below are my redacted files and command output. Any input would be appreciated, thanks.

ldap2pg.yml

version: 6

ldap:
  uri: "ldap://ldap.example.com:389"
  binddn: "CN=ldapuser,OU=xxx,dc=example,dc=com"
  password: "xxx"
  base: "OU=xxx,DC=example,DC=COM"
  sasl_mech: none

postgres:
  uri: "postgres://ldap2pg:xxx@localhost:5432/postgres"

# Excluding postgres and system roles
managed:
  - "^(?!postgres$|pg_.*$).*"

rules:
 - ldapsearch:
     base: "OU=UserAccounts,DC=example,DC=COM"
     scope: sub
     filter: "(&(objectClass=user)(!(userAccountControl:1.2.840.113556.1.4.803:=2)))"
   roles:
     - names:
         - "{sAMAccountName}"

/etc/ldap/ldap.conf

TLS_CACERT      /etc/ssl/certs/ca-certificates.crt
URI ldaps://freeipa.example.com
BASE dc=idm,dc=example,dc=com
SASL_MECH GSSAPI

/var/lib/postgresql/.ldaprc

URI ldap://ldap.example.com:389
BINDDN CN=ldapuser,OU=xxx,dc=example,dc=com
PASSWORD xxx
BASE OU=xxx,DC=example,DC=COM

Verbose output of ldap2pg execution

$ ldap2pg --verbose --config /etc/ldap2pg/ldap2pg.yml

16:53:01 INFO   Starting ldap2pg                                 version=6.5.1 commit=fe04c0e4 runtime=go1.25.1 pid=139454
16:53:01 INFO   Using YAML configuration file.                   path=/etc/ldap2pg/ldap2pg.yml
16:53:01 DEBUG  Loading YAML configuration.
16:53:01 DEBUG  Dumping normalized YAML to stderr.
ldap:
  base: OU=UserAccounts,DC=EXAMPLE,DC=COM
  binddn: CN=ldapuser,OU=xxx,dc=example,dc=com
  password: 'xxx'
  uri: ldap://ldap.example.com:389
managed:
  - ^(?!postgres$|pg_.*$).*
postgres:
  uri: postgres://ldap2pg:xxx@localhost:5432/postgres
rules:
  - description: ""
    grants: []
    ldapsearch:
      base: OU=UserAccounts,DC=EXAMPLE,DC=COM
      filter: (&(objectClass=user)(!(userAccountControl:1.2.840.113556.1.4.803:=2)))
      scope: sub
    roles:
      - comment: Managed by ldap2pg
        name: '{sAMAccountName}'
        options:
          BYPASSRLS: false
          CONNECTION LIMIT: -1
          CREATEDB: false
          CREATEROLE: false
          INHERIT: true
          LOGIN: false
          REPLICATION: false
          SUPERUSER: false
        parents: []
version: 6
16:53:01 DEBUG  Collected LDAP search attributes.                item="" base="OU=UserAccounts,DC=EXAMPLE,DC=COM" attributes=[sAMAccountName]
16:53:01 DEBUG  Loaded configuration file.                       version=6
16:53:01 WARN   Dry run. Postgres instance will be untouched.
16:53:01 DEBUG  Setting default Postgres connection timeout.     timeout=5s
16:53:01 DEBUG  Found LDAP configuration file.                   path=/etc/ldap/ldap.conf
16:53:01 DEBUG  Found LDAP configuration file.                   path=/var/lib/postgresql/.ldaprc
16:53:01 DEBUG  Found LDAP configuration file.                   path=/var/lib/postgresql/.ldaprc
16:53:01 DEBUG  Stage 0: role blacklist.
16:53:01 DEBUG  Opening Postgres global connection.              database=""
16:53:01 DEBUG  Inspecting PostgreSQL server and session.
16:53:01 DEBUG  Executing SQL query:
WITH me AS (
        SELECT
                rolname AS "current_user",
                rolsuper AS "issuper"
        FROM pg_catalog.pg_roles
        WHERE rolname = CURRENT_USER
),
postgres AS (
        SELECT
                substring(version() from '^[^ ]+ [^ ]+') AS server_version,
                current_setting('server_version_num')::BIGINT AS server_version_num,
                current_setting('cluster_name') AS cluster_name,
                current_database() AS current_database
)
SELECT
        postgres.*,
        me.*
FROM postgres, me;

16:53:01 INFO   Running as superuser.                            user=postgres super=true server="PostgreSQL 17.7" cluster=17/main database=postgres
16:53:01 DEBUG  Fallback owner configured.                       role=postgres
16:53:01 DEBUG  Inspecting roles blacklist.                      config=roles_blacklist_query
16:53:01 DEBUG  Reading values from YAML.
16:53:01 DEBUG  Roles blacklist loaded.                          patterns="[pg_* postgres]"
16:53:01 DEBUG  LDAP dial.                                       uri=ldap://ldap.example.com:389 try=1
16:53:01 DEBUG  LDAP set timeout.                                timeout=30s
16:53:01 DEBUG  Closing Postgres global connection.              database=""
16:53:01 ERROR  Fatal error.                                     err="unhandled SASL_MECH"

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions