使用R DBI软件包截断的更新字符串

时间:2018-08-22 10:14:30

标签: r r-dbi

我需要从R更新SQL SERVER上的一个宽表。因此,DBI软件包对此非常有用。 问题是R data.frame包含超过3000个字符的字符串,并且当我使用DBI dbSendQuery函数时,所有字符串都被截断为256个字符。

这里可能是一个代码示例:

con <- odbc::dbConnect(drv = odbc::odbc(),
                   dsn = '***',
                   UID = '***',
                   PWD = '***')
df = data.frame(TEST = paste(rep("A", 300), collapse=""),
            TEST_ID = 1068858)
df$TEST = df$TEST %>% as.character
query = paste0('UPDATE MY_TABLE SET "TEST"=? WHERE TEST_ID=?')
update <- DBI::dbSendQuery(con, query)
DBI::dbBind(update, df) 
DBI::dbClearResult(update) 
odbc::dbDisconnect(con)

然后以下请求返回256而不是300:

SELECT LEN(TEST) FROM MY_TABLE WHERE TEST_ID = 1068858

NB:TEST类型为(varchar(max),NULL),并且已经包含超过256个字符的字符串。

预先感谢您的任何建议

1 个答案:

答案 0 :(得分:0)

最后,我选择摆脱复杂的功能。一种解决方案是将表写入.csv文件,然后将其批量插入数据库中。这是使用RODBC包的示例:

write.table(x = df,
        file = "/path/DBI_error_test.csv",
        sep = ";",
        row.names = FALSE, col.names = FALSE,
        na = "NULL",
        quote = FALSE)

Query = paste("CREATE TABLE #MY_TABLE_TMP (
            TEST varchar(max),
            TEST_ID int 
          );

          BULK INSERT #MY_TABLE_TMP
          FROM 'C:\\DBI_error_test.csv'
          WITH
          (
          FIELDTERMINATOR = ';', 
          ROWTERMINATOR = '\n',
          BATCHSIZE = 500000,
          CHECK_CONSTRAINTS
          )

          UPDATE R
          SET R.TEST = #MY_TABLE_TMP.TEST
          FROM MY_TABLE AS R
          INNER JOIN #MY_TABLE_TMP ON #MY_TABLE_TMP.TEST_ID = R.TEST_ID;

          DROP TABLE #MY_TABLE_TMP; 
          ")

channel <- RODBC::odbcConnect(dsn = .DB_DSN_NAME,
                          uid = .DB_UID, 
                          pwd = .DB_PWD)
RODBC::sqlQuery(channel = channel, query = query, believeNRows = FALSE)
RODBC::odbcClose(channel = channel)