diff --git a/packages/vue-app/template/App.js b/packages/vue-app/template/App.js index 73786fbc28..e6544907c3 100644 --- a/packages/vue-app/template/App.js +++ b/packages/vue-app/template/App.js @@ -1,4 +1,5 @@ import Vue from 'vue' +import { getMatchedComponentsInstances, promisify, globalHandleError } from './utils' <% if (loading) { %>import NuxtLoading from '<%= (typeof loading === "string" ? loading : "./components/nuxt-loading.vue") %>'<% } %> <%if (buildIndicator) { %>import NuxtBuildIndicator from './components/nuxt-build-indicator'<% } %> <% css.forEach((c) => { %> @@ -73,6 +74,8 @@ export default { } // Add $nuxt.error() this.error = this.nuxt.error + // Add $nuxt.context + this.context = this.$options.context }, <% if (loading) { %> mounted() { @@ -100,6 +103,40 @@ export default { } } }, + async refresh() { + const pages = getMatchedComponentsInstances(this.$route) + + if (!pages.length) { + return + } + <% if (loading) { %>this.$loading.start()<% } %> + const promises = pages.map(async (page) => { + const p = [] + + if (page.$options.fetch) { + p.push(promisify(page.$options.fetch, this.context)) + } + if (page.$options.asyncData) { + p.push( + promisify(page.$options.asyncData, this.context) + .then((newData) => { + for (const key in newData) { + Vue.set(page.$data, key, newData[key]) + } + }) + ) + } + return Promise.all(p) + }) + try { + await Promise.all(promises) + } catch (error) { + <% if (loading) { %>this.$loading.fail()<% } %> + globalHandleError(error) + this.error(error) + } + <% if (loading) { %>this.$loading.finish()<% } %> + }, <% if (loading) { %> errorChanged() { if (this.nuxt.err && this.$loading) { diff --git a/test/e2e/basic.browser.test.js b/test/e2e/basic.browser.test.js index 51cff0feeb..8584efedd2 100644 --- a/test/e2e/basic.browser.test.js +++ b/test/e2e/basic.browser.test.js @@ -291,6 +291,16 @@ describe('basic browser', () => { expect(p).toBe('Nuxt.js') }) + test('/refresh-page-data', async () => { + const page = await browser.page(url('/refresh-page-data')) + let h1 = await page.$text('h1') + expect(h1).toContain('Hello from server') + await page.evaluate($nuxt => $nuxt.refresh(), page.$nuxt) + h1 = await page.$text('h1') + expect(h1).toContain('Hello from client') + page.close() + }) + // Close server and ask nuxt to stop listening to file changes afterAll(async () => { await nuxt.close() diff --git a/test/fixtures/basic/pages/refresh-page-data.vue b/test/fixtures/basic/pages/refresh-page-data.vue new file mode 100644 index 0000000000..491f45fb05 --- /dev/null +++ b/test/fixtures/basic/pages/refresh-page-data.vue @@ -0,0 +1,15 @@ + + + diff --git a/test/unit/async-config.size-limit.test.js b/test/unit/async-config.size-limit.test.js index 34c0f5f2b8..dba687312c 100644 --- a/test/unit/async-config.size-limit.test.js +++ b/test/unit/async-config.size-limit.test.js @@ -36,6 +36,6 @@ describe('size-limit test', () => { const responseSizeBytes = responseSizes.reduce((bytes, responseLength) => bytes + responseLength, 0) const responseSizeKilobytes = Math.ceil(responseSizeBytes / 1024) // Without gzip! - expect(responseSizeKilobytes).toBeLessThanOrEqual(195) + expect(responseSizeKilobytes).toBeLessThanOrEqual(196) }) })