peterHasemann
peterHasemann

Reputation: 1580

Read data from JSON, manipulate it and write it back in NodeJs

I have a small JSON file with this content

{
  "users": [
    {
      "id": 1111,
      "name": "Foo",
      "gold": 2
    },{
      "id": 2222,
      "name": "Bar",
      "gold": 7
    }
  ]
}

and when using Ajax I call this route

app.get('/incG/:id', function (req, res) {
  fs.writeFile('./database.json', 'utf8', function (err, data) {
    var json = JSON.parse(data); // get the data
    var users = json.users; // get all users
    var user = users.find(u => u.id === Number(req.params.id)); // get a user by id
    user.gold++; // increase his gold value
    res.send(user.gold); // send a response to the client
  });
});

when running the server I get this error message

undefined:1
utf8
^

SyntaxError: Unexpected token u in JSON at position 0
    at JSON.parse (<anonymous>)
    at ... \app.js:23:21
    at tryToString (fs.js:449:3)
    at FSReqWrap.readFileAfterClose [as oncomplete] (fs.js:436:12)

How can I get the data from the file, change the specific object, selected by its id, write it back to the file and send a response to the client?

My code seems to be wrong, I want to use writeFile not readFile. I don't want to read the data, I want to manipulate it.


EDIT

I tried building up this code

app.get('/incG/:id', function (req, res) {
  var database = './database.json';
  var userId = Number(req.params.id);
  fs.readFile(database, 'utf8', function (err, data) {
    var json = JSON.parse(data);
    var users = json.users;
    var user = users.find(u => u.id === userId);
    user.gold++;
    fs.writeFile(database, json, (err) => {
      res.send(user.gold);
    });
  });
});

but I think passing in json as a data object is wrong. The file content gets "destroyed"

Upvotes: 2

Views: 514

Answers (2)

Bamieh
Bamieh

Reputation: 10906

to write into a file, simply follow the node documentation:

app.get('/incG/:id', function (req, res) {
  fs.writeFile('./database.json', 'utf8', function (err, data) {

    var users = json.users; // get all users
    var user = users.find(u => u.id === Number(req.params.id));
    user.gold++; // increase his gold value

    fs.writeFile('database.json', myJSON, (err) => {
      if (err) throw err;
      res.send(user.gold);
    });
});

A better approach when reading from a file / writing to a file on a web server is to use streams, this way you will not consume a lot of memory doing the operation.

You can read more about it here in this great post:

Upvotes: 1

codejockie
codejockie

Reputation: 10844

I believe you're using writeFile wrongly. According to Node.js docs, the second argument to writeFile should be the data you want to write. See below:

fs.writeFile('message.txt', 'Hello Node.js', (err) => {
  if (err) throw err;
  console.log('The file has been saved!');
});

Upvotes: 1

Related Questions