Skip to content

Commit 33cf5b0

Browse files
CyberAPNataliaTepluhina
authored andcommitted
SSR Guide: Remove app.js (#1297)
* Remove app.js * Fix typos, code style Co-authored-by: Natalia Tepluhina <tarya.se@gmail.com> * Fix typos * Fix code style * Fix code style * Fix code style * Fix code style * Fix wrong async function Co-authored-by: Natalia Tepluhina <tarya.se@gmail.com>
1 parent a239881 commit 33cf5b0

File tree

3 files changed

+71
-68
lines changed

3 files changed

+71
-68
lines changed

src/guide/ssr/routing.md

Lines changed: 38 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -8,34 +8,50 @@
88

99
```js
1010
// router.js
11-
import { createRouter, createMemoryHistory, createWebHistory } from 'vue-router'
11+
import { createRouter } from 'vue-router'
1212
import MyUser from './components/MyUser.vue'
1313

14-
const isServer = typeof window === 'undefined'
15-
16-
const createHistory = isServer ? createMemoryHistory : createWebHistory
17-
1814
const routes = [{ path: '/user', component: MyUser }]
1915

20-
export default function() {
16+
export default function (history) {
2117
return createRouter({
22-
history: createHistory(),
18+
history,
2319
routes
2420
})
2521
}
2622
```
2723

28-
そして `app.js` と、クライアントとサーバのエントリを更新します:
24+
そしてクライアントとサーバのエントリを更新します:
25+
26+
```js
27+
// entry-client.js
28+
import { createApp } from 'vue'
29+
import { createWebHistory } from 'vue-router'
30+
import createRouter from './router.js'
31+
import App from './App.vue'
32+
33+
// ...
34+
35+
const app = createApp(App)
36+
37+
const router = createRouter(createWebHistory())
38+
39+
app.use(router)
40+
41+
// ...
42+
```
2943

3044
```js
31-
// app.js
45+
// entry-server.js
3246
import { createSSRApp } from 'vue'
47+
// サーバルータはクライアントルータとは異なる履歴を使います
48+
import { createMemoryHistory } from 'vue-router'
49+
import createRouter from './router.js'
3350
import App from './App.vue'
34-
import createRouter from './router'
3551

36-
export default function(args) {
37-
const app = createSSRApp(App)
38-
const router = createRouter()
52+
export default function () {
53+
const app = createSSRApp(Vue)
54+
const router = createRouter(createMemoryHistory())
3955

4056
app.use(router)
4157

@@ -46,20 +62,6 @@ export default function(args) {
4662
}
4763
```
4864

49-
```js
50-
// entry-client.js
51-
const { app, router } = createApp({
52-
/*...*/
53-
})
54-
```
55-
56-
```js
57-
// entry-server.js
58-
const { app, router } = createApp({
59-
/*...*/
60-
})
61-
```
62-
6365
## コード分割
6466

6567
コード分割、またはアプリの一部を遅延読み込みすることは、初期レンダリングのためにブラウザがダウンロードしなければならないアセットのサイズを減らすことができ、大きなバンドルを持つアプリケーションの TTI (time-to-interactive) を大幅に改善できます。重要なのは初期画面で「必要なものだけ読み込む」ことです。
@@ -81,11 +83,16 @@ const routes = [
8183

8284
```js
8385
// entry-client.js
84-
import createApp from './app'
86+
import { createApp } from 'vue'
87+
import { createWebHistory } from 'vue-router'
88+
import createRouter from './router.js'
89+
import App from './App.vue'
8590

86-
const { app, router } = createApp({
87-
/* ... */
88-
})
91+
const app = createApp(App)
92+
93+
const router = createRouter(createWebHistory())
94+
95+
app.use(router)
8996

9097
router.isReady().then(() => {
9198
app.mount('#app')

src/guide/ssr/server.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,14 @@
22

33
[コードの構造](./structure.html)[webpack の設定](./build-config.html) でも説明したとおり、 Express サーバのコードにもいくつかの変更を必要とします。
44

5-
- バンドル結果のビルドした `app.js` を使ってアプリケーションを作成する必要があります。ファイルパスは、webpack マニフェストを使って見つけられます:
5+
- バンドル結果からビルドした `entry-server.js` を使ってアプリケーションを作成する必要があります。ファイルパスは、webpack マニフェストを使って見つけられます:
66

77
```js
88
// server.js
99
const path = require('path')
1010
const manifest = require('./dist/server/ssr-manifest.json')
1111

12+
// 'app.js' という名前は、エントリポイント名に `.js` を接尾へ追加したものです
1213
const appPath = path.join(__dirname, './dist', 'server', manifest['app.js'])
1314
const createApp = require(appPath).default
1415
```
@@ -78,7 +79,7 @@ server.use(
7879
)
7980

8081
server.get('*', async (req, res) => {
81-
const { app } = await createApp()
82+
const { app } = createApp()
8283

8384
const appContent = await renderToString(app)
8485

src/guide/ssr/structure.md

Lines changed: 30 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,15 @@
44

55
クライアントのみのコードを書くとき、コードは毎回新しいコンテキストで評価されると考えることができます。しかし、 Node.js サーバは長時間実行されるプロセスです。コードがプロセスにはじめて要求されるとき、コードは一度評価されメモリ内にとどまります。つまり、シングルトンのオブジェクトを作成すると、すべての受信リクエストの間で共有されることになり、リクエスト間での状態の汚染リスクがあるということです。
66

7-
よって、 **リクエストごとに新しいルート Vue インスタンスを作成する** 必要があります。そのためには、リクエストごとに新しいアプリケーションのインスタンスを作成する、繰り返し実行可能なファクトリ関数を書く必要があります:
7+
よって、 **リクエストごとに新しいルート Vue インスタンスを作成する** 必要があります。そのためには、リクエストごとに新しいアプリケーションのインスタンスを作成する、繰り返し実行可能なファクトリ関数を書く必要があります。したがって、サーバコードは次のようになります:
88

99
```js
10-
// app.js
10+
// server.js
1111
const { createSSRApp } = require('vue')
12+
const { renderToString } = require('@vue/server-renderer')
13+
const express = require('express')
14+
15+
const server = express()
1216

1317
function createApp() {
1418
return createSSRApp({
@@ -20,15 +24,6 @@ function createApp() {
2024
template: `<div>Current user is: {{ user }}</div>`
2125
})
2226
}
23-
```
24-
25-
そして、サーバコードはこのようになります:
26-
27-
```js
28-
// server.js
29-
const { renderToString } = require('@vue/server-renderer')
30-
const server = require('express')()
31-
const { createApp } = require('src/app.js')
3227

3328
server.get('*', async (req, res) => {
3429
const app = createApp()
@@ -49,7 +44,7 @@ server.get('*', async (req, res) => {
4944
server.listen(8080)
5045
```
5146

52-
同じルールが他のインスタンス(ルータやストアなど)にも当てはまります。ルータやストアをモジュールから直接エクスポートしてアプリケーション全体にインポートするのではなく、 `createApp` で新しいインスタンスを作成して、ルート Vue インスタンスから注入する必要があります。
47+
同じルールが他のインスタンス(ルータやストアなど)にも当てはまります。ルータやストアをモジュールから直接エクスポートしてアプリケーション全体にインポートするのではなく、新しいリクエストがくるたびに `createApp` で新しいインスタンスを作成して、ルートの Vue インスタンスから注入する必要があります。
5348

5449
## ビルド手順の導入
5550

@@ -76,42 +71,43 @@ src
7671
├── components
7772
│ ├── MyUser.vue
7873
│ └── MyTable.vue
79-
├── App.vue
80-
├── app.js # 共通のエントリ
74+
├── App.vue # アプリケーションのルート
8175
├── entry-client.js # ブラウザでのみ実行
8276
└── entry-server.js # サーバでのみ実行
8377
```
8478

85-
### `app.js`
79+
### `App.vue`
8680

87-
`app.js` は、アプリケーションの共通のエントリです。クライアント専用のアプリケーションでは、このファイルの中で Vue アプリケーションのインスタンスを作成して、 DOM に直接マウントします。しかし SSR では、その責務はクライアント専用のエントリファイルに移されます。代わりに `app.js` でアプリケーションのインスタンスを作成して、エクスポートします:
81+
お気づきかもしれませんが、`src` フォルダのルートに `App.vue` というファイルがあります。このファイルにはアプリケーションのルートコンポーネントが格納されています。これでアプリケーションコードを安全に `server.js` から `App.vue` ファイルに移動することができます:
8882

89-
```js
90-
import { createSSRApp } from 'vue'
91-
import App from './App.vue'
92-
93-
// ルートコンポーネントを作成するためのファクトリ関数をエクスポート
94-
export default function(args) {
95-
const app = createSSRApp(App)
83+
```vue
84+
<template>
85+
<div>Current user is: {{ user }}</div>
86+
</template>
9687
97-
return {
98-
app
88+
<script>
89+
export default {
90+
name: 'App',
91+
data() {
92+
return {
93+
user: 'John Doe'
94+
}
9995
}
10096
}
97+
</script>
10198
```
10299

103100
### `entry-client.js`
104101

105-
クライアント用のエントリは、ルートコンポーネントのファクトリを使ってアプリケーションを作成し、 DOM にマウントします:
102+
クライアント用のエントリは、`App.vue` コンポーネントを使ってアプリケーションを作成し、それを DOM にマウントします:
106103

107104
```js
108-
import createApp from './app'
105+
import { createSSRApp } from 'vue'
106+
import App from './App.vue'
109107

110108
// クライアント固有の初回起動ロジック
111109

112-
const { app } = createApp({
113-
// ここでアプリケーションのファクトリに追加の引数を渡すことが可能
114-
})
110+
const app = createSSRApp(App)
115111

116112
// これは App.vue テンプレートのルート要素に `id="app"` が前提
117113
app.mount('#app')
@@ -122,12 +118,11 @@ app.mount('#app')
122118
サーバ用のエントリは、レンダリングごとに繰り返し呼び出される関数を default でエクスポートします。いまのところは、アプリケーションのインスタンスを返す以外の機能はありませんが、あとでサーバサイドのルートマッチングやデータのプリフェッチのロジックをここに加えます。
123119

124120
```js
125-
import createApp from './app'
121+
import { createSSRApp } from 'vue'
122+
import App from './App.vue'
126123

127-
export default function() {
128-
const { app } = createApp({
129-
/*...*/
130-
})
124+
export default function () {
125+
const app = createSSRApp(Vue)
131126

132127
return {
133128
app

0 commit comments

Comments
 (0)