cover
2023年12月6日
放弃从 Next.js 迁移到 Astro.js
分享使用 Astro.js 从迁移到放弃的心路历程
cover
2023年11月15日
Go 类型内嵌在反序列化中的妙用与陷阱
Go语言中的结构体嵌入的用法和技巧,包括替换字段类型和处理JSON反序列化。需要注意在处理嵌套结构体的JSON反序列化时的一些陷阱。
cover
2023年6月18日
Telegram 的富文本渲染机制浅析
对 Telegram 的 TDLib API 的分析,包括富文本数据的数据结构与渲染方案。
cover
2022年1月24日
使用 gRPC 与前端交互
使用 gRPC 与前端交互。gRPC-Gateway 适用于同时支持 rest 和 grpc 两套接口,使既有系统可以从 rest 平滑迁移到 grpc;gRPC-Web 适用于前后端直接使用 gRPC 协议交互,为 HTTP/1.x 提供支持。支持 Unary 和 Server Streaming,但不支持 Bi-directional Streaming 和 Client Streaming。
cover
2022年1月12日
服务端实时"动画"渲染
在本文中,作者分享了一种在网页上实时更新一部分数据的方法:使用 multipart/X-Mixed-Replace 格式来渲染 MJPEG 图片。作者通过实现服务端渲染 Game of Life 的服务 来展示这种方法的可行性。
cover
2022年1月1日
在生产环境使用 gRPC
本文总结了在生产环境使用 gRPC 的过程,包括使用 gRPC-Gateway 兼容 HTTP/JSON 接口、定义 ProtoBuf RPC 接口映射、挂载 gRPC-Gateway、为前端提供接口等。同时也提到了一些可能遇到的陷阱,例如多态类型和空值处理。
cover
2021年12月29日
自定义即刻 Yellow Page 域名
使用 Cloudflare Worker 实现即刻 Yellow Page 的自定义域名,让你享受到自己的成就感。这个过程其实是一个通用的使用 Cloudflare Worker 实现反向代理的流程。
cover
2021年12月20日
尝鲜 Go1.18
了解如何安装 Go1.18beta1 以及如何解决 vscode 无法解析包含泛型的代码的问题。
cover
2021年12月11日
思考 ProtoBuf 中的可选与必选字段
ProtoBuf 中的可选与必选字段,尤其是 optional 关键字的重新引入,对于扩展性的考虑和类型安全的保障带来了哪些变化?本文总结了使用 TypeScript 和 Go 的 gRPC 做的一些实验,提出了可选字段的两种实现方法。通过对比,可以更好地理解 optional 的作用和意义。
cover
2021年12月3日
对博客网页加载体积的一点优化
本文介绍了对博客网页加载体积进行优化的方法,包括对 Syntax Highlighter、lodash 和 Chakra UI 的优化,以及如何控制 NEXT_DATA 的大小。通过这些优化,网页的体积得到了明显的降低,首次加载网页的 JS 体积从 200+KB 降低到 70+KB。
cover
2021年10月25日
理解 Go singleflight 中的异常处理
理解 Go singleflight 中的异常处理,介绍了 Go 的 singleflight 库的使用方法及其异常处理方式。
cover
2021年9月26日
在 MacOS 上使用 Podman 代替 Docker
cover
2021年9月23日
深入理解 Go Comparable Type
本文主要介绍了 Go 语言中的 Comparable 类型,包括 Go 内置类型的比较规则、reflect 包中的实现方式以及相关陷阱和应用。文章指出,除了 Map、Slice 和 Func 之外,Go 中的大多数类型都是 Comparable 的,其中 Struct 和 Array 得看成员类型的支持。为避免相关问题,建议使用无法被伪造的指针类型或 Struct 类型作为 Context 的 Key。
cover
2021年9月11日
Go sync.Once 原理
了解 Go 中 sync.Once 的工作原理。通过 atomic 和 Mutex 实现双检锁单例模式,确保一段任务只会执行一次。
cover
2021年8月29日
gRPC 与『面向扩展编程』
本文探讨了如何通过 gRPC 实现向后兼容和可扩展性,包括一切字段皆可选、UnimplementedServer 的使用、输入输出必须为结构体、每个 RPC 专属的输入输出类型等。文章旨在帮助我们创建更易于维护和扩展的接口。
cover
2021年8月21日
Go 的 String Interning
介绍 Go 的 String Interning 技术,可以在特定场景下降低内存占用,提高性能。使用 String Interning 的技巧已被广泛使用,如 easyjson 可以在反序列化时引入 String Interning。
cover
2021年7月31日
在 Vercel 优雅地搭建 Go 微服务
本文介绍了如何在 Vercel 上搭建 Go 微服务,包括编写代码、自定义路由、Monorepo、RPC、定时任务、日志监控、数据库和 Integrations 等。相比于自建 K8S 集群或 AWS Lambda,使用 Vercel 的云函数可以降低很多的维护成本,但需要注意 Vercel 的功能有限。
cover
2021年5月29日
Server-Side Events: 简单高效的服务端推送
Server-Side Events 是一种简单高效的服务端推送机制,比传统轮询和长轮询更实时,网络开销更小,使用 HTTP 实现,对于服务端来说实现更为简单轻量。适合用于前端展示的消息订阅。
cover
2021年3月19日
Go Echo 如何正确地处理错误
本文介绍了在 Go Echo 中正确处理错误的方法,涉及到了 Echo 中 error 的处理流程、HTTPErrorHandler 和 Error Handle Middleware 的区别、以及 middleware 的顺序等问题。文章详细阐述了如何避免错误导致的 HTTP/500 错误,确保最终响应能符合预期,同时提供了一些建议,如何正确使用 middleware。
cover
2021年3月1日
🏗️
Golang 在即刻后端的实践
本文介绍了即刻后端服务重构的过程和实践,以及重构后的成果和方案。通过 Go 语言的优点和即刻后端服务的优化,新版服务的开销得到了显著降低。文章还介绍了仓库结构、持续集成与构建的实践经验。
cover
2020年10月31日
Got a New Keyboard
介绍了作者购买新键盘的经历,比较了几个备选方案,最终选择了 Niz 66。该键盘支持蓝牙连接和双模,键位丰富,静音,手感好。总结:购买新键盘。
cover
2020年7月5日
🔩
Use GSuite Like a PRO
使用 Google App Script 做更多事情。Google App Script 是一种基于 JavaScript 的编程语言,可以轻松访问 G Suite 应用程序的 API。本文介绍了 Google App Script 的优缺点以及如何使用它来构建更强大的应用程序。
cover
2020年5月1日
对 Go 编程哲学的一点理解
Go 编程哲学:显式错误、严格类型、简洁源码、无泛型、低心智负担。
cover
2020年4月4日
Go 中 struct 初始化
本文讲解了 Go 语言中 struct 的初始化方式、多种数据类型和结构体组合方式等问题。文章总结了不同的初始化方式及其区别,介绍了内嵌结构体的初始化以及 slice、map、channel 等需要 make 的类型的初始化方式。
cover
2019年10月10日
MongoDB 读写分离踩坑
MongoDB 读写分离踩坑。主从复制导致写操作不实时返回,解决方案包括 Write Concern 机制等。详见文章。
cover
2019年9月10日
PlantUML as a document
使用 PlantUML 在 Markdown 文档中绘制 UML 图表。PlantUML 是一种依赖于 DSL 进行 UML 图表绘制的工具。该工具支持许多类型的图表,可以在中文文档中找到相关资料。可以使用 PlantUML 服务器渲染出图片提供给前端显示。该工具与代码同步使用 Git 进行管理,非常适合工程文档的管理。
cover
2019年9月6日
从 Google passports 换到 1Password
从 Google Passwords 切换到 1Password,解决了密码管理的痛点,同时也带来了更多功能。不过删除旧密码时遇到了问题,只能通过脚本一条一条删除。
cover
2019年8月22日
JWT 的一些思考
JWT的优点和缺点,以及设计思路和实现方式,包括AccessToken+RefreshToken的组合,AccessToken和RefreshToken应该包含哪些信息,以及是否需要使用不同KeyPair。同时,讨论了如何对一组Token进行拉黑和实现零延迟地强制下线。
cover
2019年3月14日
使用 dotfiles 管理 Windows
使用 dotfiles 管理 Windows,将配置流程数据化,通过 Git 和软链接实现快速备份和迁移设备。推荐使用 dotfiles 管理 PowerShell 样式文件、启动脚本、Telegram 字体配置文件、VSCode 配置文件等。附上我的 dotfiles 仓库地址。
cover
2019年2月8日
个人项目架构的思考
个人项目架构的思考:在微服务和前后端分离流行的当下,为什么要这么做?对于个人开发来说,本身就没有分工难题,这么做反而给我带来了很多不必要的麻烦。对于简单的个人项目,如果前端只是后端数据基础的CRUD展示,也没有必要进行分离。将整个系统进行“压缩”之后,我可以一条命令就将整个项目打包成 docker 镜像,或者直接就在 AppEngine 上线,不必再为后续的维护头疼。
cover
2019年2月6日
优雅地分享即刻消息给 Telegram 好友
优雅地分享即刻消息给 Telegram 好友。使用 Jikeview Bot 解析即刻链接,转换成对 Telegram 用户最友好的图文内容,支持动图、视频和多图。快来体验!
cover
2019年2月1日
Surface Go 上手
"Surface Go 上手"是一篇介绍 Surface Go 使用体验的文章,主要关注于其轻便和续航等优点,但是也提到了触屏体验和性能方面的问题。文章介绍了选购经验和使用技巧,并总结了 Surface Go 适合需要一台便携设备用于办公和学习的用户。
cover
2019年1月21日
尝试实时渲染“截图“
本文介绍了如何使用 HTML 和 CSS 在文章中实时渲染截图。文章中详细讲解了如何渲染 HTML 和 CSS,包括行内样式、<style> 标签和 CSS 文件加载,以及实例演示。
cover
2019年1月17日
使用 Notion 搭建博客
使用 Notion 搭建博客,解决了其他平台上的问题,包括无法自定义域名、体验不好、静态博客麻烦等等。Notion 的 API 是半公开的,可以通过 API 来创建网页,将 Notion 当作和 Wordpress 一样的 CMS 来管理博客。通过后端渲染和 CDN 服务提高了页面加载速度,同时使用了 Cloudflare 的服务提高 SEO 效率。配置 Table Page,建立相应的列和视图,控制文章内容和展示。最终实现了使用 Notion 搭建博客的目标。
cover
2019年1月9日
谈谈「重构」
介绍重构的理念,如何平时重构代码。文章触动较大的是作者对于重构的理念,强调重构是一个大工程,但应该将这个工程穿插在日常开发当中,保证未来系统的强健。同时,文章提到开发过程中需要分为两个方面,功能开发和代码重构,两者不能同时进行。这一点很重要,因为两者的目标不同,同时进行会导致代码成为一团乱麻。
cover
2019年1月8日
记一次 Google Cloud 封禁
Google Cloud 封禁的经历,使用 Docker Image 时,授权文件被公开,项目被停用。需要注意管理授权文件的方式和将私钥放在项目目录当中的风险。
cover
2019年1月1日
几个 2018 年喜欢的产品
几个 2018 年喜欢的产品:Windows Subsystem Linux 和 Notion。
cover
2018年11月23日
Bitbucket Pipeline + Docker + Gradle 自动部署实践
Bitbucket Pipeline + Docker + Gradle 自动部署实践。使用 Bitbucket Pipeline 服务实现持续集成,并将项目打包成 docker 镜像,通过拉取最新的镜像来进行更新代码。使用 Gradle Docker Build 处理 Docker 打包,使用 GCR 托管镜像,使用 vps 实例部署。通过编写 Pipeline 脚本实现自动部署。
cover
2018年9月12日
浙大路由器配置指南
浙大路由器配置指南,介绍了在校园网环境下使用路由器的方法。包括使用 Linux 客户端和模拟登录两种方式,以及一个校网验证脚本的使用方法。
cover
2018年8月10日
Github Pages 反向代理跨域实践
使用 nginx 反向代理和 letsencrypt 进行配置,实现 Github Pages 上web app 的跨域问题。通过将前端流量转发到 nginx 服务器,然后再通过 nginx 反向代理将前端代理到 Github Pages,api 代理到后端服务器。同时,通过 letsencrypt 的 certbot 进行配置,实现 Https 跳转。
cover
2018年8月9日
记一次 GitHub Pages 部署
这篇文章主要介绍了作者如何将自己使用React写的小玩具部署到Github Pages上。文章详细介绍了部署过程中遇到的问题以及解决方法,对于需要将自己的项目部署到Github Pages上的开发者来说,非常实用。
cover
2016年11月16日
RxActivityResult 原理浅析
本文介绍了 RxActivityResult 库的原理和源码分析,通过启动一个代理 Activity 来实现两个 Activity 之间的数据交互。通过打包 Intent 和回调接口,启动 HolderActivity 并将 Request 提供给它,然后 HolderActivity 启动目标 Activity 并接受返回结果,最后通过回调将结果传递给订阅者。另外,文章也提到了类似的库 RxPermissions。