英文:
File download in Vaadin 23
问题
我在Wildfly服务器上运行着一个Vaadin 23应用程序。我想要添加一个按钮,然后开始下载位于web-inf目录下的文件。我只找到了这篇博客文章,似乎已经过时。
哪种方法是最佳(首选)方式来实现这一目标?
谢谢和顺祝
Matt
英文:
I habe a Vaadin 23 app running on a wildfly server. I want to add a button which then start to download a file which is located under the web-inf directory. I only found this blog article which seems to be outdated.
Which is the best (preferred) way to achieve this?
Thanks and kind regards
Matt
答案1
得分: 1
一种方法是将文件作为资源获取,并将其设置为“Anchor”。然后,您可以有一个以编程方式单击“Anchor”的“Button”。
Anchor anchor = new Anchor();
anchor.setText("下载");
anchor.getElement().getStyle().set("display", "none");
anchor.getElement().setAttribute("download", true);
anchor.setHref(resource);
Button button = new Button("下载");
button.addClickListener(event -> {
anchor.getElement().callJsFunction("click");
});
add(anchor, button);
Vaadin的目录中还有一个插件,用于打包上述过程。
请注意,如果您想在对话框中添加“下载”按钮,请确保“Anchor”不在对话框中,参见另一个问题。
您还可以在这里找到更完整的下载示例。
英文:
One approach is to get the file as resource and set it to Anchor
. Then you can have a Button
which programmatically clicks the Anchor
.
Anchor anchor = new Anchor();
anchor.setText("Download");
anchor.getElement().getStyle().set("display", "none");
anchor.getElement().setAttribute("download", true);
anchor.setHref(resource);
Button button = new Button("Download");
button.addClickListener(event -> {
anchor.getElement().callJsFunction("click");
});
add(anchor, button);
There is also an add-on in Vaadin's Directory that packages the above process.
Note, if you want to have the Download button in the Dialog, make sure that Anchor is not in the Dialog, see another question.
You can find also more complete download example here.
答案2
得分: 0
这是我提出的方法:
private Button createDownloadButton(String fileName) {
Icon icon = VaadinIcon.FILE_TABLE.create();
icon.setColor("green");
Button downloadButton = new Button(fileName, icon);
downloadButton.addThemeVariants(ButtonVariant.LUMO_TERTIARY);
downloadButton.setDisableOnClick(true);
downloadButton.addClickListener(event -> {
InputStream inputStream = VaadinServlet.getCurrent().getServletContext()
.getResourceAsStream(UiFactory.DOWNLOAD_PATH + fileName);
ReadableByteChannel readChannel = Channels.newChannel(inputStream);
Path downloadPath = Paths.get(System.getProperty("user.home"), fileName);
FileChannel writeChannel = null;
try(FileOutputStream fileOS = new FileOutputStream(downloadPath.toFile())) {
writeChannel = fileOS.getChannel();
writeChannel.transferFrom(readChannel, 0, Long.MAX_VALUE);
String message = String.format("文件成功传输到%s。", downloadPath.toString());
showStatusMessage(message, null, MessageStatus.SUCCESS);
downloadButton.setEnabled(true);
} catch (IOException exception) {
// 处理IO异常
} finally {
try {
if (writeChannel != null){
writeChannel.close();
}
readChannel.close();
} catch (IOException e) {
// 处理IO异常
}
}
});
}
问题在于没有对用户询问文件存储位置的对话框,因此这里的JavaScript解决方案非常巧妙。
英文:
Thanks I came up with this method:
private Button createDownloadButton(String fileName) {
Icon icon = VaadinIcon.FILE_TABLE.create();
icon.setColor("green");
Button downloadButton = new Button(fileName, icon);
downloadButton.addThemeVariants(ButtonVariant.LUMO_TERTIARY);
downloadButton.setDisableOnClick(true);
downloadButton.addClickListener(event -> {
InputStream inputStream = VaadinServlet.getCurrent().getServletContext()
.getResourceAsStream(UiFactory.DOWNLOAD_PATH + fileName);
ReadableByteChannel readChannel = Channels.newChannel(inputStream);
Path downloadPath = Paths.get(System.getProperty("user.home"), fileName);
FileChannel writeChannel = null;
try(FileOutputStream fileOS = new FileOutputStream(downloadPath.toFile())) {
writeChannel = fileOS.getChannel();
writeChannel.transferFrom(readChannel, 0, Long.MAX_VALUE);
String message = String.format("Successfully transferred file to %s.", downloadPath.toString());
showStatusMessage(message, null, MessageStatus.SUCCESS);
downloadButton.setEnabled(true);
} catch (IOException exception) {
// handle IO exceptions
} finally {
try {
if (writeChannel != null){
writeChannel.close();
}
readChannel.close();
} catch (IOException e) {
// handle IO exceptions
}
}
});
Problem here is that there is no dialog to ask the user where to store the file. So the JS solution is pretty smart here.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论