Hey guys,
I have been having issues with my MERN project lately.One is that I keep getting 404 errors and the other is now I see a 502 Error when I visit my DO IP address.
Today I was making changes to my signup and login code. I noticed that I would get 404 errors when trying to test it out and I would also get the same errors in POSTMAN.
I decided to visit my Explore page and would get a GET request 404 error. Which was strange because this wasn’t happening yesterday.
Then in POSTMAN I did a GET request to /api/blog/posts
and to api/users/users
and I didn’t get a list of posts or users. Instead I saw the index.html from React.
I went to my DO IP address and would see the same 404 error in my Explore page.I then got rid of all of my changes for the day and that didn’t help.
After a couple a minutes I went back to my ip address and now see a 502 Gateway Error. I went back to POSTMAN to do GET request to /api/blog/posts
and to api/users/users
and now I see 502 Gateway Error
I’m not sure what the issue. If it’s NGINX, my code, or something else. I can’ do anything with my project now.
Any help would be appreciated.
NGINX
server {
listen 80 default_server;
listen [::]:80 default_server;
# SSL configuration
#
# listen 443 ssl default_server;
# listen [::]:443 ssl default_server;
#
# Note: You should disable gzip for SSL traffic.
# See: https://bugs.debian.org/773332
#
# Read up on ssl_ciphers to ensure a secure configuration.
# See: https://bugs.debian.org/765782
#
# Self signed certs generated by the ssl-cert package
# Don't use them in a production server!
#
# include snippets/snakeoil.conf;
root /var/www/*PROJECT NAME*/client/build/index.html;
# Add index.php to the list if you are using PHP
index index.html index.htm index.nginx-debian.html;
server_name *DO IP ADDRESS*;
location ^~ /assets/ {
gzip_static on;
expires 12h;
add_header Cache-Control public;
}
location / {
proxy_http_version 1.1;
proxy_cache_bypass $http_upgrade;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_pass http://localhost:3000;
client_max_body_size 50M;
}
location = /favicon.ico {
log_not_found off;
}
}
server.js
require('dotenv').config()
const path = require("path")
const express = require('express')
const mongoose = require('mongoose')
const cookieParser = require('cookie-parser')
const app = express()
const blogAPI = require('./api/blogApi')
const auth = require('./api/auth')
const users = require('./api/users')
_/* Connect to Database */_
mongoose.connect(process.env.DBURI, {
useNewUrlParser: true,
useUnifiedTopology: true
}).then(() => console.log('MongoDB connected...'))
.catch(err => console.log(err))
app.use(cookieParser())
_/* POST form handling */_
app.use(express.json());
app.use(express.urlencoded({ extended: true }));
_/* Routing */_
app.use('/api/blog', blogAPI)
app.use('/api/auth', auth)
app.use('/api/users', users)
app.use('/public', express.static(path.join(__dirname, 'public')))
// Display React in production
app.use(express.static(path.join(__dirname, '/../client', 'build')))
app.get('*', function (req, res) {
res.sendFile(path.join(__dirname, '/../client', 'build', 'index.html'))
});
app.listen(process.env.PORT, () => console.log("Server started!"))
module.exports = app;
PostController
class PostService {
_// list_
_static_ list() {
return Post.find({})
.then((posts) => {
return posts
})
}
}
API
_/* CORS */_
const corsOptions = {
origin: `${process.env.FRONTEND}`,
methods: "GET,HEAD,PUT,PATCH,POST,DELETE",
credentials: true,
preflightContinue: false,
optionsSuccessStatus: 204
}
router.use(cors(corsOptions))
_/* Start of Routing */_
_/* Code associated with blog posts */_
_// list_
router.get('/posts', (req, res, next) => {
PostService.list()
.then((posts) => {
res.status(200)
res.json(posts)
})
})
interceptor.js
const axiosPrivate = axios.create({
baseURL: `${process.env.REACT_APP_URL}/api`
});
Explore Page
useEffect(() => {
const fetchPosts = _async_ () => {
try {
let response = await axiosPrivate.get('/blog/posts')
setPostsLoaded(response.data)
setLatestPosts(response.data.slice(-5))
setShowLatestPosts(true)
} catch (error) {
console.log(error);
}
}
fetchPosts()
}, [])
This textbox defaults to using Markdown to format your answer.
You can type !ref in this text area to quickly search our full set of tutorials, documentation & marketplace offerings and insert the link!
These answers are provided by our Community. If you find them useful, show some love by clicking the heart. If you run into issues leave a comment, or add your own answer to help others.
Hi there,
There are a few things that I could suggest here:
The 404 errors
This might be happening because the React app is not able to route the API requests correctly, and it’s serving the React app’s
index.html
instead of the actual API response. What you could do here is to update thelocation /
block in your NGINX configuration to the following:That way the React app will be served from the
/
location and the Node.js API will be served from the/api
location.The 502 Gateway Error
This could be because your Node.js server is not running or it’s crashing due to an error. Make sure your server is running and check the logs for any error messages. You can start with the following:
tail -100 /var/log/nginx/error.log
root
directive should point to the directory, not the file. eg:process.env.REACT_APP_URL
variable in theinterceptor.js
file has the correct value. It should point to your DigitalOcean Droplet’s IP address or your domain name with the appropriate protocol (http or https).Let me know how it goes after those changes!
As a side note, keep in mind that once you make a change to the Node.js project and the Nginx configuration you need to restart them. A good practice is to run
nginx -t
before restarting Nginx to make sure that there are no configuration errors.Best,
Bobby