Node.js FS模塊方法速查

1. File System

  • 所有文件操作提供同步異步的兩種方式,本筆記只記錄異步的API
  • 異步方式其最後一個參數是回調函數。回調函數的第一個參數往往是錯誤對象,如果沒有發生參數,那麼第一個參數可能是null或者undefinded
  • 同步函數可以使用try catch 捕獲異常
  • 多個異步函數在同一層次執行,是無法保證順序的。最好將一個函數放在另一個函數的回調函數中去執行。這種回調的嵌套層次一旦過深,就會造成回調地獄
  • 一般情況下,非常不建議使用同步的fs方法,因爲同步的方法會阻斷其他事情,直到fs方法完成。

1.1. 文件路徑

  • filepaths目前支持4中

    • string
    • Buffer
    • URL Object
    • file:開頭的協議
  • string 路徑會被解釋爲utf-8格式,可以使用相對路徑和絕對路徑,相對路徑是當前工作路徑,可以從process.cwd()獲取當前工作路徑。

1.2. 文件描述符

  • 操作系統會限制文件描述符的數量
  • 忘記關閉文件可能導致內存泄露或者程序崩潰
  • 任何文件描述符都支持寫操作
  • 如果文件描述符的類型是文件,那麼它不會自動關閉
  • 寫操作會從文件的開頭,而不會覆蓋之後的內容。舉例:文件內容是Hello World, 如果在寫入'Aloha',那麼文件的內容是Aloha World ,而不是'Aloha'.

1.3. 線程池使用

fs所有的api,除了那些同步的api和fs.FSWatcher(), 基本上都使用libuv的線程池。在有些應用程序上,這個可能導致非常糟糕的性能表現。libuv的線程池有固定的大小,默認只有4個,可以通過設置環境變量UV_THREADPOOL_SIZE去增加libuv的線程的數量。

1.4. Class: fs.Dirent 判斷文件類型

  • fs.readdir()或者fs.readdirSync()被調用,並且參數withFileTypestrue, 那麼返回結果就是fs.Dirent objects, 而不是strings or Buffers
  • dirent方法

    • dirent.isBlockDevice()
    • dirent.isCharacterDevice()
    • dirent.isDirectory()
    • dirent.isFIFO()
    • dirent.isFile()
    • dirent.isSocket()
    • dirent.isSymbolicLink()
    • dirent.name

1.5. Class: fs.FSWatcher 文件變動監控

來自 fs.watch()

  • Event

    • change
    • close
    • error
  • watcher.close()

注意:某些系統可能不會返回filename。如果encoding參數是buffer,那麼文件名是以buffer的形式返回,默認文件名是utf-8格式的字符串。

fs.watch('./tmp', { encoding: 'buffer' }, (eventType, filename) => {
  if (filename) {
    console.log(filename);
    // Prints: <Buffer ...>
  }
});

1.6. Class: fs.ReadStream 可讀流

來自fs.createReadStream()

  • Event

    • close
    • open
    • ready 第一次觸發是在open事件之後
  • readStream.bytesRead
  • readStream.path
  • readStream.pending

1.7. Class: fs.Stats 獲取文件信息

來自 fs.stat(), fs.lstat() and fs.fstat() 以及他們的同步版本。

  • stats.isBlockDevice()
  • stats.isCharacterDevice()
  • stats.isDirectory()
  • stats.isFIFO()
  • stats.isFile()
  • stats.isSocket()
  • stats.isSymbolicLink()
Stats {
  dev: 2114,
  ino: 48064969,
  mode: 33188,
  nlink: 1,
  uid: 85,
  gid: 100,
  rdev: 0,
  size: 527,
  blksize: 4096,
  blocks: 8,
  atimeMs: 1318289051000.1,
  mtimeMs: 1318289051000.1,
  ctimeMs: 1318289051000.1,
  birthtimeMs: 1318289051000.1,
  atime: Mon, 10 Oct 2011 23:24:11 GMT,
  mtime: Mon, 10 Oct 2011 23:24:11 GMT,
  ctime: Mon, 10 Oct 2011 23:24:11 GMT,
  birthtime: Mon, 10 Oct 2011 23:24:11 GMT }

1.8. Class: fs.WriteStream 可寫流

  • Event

    • close
    • open
    • ready
  • writeStream.bytesWritten
  • writeStream.path
  • writeStream.pending

2. 常用方法

  • 測試

    • 訪問權限測試 fs.access(path[, mode], callback) 測試是否可以訪問某個路徑。不建議fs.open(), fs.readFile() or fs.writeFile()調用前,調用fs.access去檢查
    • 測試路徑是否存在 fs.exists(path, callback), 不建議fs.open(), fs.readFile() or fs.writeFile()調用前,調用fs.exists去檢測文件是否存在
  • 流操作

    • 創建可讀流 fs.createReadStream(path[, options])
    • 創建可寫流 fs.createWriteStream(path[, options])
  • 文件夾操作

    • 創建文件夾 fs.mkdir(path[, options], callback)
    • 刪除目錄 fs.rmdir(path, callback)
    • 創建臨時文件夾 fs.mkdtemp(prefix[, options], callback)
    • 讀取文件夾 fs.readdir(path[, options], callback)
  • 文件操作

    • 打開文件 fs.open(path[, flags[, mode]], callback)
    • 讀取文件 fs.read(fd, buffer, offset, length, position, callback)
    • 讀取文件 fs.readFile(path[, options], callback)
    • 重命名文件 fs.rename(oldPath, newPath, callback)
    • 讀取文件信息 fs.stat(path[, options], callback)
    • 刪除文件 fs.unlink(path, callback)
    • 停止監控文件 fs.unwatchFile(filename[, listener])
    • 修改時間 fs.utimes(path, atime, mtime, callback)
    • 監控文件變化 fs.watch(filename, options)
    • 關閉文件 fs.close(fd, callback)
    • 追加文件 fs.appendFile(path, data[, options], callback)
    • 改變文件模式 fs.chmod(path, mode, callback)
    • 改變文件所屬 fs.chown(path, uid, gid, callback)
    • 複製文件 fs.copyFile(fs.copyFile(src, dest[, flags], callback))
    • 寫文件 fs.write(fd, buffer[, offset[, length[, position]]], callback)
    • 寫文件 fs.write(fd, string[, position[, encoding]], callback)
    • 寫文件 fs.writeFile(file, data[, options], callback)
  • 其他

    • fs常量 fs.constants
  • 注意事項

    • fs.watch並不是百分百跨平臺。例如它的recursive參數僅支持macOS和windows。fs.watch的底層通知機制在不同平臺上的實現是不同的,如果底層不支持某個特性,那麼fs.watch也是不能支持的。另外回調函數中的filename參數,也是不保證一定存在。
    • fs.watch()fs.watchFile()更高效,可能的話,儘量使用前者。

3. 參考

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章