refactoring app
This commit is contained in:
401
app.R
401
app.R
@@ -22,10 +22,17 @@ config <- config::get(file = "configs/config.yml")
|
|||||||
|
|
||||||
folder_with_schemas <- fs::path("configs/schemas")
|
folder_with_schemas <- fs::path("configs/schemas")
|
||||||
FILE_SCHEME <- fs::path(folder_with_schemas, "main.xlsx")
|
FILE_SCHEME <- fs::path(folder_with_schemas, "main.xlsx")
|
||||||
dbfile <- fs::path("data.sqlite")
|
# dbfile <- fs::path("data.sqlite")
|
||||||
|
|
||||||
|
# options(box.path = getwd())
|
||||||
|
box::purge_cache()
|
||||||
|
box::use(
|
||||||
|
modules/utils,
|
||||||
|
modules/global_options,
|
||||||
|
modules/db
|
||||||
|
)
|
||||||
|
|
||||||
# SETTINGS ================================
|
# SETTINGS ================================
|
||||||
DEBUG <- FALSE
|
|
||||||
AUTH_ENABLED <- config$auth_module
|
AUTH_ENABLED <- config$auth_module
|
||||||
|
|
||||||
# CHECK FOR PANDOC
|
# CHECK FOR PANDOC
|
||||||
@@ -35,6 +42,7 @@ rmarkdown::find_pandoc(dir = "/opt/homebrew/bin/")
|
|||||||
# TODO: dynamic button render depend on pandoc installation
|
# TODO: dynamic button render depend on pandoc installation
|
||||||
if (!rmarkdown::pandoc_available()) warning("Can't find pandoc!")
|
if (!rmarkdown::pandoc_available()) warning("Can't find pandoc!")
|
||||||
|
|
||||||
|
|
||||||
# SCHEME_MAIN UNPACK ==========================
|
# SCHEME_MAIN UNPACK ==========================
|
||||||
# load scheme
|
# load scheme
|
||||||
SCHEME_MAIN <- readxl::read_xlsx(FILE_SCHEME) %>%
|
SCHEME_MAIN <- readxl::read_xlsx(FILE_SCHEME) %>%
|
||||||
@@ -58,25 +66,25 @@ inputs_tables_list <- SCHEME_MAIN %>%
|
|||||||
|
|
||||||
|
|
||||||
# SETUP DB ==========================
|
# SETUP DB ==========================
|
||||||
#' @description Function to open connection to db, disigned to easy dubugging.
|
# #' @description Function to open connection to db, disigned to easy dubugging.
|
||||||
make_db_connection <- function(where = "") {
|
# make_db_connection <- function(where = "") {
|
||||||
if (DEBUG) message("=== DB CONNECT ", where)
|
# if (DEBUG) message("=== DB CONNECT ", where)
|
||||||
DBI::dbConnect(RSQLite::SQLite(), dbfile)
|
# DBI::dbConnect(RSQLite::SQLite(), dbfile)
|
||||||
}
|
# }
|
||||||
|
|
||||||
#' @description Function to close connection to db, disigned to easy dubugging and
|
# #' @description Function to close connection to db, disigned to easy dubugging and
|
||||||
#' hide warnings.
|
# #' hide warnings.
|
||||||
close_db_connection <- function(con, where = "") {
|
# close_db_connection <- function(con, where = "") {
|
||||||
tryCatch(
|
# tryCatch(
|
||||||
expr = DBI::dbDisconnect(con),
|
# expr = DBI::dbDisconnect(con),
|
||||||
error = function(e) print(e),
|
# error = function(e) print(e),
|
||||||
warning = function(w) if (DEBUG) message("=!= ALREADY DISCONNECTED ", where),
|
# warning = function(w) if (DEBUG) message("=!= ALREADY DISCONNECTED ", where),
|
||||||
finally = if (DEBUG) message("=/= DB DISCONNECT ", where)
|
# finally = if (DEBUG) message("=/= DB DISCONNECT ", where)
|
||||||
)
|
# )
|
||||||
}
|
# }
|
||||||
|
|
||||||
# establish connection
|
# establish connection
|
||||||
con <- make_db_connection()
|
con <- db$make_db_connection()
|
||||||
|
|
||||||
# init DB (write dummy data to "main" table)
|
# init DB (write dummy data to "main" table)
|
||||||
if (!"main" %in% DBI::dbListTables(con)) {
|
if (!"main" %in% DBI::dbListTables(con)) {
|
||||||
@@ -117,7 +125,7 @@ if (identical(colnames(DBI::dbReadTable(con, "main")), names(inputs_simple_list)
|
|||||||
# add empty data for each new input form
|
# add empty data for each new input form
|
||||||
for (i in form_base_difference) {
|
for (i in form_base_difference) {
|
||||||
df_to_rewrite <- df_to_rewrite %>%
|
df_to_rewrite <- df_to_rewrite %>%
|
||||||
dplyr::mutate(!!dplyr::sym(i) := get_empty_data(inputs_simple_list[i]))
|
dplyr::mutate(!!dplyr::sym(i) := utils$get_empty_data(inputs_simple_list[i]))
|
||||||
}
|
}
|
||||||
|
|
||||||
# reorder due to scheme
|
# reorder due to scheme
|
||||||
@@ -136,7 +144,7 @@ if (identical(colnames(DBI::dbReadTable(con, "main")), names(inputs_simple_list)
|
|||||||
}
|
}
|
||||||
|
|
||||||
# close connection to prevent data loss
|
# close connection to prevent data loss
|
||||||
close_db_connection(con)
|
db$close_db_connection(con)
|
||||||
|
|
||||||
|
|
||||||
# INLINE TABLES =====================
|
# INLINE TABLES =====================
|
||||||
@@ -144,6 +152,7 @@ close_db_connection(con)
|
|||||||
inline_tables <- purrr::map(
|
inline_tables <- purrr::map(
|
||||||
.x = purrr::set_names(inputs_tables_list),
|
.x = purrr::set_names(inputs_tables_list),
|
||||||
.f = \(x_inline_table_name) {
|
.f = \(x_inline_table_name) {
|
||||||
|
|
||||||
# получить имя файла со схемой
|
# получить имя файла со схемой
|
||||||
file_name <- SCHEME_MAIN %>%
|
file_name <- SCHEME_MAIN %>%
|
||||||
dplyr::filter(form_id == x_inline_table_name) %>%
|
dplyr::filter(form_id == x_inline_table_name) %>%
|
||||||
@@ -172,165 +181,184 @@ inline_tables <- purrr::map(
|
|||||||
|
|
||||||
# создание объектов для ввода
|
# создание объектов для ввода
|
||||||
# функция
|
# функция
|
||||||
create_forms <- function(form_id, form_label, form_type) {
|
# create_forms <- function(form_id, form_label, form_type) {
|
||||||
# check if have condition
|
# # check if have condition
|
||||||
condition <- dplyr::filter(SCHEME_MAIN, form_id == {{ form_id }}) %>%
|
# condition <- dplyr::filter(SCHEME_MAIN, form_id == {{ form_id }}) %>%
|
||||||
dplyr::distinct(condition) %>%
|
# dplyr::distinct(condition) %>%
|
||||||
dplyr::pull()
|
# dplyr::pull()
|
||||||
|
|
||||||
choices <- dplyr::filter(SCHEME_MAIN, form_id == {{ form_id }}) %>%
|
# choices <- dplyr::filter(SCHEME_MAIN, form_id == {{ form_id }}) %>%
|
||||||
dplyr::pull(choices)
|
# dplyr::pull(choices)
|
||||||
|
|
||||||
# simple text or number input
|
# # simple text or number input
|
||||||
if (form_type %in% c("text", "number")) {
|
# if (form_type %in% c("text", "number")) {
|
||||||
form <- shiny::textAreaInput(
|
# form <- shiny::textAreaInput(
|
||||||
inputId = form_id,
|
# inputId = form_id,
|
||||||
label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
|
||||||
rows = 1
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
# simple date input
|
|
||||||
if (form_type == "date") {
|
|
||||||
# supress warning while trying keep data form empty by default
|
|
||||||
suppressWarnings({
|
|
||||||
form <- dateInput(
|
|
||||||
inputId = form_id,
|
|
||||||
label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
|
||||||
value = NA, # keep empty
|
|
||||||
format = "dd.mm.yyyy",
|
|
||||||
weekstart = 1,
|
|
||||||
language = "ru"
|
|
||||||
)
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
# еденичный выбор
|
|
||||||
if (form_type == "select_one") {
|
|
||||||
form <- selectizeInput(
|
|
||||||
inputId = form_id,
|
|
||||||
label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
|
||||||
choices = choices,
|
|
||||||
selected = NULL,
|
|
||||||
options = list(
|
|
||||||
create = FALSE,
|
|
||||||
onInitialize = I('function() { this.setValue(""); }')
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
# множественный выбор
|
|
||||||
if (form_type == "select_multiple") {
|
|
||||||
form <- selectizeInput(
|
|
||||||
inputId = form_id,
|
|
||||||
label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
|
||||||
choices = choices,
|
|
||||||
selected = NULL,
|
|
||||||
multiple = TRUE,
|
|
||||||
options = list(
|
|
||||||
create = FALSE,
|
|
||||||
onInitialize = I('function() { this.setValue(""); }')
|
|
||||||
)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
# множественный выбор
|
|
||||||
if (form_type == "radio") {
|
|
||||||
form <- radioButtons(
|
|
||||||
inputId = form_id,
|
|
||||||
label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
|
||||||
choices = choices,
|
|
||||||
selected = character(0)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
if (form_type == "checkbox") {
|
|
||||||
form <- checkboxGroupInput(
|
|
||||||
inputId = form_id,
|
|
||||||
# label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
# label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
label = h6(form_label),
|
# rows = 1
|
||||||
choices = choices,
|
# )
|
||||||
selected = character(0)
|
# }
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
# вложенная таблица
|
# # simple date input
|
||||||
if (form_type == "inline_table") {
|
# if (form_type == "date") {
|
||||||
form <- rHandsontableOutput(outputId = form_id)
|
# # supress warning while trying keep data form empty by default
|
||||||
}
|
# suppressWarnings({
|
||||||
|
# form <- dateInput(
|
||||||
|
# inputId = form_id,
|
||||||
|
# label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
# value = NA, # keep empty
|
||||||
|
# format = "dd.mm.yyyy",
|
||||||
|
# weekstart = 1,
|
||||||
|
# language = "ru"
|
||||||
|
# )
|
||||||
|
# })
|
||||||
|
# }
|
||||||
|
|
||||||
# description part
|
# # еденичный выбор
|
||||||
if (form_type == "description") {
|
# if (form_type == "select_one") {
|
||||||
form <- div(HTML(form_label), style = "color:Gray;font-size: 90%;")
|
# form <- selectizeInput(
|
||||||
}
|
# inputId = form_id,
|
||||||
|
# label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
# choices = choices,
|
||||||
|
# selected = NULL,
|
||||||
|
# options = list(
|
||||||
|
# create = FALSE,
|
||||||
|
# onInitialize = I('function() { this.setValue(""); }')
|
||||||
|
# )
|
||||||
|
# )
|
||||||
|
# }
|
||||||
|
|
||||||
# если есть условие создать кондитионал панель
|
# # множественный выбор
|
||||||
if (!is.na(condition)) {
|
# if (form_type == "select_multiple") {
|
||||||
form <- conditionalPanel(
|
# form <- selectizeInput(
|
||||||
condition = condition,
|
# inputId = form_id,
|
||||||
form
|
# label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
)
|
# choices = choices,
|
||||||
}
|
# selected = NULL,
|
||||||
|
# multiple = TRUE,
|
||||||
|
# options = list(
|
||||||
|
# create = FALSE,
|
||||||
|
# onInitialize = I('function() { this.setValue(""); }')
|
||||||
|
# )
|
||||||
|
# )
|
||||||
|
# }
|
||||||
|
|
||||||
form
|
# # множественный выбор
|
||||||
}
|
# if (form_type == "radio") {
|
||||||
|
# form <- radioButtons(
|
||||||
|
# inputId = form_id,
|
||||||
|
# label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
# choices = choices,
|
||||||
|
# selected = character(0)
|
||||||
|
# )
|
||||||
|
# }
|
||||||
|
|
||||||
|
# if (form_type == "checkbox") {
|
||||||
|
# form <- checkboxGroupInput(
|
||||||
|
# inputId = form_id,
|
||||||
|
# # label = tags$span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
# label = h6(form_label),
|
||||||
|
# choices = choices,
|
||||||
|
# selected = character(0)
|
||||||
|
# )
|
||||||
|
# }
|
||||||
|
|
||||||
|
# # вложенная таблица
|
||||||
|
# if (form_type == "inline_table") {
|
||||||
|
# form <- rHandsontableOutput(outputId = form_id)
|
||||||
|
# }
|
||||||
|
|
||||||
|
# # description part
|
||||||
|
# if (form_type == "description") {
|
||||||
|
# form <- div(HTML(form_label), style = "color:Gray;font-size: 90%;")
|
||||||
|
# }
|
||||||
|
|
||||||
|
# # если есть условие создать кондитионал панель
|
||||||
|
# if (!is.na(condition)) {
|
||||||
|
# form <- conditionalPanel(
|
||||||
|
# condition = condition,
|
||||||
|
# form
|
||||||
|
# )
|
||||||
|
# }
|
||||||
|
|
||||||
|
# form
|
||||||
|
# }
|
||||||
|
|
||||||
# GENERATE UI ==================================
|
# GENERATE UI ==================================
|
||||||
# functions for making cards
|
# functions for making cards
|
||||||
make_cards_fn <- function(sub_group) {
|
# make_cards_fn <- function(sub_group) {
|
||||||
subgroups_inputs <- df_forms %>%
|
|
||||||
dplyr::filter(subgroup == {{ sub_group }}) %>%
|
|
||||||
dplyr::distinct(form_id, form_label, form_type)
|
|
||||||
|
|
||||||
bslib::card(
|
# subgroups_inputs <- df_forms %>%
|
||||||
bslib::card_header(sub_group, container = htmltools::h5),
|
# dplyr::filter(subgroup == {{sub_group}}) %>%
|
||||||
full_screen = TRUE,
|
# dplyr::distinct(form_id, form_label, form_type)
|
||||||
width = "4000px",
|
|
||||||
bslib::card_body(
|
# subgroups_inputs2 <- SCHEME_MAIN |>
|
||||||
fill = TRUE,
|
# dplyr::filter(subgroup == {{sub_group}}) %>%
|
||||||
# передаем все аргументы в функцию для создания елементов
|
# dplyr::distinct(form_id, form_label, form_type, condition)
|
||||||
purrr::pmap(subgroups_inputs, create_forms)
|
|
||||||
)
|
# print(subgroups_inputs2)
|
||||||
)
|
|
||||||
}
|
# bslib::card(
|
||||||
|
# bslib::card_header(sub_group, container = htmltools::h5),
|
||||||
|
# full_screen = TRUE,
|
||||||
|
# width = "4000px",
|
||||||
|
# bslib::card_body(
|
||||||
|
# fill = TRUE,
|
||||||
|
# # передаем все аргументы в функцию для создания елементов
|
||||||
|
# purrr::pmap(
|
||||||
|
# .l = subgroups_inputs,
|
||||||
|
# .f = utils$create_forms,
|
||||||
|
# scheme = SCHEME_MAIN
|
||||||
|
# )
|
||||||
|
# )
|
||||||
|
# )
|
||||||
|
# }
|
||||||
|
|
||||||
# get pages list
|
# get pages list
|
||||||
pages_list <- unique(SCHEME_MAIN$part)
|
pages_list <- unique(SCHEME_MAIN$part)
|
||||||
|
|
||||||
# get all forms df
|
# # get all forms df
|
||||||
df_forms <- SCHEME_MAIN %>%
|
# df_forms <- SCHEME_MAIN %>%
|
||||||
dplyr::distinct(part, subgroup, form_id, form_label, form_type)
|
# dplyr::distinct(part, subgroup, form_id, form_label, form_type)
|
||||||
|
|
||||||
# generate nav panels
|
# generate nav panels for each page
|
||||||
nav_panels_list <- purrr::map(
|
nav_panels_list <- purrr::map(
|
||||||
.x = pages_list,
|
.x = pages_list,
|
||||||
.f = \(x_page) {
|
.f = utils$make_panels,
|
||||||
# get info about inputs for current page
|
main_scheme = SCHEME_MAIN
|
||||||
page_forms <- SCHEME_MAIN %>%
|
|
||||||
dplyr::filter(part == {{ x_page }}) %>%
|
|
||||||
dplyr::distinct(subgroup, form_id, form_label, form_type)
|
|
||||||
|
|
||||||
# get list of columns
|
|
||||||
cols_list <- unique(page_forms$subgroup)
|
|
||||||
|
|
||||||
# making cards
|
|
||||||
cards <- purrr::map(
|
|
||||||
.x = cols_list,
|
|
||||||
.f = make_cards_fn
|
|
||||||
)
|
)
|
||||||
|
|
||||||
# make page wrap
|
# nav_panels_list <- purrr::map(
|
||||||
page_wrap <- bslib::layout_column_wrap(
|
# .x = pages_list,
|
||||||
# width = "350px", height = NULL, #was 800
|
# .f = \(x_page) {
|
||||||
width = 1 / 4, height = NULL, # was 800
|
|
||||||
fixed_width = TRUE,
|
|
||||||
!!!cards # unpack list of cards
|
|
||||||
)
|
|
||||||
|
|
||||||
# add panel wrap to nav_panel
|
# # get info about inputs for current page
|
||||||
bslib::nav_panel(x_page, page_wrap)
|
# page_forms <- SCHEME_MAIN %>%
|
||||||
}
|
# dplyr::filter(part == {{x_page}}) %>%
|
||||||
)
|
# dplyr::distinct(subgroup, form_id, form_label, form_type)
|
||||||
|
|
||||||
|
# # get list of columns
|
||||||
|
# cols_list <- unique(page_forms$subgroup)
|
||||||
|
|
||||||
|
# # making cards
|
||||||
|
# cards <- purrr::map(
|
||||||
|
# .x = cols_list,
|
||||||
|
# .f = utils$make_cards_fn,
|
||||||
|
# main_scheme = SCHEME_MAIN
|
||||||
|
# )
|
||||||
|
|
||||||
|
# # make page wrap
|
||||||
|
# page_wrap <- bslib::layout_column_wrap(
|
||||||
|
# # width = "350px", height = NULL, #was 800
|
||||||
|
# width = 1 / 4, height = NULL, # was 800
|
||||||
|
# fixed_width = TRUE,
|
||||||
|
# !!!cards # unpack list of cards
|
||||||
|
# )
|
||||||
|
|
||||||
|
# # add panel wrap to nav_panel
|
||||||
|
# bslib::nav_panel(x_page, page_wrap)
|
||||||
|
# }
|
||||||
|
# )
|
||||||
|
|
||||||
# UI =======================
|
# UI =======================
|
||||||
ui <- page_sidebar(
|
ui <- page_sidebar(
|
||||||
@@ -413,6 +441,7 @@ server <- function(input, output) {
|
|||||||
values <- reactiveValues(data = NULL)
|
values <- reactiveValues(data = NULL)
|
||||||
rhand_tables <- reactiveValues()
|
rhand_tables <- reactiveValues()
|
||||||
|
|
||||||
|
|
||||||
# VALIDATIONS ============================
|
# VALIDATIONS ============================
|
||||||
# create new validator
|
# create new validator
|
||||||
iv <- shinyvalidate::InputValidator$new()
|
iv <- shinyvalidate::InputValidator$new()
|
||||||
@@ -422,10 +451,13 @@ server <- function(input, output) {
|
|||||||
.x = names(inputs_simple_list),
|
.x = names(inputs_simple_list),
|
||||||
.f = \(x_input_id) {
|
.f = \(x_input_id) {
|
||||||
form_type <- inputs_simple_list[[x_input_id]]
|
form_type <- inputs_simple_list[[x_input_id]]
|
||||||
choices <- filter(SCHEME_MAIN, form_id == {{ x_input_id }}) %>% pull(choices)
|
|
||||||
val_required <- filter(SCHEME_MAIN, form_id == {{ x_input_id }}) %>%
|
choices <- dplyr::filter(SCHEME_MAIN, form_id == {{x_input_id}}) %>%
|
||||||
distinct(required) %>%
|
dplyr::pull(choices)
|
||||||
pull(required)
|
|
||||||
|
val_required <- dplyr::filter(SCHEME_MAIN, form_id == {{x_input_id}}) %>%
|
||||||
|
dplyr::distinct(required) %>%
|
||||||
|
dplyr::pull(required)
|
||||||
|
|
||||||
# for `number` type: if in `choices` column has values then parsing them to range validation
|
# for `number` type: if in `choices` column has values then parsing them to range validation
|
||||||
# value `0; 250` -> transform to rule validation value from 0 to 250
|
# value `0; 250` -> transform to rule validation value from 0 to 250
|
||||||
@@ -518,13 +550,17 @@ server <- function(input, output) {
|
|||||||
rownames(rhand_tables[[x]]) <- NULL
|
rownames(rhand_tables[[x]]) <- NULL
|
||||||
|
|
||||||
# создать объект рандсонтебл
|
# создать объект рандсонтебл
|
||||||
rh_tabel <- rhandsontable(
|
rh_tabel <- rhandsontable::rhandsontable(
|
||||||
rhand_tables[[x]],
|
rhand_tables[[x]],
|
||||||
colHeaders = headers,
|
colHeaders = headers,
|
||||||
rowHeaders = NULL,
|
rowHeaders = NULL,
|
||||||
height = 400,
|
height = 400,
|
||||||
) %>%
|
) %>%
|
||||||
hot_cols(colWidths = 120, manualColumnResize = TRUE, columnSorting = TRUE)
|
rhandsontable::hot_cols(
|
||||||
|
colWidths = 120,
|
||||||
|
manualColumnResize = TRUE,
|
||||||
|
columnSorting = TRUE
|
||||||
|
)
|
||||||
|
|
||||||
# циклом итерируемся по индексу;
|
# циклом итерируемся по индексу;
|
||||||
for (i in seq(1, length(schema_comp$form_id))) {
|
for (i in seq(1, length(schema_comp$form_id))) {
|
||||||
@@ -564,6 +600,7 @@ server <- function(input, output) {
|
|||||||
)
|
)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
||||||
# BUTTONS LOGIC ======================
|
# BUTTONS LOGIC ======================
|
||||||
## clear all inputs ==================
|
## clear all inputs ==================
|
||||||
# show modal on click of button
|
# show modal on click of button
|
||||||
@@ -579,10 +616,10 @@ server <- function(input, output) {
|
|||||||
.y = names(inputs_simple_list),
|
.y = names(inputs_simple_list),
|
||||||
.f = \(x_type, x_id) {
|
.f = \(x_type, x_id) {
|
||||||
# using function to update forms
|
# using function to update forms
|
||||||
update_forms_with_data(
|
utils$update_forms_with_data(
|
||||||
id = x_id,
|
id = x_id,
|
||||||
type = x_type,
|
type = x_type,
|
||||||
value = get_empty_data(x_type)
|
value = utils$get_empty_data(x_type)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
@@ -603,8 +640,8 @@ server <- function(input, output) {
|
|||||||
# сохранить простые данные;
|
# сохранить простые данные;
|
||||||
observeEvent(input$save_data_button, {
|
observeEvent(input$save_data_button, {
|
||||||
req(input$id)
|
req(input$id)
|
||||||
con <- make_db_connection("save_data_button")
|
con <- db$make_db_connection("save_data_button")
|
||||||
on.exit(close_db_connection(con, "save_data_button"), add = TRUE)
|
on.exit(db$close_db_connection(con, "save_data_button"), add = TRUE)
|
||||||
|
|
||||||
## MAIN
|
## MAIN
|
||||||
# собрать все значения по введенным данным;
|
# собрать все значения по введенным данным;
|
||||||
@@ -615,14 +652,14 @@ server <- function(input, output) {
|
|||||||
|
|
||||||
# return empty if 0 element
|
# return empty if 0 element
|
||||||
if (length(input_d) == 0) {
|
if (length(input_d) == 0) {
|
||||||
return(get_empty_data(inputs_simple_list[[x]]))
|
return(utils$get_empty_data(inputs_simple_list[[x]]))
|
||||||
}
|
}
|
||||||
# return element if there one
|
# return element if there one
|
||||||
if (length(input_d) == 1) {
|
if (length(input_d) == 1) {
|
||||||
return(input_d)
|
return(input_d)
|
||||||
}
|
}
|
||||||
# если елементов больше одного - объединять через ";"
|
# если елементов больше одного - объединять через ";"
|
||||||
if (length(input_d) > 1) paste(input_d, collapse = "; ")
|
if (length(input_d) > 1) paste(input_d, collapse = getOption("SYMBOL_DELIM"))
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -660,8 +697,8 @@ server <- function(input, output) {
|
|||||||
|
|
||||||
## get list of id's from db =====================
|
## get list of id's from db =====================
|
||||||
observeEvent(input$load_data_button, {
|
observeEvent(input$load_data_button, {
|
||||||
con <- make_db_connection("load_data_button")
|
con <- db$make_db_connection("load_data_button")
|
||||||
on.exit(close_db_connection(con, "load_data_button"))
|
on.exit(db$close_db_connection(con, "load_data_button"))
|
||||||
|
|
||||||
if (length(dbListTables(con)) != 0 && "main" %in% DBI::dbListTables(con)) {
|
if (length(dbListTables(con)) != 0 && "main" %in% DBI::dbListTables(con)) {
|
||||||
# GET DATA files
|
# GET DATA files
|
||||||
@@ -691,8 +728,8 @@ server <- function(input, output) {
|
|||||||
|
|
||||||
## load data to input forms ==================================
|
## load data to input forms ==================================
|
||||||
observeEvent(input$read_data, {
|
observeEvent(input$read_data, {
|
||||||
con <- make_db_connection("read_data")
|
con <- db$make_db_connection("read_data")
|
||||||
on.exit(close_db_connection(con, "read_data"), add = TRUE)
|
on.exit(db$close_db_connection(con, "read_data"), add = TRUE)
|
||||||
|
|
||||||
# main df read
|
# main df read
|
||||||
test_read_df <- read_df_from_db_by_id("main", con)
|
test_read_df <- read_df_from_db_by_id("main", con)
|
||||||
@@ -705,14 +742,14 @@ server <- function(input, output) {
|
|||||||
.x = inputs_simple_list,
|
.x = inputs_simple_list,
|
||||||
.y = names(inputs_simple_list),
|
.y = names(inputs_simple_list),
|
||||||
.f = \(x_type, x_id) {
|
.f = \(x_type, x_id) {
|
||||||
if (DEBUG) {
|
if (getOption("APP.DEBUG")) {
|
||||||
values_load <- test_read_df[[x_id]]
|
values_load <- test_read_df[[x_id]]
|
||||||
print(paste(x_type, x_id, values_load, sep = " || "))
|
print(paste(x_type, x_id, values_load, sep = " || "))
|
||||||
print(is.na(values_load))
|
print(is.na(values_load))
|
||||||
}
|
}
|
||||||
|
|
||||||
# using function to update forms
|
# updating forms with loaded data
|
||||||
update_forms_with_data(
|
utils$update_forms_with_data(
|
||||||
id = x_id,
|
id = x_id,
|
||||||
type = x_type,
|
type = x_type,
|
||||||
value = test_read_df[[x_id]]
|
value = test_read_df[[x_id]]
|
||||||
@@ -744,8 +781,8 @@ server <- function(input, output) {
|
|||||||
output$downloadData <- downloadHandler(
|
output$downloadData <- downloadHandler(
|
||||||
filename = paste0("d2tra_", format(Sys.time(), "%Y%m%d_%H%M%S"), ".xlsx"),
|
filename = paste0("d2tra_", format(Sys.time(), "%Y%m%d_%H%M%S"), ".xlsx"),
|
||||||
content = function(file) {
|
content = function(file) {
|
||||||
con <- make_db_connection("downloadData")
|
con <- db$make_db_connection("downloadData")
|
||||||
on.exit(close_db_connection(con, "downloadData"), add = TRUE)
|
on.exit(db$close_db_connection(con, "downloadData"), add = TRUE)
|
||||||
|
|
||||||
# get all data
|
# get all data
|
||||||
list_of_df <- purrr::map(
|
list_of_df <- purrr::map(
|
||||||
@@ -875,8 +912,8 @@ server <- function(input, output) {
|
|||||||
|
|
||||||
## trigger saving function =============
|
## trigger saving function =============
|
||||||
observeEvent(input$data_save, {
|
observeEvent(input$data_save, {
|
||||||
con <- make_db_connection("saving data (from modal conf)")
|
con <- db$make_db_connection("saving data (from modal conf)")
|
||||||
on.exit(close_db_connection(con, "saving data (from modal conf)"), add = TRUE)
|
on.exit(db$close_db_connection(con, "saving data (from modal conf)"), add = TRUE)
|
||||||
|
|
||||||
# убираем плашку
|
# убираем плашку
|
||||||
removeModal()
|
removeModal()
|
||||||
@@ -895,7 +932,7 @@ server <- function(input, output) {
|
|||||||
# FUNCTIONS ==============================
|
# FUNCTIONS ==============================
|
||||||
## write all inputs to db ================
|
## write all inputs to db ================
|
||||||
write_all_to_db <- function() {
|
write_all_to_db <- function() {
|
||||||
con <- make_db_connection("fn call `write_all_to_db()`")
|
con <- db$make_db_connection("fn call `write_all_to_db()`")
|
||||||
# on.exit(close_db_connection("fn call `write_all_to_db()`"), add = TRUE)
|
# on.exit(close_db_connection("fn call `write_all_to_db()`"), add = TRUE)
|
||||||
|
|
||||||
# write main
|
# write main
|
||||||
|
|||||||
57
helpers/db.R
57
helpers/db.R
@@ -1,57 +0,0 @@
|
|||||||
# based on https://github.com/datastorm-open/shinymanager/
|
|
||||||
|
|
||||||
|
|
||||||
#' @export
|
|
||||||
write_db_encrypt <- function(conn, value, name, passphrase = Sys.getenv("AUTH_DB_KEY")) {
|
|
||||||
if (is.character(conn)) {
|
|
||||||
conn <- DBI::dbConnect(RSQLite::SQLite(), dbname = conn)
|
|
||||||
on.exit(DBI::dbDisconnect(conn))
|
|
||||||
}
|
|
||||||
|
|
||||||
if (name == "credentials" && "password" %in% colnames(value)) {
|
|
||||||
if (!"is_hashed_password" %in% colnames(value)) {
|
|
||||||
value$is_hashed_password <- FALSE
|
|
||||||
}
|
|
||||||
to_hash <- which(!as.logical(value$is_hashed_password))
|
|
||||||
if (length(to_hash) > 0) {
|
|
||||||
# store hashed password
|
|
||||||
value$password[to_hash] <- sapply(value$password[to_hash], function(x) scrypt::hashPassword(x))
|
|
||||||
value$is_hashed_password[to_hash] <- TRUE
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!is.null(passphrase)) {
|
|
||||||
passphrase <- as.character(passphrase)
|
|
||||||
passphrase <- charToRaw(passphrase)
|
|
||||||
key <- openssl::sha256(passphrase)
|
|
||||||
value_serialized <- serialize(value, NULL)
|
|
||||||
value_encrypted <- openssl::aes_cbc_encrypt(data = value_serialized, key = key)
|
|
||||||
value <- data.frame(value = I(list(value_encrypted)), iv = I(list(attr(value_encrypted, "iv"))))
|
|
||||||
}
|
|
||||||
|
|
||||||
DBI::dbWriteTable(conn = conn, name = name, value = value, overwrite = TRUE)
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
#' @export
|
|
||||||
read_db_encrypt <- function(conn, name, passphrase = Sys.getenv("AUTH_DB_KEY")) {
|
|
||||||
|
|
||||||
if (is.character(conn)) {
|
|
||||||
conn <- DBI::dbConnect(RSQLite::SQLite(), dbname = conn)
|
|
||||||
on.exit(DBI::dbDisconnect(conn))
|
|
||||||
}
|
|
||||||
|
|
||||||
out <- DBI::dbReadTable(conn = conn, name = name)
|
|
||||||
|
|
||||||
if (!is.null(passphrase)) {
|
|
||||||
passphrase <- as.character(passphrase)
|
|
||||||
passphrase <- charToRaw(passphrase)
|
|
||||||
key <- openssl::sha256(passphrase)
|
|
||||||
value <- out$value[[1]]
|
|
||||||
attr(value, "iv") <- out$iv[[1]]
|
|
||||||
out <- openssl::aes_cbc_decrypt(value, key = key)
|
|
||||||
out <- unserialize(out)
|
|
||||||
}
|
|
||||||
|
|
||||||
return(out)
|
|
||||||
}
|
|
||||||
@@ -6,12 +6,12 @@ get_dummy_data <- function(type) {
|
|||||||
if (type %in% c("number")) return(as.double(999))
|
if (type %in% c("number")) return(as.double(999))
|
||||||
}
|
}
|
||||||
|
|
||||||
get_empty_data <- function(type) {
|
# get_empty_data <- function(type) {
|
||||||
if (type %in% c("text", "select_one", "select_multiple")) return(as.character(NA))
|
# if (type %in% c("text", "select_one", "select_multiple")) return(as.character(NA))
|
||||||
if (type %in% c("radio", "checkbox")) return(as.character(NA))
|
# if (type %in% c("radio", "checkbox")) return(as.character(NA))
|
||||||
if (type %in% c("date")) return(as.Date(NA))
|
# if (type %in% c("date")) return(as.Date(NA))
|
||||||
if (type %in% c("number")) return(as.character(NA))
|
# if (type %in% c("number")) return(as.character(NA))
|
||||||
}
|
# }
|
||||||
|
|
||||||
get_dummy_df <- function() {
|
get_dummy_df <- function() {
|
||||||
purrr::map(
|
purrr::map(
|
||||||
@@ -45,62 +45,3 @@ check_for_empty_data <- function(value_to_check) {
|
|||||||
|
|
||||||
FALSE
|
FALSE
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
#' @description Function update input forms.
|
|
||||||
#' @param id - input form id;
|
|
||||||
#' @param type - type of form;
|
|
||||||
#' @param value - value to update;
|
|
||||||
update_forms_with_data <- function(id, type, value) {
|
|
||||||
if (type == "text") {
|
|
||||||
shiny::updateTextAreaInput(inputId = id, value = value)
|
|
||||||
}
|
|
||||||
|
|
||||||
if (type == "number") {
|
|
||||||
shiny::updateTextAreaInput(inputId = id, value = value)
|
|
||||||
}
|
|
||||||
|
|
||||||
# supress warnings when applying NA or NULL to date input form
|
|
||||||
if (type == "date") {
|
|
||||||
suppressWarnings(
|
|
||||||
shiny::updateDateInput(inputId = id, value = value)
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
# select_one
|
|
||||||
if (type == "select_one") {
|
|
||||||
shiny::updateSelectizeInput(inputId = id, selected = value)
|
|
||||||
}
|
|
||||||
|
|
||||||
# select_multiple
|
|
||||||
# check if value is not NA and split by delimetr
|
|
||||||
if (type == "select_multiple" && !is.na(value)) {
|
|
||||||
vars <- stringr::str_split_1(value, "; ")
|
|
||||||
shiny::updateSelectizeInput(inputId = id, selected = vars)
|
|
||||||
}
|
|
||||||
# in other case fill with `character(0)` to proper reseting form
|
|
||||||
if (type == "select_multiple" && is.na(value)) {
|
|
||||||
shiny::updateSelectizeInput(inputId = id, selected = character(0))
|
|
||||||
}
|
|
||||||
|
|
||||||
# radio buttons
|
|
||||||
if (type == "radio" && !is.na(value)) {
|
|
||||||
shiny::updateRadioButtons(inputId = id, selected = value)
|
|
||||||
}
|
|
||||||
if (type == "radio" && is.na(value)) {
|
|
||||||
shiny::updateRadioButtons(inputId = id, selected = character(0))
|
|
||||||
}
|
|
||||||
|
|
||||||
# checkboxes
|
|
||||||
if (type == "checkbox" && !is.na(value)) {
|
|
||||||
vars <- stringr::str_split_1(value, "; ")
|
|
||||||
shiny::updateCheckboxGroupInput(inputId = id, selected = vars)
|
|
||||||
}
|
|
||||||
if (type == "checkbox" && is.na(value)) {
|
|
||||||
shiny::updateCheckboxGroupInput(inputId = id, selected = character(0))
|
|
||||||
}
|
|
||||||
|
|
||||||
if (type == "inline_table") {
|
|
||||||
message("EMPTY")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
29
modules/db.R
Normal file
29
modules/db.R
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
# box ========
|
||||||
|
.on_load = function(ns) {
|
||||||
|
message(
|
||||||
|
'Loading module "', box::name(), '"\n',
|
||||||
|
'Module path: "', basename(box::file()), '"'
|
||||||
|
)
|
||||||
|
}
|
||||||
|
# ================
|
||||||
|
|
||||||
|
# DB RELATED ===========================
|
||||||
|
#' @export
|
||||||
|
#' @description Function to open connection to db, disigned to easy dubugging.
|
||||||
|
#' @param where text mark to distingiush calss
|
||||||
|
make_db_connection <- function(where = "") {
|
||||||
|
if (getOption("APP.DEBUG", FALSE)) message("=== DB CONNECT ", where)
|
||||||
|
DBI::dbConnect(RSQLite::SQLite(), getOption("APP.FILE_DB", FALSE))
|
||||||
|
}
|
||||||
|
|
||||||
|
#' @export
|
||||||
|
#' @description Function to close connection to db, disigned to easy dubugging and
|
||||||
|
#' hide warnings.
|
||||||
|
close_db_connection <- function(con, where = "") {
|
||||||
|
tryCatch(
|
||||||
|
expr = DBI::dbDisconnect(con),
|
||||||
|
error = function(e) print(e),
|
||||||
|
warning = function(w) if (getOption("APP.DEBUG", FALSE)) message("=!= ALREADY DISCONNECTED ", where),
|
||||||
|
finally = if (getOption("APP.DEBUG", FALSE)) message("=/= DB DISCONNECT ", where)
|
||||||
|
)
|
||||||
|
}
|
||||||
30
modules/global_options.R
Normal file
30
modules/global_options.R
Normal file
@@ -0,0 +1,30 @@
|
|||||||
|
# box ========
|
||||||
|
.on_load = function(ns) {
|
||||||
|
message(
|
||||||
|
'Loading module "', box::name(), '"\n',
|
||||||
|
'Module path: "', basename(box::file()), '"'
|
||||||
|
)
|
||||||
|
set_global_options()
|
||||||
|
}
|
||||||
|
|
||||||
|
# ================
|
||||||
|
|
||||||
|
#' @export
|
||||||
|
#' @description костыли для упрощения работы себе
|
||||||
|
set_global_options <- function(
|
||||||
|
SYMBOL_DELIM = "; ",
|
||||||
|
APP.DEBUG = FALSE,
|
||||||
|
APP.FILE_DB = fs::path("data.sqlite"),
|
||||||
|
shiny.host = "127.0.0.1",
|
||||||
|
shiny.port = 1337,
|
||||||
|
...
|
||||||
|
) {
|
||||||
|
options(
|
||||||
|
SYMBOL_DELIM = SYMBOL_DELIM,
|
||||||
|
APP.DEBUG = APP.DEBUG,
|
||||||
|
APP.FILE_DB = APP.FILE_DB,
|
||||||
|
shiny.host = shiny.host,
|
||||||
|
shiny.port = shiny.port,
|
||||||
|
...
|
||||||
|
)
|
||||||
|
}
|
||||||
284
modules/utils.R
Normal file
284
modules/utils.R
Normal file
@@ -0,0 +1,284 @@
|
|||||||
|
# box ========
|
||||||
|
.on_load = function(ns) {
|
||||||
|
message(
|
||||||
|
'Loading module "', box::name(), '"\n',
|
||||||
|
'Module path: "', basename(box::file()), '"'
|
||||||
|
)
|
||||||
|
}
|
||||||
|
# ================
|
||||||
|
|
||||||
|
# asdasd
|
||||||
|
#' @export
|
||||||
|
make_panels <- function(page_name, main_scheme) {
|
||||||
|
|
||||||
|
# get info about inputs for current page
|
||||||
|
page_forms <- main_scheme |>
|
||||||
|
dplyr::filter(part == {{page_name}}) |>
|
||||||
|
dplyr::distinct(subgroup, form_id, form_label, form_type)
|
||||||
|
|
||||||
|
# get list of columns
|
||||||
|
cols_list <- unique(page_forms$subgroup)
|
||||||
|
|
||||||
|
# making cards
|
||||||
|
cards <- purrr::map(
|
||||||
|
.x = cols_list,
|
||||||
|
.f = make_cards_fn,
|
||||||
|
main_scheme = main_scheme
|
||||||
|
)
|
||||||
|
|
||||||
|
# make page wrap
|
||||||
|
page_wrap <- bslib::layout_column_wrap(
|
||||||
|
# width = "350px", height = NULL, #was 800
|
||||||
|
width = 1 / 4, height = NULL, # was 800
|
||||||
|
fixed_width = TRUE,
|
||||||
|
# unpack list of cards
|
||||||
|
!!!cards
|
||||||
|
)
|
||||||
|
|
||||||
|
# add panel wrap to nav_panel
|
||||||
|
bslib::nav_panel(
|
||||||
|
title = page_name,
|
||||||
|
page_wrap
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
# functions for making cards
|
||||||
|
#' @export
|
||||||
|
make_cards_fn <- function(sub_group, main_scheme) {
|
||||||
|
|
||||||
|
main_scheme <<- main_scheme
|
||||||
|
subgroups_inputs <- main_scheme |>
|
||||||
|
dplyr::filter(subgroup == {{sub_group}}) |>
|
||||||
|
dplyr::distinct(form_id, form_label, form_type)
|
||||||
|
|
||||||
|
bslib::card(
|
||||||
|
bslib::card_header(sub_group, container = htmltools::h5),
|
||||||
|
full_screen = TRUE,
|
||||||
|
width = "4000px",
|
||||||
|
bslib::card_body(
|
||||||
|
fill = TRUE,
|
||||||
|
# передаем все аргументы в функцию для создания елементов
|
||||||
|
purrr::pmap(
|
||||||
|
.l = subgroups_inputs,
|
||||||
|
.f = create_forms,
|
||||||
|
main_scheme = main_scheme
|
||||||
|
)
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
# UI RELATED ============================
|
||||||
|
#' @export
|
||||||
|
#' @param TEST s
|
||||||
|
create_forms <- function(
|
||||||
|
form_id,
|
||||||
|
form_label,
|
||||||
|
form_type,
|
||||||
|
main_scheme
|
||||||
|
) {
|
||||||
|
|
||||||
|
# check if have condition
|
||||||
|
condition <- dplyr::filter(main_scheme, form_id == {{form_id}}) |>
|
||||||
|
dplyr::distinct(condition) |>
|
||||||
|
dplyr::pull()
|
||||||
|
|
||||||
|
choices <- dplyr::filter(main_scheme, form_id == {{form_id}}) |>
|
||||||
|
dplyr::pull(choices)
|
||||||
|
|
||||||
|
# simple text or number input
|
||||||
|
if (form_type == "text") {
|
||||||
|
|
||||||
|
# get info how much rows to render
|
||||||
|
rows_to_show <- ifelse(!is.na(choices), as.integer(choices), 1)
|
||||||
|
|
||||||
|
form <- shiny::textAreaInput(
|
||||||
|
inputId = form_id,
|
||||||
|
label = shiny::span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
rows = rows_to_show
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (form_type == "number") {
|
||||||
|
form <- shiny::textAreaInput(
|
||||||
|
inputId = form_id,
|
||||||
|
label = shiny::span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
rows = 1
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
# simple date input
|
||||||
|
if (form_type == "date") {
|
||||||
|
# supress warning while trying keep data form empty by default
|
||||||
|
suppressWarnings({
|
||||||
|
form <- shiny::dateInput(
|
||||||
|
inputId = form_id,
|
||||||
|
label = shiny::span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
value = NA, # keep empty
|
||||||
|
format = "dd.mm.yyyy",
|
||||||
|
weekstart = 1,
|
||||||
|
language = "ru"
|
||||||
|
)
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
# еденичный выбор
|
||||||
|
if (form_type == "select_one") {
|
||||||
|
form <- shiny::selectizeInput(
|
||||||
|
inputId = form_id,
|
||||||
|
label = shiny::span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
choices = choices,
|
||||||
|
selected = NULL,
|
||||||
|
options = list(
|
||||||
|
create = FALSE,
|
||||||
|
onInitialize = I('function() { this.setValue(""); }')
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
# множественный выбор
|
||||||
|
if (form_type == "select_multiple") {
|
||||||
|
form <- shiny::selectizeInput(
|
||||||
|
inputId = form_id,
|
||||||
|
label = shiny::span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
choices = choices,
|
||||||
|
selected = NULL,
|
||||||
|
multiple = TRUE,
|
||||||
|
options = list(
|
||||||
|
create = FALSE,
|
||||||
|
onInitialize = I('function() { this.setValue(""); }')
|
||||||
|
)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
# множественный выбор
|
||||||
|
if (form_type == "radio") {
|
||||||
|
form <- shiny::radioButtons(
|
||||||
|
inputId = form_id,
|
||||||
|
label = shiny::span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
choices = choices,
|
||||||
|
selected = character(0)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (form_type == "checkbox") {
|
||||||
|
form <- shiny::checkboxGroupInput(
|
||||||
|
inputId = form_id,
|
||||||
|
# label = shiny::span(style = "color: #444444; font-weight: 550;", form_label),
|
||||||
|
label = shiny::h6(form_label),
|
||||||
|
choices = choices,
|
||||||
|
selected = character(0)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
# вложенная таблица
|
||||||
|
if (form_type == "inline_table") {
|
||||||
|
form <- rhandsontable::rHandsontableOutput(outputId = form_id)
|
||||||
|
}
|
||||||
|
|
||||||
|
# description part
|
||||||
|
if (form_type == "description") {
|
||||||
|
form <- shiny::div(shiny::HTML(form_label), style = "color:Gray;font-size: 90%;")
|
||||||
|
}
|
||||||
|
|
||||||
|
# если есть условие создать кондитионал панель
|
||||||
|
if (!is.na(condition)) {
|
||||||
|
form <- shiny::conditionalPanel(
|
||||||
|
condition = condition,
|
||||||
|
form
|
||||||
|
)
|
||||||
|
}
|
||||||
|
form
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
# SERVER LOGIC ==========================
|
||||||
|
#' @export
|
||||||
|
get_empty_data <- function(type) {
|
||||||
|
if (type %in% c("text", "select_one", "select_multiple")) return(as.character(NA))
|
||||||
|
if (type %in% c("radio", "checkbox")) return(as.character(NA))
|
||||||
|
if (type %in% c("date")) return(as.Date(NA))
|
||||||
|
if (type %in% c("number")) as.character(NA)
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#' @export
|
||||||
|
#' @description Function to update input forms (default variants only)
|
||||||
|
#' @param id - input form id;
|
||||||
|
#' @param type - type of form;
|
||||||
|
#' @param value - value to update;
|
||||||
|
#' @param local_delimeter - delimeter to split file
|
||||||
|
update_forms_with_data <- function(
|
||||||
|
id,
|
||||||
|
type,
|
||||||
|
value,
|
||||||
|
local_delimeter = getOption("SYMBOL_DELIM")
|
||||||
|
) {
|
||||||
|
|
||||||
|
if (type == "text") {
|
||||||
|
shiny::updateTextAreaInput(inputId = id, value = value)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (type == "number") {
|
||||||
|
shiny::updateTextAreaInput(inputId = id, value = value)
|
||||||
|
}
|
||||||
|
|
||||||
|
# supress warnings when applying NA or NULL to date input form
|
||||||
|
if (type == "date") {
|
||||||
|
suppressWarnings(
|
||||||
|
shiny::updateDateInput(inputId = id, value = value)
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
# select_one
|
||||||
|
if (type == "select_one") {
|
||||||
|
# update choices
|
||||||
|
# old_choices <- subset(scheme, form_id == id, choices) |> dplyr::pull()
|
||||||
|
# new_choices <- unique(c(old_choices, value))
|
||||||
|
# new_choices <- new_choices[!is.na(new_choices)]
|
||||||
|
|
||||||
|
# shiny::updateSelectizeInput(inputId = id, selected = value, choices = new_choices)
|
||||||
|
shiny::updateSelectizeInput(inputId = id, selected = value)
|
||||||
|
}
|
||||||
|
|
||||||
|
# select_multiple
|
||||||
|
# check if value is not NA and split by delimetr
|
||||||
|
if (type == "select_multiple" && !is.na(value)) {
|
||||||
|
vars <- stringr::str_split_1(value, local_delimeter)
|
||||||
|
|
||||||
|
# update choices
|
||||||
|
# old_choices <- subset(scheme, form_id == id, choices) |> dplyr::pull()
|
||||||
|
# new_choices <- unique(c(old_choices, vars))
|
||||||
|
# new_choices <- new_choices[!is.na(new_choices)]
|
||||||
|
|
||||||
|
# shiny::updateSelectizeInput(inputId = id, selected = vars, choices = new_choices)
|
||||||
|
shiny::updateSelectizeInput(inputId = id, selected = vars)
|
||||||
|
}
|
||||||
|
|
||||||
|
# in other case fill with `character(0)` to proper reseting form
|
||||||
|
if (type == "select_multiple" && is.na(value)) {
|
||||||
|
shiny::updateSelectizeInput(inputId = id, selected = character(0))
|
||||||
|
}
|
||||||
|
|
||||||
|
# radio buttons
|
||||||
|
if (type == "radio" && !is.na(value)) {
|
||||||
|
shiny::updateRadioButtons(inputId = id, selected = value)
|
||||||
|
}
|
||||||
|
if (type == "radio" && is.na(value)) {
|
||||||
|
shiny::updateRadioButtons(inputId = id, selected = character(0))
|
||||||
|
}
|
||||||
|
|
||||||
|
# checkboxes
|
||||||
|
if (type == "checkbox" && !is.na(value)) {
|
||||||
|
vars <- stringr::str_split_1(value, local_delimeter)
|
||||||
|
shiny::updateCheckboxGroupInput(inputId = id, selected = vars)
|
||||||
|
}
|
||||||
|
if (type == "checkbox" && is.na(value)) {
|
||||||
|
shiny::updateCheckboxGroupInput(inputId = id, selected = character(0))
|
||||||
|
}
|
||||||
|
|
||||||
|
# if (type == "inline_table") {
|
||||||
|
# message("EMPTY")
|
||||||
|
# }
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user