Skip to content
Permalink

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also or learn more about diff comparisons.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also . Learn more about diff comparisons here.
base repository: kelektiv/node.bcrypt.js
Failed to load repositories. Confirm that selected base ref is valid, then try again.
Loading
base: 054cf76ba6e2127560ed897d00b5b88d11dc5626
Choose a base ref
...
head repository: kelektiv/node.bcrypt.js
Failed to load repositories. Confirm that selected head ref is valid, then try again.
Loading
compare: ab026b202f3dfea2b3d301868a45c25a6a2b8348
Choose a head ref

Commits on Sep 7, 2017

  1. fix typo: compilant => compliant

    Bohdan Levantovych committed Sep 7, 2017
    Copy the full SHA
    5fbc8ec View commit details

Commits on Sep 14, 2017

  1. Merge pull request #542 from bodya17/master

    fix typo: compilant => compliant
    recrsn authored Sep 14, 2017
    Copy the full SHA
    7d53afa View commit details
  2. Copy the full SHA
    6746a04 View commit details
  3. Copy the full SHA
    ebb7417 View commit details
  4. Copy the full SHA
    f3a34bd View commit details

Commits on Sep 23, 2017

  1. Merge pull request #545 from agathver/test-improvements

    Improve test cases
    ncb000gt authored Sep 23, 2017
    Copy the full SHA
    7914916 View commit details
  2. Merge pull request #539 from tonylukasavage/issue-538

    preserve stack traces on async error callbacks
    ncb000gt authored Sep 23, 2017
    Copy the full SHA
    99e2a09 View commit details

Commits on Oct 1, 2017

  1. Remove support for NodeJS < 4

    Closes #529
    recrsn committed Oct 1, 2017
    Copy the full SHA
    9540ed0 View commit details

Commits on Oct 21, 2017

  1. Merge pull request #550 from agathver/drop-old-node

    Remove support for NodeJS < 4
    recrsn authored Oct 21, 2017
    Copy the full SHA
    90d438b View commit details

Commits on Nov 1, 2017

  1. Add NodeJS 9 to CI matrix

    recrsn committed Nov 1, 2017
    Copy the full SHA
    7b928fb View commit details

Commits on Dec 8, 2017

  1. Bump deps

    recrsn committed Dec 8, 2017
    Copy the full SHA
    d1cb91d View commit details
  2. Merge pull request #554 from agathver/node-9

    Add NodeJS 9 to CI matrix
    recrsn authored Dec 8, 2017
    Copy the full SHA
    096a34f View commit details

Commits on Dec 21, 2017

  1. README: comparisons resist timing attacks

    Clarify in README that the comparisons resist timing attacks.
    
    This fixes issue #563.
    david-a-wheeler authored Dec 21, 2017
    Copy the full SHA
    f2bec20 View commit details

Commits on Dec 29, 2017

  1. Merge pull request #564 from david-a-wheeler/readme-timing

    README: comparisons resist timing attacks
    recrsn authored Dec 29, 2017
    Copy the full SHA
    43734e3 View commit details

Commits on Mar 11, 2018

  1. fix: package.json to reduce vulnerabilities

    The following vulnerabilities are fixed with an upgrade:
    - https://snyk.io/vuln/npm:hoek:20180212
    
    Latest report for kelektiv/node.bcrypt.js:
    https://snyk.io/test/github/kelektiv/node.bcrypt.js
    snyk-bot committed Mar 11, 2018
    Copy the full SHA
    1da0f44 View commit details

Commits on Mar 15, 2018

  1. Merge pull request #584 from kelektiv/snyk-fix-bc668290

    [Snyk Update] New fixes for 8 vulnerable dependency paths
    recrsn authored Mar 15, 2018
    Copy the full SHA
    88590ea View commit details
  2. fix: propagate async context

    Starting with Nan 2.9.0, we have the ability to propagate async context
    across async hops. Certain variants of Nan::Callback::Call are now
    deprecated to encourage context preserving.
    
    Here's a simple patch that fixes the deprecation warnings and properly
    propagates the async context across the async APIs exposed by this
    module.
    
    For more information see [1], [2].
    
    [1]: https://github.com/nodejs/nan/blob/HEAD/doc/node_misc.md#nanasyncresource.
    [2]: https://nodejs.org/dist/latest-v9.x/docs/api/async_hooks.html#async_hooks_javascript_embedder_api
    ofrobots committed Mar 15, 2018
    Copy the full SHA
    6a79eaf View commit details
  3. Merge pull request #583 from ofrobots/async-resource

    fix: propagate async context
    recrsn authored Mar 15, 2018
    Copy the full SHA
    e8cde51 View commit details
  4. Add support for $2b$ hashes

    recrsn committed Mar 15, 2018
    2
    Copy the full SHA
    4c44f20 View commit details

Commits on Mar 16, 2018

  1. Merge pull request #549 from agathver/2b-hashes

    Add support for 2b hashes
    recrsn authored Mar 16, 2018
    Copy the full SHA
    0ea1b36 View commit details

Commits on Apr 4, 2018

  1. Copy the full SHA
    2d45be1 View commit details

Commits on Apr 6, 2018

  1. Merge pull request #587 from agathver/hash-version-support

    Allow to choose bcrypt minor version
    recrsn authored Apr 6, 2018
    Copy the full SHA
    aac593c View commit details
  2. Make binaries libc aware

    Only glibc supported as of now.
    
    Closes #559, #530, #528
    recrsn committed Apr 6, 2018
    Copy the full SHA
    9a9ab45 View commit details
  3. install and use any-promise (#504)

    * export a use function from lib/promises
    
    closes #478
    
    the `use` function can be used to change the promise implementation
    that is used by the library
    gurpreetatwal authored and recrsn committed Apr 6, 2018
    Copy the full SHA
    dab435e View commit details
  4. Merge pull request #589 from agathver/libc-aware

    Make binaries libc aware
    recrsn authored Apr 6, 2018
    Copy the full SHA
    f00d4b8 View commit details

Commits on Apr 7, 2018

  1. v2.0.0

    recrsn committed Apr 7, 2018
    Copy the full SHA
    ab026b2 View commit details
Showing with 367 additions and 181 deletions.
  1. +16 −0 .editorconfig
  2. +3 −5 .travis.yml
  3. +4 −0 CHANGELOG.md
  4. +20 −4 README.md
  5. +5 −10 appveyor.yml
  6. +47 −14 bcrypt.js
  7. +9 −13 lib/promises.js
  8. +8 −7 package.json
  9. +44 −50 src/bcrypt.cc
  10. +44 −22 src/bcrypt_node.cc
  11. +3 −3 src/node_blf.h
  12. +36 −16 test/async.js
  13. +43 −0 test/implementation.js
  14. +53 −21 test/promise.js
  15. +32 −16 test/sync.js
16 changes: 16 additions & 0 deletions .editorconfig
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
root = true

[*]
indent_style = space
indent_size = 4
end_of_line = lf
charset = utf-8
trim_trailing_whitespace = true
insert_final_newline = true

[{package.json,*.yml}]
indent_style = space
indent_size = 2

[*.md]
trim_trailing_whitespace = false
8 changes: 3 additions & 5 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -8,14 +8,12 @@ os:
- osx

node_js:
- "0.8"
- "0.10"
- "0.12"
- "4"
- "5"
- "6"
- "7"
- "8"
- "9"

addons:
apt:
@@ -29,12 +27,12 @@ before_install:
- echo Building for Node $TRAVIS_NODE_VERSION
- if [[ "$TRAVIS_OS_NAME" == "linux" ]]; then export CXX=$LINUX_CXX; $CXX --version; fi;
- if [[ "$TRAVIS_OS_NAME" == "osx" ]]; then c++ --version; fi;
- if [[ $(echo "$TRAVIS_NODE_VERSION <= 0.12" | bc -l) ]]; then npm install -g npm@2; else npm install -g npm@latest; fi;
- npm install -g npm@latest

install: true

script: npm test

after_success:
- REGEX='^v(0|[1-9]+)\.(0|[1-9]+)\.(0|[1-9]+)$'
- if [[ $TRAVIS_TAG =~ $REGEX ]] || [[ $TRAVIS_COMMIT_MESSAGE == *"publish binary"* ]]; then echo "Publishing"; npm install node-pre-gyp-github; ./node_modules/.bin/node-pre-gyp configure; ./node_modules/.bin/node-pre-gyp build; ./node_modules/.bin/node-pre-gyp package; ./node_modules/.bin/node-pre-gyp-github publish --release; fi;
- if [[ $TRAVIS_TAG =~ $REGEX ]] || [[ $TRAVIS_COMMIT_MESSAGE == *"publish binary"* ]]; then echo "Publishing"; npm install node-pre-gyp-github; ./node_modules/.bin/node-pre-gyp configure; ./node_modules/.bin/node-pre-gyp build; ./node_modules/.bin/node-pre-gyp package; ./node_modules/.bin/node-pre-gyp-github publish --release; fi;
4 changes: 4 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
# 2.0.0 (2018-04-07)

* Make `2b` the default bcrypt version

# 1.0.2 (2016-12-31)

* Fix `compare` promise rejection with invalid arguments
24 changes: 20 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
@@ -42,6 +42,12 @@ To make it easier for people using this tool to analyze what has been surveyed,

* An [issue with passwords][jtr] was found with a version of the Blowfish algorithm developed for John the Ripper. This is not present in the OpenBSD version and is thus not a problem for this module. HT [zooko][zooko].

## Compatibility Note

This library supports `$2a$` and `$2b$` prefix bcrypt hashes. `$2x$` and `$2y$` hashes are specific to bcrypt implementation developed for Jon the Ripper. In theory, they should be compatible with `$2b$` prefix.

Compatibility with hashes generated by other languages is not 100% guaranteed due to difference in character encodings. However, it should not be an issue for most cases.

## Dependencies

* NodeJS
@@ -103,9 +109,14 @@ bcrypt.compare(someOtherPlaintextPassword, hash, function(err, res) {
// res == false
});
```

The "compare" function counters timing attacks (using a so-called 'constant-time' algorithm).
In general, don't use the normal JavaScript string comparison functions to compare passwords,
cryptographic keys, or cryptographic hashes if they are relevant to security.

### with promises

bcrypt uses whatever Promise implementation is available in `global.Promise`. NodeJS >= 0.12 has a native Promise implementation built in. However, this should work in any Promises/A+ compilant implementation.
bcrypt uses whatever Promise implementation is available in `global.Promise`. NodeJS >= 0.12 has a native Promise implementation built in. However, this should work in any Promises/A+ compliant implementation.

Async methods that accept a callback, return a `Promise` when callback is not specified if Promise support is available.

@@ -159,6 +170,9 @@ As with async, both techniques achieve the same end-result.
bcrypt.compareSync(myPlaintextPassword, hash); // true
bcrypt.compareSync(someOtherPlaintextPassword, hash); // false
```
The "compareSync" function counters timing attacks (using a so-called 'constant-time' algorithm).
In general, don't use the normal JavaScript string comparison functions to compare passwords,
cryptographic keys, or cryptographic hashes if they are relevant to security.

### Why is async mode recommended over sync mode?
If you are using bcrypt on a simple script, using the sync mode is perfectly fine. However, if you are using bcrypt on a server, the async mode is recommended. This is because the hashing done by bcrypt is CPU intensive, so the sync version will block the event loop and prevent your application from servicing any other inbound requests or events.
@@ -167,10 +181,12 @@ If you are using bcrypt on a simple script, using the sync mode is perfectly fin

`BCrypt.`

* `genSaltSync(rounds)`
* `genSaltSync(rounds, minor)`
* `rounds` - [OPTIONAL] - the cost of processing the data. (default - 10)
* `genSalt(rounds, cb)`
* `minor` - [OPTIONAL] - minor version of bcrypt to use. (default - b)
* `genSalt(rounds, minor, cb)`
* `rounds` - [OPTIONAL] - the cost of processing the data. (default - 10)
* `minor` - [OPTIONAL] - minor version of bcrypt to use. (default - b)
* `cb` - [OPTIONAL] - a callback to be fired once the salt has been generated. uses eio making it asynchronous. If `cb` is not specified, a `Promise` is returned if Promise support is available.
* `err` - First parameter to the callback detailing any errors.
* `salt` - Second parameter to the callback providing the generated salt.
@@ -253,7 +269,7 @@ The code for this comes from a few sources:
* [Nate Rajlich][tootallnate] - Bindings and build process.
* [Sean McArthur][seanmonstar] - Windows Support
* [Fanie Oosthuysen][weareu] - Windows Support
* [Amitosh Swain Mahapatra][agathver] - ES6 Promise Support
* [Amitosh Swain Mahapatra][agathver] - $2b$ hash support, ES6 Promise support

## License
Unless stated elsewhere, file headers or otherwise, the license as stated in the LICENSE file.
15 changes: 5 additions & 10 deletions appveyor.yml
Original file line number Diff line number Diff line change
@@ -1,13 +1,5 @@
environment:
matrix:
- nodejs_version: "0.10"
platform: x64
- nodejs_version: "0.10"
platform: x86
- nodejs_version: "0.12"
platform: x64
- nodejs_version: "0.12"
platform: x86
- nodejs_version: "4"
platform: x64
- nodejs_version: "4"
@@ -28,13 +20,16 @@ environment:
platform: x64
- nodejs_version: "8"
platform: x86
- nodejs_version: "9"
platform: x64
- nodejs_version: "9"
platform: x86

install:
- where npm
- where node
- ps: Install-Product node $env:nodejs_version $env:platform
- 'if %nodejs_version% lss 4 npm install -g npm@2'
- 'if %nodejs_version% geq 4 npm install -g npm@latest'
- 'npm install -g npm@latest'
- 'if "%nodejs_version%_%platform%" == "4_x86" (npm config set -g cafile=package.json && npm config set -g strict-ssl=false)'

build: off
61 changes: 47 additions & 14 deletions bcrypt.js
Original file line number Diff line number Diff line change
@@ -12,43 +12,64 @@ var promises = require('./lib/promises');
/// generate a salt (sync)
/// @param {Number} [rounds] number of rounds (default 10)
/// @return {String} salt
module.exports.genSaltSync = function genSaltSync(rounds) {
module.exports.genSaltSync = function genSaltSync(rounds, minor) {
// default 10 rounds
if (!rounds) {
rounds = 10;
} else if (typeof rounds !== 'number') {
throw new Error('rounds must be a number');
}

return bindings.gen_salt_sync(rounds, crypto.randomBytes(16));
if(!minor) {
minor = 'b';
} else if(minor !== 'b' && minor !== 'a') {
console.log(minor, typeof minor);
throw new Error('minor must be either "a" or "b"');
}

return bindings.gen_salt_sync(minor, rounds, crypto.randomBytes(16));
};

/// generate a salt
/// @param {Number} [rounds] number of rounds (default 10)
/// @param {Function} cb callback(err, salt)
module.exports.genSalt = function genSalt(rounds, ignore, cb) {
module.exports.genSalt = function genSalt(rounds, minor, cb) {
var error;

// if callback is first argument, then use defaults for others
if (typeof arguments[0] === 'function') {
// have to set callback first otherwise arguments are overriden
cb = arguments[0];
rounds = 10;
minor = 'b';
// callback is second argument
} else if (typeof arguments[1] === 'function') {
// have to set callback first otherwise arguments are overriden
cb = arguments[1];
minor = 'b';
}

if (!cb) {
return promises.promise(genSalt, this, [rounds, ignore]);
return promises.promise(genSalt, this, [rounds, minor]);
}

// default 10 rounds
if (!rounds) {
rounds = 10;
} else if (typeof rounds !== 'number') {
// callback error asynchronously
error = new Error('rounds must be a number');
return process.nextTick(function() {
cb(new Error('rounds must be a number'));
cb(error);
});
}

if(!minor) {
minor = 'b'
} else if(minor !== 'b' && minor !== 'a') {
error = new Error('minor must be either "a" or "b"');
return process.nextTick(function() {
cb(error);
});
}

@@ -58,7 +79,7 @@ module.exports.genSalt = function genSalt(rounds, ignore, cb) {
return;
}

bindings.gen_salt(rounds, randomBytes, cb);
bindings.gen_salt(minor, rounds, randomBytes, cb);
});
};

@@ -87,15 +108,19 @@ module.exports.hashSync = function hashSync(data, salt) {
/// @param {String} salt the salt to use when hashing
/// @param {Function} cb callback(err, hash)
module.exports.hash = function hash(data, salt, cb) {
var error;

if (typeof data === 'function') {
error = new Error('data must be a string and salt must either be a salt string or a number of rounds');
return process.nextTick(function() {
data(new Error('data must be a string and salt must either be a salt string or a number of rounds'));
data(error);
});
}

if (typeof salt === 'function') {
error = new Error('data must be a string and salt must either be a salt string or a number of rounds');
return process.nextTick(function() {
salt(new Error('data must be a string and salt must either be a salt string or a number of rounds'));
salt(error);
});
}

@@ -110,14 +135,16 @@ module.exports.hash = function hash(data, salt, cb) {
}

if (data == null || salt == null) {
error = new Error('data and salt arguments required');
return process.nextTick(function() {
cb(new Error('data and salt arguments required'));
cb(error);
});
}

if (typeof data !== 'string' || (typeof salt !== 'string' && typeof salt !== 'number')) {
error = new Error('data must be a string and salt must either be a salt string or a number of rounds');
return process.nextTick(function() {
cb(new Error('data must be a string and salt must either be a salt string or a number of rounds'));
cb(error);
});
}

@@ -152,15 +179,19 @@ module.exports.compareSync = function compareSync(data, hash) {
/// @param {String} hash expected hash
/// @param {Function} cb callback(err, matched) - matched is true if hashed data matches hash
module.exports.compare = function compare(data, hash, cb) {
var error;

if (typeof data === 'function') {
error = new Error('data and hash arguments required');
return process.nextTick(function() {
data(new Error('data and hash arguments required'));
data(error);
});
}

if (typeof hash === 'function') {
error = new Error('data and hash arguments required');
return process.nextTick(function() {
hash(new Error('data and hash arguments required'));
hash(error);
});
}

@@ -175,14 +206,16 @@ module.exports.compare = function compare(data, hash, cb) {
}

if (data == null || hash == null) {
error = new Error('data and hash arguments required');
return process.nextTick(function() {
cb(new Error('data and hash arguments required'));
cb(error);
});
}

if (typeof data !== 'string' || typeof hash !== 'string') {
error = new Error('data and hash must be strings');
return process.nextTick(function() {
cb(new Error('data and hash must be strings'));
cb(error);
});
}

22 changes: 9 additions & 13 deletions lib/promises.js
Original file line number Diff line number Diff line change
@@ -1,17 +1,14 @@
'use strict';

var Promise = global.Promise;

/// encapsulate a method with a node-style callback in a Promise
/// @param {object} 'this' of the encapsulated function
/// @param {function} function to be encapsulated
/// @param {Array-like} args to be passed to the called function
/// @return {Promise} a Promise encapuslaing the function
/// @return {Promise} a Promise encapsulating the function
module.exports.promise = function (fn, context, args) {

//can't do anything without Promise so fail silently
if (typeof Promise === 'undefined') {
return;
}

if (!Array.isArray(args)) {
args = Array.prototype.slice.call(args);
}
@@ -35,12 +32,11 @@ module.exports.promise = function (fn, context, args) {

/// @param {err} the error to be thrown
module.exports.reject = function (err) {

// silently swallow errors if Promise is not defined
// emulating old behavior
if (typeof Promise === 'undefined') {
return;
}

return Promise.reject(err);
};

/// changes the promise implementation that bcrypt uses
/// @param {Promise} the implementation to use
module.exports.use = function(promise) {
Promise = promise;
};
15 changes: 8 additions & 7 deletions package.json
Original file line number Diff line number Diff line change
@@ -11,10 +11,10 @@
"crypto"
],
"main": "./bcrypt",
"version": "1.0.3",
"version": "2.0.0",
"author": "Nick Campbell (https://github.com/ncb000gt)",
"engines": {
"node": ">= 0.6.0"
"node": ">= 4.0.0"
},
"repository": {
"type": "git",
@@ -29,11 +29,11 @@
"install": "node-pre-gyp install --fallback-to-build"
},
"dependencies": {
"nan": "2.6.2",
"node-pre-gyp": "0.6.36"
"nan": "2.10.0",
"node-pre-gyp": "0.9.0"
},
"devDependencies": {
"nodeunit": "~0.9.1"
"nodeunit": "~0.11.1"
},
"contributors": [
"Antonio Salazar Cardozo <savedfastcool@gmail.com> (https://github.com/Shadowfiend)",
@@ -56,6 +56,7 @@
"module_name": "bcrypt_lib",
"module_path": "./lib/binding/",
"host": "https://github.com",
"remote_path": "/kelektiv/node.bcrypt.js/releases/download/v{version}/"
"remote_path": "/kelektiv/node.bcrypt.js/releases/download/v{version}/",
"package_name": "{module_name}-v{version}-{node_abi}-{platform}-{arch}-{libc}.tar.gz"
}
}
}
Loading