如何在不使用<a>具有下载属性的元素或服务器

How to download a file without using <a> element with download attribute or a server?

本文关键字:属性 有下载 元素 服务器 gt lt      更新时间:2023-09-26

根据canius的说法,<a>元素的download属性在Microsoft Edge build 10547+中受支持,但在IE或Safari中不受支持。

如何在不使用download属性集的<a>元素或服务器的情况下下载文件对象?

有很多触发下载的方法。以下是一些:

使用表格:

<form method="get" action="mydoc.doc">
<button type="submit">Download</button>
</form>

使用javascript:

<button type="submit" onclick="window.open('mydoc.doc')">Download</button>

虽然我支持@LeoFarmer的答案,但我想提供两种"可破解"的方法:

  1. 如果文件很小,可以将ahref='data:[<mediatype>][;base64],<data>'一起使用。

    这可以允许您在mediatype中添加内容处置,模拟HTTP标头。这种黑客攻击也不像人们所希望的那样便携。

  2. 对于中小型文件,可以使用AJAX下载文件,然后使用Javascript file API提示文件保存(API不支持保存,但很容易将数据转换为数据URL)。

    如果你想避免Javascript文件API,你可以尝试模仿锚点击,如这里所建议的。

同样,正如Leo Farmer所指出的,这些解决方案不能保证浏览器不会在新的选项卡中打开文件,而不是将其保存到磁盘上,但我认为可以肯定地说,所有用户都可以优雅地降级为cmd+Sctrl+S键盘快捷键:-)

您可以使用download属性和jquery来完成此操作。下载属性在ie和safari/ios中不支持。所以你可以用jquery来做

 $('.download').click(function(e) {
    e.preventDefault();  //stop the browser from following
    window.location.href = 'uploads/file.doc';
});
<a href="no-script.html" class="download">Download</a>

使用FileSaver.js

它支持所有常用的浏览器。

仅包括:

<script type="text/javascript" src="FileSaver.min.js"></script>

并像这样使用:

var file = new File(["Hello, world!"], "hello world.txt", {type: "text/plain;charset=utf-8"});
saveAs(file);

注意:为了使其在Safari<6、Opera<15和FireFox<20您需要将Blob.js作为依赖项包含在内。

您可以使用手动创建的文件的data URI data:[<mediatype>][;base64],<data>表示,也可以使用FileReader().readAsDataURL()MIME类型设置为application/octet-streamencodeURIComponent()window.open()

<script>
  var file = "data:application/octet-stream,"
             + encodeURIComponent("<!DOCTYPE html>"
             + "<html><body>"
             + "<div>abc</div>"
             + "</body></html>");
  var saveFile = window.open(file, "_self");     
</script>

<script>
  var blob = new Blob(["abc"], {type:"text/plain"});
  var reader = new FileReader();
  reader.addEventListener("load", function(e) {
    // replace existing `MIME` type with `application/octet-stream`
    var file = "data:application/octet-stream;" 
                + e.target.result.split(/;/)[1];
    var saveFile = window.open(file, "_self");
  });
  reader.readAsDataURL(blob)
</script>

plnkrhttp://plnkr.co/edit/IS1OC0laRwL3BuuF9zay?p=preview

如果您使用服务器端,请遵循表单提交机制来呈现页面。在MVC中,我们可以使用以下代码

Html

  @using (Html.BeginForm("GetAttachment", "User", FormMethod.Post))
                {
                    <button type="submit">Download</button>   
                }

MVC控制器

public ActionResult GetAttachment()
{
   string filename = "File.pdf";
string filepath = AppDomain.CurrentDomain.BaseDirectory + "/Path/To/File/" + filename;
byte[] filedata = System.IO.File.ReadAllBytes(filepath);
string contentType = MimeMapping.GetMimeMapping(filepath);
var cd = new System.Net.Mime.ContentDisposition
{
    FileName = filename,
    Inline = true,
};
Response.AppendHeader("Content-Disposition", cd.ToString());
return File(filedata, contentType);
}