GithubHelp home page GithubHelp logo

jonschlinkert / kind-of Goto Github PK

View Code? Open in Web Editor NEW
347.0 11.0 38.0 116 KB

Get the native JavaScript type of a value, fast. Used by superstruct, micromatch and many others!

Home Page: https://github.com/jonschlnkert

License: MIT License

JavaScript 100.00%
type typeof javascript kind string array object primitive date regex

kind-of's Introduction

kind-of NPM version NPM monthly downloads NPM total downloads Linux Build Status

Get the native type of a value.

Please consider following this project's author, Jon Schlinkert, and consider starring the project to show your ❤️ and support.

Install

Install with npm:

$ npm install --save kind-of

Why use this?

  1. it's fast | optimizations
  2. better type checking

Usage

es5, es6, and browser ready

const kindOf = require('kind-of');

kindOf(undefined);
//=> 'undefined'

kindOf(null);
//=> 'null'

kindOf(true);
//=> 'boolean'

kindOf(false);
//=> 'boolean'

kindOf(new Buffer(''));
//=> 'buffer'

kindOf(42);
//=> 'number'

kindOf('str');
//=> 'string'

kindOf(arguments);
//=> 'arguments'

kindOf({});
//=> 'object'

kindOf(Object.create(null));
//=> 'object'

kindOf(new Test());
//=> 'object'

kindOf(new Date());
//=> 'date'

kindOf([1, 2, 3]);
//=> 'array'

kindOf(/foo/);
//=> 'regexp'

kindOf(new RegExp('foo'));
//=> 'regexp'

kindOf(new Error('error'));
//=> 'error'

kindOf(function () {});
//=> 'function'

kindOf(function * () {});
//=> 'generatorfunction'

kindOf(Symbol('str'));
//=> 'symbol'

kindOf(new Map());
//=> 'map'

kindOf(new WeakMap());
//=> 'weakmap'

kindOf(new Set());
//=> 'set'

kindOf(new WeakSet());
//=> 'weakset'

kindOf(new Int8Array());
//=> 'int8array'

kindOf(new Uint8Array());
//=> 'uint8array'

kindOf(new Uint8ClampedArray());
//=> 'uint8clampedarray'

kindOf(new Int16Array());
//=> 'int16array'

kindOf(new Uint16Array());
//=> 'uint16array'

kindOf(new Int32Array());
//=> 'int32array'

kindOf(new Uint32Array());
//=> 'uint32array'

kindOf(new Float32Array());
//=> 'float32array'

kindOf(new Float64Array());
//=> 'float64array'

Benchmarks

Benchmarked against typeof and type-of.

# arguments (32 bytes)
  kind-of x 17,024,098 ops/sec ±1.90% (86 runs sampled)
  lib-type-of x 11,926,235 ops/sec ±1.34% (83 runs sampled)
  lib-typeof x 9,245,257 ops/sec ±1.22% (87 runs sampled)

  fastest is kind-of (by 161% avg)

# array (22 bytes)
  kind-of x 17,196,492 ops/sec ±1.07% (88 runs sampled)
  lib-type-of x 8,838,283 ops/sec ±1.02% (87 runs sampled)
  lib-typeof x 8,677,848 ops/sec ±0.87% (87 runs sampled)

  fastest is kind-of (by 196% avg)

# boolean (24 bytes)
  kind-of x 16,841,600 ops/sec ±1.10% (86 runs sampled)
  lib-type-of x 8,096,787 ops/sec ±0.95% (87 runs sampled)
  lib-typeof x 8,423,345 ops/sec ±1.15% (86 runs sampled)

  fastest is kind-of (by 204% avg)

# buffer (38 bytes)
  kind-of x 14,848,060 ops/sec ±1.05% (86 runs sampled)
  lib-type-of x 3,671,577 ops/sec ±1.49% (87 runs sampled)
  lib-typeof x 8,360,236 ops/sec ±1.24% (86 runs sampled)

  fastest is kind-of (by 247% avg)

# date (30 bytes)
  kind-of x 16,067,761 ops/sec ±1.58% (86 runs sampled)
  lib-type-of x 8,954,436 ops/sec ±1.40% (87 runs sampled)
  lib-typeof x 8,488,307 ops/sec ±1.51% (84 runs sampled)

  fastest is kind-of (by 184% avg)

# error (36 bytes)
  kind-of x 9,634,090 ops/sec ±1.12% (89 runs sampled)
  lib-type-of x 7,735,624 ops/sec ±1.32% (86 runs sampled)
  lib-typeof x 7,442,160 ops/sec ±1.11% (90 runs sampled)

  fastest is kind-of (by 127% avg)

# function (34 bytes)
  kind-of x 10,031,494 ops/sec ±1.27% (86 runs sampled)
  lib-type-of x 9,502,757 ops/sec ±1.17% (89 runs sampled)
  lib-typeof x 8,278,985 ops/sec ±1.08% (88 runs sampled)

  fastest is kind-of (by 113% avg)

# null (24 bytes)
  kind-of x 18,159,808 ops/sec ±1.92% (86 runs sampled)
  lib-type-of x 12,927,635 ops/sec ±1.01% (88 runs sampled)
  lib-typeof x 7,958,234 ops/sec ±1.21% (89 runs sampled)

  fastest is kind-of (by 174% avg)

# number (22 bytes)
  kind-of x 17,846,779 ops/sec ±0.91% (85 runs sampled)
  lib-type-of x 3,316,636 ops/sec ±1.19% (86 runs sampled)
  lib-typeof x 2,329,477 ops/sec ±2.21% (85 runs sampled)

  fastest is kind-of (by 632% avg)

# object-plain (47 bytes)
  kind-of x 7,085,155 ops/sec ±1.05% (88 runs sampled)
  lib-type-of x 8,870,930 ops/sec ±1.06% (83 runs sampled)
  lib-typeof x 8,716,024 ops/sec ±1.05% (87 runs sampled)

  fastest is lib-type-of (by 112% avg)

# regex (25 bytes)
  kind-of x 14,196,052 ops/sec ±1.65% (84 runs sampled)
  lib-type-of x 9,554,164 ops/sec ±1.25% (88 runs sampled)
  lib-typeof x 8,359,691 ops/sec ±1.07% (87 runs sampled)

  fastest is kind-of (by 158% avg)

# string (33 bytes)
  kind-of x 16,131,428 ops/sec ±1.41% (85 runs sampled)
  lib-type-of x 7,273,172 ops/sec ±1.05% (87 runs sampled)
  lib-typeof x 7,382,635 ops/sec ±1.17% (85 runs sampled)

  fastest is kind-of (by 220% avg)

# symbol (34 bytes)
  kind-of x 17,011,537 ops/sec ±1.24% (86 runs sampled)
  lib-type-of x 3,492,454 ops/sec ±1.23% (89 runs sampled)
  lib-typeof x 7,471,235 ops/sec ±2.48% (87 runs sampled)

  fastest is kind-of (by 310% avg)

# template-strings (36 bytes)
  kind-of x 15,434,250 ops/sec ±1.46% (83 runs sampled)
  lib-type-of x 7,157,907 ops/sec ±0.97% (87 runs sampled)
  lib-typeof x 7,517,986 ops/sec ±0.92% (86 runs sampled)

  fastest is kind-of (by 210% avg)

# undefined (29 bytes)
  kind-of x 19,167,115 ops/sec ±1.71% (87 runs sampled)
  lib-type-of x 15,477,740 ops/sec ±1.63% (85 runs sampled)
  lib-typeof x 19,075,495 ops/sec ±1.17% (83 runs sampled)

  fastest is lib-typeof,kind-of

Optimizations

In 7 out of 8 cases, this library is 2x-10x faster than other top libraries included in the benchmarks. There are a few things that lead to this performance advantage, none of them hard and fast rules, but all of them simple and repeatable in almost any code library:

  1. Optimize around the fastest and most common use cases first. Of course, this will change from project-to-project, but I took some time to understand how and why typeof checks were being used in my own libraries and other libraries I use a lot.
  2. Optimize around bottlenecks - In other words, the order in which conditionals are implemented is significant, because each check is only as fast as the failing checks that came before it. Here, the biggest bottleneck by far is checking for plain objects (an object that was created by the Object constructor). I opted to make this check happen by process of elimination rather than brute force up front (e.g. by using something like val.constructor.name), so that every other type check would not be penalized it.
  3. Don't do uneccessary processing - why do .slice(8, -1).toLowerCase(); just to get the word regex? It's much faster to do if (type === '[object RegExp]') return 'regex'
  4. There is no reason to make the code in a microlib as terse as possible, just to win points for making it shorter. It's always better to favor performant code over terse code. You will always only be using a single require() statement to use the library anyway, regardless of how the code is written.

Better type checking

kind-of seems to be more consistently "correct" than other type checking libs I've looked at. For example, here are some differing results from other popular libs:

