Reputation: 10012
So I have a callback function which provides a json object:
function(object){
var data=object.packet.link.ip.tcp.data;
console.log(data.toString());
}
The problem I have is that any of packet/link/ip/tcp/data can be "undefined" - my node.js program falls over every time it hits an undefined variable.
I tried putting the declaration of "data" inside try/catch, however I keep getting "undefined" errors - my guess is that I'd need to put object/object.packet/object.packet.link/object.packet.link.ip/etc. in try/catch.
So, I found some elegant coffeescript:
if object?.packet?.link?.ip?.tcp?.data? then doStuff()
which compiles to:
var _ref, _ref1, _ref2, _ref3;
if ((typeof object !== "undefined" && object !== null ? (_ref = object.packet) != null ? (_ref1 = _ref.link) != null ? (_ref2 = _ref1.ip) != null ? (_ref3 = _ref2.tcp) != null ? _ref3.data : void 0 : void 0 : void 0 : void 0 : void 0) != null) {
//doStuff:
var data = object.packet.link.ip.tcp.data;
console.log(data.toString());
}
Yuck!
Now it works perfectly, but I was just wondering if there's a more elegant (readable) way of doing this in pure Javascript?
Upvotes: 3
Views: 376
Reputation: 235972
If it is just enough to check whether or not you're dealing with truthy values, you might go like
var data = object && object.packet && object.packet.link && object.packet.link.ip; // etc.
still no beauty, but most likely the best you can go for. Of course, you always have the option of introducing the good ol' try..catch
clause.
try {
var data = object.packet.link.ip.tcp.data;
} catch( ex ) { }
Anything "better" than that in terms of "elegance" (whoever that defines) would require a custom written function, which walks step by step through the object properties, checking for existence.
Upvotes: 3
Reputation: 3179
function A(object)
{
var data = object?object.packet?object.packet.link?object.packet.link.ip?object.packet.link.ip.tcp? object.packet.link.ip.tcp.data:null:null:null:null:null;
console.log(data);
}
Note:
If data has null, you can't call toString on null, as null(along with undefined) are the only two primitives which have no object wrappers and subsequently no toString() functions.
Upvotes: 1
Reputation: 3770
You can do
["packet", "link", "ip", "tcp", "data"]
.reduce(function (m, i) { if (m) return m[i]; }, object);
You could move the reduce
into a function and have get(object, "packet", "link", "ip", "tcp", "data")
. It can be pretty, although a simple &&
solution might be more sensible.
Upvotes: 5