n8nでbinaryToStringエラーになる原因と解決法【filesystem-v2対応】
結論:binaryToStringエラーはExtract from Fileノードで解決します
n8nのbinaryDataMode=filesystem環境でRead File(s) From Diskを使い、後続のCodeノードでバイナリを読もうとしてエラーが出たことはありませんか。
解決策はシンプルです。Read File(s) From DiskノードのすぐあとにExtract from Fileノードを1つ追加するだけです。
これだけでbinaryToStringエラーは完全に解消されます。Codeノードでバイナリを直接読み出す処理は一切不要になります。
私が詰まった状況と試したこと(全部失敗した話)
今回のエラーに出会ったのは、n8nのワークフローでJSONファイルをRead File(s) From Diskで読み込み、後続のCodeノードでJSONとしてパースしようとしたときのことです。
環境はn8n 2.17.7 Self Hosted、binaryDataModeはfilesystem(docker-compose.ymlで設定)です。
最初に試したのは、よく見かけるbase64デコードの方法でした。
const base64 = $input.first().binary?.data?.data;
const jsonString = Buffer.from(base64, 'base64').toString('utf8');結果は意味不明な文字列でした。出力を確認するとbinary.data.dataの中身が"filesystem-v2"という文字列になっていて、base64ではまったくなかったのです。
次にbinaryToStringヘルパーを試しました。
const jsonString = await this.helpers.binaryToString(item.binary.data);今度はUnknown errorというエラーが出て即終了でした。
最後にbytesプロパティを使ってみました。
const bytes = item.binary.data.bytes;
const jsonString = Buffer.from(bytes).toString('utf8');こちらはReceived type number (5270)というエラーでした。bytesはファイルサイズ(5270バイト)を表す数値であって、実データではなかったのです。
3種類のアプローチをすべて試して、30分以上詰まりました。正直、かなり困りました。そこでチャッピー(ChatGPT)にセカンドオピニオンを求めたところ、原因がはっきりわかりました。
なぜ読めないのか:filesystem-v2の正体
原因はbinaryDataMode: filesystemという設定にあります。
通常のメモリモード(デフォルト)では、バイナリデータはメモリ上に保持されます。この場合、binary.data.dataにはbase64エンコードされた実データが入っています。
一方、filesystemモードでは、バイナリデータはメモリではなくディスク上のファイルとして保存されます。その結果、binary.data.dataに実データは入りません。代わりに"filesystem-v2"という識別子(参照ポインタ)が入っています。
整理するとこうなります。
モード | binary.data.data の中身
--- | ---
memory(デフォルト) | base64エンコードされた実データ
filesystem | `"filesystem-v2"`(参照ポインタ)Codeノードはこの参照ポインタを解決する手段を持っていません。だから何をやっても失敗し続けていたわけです。
「読めない」のではなく、「そこにデータが入っていない」という状態でした。これを理解してからは、解決の方向性がすぐに見えました。
解決方法:Extract from Fileノードの設定手順
解決策は非常にシンプルです。ノードを1つ追加するだけです。
ノード構成:
Read File(s) From Disk
↓
Extract from File ← ここを追加する
↓
Code(任意)Extract from Fileの設定:
- Operation:
Convert to JSON - Source Key:
data
これだけです。
設定後、Extract from Fileノードを実行すると、$json.fileContentにJSONの内容が展開されます。後続のCodeノードでは以下のように参照できます。
const session = $('Extract from File').first().json.fileContent;
const keyword = session.keyword;Codeノード自体が不要になるケースも多いです。JSONを読み込んでそのまま次のノードに渡すだけであれば、Extract from Fileノードの出力を直接使えます。
判断基準:
binary.data.dataが"filesystem-v2"になっている → Extract from Fileノードを挟むbinaryToStringでUnknown errorが出る → 同上bytesが数値として返ってくる → 同上(これはファイルサイズ)
なぜExtract from Fileで解決するのか
Extract from Fileノードはn8nの内部APIを通じてfilesystem-v2の参照ポインタを解決できます。Codeノードが持っていない「ディスク上の実ファイルを読み込む」処理を内部で実行しています。
つまり、「Codeノードで何とかしようとしていた」という方向性自体が間違いでした。
n8nのfilesystemモードは「バイナリをノードで扱え、Codeで直接触るな」という設計になっています。このことを理解してからは、同種の処理でも同じ判断ができるようになりました。
ハマりポイントまとめ
同じ場所で詰まらないために、ハマりやすいポイントを整理しておきます。あなたはどのパターンに引っかかりましたか?
ハマりポイント①:`binary.data.data`にデータが入っていると思い込む
filesystemモードではここに実データは入りません。"filesystem-v2"が入っている場合は、それは参照ポインタです。
確認方法:
return [{ json: { preview: $input.first().binary?.data?.data } }];→ "filesystem-v2"が返ってきたらExtract from Fileを使う
ハマりポイント②:Codeノードで何とかしようとする
filesystemモードのバイナリはCodeノードからは解決できません。ノードを使うのが正しいアプローチです。
ハマりポイント③:base64前提で処理する
filesystemモードではbase64エンコードされていません。Buffer.from(data, 'base64')は機能しません。
この後どうなったか
Extract from Fileノード追加後、正常に動作しました。
今回の詰まりで得た一番の学びは「filesystemモードでバイナリを扱うときは、Codeノードではなく専用のノードを使う」という判断基準です。Extract from Fileノード1つで即解決したときは、正直ホッとしました。この基準を持っていれば、同じ状況で30分以上消耗することはなかったと思います。
よくある質問
Q. `binaryToString`は使えないのでしょうか?
n8n 2.17.7のfilesystemモードでは、this.helpers.binaryToString()はUnknown errorになります。将来のバージョンで対応される可能性はありますが、現時点ではExtract from Fileノードを使う方が安定しています。
Q. Extract from Fileノードで読めるファイル形式は何ですか?
JSON・CSV・テキストファイルなどに対応しています。JSONの場合はOperation をConvert to JSONに設定します。CSVの場合はConvert to CSVを選びます。
Q. Read File(s) From Diskのファイルパスに変数を使えますか?
使えます。File(s) SelectorフィールドでFX(式)モードにすると、/files/sessions/session_{{ $json.thread_ts }}.jsonのように変数を埋め込めます。ただしパスに誤りがあると「No file(s) found」エラーになるので、実際にファイルが存在するパスを確認してから設定してください。
まとめ
今回の詰まりを一言で表すと「filesystemモードは直接読むな、ノードを使え」です。
binary.data.dataが"filesystem-v2"になっている → 実データではなく参照ポインタ- Codeノードでの解決は不可能 → Extract from Fileノードを使う
- 設定はOperation:
Convert to JSON/ Source Key:dataのみ
今日できる一歩: Read File(s) From Diskを使っているワークフローがあれば、その直後にExtract from Fileノードを追加してみてください。それだけでCodeノードのバイナリ処理が不要になります。
ただし、このままだと同じ詰まりがn8nの別のノードでまた起きたときに、どのノードに任せるべきかは判断できません。
なぜなら、「何をCodeノードに任せて、何をn8nのノードに任せるか」という設計の判断軸が、まだ整理されていないからです。
→ 判断軸の整理はこちら
bizinets.biz
記事を読んで「もっと知りたい」と思ったあなたへ
bizinets.biz では、ビジネスの仕組みづくりを体系的に学べるコンテンツを用意しています。まずは一度、覗いてみてください。
bizinets.biz へ行く →