Using Multer and Express to upload and display files - node.js

I'm using multer to upload images with express and node from a form, however all the files names come out like "8f92a1388f70c6c88eb32489f6bcfcc9". There isn't even an extension attached. How to I display this on the client side?

try:
var storage = multer.diskStorage({
destination: function (req, file, cb) {
cb(null, '/where/ever/the/upload/dir/is')
},
filename: function (req, file, cb) {
cb(null, file.orignalname)
}
})
var upload = multer({ storage: storage })
Instead of:
var upload = multer({ dest: 'uploads/' })
Requesting the file:
With the proper permissions set on the file/or directory your server should be able to request it fine, remember to explicitly write the file name with an extension if you aren't doing anything fancy after the file is written ;)
If you want more control over your uploads, you'll want to use the
storage option instead of dest. Multer ships with storage engines
DiskStorage and MemoryStorage; More engines are available from third
parties.
--The Horse
(ref: github: expressjs/multer)
Note: Multer will not append any file extension for you, your function should return a filename complete with an file extension

Related

Directory folder to store document

I am trying to make document management project using nodejs,mongodb and react. I want to make directory folder that will store document and the sub is it file. But I could not find any reference that I could use to start making the directory. Is there any specific term that I should search to get any reference to start the project? Thank you.
You can use Multer library for file uploads. It's super easy to use.
import multer from 'multer';
//specify where you want your files to be stored
var fileStorageEngine = multer.diskStorage({
destination: function (req, file, cb) {
cb(null, './images')
},
filename: function (req, file, cb) {
cb(null, Date.now() + '--' + file.originalname)
}
})
var upload = multer({ storage: fileStorageEngine });
//pass it as a middleware to a route where you expect to get a file upload
app.use('/api/file/', upload.single('image'), someRouterHere);

Node.js does multer with diskStorage create a folder if it doesn't exist?

