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 🙏

© 2026 – Pkg Stats / Ryan Hefner

sour

v3.2.0

Published

Router for functional rendering UIs

Readme

sour Build Status

Router for functional rendering UIs

sour is a standalone functional router that works in Node and the browser. It provides the state management and lifecycle hooks you'll use in your application. Sour is designed for composition. You should build your own application-specific routing layer that uses sour internally. Routing is handled by routington.

Install

$ npm install --save sour

Usage

var Sour = require('sour')
var state = Sour()

console.log(state.path())
//=> /the/current/path

var hello = Sour.route(state, {
  path: '/the/route/path',
  render: function () {
    return 'Hello world!'
  }
})

Sour.beforeEnter(state, hello, function (params, callback) {
  //=> I run before the "hello" route is rendered
  callback(null)
})

Sour.watch(state)
//=> Observe path changes and update the active route

state(function (state) {
  console.log(Sour.render(state))  
})

API

Initialization

Sour([data]) -> state

Returns an observable representation of the state.

data.path

Type: string
Default: document.location.pathname

The initial path to use. In the browser, this defaults to the current page path. In Node, it defaults to ''. Passing data.hash = true will synchronize the path with location.hash instead of location.pathname.

Sour.watch(state, [done]) -> function

Watches for path changes to update the active route. Returns an unwatch function.

done

Type: function
Arguments: none

An optional callback that will be called when the router is ready, meanin either:

  • No matching route was found
  • A match was located and the route transition was successful

Routing

Sour.route(state, options) -> object

Defines a new route, returning the route key that can later be referenced to create hooks or change routes.

options
path

Required
Type: string

A path string provided to routington.

render

Required
Type: function

The render function for the route.

Sour.transition(state, route, params, callback) -> undefined

Transitions the router to the specified route returned by Sour.route.

state

Required

The router state.

route

Required
Type: object

A route returned from Sour.route.

params

Required
Type: object

Parameters for the route. These are passed to any registered route hooks.

callback

Type: function
Default: noop
Arguments: err

A callback that will be called after the transition completes. A route transition is complete when:

  • beforeLeave hooks finish
  • afterLeave hooks finish
  • beforeEnter hooks finish
  • the active route is updated

The afterEnter hook for the destination route will be run after the transition completes.

Rendering

Sour.render(state, [args...]) -> any

Runs the render function defined via Sour.route for the active route and returns its result.

state

Required
Type: object

The current state of the router. If no active route is found, undefined is returned.

args...

A variadic set of arguments. These arguments are passed to your active render function.

Hooks

Hooks provide a way to add custom behavior that runs at different points in the routing lifecycle.

Sour.beforeEnter(state, [route], callback) -> function

Sour.afterEnter(state, [route], callback) -> function

Sour.beforeLeave(state, [route], callback) -> function

Sour.afterLeave(state, [route], callback) -> function

Enter and leave hooks run asynchronously when moving between valid routes. Each hook method returns an unlisten function that will unregister the hook.

state

The router state.

route

The route key object returned by Sour.route. If no route is provided, the hook will run for every route.

callback

Required
Type: function
Arguments: params, callback

A callback that will be called when the specified route is activated. Hooks are called in the order in which they were registered with the arguments params, callback, where:

  • params are path parameters defined by the path definition string.
  • callback: a function of err that can halt the route transition and must be called to continue route activation.

Sour.onNotFound(state, listener) -> function

listener

Required
Type: function
Arguments: {path}

Called when the current path does not match any routes. Returns an unlisten function.

Sour.onError(state, listener) -> function

listener

Required
Type: function
Arguments: err

Called when any hook errors during a transition. Returns an unlisten function.

Sour.path(state, route, [params]) -> string

Given a route and its path params, return a string representing the route's path.

route

Required Type: object

A route returned from Sour.route

params

Optional Type: object

Params to match against the params in the path of the given route.

License

MIT © Ben Drucker