Skip to content

Instantly share code, notes, and snippets.

@wardpeet
Created March 27, 2019 09:36
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save wardpeet/a50fc9af175d667c9a3eaf3a3f49dd9b to your computer and use it in GitHub Desktop.
Save wardpeet/a50fc9af175d667c9a3eaf3a3f49dd9b to your computer and use it in GitHub Desktop.
fs shim
const path = require(`path`)
const {
appendFileSync,
readFileSync,
renameSync,
existsSync,
unlinkSync,
} = require(`fs`)
const { ensureDirSync } = require(`fs-extra`)
const Configstore = require(`configstore`)
module.exports = class Store {
config;
fs = {
appendFileSync,
readFileSync,
renameSync,
existsSync,
unlinkSync,
ensureDirSync,
};
constructor() {
try {
this.config = new Configstore(`gatsby`, {}, { globalConfigPath: true })
} catch (e) {
this
// in case of some permission issues the configstore throws
// so fallback to a simple in memory config
this.config = {
get: key => this.config[key],
set: (key, value) => (this.config[key] = value),
all: this.config,
}
this.fs = {
store: [],
appendFileSync: (_, event) => fsShim.store.push(event)
readFileSync: () => fsShim.store.join('\n'),
renameSync: () => {},
existsSync: () => true,
unlinkSync: () => {},
};
}
}
getConfig(key) {
if (key) {
return this.config.get(key)
}
return this.config.all
}
updateConfig(...fields) {
this.config.set(...fields)
}
appendToBuffer(event) {
const bufferPath = this.getBufferFilePath()
try {
this.fs.appendFileSync(bufferPath, event, `utf8`)
} catch (e) {
//ignore
}
}
getBufferFilePath() {
const filePath = this.config.path
const parentFolder = path.dirname(filePath)
try {
this.fs.ensureDirSync(parentFolder)
} catch (e) {
//ignore
}
return path.join(parentFolder, `events.json`)
}
async startFlushEvents(flushOperation) {
const now = Date.now()
const filePath = this.getBufferFilePath()
try {
if (!this.fs.existsSync(filePath)) {
return
}
} catch (e) {
// ignore
return
}
const newPath = `${filePath}-${now}`
try {
this.fs.renameSync(filePath, newPath)
} catch (e) {
// ignore
return
}
let contents
try {
contents = this.fs.readFileSync(newPath, `utf8`)
this.fs.unlinkSync(newPath)
} catch (e) {
//ignore
return
}
// There is still a chance process dies while sending data and some events are lost
// This will be ok for now, however
let success = false
try {
success = await flushOperation(contents)
} catch (e) {
// ignore
} finally {
// if sending fails, we write the data back to the log
if (!success) {
this.appendToBuffer(contents)
}
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment