'use strict';
/**
* Simple wrapper around the http response object to avoid deopts
* @module skyring/lib/server/response
* @author Eric Satterwhite
* @since 1.0.0
* @requires debug
*/
const debug = require('debug')('skyring:error');
/**
* @constructor
* @alias module:skyring/lib/server/response
* @param {ServerResponse} res A {@link https://nodejs.org/api/http.html#http_class_http_serverresponse|ServerResponse}
* from the node http module
*/
function Response( res ) {
this.res = res;
this.body = null;
}
/**
* Responsible for returning a response in the case of an error
* If the error has a message, it will be sent with the `x-skyring-reason` http header
* if the error has a `statusCode` property, that will be used, otherwise a 500 will be returned
* @method module:skyring/lib/server/response#error
* @param {Error|number} err The error to handle
* @param {String} [msg] In the case `err` is a number, this will be used as the message
*/
Response.prototype.error = function error( err, msg ) {
if(typeof err === 'number') {
this.res.setHeader('x-skyring-reason', msg || 'Internal Server Error');
return this.status(err).json({
message: msg
});
}
err.statusCode = err.statusCode || err.code;
if(!err.statusCode) {
err.statusCode = 500;
err.message = 'Internal Server Error';
}
this.status(err.statusCode);
debug(err);
this.res.setHeader('x-skyring-reason', err.message);
return this.end();
};
/**
* Returns the value of a response header
* @method module:skyring/lib/server/response#get
* @param {String} header The name of the header to get
* @returns {String} The header value, if it is set
*/
Response.prototype.get = function get( key ) {
return this.res.getHeader(key);
};
/**
* Helper for responding with an Object. Will serialize the object, and set the
* Content-Type header to `application/json`
* @chainable
* @method module:skyring/lib/server/response#json
* @param {Object} body The object to set as the response body
* @returns {module:skyring/lib/server/response}
*/
Response.prototype.json = function json( body ) {
this.res.setHeader('Content-Type', 'application/json');
this.res.end(JSON.stringify(body));
return this;
};
/**
* Sets a response header
* @chainable
* @method module:skyring/lib/server/response#set
* @param {String} header The header to set
* @param {String} The header value to set
* @returns {module:skyring/lib/server/response}
*/
Response.prototype.set = function set( key, val ) {
const value = Array.isArray(val)
? val.map(String)
: typeof val === 'string' ? val : String(val);
this.res.setHeader(key, value);
return this;
};
/**
* Sets the status code on the response object
* @chainable
* @method module:skyring/lib/server/response#status
* @param {Number} code The http Status code to set
* @returns {module:skyring/lib/server/response}
*/
Response.prototype.status = function status( code ) {
this.res.statusCode = code;
return this;
};
/**
* Writes a chunk to the response stream
* @chainable
* @method module:skyring/lib/server/response#send
* @param {String} [chunk] The chunk to write
* @returns {module:skyring/lib/server/response}
*/
Response.prototype.send = function send( str ) {
this.res.write(str);
return this;
};
/**
* Ends the response
* @method module:skyring/lib/server/response#end
* @param {String} [chunk] An optional chunk to write be for closing the stream
* @returns {module:skyring/lib/server/response}
*/
Response.prototype.end = function end( str ) {
this.res.end(str);
return this;
};
module.exports = Response;