All files / PARSE/1-Discover NodeFileSystem.ts

100% Statements 24/24
100% Branches 4/4
100% Functions 12/12
100% Lines 24/24

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108                                                          4021x       402x       36755x       551x 2x   549x       1616x 86x   1530x       191x       29x       1x               49x 49x 49x 49x 49x   49x 49x               109x       96x 96x       30x               128x        
/**
 * NodeFileSystem
 * Default implementation of IFileSystem using Node.js fs module.
 *
 * This is the production implementation used when no mock is injected.
 */
 
import {
  readFileSync,
  writeFileSync,
  existsSync,
  statSync,
  mkdirSync,
  readdirSync,
  realpathSync,
  renameSync,
  unlinkSync,
  mkdtempSync,
  rmSync,
} from "node:fs";
import { tmpdir } from "node:os";
import { join } from "node:path";
import IFileSystem from "../../types/IFileSystem";
 
/**
 * Node.js file system implementation
 */
class NodeFileSystem implements IFileSystem {
  readFile(path: string): string {
    return readFileSync(path, "utf-8");
  }
 
  writeFile(path: string, content: string): void {
    writeFileSync(path, content, "utf-8");
  }
 
  exists(path: string): boolean {
    return existsSync(path);
  }
 
  isDirectory(path: string): boolean {
    if (!existsSync(path)) {
      return false;
    }
    return statSync(path).isDirectory();
  }
 
  isFile(path: string): boolean {
    if (!existsSync(path)) {
      return false;
    }
    return statSync(path).isFile();
  }
 
  mkdir(path: string, options?: { recursive?: boolean }): void {
    mkdirSync(path, options);
  }
 
  unlink(path: string): void {
    unlinkSync(path);
  }
 
  rename(from: string, to: string): void {
    renameSync(from, to);
  }
 
  async withTempFile<T>(
    name: string,
    content: string,
    use: (path: string) => Promise<T>,
  ): Promise<T> {
    const dir = mkdtempSync(join(tmpdir(), "cnext-"));
    try {
      const path = join(dir, name);
      writeFileSync(path, content, "utf-8");
      return await use(path);
    } finally {
      try {
        rmSync(dir, { recursive: true, force: true });
      } catch {
        // A directory we cannot remove is left for the OS to reclaim.
      }
    }
  }
 
  readdir(path: string): string[] {
    return readdirSync(path);
  }
 
  stat(path: string): { mtimeMs: number } {
    const stats = statSync(path);
    return { mtimeMs: stats.mtimeMs };
  }
 
  realpath(path: string): string {
    return realpathSync(path);
  }
 
  /**
   * Shared singleton instance for use across all modules. Built once, at
   * module load: it holds no state, and #1452 box 4 forbids a reassignable
   * static under a pass root, which the lazy slot it replaced was (#1444).
   */
  static readonly instance = new NodeFileSystem();
}
 
export default NodeFileSystem;