Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Testing if something is a class in javascript

Tags:

Hey all, I am trying to test if the argument passed into my function is a class name so that I may compare it to other classes using instanceof.

For example:

function foo(class1, class2) {   // Test to see if the parameter is a class.   if(class1 is a class)   {     //do some kind of class comparison.     if(class2 is a class)     {        if(class1 instanceof class2)        {           //...        }     }     else     {        //...     }   }   else     //... } 

Is this possible? I am having trouble googleing an answer.

like image 675
kgrad Avatar asked Feb 08 '09 22:02

kgrad


People also ask

How do you check if an object is in a set JavaScript?

Use the has() method to check if a Set contains an object, e.g. set.has(obj) . The object has to be passed by reference to the has method to get a reliable result. The has method tests for the presence of a value in a Set and returns true if the value is contained in the Set .

How do you test a class jest?

To test classes with Jest we write assertions for static and instance methods and check if they match expectations. The same process we use when testing functions applies to classes. The key difference is that classes with constructors need to be instantiated into objects before testing.

Which operator is used to check that object belongs to a class?

The instanceof operator allows to check whether an object belongs to a certain class.

Which statement can be used to check if an object obj is an instance of class A?

Using isinstance() function, we can test whether an object/variable is an instance of the specified type or class such as int or list. In the case of inheritance, we can checks if the specified class is the parent class of an object.


2 Answers

There is really no such thing as a "class" in javascript -- everything but primitives are an object. Even functions are objects.

instanceof DOES work with functions though. Check out this link.

function Car(make, model, year) {   this.make = make;   this.model = model;   this.year = year; } var mycar = new Car("Honda", "Accord", 1998); var a = mycar instanceof Car;    // returns true var b = mycar instanceof Object; // returns true 
like image 51
thesmart Avatar answered Nov 17 '22 08:11

thesmart


Now that we have native implementations of ES6, there are "real classes". These are largely syntactic sugar for prototypal inheritance as with constructor functions, but there are subtle differences and the two are not completely interchangeable.

So far, the only way I've found is to get the .toString() of the object's prototype's constructor function and check if it starts with class OR if the object has a constructor and the .toString() of that starts with class.

Note that if your code is compiled (ie: most Babel or TypeScript setups), then this will return function... instead of class... at runtime (since classes are transpiled to constructor functions).

function isClass(obj) {   const isCtorClass = obj.constructor       && obj.constructor.toString().substring(0, 5) === 'class'   if(obj.prototype === undefined) {     return isCtorClass   }   const isPrototypeCtorClass = obj.prototype.constructor      && obj.prototype.constructor.toString     && obj.prototype.constructor.toString().substring(0, 5) === 'class'   return isCtorClass || isPrototypeCtorClass } 

This will only work in native environments (Chrome, Firefox, Edge, node.js, etc.) that have implemented class for code that has not been transpiled to function.

Usage:

class A {} class B extends A {} isClass(A) // true isClass(new A()) // true isClass(B) // true isClass(new B()) // true  function C() {} isClass(C) // false isClass(new C()) // false isClass({}) // false isClass(Date) // false isClass(new Date()) // false  //These cases return 'true' but I'm not sure it's desired isClass(Object.create(A)) // true     const x = {} Object.setPrototypeOf(x, A) isClass(x) // true 

If there is a better way, I'd love to know what it is.

like image 41
aikeru Avatar answered Nov 17 '22 06:11

aikeru