diff --git a/examples/discrete-components/app.js b/examples/discrete-components/app.js new file mode 100644 index 000000000..2b42ac368 --- /dev/null +++ b/examples/discrete-components/app.js @@ -0,0 +1,37 @@ +import Vue from 'vue' +import VueRouter from 'vue-router' + +// 1. Use plugin. +// This installs and , +// and injects $router and $route to all router-enabled child components +Vue.use(VueRouter) + +// 2. Define route components +const Home = { template: '
Component: home
' } +const Foo = { template: '
Component: foo
' } +const Bar = { template: '
Component: bar
' } + +// 3. Create the router +const router = new VueRouter({ + mode: 'history', + base: __dirname, + routes: [ + { path: '/', component: Home }, + { path: '/foo', component: Foo }, + { path: '/bar', component: Bar } + ] +}) + +// 4. Create extended base Vue with router injected here (all +// children should inherit the same router). +const BaseVue = Vue.extend({ router }) + +// Discrete components means that a new Vue instance will be created +// and bound on multiple *independent* nodes (eg. one Vue instance +// per node); but the router should act as a singleton and keep all +// instances in sync. +document.querySelectorAll('.app').forEach((node) => { + new BaseVue({ + el: node + }) +}) diff --git a/examples/discrete-components/index.html b/examples/discrete-components/index.html new file mode 100644 index 000000000..3300621b1 --- /dev/null +++ b/examples/discrete-components/index.html @@ -0,0 +1,41 @@ + + + +← Examples index +
+
+
    +
  • /
  • +
  • /foo
  • +
  • /bar
  • +
+ $route.path value: {{ $route.path }} +
+
+
    +
  • /
  • +
  • /foo
  • +
  • /bar
  • +
+ $route.path value: {{ $route.path }} +
+
+
    +
  • /
  • +
  • /foo
  • +
  • /bar
  • +
+ $route.path value: {{ $route.path }} +
+
+
+ + $route.path value: {{ $route.path }} +
+ + diff --git a/examples/index.html b/examples/index.html index afde345b1..cd7a7a1f3 100644 --- a/examples/index.html +++ b/examples/index.html @@ -23,6 +23,7 @@

Vue Router Examples

  • Scroll Behavior
  • Lazy Loading
  • Auth Flow
  • +
  • Discrete Components
  • diff --git a/src/index.js b/src/index.js index 3061ca79f..faa1b0374 100644 --- a/src/index.js +++ b/src/index.js @@ -16,6 +16,7 @@ export default class VueRouter { static version: string; app: any; + apps: Array; options: RouterOptions; mode: string; history: HashHistory | HTML5History | AbstractHistory; @@ -26,6 +27,7 @@ export default class VueRouter { constructor (options: RouterOptions = {}) { this.app = null + this.apps = [] this.options = options this.beforeHooks = [] this.afterHooks = [] @@ -69,6 +71,13 @@ export default class VueRouter { `before creating root instance.` ) + this.apps.push(app) + + // main app already initialized. + if (this.app) { + return + } + this.app = app const history = this.history @@ -89,7 +98,9 @@ export default class VueRouter { } history.listen(route => { - this.app._route = route + this.apps.forEach((app) => { + app._route = route + }) }) } diff --git a/test/unit/specs/discrete-components.spec.js b/test/unit/specs/discrete-components.spec.js new file mode 100644 index 000000000..a0d1bf077 --- /dev/null +++ b/test/unit/specs/discrete-components.spec.js @@ -0,0 +1,22 @@ +import Vue from 'vue' +import VueRouter from '../../../src/index' + +describe('[Vue Instance].$route bindings', () => { + describe('boundToSingleVueInstance', () => { + it('updates $route on all instances', () => { + const router = new VueRouter({ + routes: [ + { path: '/', component: { name: 'foo' }}, + { path: '/bar', component: { name: 'bar' }} + ] + }) + const app1 = new Vue({ router }) + const app2 = new Vue({ router }) + expect(app1.$route.path).toBe('/') + expect(app2.$route.path).toBe('/') + router.push('/bar') + expect(app1.$route.path).toBe('/bar') + expect(app2.$route.path).toBe('/bar') + }) + }) +})