Skip to content


questions about pushState and history #456

imdonkey opened this Issue · 11 comments

6 participants


I'm trying to upgrade Backbone in my project from 0.3.3 to 0.5.0 (d2082a5 ) and want to set pushState as true when call Backbone.history.start(), but ....

here is the code:

var router = Backbone.Router.extend({
routes: {                                                                            
        ""                                       : "home",                                                       
        ":uid"                                   : "profile",                                                                          
        "search/:query"                          : "search"                              


new router();
Backbone.history.start({pushState: true});

The project is ok on IE678.. but can't work on pushState-capable browser such as FF and Chrome...
when I click any link on homepage, the URL has changed but can not trigger the correctly events that defined in router...

Is there someting wrong with my code or Backbone latest version?



when I click any link on homepage ...

Clicking HTML links certainly isn't compatible with pushState -- what would the link even be?


@jashkenas jashkenas closed this

ok thanks!
Now I replace tag 'a' with tag 'div' and bind 'click' event to trigger the router's and then call the navigate to update the URL.
It works for me.

but I can not use the 'Tab' to focus on the links.... I don't think that is a good user experience...


(this is quite ghetto/oldschool, but should solve your problem)

<a href="javascript:void(0);" onclick="triggerRouter()">whoopee</a>

(you can even the click handler elsewhere, this example is simply to show you how you could use it)


Maybe too late but you can do like this :

$('a').click(function (e) {
    app.navigate($(this).attr('href'), true);
    return false;

And use links normally :

<a href="/help">Help me</a>

Like this, if the user doesn't have JavaScript, the link will be trigger by the server, otherwise by Backbone.


Or, extending just a bit Atinux's example:

window.document.addEventListener('click', function(e) {
    e = e || window.event
    var target = || e.srcElement
    if ( target.nodeName.toLowerCase() === 'a' ) {
        var uri = target.getAttribute('href')
        app_router.navigate(uri.substr(1), true)
window.addEventListener('popstate', function(e) {
    app_router.navigate(location.pathname.substr(1), true);

if you want to have actions bound to not yet loaded views' routes and a working back button.
Please mind Backbone.history's root option.


sorry.. noob here

where would i place this code by pnbv or Atinux?


That's it.
But please take into account that using pushState only makes sense if you also have a server-side representation of each state at each location. That way you're covered when the user refreshes the page or makes a silly bookmark.
That being said you may not need to use event delegation for capturing link urls at all if your application uses a top/main view instead of a router.


Yep, what I meant was that if you want urls instead of hashes then, in my opinion, it doesn't make sense to not have one.

But, on the other hand, if your application hides the address bar or lives inside a native app then it doesn't make sense to have different urls at all.

I think there may have been some confusion about the rational behind the history api.


In my opinion there are two main use cases for Backbone.
1. Stateful application
a) In a webkit "webview" inside a native application. No address bar, refresh or back buttons. No need for hashes or urls.
b) In a browser. Hiding or not the address bar. Only one entry point. Use hashes.
2. Stateful application with server-side fallback (or stateless application with stateful mode)
a) In a browser. Application state maps to urls. Multiple entry points ready :) Use urls, pushState and popstate.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Something went wrong with that request. Please try again.