@firesystem/memory
TypeScript icon, indicating that this package has built-in type declarations

1.1.5 • Public • Published

@firesystem/memory

In-memory implementation of the Virtual File System (VFS) interface. Perfect for testing, prototyping, and scenarios where you need a temporary file system that lives only in memory.

Features

  • 🚀 Lightning Fast - All operations happen in memory
  • 🧪 Perfect for Testing - No disk I/O, fully deterministic
  • 💾 Zero Persistence - Data cleared on process exit
  • 🔄 Full VFS API - Implements complete @firesystem/core interface
  • 📦 Lightweight - Minimal overhead, no dependencies
  • 🔌 Workspace Ready - Optional integration with @workspace-fs/core
  • Native Events - Built-in reactive event system for all operations
  • 📊 Progress Tracking - Monitor initialization and batch operations
  • 🔔 Real-time Updates - Get notified of all file system changes

Installation

npm install @firesystem/memory
# or
yarn add @firesystem/memory
# or
pnpm add @firesystem/memory

Usage

import { MemoryFileSystem } from "@firesystem/memory";

// Create a new in-memory file system
const fs = new MemoryFileSystem();

// Use it like any other VFS implementation
await fs.writeFile("/hello.txt", "Hello, World!");
const file = await fs.readFile("/hello.txt");
console.log(file.content); // "Hello, World!"

// NEW: Native event support
fs.events.on("file:written", ({ path, size }) => {
  console.log(`File ${path} written (${size} bytes)`);
});

// Perfect for testing
describe("My App", () => {
  let fs: MemoryFileSystem;

  beforeEach(() => {
    fs = new MemoryFileSystem(); // Fresh instance for each test
  });

  it("should save user data", async () => {
    await saveUserData(fs, { name: "John" });
    const file = await fs.readFile("/users/john.json");
    expect(file.content.name).toBe("John");
  });
});

Event System

MemoryFileSystem now includes a native event system that emits events for all operations:

Basic Events

import { MemoryFileSystem, FileSystemEvents } from "@firesystem/memory";

const fs = new MemoryFileSystem();

// Listen to file operations
fs.events.on(FileSystemEvents.FILE_WRITTEN, ({ path, size }) => {
  console.log(`File written: ${path} (${size} bytes)`);
});

fs.events.on(FileSystemEvents.FILE_DELETED, ({ path }) => {
  console.log(`File deleted: ${path}`);
});

// Listen to directory operations
fs.events.on(FileSystemEvents.DIR_CREATED, ({ path }) => {
  console.log(`Directory created: ${path}`);
});

// Operation tracking
fs.events.on(FileSystemEvents.OPERATION_START, ({ operation, path }) => {
  console.log(`Starting ${operation} on ${path}`);
});

fs.events.on(FileSystemEvents.OPERATION_END, ({ operation, duration }) => {
  console.log(`${operation} completed in ${duration}ms`);
});

Initialization with Progress

const fs = new MemoryFileSystem({
  initialFiles: [
    { path: "/file1.txt", type: "file", content: "Hello" },
    { path: "/file2.txt", type: "file", content: "World" },
    { path: "/docs", type: "directory" },
    { path: "/docs/readme.md", type: "file", content: "# Docs" },
  ],
});

// Track initialization progress
fs.events.on(FileSystemEvents.INIT_PROGRESS, ({ loaded, total }) => {
  console.log(`Loading: ${loaded}/${total} files`);
});

// Get notified of each file during initialization
fs.events.on(FileSystemEvents.FILE_READ, ({ path, size }) => {
  console.log(`Loaded file: ${path}`);
});

// Initialize and load all files
await fs.initialize();

Integration with State Management

// Example with Zustand
import { create } from 'zustand';

const useFileStore = create((set) => ({
  files: [],

  initializeFS: async () => {
    const fs = new MemoryFileSystem({ initialFiles: [...] });

    // Listen to files being loaded during initialization
    fs.events.on(FileSystemEvents.FILE_READ, ({ path, size }) => {
      set(state => ({
        files: [...state.files, { path, size }]
      }));
    });

    // Listen to future changes
    fs.events.on(FileSystemEvents.FILE_WRITTEN, ({ path }) => {
      // Update state when files change
    });

    // Initialize and populate state
    await fs.initialize();
  }
}));

