preface

Recently, WHEN I was writing a new application, I wanted to use Koa combined with Vue SSR to write Api interface and page at the same time, so I started to write by hand. I found that there were a lot of things to write, and most of the examples I referred to used very similar codes (most of them seemed to be based on Especially big HackerNews). I simply spent the night wrapping the code into Koa’s middleware so that the laters would not have to build a wheel;

Everybody see officer, pass by, give a star to encourage once, thank! The project address

The sample

If the following documentation is not clear, please refer to the Demo I wrote for reference

The installation

npm install koa-vuessr-middleware
Copy the code

The document

use

First, you need to add a.ssrconfig file in the project root directory, which contains the following contents:

{
  "ouput": {
    "path": "./dist"."publicPath": "/dist/"
  },
  "entry": {
    "client": "./src/entry-client.js"."server": "./src/entry-server.js"
  },
  "webpackConfig": {
    "client": "./build/webpack.client.conf.js"."server": "./build/webpack.server.conf.js"}}Copy the code

Description:

  • entryIf you want to use the built-in default WebPack configuration, you must configure this, including oneclientserver.clientIs the client entry JS,serverIs the server entry JS
  • outputIf you want to use the built-in default WebPack configuration, you need to configure onepathoutputPath, you can refer toOutput configuration for Webpack
  • webpackConfigIf you want to use a custom WebPack configuration, you need to configure the following two:
    • clientWebpack configuration file for the client version
    • serverServer version of the WebPack configuration file

Note: it can be written by referring to the corresponding configuration file in the project address

The basic usage is as follows:

const koa = require('koa');
const app = new koa();
const koaRouter = require('koa-router');
const ssr = require('koa-vuessrr-middleware');

router.get('/otherroute', otherloaders);
router.get(The '*', ssr(app, opts));

app.use(router.routes());
app.listen(8080);
Copy the code
  • The development environment
router.get(The '*', ssr(app, {
    title: 'Default page title'.isProd: false.// Hot update is enabled by default.
    templatePath: './index.template.html' // Render the default template address, if not provided the built-in default template will be used
}));
Copy the code
  • The production environment

If you want to run it in production, you need to configure the scripts field in package.json.

  "scripts": {
    "build": "vuessr"
  }
Copy the code

Then execute the NPM run build command to generate the production code

Then use the following code

router.get(The '*', ssr(app, {
    title: 'Default page title'.isProd: true.// The production code will be read directly,
    templatePath: './index.template.html' // Render the default template address, if not provided the built-in default template will be used
}));
Copy the code

Recommended file directories are as follows:

├─ SRC app Directory │ ├─ Bass Exercises │ ├─ views │ ├─ Bass Exercises │ ├─ SRC app Directory │ ├─ Bass Exercises │ ├─ ├─ App.js JS file toexport a createApp function│ ├ ─ ─ App. Vue root vue │ ├ ─ ─ entry - server. Js server side entry point │ └ ─ ─ entry - client. Js client side entry point ├ ─ ─ Index.js Server Entry Point ├─.SSrConfig SSR Configuration File ├─...Copy the code

App. Js sample

import Vue from 'vue'
import App from './App.vue'
import { createRouter } from './router'
import titleMixin from './util/title'

Vue.mixin(titleMixin)
export function createApp () {
  const router = createRouter()
  const app = new Vue({
    router,
    render: h= > h(App)
  })
  return { app, router, }
}
Copy the code

Entry – client. Js sample

import Vue from 'vue'
import 'es6-promise/auto'
import { createApp } from './app'

const { app, router } = createApp()

router.onReady((a)= > {
  app.$mount('#app')})Copy the code

Entry – server. Js sample

import { createApp } from './app';
export default context => {
  return new Promise((resolve, reject) = > {
    const { app, router } = createApp()
    const { url } = context
    const { fullPath } = router.resolve(url).route
    if(fullPath ! == url) {return reject({ url: fullPath })
    }
    router.push(url)
    router.onReady((a)= > {
      const matchedComponents = router.getMatchedComponents()
      if(! matchedComponents.length) {return reject({ code: 404})}Promise.all(matchedComponents.map(({ asyncData }) = > asyncData)).then((a)= > {
        resolve(app)
      }).catch(reject)
    }, reject)
  })
}
Copy the code

conclusion

If the project is helpful to you, please click the project address star, thank you 🙏