npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

express-final-response

v1.0.1

Published

The very last middleware of Express to handle every response of every request.

Downloads

5

Readme

express-final-response

Build Status Coverage Status npm version
NPM NPM
The very last middleware of Express to handle every response of every request.

Features

  • Both json-type response and HTML-type response (with some Express template engine) are supported at the same time
  • Log every request while neccessary, and the logger is decided by you
  • Every response has consistent and standard format, and also you are highly encouraged to customize yours for every distinct response
  • Well tested

Usage

Installation

yarn add express-final-response or npm install express-final-response --save;

Work with Express

Let me just give you a clear example:

const path = require('path');
const express = require('express');
const routes = require('express-mount-routes');
const finalResp = require('express-final-response');

const app = express();

// set Express template engine if you need to
app.set('view engine', 'pug');

// mount routes, see https://github.com/Maples7/express-mount-routes
routes(app, path.join(__dirname, 'controllers'));

// a very easy-to-write 404 middleware thank to this awesome package
app.use((isAPI = true) => {
  if (isAPI) {
    return (req, res, next) => next({status: 'APINotFound'});
  } else {
    // of course you can give a view to it and then it will return an HTML page to you
    return (req, res, next) => next({status: 'PageNotFound', view: '404'});
  }
});

// aha, finally we got the protagonist
app.use(finalResp({isDebug: process.env.NODE_ENV !== 'production'}));

app.listen(3000, function () {
  console.log('Example app listening on port 3000!');
});

API

// right value of `=` is default value and all parameters are optional
app.use(finalResp({
  // you are highly encouraged to customize yours for every distinct response, see ./lib/status.json to get the essentials: 
    // statusCode -> HTTP Response Code
    // successful -> Whether a successful response or not
    // code -> Custom response code. It can be used by mobile client or front-ends to customize their own response to user. Also you'd better well classify them according to the type of response such as user module of your system or article module and make every one unique.
    // status -> this string is used to locate status in this package (it's better than using `code` because it's semantic), so make sure they are unique upon most occasions. That's to say, the former status would be replaced by the latter one who keeps the same `status` string param.
    // desc -> brief description
  customStatuses = [],

  // response encoding
  encoding = 'utf-8',

  // logger
  logger = console,

  // if response is a JSON, you can return a true JSON or a String (with `JSON.stringify(JSONResult)`)
    // JSON -> Return a true JSON
    // String -> Return a String with `JSON.stringify(JSONResult)`. This is prepared for some wired clients.
  JSONformat = 'JSON',

  // If this switch is true, all error infomation (error stack included) would be return to client while error occurs; If not, user would noly get error.message. This is prevent key infomation leak from hackers. And don't worry, all infomation will be logged.
  isDebug = false,

  // Whether only log error response or not
  onlyLogError = false,

  // if there is a global error view such as 500.pug, error response would be an HTML page with the defined error view. Also, you can customize it in each response with param `view`. 
  errorView = undefined
}));

Response in each request

Once you want to return result in each request, call Express next() function (Actually, we are making use of error handling mechanism of Express) with proper params.

If response is an error, thare are several ways to do this:

// pass an Error and `error` status would be applied automatically.
next(new Error('I am an Error')); 

// pass an object but `msg` is an error, then `DBError` status would be applied and returned `msg` would be 'TrueError'. This way is better than former one because it can pass more infomation.
next({status: 'DBError', msg: new Error('TrueError')});

// the view would be applied so an HTML page would be returned. If there is no view param, a JSON would be returned like above, and the infomation in the returned JSON could be used while rendering view template.
next({status: 'error', msg: new Error('I am an error'), view: '500'});

Response object would contain statusCode, successful, code, status, desc, msg, ext(when isDebug switch is on), for example:

{ 
  statusCode: 500,
  successful: false,
  code: 2,
  status: 'error',
  desc: 'Request Error!',
  msg: 'I am an error',
  ext: '...'  // the whole Error object
}

If response is normal data, do it like this:

// the most ordinary way, `ext` is optional. `msg` here is designed for holding real data you want to return to clients or front-ends.
next({status: 'success', msg: 'test 1 success'});

// the view would be applied so an HTML page would be returned. If there is no view param, a JSON would be returned like above, and the infomation in the returned JSON could be used while rendering view template.
next({status: 'success', msg: 'test 1 success', view: '200'});

Response object would contain statusCode, successful, code, status, desc, msg(optional), ext(optional), for example:

{
  statusCode: 200,
  successful: true,
  code: 0,
  status: 'success',
  desc: 'Request Successful!',
  msg: 'test 1 success' 
}

See default statuses definition

There are so many other defaut statuses you can choose besides success and error, make sure to see ./lib/status.json to catch them. Of course, you can define your own statuses for the benefit of customStatus parameter like what I have told you.

You are welcomed to review test.js, controllers dir and views dir in this project for more information of usage.

LICENSE

MIT