определить соединение в пакете odb c для блестящего приложения - PullRequest
0 голосов
/ 02 марта 2020

Я получаю данные из базы данных MS SQL через odbc backage в Shiny. Я хотел бы избежать повторения этой con функции в каждой реактивной функции и просто запустить ее один раз и использовать. Поэтому я поставил его на серверную функцию, например:

server <- function(input, output, session){
  con <- dbConnect(odbc(),
                   Driver = "MSODBC",
                   Server = "myserver",
                   Database = "mydatabase",
                   UID = "User",
                   PWD = "Pass",
                   encoding = "windows-1252",
                   Port = 1433) 
on.exit(odbc::dbDisconnect(con))


  main <- reactive({

    squery = dbSendQuery(con,"myQuery",stringsAsFactors = FALSE)
    parameterNmaes = dbFetch(squery )

    result= list(parameterNmaes = parameterNmaes)
    return(result)
  })
 } 

Но это не работает, и я получаю следующую ошибку:

Warning: Error in new_result: external pointer is not valid
  82: <Anonymous>     

Путем установки con функция внутри реактивной функции main, все в порядке:

server <- function(input, output, session){

  main <- reactive({
  con <- dbConnect(odbc(),
                       Driver = "MSODBC",
                       Server = "myserver",
                       Database = "mydatabase",
                       UID = "User",
                       PWD = "Pass",
                       encoding = "windows-1252",
                       Port = 1433) 
    on.exit(odbc::dbDisconnect(con))


    squery = dbSendQuery(con,"myQuery",stringsAsFactors = FALSE)
    parameterNmaes = dbFetch(squery )

    result= list(parameterNmaes = parameterNmaes)
    return(result)
  })
 }  

Даже я пытался экспортировать функцию con как результат, чтобы использовать ее в другой реактивной функции, такой как:

result= list(parameterNmaes = parameterNmaes, con = con)
sub1 <- reactive({
con <- main()$con
})

но я получаю ту же ошибку! До сих пор единственным решением было повторение функции con снова и снова во всех реактивных функциях! Любая умная идея предотвратить это бессмысленное повторение соединения с базой данных будет высоко ценится.

1 Ответ

1 голос
/ 03 марта 2020

Если вы запустите это маленькое приложение:

library(shiny)

ui <- fluidPage()

server <- function(input, output, session){
  on.exit(cat("hello"))
}

shinyApp(ui, server)

, вы увидите «hello», напечатанное в консоли R при каждом запуске приложения. Это потому, что Shiny завершил выполнение функции server. Поэтому dbDisconnect выполняется в вашем приложении при каждом запуске приложения.

Я бы попробовал

server <- function(input, output, session){
  con <- dbConnect(odbc(),
                   Driver = "MSODBC",
                   Server = "myserver",
                   Database = "mydatabase",
                   UID = "User",
                   PWD = "Pass",
                   encoding = "windows-1252",
                   Port = 1433) 
  onStop(function() odbc::dbDisconnect(con))

  main <- reactive({
    squery = dbSendQuery(con,"myQuery",stringsAsFactors = FALSE)
    parameterNmaes = dbFetch(squery )
    result= list(parameterNmaes = parameterNmaes)
    return(result)
  })
 } 
...