my express app worked perfectly when I tested it locally but when I uploaded it to vercel the static files didn't work. Here is what I did :
const exp = require('express')
// const { v4 } = require('uuid');
const app = exp()
app.use(exp.static('public'))
app.get('/', (req, res) => {
res.send(`<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<link rel="stylesheet" href="/coo.css">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Testing app</title>
</head>
<body>
<h1>testing testing from express</h1>
<script type="text/javascript" src="/ser.js"></script>
</body>
</html>`)
})
let port = process.env.PORT || 2000
app.listen(2000, () => console.log("running on http://localhost:2000"))
module.exports = app;
I also configured my vercel.json file and set the output directory:
{
"version": 2,
"builds": [
{
"src": "./app.js",
"use": "@vercel/node"
},
{
"src": "./public/*",
"use": "@vercel/static"
}
],
"routes": [
{
"src": "/(.*)",
"dest": "app.js"
}
],
"outputDirectory": "public"
}
so when I deployed there was no error in the build logs and the application was able to find the serverless function as well as the static file but it's not accessing them, here are some screen shots:
This is the expected outcome(when I ran it locally),
And this is actual outcome(when I uploaded to vercel),
And this is the deployment summary. Thanks for the help.
For express.static()
to work properly, three things must line up.
Your express.static()
usage must properly point to the root directory of your static files.
The actual target file must be in the right spot in your file system where express.static()
can find it.
The URLs you use in your web page that are supposed to reach these resources must be declared properly so that they turn into the right type of URL to match your express.static()
usage.
Let's look at each of these in the code you've shown us.
First, you have:
app.use(exp.static('public'));
That type of declaration will depend upon the current working directory when your app is launched because this will resolve to the equivalent of path.join(process.cwd(), 'public')
. If, for some reason, the current working directory was not the same as your project directory when your app runs on vercel, this could be a problem. If you intend for the public
directory to be right below your project directory, you could change this to:
app.use(exp.static(path.join(__dirname, 'public')));
And, this would remove a dependency on the current working directory in case that is difference on vercel.
Second, you need to verify that the target file which looks like it comes from this:
<script type="text/javascript" src="/ser.js"></script>
Is in the right place. That means you should have:
yourProject/public/ser.js
where yourProject is where your top level server JS file is located.
Third, your URL comes from that same script tag:
<script type="text/javascript" src="/ser.js"></script>
which is /ser.js
. This is an absolute URL and looks perfectly fine. It just has to match with a ser.js
file in the right location for express.static()
to find it.
You can debug further by adding this middleware as the first middleware in your app:
app.use((req, res, next) => {
console.log(`Incoming request for ${req.originalUrl}`);
next();
});
This will log all incoming requests and you can see if the request for /ser.js
is coming in as expected. If it is and you've made the change to app.use(exp.static(path.join(__dirname, 'public')));
, then the remaining fault is that the ser.js
file isn't in the right location on your vercel deployment.
And, you can look in the browser debug console and see if any errors are reported on that page. If ser.js
isn't being loaded, you should see an error in the browser console that tells you something about that.