risingwavelabs/risingwave · error · PsqlError

Failed to connect to LDAP server

Error message

Failed to connect to LDAP server

What it means

establish_connection calls LdapConnAsync::with_settings to open a TCP/TLS connection to the LDAP server. Any connection-level failure — DNS resolution, TCP refused, TLS handshake rejection, timeout — is wrapped as this StartupError before any bind attempt. The library cannot proceed without an LDAP session.

Source

Thrown at src/utils/pgwire/src/ldap_auth.rs:458

            let client_config = tls_config.init_client_config()?;
            settings = settings.set_config(Arc::new(client_config));

            if matches!(tls_config.req_cert, ReqCertPolicy::Demand) {
                settings = settings.set_no_tls_verify(false);
            } else {
                warn!(
                    "LDAP client certificate verification is disabled due to LDAPTLS_REQCERT policy"
                );
                settings = settings.set_no_tls_verify(true);
            }
        }

        let (conn, ldap) = LdapConnAsync::with_settings(settings, &config.server)
            .await
            .map_err(|err| {
                PsqlError::StartupError(
                    anyhow!(err)
                        .context("Failed to connect to LDAP server")
                        .into(),
                )
            })?;
        ldap3::drive!(conn);

        Ok(ldap)
    }

    /// Search for user in LDAP directory and then bind
    async fn search_and_bind(&self, username: &str, password: &str) -> PsqlResult<bool> {
        // Establish connection to LDAP server
        let mut ldap = self.establish_connection().await?;

        // Validate base_dn configuration
        let base_dn = self
            .config
            .base_dn

View on GitHub (pinned to 6469eb736d)

Solutions

  1. Test reachability: nc -zv <host> <port> or openssl s_client -connect host:636
  2. Fix host/port in the ldap_url config (default port 389 for ldap://, 636 for ldaps://)
  3. If using ldaps with a self-signed cert, add the CA to the trust store or configure the danger-accept-invalid-certs setting appropriately for your security posture
  4. Check network/firewall/DNS from the machine running RisingWave (container networking often differs from the host)

Example fix

// before (unreachable from pod)
ldap_url = 'ldaps://10.0.0.5:636'
// after (internal DNS name reachable from k8s)
ldap_url = 'ldaps://ldap.internal.svc.cluster.local:636'
Defensive patterns

Strategy: retry

Validate before calling

// pre-check before creating the LDAP connection
# nc -zv ldap.corp.local 636 || echo 'LDAP port unreachable'
# openssl s_client -connect ldap.corp.local:636 -brief </dev/null

Try / catch

catch PsqlError::StartupError with context 'Failed to connect to LDAP server', inspect the source io/rustls error; retry with exponential backoff only for transient categories (timeout, connection reset), fail fast on refusal/TLS-trust errors

Prevention

When it happens

Trigger: LdapConnAsync::with_settings(settings, &config.server) awaits to Err: unreachable host, closed port, TLS cert rejected (ldaps), connection timeout

Common situations: LDAP server down or wrong host/port in ldap_url; firewall or security group blocks 389/636; ldaps:// used but server certificate is self-signed/untrusted; DNS not resolvable from inside the container/k8s pod; LDAP service in a different VPC.

Understand the failure class

Background: ECONNREFUSED and "connection refused" / "could not connect to server" errors: what they mean and how to fix them — this error's family across 44 libraries.

Related errors


AI-assisted analysis of risingwavelabs/risingwave@6469eb736d (2026-09-11). Data as JSON: /api/errors/4c25b47d79b772ac. Report an issue: GitHub.