Node app on AWS returning 503 - node.js

I have an Hello World node app:
var express = require('express');
var app = express();
app.get('/', function (req, res) {
console.log('in the get /');
res.send('Hello World!');
});
app.listen(8080, function () {
console.log('Example app listening on port 8080!');
});
I've pushed this to my EC2 instance. I go to my url and the page is black. I see a 503 is coming back. Im seeing live Node logs and the app is going into app.get because I see 'in the get /' repeatedly.
I have 2 instances. The first is running Nginx and requests to example.net get redirected to https://www.example.net. I also have a Load Balancer listening which take requests to www.example.net and directing them to my Node instance.
Incidentally, every few seconds I see a new 'in the get /' line. So my app is getting hit repeatedly from God knows where. Could this be comething to do with getting 503 (which indicates server is busy)? Note: this worked fine yesterday.
EDIT
The app suddenly started returning "Hello World". I then restarted the app - making no code changes - and im back getting 503's again

The ELB is detecting that your instance is unhealthy because it's down during a restart (Unhealthy Threshold). Then it has to pass the health check a certain number of times before it is healty again (Healthy Threshold). You can configure all this in the ELB settings.
I would decrease the Unhealthy Threshold if you only have one instance in your pool. And possibly decrease the HealthCheck Interval as well.

Related

App.listen on an already running port of shared hosting

var express = require('express');
var app = express();
app.get("/", function(req,res){
console.log("running on that weird path i made///");
res.send("HELLO THIS IS A WEBPAGE TRYOUT!");
});
app.listen(3000, function(){
console.log("Server running on 3000");
})
I’m trying to create a simple app (for practice) which does a simple hello world. Using express via node.js
I can do it locally no problems.
The problem is I’m trying to run it on an existing server using cPanel shared hosting.
And there is obviously an already running domain name(and has website installed in Wordpress), so I cannot do a simple app.listen to a port which is obviously already running. And I’m guessing therefor I cannot do app.get(“/“....)
I’ve tried a different port-but the get request won’t work(I think obviously since that’s not the one running?)
So when I tell it to listen to the cPanel port, it throws an error that it’s already running.
And I don’t want to stop from the website to run. Is there a way to work this?
Tried also using subdomains. Same result.
Edit:
this worked on postman, when I've sent a get request to that address. tried port 3000, and it showed my res.send on the postman tab.
Edit2:
I've solved this...i forgot to put :3000 on the address..
as in www.example.com:3000
this doesn't work if i don't add the :3000.
and also if i do process.env.PORT and .IP..guessing its because its a shared hosting, or because wordpress is installed...
I won't delete just in case anyone did the same mistake as me.
If the problem that the port is already in use, you may try to use 0 as a port that will cause it to take a random free port on the machine.
const server = app.listen(0, function(){
console.log(`Server is listening on http://localhost:${server.address().port}`);
})

How to serve a nodeJS app via HTTPS on AWS EC2?

I'm trying to run a hello world express app on an EC2 instance and serve it via HTTPS.
Here is the server code:
var express = require('express');
var app = express();
app.get('/', function (req, res) {
res.send('Hello World!\n');
});
const server = app.listen(3000, function () {
console.log('Example app listening on port 3000!');
});
server.keepAliveTimeout = 65000; // Ensure all inactive connections are terminated by the ALB, by setting this a few seconds higher than the ALB idle timeout
server.headersTimeout = 66000; // Ensure the headersTimeout is set higher than the keepAliveTimeout due to this nodejs regression bug: https://github.com/nodejs/node/issues/27363
I created an EC2 instance and let it run there. Additionally to get HTTPS, I fired up an Application Load Balancer with an SSL certificate. I created a listener on port 443 and forwarded it to port 3000 on my EC2. Lastly I set up a Route53 entry to point to that ALB.
All I get 24/7 is 502 Bad Gateway. Am I missing something basic here?
How to run the most basic express server via HTTPS?
For anyone who might stumble upon this some time later:
If you wish to terminate HTTPS on the load balancer and speak HTTP to your app behind it you need to select HTTP as prototoll and the port of your node app when creating a target group in the console.
For some reason I thought for hours this should be HTTPS and 443 when I want to accept HTTPS traffic.

aws x-ray tracing breaks on outgoing requests in Node.js

