download属性のクリックによるダウンロードはドキュメントに存在しなければダウンロードできない。ブラウザ依存で。

download属性のクリックによるダウンロードはドキュメントに存在しなければダウンロードできない。ブラウザ依存で。:


要約

<a href="ダウンロードしたいファイルパス or blob" download="ダウンロードファイル名"><a> 
というdownload属性を使ったリンクは、

href,
download,
click

をJSで操作してもいいものの、a要素自体はdocument下に存在していなければならず、

JavaScript空間のみでcreateDocumentしただけのものでは一部ブラウザでダウンロードできない。

確認できたダウンロードできるブラウザは

  • Vivaldi 2.2.1388.37
おそらく参考したコード記事からの情報によりChromeも可。

ダウンロードできないブラウザは

  • Firefox 64
  • IE 9
他のブラウザに関しては下記リンクからテストしてもらえればと思います。

多ブラウザ対応としては、ファイル内容をJSで作るにしてもダウンロード用のa要素を先にHTMLで書いておくか、JSでa要素を作ってもappendChildなどでDOMツリーに追加してやればいいんじゃないでしょうか。


発端

Togetterのツイートまとめをスクレイピングしてコマンドやブラウザから一発で取得する機能の開発 #ファイルダウンロード - Qiita

downloadText(e) { 
            const blob = new Blob([this.$store.state.text], {type: 'text/plain'}) 
            const link = document.createElement('a') 
            link.href = window.URL.createObjectURL(blob) 
            link.download = this.$store.state.text.split('\n')[0] + '.txt' 
            link.click() 
        }, 
(投降直前に気づきましたが、この処理はブラウザ依存のようです。

おそらくFirefox64とIE9ではファイルをダウンロードできません。

gif動画でダウンロードしているブラウザはVivaldiです。

理由は簡単なので気が向いたときか要望が出たときにでも直します)
これがブラウザによって動いたり動かなかったりする理由を考えたとき、

「HTML文章上にないものをクリックするというシチュエーションは謎だなあ」と考え、検証してみた。

ただ、結果ではダウンロードの場合に違いが現れ、たとえばクリックでアラートを出すような処理に関しては変数に対するclickでも動作した。


コード

<button id="document"> Document 
</button> 
 
<button id="js"> JavaScript 
</button> 
 
<a id="documentElement"></a> 
 
<hr> 
 
<button id="document2"> Document download 
</button> 
 
<button id="js2"> JavaScript download 
</button> 
 
<a id="documentElement2"></a> 
function clickAlert() { 
  alert('click!') 
} 
 
const jsOnlyElement = document.createElement('a') 
jsOnlyElement.addEventListener('click', clickAlert) 
 
const documentElement = document.getElementById('documentElement') 
documentElement.addEventListener('click', clickAlert) 
 
document.getElementById('document').addEventListener('click', () => documentElement.click()) 
 
document.getElementById('js').addEventListener('click', () => jsOnlyElement.click()) 
 
/***************************/ 
 
function download(a, filename){ 
  var blob = new Blob(['download!'], {type: "text/plain"}) 
  a.href = URL.createObjectURL(blob); 
  a.target = '_blank'; 
  a.download = filename + '.txt'; 
  a.click(); 
} 
const jsOnlyElement2 = document.createElement('a') 
 
const documentElement2 = document.getElementById('documentElement2') 
 
 
document.getElementById('document2').addEventListener('click', () => download(documentElement2, 'documentElement')) 
 
document.getElementById('js2').addEventListener('click', () => download(jsOnlyElement2, 'jsOnlyElement')) 
 
CodePenの匿名埋め込みは出来ないようなのでリンクで失礼。

https://codepen.io/anon/pen/mazBXK

コメント

このブログの人気の投稿

投稿時間:2021-06-17 22:08:45 RSSフィード2021-06-17 22:00 分まとめ(2089件)

投稿時間:2021-06-20 02:06:12 RSSフィード2021-06-20 02:00 分まとめ(3871件)

投稿時間:2021-06-17 05:05:34 RSSフィード2021-06-17 05:00 分まとめ(1274件)