Last active
February 8, 2024 17:52
-
-
Save maneetgoyal/c724e8e44ad3c04a6609eba740802e5a to your computer and use it in GitHub Desktop.
Multer Storage Engine in TypeScript
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { createWriteStream, unlink } from "fs"; | |
import type { PathLike } from "fs"; | |
import type { Request } from "express"; | |
type Maybe<T> = T | null | undefined; | |
type ResponseCallback<T> = (err: Error | null, payload?: Maybe<T>) => void; | |
type RequestHandler<T> = (req: Request, file: Express.Multer.File, responseCb: ResponseCallback<T>) => void; | |
/** | |
* Custom Multer Storage Engine for uploading file to AWS S3 | |
* Ref: https://github.com/expressjs/multer/blob/master/StorageEngine.md | |
* Example Usage: | |
* ```ts | |
* const storageEngine = new MulterS3StorageEngine((_req, file, responseCb) => { | |
* responseCb(null, `/var/www/uploads/${file.originalname}`); | |
* }); | |
* ``` | |
*/ | |
export class MulterS3StorageEngine { | |
/** | |
* Tells the engine where to save the file. | |
* @param _req | |
* @param _file | |
* @param responseCb | |
*/ | |
getDestination: RequestHandler<PathLike> = (_req, _file, responseCb) => { | |
responseCb(null, "/dev/null"); | |
}; | |
/** | |
* Stores the file and returns information on how to access the file in the future. | |
* The information you provide in the callback will be merged with multer's file object, and then presented to the user via `req.files`. | |
* @param req | |
* @param file | |
* @param responseCb | |
*/ | |
_handleFile: RequestHandler<unknown> = ( | |
req: Request, | |
file: Express.Multer.File, | |
responseCb: ResponseCallback<unknown> | |
) => { | |
this.getDestination(req, file, (err, path) => { | |
if (err !== null) { | |
responseCb(err); | |
} | |
if (path !== null && path !== undefined) { | |
const outStream = createWriteStream(path); | |
file.stream.pipe(outStream); | |
outStream.on("error", responseCb); | |
outStream.on("finish", () => { | |
responseCb(null, { path, size: outStream.bytesWritten }); | |
}); | |
} | |
}); | |
}; | |
/** | |
* Removes the file if an error is encounter during file stream handling. | |
* Multer will decide which files to delete and when. | |
* @param _req | |
* @param file | |
* @param responseCb | |
*/ | |
_removeFile: RequestHandler<unknown> = ( | |
_req: Request, | |
file: Express.Multer.File, | |
responseCb: ResponseCallback<unknown> | |
) => { | |
unlink(file.path, responseCb); | |
}; | |
constructor(destination?: RequestHandler<string>) { | |
this.getDestination = destination ?? this.getDestination; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment