专栏首页YuanXin【serverless实战】腾讯云·云开发+nextjs(SSR or 静态导出)实现官网动态化

【serverless实战】腾讯云·云开发+nextjs(SSR or 静态导出)实现官网动态化

背景

www.cloudbase.net 云开发网站是基于 nextjs 开发,里面的内容是写在 js 配置文件。每当更新网站内容,都需要提交 git,并且本地进行静态导出,再借助腾讯云云开发的 cli 工具,部署到云开发控制台的「静态网站」服务。

但是内容的更新,不应该涉及到 git 记录(只包括代码或者配置的改动),而且每次改动都要手动 pull/push/deploy 一遍,属实麻烦。因此,需要进行动态化。

系统设计

动态化获取数据

利用 nextjs 提供的 getInitialProps 钩子,从 cms 系统对应的云数据库中拉取动态内容。并将最新的内容,结合模板代码导出为静态 html 文件。

在 getInitialProps 钩子中,环境既不是 browser,也不是 nodejs,而是 ssr 的环境。所以无法使用 tcb-js-sdk 以及 tcb-admin-node 这两个库来获取云开发的数据。

这里使用了 axios.js 来进行网络请求,理由如下:

  • 完美支持 ssr、node、browser 环境:直接用于 getInitialProps 钩子
  • 支持一级代理转发:可以在内网环境下获取外部数据

http 触发调用云函数

由于无法使用 tcb-js-sdk 和 tcb-admin-node,所以没办法通过 sdk 提供的 api 来读取云数据库的数据。

所以只能“曲线救国”,借助云函数 + http 触发功能来获取云数据库的数据:

  • 在 cloudbase 控制台编写用于读取数据库的云函数
  • 开启云函数的 http 触发:调用者可以通过 http url 的方式调用云函数,传入参数,获取云函数运行结果
  • 在 getInitialProps 钩子中,使用 axios 调用远程云函数,获取最新数据

部分代码实现

在需要动态化内容的页面组件中,添加 getInitialProps 钩子,里面通过 axios 触发云函数,获取云函数数据,并将其挂入组件的 props 中。

组件内部根据 props 的内容,生成对应的 jsx 结构。

代码实现如下:

const MainPage = ({activities, courses, articles}) => {
    // ...
    return ()
}

Main.getInitialProps = async () => {
    const promises = [
        getActivities(),
        getCourses(),
        getArticles()
    ]

    const [
        activities,
        courses,
        articles
    ] = await Promise.all(promises)

    return {
        activities,
        courses,
        articles
    }
}

Q:为什么不选择 SSR,而是使用静态导出?静态导出怎么保证实效性?

理论上来说,SSR 是 SEO+获取最新数据的理论最优方案。但是考虑到云函数搭配 ssr 存在冷热启动问题,而静态导出后的文件直接部署到云开发静态网站服务上,本质上是对象存储,访问速度更快,并且节省费用。

除此之外,借助 CI 工具,设置了定时构建,以获取最新数据进行更新。如果有紧急情况,开发人员也可以在平台手动触发 CI,获取实时最新数据。

一句话,最合适的方案不一定是最优的

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • NodeJS模块研究 - events

    Nodejs 使用了一个事件驱动、非阻塞 IO 的模型。events模块是事件驱动的核心模块。很多内置模块都继承了events.EventEmitter。

    心谭博客
  • 剑指offer - 数组中出现次数超过一半的数字 - JavaScript

    注意,这里要使用 ES6 的 Map,不要使用 json 对象。因为 json 对象的键存在着“隐式类型转换”,所有的键会被转换为字符串,从而导致不易排查的 b...

    心谭博客
  • 三:多页面解决方案--提取公共代码

    按照惯例,我们在src/文件夹下创建pageA.js和pageB.js分别作为两个入口文件。同时,这两个入口文件同时引用subPageA.js和subPageB...

    心谭博客
  • Java API:String class 原

    上面由API提供的描述,可以看出,String是一个最终类,继承了Object类,实现了序列化接口和排序接口以及char可读序列接口。可以得出以下几个特点。

    云飞扬
  • JAVA类String

    今天要讲的是JDK中的String类了,相信大家对这个类特别的熟悉,那今天话不多说,直接讲一些常用的方法。

    用户6055494
  • Python-OpenCV(6)

    接着上篇,这次写两个主题: OpenCV中的颜色空间转换 OpenCV中的几何变换 OpenCV中的颜色空间转换 颜色空间有许多种,常用有RGB,CMY,HSV...

    GavinZhou
  • mybatis的if test 字符串的坑

    mybatis是使用的OGNL表达式来进行解析的,在OGNL的表达式中,'y'会被解析成字符,因为java是强类型的,char 和 一个string 会导致不等...

    分母为零
  • Search a 2D Matrix

    问题:二维数组中是否存在一个数 class Solution { public: bool dfs(vector<vector<int> > &matr...

    用户1624346
  • Leetcode 74. Search a 2D Matrix

    版权声明:博客文章都是作者辛苦整理的,转载请注明出处,谢谢! https://blog.csdn....

    Tyan
  • Rotate Image

    问题:矩阵顺时针旋转90度 class Solution { public: bool dfs(vector<vector<int> > &matrix...

    用户1624346

扫码关注云+社区

领取腾讯云代金券