As the MDN link above explains:
“A TypeError is thrown when an operand or argument passed to a function is incompatible with the type expected by that operator or function” - MDN
So to avoid TypeError’s we need to be checking that the values we pass into functions are correct, and that any code we write checks the validity of an operand before using an operator on it. For example the
. operator is not compatible with
undefined and the
Lets start by looking a fairly straight forward example of getting some data from the server, performing some operations on that data, and then using it to render some HTML.
The first thing to note is that from looking at this code we don’t actually know what
conversations is supposed to be. We could assume that since it’s obviously expected to have a
map function that it should be an array, but assumptions are bad and in reality it could be anything that implements a
map method. The function passed to
map makes a lot of assumptions about the
c variable. If any of those assumptions are wrong then a TypeError will be thrown and
renderMessages() will never be called.
typeof operator returns a string indicating the type of the operand, but the types it returns are very limited. For example the following all return “object”
instanceof operator is used to determine if an object’s prototype chain contains the prototype property of a given constructor.
Although this will work, using
instanceof for checking the type of a native object is not a great idea as it does not work for primitives values.
toString method on
- If the this value is undefined return
- If the
thisvalue is null, return
- Let O be the result of calling ToObject passing the this value as the argument.
- Let class be the value of the [[Class]] internal property of O.
- Return the String value that is the result of concatenating the three Strings
"[object ", class, and
So basically this method will always return a String in the form “[object Foo]” where Foo is going to be “Null”, “Undefined”, or the internal Class used to create
this. By using the
call method to change the
this value and a simple regular expression to parse the result we can get a string representing the type of anything.
So this must be problem solved, right? Sadly not quite yet. There are still a few instances where this method will return values other than we would expect.
Both of these cases return values that we probably wouldn’t expect. In the case of
NaN it returns
"number" because technically
NaN is a type of number, although in nearly all cases we want to know if something is a number, not NOT a number. The internal class used to implement the
<body> element is
HTMLBodyElement (at least in Chrome and Firefox) and there are specific classes for every element. In most cases we would just want to know if something is an element or not, if we then cared about the tag name of that element we can use the
tagName property to retrieve it. However we can modify our existing method to handle these cases.
So now we have a method that will return the correct type for all the things we are interested in we can improve the original example to ensure that we don’t have any
Obviously there is no getting away from the fact that we have had to add quite a lot of additional code to avoid the risk of
Finally, the rather obvious downside of the
type method is that it requires checking the return value against a string every time. This is easily improved though. We can create an API similar to Underscore / LoDash / jQuery by doing the following:
type method explained in this post is available as a gist.