markdown 挑战05:使用摩卡柴进行测试

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了markdown 挑战05:使用摩卡柴进行测试相关的知识,希望对你有一定的参考价值。

For this challenge you will create a full suite of tests that confirm your app is working correctly. Then you'll setup Continuous Integration to ensure your app continues to work.

## Requirements

* Install mocha, chai and chai-http
* Update `server.js` to support tests
* Create a suite of tests:
  * Test that the environment
  * Test the static server
  * Test the endpoints
* Setup continuous integration with Travis CI

## Create Test Suite

To get started you need to install Mocha and Chai as **dev dependencies** and wire-up NPM to execute `mocha`

### Install Dev Dependencies

Mocha is a testing framework, its job is to find and run your tests. It provides a functions, `describe` and `it` to make it easy to write and document tests. It also provides the formatting output called "reporters" as well as life-cycle hooks: `before`, `beforeEach`, `after` and `afterEach` which you'll use when we discuss databases.

Chai is an assertion library, its job is to provide methods help you verify a given value matches the expected value. Chai provides three flavors of assertion styles: Assert, Should and Expect. We'll use the Expect style.

Type the following in your shell. Be sure to add the `--save-dev` flag and check `package.json` to ensure the packages were saved properly.

```sh
npm install --save-dev mocha chai
```

#### Create NPM Test Script

In `package.json`, add the following `test` command to the `scripts` property.

Open the `package.json` file and add the following `test` script property.

```json
...
  "scripts": {
      "start": "node server.js",
      "test": "mocha"
    },
...
```

