1

This is for a gameing application I declare the variable skipnpc which is designed as an indicator that a non player character has used his turn and any AI code related to his behavior is skipped for a period of time. the problem I have is I am loosing the value of skipnpc somehow I indicated where in the console.log commands I issue is related to varaible scope but I don't understand how to fix it.

function npcMovement() {
    skipnpc = false;...
    sql4 = "SELECT id FROM game_moblist WHERE spawn_id =" + spawnid + " AND posx=" + parseInt(mobpathx[mobpathx.length - 1]) + " AND posy=" + parseInt(mobpathy[mobpathy.length - 1])
    connection.query(sql4, function (err, send, fields) {
        console.log("skipnpc pathing")
        io.sockets.emit('groupmoveresult', send, parseInt(mobpathx[mobpathx.length - 1]), parseInt(mobpathy[mobpathy.length - 1]))
        skipnpc = true
        console.log("skipnpc=true:" + skipnpc)
    });
    console.log("skipnpc = false:" + skipnpc)

Later I use

if (skipnpc==false){
  ...

before any further AI code is attempted

Shawn
  • 871
  • 2
  • 12
  • 22
  • Is `skipnpc` a property of `window`? Are you using Node? – Matt Ball Aug 01 '12 at 16:18
  • no this is run in node console its just a varriable I declared to trigger an if (skipnpc==true){...} – Shawn Aug 01 '12 at 16:18
  • Are you using javascript 'strict' mode? – kidwon Aug 01 '12 at 16:21
  • @kidwon not familiar with that but I think I'm not as from what I understand its for browsers. – Shawn Aug 01 '12 at 16:22
  • 1
    Just a guess: could this be related to the async nature of the callback function? my guess would be that, either way you'll first see the console log `false`, but do you actually get to see the line `skipnpc=true:true` and then `skipnpc=false:false`? – Elias Van Ootegem Aug 01 '12 at 16:22
  • @ Elias Van Ootegem "but do you actually get to see the line skipnpc=true:true and then skipnpc=false:false?" Yes. – Shawn Aug 01 '12 at 16:24
  • @Shawn What behavior do you want `skipnpc` to have that you're not able to create? – JohnnyHK Aug 01 '12 at 16:36

2 Answers2

2

connection.query is executed asynchronous. Thus you get to your final line here before it is done.

Roest
  • 826
  • 6
  • 16
  • I don't see how that would cause this issue. But it doesn't explain how to get around the problem. – Shawn Aug 01 '12 at 16:29
  • It's hard to tell from that code snippet. Is skipnpc defined somewhere else with var or is that the first occurence here. To make sure the rest get execute after the query finishes, arg stupid comment editor you can encapsulate the rest in a function and call it at the end of the query body. – Roest Aug 01 '12 at 16:39
  • I found that javascript in node is not so forgiving as in browsers. So "use strict" certainly helps to see problems before they do unexpected things. – Roest Aug 01 '12 at 16:43
  • I defined skipnpc globally as in the snippet at the top. – Shawn Aug 01 '12 at 16:57
  • node globals are not so global as you might expect, http://stackoverflow.com/questions/4140661/global-variables-for-node-js-standard-modules has some interesting comments – Roest Aug 01 '12 at 17:01
1

To put it real simply, skipnpc is guaranteed to still be false by the time you hit your last console.log(...). You're not giving your connection.query(...) any time to execute before trying to look at its result. Anything that relies on the result of connection.query(...) has to be executed as part of the callback you passed to it; otherwise none of the results will have come in when you try to access them.

Asynchronous programming takes some getting used to. You might be able to reorganize your code using the async module and using its waterfall(...) method so everything doesn't wind up deeply nested. But you've got to realize that if you make an asynchronous call, your code will flow right past it.

ebohlman
  • 14,795
  • 5
  • 33
  • 35