Skip to content

Commit

Permalink
fix: assertion log limit (#2485)
Browse files Browse the repository at this point in the history
* Cleanup unimported setup & include test files

* Remove redundant assign

The 'assert' object is already present on the sandbox

* fix(#2484): add assertion log limit

* Document the existing sandbox and create-sandbox

* Expose opts.assertOptions on createSandbox(opts)

* Verify options are passed down

* Remove needless accessors

* Make test behavior oriented rather than implementation specific.

---------

Co-authored-by: Spencer Goossens <sgoossens18@gmail.com>
Co-authored-by: Carl-Erik Kopseng <carlerik@gmail.com>
  • Loading branch information
3 people committed Oct 27, 2023
1 parent 40caf21 commit f7d180c
Show file tree
Hide file tree
Showing 7 changed files with 131 additions and 10 deletions.
23 changes: 19 additions & 4 deletions .unimportedrc.json
@@ -1,8 +1,23 @@
{
"entry": ["lib/sinon.js", "lib/sinon-esm.js"],
"extensions": [".js"],
"ignorePatterns": ["**/node_modules/**"],
"entry": [
"lib/sinon.js",
"lib/sinon-esm.js",
"test/**/*-test.js",
"test/webworker/webworker-script.js",
"test/webworker/webworker-support-assessment.js"
],
"extensions": [
".js"
],
"ignorePatterns": [
"**/node_modules/**"
],
"ignoreUnresolved": [],
"ignoreUnimported": ["docs/**", "pkg/**", "test/**"],
"ignoreUnimported": [
"docs/**",
"pkg/**",
"vendor/**/*",
"test/es2015/check-esm-bundle-is-runnable.js"
],
"ignoreUnused": []
}
1 change: 0 additions & 1 deletion lib/create-sinon-api.js
Expand Up @@ -21,7 +21,6 @@ module.exports = function createApi(opts = { sinonXhrLib: nise }) {

const apiMethods = {
createSandbox: createSandbox,
assert: require("./sinon/assert"),
match: require("@sinonjs/samsam").createMatcher,
restoreObject: require("./sinon/restore-object"),

Expand Down
41 changes: 39 additions & 2 deletions lib/sinon/assert.js
@@ -1,4 +1,5 @@
"use strict";
/** @module */

const arrayProto = require("@sinonjs/commons").prototypes.array;
const calledInOrder = require("@sinonjs/commons").calledInOrder;
Expand All @@ -15,12 +16,48 @@ const forEach = arrayProto.forEach;
const join = arrayProto.join;
const splice = arrayProto.splice;

function createAssertObject() {
function applyDefaults(obj, defaults) {
for (const key of Object.keys(defaults)) {
const val = obj[key];
if (val === null || typeof val === "undefined") {
obj[key] = defaults[key];
}
}
}

/**
* @typedef {object} CreateAssertOptions
* @global
*
* @property {boolean} [shouldLimitAssertionLogs] default is false
* @property {number} [assertionLogLimit] default is 10K
*/

/**
* Create an assertion object that exposes several methods to invoke
*
* @param {CreateAssertOptions} [opts] options bag
* @returns {object} object with multiple assertion methods
*/
function createAssertObject(opts) {
const cleanedAssertOptions = opts || {};
applyDefaults(cleanedAssertOptions, {
shouldLimitAssertionLogs: false,
assertionLogLimit: 1e4,
});

const assert = {
failException: "AssertError",

fail: function fail(message) {
const error = new Error(message);
let msg = message;
if (cleanedAssertOptions.shouldLimitAssertionLogs) {
msg = message.substring(
0,
cleanedAssertOptions.assertionLogLimit,
);
}
const error = new Error(msg);
error.name = this.failException || assert.failException;

throw error;
Expand Down
30 changes: 29 additions & 1 deletion lib/sinon/create-sandbox.js
Expand Up @@ -7,7 +7,7 @@ const forEach = arrayProto.forEach;
const push = arrayProto.push;

function prepareSandboxFromConfig(config) {
const sandbox = new Sandbox();
const sandbox = new Sandbox({ assertOptions: config.assertOptions });

if (config.useFakeServer) {
if (typeof config.useFakeServer === "object") {
Expand Down Expand Up @@ -41,6 +41,34 @@ function exposeValue(sandbox, config, key, value) {
}
}

/**
* Customize the sandbox.
* This is mostly an integration feature most users will not need
*
* @typedef {object} SandboxConfig
* @property {string[]} properties The properties of the API to expose on the sandbox. Examples: ['spy', 'fake', 'restore']
* @property {(object|null)} injectInto TBD
* @property {boolean} useFakeTimers whether timers are faked by default
* @property {boolean} useFakeServer whether XHR's are faked and the server feature enabled by default
* @property {object} [assertOptions] see CreateAssertOptions in ./assert
*/
// This type def is really suffering from JSDoc not being
// able to reference types in other modules

/**
* A configured sinon sandbox.
*
* @typedef {object} ConfiguredSinonSandboxType
* @augments Sandbox
* @property {string[]} injectedKeys the keys that have been injected (from config.injectInto)
* @property {*} injectInto TBD
* @property {*[]} args the arguments for the sandbox
*/

/**
* @param config {SandboxConfig}
* @returns {Sandbox}
*/
function createSandbox(config) {
if (!config) {
return new Sandbox();
Expand Down
12 changes: 10 additions & 2 deletions lib/sinon/sandbox.js
Expand Up @@ -69,8 +69,16 @@ function checkForValidArguments(descriptor, property, replacement) {
}
}

function Sandbox() {
/**
* A sinon sandbox
*
* @param opts
* @param {object} [opts.assertOptions] see the CreateAssertOptions in ./assert
* @class
*/
function Sandbox(opts = {}) {
const sandbox = this;
const assertOptions = opts.assertOptions || {};
let fakeRestorers = [];
let promiseLib;

Expand All @@ -91,7 +99,7 @@ function Sandbox() {
}
}

sandbox.assert = sinonAssert.createAssertObject();
sandbox.assert = sinonAssert.createAssertObject(assertOptions);

sandbox.serverPrototype = fakeServer;

Expand Down
12 changes: 12 additions & 0 deletions test/assert-test.js
Expand Up @@ -65,6 +65,18 @@ describe("assert", function () {
sinonAssert.failException = this.exceptionName;
});

it("can be configured to limit the error message length", function () {
const customAssert = sinonAssert.createAssertObject({
shouldLimitAssertionLogs: true,
assertionLogLimit: 10,
});

assert.exception(
() => customAssert.fail("1234567890--THIS SHOULD NOT SHOW--"),
{ message: "1234567890" },
);
});

it("throws exception", function () {
assert.exception(
function () {
Expand Down
22 changes: 22 additions & 0 deletions test/create-sandbox-test.js
@@ -0,0 +1,22 @@
"use strict";

const createSandbox = require("../lib/sinon/create-sandbox");
const { assert } = require("@sinonjs/referee");

describe("create-sandbox", function () {
it("can be configured to limit the error message length", function () {
// Arrange & Act
const sb = createSandbox({
assertOptions: {
shouldLimitAssertionLogs: true,
assertionLogLimit: 10,
},
});

// Assert
assert.exception(
() => sb.assert.fail("1234567890--THIS SHOULD NOT SHOW--"),
{ message: "1234567890" },
);
});
});

0 comments on commit f7d180c

Please sign in to comment.