Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Functional & unit tests #23

Open
wants to merge 11 commits into
base: master
Choose a base branch
from
75 changes: 75 additions & 0 deletions __tests__/api.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
import APIpeline from '../dist/index';
import 'whatwg-fetch';
import exampleData from './static/example';
import server from './server';

const API_OPTIONS = {
fetchMethod: window.fetch,
domains: { default: 'http://127.0.0.1:23135' }
};

const API_SERVICES = {
testHeaders: { path: 'testHeaders' },
getExample: { path: 'example.json' },
postExample: { path: 'postExample', method: 'POST' }
};


describe('>>> Test API calls', () => {
let mockedServer;
beforeAll((done) => {
mockedServer = server.listen(23135, done);
});

afterAll((done) => {
mockedServer.close(done);
});

it('Returns headers', async () => {
const api = new APIpeline(API_OPTIONS, API_SERVICES);
try {
await expect(
api.get('testHeaders', { headers: { 'Content-Type': 'application/pdf' } })
).resolves.toHaveProperty('content-type', 'application/pdf');
} catch (err) {
throw err;
}
});

it('GET/example.json (api.get)', async () => {
const api = new APIpeline(API_OPTIONS, API_SERVICES);
await expect(api.get('getExample')).resolves.toEqual(exampleData);
});

it('GET/example.json (api.fetch)', async () => {
const api = new APIpeline(API_OPTIONS, API_SERVICES);
await expect(api.fetch('getExample')).resolves.toEqual(exampleData);
});

it('GET/example.json (api.getHeaders)', async () => {
const api = new APIpeline(API_OPTIONS, API_SERVICES);
expect.assertions(2);
try {
const headers = await api.fetchHeaders('getExample');
expect(headers).toHaveProperty('content-type');
expect(headers['content-type']).toEqual('application/json; charset=UTF-8');
} catch (err) {
throw err;
}
});

it('POST/postExample (api.post)', async () => {
const api = new APIpeline(API_OPTIONS, API_SERVICES);
try {
await expect(api.post(
'postExample',
{
fetchOptions: { body: 'key=value' },
headers: { 'Content-Type': 'application/x-www-form-urlencoded' }
}
)).resolves.toEqual({ key: 'value' });
} catch (err) {
throw err;
}
});
});
33 changes: 33 additions & 0 deletions __tests__/instantiation.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import APIpeline from '../dist';

const API_OPTIONS = {
fetchMethod: require('whatwg-fetch'),
domains: { default: 'http://default.tld' }
};

const API_SERVICES = {
example: { path: 'example' }
};

