🔥码云GVP开源项目 12k star Uniapp+ElementUI 功能强大 支持多语言、二开方便! 广告
## 8.断言 API > 原文: [http://exploringjs.com/impatient-js/ch_assertion-api.html](http://exploringjs.com/impatient-js/ch_assertion-api.html) > > 贡献者:[lq920320](https://github.com/lq920320) ### 8.1. 软件开发中的断言 在软件开发中,*断言*陈述关于值或代码片段必须为真的事实。如果不为真,则抛出异常。Node.js 通过其内置模块`assert`支持断言。例如: ```js import {strict as assert} from 'assert'; assert.equal(3 + 5, 8); ``` 该断言表明 3 加 5 的预期结果为 8。`import` 语句建议使用 [`assert`的`strict`版本](https://nodejs.org/api/assert.html#assert_strict_mode)。 ### 8.2. 本书中如何使用断言 在本书中,断言有两种用途:在代码示例中记录结果以及实现测试驱动的练习。 #### 8.2.1. 通过断言记录代码示例中的结果 在代码示例中,断言表达了预期的结果。举例来说,以下函数: ```js function id(x) { return x; } ``` `id()`返回其参数。我们可以通过断言来证明它: ```js assert.equal(id('abc'), 'abc'); ``` 在示例中,我通常省略导入`assert`的语句。 使用断言的动机是: - 您可以精确指定预期的内容。 - 代码示例可以自动测试,这可以确保它们真正起作用。 #### 8.2.2. 通过断言实现测试驱动的练习 本书的练习是通过测试框架`mocha`进行测试驱动的。测试内部的检查是通过`assert`的方法进行的。 以下是此类测试的示例: ```js // For the exercise, you must implement the function hello(). // The test checks if you have done it properly. test('First exercise', () => { assert.equal(hello('world'), 'Hello world!'); assert.equal(hello('Jane'), 'Hello Jane!'); assert.equal(hello('John'), 'Hello John!'); assert.equal(hello(''), 'Hello !'); }); ``` 有关更多信息,请参阅[关于测验和练习](/docs/11.md#91测验)的章节。 ### 8.3. 正常比较与深度比较 严格的 `equal()`使用`===`来比较值。因此,一个对象只等于它自己——即使另一个对象具有相同的内容(因为`===`不比较对象的内容,只比较它们的唯一标识): ```js assert.notEqual({foo: 1}, {foo: 1}); ``` `deepEqual()`是比较对象的更好选择: ```js assert.deepEqual({foo: 1}, {foo: 1}); ``` 此方法也适用于数组: ```js assert.notEqual(['a', 'b', 'c'], ['a', 'b', 'c']); assert.deepEqual(['a', 'b', 'c'], ['a', 'b', 'c']); ``` ### 8.4. 快速参考:模块`assert` 有关完整文档,请参阅 [Node.js 文档](https://nodejs.org/api/assert.html)。 #### 8.4.1. 普通相等 - `function equal(actual: any, expected: any, message?: string): void` `actual === expected`必须是`true`。如果不是,则抛出`AssertionError`。 ```js assert.equal(3+3, 6); ``` - `function notEqual(actual: any, expected: any, message?: string): void` `actual !== expected`必须是`true`。如果不是,则抛出`AssertionError`。 ```js assert.notEqual(3+3, 22); ``` 可选的最后一个参数`message`可用于解释断言的内容。如果断言失败,则消息用于设置抛出的`AssertionError`。 ```js let e; try { const x = 3; assert.equal(x, 8, 'x must be equal to 8') } catch (err) { assert.equal(String(err), 'AssertionError [ERR_ASSERTION]: x must be equal to 8'); } ``` #### 8.4.2. 深度相等 * `function deepEqual(actual: any, expected: any, message?: string): void` `actual`必须与`expected`完全相同。如果不是,则抛出`AssertionError`。 ```js assert.deepEqual([1,2,3], [1,2,3]); assert.deepEqual([], []); // To .equal(), an object is only equal to itself: assert.notEqual([], []); ``` * `function notDeepEqual(actual: any, expected: any, message?: string): void` `actual`不得与`expected`深度相等。如果是,则抛出`AssertionError`。 #### 8.4.3. 期望异常 如果你想(或期望)接收异常,你需要`throws()`:这个函数调用它的第一个参数,函数`block`,只有在它抛出异常时才会成功。其他参数可用于指定该异常必须是什么样的。 - `function throws(block: Function, message?: string): void` ```js assert.throws( () => { null.prop; } ); ``` - `function throws(block: Function, error: Function, message?: string): void` ```js assert.throws( () => { null.prop; }, TypeError ); ``` - `function throws(block: Function, error: RegExp, message?: string): void` ```js assert.throws( () => { null.prop; }, /^TypeError: Cannot read property 'prop' of null$/ ); ``` - `function throws(block: Function, error: Object, message?: string): void` ```js assert.throws( () => { null.prop; }, { name: 'TypeError', message: `Cannot read property 'prop' of null`, } ); ``` #### 8.4.4. 另一个工具函数 - `function fail(message: string | Error): never` 调用时始终抛出`AssertionError`。这有时对单元测试很有用。 ```js try { functionThatShouldThrow(); assert.fail(); } catch (_) { // Success } ``` ![](https://img.kancloud.cn/ff/a8/ffa8e16628cad59b09c786b836722faa.svg) **测验** 参见[测验应用程序](/docs/11.md#91测验)。