Comparing version 4.1.4 to 5.0.0-next.1
5.0.0-next / 2018-01-11 | ||
================== | ||
* Add postinstall banner pointing to Open Collective | ||
* Docs: add migration guide for v5 | ||
* Docs: Added example for how to use `restore` | ||
* Simplify hasFunctionNameSupport | ||
* Fix broken test in IE11 | ||
* Improve language of fake documentation | ||
* Add yields and yieldsTo to fake | ||
* Extract nextTick to own file | ||
* Fix typo in documentation | ||
* Clarify documentation | ||
* Fix failing tests in Chromium | ||
* Add documentation for sinon.replace and sinon.fake* | ||
* Improve input validation of sandbox.replace* methods | ||
* Rename third argument to `replacement` | ||
* Add replaceGetter and replaceSetter | ||
* Extract isPropertyConfigurable to own file | ||
* WIP | ||
* Extract isRestorable to own file | ||
* Extract isNonExistentOwnProperty to own function | ||
* Fixup: bad merge | ||
* Remove undesirable methods before returning fake | ||
* Fixup: Improve tests of fake | ||
* Add `fake` | ||
* Review: reword deprecation message to not mention sinon.Sandbox | ||
* Export enhanced sandbox as sinon api | ||
* Refactor sandbox to assimilate collection and remove collection | ||
* Update docs/changelog.md and set new release id in docs/_config.yml | ||
* Add release documentation for v4.1.4 | ||
4.1.4 / 2018-01-08 | ||
@@ -3,0 +35,0 @@ ================== |
"use strict"; | ||
exports.assert = require("./sinon/assert"); | ||
exports.collection = require("./sinon/collection"); | ||
exports.match = require("./sinon/match"); | ||
exports.spy = require("./sinon/spy"); | ||
exports.spyCall = require("./sinon/call"); | ||
exports.stub = require("./sinon/stub"); | ||
exports.mock = require("./sinon/mock"); | ||
var behavior = require("./sinon/behavior"); | ||
var createSandbox = require("./sinon/create-sandbox"); | ||
var deprecated = require("./sinon/util/core/deprecated"); | ||
var extend = require("./sinon/util/core/extend"); | ||
var fakeTimers = require("./sinon/util/fake_timers"); | ||
var format = require("./sinon/util/core/format"); | ||
var nise = require("nise"); | ||
var Sandbox = require("./sinon/sandbox"); | ||
var stub = require("./sinon/stub"); | ||
var sandbox = require("./sinon/sandbox"); | ||
exports.sandbox = sandbox; | ||
exports.expectation = require("./sinon/mock-expectation"); | ||
exports.createStubInstance = require("./sinon/stub").createStubInstance; | ||
var apiMethods = { | ||
createSandbox: createSandbox, | ||
assert: require("./sinon/assert"), | ||
fake: require("./sinon/fake"), | ||
match: require("./sinon/match"), | ||
spy: require("./sinon/spy"), | ||
spyCall: require("./sinon/call"), | ||
stub: require("./sinon/stub"), | ||
mock: require("./sinon/mock"), | ||
exports.defaultConfig = require("./sinon/util/core/default-config"); | ||
expectation: require("./sinon/mock-expectation"), | ||
createStubInstance: require("./sinon/stub").createStubInstance, | ||
defaultConfig: require("./sinon/util/core/default-config"), | ||
var fakeTimers = require("./sinon/util/fake_timers"); | ||
exports.useFakeTimers = fakeTimers.useFakeTimers; | ||
exports.clock = fakeTimers.clock; | ||
exports.timers = fakeTimers.timers; | ||
setFormatter: format.setFormatter, | ||
var nise = require("nise"); | ||
exports.xhr = nise.fakeXhr.xhr; | ||
exports.FakeXMLHttpRequest = nise.fakeXhr.FakeXMLHttpRequest; | ||
exports.useFakeXMLHttpRequest = nise.fakeXhr.useFakeXMLHttpRequest; | ||
// fake timers | ||
useFakeTimers: fakeTimers.useFakeTimers, | ||
clock: fakeTimers.clock, | ||
timers: fakeTimers.timers, | ||
exports.fakeServer = nise.fakeServer; | ||
exports.fakeServerWithClock = nise.fakeServerWithClock; | ||
exports.createSandbox = sandbox.create; | ||
exports.createFakeServer = nise.fakeServer.create.bind(nise.fakeServer); | ||
exports.createFakeServerWithClock = nise.fakeServerWithClock.create.bind(nise.fakeServerWithClock); | ||
// fake XHR | ||
xhr: nise.fakeXhr.xhr, | ||
FakeXMLHttpRequest: nise.fakeXhr.FakeXMLHttpRequest, | ||
useFakeXMLHttpRequest: nise.fakeXhr.useFakeXMLHttpRequest, | ||
var behavior = require("./sinon/behavior"); | ||
// fake server | ||
fakeServer: nise.fakeServer, | ||
fakeServerWithClock: nise.fakeServerWithClock, | ||
createFakeServer: nise.fakeServer.create.bind(nise.fakeServer), | ||
createFakeServerWithClock: nise.fakeServerWithClock.create.bind(nise.fakeServerWithClock), | ||
exports.addBehavior = function (name, fn) { | ||
behavior.addBehavior(exports.stub, name, fn); | ||
addBehavior: function (name, fn) { | ||
behavior.addBehavior(stub, name, fn); | ||
} | ||
}; | ||
var format = require("./sinon/util/core/format"); | ||
exports.setFormatter = format.setFormatter; | ||
var legacySandboxAPI = { | ||
sandbox: { | ||
create: deprecated.wrap( | ||
createSandbox, | ||
// eslint-disable-next-line max-len | ||
"`sandbox.create()` is deprecated. Use default sandbox at `sinon.sandbox` or create new sandboxes with `sinon.createSandbox()`" | ||
) | ||
} | ||
}; | ||
var sandbox = new Sandbox(); | ||
var api = extend(sandbox, legacySandboxAPI, apiMethods); | ||
module.exports = api; |
@@ -5,2 +5,3 @@ "use strict"; | ||
var functionName = require("./util/core/function-name"); | ||
var nextTick = require("./util/core/next-tick"); | ||
var valueToString = require("./util/core/value-to-string"); | ||
@@ -13,16 +14,2 @@ | ||
var nextTick = (function () { | ||
if (typeof process === "object" && typeof process.nextTick === "function") { | ||
return process.nextTick; | ||
} | ||
if (typeof setImmediate === "function") { | ||
return setImmediate; | ||
} | ||
return function (callback) { | ||
setTimeout(callback, 0); | ||
}; | ||
})(); | ||
function getCallback(behavior, args) { | ||
@@ -29,0 +16,0 @@ var callArgAt = behavior.callArgAt; |
"use strict"; | ||
var getPropertyDescriptor = require("./util/core/get-property-descriptor"); | ||
var isPropertyConfigurable = require("./util/core/is-property-configurable"); | ||
@@ -27,8 +27,2 @@ var slice = [].slice; | ||
function isPropertyConfigurable(obj, propName) { | ||
var propertyDescriptor = getPropertyDescriptor(obj, propName); | ||
return propertyDescriptor ? propertyDescriptor.configurable : true; | ||
} | ||
module.exports = { | ||
@@ -35,0 +29,0 @@ callsFake: function callsFake(fake, fn) { |
"use strict"; | ||
var extend = require("./util/core/extend"); | ||
var sinonCollection = require("./collection"); | ||
var collectOwnMethods = require("./collect-own-methods"); | ||
var getPropertyDescriptor = require("./util/core/get-property-descriptor"); | ||
var isPropertyConfigurable = require("./util/core/is-property-configurable"); | ||
var isNonExistentOwnProperty = require("./util/core/is-non-existent-own-property"); | ||
var sinonMatch = require("./match"); | ||
var sinonAssert = require("./assert"); | ||
var sinonClock = require("./util/fake_timers"); | ||
var sinonMock = require("./mock"); | ||
var sinonSpy = require("./spy"); | ||
var sinonStub = require("./stub"); | ||
var valueToString = require("./util/core/value-to-string"); | ||
var fakeServer = require("nise").fakeServer; | ||
var fakeXhr = require("nise").fakeXhr; | ||
var fakeServerWithClock = require("nise").fakeServerWithClock; | ||
var usePromiseLibrary = require("./util/core/use-promise-library"); | ||
var push = [].push; | ||
// cache original versions, to prevent issues when they are stubbed in user space | ||
var push = Array.prototype.push; | ||
var filter = Array.prototype.filter; | ||
var forEach = Array.prototype.filter; | ||
var sinonSandbox = Object.create(sinonCollection); | ||
function applyOnEach(fakes, method) { | ||
var matchingFakes = filter.call(fakes, function (fake) { | ||
return typeof fake[method] === "function"; | ||
}); | ||
function exposeValue(sandbox, config, key, value) { | ||
if (!value) { | ||
return; | ||
} | ||
if (config.injectInto && !(key in config.injectInto)) { | ||
config.injectInto[key] = value; | ||
sandbox.injectedKeys.push(key); | ||
} else { | ||
push.call(sandbox.args, value); | ||
} | ||
forEach.call(matchingFakes, function (fake) { | ||
fake[method](); | ||
}); | ||
} | ||
function prepareSandboxFromConfig(config) { | ||
var sandbox = Object.create(sinonSandbox); | ||
function Sandbox() { | ||
var sandbox = this; | ||
var collection = []; | ||
var fakeRestorers = []; | ||
var promiseLib; | ||
if (config.useFakeServer) { | ||
if (typeof config.useFakeServer === "object") { | ||
sandbox.serverPrototype = config.useFakeServer; | ||
} | ||
sandbox.serverPrototype = fakeServerWithClock; | ||
sandbox.useFakeServer(); | ||
} | ||
// this is for testing only | ||
sandbox.getFakes = function getFakes() { | ||
return collection; | ||
}; | ||
if (config.useFakeTimers) { | ||
if (typeof config.useFakeTimers === "object") { | ||
sandbox.useFakeTimers.call(sandbox, config.useFakeTimers); | ||
} else { | ||
sandbox.useFakeTimers(); | ||
// this is for testing only | ||
sandbox.getRestorers = function () { | ||
return fakeRestorers; | ||
}; | ||
sandbox.createStubInstance = function createStubInstance(constructor) { | ||
if (typeof constructor !== "function") { | ||
throw new TypeError("The constructor should be a function."); | ||
} | ||
} | ||
return this.stub.call(this, Object.create(constructor.prototype)); | ||
}; | ||
return sandbox; | ||
} | ||
sandbox.inject = function inject(obj) { | ||
obj.spy = function () { | ||
return sandbox.spy.apply(null, arguments); | ||
}; | ||
extend(sinonSandbox, { | ||
useFakeTimers: function (args) { | ||
this.clock = sinonClock.useFakeTimers.call(null, args); | ||
obj.stub = function () { | ||
return sandbox.stub.apply(null, arguments); | ||
}; | ||
return this.add(this.clock); | ||
}, | ||
obj.mock = function () { | ||
return sandbox.mock.apply(null, arguments); | ||
}; | ||
serverPrototype: fakeServerWithClock, | ||
if (sandbox.clock) { | ||
obj.clock = sandbox.clock; | ||
} | ||
useFakeServer: function useFakeServer() { | ||
var proto = this.serverPrototype || fakeServer; | ||
if (!proto || !proto.create) { | ||
return null; | ||
if (sandbox.server) { | ||
obj.server = sandbox.server; | ||
obj.requests = sandbox.server.requests; | ||
} | ||
this.server = proto.create(); | ||
return this.add(this.server); | ||
}, | ||
obj.match = sinonMatch; | ||
useFakeXMLHttpRequest: function useFakeXMLHttpRequest() { | ||
var xhr = fakeXhr.useFakeXMLHttpRequest(); | ||
return this.add(xhr); | ||
}, | ||
return obj; | ||
}; | ||
inject: function (obj) { | ||
sinonCollection.inject.call(this, obj); | ||
sandbox.mock = function mock() { | ||
var m = sinonMock.apply(null, arguments); | ||
if (this.clock) { | ||
obj.clock = this.clock; | ||
} | ||
push.call(collection, m); | ||
if (this.server) { | ||
obj.server = this.server; | ||
obj.requests = this.server.requests; | ||
} | ||
return m; | ||
}; | ||
obj.match = sinonMatch; | ||
sandbox.reset = function reset() { | ||
applyOnEach(collection, "reset"); | ||
}; | ||
return obj; | ||
}, | ||
sandbox.resetBehavior = function resetBehavior() { | ||
applyOnEach(collection, "resetBehavior"); | ||
}; | ||
usingPromise: function (promiseLibrary) { | ||
sandbox.resetHistory = function resetHistory() { | ||
forEach.call(collection, function (fake) { | ||
var method = fake.resetHistory || fake.reset; | ||
this.promiseLibrary = promiseLibrary; | ||
if (method) { | ||
method.call(fake); | ||
} | ||
}); | ||
}; | ||
return this; | ||
}, | ||
restore: function () { | ||
sandbox.restore = function restore() { | ||
if (arguments.length) { | ||
@@ -105,10 +117,17 @@ throw new Error("sandbox.restore() does not take any parameters. Perhaps you meant stub.restore()"); | ||
sinonCollection.restore.apply(this, arguments); | ||
this.restoreContext(); | ||
}, | ||
applyOnEach(collection, "restore"); | ||
collection = []; | ||
restoreContext: function () { | ||
var injectedKeys = this.injectedKeys; | ||
var injectInto = this.injectInto; | ||
forEach.call(fakeRestorers, function (restorer) { | ||
restorer(); | ||
}); | ||
fakeRestorers = []; | ||
sandbox.restoreContext(); | ||
}; | ||
sandbox.restoreContext = function restoreContext() { | ||
var injectedKeys = sandbox.injectedKeys; | ||
var injectInto = sandbox.injectInto; | ||
if (!injectedKeys) { | ||
@@ -123,32 +142,180 @@ return; | ||
injectedKeys = []; | ||
}, | ||
}; | ||
create: function (config) { | ||
if (!config) { | ||
return Object.create(sinonSandbox); | ||
function getFakeRestorer(object, property) { | ||
var descriptor = getPropertyDescriptor(object, property); | ||
return function restorer() { | ||
Object.defineProperty(object, property, descriptor); | ||
}; | ||
} | ||
sandbox.replace = function replace(object, property, replacement) { | ||
var descriptor = Object.getOwnPropertyDescriptor(object, property); | ||
if (typeof descriptor === "undefined") { | ||
throw new TypeError("Cannot replace non-existent own property " + valueToString(property)); | ||
} | ||
var sandbox = prepareSandboxFromConfig(config); | ||
sandbox.args = sandbox.args || []; | ||
sandbox.injectedKeys = []; | ||
sandbox.injectInto = config.injectInto; | ||
var exposed = sandbox.inject({}); | ||
if (typeof replacement === "undefined") { | ||
throw new TypeError("Expected replacement argument to be defined"); | ||
} | ||
if (config.properties) { | ||
config.properties.forEach(function (prop) { | ||
var value = exposed[prop] || prop === "sandbox" && sandbox; | ||
exposeValue(sandbox, config, prop, value); | ||
if (typeof descriptor.get === "function") { | ||
throw new Error("Use sandbox.replaceGetter for replacing getters"); | ||
} | ||
if (typeof descriptor.set === "function") { | ||
throw new Error("Use sandbox.replaceSetter for replacing setters"); | ||
} | ||
if (typeof object[property] !== typeof replacement) { | ||
throw new TypeError("Cannot replace " + typeof object[property] + " with " + typeof replacement); | ||
} | ||
// store a function for restoring the replaced property | ||
push.call(fakeRestorers, getFakeRestorer(object, property)); | ||
object[property] = replacement; | ||
}; | ||
sandbox.replaceGetter = function replaceGetter(object, property, replacement) { | ||
var descriptor = Object.getOwnPropertyDescriptor(object, property); | ||
if (typeof descriptor === "undefined") { | ||
throw new TypeError("Cannot replace non-existent own property " + valueToString(property)); | ||
} | ||
if (typeof replacement !== "function") { | ||
throw new TypeError("Expected replacement argument to be a function"); | ||
} | ||
if (typeof descriptor.get !== "function") { | ||
throw new Error("`object.property` is not a getter"); | ||
} | ||
// store a function for restoring the replaced property | ||
push.call(fakeRestorers, getFakeRestorer(object, property)); | ||
Object.defineProperty(object, property, { | ||
get: replacement, | ||
configurable: isPropertyConfigurable(object, property) | ||
}); | ||
}; | ||
sandbox.replaceSetter = function replaceSetter(object, property, replacement) { | ||
var descriptor = Object.getOwnPropertyDescriptor(object, property); | ||
if (typeof descriptor === "undefined") { | ||
throw new TypeError("Cannot replace non-existent own property " + valueToString(property)); | ||
} | ||
if (typeof replacement !== "function") { | ||
throw new TypeError("Expected replacement argument to be a function"); | ||
} | ||
if (typeof descriptor.set !== "function") { | ||
throw new Error("`object.property` is not a setter"); | ||
} | ||
// store a function for restoring the replaced property | ||
push.call(fakeRestorers, getFakeRestorer(object, property)); | ||
// eslint-disable-next-line accessor-pairs | ||
Object.defineProperty(object, property, { | ||
set: replacement, | ||
configurable: isPropertyConfigurable(object, property) | ||
}); | ||
}; | ||
sandbox.spy = function spy() { | ||
var s = sinonSpy.apply(sinonSpy, arguments); | ||
push.call(collection, s); | ||
return s; | ||
}; | ||
sandbox.stub = function stub(object, property) { | ||
if (isNonExistentOwnProperty(object, property)) { | ||
throw new TypeError("Cannot stub non-existent own property " + valueToString(property)); | ||
} | ||
var stubbed = sinonStub.apply(null, arguments); | ||
var isStubbingEntireObject = typeof property === "undefined" && typeof object === "object"; | ||
if (isStubbingEntireObject) { | ||
var ownMethods = collectOwnMethods(stubbed); | ||
ownMethods.forEach(function (method) { | ||
push.call(collection, method); | ||
}); | ||
usePromiseLibrary(promiseLib, ownMethods); | ||
} else { | ||
exposeValue(sandbox, config, "sandbox"); | ||
push.call(collection, stubbed); | ||
usePromiseLibrary(promiseLib, stubbed); | ||
} | ||
return stubbed; | ||
}; | ||
sandbox.useFakeTimers = function useFakeTimers(args) { | ||
var clock = sinonClock.useFakeTimers.call(null, args); | ||
sandbox.clock = clock; | ||
push.call(collection, clock); | ||
return clock; | ||
}; | ||
sandbox.verify = function verify() { | ||
applyOnEach(collection, "verify"); | ||
}; | ||
sandbox.verifyAndRestore = function verifyAndRestore() { | ||
var exception; | ||
try { | ||
sandbox.verify(); | ||
} catch (e) { | ||
exception = e; | ||
} | ||
sandbox.restore(); | ||
if (exception) { | ||
throw exception; | ||
} | ||
}; | ||
sandbox.useFakeServer = function useFakeServer() { | ||
var proto = sandbox.serverPrototype || fakeServer; | ||
if (!proto || !proto.create) { | ||
return null; | ||
} | ||
sandbox.server = proto.create(); | ||
push.call(collection, sandbox.server); | ||
return sandbox.server; | ||
}; | ||
sandbox.useFakeXMLHttpRequest = function useFakeXMLHttpRequest() { | ||
var xhr = fakeXhr.useFakeXMLHttpRequest(); | ||
return push.call(collection, xhr); | ||
}; | ||
sandbox.usingPromise = function usingPromise(promiseLibrary) { | ||
promiseLib = promiseLibrary; | ||
collection.promiseLibrary = promiseLibrary; | ||
return sandbox; | ||
}, | ||
}; | ||
} | ||
match: sinonMatch, | ||
Sandbox.prototype.assert = sinonAssert; | ||
Sandbox.prototype.match = sinonMatch; | ||
assert: sinonAssert | ||
}); | ||
module.exports = sinonSandbox; | ||
module.exports = Sandbox; |
@@ -5,3 +5,2 @@ "use strict"; | ||
var extend = require("./util/core/extend"); | ||
var deprecated = require("./util/core/deprecated"); | ||
var functionName = require("./util/core/function-name"); | ||
@@ -418,4 +417,2 @@ var functionToString = require("./util/core/function-to-string"); | ||
spyApi.reset = deprecated.wrap(spyApi.resetHistory, deprecated.defaultMsg("reset")); | ||
delegateToCalls("calledOn", true); | ||
@@ -422,0 +419,0 @@ delegateToCalls("alwaysCalledOn", false, "calledOn"); |
@@ -5,2 +5,3 @@ "use strict"; | ||
var behaviors = require("./default-behaviors"); | ||
var isNonExistentOwnProperty = require("./util/core/is-non-existent-own-property"); | ||
var spy = require("./spy"); | ||
@@ -24,3 +25,3 @@ var extend = require("./util/core/extend"); | ||
if (object && typeof property !== "undefined" && !(property in object)) { | ||
if (isNonExistentOwnProperty(object, property)) { | ||
throw new TypeError("Cannot stub non-existent own property " + valueToString(property)); | ||
@@ -27,0 +28,0 @@ } |
"use strict"; | ||
var isRestorable = require("./is-restorable"); | ||
var walk = require("./walk"); | ||
function isRestorable(obj) { | ||
return typeof obj === "function" && typeof obj.restore === "function" && obj.restore.sinon; | ||
} | ||
module.exports = function restore(object) { | ||
@@ -10,0 +7,0 @@ if (object !== null && typeof object === "object") { |
{ | ||
"name": "sinon", | ||
"description": "JavaScript test spies, stubs and mocks.", | ||
"version": "4.1.4", | ||
"version": "5.0.0-next.1", | ||
"homepage": "http://sinonjs.org/", | ||
@@ -33,3 +33,4 @@ "author": "Christian Johansen", | ||
"preversion": "./scripts/preversion.sh", | ||
"postversion": "./scripts/postversion.sh" | ||
"postversion": "./scripts/postversion.sh", | ||
"postinstall": "node -e \"console.log('\\u001b[32mLove sinon? You can now support the project via the open collective:\\u001b[22m\\u001b[39m\\n > \\u001b[96m\\u001b[1mhttps://opencollective.com/sinon/donate\\u001b[0m\\n')\" || exit 0" | ||
}, | ||
@@ -36,0 +37,0 @@ "lint-staged": { |
Sorry, the diff of this file is too big to display
Sorry, the diff of this file is too big to display
Install scripts
Supply chain riskInstall scripts are run when the package is installed. The majority of malware in npm is hidden in install scripts.
Found 1 instance in 1 package
No v1
QualityPackage is not semver >=1. This means it is not stable and does not support ^ ranges.
Found 1 instance in 1 package
3454117
53
36611
1
1