jlmakes
jlmakes

Reputation: 2965

How do I mix links that trigger page refreshes, with Angular's html5Mode = true without breaking the back button?

I'll walk through the problematic flow...

What's odd, is I've observed this only when html5Mode = true in Webkit—firefox works as desired...

. . .

First, my server.coffee looks like this:

app.get '/partials/:partial', routes.partials
app.get '/api/test', api.test
app.get '*', routes.index

Basically, all requests load the index (which bootstraps Angular), with exception for a view/partial handler, and a test api route that responds with raw JSON.

. . .

(I'm using the ui-router module for managing nested views and UI states; it uses $urlRouterProvider, which is very similar to Angular's $routeProvider)

Second, my app.coffee looks like this:

app = angular.module('app', ['ui-router'])
.config([
    '$stateProvider'
    '$locationProvider'
    '$urlRouterProvider'
    ($stateProvider, $locationProvider, $urlRouterProvider)->
        $urlRouterProvider
            .when('/api/test', [
                '$window'
                '$location'
                ($window, $location)->
                    $window.location.href = '/api/test'
            ])
            .otherwise('/')
        $stateProvider
            .state 'home',
                url: '/'
                templateUrl: 'partials/index'
                controller: 'IndexCtrl'
            .state 'projects',
                url: '/projects'
                templateUrl: 'partials/projects'
                controller: 'ProjectsCtrl'
        $locationProvider.html5Mode(true).hashPrefix '!'
])

Since everything is async, I had to use $window to access window.location.href to trigger a page refresh so that the server would handle the route.

So my question, can I mix links that trigger page refreshes with Angular's html5Mode without breaking the back button? Is this just a Webkit bug, and/or is there a better way to do this?

Ideally, I'd have the application running off Angular—but things like the "about" or "contact" page (which have no need to be dynamic or async), would be served directly from the server using regular page refreshes...

Help!

Upvotes: 8

Views: 2223

Answers (1)

Ezekiel Victor
Ezekiel Victor

Reputation: 3876

Two options:

  1. If you're using <a /> tags, specify target="_self" to let AngularJS know it shouldn't capture their clicks (those links will be handled by browser normally). This is not a hack; this is normal documented behavior.
  2. Use $window.location = 'foo' as you have been doing. That is acceptable.

Upvotes: 18

Related Questions