在R中的函数中断开DBI / RSQLite的连接

时间:2018-07-06 15:49:47

标签: r r-dbi rsqlite

我正在构建一个供内部使用的软件包,并尝试从用户那里提取所有可能的数据库交互。我需要连接到数据库,并从函数内的数据库断开连接(我认为)。但是,断开连接不起作用。

`my_func = function(){
    con = DBI::dbConnect(RSQLite::SQLite(), 'db_location.sqlite')
    r = DBI::dbSendQuery("SELECT * ...")
    dat = DBI::dbFetch(r)
    DBI::dbDisconnect(con)
    return(dat)
}`

如果调用该函数:     MY_LIBRARY::my_func()

返回了数据,但连接没有终止,并显示警告。

`Warning message:
In connection_release(conn@ptr) :
    There are 1 result in use. The connection will be released when 
    they are closed`

1 个答案:

答案 0 :(得分:6)

SQL查询通常是一个三步过程(忽略连接管理):

  1. 发送查询,接受返回的“结果”对象
  2. 使用“结果”对象获取结果
  3. 清除“结果”对象

第三步很重要,因为未清除表示代表该查询的资源。某些数据库连接不允许同时出现多个未清除的结果,一次只能进行一个查询。

这在历史上是通过以下方式完成的:

res <- dbSendQuery(con, "SELECT ...")
dat <- dbFetch(res)
dbClearResult(res)

前段时间(不知道版本),DBI提供了强大的便捷功能,可将所有这三行更改为一行代码:

dat <- dbGetQuery(con, "SELECT ...")

当查询不返回数据时,例如UPDATEINSERT,此功能不适用,在这种情况下,您应该使用dbSendStatement(可选地,后面跟{{1} })或dbGetRowsAffected(会自动调用dbExecute)。

在使用SQL参数化(以减轻sql injection)的情况下发送数据返回查询时,您应该使用dbGetRowsAffected。相反,您将返回使用dbGetQuerydbSendQuery(用于参数),dbBinddbFetch