Linux – How to get rid of “Could not connect to database” with Linux and libnss-pgsql2

debian-squeezelinuxnsspostgresql

I use libnss-pgsql2 in order to have virtual system users stored in a PostgreSQL database.
The virtual users in the database work just fine. They can log in. I can see their uid, gid, groups via the 'id' command. Example:

# id backup001
uid=10001(backup001) gid=10001(backup001) groups=10001(backup001)

However, on systems that I use libnss, I frequently get this error:

Could not connect to database

It happens, for instance, often with cron-jobs. I have one cron-job that runs every hour that dumps the postgresql databases to a backup. The contrab is this:

04 *  *   *   *     postgres umask 077 && /usr/bin/pg_dumpall | gzip > ~postgres/backup/postgresql-complete-dump-$(date +\%H).sql.gz

This job always produces the error. Thus, flooding me with an e-mail every hour.

My setup is pretty simple:
The table layout I use to store the users is available here:
http://p.adora.dk/P2486.html

I use Debian Squeeze on the server.

Relevant config files are:
nsswitch.conf : http://p.adora.dk/P2489.html

(description: use "normal" system users in /etc/passwd and /etc/shadow, however, if the user is NOT found, then proceed with a lookup via pgsql)

nss-pgsql.conf : http://p.adora.dk/P2487.html

(description: contains the SQL queries that are used to look up various information that normally is found in /etc/passwd and /etc/group)

nss-pgsql-root.conf : http://p.adora.dk/P2488.html

(description: contains the SQL queries that are used to lookup confidential info that is normally found in /etc/shadow)

Things that I have done to debug this:

  • Verified that the connection strings in both nss-pgsql.conf and nss-pgsql-root.conf work as intended.
  • Verified that the timeout does not occur. I.e. the error is echoed immediately and not after 300 seconds. Also, this happens on a server that does not do anything – so the connection should be established without delay — I have verified that it does.

I really hope you can help me fix this error.

Update 2012-08-22:

I tried doing an strace on psql. The relevant part of the strace is in the bottom of this paste:
http://paste.adora.dk/P2492.html

I notice that it tries opening /etc/nss-pgsql-root.conf and get EACCESS, however, I do not believe this should be a problem. This file should be readable by root only as it corresponds to /etc/shadow which is also only readable by root.

25341 access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory)
25341 open("/usr/lib/libgpg-error.so.0", O_RDONLY) = 4
25341 read(4, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0 \6\0\0004\0\0\0"..., 512) = 512
25341 fstat64(4, {st_mode=S_IFREG|0644, st_size=11540, ...}) = 0
25341 mmap2(NULL, 14512, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 4, 0) = 0xb6f6c000
25341 mmap2(0xb6f6f000, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 4, 0x2) = 0xb6f6f000
25341 close(4)                          = 0
25341 mprotect(0xb70bf000, 4096, PROT_READ) = 0
25341 mprotect(0xb73d8000, 4096, PROT_READ) = 0
25341 munmap(0xb7414000, 40018)         = 0
25341 open("/etc/nss-pgsql-root.conf", O_RDONLY) = -1 EACCES (Permission denied)
25341 write(2, "\nCould not connect to database\n", 31) = 31

It is possible that this is a bug in libnss-pgsql…. What do you think?

Update 2012-08-22:

OK. I dug up this five year old bug report:
http://pgfoundry.org/tracker/index.php?func=detail&aid=1010197&group_id=1000039&atid=234

It seems that this behavior is actually a bug. A patch has been provided, however, there is no activity on the bug report. Maybe the project is abandoned. I certainly hope not 🙁

Best Answer

I think the answer to your problem is in this this line:

open("/etc/nss-pgsql-root.conf", O_RDONLY) = -1 EACCES (Permission denied)

Try relaxing permissions on this file to be readable by "group" and "other" and see if that solves the problem.

You are wrong that the file corresponds to /etc/shadow. It corresponds to /etc/password, which is readable by "group" and "other". Your PostgreSQL database and tables used for authentication correspond to /etc/shadow.

It can't connect to the database because it can't read the database access credentials from this file.