Access request object in Node (question)

Hello there.

I am currently doing the headparser project from the API and Microservices.

Basically, I need to be able to access to ip, software and language of my computer.
So, I found that there is a lot of information in the request object. What I don´t understand is the way to access them.
My code:

// your first API endpoint...
app.get("/api/whoami", function (req, res) {
  res.json({
    ipaddress: req.ip,
    language: req.headers["accept-language"],
    software: req.headers["user-agent"],
  });
});

Request object:

Your app is listening on port 52643
{
  host: 'localhost:52643',
  connection: 'keep-alive',
  'sec-ch-ua': '"Chromium";v="94", "Google Chrome";v="94", ";Not A Brand";v="99"',
  'sec-ch-ua-mobile': '?0',
  'sec-ch-ua-platform': '"Windows"',
  'upgrade-insecure-requests': '1',
  'user-agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/94.0.4606.81 Safari/537.36',
  accept: 'text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9',
  'sec-fetch-site': 'none',
  'sec-fetch-mode': 'navigate',
  'sec-fetch-user': '?1',
  'sec-fetch-dest': 'document',
  'accept-encoding': 'gzip, deflate, br',
  'accept-language': 'es-ES,es;q=0.9,zh-ES;q=0.8,zh;q=0.7,en-ES;q=0.6,en;q=0.5'
}
[nodemon] restarting due to changes...
[nodemon] starting `node server.js`
Your app is listening on port 51992

Why does this work?:

language: req.headers["accept-language"]
software: req.headers["user-agent"]

For me, it makes more sense if I do:

language: req.headers.accept["accept-language"]
software: req.headers.connection["user-agent"]

I mean, “headers” is an object, isn´t it? Why do I have to “skip” the “connection” or “accept” key in order to access the keys inside them?

Hello!

Yes, it’s an object. The thing, however, is that accept and connection are not properties of the object; the properties are accept-language and user-agent. The property connection is a direct child of the headers object, like this:

{
  connection: "...",
  "accept-header": "...",
  "user-agent": "..."
}

You may have confused them because they are in quotes. This is because the property names use the dash character.

I made a mistake:

This is not correct. connection is not a property of the object, but accept is. However, accept is not an object, but a string, so it doesn’t have any properties of it’s own.

First of all, please don’t share pictures of code - cut and paste the code.

The thing, however, is that accept and connection are not properties of the object; the properties are accept-language and user-agent .

Maybe I’m misunderstanding. What I see is that req.headers is an object, the object that is logged out. I think what is confusing (as pointed out by skaparate) is that the property names look weird - the property names that are valid JS identifiers are white and property names that are not (in this case with a “-”) are in green and with quotes. But all those properties are on the same level. So, req.headers.accept is a sibling of req.headers[“accept-language”], not the parent. There is no nesting in his object. It is all just key/value pairs and all the values are strings.

If you want to reveal the hierarchy a bit better, you can do:

console.log(JSON.stringify(req.headers, null, 2));

That will convert the object into a string that represents the object like we’re use to seeing in code, with an indent of 2.

2 Likes

Sorry, I removed the screenshot and used code instead.

@skaparate @kevinSmith I understood what you meant, thanks! The difference of the colours confused me and made me think they were nested.

2 Likes