It was missleading, as the encoding was only for the upload stream, not the file contents when stored.
68 lines
1.6 KiB
JavaScript
68 lines
1.6 KiB
JavaScript
import fs from 'fs'
|
|
import promisesAll from 'promises-all'
|
|
import mkdirp from 'mkdirp'
|
|
import shortid from 'shortid'
|
|
import lowdb from 'lowdb'
|
|
import FileSync from 'lowdb/adapters/FileSync'
|
|
|
|
const UPLOAD_DIR = './uploads'
|
|
const db = lowdb(new FileSync('db.json'))
|
|
|
|
// Seed an empty DB
|
|
db.defaults({ uploads: [] }).write()
|
|
|
|
// Ensure upload directory exists
|
|
mkdirp.sync(UPLOAD_DIR)
|
|
|
|
const storeFS = ({ stream, filename }) => {
|
|
const id = shortid.generate()
|
|
const path = `${UPLOAD_DIR}/${id}-${filename}`
|
|
return new Promise((resolve, reject) =>
|
|
stream
|
|
.on('error', error => {
|
|
if (stream.truncated)
|
|
// Delete the truncated file
|
|
fs.unlinkSync(path)
|
|
reject(error)
|
|
})
|
|
.pipe(fs.createWriteStream(path))
|
|
.on('error', error => reject(error))
|
|
.on('finish', () => resolve({ id, path }))
|
|
)
|
|
}
|
|
|
|
const storeDB = file =>
|
|
db
|
|
.get('uploads')
|
|
.push(file)
|
|
.last()
|
|
.write()
|
|
|
|
const processUpload = async upload => {
|
|
const { stream, filename, mimetype } = await upload
|
|
const { id, path } = await storeFS({ stream, filename })
|
|
return storeDB({ id, filename, mimetype, path })
|
|
}
|
|
|
|
export default {
|
|
Query: {
|
|
uploads: () => db.get('uploads').value()
|
|
},
|
|
Mutation: {
|
|
singleUpload: (obj, { file }) => processUpload(file),
|
|
async multipleUpload(obj, { files }) {
|
|
const { resolve, reject } = await promisesAll.all(
|
|
files.map(processUpload)
|
|
)
|
|
|
|
if (reject.length)
|
|
reject.forEach(({ name, message }) =>
|
|
// eslint-disable-next-line no-console
|
|
console.error(`${name}: ${message}`)
|
|
)
|
|
|
|
return resolve
|
|
}
|
|
}
|
|
}
|