Reading view

There are new articles available, click to refresh the page.

探讨如何为开源项目提交 issue

此文来自于我在公司内部 Wiki 上的文章,现将其整理并转载到我的博客。

Co-Authors:OD、wan92hen

什么是 GitHub Issue

GitHub 官方文档(https://docs.github.com/en/issues/tracking-your-work-with-issues/about-issues )给出的解释是 Use GitHub Issues to track ideas, feedback, tasks, or bugs for work on GitHub.,即通过 GitHub Issues 来跟踪 GitHub 项目相关的想法、反馈、任务及缺陷。从这段描述当中我们可以发现 Issue 不仅代表了 Bug、缺陷,它可以是任何跟项目有关且需要项目维护者知晓的内容,如果将其直译为问题可能会引起歧义,所以接下来我们直接使用 Issue 这个单词来表示它。

另一个值得注意的地方是 GitHub Issues 是一种异步沟通体系。所谓异步,即我提交了一个 Issue 以后,并不意味着立即就能够收到反馈。异步沟通虽然不像同步沟通那样来得直接,但并不代表它不高效。因为不期望能立即收到反馈来进行进一步地沟通,双方都需要尽可能地将信息一次性传达到位,在一定程度上反而可以提高沟通效率。

为什么要提交 Issue

上文中提到了 Issue 所代表的含义,它可能是关于项目的一个新想法,也可能是对于某个特定功能的使用反馈,还有可能是使用过程中碰到的各种各样的 Bug。提交 Issue 的目的自然是让项目维护者知道有这样的一个 Issue 存在。这看起来是一句废话,但实际上不同的 Issue 内容,能够达成这个目的的效果可能千差万别。一个好的 Issue 能够清晰、准确地表达出自己希望传达的信息,项目维护者跟提交者之间不需要再次进行额外的沟通就能够顺利地处理掉这个 Issue。反之一个不好的 Issue 不仅起不到这样的效果,反而可能在你来我往的交互中逐渐跑偏甚至变得火药味十足。

如何提交一个 GitHub Issue

提交一个 Issue 很简单,打开 GitHub 登录下自己的账号,点几下鼠标敲几下键盘就可以提交一个 Issue。但是要提交一个好的 Issue 还是需要一定技巧的。在此之前,建议先阅读下 提问的智慧 这篇文章,虽然是来自英文版的直白翻译,其文化背景、用词风格以及社会环境跟国内有所差异,描绘的场景跟 GitHub Issues 的使用场景也略有区别,但是其中关于提问相关的注意事项还是很值得参考的。这里也借鉴下这篇文章的格式,尝试总结下如何提交一个好的 GitHub Issue。

提交之前

首先,提交一个 Issue 不仅仅是为了请求帮助或者报告问题,也有可能会帮助后续遇到此问题的使用者。从某种意义上来说,这也是对整个开源生态非常具有价值的贡献。所以,不要抱着把问题抛出去等待解决的心理,需要认真对待提交 Issue 这件事,因为你也是一个贡献者。在提交 Issue 前,建议先做以下几件事:

  1. 理清楚你遇到的问题,需要有一定的逻辑性。

  2. 查阅项目文档,搜索是否有相关功能、问题的说明。幸运的话在这个环节我们的问题就可以得到解决,也可能会发现某个功能是设计如此,当然这个情况下我们仍可以提出自己的想法,但相应的措辞就需要有所转变。

  3. 在该项目的 Issues 中搜索有没有类似问题。同样的,如果能够找到类似问题并且在回复列表中看到解决、规避方案,又可以省下我们好多等待时间。如果问题看起来类似,但又不完全一致,可以就在此 Issue 进行回复并说明你遇到的问题。

  4. 在 GitHub 项目之外进行搜索,包括但不限于搜索引擎、内部知识库、项目论坛、交流群等等任何你能想到的地方。如果该项目跟某个其他项目使用了同样的底层库或依赖,有可能类似的问题在其他项目相关资料中可以找到解决方案;如果该项目足够活跃,可能会有用户在其他论坛或博客中分享使用经验或某个问题的解决方案。

  5. Double Check 一下问题确实存在。在项目维护过程中,包括我自己的软件使用经历中,出现过很多因为自己的各种失误而引起的问题,例如某个单词拼写错误、某个功能的前置操作没有完成等等等等。如果这样的 Issue 被提交上来,不仅会浪费双方的时间,还会降低自己在项目维护者心中的可信度,使得后续真正的问题不被重视(参考狼来了的故事)。

  6. 在新版本中尝试验证。

  7. 如果是同时遇到多个不相关的问题,不要提在同一个 Issue 里,可以提交多个 Issue,方便维护者跟踪。

当你真正准备好提交一个问题时,请再次回想下 GitHub Issues 是一个异步沟通系统,假设你只能够发一条消息给项目维护者,你要怎么做才能够让自己的问题得到解决。

提交的内容

一个好的 Issue 标题

  1. 尽可能使用一句话作为标题,但要求直截了当。千万不要直接把问题的详细内容直接写在标题。

  2. 给定一个范围标记,用于缩小这个问题的范围,方便维护者和后续使用者索引。

  3. 仅填写问题简述,不要添加无关内容。

一些案例

Bad

Good

Why

表格渲染异常

编辑器:表格语法渲染异常,在编辑器可以正常渲染,发布后无法渲染

问题描述不够清晰

安装报错

安装站点异常,提示 Internal Server Error

问题描述不够清晰

列表无法渲染

文章列表:后台文章列表渲染空白,可能是src/components/PostList.vue中的 xx 属性为空

问题描述不够清晰

数学公式问题

文章页面:数学公式原样输出,没有经过渲染

问题描述不够清晰

上传附件 bug 提交,请作者看看,谢谢

附件上传:在附件管理中上传附件提示失败,浏览器控制台提示 413 Request Entity Too Large

问题描述不够清晰,包含无关内容

将一个带有 “”接口用例且接口用例里面有环境配置 “” 的接口 导出来,然后 导入另外一个项目,再创建接口用例,配置环境,有时候出现新接口用例使用的是旧的环境,根本原因是 接口导出的竟然把 对应用例的环境 ID给导出来。

接口定义导出再导入到另一个项目时,新导入接口下的用例使用了原项目中的环境

问题描述不够简洁,将详细内容直接写在了标题里

(没有标题)

如果不是有责任维护项目,甚至都不想点进去看内容

问题描述

建议参考以下几点:

  1. 避免使用大量啰嗦的文字来描述,保证干练和逻辑性即可。如果无法描述清楚,可以通过补充复现步骤来辅助。一个好的 Issue 能够恰到好处地给出所需的信息。所谓恰到好处,是指信息不多也不少,刚刚好能够支持项目维护者解决这个问题或者了解这个需求。

  2. 内容仅针对此问题,不要包含遇到的其他问题,其他问题可以另外提交 Issue。

  3. 不要包含与问题无关的话语。

  4. 没有明显的错别字,合理使用标点符号

提供详细的环境信息

一般来说,目前 GitHub 上的项目中都会包含 Issue 模板,会提示让你填写一些环境信息,按照具体要求填写即可。如果没有,也建议根据软件特性提供必要的信息,比如:浏览器类型及版本、服务器版本、使用的设备、使用的数据库版本等。这往往能帮助维护者快速定位某些在特定条件下才会出现的问题。

详细的复现步骤

这一步主要告诉维护者出现这个问题的前因后果或者上下文,因为某些问题是必须在特定的操作下才可能复现的,甚至某些问题可能是某种意义上随机出现的,如果不提供复现步骤,维护者可能会非常难以复现。这也往往增加了来回询问的过程。另外,为了更加直观的描述问题,可以提供步骤截图,GIF 动图,甚至视频(目前 GitHub 已经支持视频)。

提供日志

日志对于维护者排查问题也是至关重要的,提供日志建议参考以下几点:

  1. 对一些敏感信息脱敏处理,某些软件可能会在日志中打印一些敏感信息,建议提供之前检查一遍并手动脱敏。

  2. 仅截取相关的日志,如果不知道哪部分是相关的,建议手动复现一次这个问题并快速去查阅最新打印的日志。

  3. 不仅仅是软件内提供的日志,如果这个项目是基于浏览器运行的,也可以提供一下浏览器控制台打印的日志。

  4. 提供日志的时候请务必使用 Markdown 的代码块(```)语法包裹,否则日志会非常难以查阅。

已经尝试过的解决方式

如果有自己尝试过解决,建议补充一下。因为维护者可能在不知道的情况下也提供出你已经尝试过的解决方式,这无疑增加了来回交流的次数,一定程度地影响效率。

后续跟踪

当你提交完成一个 Issue 之后,项目维护者可能并不会及时回复,这也是异步沟通的一个特点。但请耐心等待回复,不要在短时间内评论催促,有内容需要补充除外。

当你提交的 Issue 收到回复后,GitHub 会向你的邮箱中发送通知,也可以使用 GitHub 内置的通知功能进行跟进。

几个建议:

  1. 如果收到回复,你的邮箱可能会收到 GitHub 的提醒邮件,虽然 GitHub 支持通过邮件回复 Issue,但请千万不要使用邮件回复,因为各个邮件客户端的差异,很可能导致最终的评论混乱,如:https://github.com/halo-dev/halo/issues/1799#issuecomment-1084632899

  2. 与维护者交流的时候不要像使用 IM 即时交流工具一样交流,尽可能一次提供完整的信息。

  3. 如果问题已经解决,一定要及时在 Issue 中告知,必要的时候也可以提供后续的解决方式。

礼仪相关

  1. 不要包含任何的抱怨、吐槽、隐晦等不舒适的话语。即便你说的都对,但可以换一种更加友好的表达方式,仅表述问题,不输出情绪。

  2. 不要要求项目或维护者做任何事。

对于项目管理员或维护者

提供一个贡献者文档

详尽地描述提交 Issue 和 PR 的步骤和要求。

提供 Issue 提交模板

目前 GitHub 已经提供了基于 yaml 描述表单的功能,可以提供更加直观的 Issue 提交表单,并支持表单验证,这能更加规范所有 Issue 的内容。你可以针对项目的特点,列出提交 Issue 所需的信息,如:服务器环境、浏览器版本、所使用的设备等。

相关链接:

跟踪 Issue

  1. 及时排查问题,给 Issue 打上对应的标签。

  2. 不建议将 issue 当做工单使用。

  3. 不要回复之后立马关闭 issue,可以等待提交 issue 的作者回复。

  4. 不要在解决这个 issue 之前就关闭 issue。

  5. 在任何时候,都不建议直接删除 issue 或者 issue 回复。除非十分有必要,比如留下了敏感信息。

  6. 在 Issue 中交流的时候不要像使用 IM 即时交流工具一样交流。

  7. 如果在后续的代码提交中已经修复了此问题,建议在 PR 中关联此 Issue( 可以使用 Fixes #xxx),并在 Issue 中回复。

我的 2023

关于工作

今年是全职维护 Halo 的第二年, 也是 Halo 快速成长的两年,这两年 Halo 的成长可以说比以前任何时间段都要快(虽然一共才 5 年),这如果要放在以前非全职的时候,当前 Halo 的状态我们可能花个三四年都达不到,虽然目前 Halo 依旧有很多可优化的空间。

关于 Halo 2023 年的一些总结

  1. 一共发布了 12 个版本,截止到当前编写此文,即将发布 2.12。

  2. Star 达到 30k。

  3. 终于上线了可用的应用市场,包括内置版,用户可以非常方便的下载和更新插件/主题。

  4. 应用市场支持付费应用,这为我们带来了一部分收益,但远远没有达到养活我们自己的地步。

  5. 插件和主题数量得到提升,也有了越来越多的社区开发者。

今年的一些规划

  1. 应用市场支持开发者入驻,包括发布付费应用。

  2. 通过第一点,继续推进 Halo 的生态发展。

  3. 尝试一些其他的商业模式,争取达到一个正向循环。

  4. 对 Halo 本身的功能和稳定性进行持续优化。

  5. 重视文档。

虽然 Halo 需要推进一些商业模式来得以存活,但我们最大的坚持就是保证 Halo 本身的纯净和优雅,可以从我们应用市场看出,即便是我们提供了服务的应用市场内置版本,也是通过插件的形式集成到 Halo 的,如果用户不喜欢,完全可以直接卸载,不会有任何影响。

一些反思,以下是我们需要一直反思的事情:

  1. Halo 的定位和面向群体。

  2. Halo 是否真的满足了建站的需求,还是仅仅是内容管理。

  3. 基于第二点,为什么 Slogan 是突出的建站,但我们直到 2.12 还是没有针对页面进行一些有用的功能开发,比如可视化编辑网页内容。

  4. 可持续的商业模式。

好了,以上是关于 Halo 的一些总结和反思,以下是我个人的一些工作终结,直接看图吧。

来年对我自己的期望:

  1. 继续深耕技术,需要对巩固很多基础知识。

  2. 改变对产品某些地方的思维方式,尝试一些新的东西。

  3. 提高效率,需要加强对工作优先级的判断。

  4. 开始了解一些运营和商业的知识,对于一个做技术的人来做,这一步真的很难迈出。

关于生活

依旧蓉飘中,这应该是是在成都的第 5 年了,成都虽然比不上北上广深那样的快节奏,但这主要还是分人吧,这两年基本上都投入到工作上了。

生活依旧很平淡,希望今年可以稍微改变一下。

今年最大的事应该就是结婚啦~

一些分享

在这里分享一下在 2023 年用过的一些好软件、好的日用产品等。

App

1. Raycast

https://www.raycast.com/

Raycast 其实已经用了很久了,从最开始发布的时候就一直在用,已经成为了日常必备,不管是用来启动 App,还是利用其中的插件来完成一些其他 App 的集成,都非常好用。尤其是这个产品的细节,非常打动我,这个产品是我学习的对象。

贴一张来自 Raycast 的年终使用报告吧。

2. OrbStack

https://orbstack.dev/

一个 Docker 以及 Linux 虚拟机的管理软件,非常轻量,没有官方 Docker Desktop 那样臃肿和那么多问题。这目前也是我的日常必备了,尤其是 Linux 虚拟机,如果我需要在 Linux 上测试一些东西,直接创建一个新的 Linux 实例即可,非常快速。

开源软件/库

1. TanStack Query

https://github.com/tanstack/query

一个非常好用的数据状态管理库,在此之前,我在页面上获取数据基本都只是通过 Axios 请求,然后手动管理数据的状态,一旦页面复杂一点,数据的获取和管理将会比较复杂,代码也不够简洁。用了这个库之后,可以非常容易的做到:

  1. 简化数据请求的逻辑,可以使用声明式(配置式)的写法完成数据的请求和管理。

  2. 数据缓存、数据共享(组件之间)、重复请求去重。

  3. 监听设备网络状态、窗口聚焦监听。

  4. 请求重试,支持自行编写逻辑。

  5. 定时请求,支持自行编写逻辑,这对异步接口(需要定时重新刷新数据)非常友好。

  6. 分页和滚动加载。

  7. 依赖请求。

类似的库还有 https://github.com/vercel/swr ,知道这个库是看了《为什么你不应该在 React 中直接使用 useEffect 从 API 获取数据》,非常好的一篇文章,有兴趣的话,建议详细阅读一遍。此外,我也在公司技术分享上浅浅的介绍了一下这个库,反响还不错。

2. VueUse

https://github.com/vueuse/vueuse

来自 Vue 和 Vite 的核心开发人员 https://github.com/antfu 的库,这个库利用 Vue 3 的 Composition API 封装了一系列的工具,非常好用。在 Halo 中我们用的比较多的:

  1. useLocalStorage:通常用于在浏览器临时保存一些用户偏好设置。

  2. useRouteQuery:通常用于在地址栏保存数据列表的筛选项,方便在用户切换路由或者刷新页面之后可以回到之前的查询状态。

  3. useFileDialog:用于简化上传文件的逻辑。

  4. useEventListener:再也不用担心在组件 unmounted 的时候取消注册事件。

非常钦佩 Anthony Fu 在开源社区做出的贡献,尤其是 Vue 和 Vite 生态。

3. unplugin-icons

https://github.com/unplugin/unplugin-icons

同样来自 https://github.com/antfu ,这是一个图标库,可以通过组件的方式引入,可以通过非常简单的配置上手。底层依赖于 https://iconify.design/ 作为图标集,基本涵盖了开源的常见图标集。除此之外,也可以通过配置来加载项目内的图标。

如果你使用 Tailwindcss,也可以尝试使用 tailwindcss-plugin-icons,同样依赖于 Iconify,这个库可以将 SVG 编译到最终的 CSS 产物中。这个库会在我写 Halo 主题的时候用到。

好物

1. Huadn 荞麦舒颈枕

近两年饱受颈椎问题困扰,经常会感到颈椎痛和甚至头晕,严重的时候早上起床之后都无法低头,一低头就非常刺痛。已经记不清去了多少次医院了,中医和西医都去过,还做了好几次针灸,但都没有根本解决问题,一段时间之后又会复发。于是开始怀疑是枕头的问题,于是在京东上东找西找发现了这个枕头,已经使用了大概五个月了,已经完全没有再颈椎痛过,只是偶尔会在久坐之后感到颈椎稍微有点僵硬。

原来这么久的颈椎问题是因为睡眠!可能是因为之前的枕头睡着会让颈部悬空,而这个枕头会刚好拖住我的颈椎。

如果你也有颈椎问题,不妨试着换个枕头。

2. 佳能 EOS RP 相机

在此之前,我一直以为我的 iPhone 拍照已经足够好,完全不需要相机,但购买之后发现相机拍出的质感是手机不能比的。不过 23 年没有太多机会出去玩,希望今年可以有空多出去走走。

3. 徕芬吹风机

非常佩服这家公司的产品,这个吹风机颜值高,转速快,可以让我早上早出门两分钟。

以上就是我 2023 的一些总结,希望 2024 更好!

新起点丨开源建站工具 Halo 发布 2.0 版本

2022 年 12 月 1 日,FIT2CLOUD 飞致云旗下开源建站项目 Halo( github.com/halo-dev )正式发布 v2.0 版本。这是 Halo 项目继 v1.0 版本后的第二个里程碑版本,研发团队采用全新架构进行项目重写,实现了从单用户机制向多用户体系的转变,提供全新设计的插件机制和主题机制,改进了附件管理方式,为用户提供富文本编辑器,同时提供后台全局搜索能力。

Halo 是一款好用又强大的开源建站工具,它让你无需太多的技术知识就可以快速搭建一个博客、网站或者内容管理系统。

截至目前(2022 年 12 月 1 日),Halo 已经在 Docker Hub 获得了超过 150 万次下载,GitHub Star 数突破 24 k,并拥有一百多名社区贡献者。我们在此对所有参与到 Halo 产品及社区建设的朋友们表达由衷的感谢。

主要亮点功能

多用户与权限体系

Halo 1.0 版本仅支持单管理员机制,这极大限制了 Halo 的多人使用场景。在 Halo 2.0 中,我们引入了多用户及 RBAC 权限体系,支持多用户同时登录管理 Halo,并且支持用户权限的细粒度控制,可以为不同的用户分配不同的权限,从而实现不同的用户角色。

Halo 2.0 用户管理

灵活可扩展的插件机制

Halo 2.0 带来了全新设计的插件机制,这也是 2.0 版本底层架构变动的主要原因。在 Halo 1.0 时,我们因为无法对功能进行拓展,所以随着版本不断迭代会导致系统越来越臃肿。比如我们在 1.0 集成了市面上常见的云存储方案,但绝大部分用户都不会使用到所有的存储方案,这些功能对于 Halo 来说就变成了一种负担。在 Halo 2.0 中,我们将这些功能抽离出来,通过插件的形式进行集成,这样用户可以根据自己的需求自由选择,不再会因为一些不需要的功能而导致系统的臃肿。同时也可以实现不更新整个 Halo 应用,对插件进行单独更新,降低用户更新使用新功能的代价。

我们为插件机制提供了以下能力:

  • 插件的动态加载、卸载、升级;
  • 自定义模型的接入,方便插件的数据存储;
  • 接入 Halo 的配置模块,方便插件的配置管理;
  • 以及拓展后端、管理端、主题端的能力。

Halo 2.0 插件管理

从上图可以看到:

  • 我们将评论组件和搜索组件做成了插件,这是为了方便主题直接使用,而不需要主题单独为这两个功能进行开发;
  • 1.0 的友情链接管理功能也被抽离出来,成为了一个独立的通用插件;
  • 阿里云 OSS 的存储策略也使用插件提供,安装了这个插件即可将附件上传至阿里云 OSS;
  • Umami 插件提供了对 Umami 的集成,可以在 Halo 控制台直接查看网站访问情况;
  • Unsplash 插件提供了对 Unsplash 的集成,可以在编写内容的时候从 Unsplash 选择图片。

相信随着我们对 Halo 的持续迭代和生态建设的持续投入,Halo 的插件生态会越来越丰富。

目前已支持 Halo 2.0 的插件可以访问 https://github.com/halo-sigs/awesome-halo 查阅。

全新的主题机制

Halo 2.0 在主题机制上,有以下主要改进:

  1. 使用 Thymeleaf 作为默认的模板引擎;
  2. 支持主题预览,可以在不启用主题的情况下预览主题效果;
  3. 支持多语言;
  4. 全新的设置表单定义机制,支持更多的输入选项,支持表单验证和条件判断;
  5. 全新设计的主题可视化设置界面,支持预览不同设备的效果,支持保存设置之后实时预览效果。

Halo 2.0 主题设置预览

全新的默认主题

我们为 Halo 2.0 提供了全新的默认主题,并命名为 Earth,我们计划在未来以太阳系成员的命名方式提供一系列的官方默认主题。

Halo 2.0 默认主题

可扩展的附件管理

在 Halo 1.0 时,社区用户呼声比较高的需求之一就是改进附件管理方式。在 2.0 版本,我们全新设计了附件的功能,支持分组管理、存储策略等功能。分组管理功能可以帮助用户更好地组织管理不同使用场景的附件。存储策略功能可以让用户定义多个不同的附件存储位置,同时也可以通过插件来拓展外部云存储,比如上面提到的阿里云 OSS。

Halo 2.0 附件管理
Halo 2.0 附件上传
Halo 2.0 存储策略

此外,选择附件时还可以通过插件支持更多的附件来源,比如上面提到的 Unsplash 插件,可以做到在编辑内容的时候直接从 Unsplash 网站选择配图。

Halo 2.0 Unsplash 插件

强大的富文本编辑器

在 2.0,为了解决 Markdown 编辑器无法对一些复杂的排版场景进行支持的问题,我们默认提供了富文本编辑器,它能够很好地支持图片插入、表格、任务列表等。不过考虑到部分用户对 Markdown 有较强的需求,我们将在后续版本中提供对 Markdown 格式编辑的支持。除此之外,你也可以通过安装插件的方式使用你最喜欢的编辑器。

Halo 2.0 编辑器

便捷的后台全局搜索

我们在后台提供了全局搜索功能,可以快速搜索后台的页面、文章、附件、主题等资源。并且提供了快捷键(Ctrl + K,Mac 下为 Cmd + K)来快速打开搜索框,提高后台的操作效率。

Halo 2.0 后台全局搜索

支持搜索引擎

在 Halo 1.0 的时候,我们搜索文章是通过 SQL 模糊匹配的方式来实现的,这种方式的搜索效率和准确性都不够理想。在 2.0 中,我们默认使用了 Apache Lucene 来提供搜索引擎的支持,也为主题端提供了通用的搜索框组件,大大提高了搜索功能的实用性。同样的,搜索引擎我们也支持通过插件来拓展,比如集成 Elasticsearch、MeiliSearch 等。

Halo 2.0 搜索引擎

完整变更日志

关于 Halo 2.0 的完整特性和变更日志,请访问 GitHub Release 页面(https://github.com/halo-dev/halo/releases)。

接下来

在 Halo 2.0 正式版发布之后,我们会继续完善 Halo 的功能和文档,并在每个月按时发布一个功能版本。同时将持续投入对 Halo 生态的建设,让用户能够更加方便的使用 Halo 搭建各式各样的网站,构建心中的理想站点。此外,我们也将在不久之后开启应用市场的开发,让用户获取主题、插件更加便捷。同时我们也会不断加大对前沿技术及用户体验的探索,让 Halo 朝着好用又强大的零代码建站工具的目标持续迈进。

Halo 此前的成绩离不开每一位参与者的贡献与支持,踏上这个新的起点,Halo 的未来也仍需各位共同努力。

Halo 1.5.0 发布

距离我们 2020 年 9 月 24 号发布 1.4.0 已经过去了 545 天了,期间虽然有一些版本更新,但大多数都是 patch 修复版本。终于,在今天正式发布 1.5.0 版本。其中带来了大量的优化更新,下面为大家简单介绍一些亮点功能,详细更新日志可在本文末尾查阅。

版本亮点

文章表拆分

在此版本中,新增了 contents 表专门用于存储文章内容。因为在以前的版本中,当站点有大量文章的时候会出现明显拖慢页面渲染速度的情况,这是因为在之前的版本中,查询文章列表会将内容字段也包含在其中,这就会导致数据越多就会越慢。所以在这个版本中,原本的 posts 表就不再包含 originalContentformatContent 字段,在列表查询的时候也不会包含。需要注意的是,如果你是从 1.4 版本升级的话,目前我们是没有自动清空这两个字段的内容的。当然,你可以手动清空,以获得更好的效果。

性能对比:

  • 版本:1.4.17 vs 1.5.0
  • 测试数据:文章数 1000,每篇 4000 字符。
  • 测试工具:Apache Benchmark
  • 测试平台:MacBook Pro M1 Pro
  • 测试参数:ab -c 100 -n 10000 http://localhost:8090/

1.4.17:

Screen Shot 2022-03-23 at 15.55.46

1.5.0:

Screen Shot 2022-03-23 at 16.03.46

注意:此测试可能并不是特别严谨,仅供参考。

文章保存逻辑修改

目前后台已经修改为直接保存编辑器渲染的 html 内容,保证编写时和最终发布结果完全一致。另外,数学公式和 mermaid 图表已经针对此特性做了优化。数学公式仅需在前台引入 katex css 即可。mermaid 图表会被渲染为 svg 并保存,所以无需再引入 mermaid 依赖。

数学公式可以在前台引入:

<link rel="stylesheet" href="https://unpkg.com/katex@0.12.0/dist/katex.min.css" />

Screen Shot 2022-03-23 at 14.41.51
Screen Shot 2022-03-23 at 14.42.22
Screen Shot 2022-03-23 at 14.44.14
Screen Shot 2022-03-23 at 14.44.24

目前,我们已经统一使用 @halo-dev/markdown-renderer 进行 Markdown 渲染。

编辑器重构

编辑器编辑区域修改为 Codemirror 编辑器,支持 Markdown 语法高亮,浏览文章会更加方便。

Screen Shot 2022-03-23 at 14.53.18

编辑器可以通过快捷键打开图片选择,目前也已经支持多选图片和选择之后直接插入文章。

Screen Shot 2022-03-23 at 14.52.41

预览区域支持代码块高亮。

Screen Shot 2022-03-23 at 14.51.53

支持更多 Markdown 标记语法。

Screen Shot 2022-03-23 at 14.54.15

表格编辑体验优化。众所周知,使用 Markdown 语法编写表格的体验是非常难受的,不仅编写困难,而且格式会非常难以阅读。所以我们使用了一个叫做 mte-kernel 的库来解决这个问题,不仅可以让编辑体验升级,而且会自动格式化表格。

CleanShot 2022-03-23 at 14.54.38

标签支持设置颜色

在这个版本中,我们添加了对标签设置颜色的功能,灵感来自于 GitHub Issues 的标签颜色。这样可以比较直观地区分不同的标签。

Screen Shot 2022-03-23 at 14.13.04
Screen Shot 2022-03-23 at 14.13.17

文章管理重构

重构了批量操作的逻辑,目前已经不需要提前通过文章状态筛选文章之后才能批量选择。可以任意批量选择之后进行文章状态的批量操作。

Screen Shot 2022-03-23 at 14.16.14

文章列表不再展示回收站的文章,改为单独为回收站提供一个入口。

Screen Shot 2022-03-23 at 14.16.00

文章设置弹窗进行了重构,改为更直观地显示方式,并且可以在弹窗中进行上下篇的切换。可以非常快速的预览文章设置并进行对文章设置的修改。

Screen Shot 2022-03-23 at 14.16.39

附件管理重构

目前支持将鼠标放在附件项即可显示勾选图标,不再需要提前进入批量管理功能。

Screen Shot 2022-03-23 at 14.15.17

附件详情也和文章设置一样,修改为弹窗的形式,可以进行上下项的快速切换,方便预览以及进行修改删除等操作。

Screen Shot 2022-03-23 at 14.15.32

主题设置重构

主题设置由原来的全屏抽屉形式改为单独的页面。并优化了布局,不再显示主题缩略图,将更多的空间留给设置表单。同时在界面上也展示了主题的相关信息。

Screen Shot 2022-03-23 at 14.17.16

Screen Shot 2022-03-23 at 14.18.44

版本日志

Breaking changes

Features

Improvements

Bug Fixes

Dependencies


halo-dev/halo@v1.4.17…v1.5.0

相关信息

Manjaro Gnome 安装和配置记录

╭─ryanwang at ryanwang-linux in ~
╰─○ neofetch
██████████████████  ████████   ryanwang@ryanwang-linux 
██████████████████  ████████   ----------------------- 
██████████████████  ████████   OS: Manjaro Linux x86_64 
██████████████████  ████████   Kernel: 5.10.70-1-MANJARO 
████████            ████████   Uptime: 10 hours, 29 mins 
████████  ████████  ████████   Packages: 1394 (pacman) 
████████  ████████  ████████   Shell: zsh 5.8 
████████  ████████  ████████   Resolution: 2560x1440 
████████  ████████  ████████   DE: GNOME 40.5 
████████  ████████  ████████   WM: Mutter 
████████  ████████  ████████   WM Theme: Adwaita-maia-compact-dark 
████████  ████████  ████████   Theme: Adwaita-maia-compact-dark [GTK2/3] 
████████  ████████  ████████   Icons: Papirus-Dark-Maia [GTK2/3] 
████████  ████████  ████████   Terminal: gnome-terminal 
                               CPU: Intel i5-10400 (12) @ 4.300GHz 
                               GPU: Intel CometLake-S GT2 [UHD Graphics 630] 
                               Memory: 12983MiB / 15424MiB

基础设定

检测并更换软件源:

sudo pacman-mirrors -i -c China -m rank

添加 archlinuxcn 的源:

sudo vim /etc/pacman.conf

追加如下配置:

[archlinuxcn]
SigLevel = Optional TrustedOnly
Server = https://mirrors.tuna.tsinghua.edu.cn/archlinuxcn/$arch
sudo pacman -S archlinuxcn-keyring

检查软件包更新:

sudo pacman -Syyu

常用开发工具包:

sudo pacman -S base-devel

常用软件包

常用终端工具:

sudo pacman -S htop vim tree neofetch

社区应用:

yay -S bitwarden spotify visual-studio-code-bin google-chrome github-desktop-bin com.qq.weixin.work.deepin com.qq.weixin.deepin typora telegram-desktop

输入法

最开始使用的是 fcitx5 + fcitx5-rime ,安装下来一切顺利。但是在某些场景下始终无法切换到中文输入法,不知道如何解决,然后换成了 ibus-rime。

sudo pacman -S ibus-rime
sudo vim /etc/profile.d/ibus.sh

写入:

export GTK_IM_MODULE="ibus"
export QT_IM_MODULE="ibus"
export XMODIFIERS="@im=ibus"

export XIM="ibus"
export XIM_PROGRAM="ibus"

按理来说,这时候重启或者重新登录即可生效,但是并没有,不仅无法通过快捷键(Super+Space)切换到中文输入法,而且菜单栏右侧也没有切换输入法的菜单项。后来在 @JohnNiang 的帮助下解决了此问题。解决方法:在系统设置里面添加 rime 输入法。如下图:

manjaro-keyboard-settings

rime 的配置目录位置:~/.config/ibus/rime/build

可根据自己的需求对 rime 进行定制化配置。

Terminal 配置

目前最新的 Manjaro 发行版已经默认配置了 zsh,但个人还是希望使用 ohmyzsh。和家里的 macOS 保持一致。

安装 ohmyzsh:

sh -c "$(curl -fsSL https://raw.githubusercontent.com/ohmyzsh/ohmyzsh/master/tools/install.sh)"

安装所需插件:

cd ~/.oh-my-zsh/plugins

git clone https://github.com/zsh-users/zsh-syntax-highlighting

git clone https://github.com/zsh-users/zsh-autosuggestions

修改 .zshrc

ZSH_THEME="fino"

...

plugins=(
	git
	zsh-autosuggestions
	zsh-syntax-highlighting
)

Node.js 环境配置

curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.38.0/install.sh | bash

追加下面的配置到 .zshrc

export NVM_DIR="$([ -z "${XDG_CONFIG_HOME-}" ] && printf %s "${HOME}/.nvm" || printf %s "${XDG_CONFIG_HOME}/nvm")"
[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh" # This loads nvm

安装一个 Node.js 版本

nvm install v14.17.3

Clash

yay -S clash

配置目录位置:~/.config/clash

将 clash 配置文件(config.yaml)放置到此目录,然后启动即可:

nohup clash &

Gnome 插件

https://extensions.gnome.org/extension/2890/tray-icons-reloaded/ https://extensions.gnome.org/extension/1460/vitals/

总结

使用了两三天下来整体还是不错的,暂时还没遇到什么痛点,可能问题最大的还是在中文输入法的体验上吧。之前一直在开发环境使用 Deepin,在使用上没有什么大的问题,但感觉系统整体在 UI 和交互上对于我来说存在较大问题。Deepin 就是属于那种远看界面还不错,但是近看却经不起推敲。个人不是特别建议。而且对于一个小前端开发来说,目前所需要的软件包都可以在官方源或者社区源(aur)找到。所以目前来说,Manjaro 应该是除了 macOS,我最佳的选择。

参考

Halo 1.4.10 发布

Features

Improvements

Security Fixes

Bug Fixes

Upgrade guide

https://docs.halo.run/install/upgrade

Halo 1.4.6 发布

Features

Improvements

Bug Fixes

Upgrade guide

https://docs.halo.run/install/upgrade

Halo 1.4.3 发布

随着这个版本的发布,我们的官网和文档也发生了一些变更。变更之后和 Halo 相关的站点:

Breaking changes

  • 此版本不再支持 JRE 1.8,更新到此版本需要 JRE 11 或以上版本。#1184
  • 移除 Redis Cache Store,如有配置该缓存方式,请先修改为其他方式再进行升级。#1190

Features

  • 支持 ID 别名型 文章路径类型。#1173
  • 支持自定义页面的路径层级设置。#1177
  • Content API 新增 日志点赞文章上下页 接口。#1176
  • 支持导出所有文章为 Markdown 文件。#1199

Improvements

  • 更友好的异常日志追踪。#1191
  • 日志发布不再限制字数。#1203
  • 优化后台菜单拖动排序体验。halo-dev/halo-admin#267
  • 优化后台文章编辑页面的布局。halo-dev/halo-admin#286

Bug Fixes

  • 修复定时删除回收站文章功能无效的问题。#1207
  • 修复上传主题包更新主题失败的问题。#1209
  • 修复自动转化文章标题为别名时,将非中文字符分割的问题。halo-dev/halo-admin#273
  • 修复设置 MFA 登录校验器之后,登录页面偶发无法显示 MFA 验证码输入框的问题。halo-dev/halo-admin#276

Upgrade guide

https://docs.halo.run/install/upgrade

Halo 1.4.0 发布

Feature

  • 支持静态存储重命名和修改文件内容。#819
  • 所有附件列表均支持右键复制图片链接。halo-dev/halo-admin#180
  • 开发者选项中的实时日志支持自动滚动到最新的日志。
  • 在线下载主题支持选择分支和 release。#515 #592 #835
  • 评论内容支持显示 html 文本。halo-dev/halo-admin#222
  • 文章新增 wordCount 字段,用于统计字数。#965
  • 文章编辑支持自动将文章标题的拼音设置为别名。halo-dev/halo-admin#235
  • 重构登录页面,并且支持在登录状态失效后弹出登录框,而不是直接跳转到登录页面,防止正在编辑中的文章丢失。halo-dev/halo-admin#238
  • 预览草稿的时候,不再会增加访问量。#834
  • Content API 支持使用文章或者页面的 slug 获取文章信息。#1044

Change

  • 为部分表单添加表单验证。
  • 发布文章时采用实际点击发布按钮时的时间。halo-dev/halo-admin#160
  • 添加 renderer meta 标签,让部分双核浏览器强制使用新一代内核,而不是 IE 内核导致页面无法正常渲染。halo-dev/halo-admin#207
  • 减弱所有动画效果。halo-dev/halo-admin#213
  • 移除部分操作的吐司提示,改为直接在按钮上显示操作结果。halo-dev/halo-admin#216
  • 优化大量不合理的代码。halo-dev/halo-admin#213 halo-dev/halo-admin#215
  • 移除 fastjson 依赖。#871
  • 重构主题目录扫描,允许当前没有激活中的主题。#869
  • 移除在开发者选项中重启应用的功能。#917
  • 移除 Token 不存在时抛出的异常。#962
  • 优化 Markdown 导入功能。#977
  • 修复文章管理页面刷新后分页显示不正确的问题。halo-dev/halo-admin#231
  • 修复文件上传组件无法同时上传多个文件的问题。halo-dev/halo-admin#234
  • 修复异常图片上传的时候,没有捕获异常的问题。#1025
  • 优化文章编辑提示未保存弹窗的时机。halo-dev/halo-admin#242
  • 移除开发者选项中修改配置文件和重启服务的功能。halo-dev/halo-admin#244
  • 优化主题管理页面的布局。halo-dev/halo-admin#245
  • 优化远程下载主题的体验。halo-dev/halo-admin#249
  • 优化博客设置页面的布局。halo-dev/halo-admin#251

Fixed

  • 修复取消全局绝对路径导致加密文章无法正确查看的问题。#785 #854
  • 修复 token 无法正确失效的问题。halo-dev/halo-admin#129
  • 修复附件不存在时调用删除接口抛异常的问题。#951
  • 修复 content api 中查询单篇文章或页面时,没有发出浏览量增加事件的问题。#981
  • 修复自动生成的文章摘要中清除了空格的问题。#1003
  • 修复文章页面渲染耗时过长的问题。#1008
  • 修复主题版本校验没有处理 beta 形式的版本号,从而导致无法更新或者安装主题的问题。#1011
  • 修复文章管理页面刷新后分页显示不正确的问题。halo-dev/halo-admin#231
  • 修复文件上传组件无法同时上传多个文件的问题。halo-dev/halo-admin#234
  • 修复异常图片上传的时候,没有捕获异常的问题。#1025
  • 修复退出登录和初始化引导页面的部分问题。halo-dev/halo-admin#239 halo-dev/halo-admin#240
  • 修复网站备份的时候,上级目录不存在导致备份异常的问题。#1056
  • 修复无法上传 tar.gz 类型文件的问题。#1057
  • 修复某些情况下主题设置保存失败的问题。#1070
  • 修复上传附件或者主题时,由于部分系统会定时清理临时目录,导致上传失败的问题。

升级步骤

  1. 停止运行 Halo:service halo stop
  2. 备份数据:cp -r ~/.halo ~/.halo.bak
  3. 重命名(备份)旧运行包:mv halo-latest.jar halo-latest.jar.bak
  4. 下载新运行包:wget https://dl.halo.run/release/halo-1.4.0.jar -O halo-latest.jar
  5. 运行:service halo start

注意事项

  1. 更新前不要忘了备份数据,不管你是以什么方式部署的,都请备份 ~/.halo,当然,如果你使用 docker 部署,并修改了映射路径的话,就备份你的映射路径。
  2. 如果有使用 CDN 全站加速,请更新完毕后,刷新全站缓存,并清空浏览器缓存。

相关链接

分享一个教科书式的提问方式

今天,收到一封教科书式的提问邮件。坦率地讲,这还是我第一次收到这种逻辑清晰、信息提供到位的提问。所以非常激动,特意水一篇文来和大家分享一下。

邮件原文

Ryan Wang:

你好,我是刚开始使用Halo的程序员。Halo是我接触过最优秀的作品之一,难以置信能够遇到如此优秀的博客系统,在我第一次了解到它的时候,我就决定用它来搭建一个博客。

在我安装好,顺利运行Halo之后,我迫不及待的尝试了几个主题,最后我觉得Journal非常符合我的个人喜好,同时惊喜的发现原来您也在用这款主题作为自己的主页。但随之而来我在这个主题上遇到了一个小问题。

【问题】

当在移动端显示时,博客主题的div向左偏移了一部分,同时最上方的折叠菜单栏无法正确显示,导致上下的中轴线不一样,页面总是左右滑动。

我尝试了自己调试,但在chrome上调整为手机显示后,却是正常,同时这个问题也不是在所有手机上都有问题,我使用了多款手机,发现个别手机上可以正常显示。

【截图】

以下截图为您和主题作者主页的正常截图,标题可居中显示,同时在下滑后可以显示在在折叠菜单栏。

b5870420fb005448b13521e0cb9bfa15

以下是我的博客异常显示截图,标题不居中,下滑后折叠菜单栏也无法正确显示。

  • 图1的空白处还有一个隐藏的链接,也是链接到我的主页,标题div整体偏左。
  • 图2我将标题div边界显示出来了,确实偏左。
  • 图3下滑后折叠菜单栏没有置顶显示。
  • 图4是在chrome的调试模式下能够正确显示。

af6aa871277596b107d4596d9eccabd8

b5870420fb005448b13521e0cb9bfa15

【资源】

  • Halo版本:v1.1.1
  • Journal主题:当前halo-dev/halo-theme-Journal仓库master最新版本,commit id:2747364e50880d44ae4ac8fcb1513352aa199039
  • 尝试过的浏览器:
    • iphone xs: safari、chrome、微信内置浏览器 [均异常]
    • iPhone xs max: safari [异常]
    • Huawei mate30 pro: 自带浏览器、百度浏览器 [均异常]
    • Huawei p20: chrome [正常]
  • 主页地址:http://xxxx(文章中就不写地址了)

由于我对前端相关技术非常不熟悉,自己调试很久都无法使其正确,特此咨询博主是如何解决的,若博主有时间,可否看下之前是否也遇到过类似问题,或是做过何种修改使其正确显示了。

期待您的回信,十分感谢!!

Your fans:xxxx(文章中就不写名字了)
2020年1月5日

为什么写得好?

邮件格式标准

虽说现在很多人(包括我),在发邮件的时候都不会太刻意在乎邮件格式,但是这种格式我看起来就是舒服,也有了阅读下去的欲望。

有问题简述

可以看到,上面的 【问题】 板块中,他有把问题简写为一小段,并特意标注,这样的话我就有可能能一下子了解问题所在,在我脑子里搜索一下是否有遇到过类似的问题。

有问题详细描述

紧接着 问题简述,随后就是问题的详细描述,附有多张截图。并把所有导致的问题全部描述了一遍。

有自己尝试解决问题

从上面的描述就可以知道,他有在桌面版的 Chrome 中调试过主题,也在多款手机的浏览器中调试过,说明他有尝试通过自己解决问题,比如:是否和浏览器有关?是否和设备有关?都很显而易见。

提供了环境信息

他在最后面提供了 Halo 的版本,主题的版本以及 commit id。这是最方便我们定位问题的信息,有可能在某些情况,我们已经在最新版本修复了此问题,所以当你没有提供这些信息的时候,我们往往会问你软件的版本或者主题的版本。

提供了线上地址

这就不用我多说了,这是最直接了当方便我们调试的信息。

总结

我就希望以后有同学抛出问题的时候,能多附带一些信息,比如详细日志,线上地址等等。真的,不为其他的,就为了不耽搁我们双方的时间,从而更加迅猛的帮你解决问题。某些时候真的不是不想解决你们遇到的问题,而且你们给出的信息实在过少,难以判断,而往往这时候我们又要向你问一些详细情况,这样一去一来不就耽搁时间了吗?

另外,感谢这位朋友愿意提供该邮件供我水这篇文章,我认为比我以前水的一些文章有价值多了,感谢。

优雅的让 Halo 支持 webp 图片输出

原文地址:https://halo.run/archives/halo-and-webp

是什么

WebP的有损压缩算法是基于VP8视频格式的帧内编码[17],并以RIFF作为容器格式。[2] 因此,它是一个具有八位色彩深度和以1:2的比例进行色度子采样的亮度-色度模型(YCbCr 4:2:0)的基于块的转换方案。[18] 不含内容的情况下,RIFF容器要求只需20字节的开销,依然能保存额外的 元数据(metadata)。[2] WebP图像的边长限制为16383像素。

在 WebP 的官网中,我们可以发现 Google 是这样宣传 WebP 的:

WebP lossless images are 26% smaller in size compared to PNGs. WebP lossy images are 25-34% smaller than comparable JPEG images at equivalent SSIM quality index.

简单来说,WebP 图片格式的存在,让我们在 WebP 上展示的图片体积可以有较大幅度的缩小,也就带来了加载性能的提升。(摘自 https://nova.moe/re-introduce-webp-server)

怎么做

那么如何优雅的在不替换图片地址的情况下,将图片转为 webp 格式然后输出呢?

这时候就可以使用 webp-sh 组织最新开源的 webp_server_go 了,它的大概原理就是:当我们请求一张图片的时候使用 web 代理工具转发到 webp_server_go 应用进行处理,处理完成之后返回 webp 格式的图片,并且会保留处理后的图片以供后面的访问。

目前大部分主流浏览器都已经支持了 webp 图片的显示,除了 Safari,但是不必担心,webp_server_go 会自动判断请求来源是否为 Safari,如果是,那么会返回原图。

下面将提供两种 web 服务器的代理方法。

此教程以 CentOS 7.x 为例,其他发行版本大同小异。另外,此教程只针对于 Halo,其他 web 程序可能在 config.json 部分有所不同,建议参考仓库的 README。

部署 webp_server_go

仓库 的 README 中已经大致讲解了部署方法,在这里针对 Halo 详细说明一下。

下载官方编译好的 webp_server_go 二进制文件

如果你有能力,也可以自行编译。

新建一个存放二进制文件和 config.json 文件的目录(可自定义):

mkdir /opt/webps

cd /opt/webps

下载二进制文件(最新版本请访问 releases):

wget https://github.com/webp-sh/webp_server_go/releases/download/0.1.0/webp-server-linux-amd64 -O webp-server

给予执行权限:

chmod +x webp-server

创建 config.json

{
        "HOST": "127.0.0.1",
        "PORT": "3333",
        "QUALITY": "80",
        "IMG_PATH": "/root/.halo",
        "EXHAUST_PATH": "/root/.halo/cache",
        "ALLOWED_TYPES": ["jpg","png","jpeg"]
}

参数解释:

  • HOST:一般不修改。
  • PORT:webp_server_go 的运行端口。
  • QUALITY:转换质量,默认为 80%。
  • IMG_PATH:固定格式,/运行 Halo 的用户名/.halo
  • EXHAUST_PATH:固定格式,/运行 Halo 的用户名/.halo/cache
  • ALLOWED_TYPES:需要转换的格式

使用 systemd 进行状态管理

创建 service 文件:

vim /etc/systemd/system/webps.service

写入:

[Unit]
Description=WebP Server
Documentation=https://github.com/n0vad3v/webp_server_go
After=nginx.target

[Service]
Type=simple
StandardError=journal
AmbientCapabilities=CAP_NET_BIND_SERVICE
WorkingDirectory=/opt/webps
ExecStart=/opt/webps/webp-server --config /opt/webps/config.json
ExecReload=/bin/kill -HUP $MAINPID
Restart=always
RestartSec=3s


[Install]
WantedBy=multi-user.target

需要注意的是,ExecStart 命令中的程序路径和配置文件路径一定要正确,结合你的实际情况填写。

然后执行:

systemctl daemon-reload
systemctl enable webps.service
systemctl start webps.service

查看运行状态:

systemctl status webps.service

如果没有问题,那么会输出以下日志:

WebP Server is running at 127.0.0.1:3333

使用 Nginx 进行代理

如果你的 Halo 是使用 Nginx 反向代理的话。

修改 halo.conf

在 server 节点添加:

location ^~ /upload/ {
        proxy_pass http://127.0.0.1:3333;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_hide_header X-Powered-By;
        proxy_set_header HOST $http_host;
        add_header Cache-Control 'no-store, no-cache, must-revalidate, proxy-revalidate, max-age=0';
}

重载 Nginx 配置:

# 检查配置文件是否有问题
nginx -t 

nginx -s reload

使用 Caddy 进行代理

如果你的 Halo 是使用 Caddy 反向代理的话。

修改 Caddyfile

在你域名节点下添加:

proxy /upload/ localhost:3333 {
  transparent
}

重启 Caddy:

service caddy restart

教程完毕,下面讲一下如何验证是否生效。

验证是否生效

Screen Shot 2020-03-02 at 11.47.08 PM

注意看 Type 列,图片的返回格式已经变成了 webp,而且图片大小已经远远降低,那么说明你的配置已经成功了。have fun!

如果用的开心,请关注一下 https://github.com/webp-sh/webp_server_go 哦!另外,他们还有其他语言的版本,请查看 https://github.com/webp-sh

链接:

记录优化 Vue 应用的首次加载速度

2024 年更新

不再推荐用这种偏门的方式去优化网络加载,这非常不可靠。Halo 2.x 也已经完全没有使用这种方式。正确的做法应该是在工程和代码层面优化,比如分包、异步加载路由、缓存策略、SSR 等。一定要上 CDN,也应该是从基础设施运维上面考虑。

感谢评论区的 @Yttrium 提醒更新。


Halo 的管理端使用的是 Vue 来构建的,随之收到不少反馈后台加载过于缓慢,其主要原因就是打包好的 Vue 应用的静态资源又多又大,可能同时就几十个请求,这对于一些小水管的服务器来说简直是致命的打击。

2e4f1d9d99910ce0933230d0c79d309c

解决办法

使用公共 cdn,我们只需要把打包好的静态资源丢在公共 cdn 上引用就好了。那么如何优雅的上传到公共 cdn 呢?

创建 .env.env.development

.env

NODE_ENV=production
// VERSION 需要和 package.json 的 version 一致。
PUBLIC_PATH=https://cdn.jsdelivr.net/npm/halo-admin@VERSION/dist/

.env.development

NODE_ENV=development
PUBLIC_PATH=/

修改 vue.config.js

module.exports = {
	publicPath: process.env.PUBLIC_PATH,
}

打包测试

可以在 dist/index.html 看到,所有静态资源的根路径已经变成了 https://cdn.jsdelivr.net/npm/halo-admin@VERSION/dist/

上传到 npmjs

npm login

npm init

npm publish

说明

  1. 每次发布版本前,需要修改 .envpackage.json 的版本号,且需要保持一致。
  2. 发布到 npmjs 前,需要先 npm run build
  3. 经过这些操作之后,只需要部署 dist/index.html 即可,其他静态资源无用,因为是走的 jsdelivr 的 cdn。
  4. 只建议个人小应用使用这种方式,其他类型应用请自行斟酌,毕竟上传到 npmjs 会上传项目代码。
  5. 过程描述的过于简单,仅做为记录,非教程。

相关链接

博客迁移到 Raspberry Pi

注:经过一段时间的折腾,已经放弃运行到树莓派了,其主要原因是因为家里网络质量一言难尽。

本着爱折腾之心,今天将博客搬到了吃灰已久的 Raspberry Pi 3B+。好吧,其实也是之前一个热心的网友送了我一年哲西云的内网穿透,一直没用,所以秉承着中华人民拒绝浪费的美好传统,折腾开始了...

配置

    .',;:cc;,'.    .,;::c:,,.    root@raspberrypi
   ,ooolcloooo:  'oooooccloo:    OS: Raspbian 10 buster
   .looooc;;:ol  :oc;;:ooooo'    Kernel: armv7l Linux 4.19.75-v7+
     ;oooooo:      ,ooooooc.     Uptime: 4h 4m
       .,:;'.       .;:;'.       Packages: 588
       .... ..'''''. ....        Shell: 5295
     .''.   ..'''''.  ..''.      CPU: ARMv7 rev 4 (v7l) @ 1.4GHz
     ..  .....    .....  ..      RAM: 386MiB / 926MiB
    .  .'''''''  .''''''.  .
  .'' .''''''''  .'''''''. ''.
  '''  '''''''    .''''''  '''
  .'    ........... ...    .'.
    ....    ''''''''.   .''.
    '''''.  ''''''''. .'''''
     '''''.  .'''''. .'''''.
      ..''.     .    .''..
            .'''''''
             ......

也就那样儿吧~

烧录镜像

这次搭建博客使用的镜像是官方的 Raspbian Buster Lite,之所以没选 Desktop,因为那玩意儿就是个玩具,没有实际用途,鹅且也不会用它,倒不如节省点内存。

进入官网 https://www.raspberrypi.org/downloads/raspbian ,找到 Raspbian Buster Lite,选择 Download ZIP

解压下载好的镜像得到 xxxx-xx-xx-raspbian-buster-lite.img

使用 Etcher 烧录镜像。当然,也有很多其他的烧录工具。

开启 SSH

这一步很简单,在烧录好的 SD 卡中,新建一个空白的 ssh 文件即可,需要注意的是,这个文件没有后缀,别搞个 ssh.txtssh.avi 啥的。

启动

插上 SD 和电源直接启动即可,默认用户名 pi,默认密码 raspberry,切换到 root 账户,sudo su root

环境配置

Java

sudo apt-get install openjdk-8-jre-headless
sudo apt-get install openjdk-8-jre

Vim

sudo apt-get install vim

Git

sudo apt-get install git

迁移数据

下载安装包

wget http://halo.ryanc.cc/release/halo-latest.jar -O halo-latest.jar

拉取备份的数据

git clone git@github.com:ruibaby/blog-data.git .halo

启动 Halo

java -jar halo-latest.jar

测试没问题,再配置 systemd 进行管理,教程:https://halo.run/guide/install/install-with-linux.html#%E8%BF%9B%E9%98%B6%E9%85%8D%E7%BD%AE

域名解析

由于我是直接是用的 又拍云 CDN 进行回源,所以也不需要安装 Nginx 啥的了,这个内网穿透服务提供了一个 CNAME,去解析一下就完事了。

哲西云

如有需要,可以去 http://www.zhexi.tech 体验体验。优惠码 GRRVFM

展示

56ffb0f522663785f4b031d595c1f6a0

d15419a817ec66336297bd8e08157508

758cfbd207c38b9db27a6bba295618a2

9e22bcea8ac55cd0c8a82d2c49b083c8

87e60eb23320ee7c00fb5ed66942f631

Flarum 的安装与配置

Flarum 是一款非常棒的开源论坛程序,Halo 的论坛 就是用 Flarum 搭建的。之前有人问过我 Flarum 如何搭建,所以下面讲一下 Flarum 的搭建过程(btw,官方的搭建教程实在草率)。

前提

  • 域名需要提前解析。

  • 注意服务器是否需要备案,如果没备案,会被 x 掉。

  • 有一定的 Linux 基础。

环境说明

  • Linux Server(本文是用的 CentOS 7.6)

  • Apache 或者 Nginx(本文是用的 Nginx)

  • PHP 7.1+

  • PHP 拓展: curl, dom, gd, json, mbstring, openssl, pdo_mysql, tokenizer, zip, fileinfo

  • MySQL 5.6+ 或者 MariaDB 10.0.5+

部署环境安装

更新服务器软件包

yum update -y

安装 Nginx/PHP/MySQL

这里我们使用 OneinStack 一键安装,人生苦短,懒得自己编译了。当然,如果有时间,根据需求自己编译安装更好。

2024 年更新,OneinStack 被曝包含恶意代码,请谨慎使用。
https://github.com/oneinstack/oneinstack/issues/511

image.png

如上图,选择好需要的软件以及版本后,复制安装命令到服务器执行就行了,安装过程可能会有点慢,耐心等待就行了。

需要注意的是,PHP 扩展中的 fileinfo 一定要勾选,Flarum 官方文档居然没有写需要这个扩展。(没错,这里我被坑了,嘤嘤嘤嘤~)

安装完成应该会打印出这些东西:
image.png

安装 Composer

php -r "copy('https://install.phpcomposer.com/installer', 'composer-setup.php');"

php composer-setup.php

php -r "unlink('composer-setup.php');"

mv composer.phar /usr/local/bin/composer

由于 Composer 的服务器在国外,可能导致下载 Flarum 已经依赖包会很慢,所以我们需要更换一下源地址。至于 Composer 是啥,其实就是 PHP 的一个包管理,类似 Java 的 MavenGradle 工具。

composer config -g repo.packagist composer https://packagist.phpcomposer.com

安装 Flarum

进入到 oneinstack 目录,执行 vhost.sh 脚本新建一个网站
image.png

然后会提示 SSL 证书选项,网站目录之类的东西,按照自己的需求选择即可。

创建完成后应该是这样子。

image.png

然后进入网站目录执行:

composer create-project flarum/flarum . --stability=beta

更新,现在 Flarum 已经发布正式版,请使用下面的命令安装:

composer create-project flarum/flarum .

然后等待下载 Flarum 以及对应的依赖即可,安装完成应该是这个样子的:

image.png

配置运行

上面其实就已经安装好了 Flarum,但是还需要进一步配置才能正确运行。

创建数据库

登陆 MySQL:

mysql -u root -p密码

创建数据库:

create database 数据库名 character set utf8mb4 collate utf8mb4_bin;

这里的字符集一定要是 utf8mb4,至于为什么是 utf8mb4,参考:https://www.jianshu.com/p/6967ce16a202

修改 Nginx 配置

进入 Nginx 配置文件目录:

cd /usr/local/nginx/conf/vhost

修改网站的配置文件:

vim xxx.conf

需要修改的地方:

  1. root:需要在路径后面加上 public,比如我的原本是 root /data/wwwroot/bbs.ryanwang.me;,需要修改为 root /data/wwwroot/bbs.ryanwang.me/public;

  2. 引入 Flarum 提供的配置,在 server 大括号中任意位置加上 include /data/wwwroot/xxx/.nginx.conf;xxx 为网站目录名。比如我的是 include /data/wwwroot/bbs.ryanwang.me/.nginx.conf;

最后的配置示例:

server {
  listen 80;
  listen 443 ssl http2;
  ssl_certificate /usr/local/nginx/conf/ssl/bbs.ryanwang.me.crt;
  ssl_certificate_key /usr/local/nginx/conf/ssl/bbs.ryanwang.me.key;
  ssl_protocols TLSv1 TLSv1.1 TLSv1.2 TLSv1.3;
  ssl_ciphers TLS13-AES-256-GCM-SHA384:TLS13-CHACHA20-POLY1305-SHA256:TLS13-AES-128-GCM-SHA256:TLS13-AES-128-CCM-8-SHA256:TLS13-AES-128-CCM-SHA256:EECDH+CHACHA20:EECDH+AES128:RSA+AES128:EECDH+AES256:RSA+AES256:EECDH+3DES:RSA+3DES:!MD5;
  ssl_prefer_server_ciphers on;
  ssl_session_timeout 10m;
  ssl_session_cache builtin:1000 shared:SSL:10m;
  ssl_buffer_size 1400;
  add_header Strict-Transport-Security max-age=15768000;
  ssl_stapling on;
  ssl_stapling_verify on;
  server_name bbs.ryanwang.me;
  access_log /data/wwwlogs/bbs.ryanwang.me_nginx.log combined;
  index index.html index.htm index.php;
  root /data/wwwroot/bbs.ryanwang.me/public;
  if ($ssl_protocol = "") { return 301 https://$host$request_uri; }

  include /usr/local/nginx/conf/rewrite/other.conf;
  #error_page 404 /404.html;
  #error_page 502 /502.html;

  location ~ [^/]\.php(/|$) {
    #fastcgi_pass remote_php_ip:9000;
    fastcgi_pass unix:/dev/shm/php-cgi.sock;
    fastcgi_index index.php;
    include fastcgi.conf;
  }

  location ~ .*\.(gif|jpg|jpeg|png|bmp|swf|flv|mp4|ico)$ {
    expires 30d;
    access_log off;
  }
  location ~ .*\.(js|css)?$ {
    expires 7d;
    access_log off;
  }
  location ~ /(\.user\.ini|\.ht|\.git|\.svn|\.project|LICENSE|README\.md) {
    deny all;
  }
  include /data/wwwroot/bbs.ryanwang.me/.nginx.conf;
}

最后我们需要检查 Nginx 配置是否有误并重载 Nginx 配置:

nginx -t

nginx: the configuration file /usr/local/nginx/conf/nginx.conf syntax is ok
nginx: configuration file /usr/local/nginx/conf/nginx.conf test is successful
nginx -s reload

Flarum 安装引导

如果出现下面的情况:

image

是因为没有对网站目录写入的权限,我们加一下权限即可:

# xxx 为网站目录名称
chmod -R 777 /data/wwwroot/xxx

然后刷新页面就可以看到安装表单了。

image.png

然后填写数据库信息以及管理员信息,点击安装即可。

安装部署部分到此结束。

常用插件安装

安装完成后会发现不支持中文,所以我们需要安装中文语言包。还有一些常用的插件。

进入网站目录:

# xxx 为网站目录名称
cd /data/wwwroot/xxx
# 简体中文语言包
composer require csineneo/lang-simplified-chinese

# 繁体中文语言包
composer require csineneo/lang-traditional-chinese

# 编辑器 Emoji 表情选择框
composer require clarkwinkelmann/flarum-ext-emojionearea

# Sitemap 生成器
composer require flagrow/sitemap

# Fancybox 插件
composer require squeevee/flarum-ext-fancybox 

安装完成后去后台启用即可(后台地址:网址/admin)。

image.png

使用 Caddy 自动部署 Gridea 博客

Gridea 是一个静态博客客户端,也可以称之为博客生成器,和 Hexo 之类的静态博客生成器很类似,唯一不同的是,Gridea 提供了一个非常好的可视化界面,非常容易就可以完成一个博客的搭建,而且配置都是可视化的,所以对小白来说非常友好。但是目前 Gridea 仅支持部署到 Github 和 Coding,由于众所周知的原因,Github Pages 会偶尔出现访问不了的情况(而且访问相对较慢),而且百度是不收录 Github Pages 的站点的。Coding 的话,抽风就更严重了。所以下面介绍一种方式,可以自动部署到自己的服务器。

前言

在开始之前,你至少需要了解 Gridea 如何部署到 Github,并且需要熟悉 Linux 的一些基本命令。对了,此方法基于 Github Pages,所以最好先在 Github Pages 上部署好博客。

Gridea 客户端配置

image.png

需要注意的是,这里的域名一定要填写为解析到自己服务器 ip 的地址。

服务器环境配置

在这里我使用 Ubuntu 16.04 作为演示,其他发行版大同小异。

安装 Git

sudo apt-get install git

安装 Caddy

Caddy 是一个使用 Go 语言编写的 web 服务器。如果需要详细了解,请访问:https://caddyserver.com 在这里就不在赘述。

# 安装 Caddy
curl https://getcaddy.com | bash -s personal http.git
# 配置 systemd,方便管理 Caddy 的运行状态
wget https://raw.githubusercontent.com/caddyserver/caddy/master/dist/init/linux-systemd/caddy.service
sudo cp caddy.service /etc/systemd/system/
sudo chown root:root /etc/systemd/system/caddy.service
sudo chmod 644 /etc/systemd/system/caddy.service
sudo systemctl daemon-reload
sudo systemctl start caddy.service

编写 Caddyfile

Caddyfile 即 Caddy 的站点配置文件,类似于 Nginx 的 nginx.conf。

touch /etc/caddy/Caddyfile

vim /etc/caddy/Caddyfile
https://[DOMAIN] {
    tls [EMAIL]
    gzip
    root [ROOT]
    git {GITHUB} {
        path [ROOT]
        hook /webhook [SECRET]
        hook_type github
        clone_args --recursive
        pull_args --recurse-submodules
    }
}

配置详解:

  1. [DOMAIN]:即博客地址,需要注意是否已经将服务器 ip 以 A 记录的类型解析到域名。

  2. [EMAIL]:SSL 证书申请邮箱,填写自己的即可。

  3. [ROOT]:静态页面存放地址,如:/data/wwwroot/gridea

  4. [SECRET]:Github 的 webhook secret key,下面会详解如何获取。

根据自己的实际情况填写完成之后应该是类似这个样子的:

https://gridea.ryanc.cc {
    tls i@ryanc.cc
    gzip
    root /data/wwwroot/gridea.ryanc.cc
    git github.com/ruibaby/ruibaby.github.io {
        path /data/wwwroot/gridea.ryanc.cc
        hook /webhook 123456
        hook_type github
        clone_args --recursive
        pull_args --recurse-submodules
    }
}

Github 的 Webhook 设置

为啥需要设置这个?因为我们需要做到每次更新到 Github Pages 的时候,让 Caddy 知道有更新,然后会自动拉取最新的静态页面资源,完成自动更新网站内容。

找到部署的仓库,然后选择 Settings -> Webhooks。点击 Add Webhook。

image

image.png

  1. Payload URL 的填写规则为:博客地址/webhook。

  2. Secret 自行设置。

  3. 然后点击 Add webhook 即可。

  4. 将填写好的 Secret 填写到上面 Caddyfile 的 [SECRET]。

启动 Caddy

进行到这里,我们只需要启动 Caddy 服务即可。

# 开机自启 Caddy
sudo systemctl enable caddy.service
# 启动 Caddy
sudo service caddy start
# 重启 Caddy
sudo service caddy restart
# 停止 Caddy
sudo service caddy stop

结尾

其实这种方式适用于任何部署在 Github Pages 的静态博客,有兴趣的小伙伴可以自己去折腾试试。

中国移动,你太坏了。

起因

本人于今年五月份左右办理了 中国移动 的电话卡,至于为啥要办移动的卡呢?是因为我一直都想逃离 中国联通 这个坑。你能想象去商店里买东西付款的时候木有信号吗?所以,我就办了张移动卡以作为备用,然后慢慢从联通切过去。毕竟我联通卡用了好长一段时间了,什么都绑定的这张卡。要先换绑,然后在换卡,这是常识。

经过

使用过程中,一直好好的,话费我也有好好地交,尽管不常用。而且一直是放在备用机上面的,偶尔开机使用一下。结果到了九月份的时候,突然就给我停机了,拨打电话提示“您已停机,请续交话费”,我开始天真的以为是没有话费了,然后我分几次差不多冲了100左右的话费。结果还是“您已停机,请续交话费”。然后我就拨打 10086 查询了一次话费,提示还有余额。这就奇怪了,为啥有余额还是停机呢?于是上网搜了搜,大部分都说是“停机保号”,一般一天左右就恢复。就这样我等了几天,还是木有恢复。

然后在某个风和日丽的早上我打了 10086 人工客服,对方称并不是所谓的“停机保号”,而是我在试用期间违规发送大量短信和拨打了违规电话。于是乎,我就要求提供详细的通话记录以及短信记录。对方说不能提供。也就是说,说我作恶,又不提供证据?就像是我说你在外面有几个私生子,你问我证据,我说不能提供。一个意思是吗?

客服给我的解决方案是叫我去当地的营业厅提交一张免冠照,然后就给我开通。我说我没在号码归属地,他让我把我免冠照发送到他们邮箱。WTF,凭啥?店大欺客是吧。

结果

我去黑猫投诉查询了一下 10086 栏目下的投诉记录,发现不少和我类似的经历,于是乎我也投诉了一遍。希望能快些处理。

后话

这到底是 中国移动 的系统错误还是他们故意作恶?如果是系统错误,为什么还不修复?你可是三大运营商之首啊,技术这么垃圾?如果是故意作恶,那我倒是能理解了。不作恶怎么赚钱嘛,是吧?

黑猫投诉中国移动栏目链接:https://tousu.sina.com.cn/company/view/?couid=1991428685

记一次拯救我的博客

事情的缘由是我服务器到期了,又没来得及续费,导致无法上服务器备份数据(使用的腾讯云老版本的学生机,每月一块钱的那种,这个月刚好到期,所以不想再用原价续费了,而且 1g 内存可能满足不了以后的需求,所以索性重新买了一台…)

数据咋办?

既然不想续费了,所以是无法上服务器备份数据的,正当我想去咬牙续费的时候,突然想起来曾经把数据备份到 Github 上过… 那么这就相当好办了。

重装博客

晒一张我在 Github 上的备份,虽然是五天前备份的了,但是影响不大,好在我这几天都没怎么操作。
image.png

嗯,得益于我用的 Halo 博客系统,所以只需要备份这一个目录就完全 OK,所有数据都不会丢失。因为这个系统他的用户数据和程序本身是完全分开的(数据库 db,上传的附件 upload,配置文件 application.yaml),当然,所有主题也是在这个目录的,但是因为主题是可以另外下载的,而且主题的配置数据也在数据库,所以我没有备份。

接下来我只需要把这个仓库克隆到服务器就好了。

git clone https://github.com/ruibaby/blog-data.git .halo

然后配置个 Java 环境,下载个 Halo 运行包。启动就完事。

配置服务器

这个环节没啥做的,配置个 Java 环境就好了,一行命令的事。

然后我跟着这个教程就完成了所有事情。https://halo.run/guide/install/install-with-linux.html

当然,我并没有配置反向代理,因为我是使用的又拍云的 cdn 全站加速,去控制台改改服务器 ip (源站地址)就好了。

自动备份脚本

考虑到后面可能会忘记备份数据,所以写了个自动提交的脚本。

#! /bin/bash

message=`date -u +"%Y_%m_%d_%H_%M"`

cd /root/.halo

rm -rf .git

git init

git remote add origin repo_url

git add application.yaml upload/ db/

git commit -m $message

git push -f origin master
  1. 将其写入到一个 sh 文件里面。

  2. 赋予执行权限 chmod +x {NAME}.sh

  3. 初始化 ~/.halo 仓库,cd ~/.halo & git init

  4. 去 Github 配置 ssh key。这一步不详细讲,自行百度。目的是在 push 的时候不需要输入用户名和密码。

  5. 执行 crontab -e 添加 00 03 * * * /bin/sh {NAME}.sh 的绝对路径。(00 03 * * * 表示每天三点执行)。

  6. 执行 service crond restart 使配置的定时任务生效。

结尾

数据无价,还好这次有备份数据。

Halo v1.0 正式发布

前言

Halo 从去年 5 月开源以来,广受小伙伴们的喜爱,在此非常感谢使用 Halo 发表博客的小伙伴们。

今年,在 @JohnNiang 的帮助下,我们几乎完全重写了 Halo,然后 1.0 正式版就发布了。在此,非常感谢 @JohnNiang 的加入以及他做出的贡献。再到后面,我们公开了 admin api 之后,@雨季不再来 使用了 Flutter 为 Halo 开发了管理端的 APP。相信以后越来越多人加入之后,Halo 会变得更好。希望大家会喜欢。

主要特性

  1. 拥有使用 Vue 开发的后台管理,体验升级,但是并不需要独立部署,启动 Halo 即可。
  2. 拥有 Restful 风格的 Content api,你可以用于开发单页面主题,微信小程序等。
  3. 拥有 Restful 风格的 Admin api,你可以用于开发桌面管理客户端,管理 App(已有) 等。
  4. 拥有使用 Flutter 开发的管理端 App,支持 Android 和 iOS,随时随地发表你的想法!感谢@雨季不再来。
  5. 拥有独立的评论插件,使用 Vue 开发,只需在页面引入构建好的 JS 文件即可,完美地和主题相结合。
  6. 支持多主题。另外,还支持在线下载主题以及更新主题。
  7. 支持在线修改主题文件内容,无需在本地修改然后上传。
  8. 十分友好的主题开发体验,支持自定义配置。(主题开发文档正在开发中)。
  9. 功能强大的附件管理,同时支持本地上传,又拍云/七牛云/阿里云等云存储,另外,还支持 SM.MS 图床(非常感谢 SM.MS,请大家善用该服务哦)。
  10. 自带友情链接管理,图库管理(给爱摄影的小伙伴们)。
  11. 支持自定义页面。
  12. 支持 Markdown 文档导入,顺带解析 FrontMatter。
  13. 支持日志功能,类似于 QQ 空间的说说,亦或者微博。同时支持微信发布日志(后续计划)。
  14. 还有…

相关链接

有喜欢的同学可以点个 star 哦。有任何问题可以去 Github issues 或者 https://bbs.halo.run

预览图

anatole.png

casper.png

material.png

admin-install.png

admin-login.png

admin-dashboard.png

admin-posts.png

admin-write.png

admin-write1.png

admin-write2.png

admin-attachment.png

admin-themes.png

admin-theme-settings.png

admin-profile.png

admin-options.png

❌