Workspace Integration

MemoryFileSystem can be integrated with @workspace-fs/core through the MemoryWorkspaceProvider:

Standalone Usage (Default)

import { MemoryFileSystem } from "@firesystem/memory";

// Use directly without workspace
const fs = new MemoryFileSystem();
await fs.writeFile("/test.txt", "Hello World");

With Workspace

import { WorkspaceFileSystem } from "@workspace-fs/core";
import { memoryProvider } from "@firesystem/memory/provider";

// Register the provider
const workspace = new WorkspaceFileSystem();
workspace.registerProvider(memoryProvider);

// Create memory-based projects
const project = await workspace.loadProject({
  id: "temp-project",
  name: "Temporary Project",
  source: {
    type: "memory",
    config: {
      initialData: {
        "/README.md": "# My Project",
        "/src/index.js": "console.log('Hello');",
        "/package.json": {
          content: JSON.stringify({ name: "my-project" }, null, 2),
          metadata: { description: "Package manifest" },
        },
      },
    },
  },
});

// Work with the project
await workspace.writeFile("/src/utils.js", "export const helper = () => {};");

Provider Configuration

The memory provider accepts the following configuration:

interface MemoryProviderConfig {
  // Initial files to populate
  initialData?: {
    [path: string]:
      | string
      | {
          content: any;
          metadata?: Record<string, any>;
        };
  };

  // Maximum storage size (future feature)
  maxSize?: number;
}

Use Cases

1. Testing

import { MemoryFileSystem } from "@firesystem/memory";
import { MyApp } from "./my-app";

test("file operations", async () => {
  const fs = new MemoryFileSystem();
  const app = new MyApp(fs);

  await app.saveConfig({ theme: "dark" });

  const config = await fs.readFile("/config.json");
  expect(config.content.theme).toBe("dark");
});

2. Temporary Processing

const fs = new MemoryFileSystem();

// Process files without touching disk
await fs.writeFile("/input.csv", csvData);
await processCSV(fs, "/input.csv", "/output.json");
const result = await fs.readFile("/output.json");

3. Prototyping

// Quickly prototype without setting up real storage
const fs = new MemoryFileSystem();
const cms = new SimpleCMS(fs);

await cms.createPost({
  title: "Hello World",
  content: "My first post",
});

Memory Management

The memory file system stores all data in JavaScript objects. Be mindful of memory usage when working with large files:

const fs = new MemoryFileSystem();

// Monitor storage size with events
fs.events.on(FileSystemEvents.STORAGE_SIZE_CALCULATED, ({ size }) => {
  console.log(`Storage size: ${size} bytes`);
});

// Check total size
const size = await fs.size();
console.log(`Using ${size} bytes`);

// Clear all data with progress tracking
fs.events.on(FileSystemEvents.STORAGE_CLEARING, () => {
  console.log("Clearing storage...");
});

fs.events.on(FileSystemEvents.STORAGE_CLEARED, ({ duration }) => {
  console.log(`Storage cleared in ${duration}ms`);
});

await fs.clear();

Constructor Options

interface MemoryFileSystemOptions {
  initialFiles?: Array<{
    path: string;
    type: "file" | "directory";
    content?: any;
    size?: number;
    created?: Date;
    modified?: Date;
    metadata?: Record<string, any>;
  }>;
}

// Example with initial files
const fs = new MemoryFileSystem({
  initialFiles: [
    { path: "/config.json", type: "file", content: { theme: "dark" } },
    { path: "/data", type: "directory" },
    { path: "/data/users.json", type: "file", content: [] },
  ],
});

API Reference

See @firesystem/core for the complete VFS API documentation.

License

MIT © Anderson D. Rosa

Package Sidebar

Install

npm i @firesystem/memory

Weekly Downloads

3

Version

1.1.5

License

MIT

Unpacked Size

148 kB

Total Files

14

Last publish

Collaborators

  • andersondrosa