FileAPIを使ってみる

はじめに

JavaScriptでCSVやエクセルファイルを弄れるようにしたかったので試してみました。

✅参考
パーフェクトJavaScript

FileAPI

✅FileAPIとは

参考:JavaScriptのFileReaderの使い方を現役エンジニアが解説【初心者向け】

ローカルに保存されているファイルの情報や中身を取得するためのAPI。

✅Fileオブジェクト

ファイル情報を取得可能で、Blobオブジェクトを継承している。

inputタグのtype属性をfileにすると、OS標準のファイル選択ダイヤログが利用可能。

<input type="file"> // value属性はファイルの名前となる。

イベントハンドラ

onchange:ファイルを選択された際、選択されたファイルのFileオブジェクトを取得

プロパティ

files:選択されたファイルのFileオブジェクトを含む配列

✅FileReaderオブジェクト

ファイルの中身を読み込むには、FileReaderオブジェクトを使用。

let fileReader = new FileReader();

メソッド

readAsText(blob,encoding):テキスト形式でファイルを読み込む

Blobオブジェクトを引数に指定可能。読込は非同期で処理されるため、イベントハンドラとセットで使われる。

イベントハンドラ

onload:読込成功時に実行

プロパティ

result:読込結果が格納されている

✅Blobオブジェクト(Binary Large Object)

大きなデータを効率よく扱うためのインターフェース。

FileオブジェクトはBlobオブジェクトを継承している。

Textファイルを扱う

✅読込

※後述CSVと同様のコードのため割愛

txt

テキストファイルを読み込めるか確認

✅出力

参考:JavaScriptで文字列をファイル出力する方法を現役エンジニアが解説【初心者向け】

html

<input type="button" value="textファイル出力" onclick="textFC()">

<script language="javascript" type="text/javascript">

let textFC = () => {
let blob = new Blob(['あいうえお'],{type:"text/plan"});
let link = document.createElement('a');
link.href = URL.createObjectURL(blob);
link.download = '作ったファイル.txt';
link.click();
}

</script>

🙄テキストファイルはBlobオブジェクトを扱えば簡単に扱えますね!!

CSVファイル

CSVとはComma Separated Valueの略でカンマで区切られた値が入力されたファイルのこと。

✅読込

参考:

JavaScriptでCSVファイルを読み込む方法を現役エンジニアが解説【初心者向け】

File APIでCSVファイルを読み込む こっちの方が詳しめ

pug

-
  const ttl = "FileAPI study"
doctype
html(lang="ja")
  head
    meta(charset="utf-8")
    meta(name="viewport" content="width=device-width,initial-scale=1.0")
    title #{ttl}
    link(rel="stylesheet" href="css/style.css")
  body
    header
      h1 #{ttl}
    main
      input#file(type="file")
      p FileAPIの読込結果(※CSVファイル)
      div#result(style="background-color:#f4ca3630")
    script(src="js/index.js")

index.js

let fileInput = document.getElementById('file'); // HTMLからIDを指定
let result = document.getElementById('result');

let fileReader = new FileReader(); // インスタンス生成
fileInput.onchange = () => { // イベント発生時の処理
  let file = fileInput.files[0]; // 
  fileReader.readAsText(file);
};

fileReader.onload = () => {
  result.textContent = fileReader.result;
};

test.csv

山田,鈴木,佐藤,田中

読み込めた!

※localサーバー立ち上げなくてもできた。

✅出力

参考:JavaScript のデータを CSV で保存する

※出力は文字化けやらでいろいろ配慮が大変らしい。

Excelファイル

✅読込

参考:

ウェブブラウザ上のJavaScriptでExcelファイルをゴニョゴニョしたい

Sheet.js(リポジトリ)を使うのが定番ぽい。

ダウンロードにはFileSaver(リポジトリ)

CDNの場合こうなる