Rhe `scripts` property allows NPM to run the command. The `start` and `test` commands are just a couple of the pre-defined properties which NPM supports. For these scripts you can simply run `npm start` and `npm test`, respectively. For custom scripts you need use `npm run [SCRIPT NAME]`. See [scripts docs](https://docs.npmjs.com/misc/scripts) for more info.

In your shell, run `npm test`. You should see the following message.

```sh
$ npm test
> mocha

No test files found
npm ERR! Test failed.  See above for more details.
```

Mocha ran successfully, but it could not find any test files. Let's fix that now.

### Create Basic Tests

Next, create a test file with a couple tests to confirm the packages are loaded and configured properly.

Create `/test/server.test.js` and add the following:

```js
const chai = require('chai');

const expect = chai.expect;

describe('Reality check', function () {

  it('true should be true', function () {
    expect(true).to.be.true;
  });

  it('2 + 2 should equal 4', function () {
    expect(2 + 2).to.equal(4);
  });

});
```

Back in the shell, run `npm test` again. You should see the following output:

```sh
$ npm test
> mocha

  Reality Check
    ✓ true should be true
    ✓ 2 + 2 should equal 4

  2 passing (6ms)
```

Congrats, you've setup and run your first tests.

### Configure App for Testing

Next you will create tests to confirm the Express Static Server is working properly but you'll need to perform some additional setup first.

#### Update `server.js` for testing

In `server.js` wrap the `app.listen` call with the following condition `if (require.main === module) {...}` and then export the `app`.

```js
// Listen for incoming connections
if (require.main === module) {
  app.listen(PORT, function () {
    console.info(`Server listening on ${this.address().port}`);
  }).on('error', err => {
    console.error(err);
  });
}

module.exports = app; // Export for testing
```

The above requires some explaining. When running the server, (e.g. `npm start` or `node server.js`) node sets the `require.main` to the current module. That means that it is easy to determine if a file has been run directly by testing `require.main === module`. Basically, the `if (require.main === module) {...}` condition prevents the server from automatically starting when we run the tests.

The `module.exports = app;` exports the Express app so it can be required and used in your test files.

#### Install additional dependencies

Chai has a plug-in named `chai-http` which allows you to make requests, send data, and receive the responses from endpoints.

In your shell, install `chai-http` to the devDependencies

```sh
npm install --save-dev chai-http
```

In `/test/server.test.js`, require the `app` and `chai-http`, then inform `chai` to use `chai-http`. At this point, the top of your file should look like this.

```js
const app = require('../server');
const chai = require('chai');
const chaiHttp = require('chai-http');

const expect = chai.expect;

chai.use(chaiHttp);

describe('Reality check', function () {

  // REMOVED FOR BREVITY

});
```

Run `npm test` again to verify the tests are still working properly.

### Test the Static Server

Your test environment is now ready to test Express. Below the "Reality check" tests, add the following two tests:

```js
describe('Express static', function () {

  it('GET request "/" should return the index page', function () {
    return chai.request(app)
      .get('/')
      .then(function (res) {
        expect(res).to.exist;
        expect(res).to.have.status(200);
        expect(res).to.be.html;
      });
  });

});

describe('404 handler', function () {

  it('should respond with 404 when given a bad path', function () {
    return chai.request(server)
      .get('/DOES/NOT/EXIST')
      .then(res => {
        expect(res).to.have.status(404);
      });
  });

});
```

Run your tests to confirm everything is working properly.

### Test the API Endpoints

Your challenge is to create tests for the rest of the endpoints. You should try to test both positive (eg 2XX) and negative (eg 4XX) outcomes.

Below is a list of requirements to help guide you.

* Static server
  * GET request "/" should return the index page

* 404 handler
  * should respond with 404 when given a bad path

* GET /api/notes
  * should return the default of 10 Notes as an array
  * should return an array of objects with the `id`, `title` and `content`
  * should return correct search results for a valid query
  * should return an empty array for an incorrect query

* GET /api/notes/:id
  * should return correct note object with `id`, `title` and `content` for a given id
  * should respond with a 404 for an invalid id (`/api/notes/DOESNOTEXIST`)

* POST /api/notes
  * should create and return a new item with location header when provided valid data
  * should return an object with a message property "Missing `title` in request body" when missing "title" field

* PUT /api/notes/:id
  * should update and return a note object when given valid data
  * should respond with a 404 for an invalid id  (`/api/notes/DOESNOTEXIST`)
  * should return an object with a message property "Missing `title` in request body" when missing "title" field

* DELETE  /api/notes/:id
  * should delete an item by id

Good luck!

## Set up Continuous Integration and Continuous Deployment

Excellent, you have a test suite! Now, let's set up CICD. If you prefer, here are [command-line only instructions](https://gist.github.com/cklanac/789e902b2f03963fabaf9032f35b19d7#file-cicd-cli-only-md) for the CLI Ninjas.

### Install Travis and Heroku Command Line Clients

Before starting, make sure you have Travis and Heroku command line clients installed

[Install Travis CI's CLI](https://github.com/travis-ci/travis.rb)

On a Mac: `gem install travis`

[Install Heroku CLI](https://devcenter.heroku.com/articles/heroku-cli)

### Configure GitHub <> Travis CI Integration

Configure Travis CI to run your test suite when you or your teammates push changes to GitHub. Sign into [Travis CI](https://travis-ci.org/) with your GitHub account.

> Note: Free (org) vs Paid (com): Be sure to use Travis CI's free service on .org rather than the paid service not .com.

Activate Travis CI <> GitHub connection:

* On Travis CI:
  * Go to Profile: User (in upper-right) > Accounts
  * Click "Sync Account"
  * If the repo is in a GitHub organization opposed to your personal account then select the organization from the menu.
  * Activate repo by toggling the switch

Verify a "Travis CI" setup on GitHub

* On GitHub:
  * Go to Settings > Integrations & Services
    * Verify a "Travis CI" under Services section

### Add Travis Config File

In the root of your project, create a file name `.travis.yml` and add the following.

```yaml
language: node_js
node_js: node
```

Commit the file and push repo to Github

```sh
git add -A
git commit -m 'add .travis.yml'
git push origin master
```

On Travis CI:

* Watch build complete successfully :-)

### Create Heroku App and Configure for Deployment

Next you'll create an app on Heroku and configure it to automatically deploy when Travis CI tests pass

* Login to Heroku and create an app
* Click on the "Deploy" tab
* Click "GitHub" (in the Deployment Method section)
* Select the correct account and search for your repo
* Click "Connect"
* Select "Wait for CI to pass before deploy" checkbox
* Click "Enable Automatic Deploys"

Back on your repo, make a change to any file and commit and push to trigger new build.

```sh
git commit -am 'setup heroku'
git push origin master
```

### Bonus: Add Travis CI badge to your repo

Add a Travis CI badge to your repo:

* On Travis CI, find your project and click on the badge
* Change the dropdown menu to "Markdown" and copy the output
* Add the badge code to your `readme.md` file, commit and push
* The code looks something like this:

```markdown
[![Build Status](https://travis-ci.org/<USERNAME>/<REPO-NAME>.svg?branch=master)](https://travis-ci.org/<USERNAME>/<REPO-NAME>)
```

## Solutions

You can view an example solution and compare the differences between branches

* [solution/05-testing](https://github.com/thinkful-ei20/noteful-app-v1/tree/solution/05-testing)
* [compare the differences](https://github.com/thinkful-ei20/noteful-app-v1/compare/solution/04-promises...solution/05-testing)

Good Luck!

以上是关于markdown 挑战05:使用摩卡柴进行测试的主要内容,如果未能解决你的问题,请参考以下文章

html 摩卡/柴锅炉

摩卡的全局`before`和`beforeEach`?

如何在手表模式下进行任何摩卡测试之前运行全局设置脚本

带有猫鼬调用的摩卡测试功能

摩卡在测试后没有退出

markdown 挑战10:Knex JS测试