Completed
Push — master ( b6e14c...5630cf )
by
unknown
53s
created

src/middleware/error-handler.js   A

Complexity

Total Complexity 25
Complexity/F 3.13

Size

Lines of Code 94
Function Count 8

Duplication

Duplicated Lines 0
Ratio 0 %

Test Coverage

Coverage 76.09%

Importance

Changes 2
Bugs 0 Features 0
Metric Value
cc 0
wmc 25
c 2
b 0
f 0
nc 1
mnd 2
bc 10
fnc 8
dl 0
loc 94
ccs 35
cts 46
cp 0.7609
crap 0
rs 10
bpm 1.25
cpm 3.125
noi 0

1 Function

Rating   Name   Duplication   Size   Complexity  
A error-handler.js ➔ ??? 0 5 1
1
/**
2
 * Hapi middleware for handling errors
3
 *
4
 * @since 1.0.0
5
 */
6
7 1
const NotifierError = require('../common/Error');
8
9 1
const defaultOptions = Object.freeze({
10
  apiPrefix: '/api',
11
  errorView: 'error',
12
});
13
14 4
const generateErrorResponseBody = request => ({
15
  code: request.response.errorCode,
16
  message: request.response.message,
17
  success: false,
18
});
19
20 4
const getStatusCode = request => request.response.statusCode || request.response.output.statusCode;
21
22
/* eslint no-param-reassign: ["error", { "props": false }] */
23 1
const onSuccess = (request, reply, options) => {
24 10
  const path = request.path;
25 10
  if (path.includes(options.apiPrefix)) {
26 10
    const responseObj = request.response.source || {};
27 10
    responseObj.success = true;
28 10
    request.response.source = responseObj;
29
  }
30 10
  return null;
31
};
32
33 1
const onApiError = (request, reply) => {
34 4
  const statusCode = getStatusCode(request);
35 4
  const responseBody = generateErrorResponseBody(request);
36 4
  switch (statusCode) {
37
    case 400:
38 2
      if (request.response.data && request.response.data.name === 'ValidationError') {
39 1
        responseBody.code = NotifierError.Types.BAD_REQUEST_INVALID.code;
40 1
        responseBody.message = NotifierError.Types.BAD_REQUEST_INVALID.message({ message: request.response.message });
41
      }
42 2
      return reply(responseBody).code(statusCode);
43
    case 401:
44
    case 403:
45 2
      return reply(responseBody).unstate('token').code(statusCode);
46
    case 500:
47
      if (!responseBody.code) {
48
        responseBody.code = NotifierError.Types.SERVER.code;
49
      }
50
      return reply(responseBody).code(statusCode);
51
    default:
52
      return reply(responseBody).code(statusCode);
53
  }
54
};
55
56 1
const onUIError = (request, reply, options) => {
57
  const statusCode = getStatusCode(request);
58
  const responseBody = generateErrorResponseBody(request);
59
  switch (statusCode) {
60
    case 401:
61
    case 403:
62
      return reply.redirect(`/login?redirect=${request.path || '/'}`).unstate('token');
63
    case 404:
64
    case 500:
65
      responseBody.statusCode = statusCode;
66
      return reply.view(options.errorView, responseBody).code(statusCode);
67
    default:
68
      return null;
69
  }
70
};
71
72 1
const onError = (request, reply, options) => {
73 4
  const isApi = request.path.includes(options.apiPrefix);
74 4
  return isApi
75
    ? onApiError(request, reply)
76
    : onUIError(request, reply, options);
77
};
78
79 1
const register = (server, opts, next) => {
80 1
  const options = Object.assign({}, defaultOptions, opts);
81 1
  server.ext('onPreResponse', (request, reply) => {
82 14
    const statusCode = request.response.statusCode || request.response.output.statusCode;
83 14
    const response = (statusCode === 200)
84
      ? onSuccess(request, reply, options)
85
      : onError(request, reply, options);
86
87 14
    if (response) {
88 4
      return response;
89
    }
90 10
    return reply.continue();
91
  });
92 1
  next();
93
};
94
95 1
register.attributes = {
96
  name: 'hapi-error-handler',
97
  version: '1.0.0',
98
};
99
100
module.exports = register;
101