describe('>>> Instantiation', () => {

it('Success with options and services', () => {
new APIpeline(API_OPTIONS, API_SERVICES);
});

it('Success without services', () => {
new APIpeline(API_OPTIONS);
});

it('Fails when fetchMethod is missing', () => {
expect(() => {
new APIpeline({ ...API_OPTIONS, fetchMethod: undefined }, API_SERVICES);
}).toThrow(/^Your fetch method is undefined/);
});

it('Fails when default domain is missing', () => {
expect(() => {
new APIpeline({ ...API_OPTIONS, domains: { staging: 'http://staging.myapi.tld' } }, API_SERVICES);
}).toThrow(/^You didn't set your default domain URL in your options/);
});
});
12 changes: 12 additions & 0 deletions __tests__/requirements.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import APIpeline from '../dist/index';

const API_OPTIONS = {
fetchMethod: require('whatwg-fetch'),
domains: { default: 'default' }
};

describe('>>> Requirements', () => {
it('Fetch is polyfilled', () => {
new APIpeline(API_OPTIONS);
});
});
19 changes: 19 additions & 0 deletions __tests__/server.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
const express = require('express');
const bodyParser = require('body-parser');

const app = express();
const appRouter = express.Router();
app.use((req, res, next) => {
res.header('Access-Control-Allow-Origin', '*');
res.header('Access-Control-Allow-Headers', '*');
res.header('Access-Control-Request-Headers', '*');
next();
});
appRouter.use('/', express.static('__tests__/static'));
app.use(appRouter);
appRouter.use(bodyParser.urlencoded({ extended: true }));

appRouter.get('/testHeaders', async (req, res) => res.json(req.headers));
appRouter.post('/postExample', async (req, res) => res.json(req.body));

export default app;
66 changes: 66 additions & 0 deletions __tests__/setup.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
import APIpeline, { DEFAULT_API_OPTIONS, DEFAULT_SERVICE_OPTIONS } from '../dist';

const API_OPTIONS = {
fetchMethod: require('whatwg-fetch'),
domains: { default: 'http://default.tld' }
};

describe('>>> Setup API options and services', () => {

it('Merges the default API options for missing keys', () => {
const api = new APIpeline(API_OPTIONS);
expect(api._APIOptions).toStrictEqual({
...DEFAULT_API_OPTIONS,
...API_OPTIONS,
});
});

it('Merges the default services options for each service', () => {
const SERVICES = { default: { path: '/' }, simpleService: { path: 'simpleService', method: 'POST' } };
const api = new APIpeline(API_OPTIONS, SERVICES);
expect(api._APIServices).toStrictEqual({
default: { ...DEFAULT_SERVICE_OPTIONS, ...SERVICES.default, },
simpleService: { ...DEFAULT_SERVICE_OPTIONS, ...SERVICES.simpleService },
});
});

it('Updates API options after instantiation', () => {
const api = new APIpeline(API_OPTIONS);
const UPDATED_OPTIONS = { printNetworkRequests: true };
api.setOptions(UPDATED_OPTIONS);
expect(api._APIOptions).toStrictEqual({
...DEFAULT_API_OPTIONS,
...API_OPTIONS,
...UPDATED_OPTIONS
});
});

it('Sets up services after instantiation without pre-defined services', () => {
const UPDATED_SERVICES = { newService: { path: 'http://myNewService.tld' } };
const api = new APIpeline(API_OPTIONS);
api.setServices(UPDATED_SERVICES);
expect(api._APIServices).toStrictEqual({
newService: {
...UPDATED_SERVICES.newService,
...DEFAULT_SERVICE_OPTIONS
}
});
});

it('Adds a new service after instantiation with pre-defined services', () => {
const PRE_DEF_SERVICES = { default: { path: 'http://default.tld' } };
const UPDATED_SERVICES = { newService: 'http://myNewService.tld' };
const api = new APIpeline(API_OPTIONS, PRE_DEF_SERVICES);
api.setServices(UPDATED_SERVICES);
expect(api._APIServices).toStrictEqual({
default: {
...PRE_DEF_SERVICES.default,
...DEFAULT_SERVICE_OPTIONS
},
newService: {
...UPDATED_SERVICES.newService,
...DEFAULT_SERVICE_OPTIONS
}
});
});
});
3 changes: 3 additions & 0 deletions __tests__/static/example.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"test": "ok"
}
17 changes: 17 additions & 0 deletions __tests__/unit.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import APIpeline, { HTTP_METHODS } from '../dist';

const API_OPTIONS = {
fetchMethod: require('whatwg-fetch'),
domains: { default: 'http://default.tld' }
};


describe('>>> Unit tests', () => {

it('Implements every HTTP methods', () => {
const api = new APIpeline(API_OPTIONS);
HTTP_METHODS.forEach((method) => {
expect(typeof api[method.toLowerCase()]).toBe('function');
});
})
});
17 changes: 15 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,13 @@
"types": "./src/index.d.ts",
"scripts": {
"start": "tsc --watch",
"test": "echo \"Error: no test specified\" && exit 1"
"build": "tsc",
"test": "jest --watch --verbose",
"test:coverage": "jest --collectCoverage"
},
"jest": {
"testRegex": "(\\/__tests__\\/.*|(\\.|\\/)(test|spec))\\.(test)\\.[jt]sx?$",
"collectCoverageFrom": ["dist/**/*.js"]
},
"repository": {
"type": "git",
Expand Down Expand Up @@ -37,7 +43,14 @@
},
"homepage": "https://github.com/Exilz/apipeline#readme",
"devDependencies": {
"typescript": "^2.4.2"
"@babel/core": "^7.4.0",
"@babel/preset-env": "^7.4.2",
"@types/jest": "^24.0.11",
"babel-jest": "^24.5.0",
"express": "^4.16.4",
"jest": "^24.5.0",
"typescript": "^2.4.2",
"whatwg-fetch": "^3.0.0"
},
"dependencies": {
"jssha": "^2.3.1",
Expand Down
7 changes: 4 additions & 3 deletions tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
"compilerOptions": {
"target": "es5",
"baseUrl": "./",
"lib": ["es2015"],
"lib": ["es2015", "dom"],
"pretty": true,
"jsx": "react-native",
"outDir": "./dist",
Expand All @@ -20,6 +20,7 @@
],
"exclude": [
"node_modules",
"demo"
"demo",
"__tests__"
]
}
}