欢迎来到我的博客,本博客主要分享 WEB 开发的一些学习经历。以及我个人读书的思考和对生活的感悟。
-
本博客也会涉及一些对于编程思想的介绍和开发工具的一些好用的插件及进阶用法。
-
如果博客里的文章引发了你的思考,欢迎你与我交流。
欢迎来到我的博客,本博客主要分享 WEB 开发的一些学习经历。以及我个人读书的思考和对生活的感悟。
本博客也会涉及一些对于编程思想的介绍和开发工具的一些好用的插件及进阶用法。
如果博客里的文章引发了你的思考,欢迎你与我交流。
一直以来,我都感觉传统编辑器鼠标和键盘的频繁切换的体验让我无法接受,它让编程这件事情拆分成了两个系统:输入和移动。我一直有将他们统一的冲动,但又受限于 vim 学习成本过高的固有认知一直没有行动。它像一根若有若无的刺一直刺痛着我,直到有一天我接触到了 lazyvim,我想也许是时候改变了。 lazyvim 可以极大程度降低了配置难度,可以在不进行任何配置的情况下拥有一个轻量级的代码编辑器。 我切换 Neovim 除了 lazyvim 降低了配置成本还有另一个原因:我认为自己还会有相当长的时间开发相关的活动,一个高度可定制的编辑器,可以让我随心所欲的打造一个称手的工具。 关于配置我使用的是 https://github.com/craftzdog/dotfiles-public 并在此基础上扩充了 PHP 开发相关的配置。在文章底部我会贴出自己的 dotfile 仓库,目前我的配置可以用于 VUE、PHP、GO 的开发,如果需要可以自取。 在开发之前我们还是需要对 Neovim 基础操作有一定的了解,这里介绍一下我的学习方式。 我是通过 https://lazyvim-ambitious-devs.phillips.codes/ 一书建立的最初的基本只是,后续又看了一些视频加深我对 Neovim 的理解。 在视频学习的过程中,可以很好的学习资深的 vimer 是如何进行 vim 操作的,拿来主义可以省去很多自己探索的精力。最开始只需要模仿就可以了,等你对 vim 使用熟练后你会有自己的想法,那时自然而然的会形成自己独有的操作方式。 视频的学习我参考了 craftzdog 比较多,在 B 站上也学习了其他人的一些操作技巧。 Neovim 的学习成本也没有想象中那个高,正常下来,一周你就可以比较得心应手的进行开 发了。 得益于 LSP 的技术,让 Neovim 对开发语言的支持和 Vs code 并没什么本质的差别。 Vs code 对语言的支持也是通过 LSP 来实现的。 Neovim 带来了什么?它确实能使我整个开发的工作流完全脱离了鼠标,所有开发的工作包括但不限于代码编写、函数跳转、以及 git 的提交等全部都可以脱离鼠标完成,双手不需要离开键盘区域就可以完成编程所需要的操作。 此外像文件操作:打开、删除、重命名等操作,Neovim 也可以很方便的操作。它确实让我更专注了,所有的操作都没有任何的打断,我不需要频繁的把手离开键盘做一些额外的鼠标操作。 上文说到,Neovim 可定制化程度更更高,理论上你能按照你的习惯去配置 Neovim 来使它与你配合的更默契。 Neovim 会不会对开发效率带来一定的提升?从我目前的使用程度来看,它并不能带来明显的开发效率的提升,Neovim 在一些操作上的确更有优势,但是也有一些操作没有 GUI 更加的高效。总的看来我觉得它的开发效率和 Vs code 差不多。...
在多年的开发经历中,我发现不重视编程规范是普遍存在的一个问题。很多开发人员对规范的态度都是很抵触的,认为规范的条条框框是枷锁,会降低开发效率。 不仅仅是普通员工,很多公司的管理人员对于规范的重视程度也是不够的,甚至就没有制定规范的想法。 为什么会出现这种现象呢,我想每个人都会有自己的角度,大多数原因可能是因为项目周期紧张,没有时间制定规范,或是单纯的认为规范会影响开发效率。 上面的原因是客观存在的,所以大家对于不制定规范也没有太大的心智负担。今天我想就这个现象谈谈我对规范的认识。 规范一般有两种,一种是项目规范一种是编程规范。 关于项目规范 我在刚开始入行的时候,公司虽然也没有自己的规范,但是带我的前辈,给了我一份谷歌的开发规范,让我学习,代码的书写格式是怎么样的,什么时候应该换行,应该怎么避免写嵌套 if… 这让我对代码规范有了一个最基本的认识。 代码需要书写的简洁,易读。代码规范有点像写文章时的字体工整程度,越遵守代码规范,字体就越工整。你可以想象就算同样的一篇文章,字体工整和字体潦草给阅读人的感受是完全不同的。 后来我在一家公司做管理,刚到公司时也没有自己的规范,每个人的代码风格,变量命名,项目组织的习惯各有不同,导致项目的风格多样,这给我们带来了一些问题。 维护成本高 当我们维护其他同事写的代码的话,需要从头开始阅读一遍代码,才能了解问题具体出在哪。如果我们有规范就不需要通读所有代码,仅需依据规范出问题代码的大体位置。 代码复用差 当我们有一些通用业务需要封装时,如果没有规范,就需要考虑所有的代码风格,甚至要做一些额外的兼容才能把组件封装完成,有了规范我们完全就可以避免这类问题。 项目对接慢 由于没有规范,每次公司来了新同事,我们并没有很完善的文档给到他。导致新同事上手项目比较困难,中间还要不断地去询问老同事,才能对代码有一个相对比较完善的理解。 这无疑增加了很多的摩擦成本,且团队越大,这种摩擦成本就会越高。就像我们都说中文,又各自有自己的方言,大家需要了解每个人的方言体系,才能更好的深入交流。 我们需要“普通话”这样一个统一的说话规范,来降低我们团队内部的摩擦成本。 建立规范 为了解决上述问题,我们结合自身团队的特点,参考了他人的规范制定出了我们自己规范的初版。 初版规范经过内部评审和修改后,我们形成了自己的规范文档。 后续我们在实践的过程中遇到了一些规范上的不足,也进一步对规范做了补充,使规范在原有的基础上不断的迭代和优化。 这样一套规范建立后,使我们每一步都是在之前的基础之上,而不是每一次都是从 0 开始。这让我们可以不断的阶梯向上。 如何让规范落地 规范的制定后就需要考虑规范落地问题,如何让团队更好的遵守规范。 首先需要让团队认识到规范对我们团队合作是有益的。做好心理建设,消除心理的抵制情绪。 把规范塑造成开发文档,让团队养成经常查阅的习惯,对规范有疑惑就去规范文档找答案。 利用工具降低规范的执行难度,像一些代码风格的问题可以通过 IDE 代码格式化解决,不用团队开发者额外注意。 使用静态代码分析工具检测代码是否符合规范,如果使用 CI/CD 可以把这一步集成到 CI/CD 中,让不符合规范的代码,无法提交到线上环境。 关于编程规范 编程规范包括:设计模式,设计原则,编程范式,最佳实践等等。这类规范一般是行业发展多年,一些经验丰富的前辈总结的一些开发工作的规范。 因为这类规范通常是前辈们在长期实践中总结出来的。遵守这类规范能让我们更容易开发出稳定的程序,少走弯路。 这类规范一般都具有普遍性,对语言没有任何的限制,因此一旦你熟练的掌握,你用任何语言开发的程序都会有更好的稳定性,更少 Bug 、更容易维护和扩展。 我发现有些同学会遇到一些奇奇怪怪的问题,或者一段时间后,程序出现了运行瓶颈。有不少是因为没有遵守某些编程规范引发的问题。 有时他们不遵守编程规范,并非不愿意,而是因为他们不了解某些规范。因此对于编程规范,要像探寻宝藏一般,时常去探索一下。不断地完善和补充自己对编程规范的理解。 总结 规范短期看可能会觉得有点浪费时间,影响开发效率,从长期看,却未必如此,那些减少的 Bug, 复用的代码,以及与同事之间协作效率的提升,足以弥补开发时的损耗。 牛顿说:我之所以比现别人看的远,是因为我站在巨人的肩上。 运用前人的智慧和经验,能让我们做事情更加的顺利。要站在前人的肩膀上,哪怕你觉得这个人不够高,也比自己站在平地上看的更远。
在项目迭代的过程中,我们经常会进行更新线上代码的操作,而更新的操作我们会希望影响的用户越少越好,最好是能做到零停机更新。 在目前云原生的大背景下,K8s 的滚动更新策略会更为人知一些,但是一些中小型项目的部署建立一套 K8s 服务从成本和收益的角度来看是有些得不偿失的。 本文介绍用 Docker 和 Traefik 如何实现零停机升级服务。关于 Traefik 在 更靠近云原生的反向代理神器-Traefik 一文中有更详细的介绍。 整个服务部署流程如下 本方案通过 gitlab CI/CD 来进行部署,开发人员仅需在对应的分支提交代码,服务器会自动完成 构建 -> 部署 -> 通知 等操作。 在 部署 阶段通过蓝绿发布的方式来进行零停机升级的。 蓝绿发布是通 shell 脚本进行操作的,由于 Traefik 的 docker provider 不支持动态的增删服务,本方案采取了 file provider,shell 会启动新服务的时候修改Traefik 的 file provider 来把新服务加入到负载均衡的集群,并在新服务启动完成后,把老服务从负载均衡迁出并停用老服务。 得益于 Traefik 对动态配置的支持,所有对配置文件的修改是无需重启 Traefik,它会自动发现配置文件的变动,把最新的配置加载到程序内部。 整个 部署 流程中始终都会有容器在线提供服务,我们也就实现了零停机升级系统的目标。 本文最后会附上一份完整的 demo 链接,感兴趣的可以下载之后运行一下了解整个操作机制。 本方案还存在一些局限,如蓝绿发布其实是 blue 和 green 交替提供服务,如果你本身是一个服务集群,这个方案并不能很好的适应。 如果你面临上述问题可以考虑 docker swarm 来解决问题,或者部署 K8s,其间的选择主要是看你服务的规模。 本文到此基本结束,如果你更好的想法,欢迎留言讨论。 示例代码:https://github.com/yunxi177/zero-downtime References zero-downtime deploys with Docker Compose and Traefik:https://github....
Traefik 是一个用于反向代理的软件,如果你没有听说过,可以把它看作 Nignx 也是可以的。 Traefik 相比与 Nginx 更适合容器化部署: 只需要配置下容器的标签,Traefik 就可以自动发现新服务的加入,并根据标签绑定对应的域名 支持 TLS 证书自动申请(Let’s Encrypt) 支持 TCP/UDP 协议的转发 支持动态配置,可以在服务运行的状态下进行 Service、Router、Middleware 的增/删/改 Traefik 在项目最初部署阶段,会让整个部署更聚焦。以前用 Nginx 部署,你除了需要把容器启动起来,还需要配置 Nignx 将对应服务的域名反向代理到容器导出的端口上。 Traefik 将这个绑定域名的步骤放在了 docker compose 编写的阶段只需给容器加一个标签即可。项目上线时启动容器,Traefik 根据标签的配置把域名绑定到对应的容器上。 Traefik 可以通过 docker network 容器进行通讯,这意味着容器服务的端口无须再导出到物理机,Traefik 通过 docker network 就可以找到对应的容器处理请求。 Traefik 整个流程如下(中间件非必须,可有可无): 入口点(Entrypoints) -> 路由(Routers) -> [中间件(Middleware)] -> 服务(Service) -> Server Traefik 的配置分为两个:程序配置和路由配置。程序配置通过 traefik.yml 文件进行配置。traefik.yml 提供了路由配置的解析引擎(Providers)。 traefik.yml 配置示例如下: log: level: INFO accessLog: {} api: dashboard: true insecure: true entryPoints: # 入口点配置 web: address: ":80" providers: docker: # 通过 docker label 的方式进行路由配置 endpoint: "unix:///var/run/docker....
由于本地项目比较多,且对于环境要求各不相同,导致电脑上要装多个环境才能满足项目的运行。以我常用的 PHP 开发为例,需要 PHP 7.1 、PHP 7.3、PHP 8.1 、PHP 8.3,在这些项目中 compose 如何寻找到正确的 PHP 版本来安装依赖也是一个比较难以解决的问题。 为了不再受此困扰,我决定用容器来解决我面临的问题。开发环境容器化还有一个考虑就是容器本身对 CI/CD 比较友好,我们在测试和线上环境已经开始转向容器化部署,如果本地也进行容器化,编写好的 Dockfile 可以复用到后面的部署流程。 我的方案是为每个项目编写一个 docker-compose.yml 当我开始进入某个项目的开发工作时。只要打开对应的项目通过 docker-compose.yml 启动容器就可以启动对应项目的开发环境进行开发了。 容器化给我带来了哪些好处: 纯净的物理机:我不需要在物理机上安装各种各样的环境 低负载开发: 只有运行开发的相关环境,其他不相关的服务都不会在后台运行 部署和开发一致: 由于都是 Docker 部署,不会因为环境问题导致本地开发没问题线上出错的情况 专注于开发本身 :免去了多种环境下互相兼容下的管理工作,专注于开发本身。 在容器话的过程中,我也遇到了一些问题,在这里记录一下,供诸君参考。 一些问题 首先遇到的问题就是依赖缓存的问题,比如一个 GO 的项目,因为 GO 的环境是在容器里,这样每次启动项目都要重新下载一次依赖,浪费时间也没有必要,于是我就将 mod 依赖下载目录通过挂载卷映射到我本机上。 如此依赖就解决了每次启动容器,都要重新安装依赖的问题,这样做还有一个额外的好处就是我其他的 GO 项目也也可以把 mod 依赖下载路径映射到相同的位置,这样就能实现下载依赖的复用,也能避免过多的磁盘占用。 如果你是前端项目使用 pnpm 管理工具,也可以参考上述思路解决 npm 包的依赖复用问题。 遇到的另一个问题就是 Windows 环境下,文件读写性能不足的问题。Windows 用户在开发环境容器化是需要注意一下,如果你的项目运行需要大量的文件读取,会导致项目启动异常慢,这个是 Windows 下面使用容器的硬伤,目前无解。Linux 和 MacOS 并不会出现此类问题。 工具推荐 如果你用 Visual Studio Code 进行开发,可以安装一个 Docker 的扩展,通过设置 Docker: Compose Down 和 Docker: Compose Up 两个快捷键实现快速的启动和停止项目。...