Nollie is a testing framework to be used in RestAPI testing.
Can be used to run only specific cases:
-
normal
: all cases -
failed
: failed cases from the last run -
smart
: if there were failed cases in the last run - run them, otherwise - run all cases
It is a special variable(namespaces) that can be used in specs. Has the following features:
-
db
-
sql
- make an arbitrary SQL-query to the database specified inTesterOptions
-
-
actions
-
sleep
- wait for specified amount of time(in ms) before continuing the case execution -
mockDate
- mock the date returned by theDate
constructor. The framework will automatically "unmock" theDate
after case execution -
unmockDate
- "unmock" date manually
-
-
regex
- contains some useful regular expression, which, for example, can be used with Jest'sexpect.stringMatching
-
generators
-
randomString
- generate a random string -
uuidv4
- generate an UUID
-
- Postgresql
- data in database automatically truncated before running each case.
TesterOptions.db.excludeTruncateOnTables
can be used to specify tables which should be excluded from truncating
For each case there is a specific namespace that can be used to store arbitrary data for that particular case.
You can store data returned by an action using ActioOptions.storeResultAs
and RequestActionOptions.storeDataAs
.
You also have access to the case scope in functional actions, where you can freely manipulate on the scope.
Each stored values should be of type string
.
Example usage in actions:
// Assuming "user" stored in the case scope previously
const updateUser: RequestAction = {
method: "POST",
path: `api/users/{{user.id}}`,
payload: {
name: "{{user.firstName}} {{user.lastName}}",
}
};
Example usage in asserts:
const assertObj: AssertObject = {
status: 200,
data: { name: "{{user.firstName}} {{user.lastName}}"}
};
const assertFunc: AssertFunc = (testResult, caseScope) => {
expect(testResult.data.name).toBe(`${caseScope.user.firstName} ${caseScope.user.lastName}`);
}
You can skip/focus particular cases or specs by using focus
and skip
options.
NOTE: might work unpredictable if you're mixing this options for cases and specs simultaneously.
Assert
can be an AssertObject
or AssertFunction
:
- object form is useful for cases when you want to assert only the result of the case(the last action).
- function form is much more powerful. It can be used to perform assert on different entities(e.g. database, environment, data from 3rd party application).
There is a special option for cases - log
.
It's useful for debugging, when you want to get better understanding what is going on in some particular case.
You can log the following information:
- case scope(logged before running an action)
- database queries(performed by
NollieUtils.db.sql
) - request action headers
- request action payload.
- request action response data (e.g. "axiosResponse.data")
- Jest's
expect
can be used inAssert
(function or object) - Case scope variables can be used in
Action
andAssert
- Start with failure cases, then move to successful ones.
- Examples of failure cases:
- Failed auth
- Bad payload(missing required fields, bad format)
- Resource not found
- You can avoid repetitions in specs by extracting some entities(e.g. payload, responses) in separate files
- The framework allow to specify "intermediate" asserts. Such assert performed between actions(in the middle of case). Make sure you do not overuse this feature. It's primary purpose is to group similar "failure" cases into single and avoid redundant case initialization(e.g. creating user for each case). Try to keep your scenarios as small as possible.
- Plain actions can be grouped together in an array of actions(
ActionGroup
), so it can be easily reused by multiple cases.
- Update module version in package.json
- Run
npm publish
- Run
yarn build
- Install local Nollie version in target project:
yarn add /path-to-nollie-root-dir/
Igor Pavlov - the initial idea
Denis Volok - main contributor
The MIT License (MIT)
Copyright (c) 2022 Native Platform Ltd.