UNPKG

@naturalcycles/nodejs-lib

Version:
117 lines 4.3 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); const js_lib_1 = require("@naturalcycles/js-lib"); const got_1 = require("got"); const __1 = require(".."); const colors_1 = require("../colors"); /** * Returns instance of Got with "reasonable defaults": * * 1. Error handler hook that prints helpful errors. * 2. Hooks that log start/end of request (optional, false by default). */ function getGot(opt = {}) { return got_1.default.extend({ hooks: { beforeError: [gotErrorHook(opt)], beforeRequest: [gotBeforeRequestHook(opt)], afterResponse: [gotAfterResponseHook(opt)], }, }); } exports.getGot = getGot; /** * Without this hook (default behaviour): * * HTTPError: Response code 422 (Unprocessable Entity) * at EventEmitter.<anonymous> (.../node_modules/got/dist/source/as-promise.js:118:31) * at processTicksAndRejections (internal/process/task_queues.js:97:5) { * name: 'HTTPError' * * * With this hook: * * HTTPError 422 GET http://a.com/err?q=1 in 8 ms * { * message: 'Reference already exists', * documentation_url: 'https://developer.github.com/v3/git/refs/#create-a-reference' * } * * Features: * 1. Includes original method and URL (including e.g searchParams) in the error message. * 2. Includes response.body in the error message (limited length). * 3. Auto-detects and parses JSON response body (limited length). * 4. Includes time spent (gotBeforeRequestHook must also be enabled). */ function gotErrorHook(opt = {}) { const { maxResponseLength = 10000 } = opt; return err => { if (err instanceof got_1.HTTPError) { const { statusCode } = err.response; const { method, url, context } = err.options; const { started } = context; // Auto-detect and prettify JSON response (if any) let body = js_lib_1._jsonParseIfPossible(err.response.body); // Detect HttpErrorResponse if (js_lib_1._isHttpErrorResponse(body)) { body = body.error; } body = __1.inspectAny(body, { maxLen: maxResponseLength, colors: false, }); err.message = [ [statusCode, method, url, started && `in ${js_lib_1._since(started)}`].filter(Boolean).join(' '), body, ] .filter(Boolean) .join('\n'); } return err; }; } exports.gotErrorHook = gotErrorHook; function gotBeforeRequestHook(opt = {}) { return options => { options.context = { ...options.context, started: Date.now(), }; if (opt.logStart) { console.log([colors_1.dimGrey(' >>'), colors_1.dimGrey(options.method), colors_1.grey(options.url)].join(' ')); } }; } exports.gotBeforeRequestHook = gotBeforeRequestHook; function gotAfterResponseHook(opt = {}) { return resp => { const success = resp.statusCode >= 200 && resp.statusCode < 400; if (opt.logFinished) { const { started } = resp.request.options.context; console.log([ colors_1.dimGrey(' <<'), coloredHttpCode(resp.statusCode), colors_1.dimGrey(resp.request.options.method), colors_1.grey(resp.request.options.url), started && colors_1.dimGrey('in ' + js_lib_1._since(started)), ] .filter(Boolean) .join(' ')); // console.log(`afterResp! ${resp.request.options.method} ${resp.url}`, { context: resp.request.options.context }) } // Error responses are not logged, cause they're included in Error message already if (opt.logResponse && success) { console.log(__1.inspectAny(js_lib_1._jsonParseIfPossible(resp.body), { maxLen: opt.maxResponseLength })); } return resp; }; } exports.gotAfterResponseHook = gotAfterResponseHook; function coloredHttpCode(statusCode) { if (statusCode < 400) return colors_1.dimGrey(statusCode); // default if (statusCode < 500) return colors_1.yellow(statusCode); return colors_1.red(statusCode); } //# sourceMappingURL=got.hooks.js.map