0

I try every possible solution that is available in SO. like using global or using bind but can not access the global variable. here is my code i am trying to generate sitemap in nodejs here is my .js file.

    module.exports = function (portal) {
    var mongoose = require('mongoose');
    var News = mongoose.model('News');
    var urls ="";
    var gensitemap =  function(){
    urls = "abc";

    console.log(urls);// print abc as expected
    News.find().exec(function (err, news) {
      news.forEach(function (t) {
        urls += "<url><loc>"+cdn_url+"/news"+t.slug+"</loc>"+"</url>";
       });
    });
    console.log(urls);// print still abc as not  expected it should be change
    }   
    var allUsers = portal.setupContext({});
    app.get('/gensitemap',allUsers ,gensitemap);
  };

here you can see i use url variable befor and after News.find() method.but instead of change the url its is printing same output.

Any idea i already try global or async.parallel({}) but same issue in News.find() node js treat that variable as different.

Any help ?

UPDATE :

After reading the comments and some of the mention question i try this

    Events.find().exec(function (err1, events) {
            events.forEach(function (t1) {
                url += "<url><loc>"+cdn_url+"/event"+t1.slug+"</loc>"+changefreq+priority+"</url>";
            });
            News.find().exec(function (err2, news) {
                    news.forEach(function (t2) {
                        url += "<url><loc>"+cdn_url+"/news"+t2.slug+"</loc>"+changefreq+priority+"</url>";
                    });
                    var static_urls = ['about-us','categories','overview','media','contact-us','login','register','pages/en/faq'];
                            for(var i = 0 ;i < static_urls.length;i++){
                                url += "<url><loc>"+"http://192.168.10.38:3000/"+static_urls[i]+"</loc>"+"<changefreq>weekly</changefreq>"+"<priority>1</priority>"+"</url>";
                            }
                    console.log(url);

//this url(variable) print only the changes i made in above for loop.. :-(
                });
        });

I also notice after waiting some time i am able to see the change but they are not in same order.

Foram Sangani
  • 287
  • 1
  • 4
  • 17
  • 3
    Possible duplicate of [How to return the response from an asynchronous call?](https://stackoverflow.com/questions/14220321/how-to-return-the-response-from-an-asynchronous-call) – baao Nov 20 '17 at 11:24
  • try to this link and slove qution; https://stackoverflow.com/questions/10987444/how-to-use-global-variable-in-node-js – Dharmik Unagar Nov 20 '17 at 11:24
  • but my variable are in the same file @DharmikUnagar – Foram Sangani Nov 20 '17 at 11:26
  • no not possibly duplicate @baao – Foram Sangani Nov 20 '17 at 11:27
  • 3
    Yes it is. The answers to the question solve exactly your problem. But keep trying to do something with global variables if you know it better... :-) – baao Nov 20 '17 at 11:28
  • this example is saying that use `global` i already try but same out put @DharmikUnagar – Foram Sangani Nov 20 '17 at 11:28
  • This type of question are asked many time .please study asychronous programming before you start node.js .just to give hint the new.find is i/o block so it goes to event loop to execute on the same time as that was the i/o request the processing of next statement started and urls print as it is – Himanshu sharma Nov 20 '17 at 11:42
  • Yah Thanks for the advice. but we can not learn everything so i just started to learn nodejs @Himanshusharma – Foram Sangani Nov 20 '17 at 11:55
  • checkout this . This may help. https://stackoverflow.com/questions/29682163/call-function-when-for-loop-finished-in-node-js .If it don't help comment here i will give answer . – Himanshu sharma Nov 20 '17 at 12:10
  • Possible duplicate of [Call function when for loop finished in Node js](https://stackoverflow.com/questions/29682163/call-function-when-for-loop-finished-in-node-js) – Himanshu sharma Nov 20 '17 at 12:10
  • 1
    Your problem is you don't understand the life cycle of an asynchronous call in NodeJS. You don't need to use global or async (using global is an 95% bad idea in all cases). Your just need to understanding is useless to try too access urls before mongo reply to your request. – Techniv Nov 20 '17 at 13:09
  • Yes i accept i don't understand that why i put the question in SO. Please Help me to understand @Techniv – Foram Sangani Nov 21 '17 at 05:14
  • And this is why we reply to you this is a duplicate of [How to return the response from an asynchronous call?](https://stackoverflow.com/questions/14220321/how-to-return-the-response-from-an-asynchronous-call). Don't focalise your attention on the question, it's not the same question, you're right. But the answer to the both question is the same, because this is the same problem of misunderstanding of asynchronous call. – Techniv Nov 21 '17 at 09:55

1 Answers1

1
    module.exports = function (portal) {
    var mongoose = require('mongoose');
    var News = mongoose.model('News');
    var urls ="";
    var gensitemap =  function(){
    urls = "abc";

    console.log(urls);// print abc as expected
    News.find().exec(function (err, news) {//this block of code gets executed after the News.find().exec() function return . Anything you want to do after the exec function call get a response you have to do it here. inside this call back function.

      news.forEach(function (t) {
        urls += "<url><loc>"+cdn_url+"/news"+t.slug+"</loc>"+"</url>";
       });
      //if you log the url here you should find ur desired value
      console.log(urls);
    });
    //This is getting called before your News.find().exec() function returns any value.
    console.log(urls);// print still abc as not  expected it should be change
    }   
    var allUsers = portal.setupContext({});
    app.get('/gensitemap',allUsers ,gensitemap);
  };
Kishan Oza
  • 1,707
  • 1
  • 16
  • 38
Mustafa Mamun
  • 2,591
  • 2
  • 14
  • 17
  • Look i agree in the `News.find()` call back i get my desire out put but i have more 3 other call like `News.find()` then what i suppose to do ? – Foram Sangani Nov 21 '17 at 05:13
  • depends on how you want to use them. You can look at these packages. https://www.npmjs.com/package/async or http://bluebirdjs.com/docs/getting-started.html – Mustafa Mamun Nov 21 '17 at 12:43
  • Or the classic ES6 [Promise](https://developer.mozilla.org/fr/docs/Web/JavaScript/Reference/Objets_globaux/Promise) – Techniv Nov 21 '17 at 17:11