typeof lib

Incorrectly identifies instances of custom constructors (pretty common):

var typeOf = require('typeof');
function Test() {}
console.log(typeOf(new Test()));
//=> 'test'

Returns object instead of arguments:

function foo() {
  console.log(typeOf(arguments)) //=> 'object'
}
foo();

Incorrectly returns object for generator functions, buffers, Map, Set, WeakMap and WeakSet:

function * foo() {}
console.log(typeOf(foo));
//=> 'object'
console.log(typeOf(new Buffer('')));
//=> 'object'
console.log(typeOf(new Map()));
//=> 'object'
console.log(typeOf(new Set()));
//=> 'object'
console.log(typeOf(new WeakMap()));
//=> 'object'
console.log(typeOf(new WeakSet()));
//=> 'object'

About

Contributing

Pull requests and stars are always welcome. For bugs and feature requests, please create an issue.

Running Tests

Running and reviewing unit tests is a great way to get familiarized with a library and its API. You can install dependencies and run tests with the following command:

$ npm install && npm test
Building docs

(This project's readme.md is generated by verb, please don't edit the readme directly. Any changes to the readme must be made in the .verb.md readme template.)

To generate the readme, run the following command:

$ npm install -g verbose/verb#dev verb-generate-readme && verb

Related projects

You might also be interested in these projects:

Contributors

Commits Contributor
102 jonschlinkert
4 doowb
3 aretecode
2 miguelmota
1 dtothefp
1 ianstormtaylor
1 ksheedlo
1 pdehaan
1 laggingreflex
1 tunnckoCore
1 struct78

Author

Jon Schlinkert

License

Copyright © 2023, Jon Schlinkert. Released under the MIT License.


This file was generated by verb-generate-readme, v0.8.0, on July 12, 2023.

kind-of's People

Contributors

aretecode avatar doowb avatar dtothefp avatar ianstormtaylor avatar jonschlinkert avatar ksheedlo avatar laggingreflex avatar miguelmota avatar pdehaan avatar qcve avatar struct78 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

kind-of's Issues

Async function support?

Are there plans to identify async functions?

I've been doing checks with example below but I am sure that it'll be a very fragile approach.

const fn = async function() {};
kindOf(fn); // function
fn[Symbol.toStringTag] === 'AsyncFunction'; // true

Add CodeQL analysis tool

Proposal

Hello, I'm working on behalf of Google and the Open Source Security Foundation (OpenSSF) to help open-source projects improve their supply-chain security. Given kind-of project importance to the JavaScript community, the OpenSSF has identified it as one of the 100 most critical open source projects.

Would you consider adopting an analysis tool called CodeQL? CodeQL scans your code for potential vulnerabilities and reports the results as code scanning alerts. It is developed by GitHub and can help improve the project's security posture.

Would you be interested in a PR adding this tool?

Additional Context

To simplify maintainers' lives, CodeQL can be configured with CodeQL GitHub Action. It runs on every change or pull request to the repository's main branch. This Action is recommended by GitHub and Scorecards.

Let me know if you have any questions!

Date is undefined

<my package>/node_modules/nyc/node_modules/test-exclude/node_modules/kind-of/index.js:82
  if (val instanceof Date) return true;
                     ^

ReferenceError: Date is not defined

node version: v7.10.1
npm version: 4.2.0
container image: phusion/baseimage

x instanceof Date works in the node console within the same container

Image for sponsorships

Thanks to @ImZeus_XYZ 🙌 for his generous sponsorship! It will give me the ability to spend several more hours every week on open source!


Pasting this image here allows us to use GitHub's CDN for images related to this project. This image is for the sponsors section on the readme.

102035575

type checking

We found that a maliciously crafted user-input object can type checking result of kind-of module.
The vulnerability is from the following code: kind-of leverages the built-in constructor of unsafe user-input to detect type information. However, a crafted payload can overwrite this builtin attribute to manipulate the type detection result.

kind-of/index.js

Lines 68 to 70 in 4da96c0

function ctorName(val) {
return val.constructor ? val.constructor.name : null;
}

Reproduce Script

var kindOf = require('kind-of');


var user_input = {
  user: 'barney',
  age: 36,
  active: true,
  "constructor":{"name":"Symbol"}
};
console.log(kindOf(user_input));

This issue can be fixed by adding one simply check to the ctorName() function:
check typeof val.constructor === function . This check can patch the vulnerability because attackers can't use json to send function instances to the victim server.

