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

Always return empty array when no errors are found #33

Merged
merged 2 commits into from
Jan 15, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -173,9 +173,9 @@ serializer.serialize([parsedError]);

> The `parseErrors` function will load the i18n configuration once, and reuse the same instance afterwards. It is not possible to overwrite the configuration after the first call. This has to do with performance and caching of translations.

### parseJsonResponse(object)
### parseJsonErrors(object)

Parse json object containing errors into javascript `ApiError` instances.
Parse json object containing errors into javascript `ApiError` instances. Will return an array with all non-errors filtered out or default InternalServerError if no errors were found.

```javascript
try {
Expand All @@ -191,8 +191,8 @@ Parse json object containing errors into javascript `ApiError` instances.

## Tests

- You can run `yarn test` to run all tests
- You can run `yarn test:coverage` to run all tests with coverage report
- You can run `npm run test` to run all tests
- You can run `npm run test:coverage` to run all tests with coverage report

## Bugs

Expand Down
15 changes: 8 additions & 7 deletions src/lib/parser.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import * as ev from 'express-validation';
import * as _ from 'lodash';

import { ApiError, ValidationError } from './errors';
import { ApiError, ValidationError, InternalServerError } from './errors';
import { errors } from '../config/errors.config';
import { errorDefaults } from '../config/defaults.config';
import { getTranslator } from './translator';
Expand Down Expand Up @@ -90,19 +90,20 @@ export function parseErrors(error: any = {}, translatorOptions?: TranslatorOptio
* Parse json response containing errors into actual ApiError objects
* @param {Object} response
*/
export function parseJsonResponse<T>(response: any): ApiError[] | T {
export function parseJsonErrors(response: any): ApiError[] {
if ((response || {}).hasOwnProperty('errors') && Array.isArray(response.errors)) {
return response.errors.map((error: any) => {
return response.errors.reduce((acc: ApiError[], error: any) => {
if (isApiError(error)) {
const { status, code, title, detail, meta = {} } = error;
return new ApiError(status, { code, message: title }, { detail, stack: (meta || {}).stack });
return [...acc, new ApiError(status, { code, message: title }, { detail, stack: (meta || {}).stack })];
}

return error;
});
return acc;
}, []);
}

return response;
// Make sure to always return ApiError
return [new InternalServerError(errors.INTERNAL_ERROR, { detail: response })];
}

// Interfaces
Expand Down
36 changes: 14 additions & 22 deletions tests/parser.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import * as httpStatus from 'http-status';
import { ValidationError } from 'express-validation';

import * as translator from '../src/lib/translator';
import { ApiError, errors, parseErrors, parseJsonResponse, isApiError } from '../src';
import { ApiError, errors, parseErrors, parseJsonErrors, isApiError, InternalServerError } from '../src';
import { errorDefaults } from '../src/config/defaults.config';

describe('errorParser', () => {
Expand Down Expand Up @@ -220,9 +220,9 @@ describe('errorParser', () => {
});
});

describe('parseJsonResponse', () => {
describe('parseJsonErrors', () => {
it('Should succesfully return parsed errors', () => {
const result = parseJsonResponse({
const result = parseJsonErrors({
errors: [{
status: httpStatus.BAD_REQUEST,
code: 'MY_CODE',
Expand All @@ -231,7 +231,8 @@ describe('errorParser', () => {
meta: {
stack: 'Something wrong',
},
}],
},
{}], // Should be filtered out
});

expect(result).toBeInstanceOf(Array);
Expand All @@ -249,7 +250,7 @@ describe('errorParser', () => {
});

it('Should succesfully return parsed errors with empty meta', () => {
const result = parseJsonResponse({
const result = parseJsonErrors({
errors: [{
status: httpStatus.BAD_REQUEST,
code: 'MY_CODE',
Expand All @@ -274,7 +275,7 @@ describe('errorParser', () => {
});

it('Should succesfully return parsed errors without meta', () => {
const result = parseJsonResponse({
const result = parseJsonErrors({
errors: [{
status: httpStatus.BAD_REQUEST,
code: 'MY_CODE',
Expand All @@ -297,14 +298,14 @@ describe('errorParser', () => {
});
});

it('Should return response object when contains no errors', () => {
expect(parseJsonResponse(null)).toEqual(null);
expect(parseJsonResponse([])).toEqual([]);
expect(parseJsonResponse({ errors: [] })).toEqual([]);
it('Should return internalServerError response when contains no errors', () => {
expect(parseJsonErrors(null)[0]).toBeInstanceOf(InternalServerError);
expect(parseJsonErrors([])[0]).toBeInstanceOf(InternalServerError);
expect(parseJsonErrors({ errors: [] })).toEqual([]);
});

it('Should return same error when not all properties were found', () => {
const result = parseJsonResponse({
it('Should return empty error when not all properties were found', () => {
const result = parseJsonErrors({
errors: [{
status: httpStatus.BAD_REQUEST,
detail: { key: 'Value Mister' },
Expand All @@ -315,16 +316,7 @@ describe('errorParser', () => {
});

expect(result).toBeInstanceOf(Array);
expect(result).toHaveLength(1);

expect(result[0]).not.toBeInstanceOf(ApiError);
expect(result[0]).toMatchObject({
status: httpStatus.BAD_REQUEST,
detail: { key: 'Value Mister' },
meta: {
stack: 'Something wrong',
},
});
expect(result).toHaveLength(0);
});
});
});