连接Debian的SSL Postgres外部数据库时出现问题(证书权限错误)

3

问题

脚本示例

<?php 
// define constants
define('DB_HOST', '1.1.1.1');
define('DB_USER', 'usr');
define('DB_PASS', 'pw');
define('DB_NAME', 'db');
define('DB_PORT', '5432');

// connection string with SSL certificate files 
$conn_str  = 'host=' . DB_HOST . ' ';
$conn_str .= 'port=' . DB_PORT . ' ';
$conn_str .= 'dbname=' . DB_NAME . ' ';
$conn_str .= 'user=' . DB_USER . ' ';
$conn_str .= 'password=' . DB_PASS . ' ';
$conn_str .= 'sslmode=verify-full ';
$conn_str .= 'sslcert=etc/apache/ssl/postgresql.crt ';
$conn_str .= 'sslkey=etc/apache/ssl/postgresql.key '; 
$conn_str .= 'sslrootcert=etc/apache/ssl/root.key '; 

// attempt connection
$conn = pg_connect($conn_str) or die('Cannot connect to database.');

// set sql string
$sql = 'SELECT * FROM locations;'; 

// query and iterate results
if($result = pg_query($conn, $sql)) 
    while($row=pg_fetch_row($result)) {
        var_dump($row);
    } 

// close it up
pg_close();
?>

我能够使用xampp和PHP连接到外部SSL Postgres数据库,但是在我的debian linux服务器上尝试时,无法建立连接。

我怀疑这是路径问题或权限问题。我将我的证书放在/var/www/html和/etc/ssl中,但我的生产服务器上的这两个路径都无法工作。在xampp中,我只需指定c:/xampp/htdocs/certs.key/.crt即可正常工作。

是什么导致了我的生产服务器出现问题?

解决方案(部分)

由于pg_last_error()和pg_errormessage()不会返回连接尝试的错误,因此我不得不创建一个自定义的异常处理程序。我附加了自定义的异常处理程序,最终获得了错误:

"pg_connect(): Unable to connect to PostgreSQL server: private key file "/etc/apache2/ssl/postgresql.key" has group or world access; permissions should be u=rw (0600) or less"

接下来,我尝试更改 key/crt 的 CHMOD 权限。

sudo chmod 0600 /etc/apache2/ssl/postgresql.crt
sudo chmod 0600 /etc/apache2/ssl/postgresql.key 

这让我出现了错误。
pg_connect(): Unable to connect to PostgreSQL server: could not read certificate file "/etc/apache2/ssl/postgresql.crt": Permission denied

我使用了Linux命令"ls -la",发现我是所有者,所以我执行了chown命令。

chown root:root /etc/apache2/ssl/postgresql.crt
chown root:root /etc/apache2/ssl/postgresql.key

好的,那没有成功,我在我的PHP脚本中添加了

echo exec('whoami');

那个输出了 'www-data',好的,所以我输入了:
sudo chown -R www-data:www-data /etc/ssl/
chmod 700 /etc/ssl/ 

终于成功了!虽然不确定这个方法是否安全,但这是我的临时解决方案。

最终脚本

<?php  
// Create a custom exception error handler for pg_connect
function exception_error_handler($errno, $errstr, $errfile, $errline ) {
    throw new ErrorException($errstr, $errno, 0, $errfile, $errline);
}
// Set the error handler
set_error_handler("exception_error_handler");

// Force output of all errors
error_reporting(E_ALL);

// Define constants
define('DB_HOST', '1.1.1.1');
define('DB_USER', 'USR');
define('DB_PASS', 'PW');
define('DB_NAME', 'DB');
define('DB_PORT', '5432');

// Connection string with SSL certificate files
$conn_str  = 'host=' . DB_HOST . ' ';
$conn_str .= 'port=' . DB_PORT . ' ';
$conn_str .= 'dbname=' . DB_NAME . ' ';
$conn_str .= 'user=' . DB_USER . ' ';
$conn_str .= 'password=' . DB_PASS . ' ';
$conn_str .= 'sslmode=require ';
$conn_str .= 'sslcert=/etc/apache2/ssl/postgresql.crt ';
$conn_str .= 'sslkey=/etc/apache2/ssl/postgresql.key ';  

// Try catch block grabbing stored exception
try {
    echo "Attempting pg_connect: " . $conn_str . "<br>";
    $conn=@pg_connect($conn_str);
} catch (Exception $e) {
    echo $e->getMessage();
}

// Attempt Connection
$conn = pg_connect($conn_str) or die('Cannot connect to database.');

// Set SQL String
$sql = 'SELECT * FROM locations'; 

// Attempt query and iterate results
if(result = pg_query($conn, $sql)) 
    while($row=pg_fetch_row($result)) {
        var_dump($row);
    } 

// Close it up
pg_close();
?>

欢迎来到SO!你能发布一下你收到的确切错误吗? - ewitkows
1个回答

0

使用sslcert和sslkey时,我遇到了连接字符串的问题。 一直收到Fatal connection requires a valid clien certificate的错误信息。 更改了权限、用户组,最终通过提供完整路径解决了我的问题。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接