Hey I'm trying to trace outgoing requests from an express app, but I can't get it to work.
When I dont use the AWSXRAY.captureHttpsGlobal function everything works fine with incoming requests and I can see my application in "Service Map" and my incoming request traces coming in on AWS, but I want to trace outgoing requests and as soon as I add AWSXRAY.captureHttpsGlobal then nothing works and I get no exception or anything, and my Daemon doesnt print the usual "Successfully sent batch of 1 segments (0.058 seconds)"
This is my code.
var AWSXRay = require('aws-xray-sdk');
const express = require("express");
var app = express();
app.use(AWSXRay.express.openSegment('MyApp'));
AWSXRay.captureHTTPsGlobal(require('https')); // works when i comment this out
var http = require('https');
app.get('/', function (req, res) {
http.get("https://google.com", (resp) => {
res.send("googlefetched")
});
//res.send("hello world")
});
app.use(AWSXRay.express.closeSegment());
app.listen(3000, () => console.log('Example app listening on port 3000!'))
could you share which node runtime version your code is running at and which X-Ray SDK version you are using so we can try to reproduce this issue on our side?
At the meantime I would like to share a previous issue that has been fixed since v1.2.0 https://github.com/aws/aws-xray-sdk-node/issues/18 where if the response body is not consumed then the entire segment will never be flushed to the daemon.
Please let me know.

Express JS route continues to execute endlessly

I am new to Express JS and Node in general, and I am having a slight problem here that I don't understand its reason.
So basically, this is my code for index.js:
const express = require('express')
const app = express();
app.get('/', (req, res) => {
console.log("Continuous message!");
res.send("Hello World");
});
app.listen(3000, () => console.log('Example app listening on port 3000!')
)
Everything works great except for one thing. In my console the message "Continuous message!" keeps showing up endlessly in my console. Am I doing anything wrong here? Or is this the normal behavior here?
Thank you!
Update: the reason turned out to be the redirection from port 80 to port 3000. So I edited server's site-available and the repetition no longer occurs. Question is now, how do I configure my AWS EC2 server to redirect traffic from port 80 to port 3000 without previous problem?
Update: I tried the EC2 Load Balancer and iptables commands. The problem is still there. Console messages and route code continues to execute every like 5 seconds. Which causes problems with my code flow.

Trying to run node app on fedora server

Ok I am making website and want to use mongo, express, etc. I setup a server using fedora server ISO. The problem is getting node working. I have followed several tutorials, and its all the same. Nothing works. So I have to be doing something wrong. Trying to get the simplest thing to display on screen.
I think the server is running httpd server, whatever fedora has built in. I get the default fedora server page when going to the url. So the server is running and working, just hasn't been configured. When running node on the server do I have to use httpd-node? Or can it be http, etc.
Here is my app.js
const express = require('express')
const app = express()
app.get('/', function (req, res) {
res.send('Hello World!')
})
app.listen(3000, function () {
console.log('Example app listening on port 3000!')
})
And then I have a basic index.html that should be rendered just saying test.
I ssh into the server and run node start, it runs and the console logs the message like it should. But if I go to the address 192.168.1.5, or the domain that points to the server, I get nothing, just a blank page.
If someone can help me get this working, I can actually get to work coding out the application. Any help would be appreciated.
I think you make a confusion. When you build an Express application, you do not need another server at all.
When you start your app with:
app.listen(3000, function () {})
Express returns an http.Server object listening to port 3000.
When you navigate to your local adress on port 3000, you will see your "hello world" message.
It is possible that httpd service is already running in your Fedora environnement on default port 80 (the default port for http, the one your reach when you go to your local adress) but this is an Apache server and you do not need it to run your Nodejs app.
To build a Nodejs server, you can also use httpd-node package, but this is redundant as you're using Express framework.
If you need to serve a simple html file, a method I like for its simplicity is to use ejs template engine, something like this.
res.send('Hello World!') - this is your problem! Why?
How you receive this answer on client side?
Solution: use res.render(..) - for rendering from server or use AJAX on client side for receive this text!
P.S: render page and you don't see blank page anymore! Or use client-server conversation logic with your server through AJAX.
Try 192.168.1.5:3000
If I wrong: show your full project setup...
Test your app with curl (https://curl.haxx.se)! Check connection establishment, and show results here!

Resources