iT邦幫忙

2026 iThome 鐵人賽

DAY 9
0

day09_title

前言

每個程式語言都有他與檔案處理和溝通的方式,當然 nodejs 也不例外,
當然在 bun 這方面也是非常厲害,甚至比想像中多不少東西,
今天我們會一一介紹一些厲害且實用關於 File I/O 相關的操作以及工具等

讓我們開始

在我們開始前我們先從我們的 nodejs 對於 File I/O 的操作進入
我們先個基本操作「讀檔案」並且「寫入檔案」

import { readFile, writeFile } from 'node:fs/promises'

const content = await readFile('data.txt', 'utf-8');
await writeFile('output.txt', content, 'utf-8')

我相信有操作過檔案的朋友們,對這段肯定不陌生

如果想試試看的朋友可以看以下範例:

  • 專案架構 : (我這裡無視 node_modules)
.
├── bun.lock
├── data.txt
├── index.ts
├── package.json
├── README.md
└── tsconfig.json

這是 data.txt 的內容

writefile_1

我們要把它複寫到 output.txt

這時候可以跑

bun index.ts

就會看到產生 output.txt 裡面的內如有 「我是一隻貓咪!喵🐈」

那這個跟 bun 有什麼關係?

Bunfile 與 一般 nodejs 處理上面的差異

BunFile 是懶載入的 Blob

解釋 : Bun 提供 Bun.file(path)會回傳一個物件叫做 BunFile
因為他是 lazy 所以 Bun.file() 摳它的當下不會真的去讀磁碟,

只有你實際呼叫讀取方法時才會發生 I/O

我們拿程式碼做個示範 - 並註解解釋

const file = Bun.file('data.txt'); // 這時候還不會讀檔案
file.size // 這個方法是抓檔案大小的(bytes)
file.type // 這會徵側 MIME Type (text/plain;charset=utf8)

因為 BunFile 是 webApi 的 Blob interface
所以讀取方式和瀏覽器的 File/Blob 物件方式一樣

以下常見方法

const file = Bun.file('data.json');
await file.text() // 讀成字串
await file.json() // 讀成json物件
await file.arrayBuffer() // 讀成ArrayBuffer
await file.bytes() // 讀成Uint8Array
await file.stream() // 讀成 ReadableStream

寫檔案: 在 Bun 的世界裡一招就可以

await Bun.write('output.txt', '這是包子貓咪🌭')

// 寫入 Uint8Array/ArrayBuffer 示範
const encoder = new TextEncoder();
await Bun.write('output.txt', encoder.encode('測試資料wow'));

// 把檔案複製到另一個檔案
await Bun.write('copy.txt', Bun.file('data.txt'));

// 弄出一張貓咪圖片
const res = await fetch('https://i.pinimg.com/736x/99/ef/5e/99ef5e2fe87e5918bbd9b6b223814c20.jpg');
await Bun.write('image.png', res);

複製出來

貓咪圖片

關於 Node fs 與 Bun 操作檔案的比較

  1. 統一心智模型
比較項目 敘述
nodejs nodejs 有一堆像是 readFile, writeFile, appendFile...etc
Bun Bun.file 以及瀏覽器常見的 webApi (Blob/File)
  1. 不用手動處理編碼
比較項目 敘述
nodejs 記得要寫 utf-8,忘記寫就會拿到 Buffer
Bun 可以用 .text(), .json() ...etc 轉成自己要的
  1. 效能 : Bun.write 是高度優化過

大檔案處理: FileSink 增量寫入

Bun 有 FileSink 的方法可以把檔案增量寫入

示範 :

const file = Bun.file('output.txt');
const writer = file.writer();
writer.write('報社貓咪!!\n');
writer.write('水果攤貓咪!!\n');
await writer.flush(); // 手動把緩衝區內容寫入磁碟

fileSink

補充 :

const writer = file.writer({ highWaterMark: 1024 * 1024 }) // 1MB

這個當緩衝區達到自訂大小時會自動 flush 的方法

結論

從讀檔到寫檔,Bun 用一組貼近 Web API 的介面,把 Node.js 裡分散的 fs 方法收斂成一個直覺的心智模型:Bun.file() 懶加載、按需讀取;Bun.write() 一行搞定字串、二進位、甚至是檔案對檔案的複製;再加上 FileSink 應付大檔案的增量寫入需求。
比起單純「少寫幾行程式碼」,這其實反映了 Bun 的設計哲學——盡量貼近瀏覽器已經很成熟的 Blob/File 標準,讓開發者不用在 Node.js 和前端之間切換兩套完全不同的檔案處理邏輯。對於習慣了 Web API 的前端工程師來說,這種一致性尤其友善。
如果你還在為 readFile 要不要加 'utf-8'、忘記編碼拿到 Buffer 而困擾,不妨找個小專案試試 Bun 的檔案操作,感受一下這種「所見即所得」的開發體驗。下一篇我們可以繼續深入 Bun 在其他 I/O 或 API 上的優化,敬請期待!


上一篇
Bun.serve():打造高效能 HTTP Server,一行程式碼搞定
下一篇
Bun File I/O:讀寫檔案與 AWS s3 完美整合
系列文
不只是快 —— Bun 30 天:從底層架構、全套工具鏈到生產部署10
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言