[英]Ηow can I get the filename of a file uploaded with a shiny fileInput?
[英]R shiny restrict fileInput to filename pattern and not just file type
我有一个 Shiny 应用程序,它使用fileInput
在客户端获取一些文件(我不能使用在服务器端管理文件的 shinyFiles package)。
我希望用户只能上传与特定模式匹配的文件(例如helloWorld.txt
),而不仅仅是匹配文件类型(例如文本、csv 等)。
fileInput
有一个accept
参数,您可以在其中提供接受的文件类型。 从文档:
accept A character vector of MIME types; gives the browser a hint of
what kind of files the server is expecting.
我不只是想指定接受的文件类型,这对我的应用程序来说不够严格。 有没有办法做到这一点?
这是一个只接受文本文件的 MWE:
library(shiny)
ui <- fluidPage(
fileInput(
"file_choice",
label = "Choose a files",
multiple = TRUE,
accept = c(
".txt"
)
)
)
server <- function(input, output, session) {}
shinyApp(ui, server)
如果我使用:
accept = c(
"helloWorld.txt"
)
它不起作用,因为它不是 MIME 类型。
此页面Shiny 文件输入参数“接受”问题建议在服务器端之后处理所选文件,这是我最终要做的,但我更喜欢先验限制而不是后验限制(以避免服务器端文件检查并反馈给用户)。
一种方法是插入一些 javascript 作为onchange
事件触发器,检查文件名,如果不匹配,则中断上传过程。 这种方法使用alert
,我知道很多人认为这种方法有点侵入性并且不美观,我相信其他人可以提出更好的建议。
我应该从一个简单的警告开始:这里的条件严格来说是“文件名以文字hello
开头” 。 您的示例可能需要更多技巧,而不是需要文件名 sans-extension 匹配。 在这种情况下,可能需要正则表达式,请参考https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions 之类的内容以获取更多信息。 这个答案提供的是一个框架供您填补漏洞。
(在修改此代码时,您可能会发现添加alert(FileName)
和/或alert(FileBase)
以查看 javascript 与您的模式进行比较很有用。每次尝试都会弹出。在我的例子中,它帮助我发现毫不奇怪,存在 windows 路径,这意味着它使用反斜杠而不是正斜杠,需要split(/[\\/]/)
,进一步转义为 R。)
checkjs <- 'function checkFileName(fieldObj) {
var FileName = fieldObj.value;
var FileBase = FileName.split(/[\\\\/]/).pop();
if (! FileBase.startsWith("hello")) {
fieldObj.value = "";
alert("File does not start with hello");
return false;
}
return true;
}'
attrib_replace <- function(x, cond, ...) {
if (all(names(cond) %in% names(x)) && identical(cond, x[names(cond)])) x <- c(x, list(...))
if ("attribs" %in% names(x)) x$attribs <- attrib_replace(x$attribs, cond = cond, ...)
if ("children" %in% names(x)) x$children <- lapply(x$children, function(ch) attrib_replace(ch, cond = cond, ...))
x
}
一个示例应用程序,使用它:
library(shiny)
shinyApp(
ui = fluidPage(
tags$script(checkjs),
attrib_replace(fileInput(
"file_choice",
label = "Choose a file",
multiple = TRUE,
accept = c(".txt")
), list(id = "file_choice", type = "file"), onchange = "checkFileName(this);")
),
server = function(input, output, session) {}
)
当您 select 文件不以“hello”开头时,它会发出警报并且不会上传文件。 正确的文件只上传文件。
我为此引用的其他一些答案:
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.