The plugin is needed for routing your app in a very convenient way. It uses HTML5 History API for manipulating browser history without reloading the page.
$ npm install --save dwayne-router
The plugin exports Router, Route and Link blocks.
Route object describes a route with many options:
Default: false
If the route is abstract
it can't be rendered as a high-level
route (the current route), but it's rendered when one of the
children is the current route.
An abstract
route can't be the default
route or the fallback
route.
A non-abstract route can't have children (meaning it's a high-level route).
Default: '/'
Describes a route path
. Must start with a '/'
. May be a
string, regexp or a function.
All types accept the part of the path, which is relative to the parent path.
- string: may contain URL params which look like
:paramName
. An URL part (between slashes) may contain only one URL param. - regexp: may contain captured groups which will be
remembered and passed as the
additionalParams
route option. - function: if returns truthy value, it's passed as
additionalParams
route option.
Describes the block which is rendered when the path matches the page URL.
If a route is abstract
, the option may be not specified
and it defaults to the block which renders its children
(see useOriginalChildren).
If it's not abstract, the option is required and must be a Block
class or a template.
Default: {}
An object which describes query params validators. The keys are params keys and the values are validators. A validator may be one of the following:
- array: the param matches if it's one of the array values.
- regexp: the param matches if it's present and if it matches the regexp.
- function: the param matches if the function returns a truthy value.
- the rest: the param matches if it equals to the validator.
Default: {}
Similar to the query
option, but for URL params.
Default: false
If true
, this route is considered the default route. Each time
the page URL doesn't match any routes, the default route is
rendered (without changing the page URL).
Restrictions:
- Default route can't have an URL.
- There can't be two default routes.
- Default route and its parents can't have a dynamic path (regexp or function).
- Default route and its parents can't have URL and query params.
Default: false
Similar to the default option, only it makes the router change the page URL to the URL of the fallback route.
The same restrictions (as for default
route) stand for fallback
route (except for the first one).
Default: true
Fallback route may have an additional replace
option. If true
,
the router replaces (see History#replaceState)
the page URL with the fallback URL, when the URL doesn't match any
routes, and if false
it pushes the URL (see History#pushState).
Default: {}
Route children routes object. The keys are routes names (which
must be unique) and the values are their descriptions. The root
route has $root
name.
A high-level (non-abstract) route can't have children.
Default: router.args.handleTrailingSlash
(see handleTrailingSlash)
If true
, the router handles trailing slash URLs the same way
as without them, and if false
, it doesn't.
If not specified, defaults to the same Router
arg.
The block renders the root Route
block. It sets the global router
and route
variables (see Route).
It accepts three args (all of them are not watched):
Required. Describes the root route children. (see route children). Basically it's the whole structure of all the routes that are handled by the router.
Example:
// routes.js
// import this module and pass as an arg to the Router block
import Home from 'HomeBlockPath';
import NotFound from 'NotFoundBlockPath';
import Login from 'LoginBlockPath';
import Register from 'RegisterBlockPath';
import Users from 'UsersBlockPath';
import UsersList from 'UsersListBlockPath';
import User from 'UserBlockPath';
const routes = {
abstract: true,
children: {
home: {
path: '/', // matches '/'
block: Home
},
404: {
path: '/404',
// will be rendered when no route will match the URL
fallback: true,
block: NotFound
},
auth: {
abstract: true,
path: '/auth',
// no block field because Route block can
// automatically render its child routes
children: {
login: {
path: '/login', // matches '/auth/login'
block: Login
},
register: {
path: '/register', // matches '/auth/register'
block: Register
}
}
},
users: {
abstract: true,
path: '/users',
block: Users,
children: {
usersList: {
// path defaults to '/' so the full path is '/users',
block: UsersList
},
user: {
path: '/:id', // for example, matches '/users/12'
block: User,
params: {
id: /^\d+$/ // id param matches only digits
}
}
}
}
}
};
export default routes;
Default: false
If true, the router will handle URLs with a trailing slash (such
as /login/
).
Default: false
If true, the router will pass the children of the Router
and
Route
blocks to the corresponding block, which is specified in the
route object. Otherwise, these blocks will pass its own child routes
as children.
Examples of the possible layout for the structure above:
true
value (more declarative way):
<!-- App/index.html -->
<Header/>
<section>
<Router routes="{routes}" useOriginalChildren>
<Route name="home"/>
<Route name="404"/>
<Route name="auth">
<Route name="login"/>
<Route name="register"/>
</Route>
<Route name="users">
<div class="users-content">
<Route name="usersList"/>
<Route name="user"/>
</div>
</Route>
</Router>
</section>
<Footer/>
Note: in this example you may not need the Users block, because the
div.users-content
container is already included in the layout. Though you may move this part of the layout to the Users block.
false
value (more minimalistic way):
<!-- App/index.html -->
<Header/>
<section>
<Router routes="{routes}"/>
</section>
<Footer/>
<!-- Users/index.html -->
<div class="users-content">
<!-- Children are its own child routes: usersList and user -->
<Children/>
</div>
The block renders the block, which is specified in the route (pass the route name as an arg to this block) description. It passes it the children (see useOriginalChildren).
It passes it two arguments as well:
router
is an instance of the RouterInternal class.route
is an instance of the RouteParams.
It also passes all the args it received as rest args.
The block renders an anchor (HTML a
tag) with a href that is
specified by the args. There are two types of args:
- usual
href
anchor attribute. the block just passes it to the anchor. to
(name of the route),params
,query
andhash
args. They are passed to RouterInternal#buildURL.
The block also passes the children and the rest args to the anchor.
Example:
<Link href="/route">Link text</Link>
<Link
to="route"
params="{{ a: '1' }}"
query="{{ b: '2' }}"
hash="hash"
>
Link text
</Link>
This is a class which has the following methods:
API: router.buildURL(name: String, options?: URLOptions): String
The method builds an URL (relative to the page origin URL) and returns it.
name
: name of the route which you want to build the URL for.options
: an object with the following properties:- params (default:
{}
): URL params object. - query (default:
{}
): query params object. - hash (default:
''
): URL hash.
- params (default:
API: router.go(name: String, options?: URLOptions): void
The method builds an URL using RouterInternal#buildURL and navigates to it (using History#pushState) and re-renders the layout according to the new URL.
name
: name of the route which will be navigated to.options
: see RouterInternal#buildURL options param.
API: router.redirect(name: String, options?: URLOptions): void
The method is the same as the previous one, except it uses History#replaceState.
API: router.goToURL(url: String): void
The method navigates to the url from the parameter using History#pushState and re-renders the layout according to the new URL.
API: router.redirectToURL(url: String): void
The method is the same as the previous one, except it uses History#replaceState.
API: router.pushURL(url: String): void
The method pushes the url using History#pushState without re-rendering the layout.
API: router.replaceURL(url: String): void
The method is the same as the previous one, except it uses History#replaceState.
This is a class with the following instance properties:
- name: route name
- host: see Location API
- hostname: see Location API
- href: see Location API
- origin: see Location API
- pathname: see Location API
- port: see Location API
- protocol: see Location API
- search: see Location API
- query: query params object
- params: URL params object
- hash: URL hash (without
#
) - additionalParams: see route object
path
option.
The router listens to all link click
events that reach window
,
prevents the default behavior and uses the HistoryAPI to navigate
to the new URL.
If the link has a disabled
attribute, the default behavior will
be prevented and nothing will happen.
If the link has a no-routing
attribute, the link won't be used
by the Router (and the default behavior will stand).
If the link has a replace
attribute, the URL that will be navigated
to will replace the previous URL (see History#replaceState).