Low Sev security vulnerability

Validation Bypass is reported as a low sev security vulnerability in audit and causing over 3000 lines of error in the audit trail

Security vulnerability backport to 3.x line.

Chokidar@2 depends on this module in version 3.x. It would be great to release the security fix to this line, so that Chokidar@2 is not vulnerable anymore.

I think the security fix is 975c13a. Is this the only thing?

I'm happy to do the PR to backport the change if you cut me a 3.x branch

kind-of-4.0.0 Vulnerability issue

We have facing the Vulnerability in the WhiteSource Bolt Build Report for the library "kind-of-4.0.0 (File: index.js)", below i have given the error details. we have upgraded the fresh module to latest version of 0.5.2 as mentioned in the error description, still the error not getting resolved, Kindly suggest us.

Vulnerability : CVE-2017-16119

Library: kind-of-4.0.0 (File: index.js)

Description: Fresh is a module used by the Express.js framework for HTTP response freshness testing. It is vulnerable to a regular expression denial of service when it is passed specially crafted input to parse. This causes the event loop to be blocked causing a denial of service condition.
Fix : Upgrade to version 0.5.2
https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2017-16119

Question

Why would you do a lot of conditions instead of...

function getType(query) {
  return query.constructor ? 
    String(query.constructor.name).toLowerCase() || typeof query 
    : typeof query;
}

It does pretty much the same

getType(new UInt8Array()); // "uint8array"
getType(new WeakMap()); // "weakmap"

Isn't it faster?

Detected vulnerability

Service:
FOSSA(app.fossa.com)

Vulnerability Code:
CVE-2019-20149

Description:
ctorName in index.js in kind-of v6.0.3 allows external user input to overwrite certain internal attributes via a conflicting name, as demonstrated by ‘constructor’: {‘name’:‘Symbol’}. Hence, a crafted payload can overwrite this built-in attribute to manipulate the type detection result.

Checking "typeof Buffer" causes browserify to bundle buffer package

Rel browserify/browserify#1228

I found this code, which causes browserify to bundle the buffer package:

if (typeof Buffer !== 'undefined' && isBuffer(val)) {
  return 'buffer';
}

The check for typeof Buffer !== 'undefined' is unnecessary since is-buffer already works fine in environments where Buffer is not defined. Removing it will prevent kind-of from causing this package (which pulls in a lot of code) to bloat the consumer's bundle.

Feature request: restricted type list

It is a common use case to only need to assert on certain types.

