アップロードされたファイルのMIMEタイプを検証する
アップロードされたファイルが正常か判断するため、MIMEタイプの検出方法について調べて実装したので、情報をまとめます。
MIMEタイプ
MIMEタイプ(Multipurpose Internet Mail Extensions)はファイルの識別子のようなもの。
MIMEタイプにはそのファイルのマジックナンバーというものが含まれていて、バイト構造見ることでファイルタイプを識別できます。
マジックナンバー。バイト構造を見ることで、様々な形式の構文によりファイルタイプを推測することができます。例えば GIF ファイルは16進数の値 47 49 46 38 39 (
GIF89
)、 PNG ファイルは 89 50 4E 47 (.PNG
) で始まります。マジックナンバーを持たない種類のファイルもありますので、100%!信(MISSING)頼できるシステムではありません。https://developer.mozilla.org/ja/docs/Web/HTTP/Basics_of_HTTP/MIME_types
ブラウザで検出しているMIMEタイプ
ブラウザで検出しているMIMEタイプは拡張子で判別しており、バイナリまでチェックしてないようです。そのため拡張子が偽造されたファイルを正確に判別できません。
GoでMIMEタイプを検出する方法
Goのhttpパッケージに DetectContentType
というファンクションがあります。
https://golang.org/pkg/net/http/#DetectContentType
node.jsでMIMEタイプを検出する方法
MIMEタイプを検出するnpmパッケージがいくつか見つかりました。
mime
はbufferから検出できませんが、 file-type
はbufferからの検出ができ、ブラウザからアップロードされたファイルにも対応できます。
file-typeパッケージを利用したMIMEタイプの検出
yarnかnpmでインストールし、下記のように使えます。超簡単でした。
const fileType = require('file-type')
const b = await fileType.fromBuffer(buffer)
console.log(b.mime)
まとめ
MIMEタイプとGo、Node.jsで検出する方法をまとめました。