Node Http server - request received twice - node.js

I am learning Node.js and I have created this simple http server.
var http = require('http');
var server = http.createServer(function(req,res){
console.log('request accepted');
res.end();
});
server.listen(3000,function(){
console.log("Server listening on port #3000");
});
It is working fine but when I visit http://localhost:3000/ the console logs request accepted thing twice. In short, if I'm understanding correctly, the request is received twice.
Is it a correct behavior or am I doing something wrong here?

Your browser makes two HTTP requests. One for the page at / and the other for /favicon.ico.
You can prove this by inspecting req.url.

you can try to put your favicon as a data64 string so you will save that request, anyway some browsers could make that request anyway.

Related

HTTP server gives error when responses some requests

I am making an express.js server to store pictures.
const express = require('express');
const app = express();
app.get('/*', (request, response) =>
{
response.sendFile(__dirname + '/data' + request.path);
});
app.listen(9999);
console.log('Server started on port 9999');
And I have a problem. If I type http://127.0.0.1:9999/vehicles/boats/dinghy.png into browser, I get a picture, but when I type https://127.0.0.1:9999/main/avatar.png I get This site can’t provide a secure connection 127.0.0.1 sent an invalid response. Both files do exist, but one of them is sent correctly, but another one gives an error. What can it be caused by?
Your second request is sent via https. As you're not providing a valid certificate for localhost at your express app, the browser will give you a hint about this.

what is the difference between using Express GET method and HTTPS GET method in the below code?

const express = require("express");
const app = express();
const https = require("https");
app.get("/", function (req, res){
var url = "https://***";
https.get(url, function(response){
console.log(response);
});
res.send("server running");
});
Express is really just a layer on top of http.
I reckon those following links might help you out, this question has been asked.
what's the technical difference between express and http, and connect for that matter
Difference between a server with http.createServer and a server using express in node js
app.get() registers a listener for a specific INCOMING http request path on a local Express server.
https.get() makes an OUTBOUND https request TO some other https server to fetch content from that other server.
And, obviously, the https.get() is using https, not http. The app.get() could be listening for either - it depends upon how the server it is part of is started (as an http server or an https server) which the code you have in your question does not show.

How to emulate traffic in express.js

I have a node express server responding to http traffic:
const http = require("http");
const express = require("express");
const app = express();
const server = http.createServer(app);
app.use(function(req,res,next){
console.log(`logging: req: ${util.inspect(req)}`);
next();
});
and all that works fine. I'd like to have a program on my node server inject emulated http traffic into the express stack, without a network connection. I can't just magic up a (req,res) pair and call a middleware function like the one in app.use above, because I don't have a next to give it, and my req and res will not be the ones next passes on to the next middleware in the stack.
Edit: What I actually have is a websocket connection sending data packets of a different format, different data contents from http traffic that can also carry the same information. I can take those websocket packets and build from those a request that is in the same format that the http traffic uses. I would like to pass that transformed request through the express http middleware stack and have it processed in the same way. Going all the way back to create an http request having just dealt with a ws request seems a bit far.
What's the simplest way to emulate some traffic, please? Can I call a function on app? Call some express middleware, or write a middleware of my own to inject traffic? Call a function on server?
Thanks!
Emulation traffic by calling some Express.js internal functions isn't the right way. Much easier is to trigger the server by HTTP request from the same process
const http = require('http');
const util = require('util');
const express = require('express');
const app = express();
const server = http.createServer(app);
app.use(function(req, res, next) {
console.log(`logging: req: ${util.inspect(req)}`);
next();
});
const port = 8081;
server.listen(port);
http.request({ port }).end();
From your question
I'd like to have a program on my node server inject emulated http traffic into the express stack, without a network connection
Can you clarify, why without a network connection?
A few things:
You need to make an endpoint
You need to host your server somewhere
You need something to send requests to your server
Express provides you a way to receive requests (req, res) (might be from a browser, might not be), perform some operations, and return responses (req, res) to the requester.
The expression
app.use(function(req,res,next){
console.log(`logging: req: ${util.inspect(req)}`);
next();
});
is actually a middleware function. This will take every request to your server and change the request object created by express into a string, and print it in your server log.
If you want a testable endpoint, you would add this to the bottom of the snippet you posted
app.get('/test', function (req, res) {
res.json({success:true})
})
This tells your app to allow GET requests at the endpoint /test
Next you're going to need to host your express server somewhere you can send requests to it. Your local machine (localhost) is a good place to do that. That way, you don't need an internet connection.
Pick a port you want to host the server on, and then it will be reachable at http://localhost:<Your Port>.
Something like this will host a server on http://localhost:3000. Add this below the route we declared above:
server.listen(3000, function() {
console.log('Server running on port 3000');
});
Finally, you'll need a way to send requests to the server on localhost. Postman is a great tool for testing express routes.
I would suggest installing Postman and using that to emulate http traffic.
Once your server is running, open postman and send a GET request to your server by entering the server address and port, and hitting the blue send button (You'll be sending the request to http://localhost:3000/test).
Here's an image of what postman should look like if all goes well
You should also see your middleware fire and print out the request object in your terminal.
Good Luck!

http.request vs http.createServer

What is the difference between the request in this line of code:
http.createServer(function(request,response){. . .}
and request in
http.request()
Are both requests done to the server?
I am new to node.js and I am sorry if I sound dumb!
How does http.request() work?
In http.request() we fetch data from another site but in order to fetch data from another site we first need to go to our site and then make a request? Explain it with a simple real-life example!
http.request() makes a request to another HTTP server. Suppose for some reason I wanted to go download Stack Overflow's home page...
http.request('https://stackoverflow.com/', (res) => {
// ...
});
http.createServer()... it creates an HTTP server. That is, it binds your application to a socket to listen on. When a new connection is made from somewhere or something else, it handles the underlying HTTP protocol of that request and asks your application to deal with it by way of a callback. From the Node.js documentation:
http.createServer((req, res) => {
res.writeHead(200, { 'Content-Type': 'text/plain' });
res.end('okay');
});
These two methods have absolutely nothing to do with each other. http.request() is for making a request to an HTTP server. http.createServer() is for creating your own HTTP server. Don't get confused by the callbacks.
Based on the source code of nodejs (extract below), createServer is just a helper method to instantiate a Server.
Extract from line 1674 of http.js.
exports.Server = Server;
exports.createServer = function(requestListener) {
return new Server(requestListener);
};
The http.request() API is for when you want your server code to act as a client and request content from another site and has GET, POST, PUT, DELETE methods.

Why the callback function gets called twice for each request?

Guys I am new to node js and this behavior is strange to me!
In the code snippet below,
'use strict';
var http = require('http');
var numberOfRequests = 0;
http.createServer(function (request, responce) {
console.log('Request number ' + numberOfRequests + ' received!');
responce.writeHead(200);
responce.write("Here is responce to your request..");
responce.end();
numberOfRequests++;
}
).listen(8080);
console.log('listening ...');
for each
localhost:8080
call at Chrome, the app writes twice onto console? e.i
for a single 8080 call, it prints out:
Request number 0 received!
Request number 1 received!
I am using Visual studio to run this node js app.
Usually, when you see two requests for each page request, one is for the desired page and one is for the favicon for the website. This is what most browsers do unless there is meta tag in the page that tells the browser not to request a favicon resource. If you do this in your handler:
console.log(request.url)
That will likely show you what's going on. In general, you don't want to have a web server where you never look at what resource is being requested. If you based your logic on a specific resource being requested such as /, then you would easily be able to ignore other types of requests such as the favicon.
Run curl <hostname:port> to make a single request. This proves it's the browser making multiple.

Resources