questionmark.js
A tiny and mighty utility for optional chaining in pure JavaScript.
# get it npm install questionmark
const q = ; // If data.foo.bar.baz[0].bat[10] exists, its value will be returned.// If any of bar, baz, baz[0], or bat[10] don't exist, we return undefined.// You don't have to worry about accessing properties on null/undefined anymore!data; // Not sure if `data` itself is null or undefined? No problem. // Use this alternative syntax:; // q works with function invocations as well:data;
It's similar to idx.macro but doesn't get babel involved.
Tests
Lovingly tested in mocha.
npm test
Contribute
Fork and PR please.
Background: What is optional chaining?
Imagine you are accessing a property from a deeply nested JSON object (perhaps from a server response?)
;
But if json
, or json.libraries
, or json.libraries["UL London"]
, or any other value in that chain is null
or undefined
, your callback will throw an exception. You have to write some verbose guard clauses against that:
let book = !!json && !!jsonlibraries && !!jsonlibraries"UL London" && !!jsonlibraries"UL London"shelves && !!jsonlibraries"UL London"shelves"Science Fiction" && !!jsonlibraries"UL London"shelves"Science Fiction"authors && !!jsonlibraries"UL London"shelves"Science Fiction"authors"Herbert, Frank" && !!jsonlibraries"UL London"shelves"Science Fiction"authors"Herbert, Frank"mostPopularBook && jsonlibraries"UL London"shelves"Science Fiction"authors"Herbert, Frank"mostPopularBooktitle || "unknown";
Eugh!
Some languages have optional chaining to indicate that you only want to access a property if it exists; if not, further drill-downs just give you a null
value. This way you don't have to test every single step in the chain, and can just check whether you have a real value at the end.
This is also proposed for JavaScript:
let book = json?libraries?"UL London"? shelves?"Science Fiction"? authors?"Herbert, Frank"? mostPopularBook?title || "unknown"
That's much better. questionmark.js
aims to tide us over while we wait.
let book = json || "unknown";