You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过Shiny将rhandsontable修改内容保存至SQLite数据库?

解决rhandsontable修改内容保存到SQLite数据库的问题

问题背景

尝试通过Shiny将rhandsontable的修改内容保存到SQLite数据库,但点击"Write to DB"按钮后,数据库仅保存NA值,手动添加的"Total"汇总行也未被正确保存。

问题原因

  1. 未转换rhandsontable对象:input$hotable1是rhandsontable组件对象,不是可直接写入数据库的数据框,必须通过hot_to_r()转换为标准数据格式
  2. 错误使用写入模式:原代码用append=TRUE会向表中追加新行,但实际需要覆盖原有的任务数据,而非新增
  3. 未使用处理后的数据集:保存逻辑没有调用已经处理好的数据集,而是直接使用原始输入对象,导致数据未正确读取

修改后的完整代码

1. 创建初始数据库(无需修改)

library(collapse)
library(DBI)
library(shiny)
library(RSQLite)
library(rhandsontable)

# Create sqlite base and connect ----------------------------------------------
db <- dbConnect(RSQLite::SQLite(), "test.sqlite")

task <- c("evaluation", 
          "coordination", 
          "seminars",
          "collaboration")

d <- qTBL(task) |> 
  fmutate(Minutes = as.integer(NA))
numberofrows <- nrow(d)

dbWriteTable(db, "monitoring", d, overwrite = T)
dbDisconnect(db)

2. 修改后的Shiny应用代码

ui = fluidPage(
  rHandsontableOutput("hotable1", width = "100%"),
  actionButton("action", label = "Write to DB"),
  hr()
)

server <- shinyServer(function(input, output, session) {
  
  previous <- reactive({d})
  
  MyChanges <- reactive({
    if(is.null(input$hotable1)){return(previous())}
    else if(!identical(previous(),input$hotable1)){
      mytable <- as.data.frame(hot_to_r(input$hotable1))
      # 只保留原始任务行,避免Total行被误写入
      mytable <- mytable[1:numberofrows,]
      mytable[,2][is.na(mytable[,2])] <- NA
      # 添加Total汇总行用于前端展示
      mytable[numberofrows+1,2] <- sum(mytable[,2],na.rm = T)
      mytable[numberofrows+1,1] <- "Total"
      mytable
    }
  })
  
  output$hotable1 <- renderRHandsontable({rhandsontable(MyChanges())})
  
  data <- eventReactive(input$action, {
    db <- dbConnect(RSQLite::SQLite(), "test.sqlite")
    # 转换rhandsontable输入为数据框,只取原始任务行(不含Total)
    updated_data <- as.data.frame(hot_to_r(input$hotable1))[1:numberofrows,]
    # 覆盖原表保存修改后的数据
    dbWriteTable(db, "monitoring", updated_data, overwrite = TRUE)
    data <- dbReadTable(db, "monitoring")
    dbDisconnect(db)
    return(data)
  })
})

shinyApp(ui = ui, server = server)

验证步骤

点击"Write to DB"按钮后,执行以下代码查看数据库内容:

db <- dbConnect(RSQLite::SQLite(), "test.sqlite")
tbl(db, "monitoring")
dbDisconnect(db)

此时数据库会正确保存修改后的任务分钟数,"Total"汇总行为前端展示用,无需存入数据库。

内容的提问来源于stack exchange,提问作者kokolet

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.13 13:56:06