NOTE
As APIs Bun.file e Bun.write documentadas nesta página são altamente otimizadas e representam a maneira recomendada de executar tarefas de sistema de arquivos usando o Bun. Para operações que ainda não estão disponíveis com Bun.file, como mkdir ou readdir, você pode usar a implementação quase completa do Bun do módulo node:fs.
Lendo arquivos (Bun.file())
Bun.file(path): BunFile
Crie uma instância BunFile com a função Bun.file(path). Um BunFile representa um arquivo carregado preguiçosamente; inicializá-lo não lê realmente o arquivo do disco.
const foo = Bun.file("foo.txt"); // relativo ao cwd
foo.size; // número de bytes
foo.type; // tipo MIMEA referência segue a interface Blob, então o conteúdo pode ser lido em vários formatos.
const foo = Bun.file("foo.txt");
await foo.text(); // conteúdo como string
await foo.json(); // conteúdo como objeto JSON
await foo.stream(); // conteúdo como ReadableStream
await foo.arrayBuffer(); // conteúdo como ArrayBuffer
await foo.bytes(); // conteúdo como Uint8ArrayReferências de arquivo também podem ser criadas usando descritores de arquivo numéricos ou URLs file://.
Bun.file(1234);
Bun.file(new URL(import.meta.url)); // referência ao arquivo atualUm BunFile pode apontar para um local no disco onde um arquivo não existe.
const notreal = Bun.file("notreal.txt");
notreal.size; // 0
notreal.type; // "text/plain;charset=utf-8"
const exists = await notreal.exists(); // falseO tipo MIME padrão é text/plain;charset=utf-8, mas pode ser sobrescrito passando um segundo argumento para Bun.file.
const notreal = Bun.file("notreal.json", { type: "application/json" });
notreal.type; // => "application/json;charset=utf-8"Por conveniência, o Bun expõe stdin, stdout e stderr como instâncias de BunFile.
Bun.stdin; // somente leitura
Bun.stdout;
Bun.stderr;Deletando arquivos (file.delete())
Você pode deletar um arquivo chamando a função .delete().
await Bun.file("logs.json").delete();Escrevendo arquivos (Bun.write())
Bun.write(destination, data): Promise<number>
A função Bun.write é uma ferramenta multiuso para escrever payloads de todos os tipos no disco.
O primeiro argumento é o destination que pode ter qualquer um dos seguintes tipos:
string: Um caminho para um local no sistema de arquivos. Use o módulo"path"para manipular caminhos.URL: Um descritorfile://.BunFile: Uma referência de arquivo.
O segundo argumento são os dados a serem escritos. Pode ser qualquer um dos seguintes:
stringBlob(incluindoBunFile)ArrayBufferouSharedArrayBufferTypedArray(Uint8Array, etc.)Response
Todas as permutações possíveis são tratadas usando as chamadas de sistema mais rápidas disponíveis na plataforma atual.
Ver syscalls
| Saída | Entrada | Chamada de sistema | Plataforma |
|---|---|---|---|
| arquivo | arquivo | copy_file_range | Linux |
| arquivo | pipe | sendfile | Linux |
| pipe | pipe | splice | Linux |
| terminal | arquivo | sendfile | Linux |
| terminal | terminal | sendfile | Linux |
| socket | arquivo ou pipe | sendfile (se http, não https) | Linux |
| arquivo (não existe) | arquivo (caminho) | clonefile | macOS |
| arquivo (existe) | arquivo | fcopyfile | macOS |
| arquivo | Blob ou string | write | macOS |
| arquivo | Blob ou string | write | Linux |
Para escrever uma string no disco:
const data = `It was the best of times, it was the worst of times.`;
await Bun.write("output.txt", data);Para copiar um arquivo para outro local no disco:
const input = Bun.file("input.txt");
const output = Bun.file("output.txt"); // ainda não existe!
await Bun.write(output, input);Para escrever um array de bytes no disco:
const encoder = new TextEncoder();
const data = encoder.encode("datadatadata"); // Uint8Array
await Bun.write("output.txt", data);Para escrever um arquivo para stdout:
const input = Bun.file("input.txt");
await Bun.write(Bun.stdout, input);Para escrever o corpo de uma resposta HTTP no disco:
const response = await fetch("https://bun.com");
await Bun.write("index.html", response);Escrita incremental com FileSink
O Bun fornece uma API nativa de escrita incremental de arquivos chamada FileSink. Para recuperar uma instância FileSink de um BunFile:
const file = Bun.file("output.txt");
const writer = file.writer();Para escrever incrementalmente no arquivo, chame .write().
const file = Bun.file("output.txt");
const writer = file.writer();
writer.write("it was the best of times\n");
writer.write("it was the worst of times\n");Estes chunks serão armazenados em buffer internamente. Para liberar o buffer para o disco, use .flush(). Isso retorna o número de bytes liberados.
writer.flush(); // escreve buffer para discoO buffer também será liberado automaticamente quando o high water mark do FileSink for atingido; isto é, quando seu buffer interno estiver cheio. Este valor pode ser configurado.
const file = Bun.file("output.txt");
const writer = file.writer({ highWaterMark: 1024 * 1024 }); // 1MBPara liberar o buffer e fechar o arquivo:
writer.end();Note que, por padrão, o processo bun permanecerá ativo até que este FileSink seja explicitamente fechado com .end(). Para desativar este comportamento, você pode "unref" a instância.
writer.unref();
// para "re-ref" mais tarde
writer.ref();Diretórios
A implementação do node:fs do Bun é rápida, e ainda não implementamos uma API específica do Bun para ler diretórios. Por enquanto, você deve usar node:fs para trabalhar com diretórios no Bun.
Lendo diretórios (readdir)
Para ler um diretório no Bun, use readdir de node:fs.
import { readdir } from "node:fs/promises";
// lê todos os arquivos no diretório atual
const files = await readdir(import.meta.dir);Lendo diretórios recursivamente
Para ler recursivamente um diretório no Bun, use readdir com recursive: true.
import { readdir } from "node:fs/promises";
// lê todos os arquivos no diretório atual, recursivamente
const files = await readdir("../", { recursive: true });Criando diretórios (mkdir)
Para criar recursivamente um diretório, use mkdir em node:fs:
import { mkdir } from "node:fs/promises";
await mkdir("path/to/dir", { recursive: true });Benchmarks
A seguir está uma implementação de 3 linhas do comando Linux cat.
// Uso
// bun ./cat.ts ./path-to-file
import { resolve } from "path";
const path = resolve(process.argv.at(-1));
await Bun.write(Bun.stdout, Bun.file(path));Para executar o arquivo:
bun ./cat.ts ./path-to-fileEle roda 2x mais rápido que o GNU cat para arquivos grandes no Linux.
Referência
interface Bun {
stdin: BunFile;
stdout: BunFile;
stderr: BunFile;
file(path: string | number | URL, options?: { type?: string }): BunFile;
write(
destination: string | number | BunFile | URL,
input: string | Blob | ArrayBuffer | SharedArrayBuffer | TypedArray | Response,
): Promise<number>;
}
interface BunFile {
readonly size: number;
readonly type: string;
text(): Promise<string>;
stream(): ReadableStream;
arrayBuffer(): Promise<ArrayBuffer>;
json(): Promise<any>;
writer(params: { highWaterMark?: number }): FileSink;
exists(): Promise<boolean>;
}
export interface FileSink {
write(chunk: string | ArrayBufferView | ArrayBuffer | SharedArrayBuffer): number;
flush(): number | Promise<number>;
end(error?: Error): number | Promise<number>;
start(options?: { highWaterMark?: number }): void;
ref(): void;
unref(): void;
}