如何使用 R 连接到远程 PostgreSQL,需要证书验证

Posted

技术标签:

【中文标题】如何使用 R 连接到远程 PostgreSQL,需要证书验证【英文标题】:How to connect to remote PostgreSQL with R, certificate validation required 【发布时间】:2016-03-10 22:46:12 【问题描述】:

我正在尝试使用ssl = verify ca 模式连接到远程 Postgres 数据库。我的问题似乎类似于Connect to Redshift via SSL using R 和Connect to Postgres via SSL using R,但它们不能正常工作。错误总是

Error in postgresqlNewConnection(drv, ...) : RS-DBI driver: (could not connect (null)@datadb1 on dbname "(null)"

我的代码是这样的

library("RPostgreSQL")
host = 'datadb1'
dbname = 'test'
port = 5432
password = pw
username = 'pep'

pg_dsn = paste0(
  'dbname=', dbname, ' ',
  'sslrootcert=', "C://root-ca.crt", ' ',
  "sslkey=C://pep.key", " ",
  "sslcert=C://pep.crt", 
  'sslmode=verify-ca'
)
dbConnect(RPostgreSQL::PostgreSQL(), dbname=pg_dsn, host=host, 
          port=port, password=password, user=username)

但这不是一般的数据库问题,因为我可以使用 Python 连接到数据库。 更新:我在指定路径时出错了;错误实际上是这样的:

Error in postgresqlNewConnection(drv, ...) : RS-DBI driver: (could not connect pep@datadb1 on dbname "test") 

【问题讨论】:

【参考方案1】:

根据错误消息,问题在于您为用户名和数据库名称传递了空值。这表明您的实际代码与您在此处输入的内容不匹配。我会编写一个 10 行的 Rscript 程序,它只连接并抓取一些数据,如下所示:

#!/usr/bin/Rscript

library("RPostgreSQL")
host = '192.168.36.2'
dbname = 'test'
port = 5432
password = 'secret'
username = 'pep'

pg_dsn = paste(
                'dbname=', dbname, ' ',
                'sslrootcert=', 'rootCA.pem', ' ',
                'sslkey=pem.key', ' ',
                'sslcert=pem.crt', ' ',
                'sslmode=verify-ca',
                sep=""
                )

conn <- dbConnect(RPostgreSQL::PostgreSQL(), dbname=pg_dsn, host=host,
          port=port, password=password, user=username)
rs <- dbSendQuery(conn, statement="SELECT COUNT(*) FROM users")
data <- fetch(rs, n=1)
dim(data)

所以我认为这根本与 SSL 证书无关,而是您的变量没有按照您认为的方式设置。

编辑:我创建了自己的 CA 并使用它来签署服务器证书和客户端证书。我将 Postgres 9.3 放在一个新的虚拟机上,并且连接正常,双方都需要证书。我可以同时连接 psql 和 R。所以恐怕我无法重现你的问题。但是您的代码中有几处看起来很可疑:

路径中只需要一个正斜杠,而不是两个。 (如果您使用反斜杠,则需要两个。)

sslmode 之前需要一个空格,如下所示:

'sslcert=pem.crt', ' ',

不是这个:

'sslcert=pem.crt',

这些更改是否能解决您的问题?

【讨论】:

如果我只是删除所有 SSL 证书并运行上面的代码,这就是错误:Error in postgresqlNewConnection(drv, ...) : RS-DBI driver: (could not connect pep@datadb1 on dbname "test" )。我想我在某处读到 RPostgreSQL 不支持 SSL 连接,所以我可能不得不完全切换库 好的,编辑答案尝试更多的事情。 感谢您在设置过程中遇到的麻烦以及您的耐心等待。我做了你提到的两点,但仍然给出同样的错误。我让几个人检查它以防我遗漏某事,但没有。我正在考虑一种方法来制作一个可重现的示例,但目前我想不出任何方法 我仍然认为您的错误消息中的"(null)" 是一个强烈的信号,您的变量根本没有正确设置。我已经更新了我的测试程序以包含 SSL 证书内容。如果您更改文件名以匹配您自己的文件名,这是否会给您同样的错误? 您说的名称设置不正确是对的。我将它们放在文件夹 c:/db cred 中,当我将它们移动到 c:/users/pep 时,null 问题就解决了。我的错,对不起。但现在的错误是:Error in postgresqlNewConnection(drv, ...) : RS-DBI driver: (could not connect pep@datadb1 on dbname test)

以上是关于如何使用 R 连接到远程 PostgreSQL,需要证书验证的主要内容,如果未能解决你的问题,请参考以下文章

如何连接到谷歌计算引擎上的远程 PostgreSQL 服务器?

R RPostgreSQL 使用 SSL 连接到远程 Postgres 数据库

text 如何允许远程连接到本地开发PostgreSQL服务器?

如何设置远程连接到 postgresql 数据库的 jdbc 连接超时值?

使用 MS Access 和 ODBC 连接到远程 PostgreSQL

使用 Python 通过 SSH 隧道连接到远程 PostgreSQL 数据库