For example, I need to know if it's an object or a function and don't care otherwise. Or, I'd like to know if it's an array, object or Map (don't care otherwise).

In the second case, this check may be called with each React rendering during mouse drag - so performance may be important.

Would be nice if the API changes to:

const allTypes = [/* ... */];
function kindOf(val, typeList = allTypes) {
  // ...
}

I wrote one , need your evaluation.

function priviteKindOf(sth) {
    if (typeof sth === 'object' || typeof sth === 'function') {
        const type = /\[object (.*)\]/.exec(Object.prototype.toString.call(sth))[1].toLowerCase().replace(/\s/, '')

        if (type === 'uint8array' && sth instanceof Buffer) {
            return 'buffer'
        }
        return type
    }
    return typeof sth
}
module.exports = priviteKindOf

Passed all your tests, simpler, but performance is not so good.
Benchmarking: (21 of 21), priviteKindOf's better amount is 6, kindOf is 15.

# benchmark/fixtures/arguments.js (32 bytes)
  kind-of x 46,303,737 ops/sec ±0.84% (87 runs sampled)
  priviteKindOf x 49,144,123 ops/sec ±0.44% (93 runs sampled)

  fastest is priviteKindOf

# benchmark/fixtures/array.js (22 bytes)
  kind-of x 35,050,057 ops/sec ±0.55% (94 runs sampled)
  priviteKindOf x 5,403,902 ops/sec ±1.34% (89 runs sampled)

  fastest is kind-of

# benchmark/fixtures/boolean.js (24 bytes)
  kind-of x 39,480,494 ops/sec ±0.81% (93 runs sampled)
  priviteKindOf x 50,521,049 ops/sec ±0.63% (91 runs sampled)

  fastest is priviteKindOf

# benchmark/fixtures/buffer.js (38 bytes)
  kind-of x 26,790,947 ops/sec ±0.64% (93 runs sampled)
  priviteKindOf x 1,499,540 ops/sec ±0.55% (92 runs sampled)

  fastest is kind-of

# benchmark/fixtures/date.js (30 bytes)
  kind-of x 21,006,428 ops/sec ±1.22% (87 runs sampled)
  priviteKindOf x 5,258,425 ops/sec ±0.40% (93 runs sampled)

  fastest is kind-of

# benchmark/fixtures/error.js (36 bytes)
  kind-of x 17,555,723 ops/sec ±1.21% (89 runs sampled)
  priviteKindOf x 5,578,384 ops/sec ±0.32% (96 runs sampled)

  fastest is kind-of

# benchmark/fixtures/function.js (34 bytes)
  kind-of x 18,311,781 ops/sec ±0.28% (91 runs sampled)
  priviteKindOf x 5,278,844 ops/sec ±0.44% (92 runs sampled)

  fastest is kind-of

# benchmark/fixtures/generator.js (39 bytes)
  kind-of x 16,307,369 ops/sec ±0.82% (90 runs sampled)
  priviteKindOf x 1,493,459 ops/sec ±0.71% (91 runs sampled)

  fastest is kind-of

# benchmark/fixtures/map.js (30 bytes)
  kind-of x 8,123,220 ops/sec ±0.79% (90 runs sampled)
  priviteKindOf x 4,127,706 ops/sec ±0.33% (92 runs sampled)

  fastest is kind-of

# benchmark/fixtures/null.js (24 bytes)
  kind-of x 36,778,380 ops/sec ±3.99% (79 runs sampled)
  priviteKindOf x 5,392,973 ops/sec ±0.54% (91 runs sampled)

  fastest is kind-of

# benchmark/fixtures/number.js (22 bytes)
  kind-of x 37,574,334 ops/sec ±3.44% (84 runs sampled)
  priviteKindOf x 33,370,196 ops/sec ±1.52% (87 runs sampled)

  fastest is kind-of

# benchmark/fixtures/object-instance.js (22 bytes)
  kind-of x 6,790,378 ops/sec ±0.62% (91 runs sampled)
  priviteKindOf x 5,270,510 ops/sec ±0.63% (92 runs sampled)

  fastest is kind-of

# benchmark/fixtures/object-plain.js (47 bytes)
  kind-of x 5,928,275 ops/sec ±0.55% (91 runs sampled)
  priviteKindOf x 5,085,198 ops/sec ±0.58% (91 runs sampled)

  fastest is kind-of

# benchmark/fixtures/regex.js (25 bytes)
  kind-of x 11,512,111 ops/sec ±1.38% (83 runs sampled)
  priviteKindOf x 5,081,246 ops/sec ±0.64% (91 runs sampled)

  fastest is kind-of

# benchmark/fixtures/set.js (30 bytes)
  kind-of x 7,139,086 ops/sec ±0.56% (92 runs sampled)
  priviteKindOf x 3,937,407 ops/sec ±0.48% (91 runs sampled)

  fastest is kind-of

# benchmark/fixtures/string.js (33 bytes)
  kind-of x 26,591,874 ops/sec ±1.28% (89 runs sampled)
  priviteKindOf x 32,886,354 ops/sec ±1.59% (88 runs sampled)

  fastest is priviteKindOf

# benchmark/fixtures/symbol.js (34 bytes)
  kind-of x 27,769,816 ops/sec ±1.37% (88 runs sampled)
  priviteKindOf x 34,443,818 ops/sec ±2.29% (69 runs sampled)

  fastest is priviteKindOf

# benchmark/fixtures/template-strings.js (36 bytes)
  kind-of x 26,634,815 ops/sec ±1.15% (89 runs sampled)
  priviteKindOf x 33,198,302 ops/sec ±1.55% (87 runs sampled)

  fastest is priviteKindOf

# benchmark/fixtures/undefined.js (29 bytes)
  kind-of x 31,228,852 ops/sec ±1.62% (70 runs sampled)
  priviteKindOf x 34,936,430 ops/sec ±1.83% (83 runs sampled)

  fastest is priviteKindOf

# benchmark/fixtures/weakmap.js (34 bytes)
  kind-of x 6,802,391 ops/sec ±0.55% (92 runs sampled)
  priviteKindOf x 1,791,358 ops/sec ±0.87% (92 runs sampled)

  fastest is kind-of

# benchmark/fixtures/weakset.js (34 bytes)
  kind-of x 6,540,679 ops/sec ±0.72% (90 runs sampled)
  priviteKindOf x 1,722,102 ops/sec ±1.68% (85 runs sampled)

  fastest is kind-of

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.