I have a small app that receives via POST a file and stores it in a specific folder.
I know that this line:
const multer = multer({ dest: ‘media' })
(of course with some more code, where I use the multer.single('somefilename')) will create a new folder named media if it doesn't exist already.
But I want to be able to control the name given to the file and some other stuff, so I'm using it with diskStorage instead:
const x = multer.diskStorage({
destination: function (req, file, cb) {
cb(null, 'media')
},
filename: function (req, file, cb) {
cb(null, file.originalname);
}
})
const multer = multer({ storage: x })
(there's some more code of course with multer.single('somefilename'))
It works fine when the folder 'media' already exists, but doesn't create it if it doesn't - is it supposed to, or only the simpler multer can do that?
Thanks in advance!
It won't create the folder, they warn that in the official doc:
Note: You are responsible for creating the directory when providing
destination as a function. When passing a string, multer will make
sure that the directory is created for you.
Below is an example of how to create the entire path, but exist many alternatives:
const path = require("path");
const shell = require('shelljs');
const fullPath = path.join(__dirname, '..', '..', "uploads");
shell.mkdir('-p', fullPath);
As #robertklep suggest, please consider: fs.mkdir() instead of shell:
fs.mkdir(path.join(__dirname, 'test'), { recursive: true })

Upload Images to Web Server directory using Multer [Nodejs]

I am upload images using multer and Nodejs. The upload works perfectly. The problem is I want to upload those images directly to a folder inside wwwroot folder of the IIS Webserver.
var Storage = multer.diskStorage({
destination: function (req, file, callback) {
// callback(null, "../grit-server/uploads/");
callback(null, "https://example.com/grit/images/photogallery/");
},
filename: function (req, file, callback) {
const sqc = sqlConn;
var fileNames = (file.originalname.split('_'))
let query = 'INSERT INTO dbo.MS_PhotoGallery (MinorId,Photo_Name) VALUES (#MinorId,#PhotoName)'
let params = [
sqc.paramize('MinorId', fileNames[1], sql.Int()),
sqc.paramize('PhotoName',fileNames[2], sql.VarChar(255))
]
sqc.SqlExecuteStatementCallback(
query,params,(result)=>{
res.send(result)
}
)
callback(null, file.originalname);
}
});
The above code is of the Multer storage where I am setting the URL where to upload the images. But it is throwing error
'Error [ERR_HTTP_HEADERS_SENT]: Cannot set headers after they are sent to the client'
What modifications shall I do to upload the images in the URL mentioned under Storage to save any photos in the location.
I have solved this problem hardcoding the path like '../../../../wwwroot/abc/def/'. This is not the efficient way but it works for my specific problem as the images folder is not going to change in future.

Heroku | Cannot GET

I deployed an API to heroku. One of its functions is file uploading. I made a static folder called "uploads" and upload files using multer package.
app.use('/api/uploads', uploadRouter);
app.use('/uploads', express.static(path.join(__dirname, '/uploads')));
Above code snippet comes from server.js. Below is the router and multer setup.
const storage = multer.diskStorage({
destination(req, file, cb) {
cb(null, 'uploads/');
},
filename(req, file, cb) {
cb(null, `${Date.now()}.jpg`);
},
});
const upload = multer({ storage });
uploadRouter.post('/', upload.single('image'), (req, res) => {
res.send(`https://app.herokuapp.com/${req.file.path}`);
});
uploadRouter.post('/imgs', upload.array('images'), (req, res) => {
try{
let filesArray = [];
req.files.forEach(file => {
filesArray.push(`https://app.herokuapp.com/${file.path}`)
})
res.status(201).send(filesArray);
}catch(error) {
res.status(400).send(error.message);
}
});
Something tells me that my approach is far from an ideal one. However, it used to work just perfect until I introduced multiple file upload. Now, images after being uploaded stay there for a little bit (I can access them via links like https://app.herokuapp.com/uploads/1623782012131.jpg) and disappear over few minutes. Then, these URLs throw the following:
Cannot GET /uploads/1623782012131.jpg
The thing is that my previous images that I uploaded before introducing multiple file upload are still accessible. I thought it had to do with heroku file size limitations but it was not the case since I've only used about 50mb out of 500mb. What might be the reason?
Heroku's filesystem is ephemeral/short lived. This means that any images you save on the disk will disappear after you restart or deploy your app. You can't rely on Heroku's filesystem to store images that need to persist for a longer time. Read more here: https://help.heroku.com/K1PPS2WM/why-are-my-file-uploads-missing-deleted
For a reliable image storage, have a look at cloud storage solutions such as Cloudinary or AWS S3.

Node js store images into external server

I am developing one web application in which server is stored in different Azure server and front-end is also stored in different one.
When I try to use multer in node js to store URL to front-end server it always returns that path is not found.when I saw the error log it I found this
Error: ENOENT: no such file or directory, open
'D:\home\site\wwwroot\http:\nomadiccare-portal.azurewebsites.net\images\undefined.png'
at Error (native)
Here is my source code for node js which is working perfectly on localhost.
var uploadImageURL="http://nomadiccare-portal.azurewebsites.net/images/";
var currentClientId;
var storage = multer.diskStorage({
destination: function (request, file, callback) {
callback(null, uploadImageURL);
},
filename: function (request, file, callback){
console.log("It Is In"+file);
callback(null,currentClientId+".png");
}
});
var upload = multer({ storage: storage });
How can I remove D:\home\site\wwwroot\ from URL?
destination of DiskStorage is used to determine within which folder the uploaded files should be stored. It must be the path of the disk rather than a URL of the website.
If the other server has a post route to upload a file, you can make a post request with the file data from your server after you saved the file successfully. Refer to this you can learn how to send HTTP post request from a server to another server with data in Node.js.
var storage = multer.diskStorage({
destination: uploadImageURL, // change here
filename: function (request, file, callback) {
console.log('It Is In' + file)
callback(null, currentClientId + '.png')
}
})

Resources