<script src="https://cdnjs.cloudflare.com/ajax/libs/xlsx/0.14.2/xlsx.full.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/FileSaver.js/1.3.8/FileSaver.min.js"></script>

JavaScriptでオブジェクトをExcelファイルに出力する方法を現役エンジニアが解説【初心者向け】

上記サイトのサンプル。

配列部分をExcel用に変換し、FileSaverでxlsxファイルとしてダウンロード。

var array1 =
[
  ["apple", "banana", "cherry"],
  [1, 2, 3]
];

🙄上手く応用すればなにかできそう。

参考:Excel内でjavascriptが使える!?

逆にExcel側でJSを使う手法もあるらしい。

文字化けに関して

✅読込

JavaScriptでShift_JISのcsvを読み込む(文字化け対策)

Excel経由でCSVを保存するとデフォルトでShift_jsになりブラウザで読み込むと文字化けする。

なので以下のようにCSV UTF-8(with BOM)を指定して対処する。

✅VSCodeでの読み込み

VSCodeでもデフォルトでUTF-8としてファイルを開く(参考)ためShift-jsは文字化けするので、Excel保存時にCSV UTF-8で保存すること。

※この文字化けは右下の文字コードをクリックして[エンコード付きで再度開く]もしくは[エンコード付きで保存]で直せるが、Excel側でも開きながらだとバグるので注意。

ちなみにVSCodeで編集したのちに再度Excel側を開くとこうなる。

区切り文字カンマにチェックで無事表示。

””を入れればカンマもエスケープできる。

あと、Excel側でセル結合して保存しても、CSVでは対応できないぽい。

✅出力

JavaScript のデータを CSV で保存する

日本語を含むCSVをExcelで開きたい場合

・Shift_JIS

・BOM付きUTF-8 ※Mac✖

・BOM付きUTF-16LE

※Win/Mac間で更に調整が必要らしい。。。

CSV形式で深掘りしてみる

普段使っているサークルの管理シート(Excel)のメイン部分を抜粋。

これをコピペしてCSV with UTF-8で保存。

再度開くとこうなる(※セル幅は調整済み)。

テキストベースで確認すると以下。

Vo,,,Gt,,,
なかおさん(初)、いとかなちゃん、さかもとさん、じょーさん初、ゆいちゃん、ちゃまさん??、ゆーきちくん,,,みどりさん、まさる、やぎくん、えのちゃん、ウッディ,,,
ba,,,Dr、Key,,,
ながしまさん(見学)、あべさん初、かいとさん,,,なおきさん初、ならちゃん、くわ、あべくん,,,
■課題曲,Vo,Gt1(リード),Gt2(リズム),Ba,Dr,Key
ロック/Go!Go!7188 ※いなそう~汗,,,,,,
Changes/Base Ball Bear,なかおさん、さかもとさん,うっでぃ,,かいとさん,,
マリーゴールド/あいみょん,いとかなちゃん、じょーさん,やぎくん,みどりさん,まさる??,なおきさん、あべくん,
ガラスのブルース/bump,さかもとさん,うっでぃ,,,◎,
拝啓、少年よ/Hump Back,いとかなちゃん,やぎくん,みどりさん,かいとさん,◎,
小さな恋のうた/MONGOL800,◎,◎,,かいとさん,なおきさん,

セルの結合場所は単純に,,で空白セルができていて、行は改行されているだけ。

ブラウザで読み込んでもただの文字列。笑

これをブラウザ側でいい感じに表示&編集&エクセル出力できるアプリを作りたい。

おわりに

以前全然理解できなかったFileAPIを少し実践できた。

そもそものJavaScriptの仕組みが少し理解できるようになってきた恩恵◎

この調子でエクセル弄ったりできるようにしたい。

まずは上記のスタジオ管理シートの代替となるアプリを制作していきたいと思います。

※クライアント側での操作がメインなのでむしろCSV出力はおまけ程度に考えても良いかもしれない。

コメントを残す