references in node.js callbacks

I have just been writing some tests when a fundamental problem emerged. I wrote the bare skeleton of a test framework. It first collects all tests (their callbacks) in an array and executes them afterwards in a separate loop. However, this

//test.js
var testArray = [
    {
    n : 1,
    d : 'text1'
    },
    {
    n : 2,
    d : 'text2'
    }
];

var cbs = [];
function fnWithCallback(d, cb) {
    console.log('d=('+d+')');
    cbs.push(cb);
}

for(var i=0; i < testArray.length; i++) {
    var v = testArray[i];

    fnWithCallback(v.d, function() {
    console.log('v=('+v.n+'), i=('+i+')');
    });
}

for(var j=0; j < cbs.length; j++) {
    cbs[j]();
}

When I run this sample I get this:

> node test.js
d=(text1)
d=(text2)
v=(2), i=(2)
v=(2), i=(2)

That means in the callback 'v' has been assigned to the last element of the last array and 'i' to it's last state, not to the one when the callback has been 'created' and passed to the 'fnWithCallback' function. However, since 'd' is printed out within the callback it hast the value of the element when 'fnWithCallback' has been called.

"Unlooping" the loop does not help.

var v = testArray[0];

fnWithCallback(v.d, function() {
    console.log('v=('+v.n+')');
});

v = testArray[1];

fnWithCallback(v.d, function() {
    console.log('v=('+v.n+')');
});

results in the same behaviour.

Can someone explain this and provide a solution?

Use a closure

fnWithCallback(v.d, (function(v,i){
    return function() {
        console.log('v=('+v.n+'), i=('+i+')');
    };
})(v,i)));