How to Test Zappa(JS) Apps
Introduction
In this document we describe how to refactor the following, typical Zappa(JS) code in order to make it easier to test.
require('zappajs') 2222, ->
@get '/health', ->
@jsonp
pid: process.pid
memory: process.memoryUsage()
uptime: process.uptime()
Use @include
You can break down a large Zappa application into smaller bits by using @include
. This allows you to build large Zappa applications by combining reusable, smaller, domain-specific applications. These might turn into reusable components that could be shared and combined into new projects.
More importantly for our goal here, @include
can be used to split the code that starts the application (the web server) and the application logic itself, as follows.
A Simple Server
The server is a two-line script in our case:
# server.coffee
module.exports = require('zappajs') 2222, ->
@include './app.coffee'
If you want to integrate the server with clustering or forever
, this would be a good place to add these.
The Application
The application itself is written in a separate file.
# app.coffee
@include = ->
@get '/health', ->
@jsonp
pid: process.pid
memory: process.memoryUsage()
uptime: process.uptime()
Testing the Application
You can now test the application without actually starting a web server. For example using mocha
:
# test.coffee for mocha
server = require('zappajs').app ->
@include './app.coffee'
express = server.app
supertest = require 'supertest'
describe 'GET /health', ->
it 'returns a 200 OK', (done) ->
supertest(express)
.get '/health'
.expect 'Content-Type', /json/
.expect 200, done
Note how the application is created using zappajs.app
, which creates a Node.js server but does not bind it to a specific port.
Run mocha --compilers coffee:coffee-script/register test.coffee
to confirm the application works as expected.
If you need to make sure the test uses a brand new server each time, move the server creation code inside the tests:
# test.coffee for mocha
supertest = require 'supertest'
new_app = ->
server = require('zappajs').app ->
@include './app.coffee'
server.app
describe 'GET /health', ->
express = new_app()
it 'returns a 200 OK', (done) ->
supertest(express)
.get '/health'
.expect 'Content-Type', /json/
.expect 200, done