Home > Back-end >  Node.js file blocks terminal after correct execution
Node.js file blocks terminal after correct execution

Time:09-01

I'm new to using Node and fetch and of course I'm having some problems with my code. Essentially I'm trying to implement a project where I get some json data through an API request and store it into a mysql database. These data is contained in multiple pages and therefore I used a simple for cycle for multiple fetching. I do this 2 times as I have to get data from 2 different object lists. For storing the data I first established a mysql connection and later I execute the sql query inside another for iterating the single object data. It performes correctly both extraction of json data and storage in mysql database but once I execute node index.js on the terminal, the process keeps on running and the terminal gets suspended until I force the process to terminate. I used why-is-node-running and found out this:enter image description here

Here's the code of index.js:

import mysql from 'mysql';
import fetch from 'node-fetch';
import log from 'why-is-node-running';

const URL0 = "https://atlas.ripe.net/api/v2/probes/?status=1";
const sql = "INSERT INTO probes (id, country, longitude, latitude) VALUES (?,?,?,?)";
const sql1 = "INSERT INTO anchors (id, country, longitude, latitude) VALUES (?,?,?,?)";
const PG_SIZE = 100;
let num_pages_probes=120;
let i=0, j=1, k=1, a=0;

const con = mysql.createConnection({
    host:'localhost',
    user:'root',
    password:'',
    database:'probes&anchors'
});

        
con.connect((err)=>{
    if(err){
        console.log("Connection not proper");
    }else{
        console.log("connected");
    }
});
/*
fetch(URL0)
    .then((response) => {
      if (!response.ok) {
          throw new Error("HTTP error! status: "
            response.status);
          } else {
          return response.json();
          }
    })
.then((data) => {

    num_pages_probes = Math.ceil(data.count/PG_SIZE);
    console.log(num_pages_probes);
});
*/
for (j; j<=2; j  ){
    console.log("j=" j);
    let URLi = "https://atlas.ripe.net/api/v2/probes/?page=" j "&status=1";
    fetch(URLi)
    .then((response) => {
      if (!response.ok) {
          throw new Error("HTTP error! status: "
            response.status);
          } else {
          return response.json();
          }
    })
    .then((data) => {

        for (let probe of data.results){
            i  ;
            let id0 = probe.id;
            let country = probe.country_code;
            let longitude = probe.geometry.coordinates[0];
            let latitude = probe.geometry.coordinates[1];
            
            con.query(sql, [id0, country, longitude, latitude], function (err, result) {
                if (err) throw err;
                console.log("1 record inserted");
            });
    
            console.log("id0: " id0 "\t" "cc: " country "\t" "long: " longitude "\t" "lati: " latitude);
            console.log(i);
        }
      //  con.end();

    });
}



for (k; k<=2; k  ){
    console.log("k=" k);
    let URLi = "https://atlas.ripe.net/api/v2/anchors/?page=" k;
    fetch(URLi)
    .then((response) => {
      if (!response.ok) {
          throw new Error("HTTP error! status: "
            response.status);
          } else {
          return response.json();
          }
    })
    .then((data) => {

        for (let anchor of data.results){
            a  ;
            let id0 = anchor.id;
            let country = anchor.country;
            let longitude = anchor.geometry.coordinates[0];
            let latitude = anchor.geometry.coordinates[1];
            
            con.query(sql1, [id0, country, longitude, latitude], function (err, result) {
                if (err) throw err;
                console.log("1 record inserted");
            });
            
            console.log("id0: " id0 "\t" "cc: " country "\t" "long: " longitude "\t" "lati: " latitude);
            console.log(a);
        }

    });
}

setTimeout(function () {
    log() // logs out active handles that are keeping node running
  }, 100)

Can someone help me out please? I don't know where to put my hands on.
PS. I purposely limited the cycle to 2 but it would actually be like 120.

CodePudding user response:

You are not closing your mysql connection which keep your proccess up.

You probably want to close your connection when all your fetch/inserts are done, the tricks here is to ensure you've completed all your inserts before closing your connection.

You can have a look at async/await syntax, it will help you ensure you are closing only when you've done your inserts.

A very simplified version would look like:

const fn = async () => {
  const con = mysql.createConnection({ ... });
  for (...) {
    const res = await fetch({ ... });
    const data = await res.json();
    await con.query({ ... });
  }
  await con.close();
}
fn();

NOTE: The mysql lib seems to only work with callback, so you will probably have to promisify the methods you need (see utils.promisify)

  • Related