{"id":27168037,"url":"https://github.com/alexayan/dva-ssr","last_synced_at":"2025-04-09T05:20:17.812Z","repository":{"id":22089280,"uuid":"95206376","full_name":"alexayan/dva-ssr","owner":"alexayan","description":"dva server side render (dva 服务器端渲染库)","archived":false,"fork":false,"pushed_at":"2022-12-02T13:59:48.000Z","size":223,"stargazers_count":30,"open_issues_count":3,"forks_count":3,"subscribers_count":6,"default_branch":"master","last_synced_at":"2024-05-03T20:07:24.489Z","etag":null,"topics":["dva","isomorphic","server-side-rendering"],"latest_commit_sha":null,"homepage":"","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/alexayan.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2017-06-23T09:40:11.000Z","updated_at":"2020-01-23T17:08:41.000Z","dependencies_parsed_at":"2023-01-11T21:28:41.866Z","dependency_job_id":null,"html_url":"https://github.com/alexayan/dva-ssr","commit_stats":null,"previous_names":["alexayan/express-dva-ssr"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/alexayan%2Fdva-ssr","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/alexayan%2Fdva-ssr/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/alexayan%2Fdva-ssr/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/alexayan%2Fdva-ssr/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/alexayan","download_url":"https://codeload.github.com/alexayan/dva-ssr/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247981477,"owners_count":21027930,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["dva","isomorphic","server-side-rendering"],"created_at":"2025-04-09T05:20:17.142Z","updated_at":"2025-04-09T05:20:17.773Z","avatar_url":"https://github.com/alexayan.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# dva-ssr\n\n![Build Status](https://img.shields.io/travis/alexayan/express-dva-ssr.svg)\n![Coverage](https://img.shields.io/coveralls/alexayan/express-dva-ssr.svg)\n![Downloads](https://img.shields.io/npm/dm/express-dva-ssr.svg)\n![Downloads](https://img.shields.io/npm/dt/express-dva-ssr.svg)\n![npm version](https://img.shields.io/npm/v/express-dva-ssr.svg)\n![dependencies](https://img.shields.io/david/alexayan/dva-ssr.svg)\n![dev dependencies](https://img.shields.io/david/dev/alexayan/dva-ssr.svg)\n![License](https://img.shields.io/npm/l/express-dva-ssr.svg)\n\n基于 [dva](https://github.com/dvajs/dva) 的服务器端渲染库。\n\n特性：\n\n- 无需添加额外的服务器端数据获取代码\n- 最小化客户端与服务器端渲染的差异\n\n## 依赖\n\n`react@16.x` `react-router@4.x` `dva@2.x`\n\n## 安装\n\n``` bash\n$ npm install express-dva-ssr --save\n```\n\n## API\n\n### config(options: Object)\n\n配置服务器端渲染参数\n\n``` javascript\nimport ssr from 'express-dva-ssr';\n\nssr.config({\n\ttimeout: 6 * 1000, // 等待异步操作的超时时间\n\n\t/**\n\t * 异步操作超时后，是否终止渲染，并抛出异常\n\t *\n\t * true：忽略超时，停止等待异步操作，直接返回渲染结果\n\t * false：终止渲染，并抛出异常，渲染失败\n\t */\n\tignoreTimeout: true,\n\n\tverbose: true, // console 输出日志\n\n\tstaticMarkup: false, // 是否创建额外的DOM属性\n});\n\n```\n\n### render(options: Object): Promise(RenderResult)\n\n服务器端渲染核心函数\n\n``` javascript\nimport ssr from 'express-dva-ssr';\n\nssr.render({\n\turl: 'https://www.example.com/users/alexyan', // 需要渲染的路由\n\n\t/**\n\t * 服务器端环境数据。\n\t * 在服务器端会在 namespace 为 ssr 的 model 中注入\n\t * 可以传入 http 请求中的 useragent 等请求相关信息，方便对渲染进行控制\n\t *\n\t * 注意!!!: 出于安全考虑，请不要传入服务器敏感信息\n\t */\n\tenv: { platform: 'mobile' },\n\n\t/**\n\t * 配置初始化 state\n\t */\n\tinitialState: {\n\n\t},\n\n\t/**\n\t * 初始化 dva app, 注册 model, 返回 dva 实例\n\t *\n\t * 如果指定 createApp, models 将不生效\n\t */\n\tcreateApp: function(opts) {\n\t\tconst app = dva(opts);\n  \t\tapp.model(require('./models/app'));\n  \t\tapp.model(require('./models/user'));\n  \t\treturn app;\n\t},\n\n\t/**\n\t * 配置 Routes, 参数详见 react-router\n\t */\n\troutes: [\u003cRoute path=\"/\" render={() =\u003e \u003cdiv\u003e/\u003c/div\u003e} /\u003e,\n\t\t\u003cRoute path=\"/user\" render={() =\u003e \u003cdiv\u003e/tech\u003c/div\u003e} /\u003e\n  \t],\n\n  \t/**\n\t * 配置 models, 详见 dva model\n\t */\n\tmodels: [\n\t\tModel\n\t],\n\n\t/**\n\t * 生成完整网页\n\t *\n\t * html: 服务器端渲染片段\n\t * state: 渲染后的 state\n\t * context: 服务器端渲染上下文\n\t */\n\trenderFullPage: async ({html, state, context}) =\u003e {\n\t\tconst ssrHtml = `\n\t\t  \u003cdiv id=\"root\"\u003e\n\t\t  ${html}\n\t\t  \u003c/div\u003e\n\t\t  \u003cscript\u003e\n\t\t  window.__INITIAL_STATE__ = ${JSON.stringify(state)};\n\t\t  \u003c/script\u003e\n\t\t`;\n\t\treturn indexHtml.replace(`\u003cdiv id=\"root\"\u003e\u003c/div\u003e`, ssrHtml);\n\t}\n\n\t/**\n\t * 完成最终渲染页面后调用，可以在这个阶段进行结果缓存等操作\n\t *\n\t * html: 服务器端渲结果\n\t * url: 渲染路由\n\t * state: 渲染后的 state\n\t * env: 服务器端环境数据\n\t */\n\tonRenderSuccess: async (html, url, env, state) =\u003e {\n\n\t}\n}).then((RenderResult) =\u003e {\n\tconsole.log(RenderResult);\n})\n\n```\n\n### type RenderResult\n\n服务器端渲染结果类型描述\n\n``` javascript\n{\n\t/**\n\t * 渲染结果状态码\n\t *\n\t * 200: 渲染成功\n\t * 404: 渲染失败，url 无法找到匹配的 route\n\t * 500: 渲染失败\n\t */\n\tcode: 200,\n\n\turl: 'https://www.example.com/users/alexyan', // 渲染的路由\n\n\tenv: {}, // 服务器端环境数据\n\n\thtml: '\u003chtml\u003e\u003c/html\u003e', // 服务器端渲染最终页面\n\n\terror: new Error('error') // 渲染异常，当 code 为 500 时存在\n}\n```\n\n### runtimeSSRMiddle({routes, models, renderFullPage, createApp, initialState, onRenderSuccess})\n\n返回 `Express` 中间件\n\n\u003e 参数介绍见 render() 函数\n\n``` javascript\nconst exporesMiddleware = ssr.runtimeSSRMiddle({\n  routes,\n  models,\n  createApp,\n  renderFullPage,\n  onRenderSuccess,\n  initialState\n});\n\nconst app = express();\n\napp.use(exporesMiddleware);\n\n```\n\n### route sync property\n\n设置 sync 强制跳过异步操作，直接进行渲染\n\n`\u003cRoute path=\"/\" sync component={Index} /\u003e`\n\n## 写一个简单的服务器端渲染中间件\n\n```\nfunction runtimeSSRMiddle({\n  routes, renderFullPage, createApp, initialState, onRenderSuccess\n}) {\n  return async (req, res, next) =\u003e {\n    const result = await render({\n      url: req.url,\n      env: { ua: req.headers['user-agent'] },\n      routes,\n      renderFullPage,\n      createApp,\n      initialState,\n      onRenderSuccess\n    });\n    switch (result.code) {\n      case 200:\n        return res.end(result.html);\n      case 302:\n        return res.redirect(302, result.redirect);\n      case 404:\n        next();\n        break;\n      case 500:\n        next(result.error);\n        break;\n      default:\n        next();\n        break;\n    }\n  };\n}\n```\n\n## DEMO\n\n[dva-example-user-dashboard-ssr](https://github.com/alexayan/dva-example-user-dashboard-ssr)\n\n\n\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Falexayan%2Fdva-ssr","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Falexayan%2Fdva-ssr","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Falexayan%2Fdva-ssr/lists"}