I have a full web application using NodeJS, MongoDB (Mongoose as the driver) and ExpressJS.
The project works perfectly on my local machine. Today I decided to move everything to production. I'm using Google App Engine to host my application, and Compose (formally MongoHQ) to host my database.
App Engine servers my application perfectly, although my API does not seem to work. My API is served from example.com/api
, and each request (GET
, POST
, DELETE
and PUT
) all returns a 502 (Bad Gateway) error.
I tried running my application on my local machine while connected to my remote MongoDB database and that worked perfectly fine. So it must be a problem with App Engine or NodeJS, not with MongoDB.
I have tried checking all error logs within Google Cloud, although there are no errors.
Why is App Engine/NodeJS serving my application's static content perfectly fine, although not allowing any requests to my API?
The 502 (Bad Gateway) status code indicates that the server, while acting as a gateway or proxy, received an invalid response from an inbound server it accessed while attempting to fulfill the request. Every time you visit a website your browser sends a request to a web server.
Clear your browser's cache. Outdated or corrupted files that are being stored by your browser could be causing 502 Bad Gateway issues. Clearing the Cache in Edge. Removing those cached files and trying the page again will solve the problem if this is the cause.
Clear Your Browser's Cache and Cookies If trying a different browser works, it's possible that your main browser has cached outdated or corrupt files that might be causing the 502 error. Removing these cached files and trying to open the website could solve the problem.
just make sure that your server listens on 8080 port https://cloud.google.com/appengine/docs/flexible/custom-runtimes/build#listen_to_port_8080
502 Bad Gateway is usually an error on the Nginx side. Unfortunately those logs are not surfaced to Cloud Logging, yet.
A lot of times the problem is that your HTTP packets are too big for the buffers or something similar. The way you can see the nginx log is something like this:
manual_scaling:
instances: 1
then re-deploy
Switch the VM from "Google owned" to self-managed. This can be done in the Cloud Console. Go to Compute Engine, instances, click on the instance name that matches the App Engine version, and you should see an option to switch it to self-managed.
gcloud compute ssh <instance name>
to SSH to the machine
docker ps
to see your running containers. Look for the container named nginx and grab its id.
Once you have a container ID, you should be able to docker exec -it <container id> -- cat /var/log/nginx/error.log
. You might want to ls
that whole log directory.
You will likely see an error there which will be a bigger hint as to what's going wrong.
I know this is way more complicated than it should be :-\ If you have any problems with the steps above, leave a comment. If you do find an error and you're not sure what to do with it, also leave a comment.
I had the same problem, I was getting "nginx 502 bad gateway" error on GAE standard environment. There are many reasons for this but I finally got it working. Try these:
1) Run the app on the correct port. Google will set the PORT
environment variable. I was running on port 8080, in the stackdriver logs I was getting this warning:
App is listening on port 8080. We recommend your app listen on the port defined by the PORT environment variable to take advantage of an NGINX layer on port 8080.
The code below gets the port from environment, if PORT
is set otherwise defaults to 8080:
const PORT = process.env.PORT || 8080;
2) Go to google cloud console -> logging -> logs viewer
. Select Google App Engine
and then your service from the down and check you logs. Are you getting the requests at all or does it look like the requests do not react to your server. In my case, I was not getting them even after I fixed the port:
2020-03-02 21:50:07 backend[20200302t232314] Server listening on port 8081! 2020-03-02 21:50:08 backend[20200302t232314] "GET /create-user HTTP/1.1" 502
Fix any error if it looks like your application is failing to start, throwing exceptions etc..
3) Don't pass an IP when you are running your server. It seems Google runs the app at a pre-defined IP address and do not want you to modify it:
server.listen(PORT);
4) Don't try to run on https! Google is running an nginx server in front of your app and it is handling the SSL and redirects to your app over http. You can use the environment variable NODE_ENV
(it is set to "production" in GAE environment) to run on http on production and https elsewhere, like this:
let https = require('https');
let http = require('http');
if (process.env.NODE_ENV == "production") {
http.createServer(app).listen(PORT, function () {
console.log(`Server listening on port ${PORT}!`)
});
} else {
https.createServer({
key: fs.readFileSync('host.key'),
cert: fs.readFileSync('host.cert')
}, app).listen(PORT, function () {
console.log(`Server listening on port ${PORT}!`)
});
}
5) I didn't need to set any handlers in my yaml file, it might be causing errors for you if you have incorrect configuration. My yaml file is pretty straightforward:
runtime: nodejs12
env: standard
instance_class: F1
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With