﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>语源科技BlogJava-首页技术区</title><link>http://www.blogjava.net/</link><description>专注于Java技术</description><language>zh-cn</language><lastBuildDate>Mon, 20 Apr 2026 18:22:33 GMT</lastBuildDate><pubDate>Mon, 20 Apr 2026 18:22:33 GMT</pubDate><ttl>60</ttl><item><title>社交场景下的统一即时通讯im消息流交互层模块化技术实践</title><link>http://www.blogjava.net/jb2011/archive/2026/04/20/451777.html</link><dc:creator>Jack Jiang</dc:creator><author>Jack Jiang</author><pubDate>Mon, 20 Apr 2026 10:43:00 GMT</pubDate><guid>http://www.blogjava.net/jb2011/archive/2026/04/20/451777.html</guid><wfw:comment>http://www.blogjava.net/jb2011/comments/451777.html</wfw:comment><comments>http://www.blogjava.net/jb2011/archive/2026/04/20/451777.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/jb2011/comments/commentRss/451777.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/jb2011/services/trackbacks/451777.html</trackback:ping><description><![CDATA[<p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">网易技术团队旭风分享，有排版优化和修订。</p><h1>1、引言</h1><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">一款社交产品的诞生，离不开即时通讯（IM）场景。随着团队业务版图在社交领域的布局，诞生了多个社交场景APP，涉及的IM场景，包含私聊、群聊、聊天室等。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>这些IM场景，在消息流的展示形式上是极为相似的，同时每个业务又有着自己特殊的交互需求。基于此，我们对IM消息流能力做了标准化的构建，来减少IM功能的业务接入成本；同时也是为了统一各个业务的技术方案，减少跨业务开发的理解和维护成本。</strong>本文主要针对iOS端在IM消息流交互层的设计上，提供一些实践思路。</p><div img-uploading-status=""  image-package-1"="" data-index="1" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="cover_opti" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172238382-1940825930.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172238382-1940825930.png" medium-zoom-image="" ls-is-cached=""  lazyloaded"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div></div><h1>2、业界的实现方案</h1><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">目前业界有各种即时通讯服务商提供的配套交互层解决方案，其大多以牺牲灵活性来满足快速集成需要，在定制能力上远不能胜任我们业务需要。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">再诸如 MessageKit之类的社区IM框架，其在视觉交互表现上功能完备，能帮助我们快速、灵活搭建IM消息流结构，但业务需要的是一套完整的携带消息交互能力的方案，因此对此类框架，仍需要做不小的改造才能适应我们的业务（另一参考方案：<a href="https://gitee.com/jackjiang/MobileIMSDK" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">MobileIMSDK</a>（<a href="https://www.cnblogs.com/imteck4713/p/gitee.com/jackjiang/MobileIMSDK" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">Gitee源码托管地址</a>））。</p><h1>3、我们的想法</h1><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>对于一个IM消息流交互层方案，主要考虑几个方面：</strong></p><ul style="margin-left: 2.5rem; padding-left: 0px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><li style="list-style: inherit;"><em>1）</em>规范的消息流结构：提供消息流视图结构规范化的构建方式；</li><li style="list-style: inherit;"><em>2）</em>标准的消息交互能力：统一消息交互能力，业务方按需使用，快速集成；</li><li style="list-style: inherit;"><em>3）</em>业务拓展性：针对数据源、消息交互能力提供业务灵活拓展点；</li><li style="list-style: inherit;"><em>4）</em>业务接入成本：内置通用交互方案，降低业务接入成本。</li></ul><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">目前，我们存量业务中的IM场景，底层IM能力主要由云信引擎提供。同时又存在基于业务服务端，通过HTTP去交互的场景。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">另外，还需要预留后期切换IM引擎的可能性，因此需要将交互层IM能力抽象出来。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">此外，为了适应团队现状，减小业务接入成本，考虑将云信提供的交互能力内置在方案中。</p><h1>4、整体设计</h1><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>设计愿景：</strong>提供标准化的能力，同时对拓展开放。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">我们期望一套通用的IM消息流能力，能够在方案上标准化。这里的标准化，主要包含消息流结构构建的标准化，以及消息交互能力的标准化。同时，方案需要在交互能力上适应不同业务场景，因此采用依赖注入的方式，提供业务定制能力。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>按照职能划分，将框架整体分为了两层：</strong></p><div img-uploading-status=""  image-package-2"="" data-index="2" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="1" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172248072-572198573.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172248072-572198573.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin: 10px auto;">&nbsp;</p></div></div></div><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>1）</em></strong>消息流结构层：负责消息流结构的构建，定义消息视图、布局、数据上的规范，提供业务层分别在「消息」、「会话」两个维度的配置能力。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>2）</em></strong>消息交互层：提供消息能力、消息流、消息数据方面的交互能力，向下依赖交互接口，内置标准交互能力的同时，也支持业务按需注入交互实现。</p><h1>5、聊天消息流的显示结构</h1><h2>5.1 消息组件</h2><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">不同的业务场景，消息流样式表现必然有所差异。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>下面列出了我们几个业务中的消息流界面：</strong></p><div img-uploading-status=""  image-package-3"="" data-index="3" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="2" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172253118-172076407.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172253118-172076407.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div></div><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">如何设计一套通用的消息流视图结构，满足不同业务需要？经过对各个业务以及一些主流IM工具的观察，将消息视图结构设计成如下结构，是能够满足我们各个IM场景需要的（见下图）。</p><div img-uploading-status=""  image-package-4"="" data-index="4" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="3" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172300245-2086082730.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172300245-2086082730.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div></div><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">我将消息结构拆分成了5部分，对应5个消息组件&nbsp;&nbsp;MessageView ，每个消息组件都支持业务对其「样式」、「显隐」、「布局」进行配置，从而满足不同场景定制需要。</p><blockquote style="background-image: none; border-width: medium medium medium 3px; border-style: none none none solid; border-color: currentcolor currentcolor currentcolor #e2dfdf; margin: 10px 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin: 10px auto;">MessageView作为基础消息组件，提供了一些标准能力，例如是否响应菜单动作 canPerformMenuAction 、视图重用回调时机 prepareForReuse 、尺寸策略等。</p><p style="margin: 10px auto;">open&nbsp;class&nbsp;MessageView: MessageAbstractView {</p><p style="margin: 10px auto;">&nbsp;&nbsp;public&nbsp;var&nbsp;canPerformMenuAction =&nbsp;false</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;open func refresh(with&nbsp;message: Message) {}</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;open func prepareForReuse() {}</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;open&nbsp;class&nbsp;func createSizeStrategy(message: Message, fittingSize: CGSize) -&gt; MessageLayoutSizeStrategy? {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;// ...</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;}</p><p style="margin: 10px auto;">}</p></blockquote><h2>5.2 尺寸策略</h2><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">消息组件尺寸作为消息流布局上不可或缺的要素，方案提供了多种尺寸计算策略 MessageLayoutSizeStrategy 。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>具体是：</strong></p><ul style="margin-left: 2.5rem; padding-left: 0px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><li style="list-style: inherit;"><em>1）</em>自动布局计算策略：业务方对消息组件使用 AutoLayout 布局时使用，内部会依据约束自动计算好组件尺寸；</li><li style="list-style: inherit;"><em>2）</em>SizeThatFit 策略：依据组件 SizeThatFit 方法返回的尺寸进行布局；</li><li style="list-style: inherit;"><em>3）</em>自定义策略：提供自定义尺寸计算方式。</li></ul><blockquote style="background-image: none; border-width: medium medium medium 3px; border-style: none none none solid; border-color: currentcolor currentcolor currentcolor #e2dfdf; margin: 10px 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin: 10px auto;">public protocol MessageLayoutSizeStrategy {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func caclulateSize(_ sizeViewType: MessageView.Type,</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;message: Message,</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fittingSize: CGSize) -&gt; CGSize</p><p style="margin: 10px auto;">}</p><p style="margin: 10px auto;">&nbsp;</p><p style="margin: 10px auto;">public struct MessageAutoLayoutSizeStrategy: MessageLayoutSizeStrategy {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;public func caclulateSize(_ sizeViewType: MessageView.Type,</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;message: Message,</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fittingSize: CGSize) -&gt; CGSize {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;// ...省略其他代码</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;sizeView.systemLayoutSizeFitting(UIView.layoutFittingCompressedSize)</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;}</p><p style="margin: 10px auto;">&nbsp;</p><p style="margin: 10px auto;">}</p><p style="margin: 10px auto;">&nbsp;</p><p style="margin: 10px auto;">public struct MessageSizeThatFitsStrategy: MessageLayoutSizeStrategy {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;public func caclulateSize(_ sizeViewType: MessageView.Type,</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;message: Message,</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fittingSize: CGSize) -&gt; CGSize&nbsp; {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;// ...省略其他代码</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return&nbsp;sizeView.sizeThatFits(fittingSize)</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;}</p><p style="margin: 10px auto;">}</p></blockquote><h2>5.3 布局快照</h2><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">我们还针对消息组件维度支持了布局快照。通常当一个消息组件尺寸固定，在交互过程中尺寸不会发生的情况下，打开布局快照，以减少布局计算消耗。同时也提供了快照清除的能力。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">我们对多个消息流在快速滚动过程中的CPU峰值做了统计，在使用自动布局尺寸策略的情况下，开启布局快照，峰值降低了10%~20%。</p><div img-uploading-status=""  image-package-5"="" data-index="5" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="4" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172308798-1399375821.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172308798-1399375821.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div></div><h2>5.4 交互事件</h2><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">另外在手势交互上，对外暴露了各个消息组件的一系列交互事件。常见的场景例如单击浏览消息内容，长按展示消息菜单等。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">方案内部提供了基于系统样式的长按菜单，并提供上层菜单配置能力，同时也可以基于暴露的长按手势事件来自定义菜单。</p><h2>5.5 消息流</h2><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">一个会话对应一个流，方案也提供了消息流在会话维度上的一些标准化配置。例如消息分页数量、是否自动拉取历史消息、是否开启增量刷新，以及在时间展示上的样式配置等。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">此外为了减少列表重绘，消息流也支持增量刷新。通常情况下业务层不需要主动刷新列表，只需对消息数据进行增删改操作，内部会触发对数据源的「diff-update」计算，从而驱动列表的增量更新。</p><div img-uploading-status=""  image-package-6"="" data-index="6" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="5" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172314511-1003407726.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172314511-1003407726.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div></div><h1>6、聊天消息交互层</h1><h2>6.1 概述</h2><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>对于业务方而言，在消息交互上通常关心这么几点：</strong></p><ul style="margin-left: 2.5rem; padding-left: 0px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><li style="list-style: inherit;"><em>1）</em>提供了哪些标准化的交互能力；</li><li style="list-style: inherit;"><em>2）</em>如何拓展自定义的交互实现；</li><li style="list-style: inherit;"><em>3）</em>如何对交互流程进行干预。</li></ul><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">结合团队现状，我们在方案内部内置了基于某信的IM交互能力，同时定义了相关交互接口，供业务方按需注入实现。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">在实际业务中，一个APP内可能存在多个IM场景，因此交互能力支持按会话维度进行注入，各个会话之间的交互是相互隔离的。</p><h2>6.2 消息源</h2><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">不同的IM场景，消息数据来源可能存在差异。例如我们私聊、群聊的数据源来自云信数据同步服务，聊天室数据需要通过云信提供的历史消息接口拉取，另外也存在诸如通过业务服务端接口来拉取消息数据的场景。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">因此方案上设置了数据源接口 SessionMessageProvider ，提供不同场景消息源的定制能力。</p><blockquote style="background-image: none; border-width: medium medium medium 3px; border-style: none none none solid; border-color: currentcolor currentcolor currentcolor #e2dfdf; margin: 10px 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin: 10px auto;">public protocol SessionMessageProvider {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func messages(in&nbsp;session: Session,</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;anchorMessage: Message?,</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;limit: Int,</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;completion: @escaping ([Message]) -&gt; Void)</p><p style="margin: 10px auto;">}</p></blockquote><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">方案设置了一个负责管理消息数据源的 DataManager 实例， 其依赖 SessionMessageProvider 提供的数据源。同时内置了基于云信的数据源获取实现，能够根据当前会话类型，获取私聊、群聊、聊天室的数据源。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">如果当前场景是通过HTTP拉取消息的，则需要业务上层手动注入一个从接口获取数据源的 SessionMessageProvider 实例。</p><div img-uploading-status=""  image-package-7"="" data-index="7" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="6" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172322020-1289552147.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172322020-1289552147.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div></div><h2>6.3 交互源</h2><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">方案提供了IM标准交互能力，例如消息收发、消息撤回、保存等，以统一各业务交互姿势。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">具体的交互源除了要考虑目前包含的云信及业务服务端，也要适应其他交互源，因此将交互实现部分也抽象出了接口 MessageServiceInterface 。业务根据当前实际场景，注入具体的交互实现即可。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>下面列出了一些交互申明：</strong></p><blockquote style="background-image: none; border-width: medium medium medium 3px; border-style: none none none solid; border-color: currentcolor currentcolor currentcolor #e2dfdf; margin: 10px 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin: 10px auto;">public protocol MessageServiceInterface {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func send(message: Message,&nbsp;in&nbsp;session: Session, completion: @escaping MessageServiceInterfaceCompletion)</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func resend(message: Message, completion: @escaping MessageServiceInterfaceCompletion)</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func forward(message: Message, to session: Session, completion: @escaping MessageServiceInterfaceCompletion)</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func revoke(message: Message, completion: @escaping MessageServiceInterfaceCompletion)</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func save(message: Message,&nbsp;in&nbsp;session: Session, completion: @escaping MessageServiceInterfaceCompletion)</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func&nbsp;delete(message: Message, completion: @escaping MessageServiceInterfaceCompletion)</p><p style="margin: 10px auto;">}</p></blockquote><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">同样，我们也内置了一些通用交互方案，例如支持云信提供的私聊群聊交互能力，以及由中台提供的通用聊天室服务交互能力，以支持相关场景下快速接入。</p><div img-uploading-status=""  image-package-8"="" data-index="8" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="7" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172331316-289718956.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172331316-289718956.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div></div><h2>6.4 交互钩子</h2><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">在实际IM业务开发过程中，往往需要对交互流程做一些干预，或是在交互过程中做一些定制化的动作。因此方案也提供了一些交互钩子，支持「交互前置校验」、「交互前准备」。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>以消息发送流程为例，提供了「发送前校验」、「发送准备」两个消息发送过程的回调钩子：</strong></p><blockquote style="background-image: none; border-width: medium medium medium 3px; border-style: none none none solid; border-color: currentcolor currentcolor currentcolor #e2dfdf; margin: 10px 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin: 10px auto;">public protocol MessageServicePrechecker {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;// 消息发送前置校验&nbsp;</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func shouldSend(message: Message,&nbsp;in&nbsp;session: Session) -&gt; Bool</p><p style="margin: 10px auto;">&nbsp;</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;// ...省略其他代码</p><p style="margin: 10px auto;">}</p><p style="margin: 10px auto;">&nbsp;</p><p style="margin: 10px auto;">public protocol MessageServicePreparation {</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;/// 准备发送准备</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;func prepareSend(message: Message,&nbsp;in&nbsp;session: Session, callback: @escaping MessageServicePreparationCallback)</p><p style="margin: 10px auto;">&nbsp;</p><p style="margin: 10px auto;">&nbsp;&nbsp;&nbsp;&nbsp;// ...省略其他代码</p><p style="margin: 10px auto;">}</p></blockquote><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>整体的发送流程如图所示：</strong></p><div img-uploading-status=""  image-package-9"="" data-index="9" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="8" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172339025-249421311.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172339025-249421311.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div></div><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">前置校验阶段，用来作消息发送前的校验工作，根据实际状态决定消息是否可以发送。发送准备阶段，则可以在消息投递前做最后的准备工作，例如海外业务可以在这里处理消息资源附件上传Amazon，或是在此处对消息塞入一些客户端信息、反作弊Token等，支持异步操作。</p><h1>7、业务接入能力</h1><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">业务只需要在上层提供针对消息以及会话两个维度的配置，就能基于内置的交互能力，构建出一套基础的IM消息流能力。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">在具体的消息样式呈现上，则通常需要业务层维护一组关于「消息类型-消息组件类型-消息结构」的映射关系。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>具体关联如下：</strong></p><div img-uploading-status=""  image-package-10"="" data-index="10" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="9" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172344348-320868519.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260420172344348-320868519.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div></div><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">在交互能力上，提供了IM场景的标准能力，业务可以按需使用。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">另外，实际IM场景可能需要一些更为丰富的定制能力，则可以依据方案提供的消息数据源接口、消息交互接口来对具体交互实现进行定制。同时也可以使用相关的交互钩子对交互过程进行干预，以适应自己的业务。</p><h1>8、本文小结</h1><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">本文对团队IM场景的现状做了简单介绍，撇开具体实现细节，就如何搭建一套能够适应多业务需要的通用IM消息流交互层方案，提供了一些思考和实践经验。</p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">从结果来看，该方案稳定支撑了团队多个IM场景，抹除各场景实现差异，有效降低了维护成本和新业务接入成本。</p><h1>9、参考资料</h1><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[1]&nbsp;<a href="http://www.52im.net/thread-3065-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">零基础IM开发入门(一)：什么是IM聊天系统？</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[2]&nbsp;<a href="http://www.52im.net/thread-812-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">一套海量在线用户的移动端IM架构设计实践分享(含详细图文)</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[3]&nbsp;<a href="http://www.52im.net/thread-151-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">一套原创分布式即时通讯(IM)系统理论架构方案</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[4]&nbsp;<a href="http://www.52im.net/thread-2796-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">从游击队到正规军(二)：马蜂窝旅游网的IM客户端架构演进和实践总结</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[5]&nbsp;<a href="http://www.52im.net/thread-2966-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">社交软件红包技术解密(十)：手Q客户端针对2020年春节红包的技术实践</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[6]&nbsp;<a href="http://www.52im.net/thread-4636-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">微信团队分享：来看看微信十年前的IM消息收发架构，你做到了吗</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[7]&nbsp;<a href="http://www.52im.net/thread-4690-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">携程技术分享：亿级流量的办公IM及开放平台技术实践</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[8]&nbsp;<a href="http://www.52im.net/thread-4707-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">百度公共IM系统的Andriod端IM SDK组件架构设计与技术实现</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[9]&nbsp;<a href="http://www.52im.net/thread-4764-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">转转平台IM系统架构设计与实践(一)：整体架构设计</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[10]&nbsp;<a href="http://www.52im.net/thread-4812-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">一年撸完百万行代码，企业微信的全新鸿蒙NEXT客户端架构演进之路</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[11]&nbsp;<a href="http://www.52im.net/thread-4874-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">转转客服IM聊天系统背后的技术挑战和实践分享</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[12]&nbsp;<a href="http://www.52im.net/thread-4886-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">B站IM消息系统的新架构升级实践</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[13]&nbsp;<a href="http://www.52im.net/thread-4437-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">企业微信针对百万级组织架构的客户端性能优化实践</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[14]&nbsp;<a href="http://www.52im.net/thread-3631-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">企业微信的IM架构设计揭秘：消息模型、万人群、已读回执、消息撤回等</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[15]&nbsp;<a href="http://www.52im.net/thread-1470-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">从客户端的角度来谈谈移动端IM的消息可靠性和送达机制</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[16]&nbsp;<a href="http://www.52im.net/thread-1413-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">现代移动端网络短连接的优化手段总结：请求速度、弱网适应、安全保障</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[17]&nbsp;<a href="http://www.52im.net/thread-1998-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">IM消息ID技术专题(一)：微信的海量IM聊天消息序列号生成实践（算法原理篇）</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[18]&nbsp;<a href="http://www.52im.net/thread-3088-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">IM开发干货分享：有赞移动端IM的组件化SDK架构设计实践</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[19]&nbsp;<a href="http://www.52im.net/thread-3615-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">阿里技术分享：闲鱼IM基于Flutter的移动端跨端改造实践</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[20]&nbsp;<a href="http://www.52im.net/thread-3732-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">IM开发干货分享：万字长文，详解IM&#8220;消息&#8220;列表卡顿优化实践</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[21]&nbsp;<a href="http://www.52im.net/thread-4202-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">IM开发干货分享：IM客户端不同版本兼容运行的技术思路和实践总结</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[22]&nbsp;<a href="http://www.52im.net/thread-4359-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">百度统一socket长连接组件从0到1的技术实践</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[23]&nbsp;<a href="http://www.52im.net/thread-4470-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">淘宝移动端统一网络库的架构演进和弱网优化技术实践</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[24]&nbsp;<a href="http://www.52im.net/thread-4620-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1;">抖音技术分享：飞鸽IM桌面端基于Rust语言进行重构的技术选型和实践总结</a></p><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[25]&nbsp;<a href="http://www.52im.net/thread-4633-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">大型IM工程重构实践：企业微信Android端的重构之路</a></p><blockquote style="background-image: none; border-width: medium medium medium 3px; border-style: none none none solid; border-color: currentcolor currentcolor currentcolor #e2dfdf; margin: 10px 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin: 10px auto;"><strong>即时通讯技术学习：</strong></p><p style="margin: 10px auto;">- 移动端IM开发入门文章：《<a href="http://www.52im.net/thread-464-1-1.html" rel="noopener nofollow" target="_blank" style="color: #1d58d1; text-decoration: none;">新手入门一篇就够：从零开发移动端IM</a>》</p><p style="margin: 10px auto;">- 开源IM框架源码：<a href="https://github.com/JackJiang2011/MobileIMSDK" rel="noopener nofollow" target="_blank" style="color: #1d58d1; text-decoration: none;">https://github.com/JackJiang2011/MobileIMSDK</a>（<a href="https://gitee.com/jackjiang/MobileIMSDK" rel="noopener nofollow" target="_blank" style="color: #1d58d1; text-decoration: none;">备用地址点此</a>）</p></blockquote><p style="margin: 10px auto; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">（<strong>本文同步发布于：</strong><a href="http://www.52im.net/thread-4905-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration: none;">http://www.52im.net/thread-4905-1-1.html</a>）</p><img src ="http://www.blogjava.net/jb2011/aggbug/451777.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/jb2011/" target="_blank">Jack Jiang</a> 2026-04-20 18:43 <a href="http://www.blogjava.net/jb2011/archive/2026/04/20/451777.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>AGENTS.md 和 SOUL.md 有啥区别</title><link>http://www.blogjava.net/paulwong/archive/2026/04/16/451776.html</link><dc:creator>paulwong</dc:creator><author>paulwong</author><pubDate>Thu, 16 Apr 2026 08:26:00 GMT</pubDate><guid>http://www.blogjava.net/paulwong/archive/2026/04/16/451776.html</guid><wfw:comment>http://www.blogjava.net/paulwong/comments/451776.html</wfw:comment><comments>http://www.blogjava.net/paulwong/archive/2026/04/16/451776.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/paulwong/comments/commentRss/451776.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/paulwong/services/trackbacks/451776.html</trackback:ping><description><![CDATA[<div style="font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif; line-height: 1.8; color: #333; background: #f5f5f5; padding: 20px; margin: 0;"> <div style="max-width: 900px; margin: 0 auto; background: #fff; border-radius: 8px; box-shadow: 0 2px 8px rgba(0,0,0,0.1); padding: 40px;"> <h1 style="font-size: 28px; color: #1a1a1a; margin-bottom: 30px; padding-bottom: 15px; border-bottom: 3px solid #2196F3;">AGENTS.md vs SOUL.md 区别</h1> <table style="width: 100%; border-collapse: collapse; margin: 20px 0; background: #fff;"> <tbody><tr> <th style="width: 20%; padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0; background: #2196F3; color: #fff; font-weight: 600;">特性</th> <th style="width: 40%; padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0; background: #2196F3; color: #fff; font-weight: 600;">AGENTS.md</th> <th style="width: 40%; padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0; background: #2196F3; color: #fff; font-weight: 600;">SOUL.md</th> </tr> <tr style="background: #f8f9fa;"> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;"><strong style="color: #2196F3;">作用</strong></td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">工作空间规则和操作指南</td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">Agent 的身份、性格和核心行为准则</td> </tr> <tr> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;"><strong style="color: #2196F3;">内容</strong></td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">任务流程、通信协议、安全规范、工具使用说明</td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">角色定义、价值观、行为风格、自我认知</td> </tr> <tr style="background: #f8f9fa;"> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;"><strong style="color: #2196F3;">谁制定</strong></td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">系统/Manager 生成 + 用户自定义规则</td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">用户为每个 Agent 量身定制</td> </tr> <tr> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;"><strong style="color: #2196F3;">层级</strong></td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">组织/工作空间级别</td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">个人/Agent 级别</td> </tr> <tr style="background: #f8f9fa;"> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;"><strong style="color: #2196F3;">修改权限</strong></td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">可追加自定义规则</td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">完全可定制</td> </tr> <tr> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;"><strong style="color: #2196F3;">目的</strong></td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">告诉 Agent <strong style="color: #2196F3;">如何工作</strong></td> <td style="padding: 12px 15px; text-align: left; border: 1px solid #e0e0e0;">告诉 Agent <strong style="color: #2196F3;">它是谁</strong></td> </tr> </tbody></table> <h2 style="font-size: 22px; color: #333; margin: 30px 0 15px;">具体对比</h2> <h3 style="font-size: 18px; color: #555; margin: 25px 0 12px;">AGENTS.md - "工作手册"</h3> <div style="background: #fff3e0; border-left: 4px solid #FF9800; padding: 20px; margin: 20px 0; border-radius: 4px;">
<pre style="background: #263238; color: #aed581; padding: 15px; border-radius: 6px; overflow-x: auto; margin: 15px 0;"><code style="background: transparent; color: inherit; padding: 0; font-family: 'SF Mono', Monaco, 'Courier New', monospace; font-size: 14px;">## Task Execution
1. Sync files first: `hiclaw-sync` 2. Read the task spec
3. Create `plan.md` before starting
... ## Communication
- @mention Manager when task completed
- NO_REPLY usage rules
- History context handling</code></pre> </div> <p style="margin: 15px 0;"><strong style="color: #2196F3;">解决什么问题：</strong></p> <ul style="margin: 15px 0; padding-left: 25px;"> <li style="margin: 8px 0;">怎么接收任务？</li> <li style="margin: 8px 0;">怎么和 Manager/其他 Worker 沟通？</li> <li style="margin: 8px 0;">文件放哪里？</li> <li style="margin: 8px 0;">什么时候 @mention？</li> <li style="margin: 8px 0;">安全规范是什么？</li> </ul> <h3 style="font-size: 18px; color: #555; margin: 25px 0 12px;">SOUL.md - "灵魂/人格定义"</h3> <div style="background: #e8f5e9; border-left: 4px solid #4CAF50; padding: 20px; margin: 20px 0; border-radius: 4px;">
<pre style="background: #263238; color: #aed581; padding: 15px; border-radius: 6px; overflow-x: auto; margin: 15px 0;"><code style="background: transparent; color: inherit; padding: 0; font-family: 'SF Mono', Monaco, 'Courier New', monospace; font-size: 14px;"># Worker: cs-assistant ## Identity
You are cs-assistant, a technical support specialist... ## Personality
- Professional yet approachable
- Patient with technical questions
... ## Domain
- Wiki.js management
- Technical documentation
... ## Response Style
- Provide clear, structured answers
- Include command examples when relevant</code></pre> </div> <p style="margin: 15px 0;"><strong style="color: #2196F3;">解决什么问题：</strong></p> <ul style="margin: 15px 0; padding-left: 25px;"> <li style="margin: 8px 0;">我是谁？</li> <li style="margin: 8px 0;">我的专业领域是什么？</li> <li style="margin: 8px 0;">我该怎么说话？（语气、风格）</li> <li style="margin: 8px 0;">我的价值观是什么？</li> <li style="margin: 8px 0;">面对不同情况该怎么反应？</li> </ul> <h2 style="font-size: 22px; color: #333; margin: 30px 0 15px;">实际例子</h2> <div style="background: #e3f2fd; border-left: 4px solid #2196F3; padding: 20px; margin: 20px 0; border-radius: 4px;"> <p style="margin: 0 0 15px 0;"><strong>用户问："怎么备份 Wiki.js？"</strong></p> <br /> <p style="margin: 0 0 10px 0;"><strong>AGENTS.md 告诉 cs-assistant：</strong></p> <p style="margin: 0 0 15px 0;">&#8594; 先检查知识库有没有相关内容，然后基于知识库回答，最后引用来源文件</p> <br /> <p style="margin: 0 0 10px 0;"><strong>SOUL.md 告诉 cs-assistant：</strong></p> <p style="margin: 0 0 15px 0;">&#8594; 你是技术专家，应该用专业但友好的语气回答，给出具体命令示例</p> <br /> <p style="margin: 0 0 10px 0;"><strong>实际回答：</strong></p>
<pre style="background: #263238; color: #aed581; padding: 15px; border-radius: 6px; overflow-x: auto; margin: 15px 0;"><code style="background: transparent; color: inherit; padding: 0; font-family: 'SF Mono', Monaco, 'Courier New', monospace; font-size: 14px;">Based on [wiki-guide.md]:
Wiki.js 支持以下备份方式... 具体操作命令：
wikijs backup --output ~/wiki-backup.zip Additional context:
建议定期备份，可以设置定时任务...</code></pre> </div> <div style="background: linear-gradient(135deg, #667eea 0%, #764ba2 100%); color: #fff; padding: 25px; border-radius: 8px; margin-top: 30px;"> <h2 style="font-size: 22px; color: #fff; margin: 0 0 15px 0;">一句话总结</h2> <p style="margin: 0 0 10px 0;"><strong>AGENTS.md</strong> = "工作规范说明书"（流程、规则、工具）</p> <p style="margin: 0 0 15px 0;"><strong>SOUL.md</strong> = "人格定义书"（身份、性格、专业领域）</p> <p style="margin: 0;">两者配合：AGENTS.md 确保 Agent <strong>正确做事</strong>，SOUL.md 确保 Agent <strong>像自己</strong>。</p> </div> </div>
</div><img src ="http://www.blogjava.net/paulwong/aggbug/451776.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/paulwong/" target="_blank">paulwong</a> 2026-04-16 16:26 <a href="http://www.blogjava.net/paulwong/archive/2026/04/16/451776.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>HICLAW案例</title><link>http://www.blogjava.net/paulwong/archive/2026/04/15/451775.html</link><dc:creator>paulwong</dc:creator><author>paulwong</author><pubDate>Wed, 15 Apr 2026 03:08:00 GMT</pubDate><guid>http://www.blogjava.net/paulwong/archive/2026/04/15/451775.html</guid><wfw:comment>http://www.blogjava.net/paulwong/comments/451775.html</wfw:comment><comments>http://www.blogjava.net/paulwong/archive/2026/04/15/451775.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/paulwong/comments/commentRss/451775.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/paulwong/services/trackbacks/451775.html</trackback:ping><description><![CDATA[基于 HiClaw 的运维场景多智能体协同实践<br /><a href="https://www.cnblogs.com/alisystemsoftware/p/19840321" target="_blank">https://www.cnblogs.com/alisystemsoftware/p/19840321</a><br /><br /><img src ="http://www.blogjava.net/paulwong/aggbug/451775.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/paulwong/" target="_blank">paulwong</a> 2026-04-15 11:08 <a href="http://www.blogjava.net/paulwong/archive/2026/04/15/451775.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>agent使用FireCrawl简介</title><link>http://www.blogjava.net/paulwong/archive/2026/04/15/451774.html</link><dc:creator>paulwong</dc:creator><author>paulwong</author><pubDate>Wed, 15 Apr 2026 03:03:00 GMT</pubDate><guid>http://www.blogjava.net/paulwong/archive/2026/04/15/451774.html</guid><wfw:comment>http://www.blogjava.net/paulwong/comments/451774.html</wfw:comment><comments>http://www.blogjava.net/paulwong/archive/2026/04/15/451774.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/paulwong/comments/commentRss/451774.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/paulwong/services/trackbacks/451774.html</trackback:ping><description><![CDATA[FireCrawl本地安装<br />docker-compose.yaml<br /><div style="background-color:#eeeeee;font-size:13px;border:1px solid #CCCCCC;padding-right: 5px;padding-bottom: 4px;padding-left: 4px;padding-top: 4px;width: 98%;word-break:break-all"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />-->name:&nbsp;firecrawl<br /><br />x-common-service:&nbsp;<span style="color: #FF0000; ">&amp;common-service</span><br />&nbsp;&nbsp;#&nbsp;NOTE:&nbsp;If&nbsp;you&nbsp;don't&nbsp;want&nbsp;to&nbsp;build&nbsp;the&nbsp;service&nbsp;locally,<br />&nbsp;&nbsp;#&nbsp;comment&nbsp;out&nbsp;the&nbsp;build:&nbsp;statement&nbsp;and&nbsp;uncomment&nbsp;the&nbsp;image:&nbsp;statement<br />&nbsp;&nbsp;image:&nbsp;ghcr.io/firecrawl/firecrawl:latest<br />&nbsp;&nbsp;#&nbsp;build:&nbsp;apps/api<br /><br />&nbsp;&nbsp;ulimits:<br />&nbsp;&nbsp;&nbsp;&nbsp;nofile:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;soft:&nbsp;65535<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;hard:&nbsp;65535<br />&nbsp;&nbsp;networks:<br />&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;backend<br />&nbsp;&nbsp;extra_hosts:<br />&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;"host.docker.internal:host-gateway"<br />&nbsp;&nbsp;logging:<br />&nbsp;&nbsp;&nbsp;&nbsp;driver:&nbsp;"json-file"<br />&nbsp;&nbsp;&nbsp;&nbsp;options:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-size:&nbsp;"10m"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-file:&nbsp;"3"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;compress:&nbsp;"true"<br /><br />x-common-env:&nbsp;<span style="color: #FF0000; ">&amp;common-env</span><br />&nbsp;&nbsp;REDIS_URL:&nbsp;${REDIS_URL:-redis://redis:6379}<br />&nbsp;&nbsp;REDIS_RATE_LIMIT_URL:&nbsp;${REDIS_URL:-redis://redis:6379}<br />&nbsp;&nbsp;PLAYWRIGHT_MICROSERVICE_URL:&nbsp;${PLAYWRIGHT_MICROSERVICE_URL:-http://playwright-service:3000/scrape}<br />&nbsp;&nbsp;POSTGRES_USER:&nbsp;${POSTGRES_USER:-postgres}<br />&nbsp;&nbsp;POSTGRES_PASSWORD:&nbsp;${POSTGRES_PASSWORD:-postgres}<br />&nbsp;&nbsp;POSTGRES_DB:&nbsp;${POSTGRES_DB:-postgres}<br />&nbsp;&nbsp;POSTGRES_HOST:&nbsp;${POSTGRES_HOST:-nuq-postgres}<br />&nbsp;&nbsp;POSTGRES_PORT:&nbsp;${POSTGRES_PORT:-5432}<br />&nbsp;&nbsp;USE_DB_AUTHENTICATION:&nbsp;${USE_DB_AUTHENTICATION:-false}<br />&nbsp;&nbsp;NUM_WORKERS_PER_QUEUE:&nbsp;${NUM_WORKERS_PER_QUEUE:-8}<br />&nbsp;&nbsp;CRAWL_CONCURRENT_REQUESTS:&nbsp;${CRAWL_CONCURRENT_REQUESTS:-10}<br />&nbsp;&nbsp;MAX_CONCURRENT_JOBS:&nbsp;${MAX_CONCURRENT_JOBS:-5}<br />&nbsp;&nbsp;BROWSER_POOL_SIZE:&nbsp;${BROWSER_POOL_SIZE:-5}<br />&nbsp;&nbsp;OPENAI_API_KEY:&nbsp;${OPENAI_API_KEY}<br />&nbsp;&nbsp;OPENAI_BASE_URL:&nbsp;${OPENAI_BASE_URL}<br />&nbsp;&nbsp;MODEL_NAME:&nbsp;${MODEL_NAME}<br />&nbsp;&nbsp;MODEL_EMBEDDING_NAME:&nbsp;${MODEL_EMBEDDING_NAME}<br />&nbsp;&nbsp;OLLAMA_BASE_URL:&nbsp;${OLLAMA_BASE_URL}<br />&nbsp;&nbsp;AUTUMN_SECRET_KEY:&nbsp;${AUTUMN_SECRET_KEY}<br />&nbsp;&nbsp;SLACK_WEBHOOK_URL:&nbsp;${SLACK_WEBHOOK_URL}<br />&nbsp;&nbsp;BULL_AUTH_KEY:&nbsp;${BULL_AUTH_KEY}<br />&nbsp;&nbsp;TEST_API_KEY:&nbsp;${TEST_API_KEY}<br />&nbsp;&nbsp;SUPABASE_ANON_TOKEN:&nbsp;${SUPABASE_ANON_TOKEN}<br />&nbsp;&nbsp;SUPABASE_URL:&nbsp;${SUPABASE_URL}<br />&nbsp;&nbsp;SUPABASE_SERVICE_TOKEN:&nbsp;${SUPABASE_SERVICE_TOKEN}<br />&nbsp;&nbsp;SELF_HOSTED_WEBHOOK_URL:&nbsp;${SELF_HOSTED_WEBHOOK_URL}<br />&nbsp;&nbsp;LOGGING_LEVEL:&nbsp;${LOGGING_LEVEL}<br />&nbsp;&nbsp;PROXY_SERVER:&nbsp;${PROXY_SERVER}<br />&nbsp;&nbsp;PROXY_USERNAME:&nbsp;${PROXY_USERNAME}<br />&nbsp;&nbsp;PROXY_PASSWORD:&nbsp;${PROXY_PASSWORD}<br />&nbsp;&nbsp;SEARXNG_ENDPOINT:&nbsp;${SEARXNG_ENDPOINT}<br />&nbsp;&nbsp;SEARXNG_ENGINES:&nbsp;${SEARXNG_ENGINES}<br />&nbsp;&nbsp;SEARXNG_CATEGORIES:&nbsp;${SEARXNG_CATEGORIES}<br />&nbsp;&nbsp;MAX_CPU:&nbsp;${MAX_CPU:-0.8}<br />&nbsp;&nbsp;MAX_RAM:&nbsp;${MAX_RAM:-0.8}<br />&nbsp;&nbsp;ALLOW_LOCAL_WEBHOOKS:&nbsp;${ALLOW_LOCAL_WEBHOOKS:-false}<br /><br />services:<br />&nbsp;&nbsp;playwright-service:<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;NOTE:&nbsp;If&nbsp;you&nbsp;don't&nbsp;want&nbsp;to&nbsp;build&nbsp;the&nbsp;service&nbsp;locally,<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;comment&nbsp;out&nbsp;the&nbsp;build:&nbsp;statement&nbsp;and&nbsp;uncomment&nbsp;the&nbsp;image:&nbsp;statement<br />&nbsp;&nbsp;&nbsp;&nbsp;image:&nbsp;ghcr.io/firecrawl/playwright-service:latest<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;build:&nbsp;apps/playwright-service-ts<br />&nbsp;&nbsp;&nbsp;&nbsp;environment:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;PORT:&nbsp;3000<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;PROXY_SERVER:&nbsp;${PROXY_SERVER}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;PROXY_USERNAME:&nbsp;${PROXY_USERNAME}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;PROXY_PASSWORD:&nbsp;${PROXY_PASSWORD}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ALLOW_LOCAL_WEBHOOKS:&nbsp;${ALLOW_LOCAL_WEBHOOKS:-false}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;BLOCK_MEDIA:&nbsp;${BLOCK_MEDIA:-false}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;Configure&nbsp;maximum&nbsp;concurrent&nbsp;pages&nbsp;for&nbsp;Playwright&nbsp;browser&nbsp;instances<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;MAX_CONCURRENT_PAGES:&nbsp;${CRAWL_CONCURRENT_REQUESTS:-10}<br />&nbsp;&nbsp;&nbsp;&nbsp;networks:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;backend<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;Resource&nbsp;limits&nbsp;for&nbsp;Docker&nbsp;Compose&nbsp;(not&nbsp;Swarm)<br />&nbsp;&nbsp;&nbsp;&nbsp;cpus:&nbsp;2.0<br />&nbsp;&nbsp;&nbsp;&nbsp;mem_limit:&nbsp;4G<br />&nbsp;&nbsp;&nbsp;&nbsp;memswap_limit:&nbsp;4G<br />&nbsp;&nbsp;&nbsp;&nbsp;logging:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;driver:&nbsp;"json-file"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;options:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-size:&nbsp;"10m"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-file:&nbsp;"3"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;compress:&nbsp;"true"<br />&nbsp;&nbsp;&nbsp;&nbsp;tmpfs:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;/tmp/.cache:noexec,nosuid,size=1g<br /><br />&nbsp;&nbsp;api:<br />&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">&lt;</span><span style="color: #800000; ">&lt;:&nbsp;</span><span style="color: #FF0000; ">*common-service<br />&nbsp;&nbsp;&nbsp;&nbsp;environment:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;&lt;:&nbsp;*common-env<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;HOST:&nbsp;"0.0.0.0"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;PORT:&nbsp;${INTERNAL_PORT:-3002}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;EXTRACT_WORKER_PORT:&nbsp;${EXTRACT_WORKER_PORT:-3004}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;WORKER_PORT:&nbsp;${WORKER_PORT:-3005}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;NUQ_RABBITMQ_URL:&nbsp;amqp://rabbitmq:5672<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ENV:&nbsp;local<br />&nbsp;&nbsp;&nbsp;&nbsp;depends_on:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;redis:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;condition:&nbsp;service_started<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;playwright-service:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;condition:&nbsp;service_started<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;rabbitmq:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;condition:&nbsp;service_healthy<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;nuq-postgres:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;condition:&nbsp;service_started<br />&nbsp;&nbsp;&nbsp;&nbsp;ports:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;"${PORT:-3002}:${INTERNAL_PORT:-3002}"<br />&nbsp;&nbsp;&nbsp;&nbsp;command:&nbsp;node&nbsp;dist/src/harness.js&nbsp;--start-docker<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;Resource&nbsp;limits&nbsp;for&nbsp;Docker&nbsp;Compose&nbsp;(not&nbsp;Swarm)<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;Increase&nbsp;if&nbsp;you&nbsp;have&nbsp;more&nbsp;CPU&nbsp;cores/RAM&nbsp;available<br />&nbsp;&nbsp;&nbsp;&nbsp;cpus:&nbsp;4.0<br />&nbsp;&nbsp;&nbsp;&nbsp;mem_limit:&nbsp;8G<br />&nbsp;&nbsp;&nbsp;&nbsp;memswap_limit:&nbsp;8G<br /><br />&nbsp;&nbsp;redis:<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;NOTE:&nbsp;If&nbsp;you&nbsp;want&nbsp;to&nbsp;use&nbsp;Valkey&nbsp;(open&nbsp;source)&nbsp;instead&nbsp;of&nbsp;Redis&nbsp;(source&nbsp;available),<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;uncomment&nbsp;the&nbsp;Valkey&nbsp;statement&nbsp;and&nbsp;comment&nbsp;out&nbsp;the&nbsp;Redis&nbsp;statement.<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;Using&nbsp;Valkey&nbsp;with&nbsp;Firecrawl&nbsp;is&nbsp;untested&nbsp;and&nbsp;not&nbsp;guaranteed&nbsp;to&nbsp;work.&nbsp;Use&nbsp;with&nbsp;caution.<br />&nbsp;&nbsp;&nbsp;&nbsp;image:&nbsp;redis:alpine<br />&nbsp;&nbsp;&nbsp;&nbsp;#&nbsp;image:&nbsp;valkey/valkey:alpine<br /><br />&nbsp;&nbsp;&nbsp;&nbsp;networks:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;backend<br />&nbsp;&nbsp;&nbsp;&nbsp;command:&nbsp;redis-server&nbsp;--bind&nbsp;0.0.0.0<br />&nbsp;&nbsp;&nbsp;&nbsp;volumes:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;redis-data:/data<br />&nbsp;&nbsp;&nbsp;&nbsp;logging:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;driver:&nbsp;"json-file"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;options:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-size:&nbsp;"5m"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-file:&nbsp;"2"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;compress:&nbsp;"true"<br /><br />&nbsp;&nbsp;rabbitmq:<br />&nbsp;&nbsp;&nbsp;&nbsp;image:&nbsp;rabbitmq:3-management<br />&nbsp;&nbsp;&nbsp;&nbsp;networks:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;backend<br />&nbsp;&nbsp;&nbsp;&nbsp;command:&nbsp;rabbitmq-server<br />&nbsp;&nbsp;&nbsp;&nbsp;healthcheck:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;test:&nbsp;["CMD",&nbsp;"rabbitmq-diagnostics",&nbsp;"-q",&nbsp;"check_running"]<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;interval:&nbsp;10s<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;timeout:&nbsp;10s<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;retries:&nbsp;10<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;start_period:&nbsp;30s<br />&nbsp;&nbsp;&nbsp;&nbsp;volumes:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;rabbitmq-data:/var/lib/rabbitmq<br />&nbsp;&nbsp;&nbsp;&nbsp;logging:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;driver:&nbsp;"json-file"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;options:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-size:&nbsp;"5m"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-file:&nbsp;"2"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;compress:&nbsp;"true"<br /><br />&nbsp;&nbsp;nuq-postgres:<br />&nbsp;&nbsp;&nbsp;&nbsp;image:&nbsp;ghcr.io/firecrawl/nuq-postgres:latest<br />&nbsp;&nbsp;&nbsp;&nbsp;environment:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;POSTGRES_USER:&nbsp;${POSTGRES_USER:-postgres}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;POSTGRES_PASSWORD:&nbsp;${POSTGRES_PASSWORD:-postgres}<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;POSTGRES_DB:&nbsp;${POSTGRES_DB:-postgres}<br />&nbsp;&nbsp;&nbsp;&nbsp;networks:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;backend<br />&nbsp;&nbsp;&nbsp;&nbsp;volumes:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;-&nbsp;postgres-data:/var/lib/postgresql/data<br />&nbsp;&nbsp;&nbsp;&nbsp;logging:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;driver:&nbsp;"json-file"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;options:<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-size:&nbsp;"10m"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;max-file:&nbsp;"3"<br />&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;compress:&nbsp;"true"<br /><br />networks:<br />&nbsp;&nbsp;backend:<br />&nbsp;&nbsp;&nbsp;&nbsp;driver:&nbsp;bridge<br /><br />volumes:<br />&nbsp;&nbsp;redis-data:<br />&nbsp;&nbsp;&nbsp;&nbsp;driver:&nbsp;local<br />&nbsp;&nbsp;rabbitmq-data:<br />&nbsp;&nbsp;&nbsp;&nbsp;driver:&nbsp;local<br />&nbsp;&nbsp;postgres-data:<br />&nbsp;&nbsp;&nbsp;&nbsp;driver:&nbsp;local<br /></span></div><br />.env<br /><div style="background-color:#eeeeee;font-size:13px;border:1px solid #CCCCCC;padding-right: 5px;padding-bottom: 4px;padding-left: 4px;padding-top: 4px;width: 98%;word-break:break-all"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />-->#&nbsp;=====&nbsp;Required&nbsp;ENVS&nbsp;======<br />PORT=8019<br />HOST=0.0.0.0<br /><br />#&nbsp;Note:&nbsp;PORT&nbsp;is&nbsp;used&nbsp;by&nbsp;both&nbsp;the&nbsp;main&nbsp;API&nbsp;server&nbsp;and&nbsp;worker&nbsp;liveness&nbsp;check&nbsp;endpoint<br /><br />#&nbsp;To&nbsp;turn&nbsp;on&nbsp;DB&nbsp;authentication,&nbsp;you&nbsp;need&nbsp;to&nbsp;set&nbsp;up&nbsp;Supabase.<br />USE_DB_AUTHENTICATION=false<br /><br />#&nbsp;=====&nbsp;Optional&nbsp;ENVS&nbsp;======<br /><br />##&nbsp;===&nbsp;AI&nbsp;features&nbsp;(JSON&nbsp;format&nbsp;on&nbsp;scrape,&nbsp;/extract&nbsp;API)&nbsp;===<br />#&nbsp;Provide&nbsp;your&nbsp;OpenAI&nbsp;API&nbsp;key&nbsp;here&nbsp;to&nbsp;enable&nbsp;AI&nbsp;features<br />#&nbsp;OPENAI_API_KEY=your_openai_api_key_here<br /><br />#&nbsp;Experimental:&nbsp;Use&nbsp;Ollama<br />#&nbsp;OLLAMA_BASE_URL=http://localhost:11434/api<br />#&nbsp;MODEL_NAME=deepseek-r1:7b<br />#&nbsp;MODEL_EMBEDDING_NAME=nomic-embed-text<br /><br />#&nbsp;Experimental:&nbsp;Use&nbsp;any&nbsp;OpenAI-compatible&nbsp;API<br />#&nbsp;OPENAI_BASE_URL=https://example.com/v1<br />#&nbsp;OPENAI_API_KEY=your_api_key_here<br /><br />##&nbsp;===&nbsp;Proxy&nbsp;===<br />#&nbsp;PROXY_SERVER&nbsp;can&nbsp;be&nbsp;a&nbsp;full&nbsp;URL&nbsp;(e.g.&nbsp;http://0.1.2.3:1234)&nbsp;or&nbsp;just&nbsp;an&nbsp;IP&nbsp;and&nbsp;port&nbsp;combo&nbsp;(e.g.&nbsp;0.1.2.3:1234)<br />#&nbsp;Do&nbsp;not&nbsp;uncomment&nbsp;PROXY_USERNAME&nbsp;and&nbsp;PROXY_PASSWORD&nbsp;if&nbsp;your&nbsp;proxy&nbsp;is&nbsp;unauthenticated<br />#&nbsp;PROXY_SERVER=<br />#&nbsp;PROXY_USERNAME=<br />#&nbsp;PROXY_PASSWORD=<br /><br />##&nbsp;===&nbsp;/search&nbsp;API&nbsp;===<br />#&nbsp;By&nbsp;default,&nbsp;the&nbsp;/search&nbsp;API&nbsp;will&nbsp;use&nbsp;Google&nbsp;search.<br /><br />#&nbsp;You&nbsp;can&nbsp;specify&nbsp;a&nbsp;SearXNG&nbsp;server&nbsp;with&nbsp;the&nbsp;JSON&nbsp;format&nbsp;enabled,&nbsp;if&nbsp;you'd&nbsp;like&nbsp;to&nbsp;use&nbsp;that&nbsp;instead&nbsp;of&nbsp;direct&nbsp;Google.<br />#&nbsp;You&nbsp;can&nbsp;also&nbsp;customize&nbsp;the&nbsp;engines&nbsp;and&nbsp;categories&nbsp;parameters,&nbsp;but&nbsp;the&nbsp;defaults&nbsp;should&nbsp;also&nbsp;work&nbsp;just&nbsp;fine.<br />#&nbsp;SEARXNG_ENDPOINT=http://your.searxng.server<br />#&nbsp;SEARXNG_ENGINES=<br />#&nbsp;SEARXNG_CATEGORIES=<br /><br />##&nbsp;===&nbsp;PostgreSQL&nbsp;Database&nbsp;Configuration&nbsp;===<br />#&nbsp;Configure&nbsp;PostgreSQL&nbsp;credentials.&nbsp;These&nbsp;should&nbsp;match&nbsp;the&nbsp;credentials&nbsp;used&nbsp;by&nbsp;the&nbsp;nuq-postgres&nbsp;container.<br />#&nbsp;If&nbsp;you&nbsp;change&nbsp;these,&nbsp;ensure&nbsp;all&nbsp;three&nbsp;are&nbsp;set&nbsp;consistently.<br />#&nbsp;Note:&nbsp;nuq-postgres&nbsp;requires&nbsp;using&nbsp;'postgres'&nbsp;as&nbsp;the&nbsp;database&nbsp;name&nbsp;for&nbsp;proper&nbsp;pg_cron&nbsp;initialization<br />POSTGRES_USER=postgres<br />POSTGRES_PASSWORD=postgres<br />POSTGRES_DB=postgres<br /><br />##&nbsp;===&nbsp;Redis&nbsp;Configuration&nbsp;===<br />#&nbsp;These&nbsp;are&nbsp;auto-configured&nbsp;by&nbsp;docker-compose.yaml.&nbsp;You&nbsp;shouldn't&nbsp;need&nbsp;to&nbsp;change&nbsp;them.<br />#&nbsp;REDIS_URL=redis://redis:6379<br />#&nbsp;REDIS_RATE_LIMIT_URL=redis://redis:6379<br /><br />##&nbsp;===&nbsp;Playwright&nbsp;Service&nbsp;===<br />#&nbsp;This&nbsp;is&nbsp;auto-configured&nbsp;by&nbsp;docker-compose.yaml.&nbsp;You&nbsp;shouldn't&nbsp;need&nbsp;to&nbsp;change&nbsp;it.<br />#&nbsp;PLAYWRIGHT_MICROSERVICE_URL=http://playwright-service:3000/scrape<br /><br />##&nbsp;===&nbsp;Supabase&nbsp;Setup&nbsp;(used&nbsp;to&nbsp;support&nbsp;DB&nbsp;authentication,&nbsp;advanced&nbsp;logging,&nbsp;etc.)&nbsp;===<br />#&nbsp;SUPABASE_ANON_TOKEN=<br />#&nbsp;SUPABASE_URL=<br />#&nbsp;SUPABASE_SERVICE_TOKEN=<br /><br />#&nbsp;Use&nbsp;if&nbsp;you've&nbsp;set&nbsp;up&nbsp;authentication&nbsp;and&nbsp;want&nbsp;to&nbsp;test&nbsp;with&nbsp;a&nbsp;real&nbsp;API&nbsp;key<br />#&nbsp;TEST_API_KEY=<br /><br />#&nbsp;This&nbsp;key&nbsp;lets&nbsp;you&nbsp;access&nbsp;the&nbsp;queue&nbsp;admin&nbsp;panel.&nbsp;Change&nbsp;this&nbsp;if&nbsp;your&nbsp;deployment&nbsp;is&nbsp;publicly&nbsp;accessible.<br />BULL_AUTH_KEY=CHANGEME<br /><br />##&nbsp;===&nbsp;PDF&nbsp;Parsing&nbsp;===<br />#&nbsp;Set&nbsp;if&nbsp;you&nbsp;have&nbsp;a&nbsp;llamaparse&nbsp;key&nbsp;you'd&nbsp;like&nbsp;to&nbsp;use&nbsp;to&nbsp;parse&nbsp;pdfs<br />#&nbsp;LLAMAPARSE_API_KEY=<br /><br />##&nbsp;===&nbsp;Monitoring&nbsp;===<br />#&nbsp;Set&nbsp;if&nbsp;you'd&nbsp;like&nbsp;to&nbsp;send&nbsp;server&nbsp;health&nbsp;status&nbsp;messages&nbsp;to&nbsp;Slack<br />#&nbsp;SLACK_WEBHOOK_URL=<br /><br />#&nbsp;Set&nbsp;if&nbsp;you'd&nbsp;like&nbsp;to&nbsp;send&nbsp;posthog&nbsp;events&nbsp;like&nbsp;job&nbsp;logs<br />#&nbsp;POSTHOG_API_KEY=<br />#&nbsp;POSTHOG_HOST=<br /><br />##&nbsp;===&nbsp;System&nbsp;Resource&nbsp;Configuration&nbsp;===<br />#&nbsp;Maximum&nbsp;CPU&nbsp;usage&nbsp;threshold&nbsp;(0.0-1.0).&nbsp;Worker&nbsp;will&nbsp;reject&nbsp;new&nbsp;jobs&nbsp;when&nbsp;CPU&nbsp;usage&nbsp;exceeds&nbsp;this&nbsp;value.<br />#&nbsp;Default:&nbsp;0.8&nbsp;(80%)<br />MAX_CPU=0.8<br /><br />#&nbsp;Maximum&nbsp;RAM&nbsp;usage&nbsp;threshold&nbsp;(0.0-1.0).&nbsp;Worker&nbsp;will&nbsp;reject&nbsp;new&nbsp;jobs&nbsp;when&nbsp;memory&nbsp;usage&nbsp;exceeds&nbsp;this&nbsp;value.<br />#&nbsp;Default:&nbsp;0.8&nbsp;(80%)<br />MAX_RAM=0.8<br /><br />#&nbsp;Number&nbsp;of&nbsp;workers&nbsp;per&nbsp;queue<br />NUM_WORKERS_PER_QUEUE=8<br /><br />#&nbsp;Concurrent&nbsp;requests&nbsp;for&nbsp;crawling<br />CRAWL_CONCURRENT_REQUESTS=10<br /><br />#&nbsp;Maximum&nbsp;concurrent&nbsp;jobs<br />MAX_CONCURRENT_JOBS=5<br /><br />#&nbsp;Browser&nbsp;pool&nbsp;size<br />BROWSER_POOL_SIZE=5<br /><br />#&nbsp;Set&nbsp;if&nbsp;you'd&nbsp;like&nbsp;to&nbsp;allow&nbsp;local&nbsp;webhooks&nbsp;to&nbsp;be&nbsp;sent&nbsp;to&nbsp;your&nbsp;self-hosted&nbsp;instance<br />#&nbsp;ALLOW_LOCAL_WEBHOOKS=true<br /><br />#&nbsp;Block&nbsp;media&nbsp;in&nbsp;Playwright<br />#&nbsp;BLOCK_MEDIA=true<br /><br />#&nbsp;Logging&nbsp;level&nbsp;(DEBUG,&nbsp;INFO,&nbsp;WARN,&nbsp;ERROR)<br />LOGGING_LEVEL=INFO</div><br /><br /><br /><img src ="http://www.blogjava.net/paulwong/aggbug/451774.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/paulwong/" target="_blank">paulwong</a> 2026-04-15 11:03 <a href="http://www.blogjava.net/paulwong/archive/2026/04/15/451774.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>现代IM系统中聊天消息的同步和存储方案探讨</title><link>http://www.blogjava.net/jb2011/archive/2026/04/14/451773.html</link><dc:creator>Jack Jiang</dc:creator><author>Jack Jiang</author><pubDate>Tue, 14 Apr 2026 03:39:00 GMT</pubDate><guid>http://www.blogjava.net/jb2011/archive/2026/04/14/451773.html</guid><wfw:comment>http://www.blogjava.net/jb2011/comments/451773.html</wfw:comment><comments>http://www.blogjava.net/jb2011/archive/2026/04/14/451773.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/jb2011/comments/commentRss/451773.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/jb2011/services/trackbacks/451773.html</trackback:ping><description><![CDATA[<p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">本文作者阿里云高级技术专家木洛，有优化和修订。</p><h1>1、前言</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">IM全称是&#8220;Instant Messaging&#8221;，中文名是即时通讯。在这个高度信息化的移动互联网时代，生活中IM类产品已经成为必备品，比较有名的如钉钉、微信、QQ等以IM为核心功能的产品。当然目前微信已经成长为一个生态型产品，但其核心功能还是IM。还有一些非以IM系统为核心的应用，最典型的如一些在线游戏、社交应用，IM也是其重要的功能模块。可以说，带有社交属性的应用，IM功能一定是必不可少的。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">IM系统在互联网初期即存在，其基础技术架构在这十几年的发展中更新迭代多次，从早期的CS、P2P架构，到现在后台已经演变为一个复杂的分布式系统，涉及移动端、网络、安全和存储等技术的方方面面。其支撑的规模也从早期的少量日活，到现在微信这个巨头最新公布的达到9亿的日活的体量。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>IM系统中最核心的是消息系统，消息系统最核心的是消息的同步和存储：</strong></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>1）</em>消息的同步：</strong>将消息完整的、快速的从发送方传递到接收方，就是消息的同步。消息同步系统最重要的衡量指标就是消息传递的实时性、完整性以及能支撑的消息规模。从功能上来说，一般至少要支持在线和离线推送，高级的IM系统还支持&#8220;多端同步&#8221;；</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>2）</em>消息的存储：</strong>消息存储即消息的持久化保存，这里不是指消息在客户端本地的保存，而是指云端的保存，功能上对应的就是&#8220;消息漫游&#8221;。&#8220;消息漫游&#8221;的好处是可以实现账号在任意端登陆查看所有历史消息，这也是高级IM系统特有的功能之一。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>本文内容主要涉及IM系统中的消息系统架构，探讨一种适用于大用户量的消息同步以及存储系统的架构实现，能够支持消息系统中的高级特性&#8220;多端同步&#8221;以及&#8220;消息漫游&#8221;。在性能和规模上，能够做到全量消息云端存储，百万TPS以及毫秒级延迟的消息同步能力。</strong></p><h1>2、架构设计</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">本章主要会介绍基于TableStore的现代IM消息系统的架构设计，在详细介绍架构设计之前，会先介绍一种Timeline逻辑模型，来抽象和简化对IM消息同步和存储模型的理解。理解了Timeline模型后，会介绍如何基于此模型对消息的同步以及存储进行建模。基于Timeline模型，在实现消息同步和存储时还会有各方面的技术权衡，例如如何对消息同步常见的读扩散和写扩散两种模型进行对比和选择，以及针对Timeline模型的特征如何来选择底层数据库。</p><div img-uploading-status=""  image-package-1"="" data-index="1" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="1" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181023972-940776420.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181023972-940776420.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;"><span style="color: #888888;">&nbsp;&#9650; 上图是消息系统传统架构与现代架构的简单对比</span></p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>传统架构下，消息是先同步后存储：</strong></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">对于在线的用户，消息会直接实时同步到在线的接收方，消息同步成功后，并不会进行持久化。而对于离线的用户或者消息无法实时同步成功时，消息会持久化到离线库，当接收方重新连接后，会从离线库拉取所有未读消息。当离线库中的消息成功同步到接收方后，消息会从离线库中删除。传统的消息系统，服务端的主要工作是维护发送方和接收方的连接状态，并提供在线消息同步和离线消息缓存的能力，保证消息一定能够从发送方传递到接收方。服务端不会对消息进行持久化，所以也无法支持消息漫游。</p></blockquote><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>现代架构下，消息是先存储后同步：</strong></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">先存储后同步的好处是，如果接收方确认接收到了消息，那这条消息一定是已经在云端保存了。并且消息会有两个库来保存，一个是消息存储库，用于全量保存所有会话的消息，主要用于支持消息漫游。另一个是消息同步库，主要用于接收方的多端同步。</p><p style="margin-top: 10px; margin-bottom: 10px;">消息从发送方发出后，经过服务端转发，服务端会先将消息保存到消息存储库，后保存到消息同步库。完成消息的持久化保存后，对于在线的接收方，会直接选择在线推送。但在线推送并不是一个必须路径，只是一个更优的消息传递路径。</p><p style="margin-top: 10px; margin-bottom: 10px;">对于在线推送失败或者离线的接收方，会有另外一个统一的消息同步方式。接收方会主动的向服务端拉取所有未同步消息，但接收方何时来同步以及会在哪些端来同步消息对服务端来说是未知的，所以要求服务端必须保存所有需要同步到接收方的消息，这是消息同步库的主要作用。对于新的同步设备，会有消息漫游的需求，这是消息存储库的主要作用，在消息存储库中，可以拉取任意会话的全量历史消息。</p></blockquote><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">以上是传统架构和现代架构的一个简单的对比，现代架构上整个消息的同步和存储流程，并没有变复杂太多，但是其能实现多端同步以及消息漫游。现代架构中最核心的就是两个消息库&#8220;消息同步库&#8221;和&#8220;消息存储库&#8221;，是消息同步和存储最核心的基础。而本篇文章接下来的部分，都是围绕这两个库的设计和实现来展开。</p><h1>3、Timeline模型</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">在分析&#8220;消息同步库&#8221;和&#8220;消息存储库&#8221;的设计和实现之前，在本章会先介绍一个逻辑模型-Timeline。Timeline模型会帮助我们简化对消息同步和存储模型的理解，而消息库的设计和实现也是围绕Timeline的特性和需求来展开。</p><div img-uploading-status=""  image-package-2"="" data-index="2" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="2" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181031449-115397958.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181031449-115397958.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;"><span style="color: #888888;">&#9650; Timeline模型</span></p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>如图是Timeline模型的一个抽象表述，Timeline可以简单理解为是一个消息队列，但这个消息队列有如下特性：</strong></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>1）</em></strong>每个消息拥有一个顺序ID（SeqId），在队列后面的消息的SeqId一定比前面的消息的SeqId大，也就是保证SeqId一定是增长的，但是不要求严格递增；</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>2）</em></strong>新的消息永远在尾部添加，保证新的消息的SeqId永远比已经存在队列中的消息都大；</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>3）</em></strong>可根据SeqId随机定位到具体的某条消息进行读取，也可以任意读取某个给定范围内的所有消息。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">有了这些特性后，消息的同步可以拿Timeline来很简单的实现。图中的例子中，消息发送方是A，消息接收方是B，同时B存在多个接收端，分别是B1、B2和B3。A向B发送消息，消息需要同步到B的多个端，待同步的消息通过一个Timeline来进行交换。A向B发送的所有消息，都会保存在这个Timeline中，B的每个接收端都是独立的从这个Timeline中拉取消息。每个接收端同步完毕后，都会在本地记录下最新同步到的消息的SeqId，即最新的一个位点，作为下次消息同步的起始位点。服务端不会保存各个端的同步状态，各个端均可以在任意时间从任意点开始拉取消息。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">消息漫游也是基于Timeline，和消息同步唯一的区别是，消息漫游要求服务端能够对Timeline内的所有数据进行持久化。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">基于Timeline，从逻辑模型上能够很简单的理解在服务端如何去实现消息同步和存储，并支持多端同步和消息漫游这些高级功能。落地到实现的难点主要在如何将逻辑模型映射到物理模型，Timeline的实现对数据库会有哪些要求？我们应该选择何种数据库去实现？这些是接下来会讨论到的问题。</p><h1>4、消息存储模型</h1><div img-uploading-status=""  image-package-3"="" data-index="3" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="3" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181037019-819894174.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181037019-819894174.png"  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;"><span style="color: #888888;">&#9650; 基于Timeline的消息存储模型</span></p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">如图是基于Timeline的消息存储模型，消息存储要求每个会话都对应一个独立的Timeline。如图例子所示，A与B/C/D/E/F均发生了会话，每个会话对应一个独立的Timeline，每个Timeline内存有这个会话中的所有消息，服务端会对每个Timeline进行持久化。服务端能够对所有会话Timeline中的全量消息进行持久化，也就拥有了消息漫游的能力。</p><h1>5、消息同步模型</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">消息同步模型会比消息存储模型稍复杂一些，消息的同步一般有读扩散和写扩散两种不同的方式，分别对应不同的Timeline物理模型。</p><div img-uploading-status=""  image-package-4"="" data-index="4" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="4" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181044257-470653877.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181044257-470653877.png"  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;"><span style="color: #888888;">&#9650; 读扩散和写扩散两种不同同步模式下对应的不同的Timeline模型</span></p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">如图是读扩散和写扩散两种不同同步模式下对应的不同的Timeline模型，按图中的示例，A作为消息接收者，其与B/C/D/E/F发生了会话，每个会话中的新的消息都需要同步到A的某个端，看下读扩散和写扩散两种模式下消息如何做同步。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>读扩散：</strong></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">消息存储模型中，每个会话的Timeline中保存了这个会话的全量消息。读扩散的消息同步模式下，每个会话中产生的新的消息，只需要写一次到其用于存储的Timeline中，接收端从这个Timeline中拉取新的消息。</p><p style="margin-top: 10px; margin-bottom: 10px;">优点是消息只需要写一次，相比写扩散的模式，能够大大降低消息写入次数，特别是在群消息这种场景下。但其缺点也比较明显，接收端去同步消息的逻辑会相对复杂和低效。接收端需要对每个会话都拉取一次才能获取全部消息，读被大大的放大，并且会产生很多无效的读，因为并不是每个会话都会有新消息产生。</p></blockquote><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>写扩散：</strong></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">写扩散的消息同步模式，需要有一个额外的Timeline来专门用于消息同步，通常是每个接收端都会拥有一个独立的同步Timeline，用于存放需要向这个接收端同步的所有消息。</p><p style="margin-top: 10px; margin-bottom: 10px;">每个会话中的消息，会产生多次写，除了写入用于消息存储的会话Timeline，还需要写入需要同步到的接收端的同步Timeline。在个人与个人的会话中，消息会被额外写两次，除了写入这个会话的存储Timeline，还需要写入参与这个会话的两个接收者的同步Timeline。而在群这个场景下，写入会被更加的放大，如果这个群拥有N个参与者，那每条消息都需要额外的写N次。</p><p style="margin-top: 10px; margin-bottom: 10px;">写扩散同步模式的优点是，在接收端消息同步逻辑会非常简单，只需要从其同步Timeline中读取一次即可，大大降低了消息同步所需的读的压力。其缺点就是消息写入会被放大，特别是针对群这种场景。</p></blockquote><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>在IM这种应用场景下，通常会选择写扩散这种消息同步模式。</strong></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">IM场景下，一条消息只会产生一次，但是会被读取多次，是典型的读多写少的场景，消息的读写比例大概是10:1。若使用读扩散同步模式，整个系统的读写比例会被放大到100:1。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">一个优化的好的系统，必须从设计上去平衡这种读写压力，避免读或写任意一维触碰到天花板。所以IM系统这类场景下，通常会应用写扩散这种同步模式，来平衡读和写，将100:1的读写比例平衡到30:30。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">当然写扩散这种同步模式，还需要处理一些极端场景，例如万人大群。针对这种极端写扩散的场景，会退化到使用读扩散。一个简单的IM系统，通常会在产品层面限制这种大群的存在，<strong>而对于一个高级的IM系统，会采用读写扩散混合的同步模式，来满足这类产品的需求。</strong>采用混合模式，会根据数据的不同类型和不同的读写负载，来决定用写扩散还是读扩散。</p><h1>6、典型架构设计</h1><div img-uploading-status=""  image-package-5"="" data-index="5" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="8" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202511/1834368-20251119161427966-1874426070.jpg" src="https://img2024.cnblogs.com/blog/1834368/202511/1834368-20251119161427966-1874426070.jpg"  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;">如上图所示，是一个典型的消息系统架构。</p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>该典型的消息系统架构中包含几个重要组件：</strong></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><em>1）</em>端：作为消息的发送和接收端，通过连接消息服务器来发送和接收消息。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><em>2）</em>消息服务器：一组无状态的服务器，可水平扩展，处理消息的发送和接收请求，连接后端消息系统。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><em>3）</em>消息队列：新写入消息的缓冲队列，消息系统的前置消息存储，用于削峰填谷以及异步消费。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><em>4）</em>消息处理：一组无状态的消费处理服务器，用于异步消费消息队列中的消息数据，处理消息的持久化和写扩散同步。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><em>5）</em>消息存储和索引库：持久化存储消息，每个会话对应一个 Timeline 进行消息存储，存储的消息建立索引来实现消息检索。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><em>6）</em>消息同步库：</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">写扩散形式同步消息，每个用户的收件箱对应一个 Timeline，同步库内消息不需要永久保存，通常对消息设定一个生命周期。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">新消息会由端发出，通常消息体中会携带消息 ID（用于去重）、逻辑时间戳（用于排序）、消息类型（控制消息、图片消息或者文本消息等）、消息体等内容。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">消息会先写入消息队列，作为底层存储的一个临时缓冲区。消息队列中的消息会由消息处理服务器消费，可以允许乱序消费。消息处理服务器对消息先存储后同步，先写入发件箱 Timeline（存储库），后写扩散至各个接收端的收件箱（同步库）。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">消息数据写入存储库后，会被近实时的构建索引，索引包括文本消息的全文索引以及多字段索引（发送方、消息类型等）。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">对于在线的设备，可以由消息服务器主动推送至在线设备端。对于离线设备，登录后会主动向服务端同步消息。每个设备会在本地保留有最新一条消息的顺序 ID，向服务端同步该顺序 ID 后的所有消息。</p><h1>7、消息库设计</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">基于Timeline模型，以及Timeline模型在消息存储和消息同步的应用，我们看下消息同步库和消息存储库的设计。</p><div img-uploading-status=""  image-package-6"="" data-index="6" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="6" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181057300-191979039.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181057300-191979039.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div><div><span style="color: #888888;">&#9650; 基于Timeline的消息库设计</span></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>消息同步库：</strong></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">消息同步库用于存储所有用于消息同步的Timeline，每个Timeline对应一个接收端，主要用作写扩散模式的消息同步。</p><p style="margin-top: 10px; margin-bottom: 10px;">这个库不需要永久保留所有需要同步的消息，因为消息在同步到所有端后其生命周期就可以结束，就可以被回收。但是如前面所介绍的，一个实现简单的多端同步消息系统，在服务端不会保存有所有端的同步状态，而是依赖端自己主动来做同步。</p><p style="margin-top: 10px; margin-bottom: 10px;">所以服务端不知道消息何时可以回收，通常的做法是为这个库里的消息设定一个固定的生命周期，例如一周或者一个月，生命周期结束可被淘汰。</p></blockquote><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>消息存储库：</strong></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">消息存储库用于存储所有会话的Timeline，每个Timeline包含了一个会话中的所有消息。这个库主要用于消息漫游时拉取某个会话的所有历史消息，也用于读扩散模式的消息同步。</p><p style="margin-top: 10px; margin-bottom: 10px;">消息同步库和消息存储库，对数据库有不同的要求，如何对数据库做选型，在下面会讨论。</p></blockquote><h1>8、数据库选型</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>消息系统最核心的两个库是消息同步库和消息存储库，两个库对数据库有不同的要求：</strong></p><div img-uploading-status=""  image-package-7"="" data-index="7" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="7" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181102987-1731984220.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260413181102987-1731984220.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;"><strong>总结下来，对数据库的要求有如下几点：</strong></p></div></div></div><ul style="margin-left: 2.5rem; padding-left: 0px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><li style="list-style: inherit;"><em>1）</em>表结构设计能够满足Timeline模型的功能要求：不要求关系模型，能够实现队列模型，并能够支持生成自增的SeqId；</li><li style="list-style: inherit;"><em>2）</em>能够支持高并发写和范围读，规模在十万级TPS；</li><li style="list-style: inherit;"><em>3）</em>能够保存海量数据，百TB级；</li><li style="list-style: inherit;"><em>4）</em>能够为数据定义生命周期。</li></ul><h1>9、本文小结</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">本文主要介绍了现代IM系统中消息推送和存储架构的实现，基于逻辑的Timeline模型，我们可以很清晰明了的理解整个消息推送和存储的架构。而基于Timeline的消息存储和推送模型，其实不光可以应用在IM消息系统中，还可应用在例如Feeds流、实时消息同步、直播弹幕等场景。</p><h1>10、参考资料</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[1]&nbsp;<a href="http://www.52im.net/thread-307-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">浅谈IM系统的架构设计</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[2]&nbsp;<a href="http://www.52im.net/thread-289-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">简述移动端IM开发的那些坑：架构设计、通信协议和客户端</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[3]&nbsp;<a href="http://www.52im.net/thread-812-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一套海量在线用户的移动端IM架构设计实践分享(含详细图文)</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[4]&nbsp;<a href="http://www.52im.net/thread-151-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一套原创分布式即时通讯(IM)系统理论架构方案</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[5]&nbsp;<a href="http://www.52im.net/thread-152-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">从零到卓越：京东客服即时通讯系统的技术架构演进历程</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[6]&nbsp;<a href="http://www.52im.net/thread-31-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">蘑菇街即时通讯/IM服务器开发之架构选择</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[7]&nbsp;<a href="http://www.52im.net/thread-158-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">腾讯QQ1.4亿在线用户的技术挑战和架构演进之路PPT</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[8]&nbsp;<a href="http://www.52im.net/thread-1221-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">移动端IM中大规模群消息的推送如何保证效率、实时性？</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[9]&nbsp;<a href="http://www.52im.net/thread-1961-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">子弹短信光鲜的背后：网易云信首席架构师分享亿级IM平台的技术实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[10]&nbsp;<a href="http://www.52im.net/thread-1998-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">微信技术分享：微信的海量IM聊天消息序列号生成实践（算法原理篇）</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[11]&nbsp;<a href="http://www.52im.net/thread-2015-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一套高可用、易伸缩、高并发的IM群聊、单聊架构方案设计实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[12]&nbsp;<a href="http://www.52im.net/thread-2202-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">社交软件红包技术解密(一)：全面解密QQ红包技术方案&#8212;&#8212;架构、技术实现等</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[13]&nbsp;<a href="http://www.52im.net/thread-2519-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">社交软件红包技术解密(二)：解密微信摇一摇红包从0到1的技术演进</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[14]&nbsp;<a href="http://www.52im.net/thread-2675-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">从游击队到正规军(一)：马蜂窝旅游网的IM系统架构演进之路</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[15]&nbsp;<a href="http://www.52im.net/thread-2807-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">瓜子IM智能客服系统的数据架构设计（整理自现场演讲，有配套PPT）</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[16]&nbsp;<a href="http://www.52im.net/thread-2848-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">阿里钉钉技术分享：企业级IM王者&#8212;&#8212;钉钉在后端架构上的过人之处</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[17]&nbsp;<a href="http://www.52im.net/thread-3742-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">IM开发基础知识补课(十)：大型IM系统有多难？万字长文，搞懂异地多活！</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[18]&nbsp;<a href="http://www.52im.net/thread-3252-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">阿里技术分享：电商IM消息平台，在群聊、直播场景下的技术实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[19]&nbsp;<a href="http://www.52im.net/thread-3393-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一套亿级用户的IM架构技术干货(上篇)：整体架构、服务拆分等</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[20]&nbsp;<a href="http://www.52im.net/thread-3472-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">从新手到专家：如何设计一套亿级消息量的分布式IM系统</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[21]&nbsp;<a href="http://www.52im.net/thread-3631-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">企业微信的IM架构设计揭秘：消息模型、万人群、已读回执、消息撤回等</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[22]&nbsp;<a href="http://www.52im.net/thread-3638-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">融云技术分享：全面揭秘亿级IM消息的可靠投递机制</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[23]&nbsp;<a href="http://www.52im.net/thread-3675-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">IM开发技术学习：揭秘微信朋友圈这种信息推流背后的系统设计</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[24]&nbsp;<a href="http://www.52im.net/thread-3699-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">阿里IM技术分享(三)：闲鱼亿级IM消息系统的架构演进之路</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[25]&nbsp;<a href="http://www.52im.net/thread-3752-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">基于实践：一套百万消息量小规模IM系统技术要点总结</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[26]&nbsp;<a href="http://www.52im.net/thread-3816-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">跟着源码学IM(十)：基于Netty，搭建高性能IM集群（含技术思路+源码）</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[27]&nbsp;<a href="http://www.52im.net/thread-3954-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一套十万级TPS的IM综合消息系统的架构实践与思考</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[28]&nbsp;<a href="http://www.52im.net/thread-3994-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">直播系统聊天技术(八)：vivo直播系统中IM消息模块的架构实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[29]&nbsp;<a href="http://www.52im.net/thread-4153-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">得物从0到1自研客服IM系统的技术实践之路</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[30]&nbsp;<a href="http://www.52im.net/thread-4404-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">海量用户IM聊天室的架构设计与实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[31]&nbsp;<a href="http://www.52im.net/thread-4437-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">企业微信针对百万级组织架构的客户端性能优化实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[32]&nbsp;<a href="http://www.52im.net/thread-4564-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一套分布式IM即时通讯系统的技术选型和架构设计</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[33]&nbsp;<a href="http://www.52im.net/thread-4627-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">陌陌技术分享：陌陌IM在后端KV缓存架构上的技术实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[34]&nbsp;<a href="http://www.52im.net/thread-4636-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">微信团队分享：来看看微信十年前的IM消息收发架构，你做到了吗</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[35]&nbsp;<a href="http://www.52im.net/thread-4690-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">携程技术分享：亿级流量的办公IM及开放平台技术实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[36]&nbsp;<a href="http://www.52im.net/thread-4764-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">转转平台IM系统架构设计与实践(一)：整体架构设计</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[37]&nbsp;<a href="http://www.52im.net/thread-4789-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">支持百万人超大群聊的Web端IM架构设计与实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[38]&nbsp;<a href="http://www.52im.net/thread-4812-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一年撸完百万行代码，企业微信的全新鸿蒙NEXT客户端架构演进之路</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[39]&nbsp;<a href="http://www.52im.net/thread-4874-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">转转客服IM聊天系统背后的技术挑战和实践分享</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[40]&nbsp;<a href="http://www.52im.net/thread-4886-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">B站IM消息系统的新架构升级实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[41]&nbsp;<a href="http://www.52im.net/thread-4887-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">如何保障分布式IM聊天系统的消息有序性（即消息不乱）</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[42]&nbsp;<a href="http://www.52im.net/thread-464-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">新手入门一篇就够：从零开发移动端IM</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[43]&nbsp;<a href="http://www.52im.net/thread-1587-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">移动端IM开发者必读(一)：通俗易懂，理解移动网络的&#8220;弱&#8221;和&#8220;慢&#8221;</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[44]&nbsp;<a href="http://www.52im.net/thread-3065-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">零基础IM开发入门(一)：什么是IM聊天系统？</a></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;"><strong>即时通讯技术学习：</strong></p><p style="margin-top: 10px; margin-bottom: 10px;">- 移动端IM开发入门文章：《<a href="http://www.52im.net/thread-464-1-1.html" rel="noopener nofollow" target="_blank" style="color: #1d58d1; text-decoration-line: none;">新手入门一篇就够：从零开发移动端IM</a>》</p><p style="margin-top: 10px; margin-bottom: 10px;">- 开源IM框架源码：<a href="https://github.com/JackJiang2011/MobileIMSDK" rel="noopener nofollow" target="_blank" style="color: #1d58d1; text-decoration-line: none;">https://github.com/JackJiang2011/MobileIMSDK</a>（<a href="https://gitee.com/jackjiang/MobileIMSDK" rel="noopener nofollow" target="_blank" style="color: #1d58d1; text-decoration-line: none;">备用地址点此</a>）</p></blockquote><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">（<strong>本文内容引用自：</strong><a href="http://www.52im.net/thread-1230-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">http://www.52im.net/thread-1230-1-1.html</a>）</p><img src ="http://www.blogjava.net/jb2011/aggbug/451773.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/jb2011/" target="_blank">Jack Jiang</a> 2026-04-14 11:39 <a href="http://www.blogjava.net/jb2011/archive/2026/04/14/451773.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Karpathy's LLM-Wiki pattern 知识库资源</title><link>http://www.blogjava.net/paulwong/archive/2026/04/12/451771.html</link><dc:creator>paulwong</dc:creator><author>paulwong</author><pubDate>Sun, 12 Apr 2026 09:32:00 GMT</pubDate><guid>http://www.blogjava.net/paulwong/archive/2026/04/12/451771.html</guid><wfw:comment>http://www.blogjava.net/paulwong/comments/451771.html</wfw:comment><comments>http://www.blogjava.net/paulwong/archive/2026/04/12/451771.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/paulwong/comments/commentRss/451771.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/paulwong/services/trackbacks/451771.html</trackback:ping><description><![CDATA[<div>小龙虾直接安装可用</div>
<div><a href="https://skillhub.cn/skills/llm-wiki" target="_blank">https://skillhub.cn/skills/llm-wiki</a><br />
</div>
<div><br />
</div>
<div>clawhub上的</div>
<div><a href="https://clawhub.ai/john-ver/karpathy-llm-wiki" target="_blank">https://clawhub.ai/john-ver/karpathy-llm-wiki</a><br />
</div>
<div><br />
深加工成知识图谱的graphify</div>
<div><a href="https://github.com/safishamsi/graphify/blob/v4/README.zh-CN.md" target="_blank">https://github.com/safishamsi/graphify/blob/v4/README.zh-CN.md</a><br />
</div>
<div><br />
</div>
<div>微信公众号文章拉取技能</div>
<div><a href="https://skillhub.cn/skills/wechat-article-spider" target="_blank">https://skillhub.cn/skills/wechat-article-spider</a><br />
</div>
<div><br />
</div>
<div>将html转成markdown的技能</div>
<div><a href="https://skillhub.cn/skills/markdown-converter" target="_blank">https://skillhub.cn/skills/markdown-converter</a><br />
</div>
<div><br />
</div>
<div><br />
</div>
<img src ="http://www.blogjava.net/paulwong/aggbug/451771.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/paulwong/" target="_blank">paulwong</a> 2026-04-12 17:32 <a href="http://www.blogjava.net/paulwong/archive/2026/04/12/451771.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>playwright-cli 案例</title><link>http://www.blogjava.net/paulwong/archive/2026/04/12/451769.html</link><dc:creator>paulwong</dc:creator><author>paulwong</author><pubDate>Sun, 12 Apr 2026 02:24:00 GMT</pubDate><guid>http://www.blogjava.net/paulwong/archive/2026/04/12/451769.html</guid><wfw:comment>http://www.blogjava.net/paulwong/comments/451769.html</wfw:comment><comments>http://www.blogjava.net/paulwong/archive/2026/04/12/451769.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/paulwong/comments/commentRss/451769.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/paulwong/services/trackbacks/451769.html</trackback:ping><description><![CDATA[<h1>环境</h1>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->hiclaw&nbsp;docker<br />
cat&nbsp;/etc/os-release&nbsp;<br />
PRETTY_NAME="Ubuntu&nbsp;22.04.5&nbsp;LTS"<br />
NAME="Ubuntu"<br />
VERSION_ID="22.04"<br />
VERSION="22.04.5&nbsp;LTS&nbsp;(Jammy&nbsp;Jellyfish)"<br />
VERSION_CODENAME=jammy<br />
ID=ubuntu<br />
ID_LIKE=debian<br />
HOME_URL="https://www.ubuntu.com/"<br />
SUPPORT_URL="https://help.ubuntu.com/"<br />
BUG_REPORT_URL="https://bugs.launchpad.net/ubuntu/"<br />
PRIVACY_POLICY_URL="https://www.ubuntu.com/legal/terms-and-policies/privacy-policy"<br />
UBUNTU_CODENAME=jammy</div>
</div>
<div><br />
</div>
<h1>安装</h1>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->npm&nbsp;install&nbsp;-g&nbsp;@playwright/cli@latest</div>
</div>
<div><br />
</div>
<h1>安装chrome</h1>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->npx&nbsp;playwright&nbsp;install&nbsp;chrome</div>
</div>
<div><br />
</div>
<h1>操作</h1>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->playwright-cli&nbsp;open&nbsp;www.cnn.com&nbsp;<br />
###&nbsp;Browser&nbsp;`default`&nbsp;opened&nbsp;with&nbsp;pid&nbsp;159651.<br />
###&nbsp;Ran&nbsp;Playwright&nbsp;code<br />
```js<br />
await&nbsp;page.goto('https://www.cnn.com')<span style="color: #008000; ">;<br />
</span>```<br />
###&nbsp;Page<br />
-&nbsp;Page&nbsp;URL:&nbsp;https://edition.cnn.com/<br />
###&nbsp;Snapshot<br />
-&nbsp;<span style="color: #800000; font-weight: bold; ">[</span><span style="color: #800000; ">Snapshot</span><span style="color: #800000; font-weight: bold; ">]</span>(.playwright-cli/page-2026-04-12T02-21-31-067Z.yml)</div>
</div>
<div><br />
</div>
<h1>安装skill</h1>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->cd&nbsp;~<br />
playwright-cli&nbsp;install&nbsp;--skills</div>
</div>
<div>
<div>默认会在当前目录下生成 .claude/skills/playwright-cli</div>
<div>得将playwright-cli搬到不同agent的skills目录下</div>
</div>
<div><br />
</div>
<h1>案例1:打开页面，输入内容</h1>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->用paywight-cLi参数--headed&nbsp;--persistent，打开grok，问问今天青岛天气怎么样?</div>
</div>
<div><br />
</div>
<h1>案例2:打开页面，需点击加载数据</h1>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->用playwrightcli&nbsp;带参数&nbsp;--headed&nbsp;--persistent&nbsp;查看https://detail.tmall.com/item.htm?&amp;xxc=taobaoSearchabbucket=4&amp;id=612098145454&amp;mi_id=0000AWGjgiGB7oSCDLfegRXMs0rDPkp34S50rNrByn86yAY&amp;ns=1&amp;skuId=5872701131539&amp;spm-a21n57.1.hoverItem.2utparam-%7B%22aplus_abtest%22%3A%2240acb849856085978c81b6cdec803550%22%70D<br />
前100条评论保存到一个csV文件里面。</div>
</div>
<div><br />
</div>
<div>让ai保存成一个skill</div>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->创建一个save_mall_comments&nbsp;skill把刚才打开网站，查看评论，并且保存评论的全过程，遇到的坑都提炼出来保存到skill里面</div>
</div>
<div><br />
</div>
<div>直接保存成一个不依赖ai的可执行脚本</div>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->你把刚才所有的playWwright&nbsp;CLI命令汇总成成一个脚本，执行脚本就能获取商品前100条评论，并且保存到一个CSV文件里面。注意每一步都有合理的延时与等待，确保任务成功。脚本写完你先测试一轮。</div>
</div>
<div><br />
</div>
<div>下次直接执行</div>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->./save_mall_comments.sh&nbsp;"https://detail.tmall.com/item.htm?id=612098145454&amp;skuId=5872701131539"&nbsp;100&nbsp;--output&nbsp;tmall_reviews_612098145454_top100.csv&nbsp;--close-browser</div>
</div>
<div><br />
</div>
<h1>案例3:web自动化测试</h1>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->阅读代码，把从注册开始的主体流程写一个中文的测试文档，只测试主流程即可。然后用playwright-cli&nbsp;open&nbsp;--headed&nbsp;--persistent&nbsp;打开网页，根据你的测试用例，完成进行测试，</div>
</div>
<div><br />
</div>
<div>还可以借助openclaw，进行定时自动化测试</div>
<div><br />
</div>
<h1>案例4:在x上发推</h1>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->playwright-cli&nbsp;https://x.com/compose/articles&nbsp;&nbsp;--headed&nbsp;--persistent&nbsp;&nbsp;打开网站，创建写一个新的文章，把&nbsp;为什么巨头都在做CLI.local.html&nbsp;的内容粘贴进去。<br />
<br />
然后找到所有的"1f4f7.svg"小icon的位置，按Backspace键删除，然后复制images文件夹里面的图片，按Ctrl+V粘贴进去。"1f4f7.svg"小icon数量跟图片数量是相等的，你要按顺序替换。复制操作你应使用操作系统的CLI命令，粘贴操作在浏览器里按Ctrl+V就行了。</div>
</div>
<div><br />
</div>
<div>整理成skill</div>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->好，非常好，你把从把文章里的图片下载到本地，开始的全流程，整理成一个skills，放到项目目录。以后我只要给你一个文章，你就能自动发布</div>
</div>
<div><br />
</div>
<div>如何使用这个skill</div>
<div>
<div style="background-color: #eeeeee; font-size: 13px; border-left-color: #cccccc; border-image: none; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all;"><!--<br />
<br />
Code highlighting produced by Actipro CodeHighlighter (freeware)<br />
http://www.CodeHighlighter.com/<br />
<br />
-->http://xxx.xxx.xxx/xxx.html&nbsp;文章路径，用&nbsp;x-article-auto-publisher自动发布</div>
</div>
<div><br />
</div>
<div><br />
</div>
<img src ="http://www.blogjava.net/paulwong/aggbug/451769.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/paulwong/" target="_blank">paulwong</a> 2026-04-12 10:24 <a href="http://www.blogjava.net/paulwong/archive/2026/04/12/451769.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>即时通讯安全篇（十六）：对称加密 vs 非对称加密？一文搞懂！</title><link>http://www.blogjava.net/jb2011/archive/2026/04/09/451768.html</link><dc:creator>Jack Jiang</dc:creator><author>Jack Jiang</author><pubDate>Thu, 09 Apr 2026 04:29:00 GMT</pubDate><guid>http://www.blogjava.net/jb2011/archive/2026/04/09/451768.html</guid><wfw:comment>http://www.blogjava.net/jb2011/comments/451768.html</wfw:comment><comments>http://www.blogjava.net/jb2011/archive/2026/04/09/451768.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/jb2011/comments/commentRss/451768.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/jb2011/services/trackbacks/451768.html</trackback:ping><description><![CDATA[<p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">本文由vivo 互联网服务器团队Deng Qian分享，有排版和内容优化。</p><h1>1、引言</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>在了解加密原理前，我们来看看这样一个故事：</strong></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">小红和小明是情侣，一天，小红给小明发短信说：&#8220;亲爱的，我银行卡上没有钱了，你给我转1万块钱吧。&#8221;有过上当受骗经历的人都知道这有可能是小偷偷了小红手提包，然后拿手机发的短信。</p><p style="margin-top: 10px; margin-bottom: 10px;">不过我们小明学过加密原理，于是他回复说：&#8220;你直接拿我的银行卡刷吧，密码加上我们第一次约会的日期就是663156。&#8221;</p><p style="margin-top: 10px; margin-bottom: 10px;">很明显，只有小明和小红知道他们第一次约会是什么时候，假设是2008年4月1号，那么小红就可以根据计算663156-200841=462315得到银行卡密码，就可以消费了。</p></blockquote><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>这就是加密的本质：</strong>将信息与密钥相加得到加密后的信息，只有知道密钥的人才能解密。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>本文将以通俗案例讲解加密本质，介绍对称加密（含 AES、迪菲&#8211;赫尔曼密钥交换）与非对称加密（RSA）原理、特点及应用，并阐释其数学基础。</strong></p><div img-uploading-status=""  image-package-1"="" data-index="1" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><img alt="cover-opti" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164625913-1412249552.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164625913-1412249552.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /></div></div><h1>2、系列文章</h1><ol style="margin-left: 2.5rem; padding-left: 0px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-216-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（一）：正确地理解和使用Android端加密算法</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-217-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（二）：探讨组合加密算法在IM中的应用</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-219-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（三）：常用加解密算法与通讯安全讲解</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-312-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（四）：实例分析Android中密钥硬编码的风险</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-642-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（五）：对称加密技术在Android平台上的应用实践</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-653-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（六）：非对称加密技术的原理与应用实践</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-2106-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（七）：用JWT技术解决IM系统Socket长连接的身份认证痛点</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-1890-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（八）：如果这样来理解HTTPS原理，一篇就够了</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-2866-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（九）：你知道，HTTPS用的是对称加密还是非对称加密？</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-3897-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（十）：为什么要用HTTPS？深入浅出，探密短连接的安全性</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-4015-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（十一）：IM聊天系统安全手段之通信连接层加密技术</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-4026-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（十二）：IM聊天系统安全手段之传输内容端到端加密技术</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-4552-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（十三）：信创必学，一文读懂什么是国密算法</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-4644-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（十四）：网络端口的安全防护技术实践</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-4781-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（十五）：详解硬编码密码的泄漏风险及其扫描原理和工具</a>》</li><li style="list-style: inherit;">《<a href="http://www.52im.net/thread-4899-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯安全篇（十六）：对称加密 vs 非对称加密？一文搞懂！</a>》（<span style="color: #ff0000;"><strong>&#9756; 本文</strong></span>）</li></ol><h1>3、什么是秘钥</h1><div img-uploading-status=""  image-package-2"="" data-index="2" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="1" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164638282-1077976364.jpg" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164638282-1077976364.jpg"  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;"><strong>既然加密需要密钥，那么密钥是什么呢？</strong></p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">密钥是作用于加密时的一串密码，通过密钥进行信息加密，传输，到达接收者和监听者，由于接收者也有密钥，所以接收者可以根据密钥进行解密。从而防止通讯信息泄露。</p><h1>4、什么是对称加密</h1><div img-uploading-status=""  image-package-3"="" data-index="3" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="2" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164644792-430788659.jpg" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164644792-430788659.jpg" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;"><strong>前言讲的故事就是一个对称式加密</strong>，小明和小红都知道第一次约会的日期。所以传统的对称式加密需要通讯双方都保存同一份密钥，通过这份密钥进行加密和解密。所以对称加密也称为单密钥加密。</p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>对称加密的优势在于加解密速度快，但是安全性较低</strong>，密钥一旦泄露，所有的加密信息都会被破解。同时密钥的传输和保密也成为难题。为了解决密钥传输的问题，出现通过密钥交换建立共享密钥的技术。具体如何建立共享密钥呢？我们往下看。</p><h1>5、对称加密之建立共享密匙</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">在小明、小红和小偷的三人世界中，由于小明是学过加密原理的，知道迪菲&#8211;赫尔曼密钥交换（Diffie-Hellman Key Exchange），所以他知道如何建立共享密钥。</p><h2>5.1 颜料混合把戏</h2><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">接下来我们看看如何通过颜料混合把戏建立共享密钥吧。</p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">假设在房间中有小明、小红和小偷三个人，每个人各自拥有相同颜色的颜料。在房间的正中间也有这些颜料。接下来，小明要和小红建立共享密钥了。</p><p style="margin-top: 10px; margin-bottom: 10px;">此时，小明对大家说：&#8220;我要用蓝色。&#8221;然后小明从自己的颜料里选择了黄色，这个黄色就是小明的私钥，小红和小偷都不知道。</p><p style="margin-top: 10px; margin-bottom: 10px;">小明将自己的私钥黄色与公钥蓝色混合后，得到了一种不能分解的颜色，我们就叫&#8220;小明-蓝色&#8221;吧（虽然大家都知道黄+蓝变绿，但是这里我们为了知道是谁的混合色，还是以名字加公钥颜色来称呼），然后小明将&#8220;小明-蓝色&#8221;公布了出来。</p><p style="margin-top: 10px; margin-bottom: 10px;">同样，小红听到了小明说用蓝色后，也选择了自己的私钥红色与公钥蓝色混合，得到了&#8220;小红-蓝色&#8221;并公布了出来。</p></blockquote><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>此时，房间中小明、小红、小偷三人都知道了几个信息：</strong></p><ul style="margin-left: 2.5rem; padding-left: 0px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><li style="list-style: inherit;"><em>1）</em>他们都用了蓝色；</li><li style="list-style: inherit;"><em>2）</em>小明公布了&#8220;小明-蓝色&#8221;（小红和小偷不知道是什么颜料与蓝色的混合）；</li><li style="list-style: inherit;"><em>3）</em>小红公布了&#8220;小红-蓝色&#8221;（小红和小偷不知道是什么颜料与蓝色的混合）。</li></ul><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>接下来，见证奇迹的时刻到了：</strong>小明拿到&#8220;小红-蓝色&#8221;与自己的私钥&#8220;黄色&#8221;混合，得到&#8220;小红-蓝色-小明&#8221;的新颜料。同样的，小红拿到&#8220;小明-蓝色&#8221;与自己的私钥&#8220;红色&#8221;混合，得到&#8220;小明-蓝色-小红&#8221;。大家发现了吗？&#8220;小红-蓝色-小明&#8221;和&#8220;小明-蓝色-小红&#8221;是一模一样的颜色。而小偷不知道小明和小红的私钥颜色，无法混合出与他们相同的颜色。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>至此，共享密钥建立起来了。</strong>在了解了共享密钥的建立过程后，我们将告别实体颜料，采用数字的方式来建立共享密钥。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>注：</strong>大家可能想到了，小偷可以根据自己的颜料与公钥&#8220;蓝色&#8221;混合，尝试得出&#8220;小明-蓝色&#8221;和&#8220;小红-蓝色&#8221;。这样的方法称之为穷举法，也就是尝试所有的可能性，进行信息破解，所以加密算法在理论上都是可以通过穷举法破解的，只不过实际上，超级计算机都需要计算万亿年才能穷举出所有可能性。</p><h2>5.2 乘法把戏</h2><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">首先，我们假设乘法如同颜料混合一样，是不能分解的，看看如何用乘法与数字建立共享密钥。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">小明公开了一个数字5，然后小明选择了一个私人数字4，然后利用乘法将两者混合起来，得到&#8220;小明-5&#8221;（20），接下来小红也选择了一个私人数字7得到&#8220;小红-5&#8221;（35），小明拿到35*4=140，小红拿到20*7=140。共享密钥建立完成。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">大家也发现了，小偷知道20,35,5这三个数字后，用除法就能算出小明和小红的私钥。所以，接下来我们将了解实际使用中的如何使用乘法把戏来防止私钥被计算出来的。</p><h1>6、对称加密之迪菲&#183;赫尔曼密钥交换算法</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">我们都知道幂运算，但是要让计算机计算就比较难了。所以，我们会用幂运算作为建立共享密钥的乘法把戏。同时，我们还要了解钟算的原理，这里的钟可以理解成我们经常看到的时钟，我们常见的时钟最大是12，如果当前是10点，过了4个小时后，就变成了下午2点。也就是<em>(10+4)mod12=2</em>。了解了钟算和幂运算后，就开始进入正题吧。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">还是小明、小红和小偷的房间，小明声明了钟为11，幂运算的底为2，接下来小明和小红分别选择了自己的私钥4和7。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>1）</em>第一步：</strong>小明混合自己的&#8220;小明-11,2&#8221;得到，小红混合自己的&#8220;小红-11,2&#8221;得到。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>2）</em>第二步：</strong>小明拿到&#8220;小红-11,2&#8221;（7）进行计算，小红拿到&#8220;小明-11,2&#8221;（5）进行计算。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>大家注意到了吗：</strong>小明和小红建立了共享密钥3，而小偷无法根据已知的11、2、5、7这几个数字计算出密钥或小明小红的私钥。有了共享密钥后，小明和小红就可以安全进行加密传输了。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>迪菲－赫尔曼密钥交换：</strong></p><div img-uploading-status=""  image-package-4"="" data-index="4" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="3" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164653497-2010761922.jpg" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164653497-2010761922.jpg" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><h1>7、 对称加密之AES加密过程</h1></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">AES&nbsp;的全称是 Advanced Encryption Standard ，是最流行的对称加密算法，其加解密速度快。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">AES支持128位，192位，256位三种长度的密钥，密钥越长安全性越高。AES加密时会把明文切分成许多小块的明文，然后对每块明文单独加密，将加密后的密文传送出去，接收方再将密文切块解密，得到明文。如下图所示。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>AES加密原理：</strong></p><div img-uploading-status=""  image-package-5"="" data-index="5" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="4" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164701309-1650213049.jpg" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164701309-1650213049.jpg" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;">上一步中小明和小红已经协商好了密钥3。接下来就可以通过对称加密进行通信了。</p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>在小明、小红和小偷的房间中，小明想把密码&#8220;462315&#8221;告诉小红，于是：</strong></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>1）</em>第一步：</strong>将密码按照一位的长度进行切分（实际中通常按128位进行切分）；就变成了&#8220;4&#8221;&#8220;6&#8221;&#8220;2&#8221;&#8220;3&#8221;&#8220;1&#8221;&#8220;5&#8221;；</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>2）</em>第二步：</strong>对每块明文通过密钥3进行加密，结果就是&#8220;795648&#8221;，然后小明告诉小红和小偷：&#8220;我的密码是795648&#8221;；</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong><em>3）</em>第三步：</strong>小红拿到密文后，对密文进行切块，对每块通过密钥3进行解密，就得到了正确的密码&#8220;462315&#8221;，而小偷由于不知道密钥，就无法解密出正确的信息。</p><h1>8、什么是非对称加密</h1><h2>8.1 概述</h2><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>在对称加密中，加密和解密使用的是同一份密钥。所以，在非对称加密中，加密和解密使用的是不同的密钥。</strong></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">非对称加密中的密钥分为公钥和私钥。公钥顾名思义就是公开的，任何人都可以通过公钥进行信息加密，但是只有用户私钥的人才能完成信息解密。非对称加密带来了一个好处，避免了对称式加密需要传输和保存同一份密钥的痛苦。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">现在最流行的非对称加密算法就是RSA加密算法，具体是怎么做的呢，我们继续往下看。</p><h2>8.2 RSA加密过程</h2><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>百科是这么解释的：</strong></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">RSA加密算法是一种非对称加密算法，在公开密钥加密和电子商业中被广泛使用。RSA是由罗纳德&#183;李维斯特（Ron Rivest）、阿迪&#183;萨莫尔（Adi Shamir）和伦纳德&#183;阿德曼（Leonard Adleman）在1977年一起提出的。当时他们三人都在麻省理工学院工作。RSA 就是他们三人姓氏开头字母拼在一起组成的。</p></blockquote><div img-uploading-status=""  image-package-6"="" data-index="6" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="5" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164708427-640238836.jpg" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164708427-640238836.jpg" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;">&#9650; RSA算法的作者合影（照片拍摄于1978年）</p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">前面我们讲了如何通过钟算和幂函数建立不可逆（计算机可以通过穷举法计算出私钥，实际场景中就算是超级计算机也要计算几万亿年之久）的共享密钥。由于小红是小明的女朋友，小明天天在小红面前给她讲RSA加密算法的原理，所以小红也知道怎么得出自己的公钥和私钥。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>接下来我们一起跟着小红的脚步，看看RSA加密的公钥和私钥是怎么计算出来的：</strong></p><ul style="margin-left: 2.5rem; padding-left: 0px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><li style="list-style: inherit;"><em>1）</em>第一步：小红选择了两个很大的质数p和q，这里为了便于计算，选择2和11;</li><li style="list-style: inherit;"><em>2）</em>第二步：计算p和q的乘积n=p*q=2*11=22；</li><li style="list-style: inherit;"><em>3）</em>第三部：计算n的欧拉函数&#966;(n)=(p-1)*(q-1)=10；</li><li style="list-style: inherit;"><em>4）</em>第四步：选择一个小于&#966;(n)且与&#966;(n)互质的整数e，{1,3,7,9}，这里选择e=7；</li><li style="list-style: inherit;"><em>5）</em>第五步：计算e对于&#966;(n)的模反元素（ed mode &#966;(n) = 1）d，d=3。</li></ul><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">到这里小红就得到了他自己的公钥(n,e)和私钥(n,d)。其中n就是钟大小，e和d就是幂函数的幂。接下来就通过计算出来的公钥和私钥进行数据的加解密。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">还是小明、小红和小偷三个人，小红对大家说，我的公钥是（22,7），小明知道了小红的公钥后，想讲自己的信息&#8220;14&#8221;告诉小红，于是就用小红公开的公钥进行加密。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>具体步骤如下：</strong></p><ul style="margin-left: 2.5rem; padding-left: 0px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><li style="list-style: inherit;"><em>1）</em>第一步：小明根据要加密的信息14进行计算，得到加密后的信息20，然后将20告诉小红和小偷；</li><li style="list-style: inherit;"><em>2）</em>第二步：小红有自己的私钥，将加密信息20进行解密，，得到了小明想传递给小红的信息。而小偷呢，知道22,7,20，但是不知道小红的密钥（22,3），无法解密出正确的信息。</li></ul><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>RSA加密算法在数字签名中也发挥着巨大的作用：</strong>假设小偷可以假冒小红，说小红的公钥是（22,9），而小明不知道是小偷假扮的，按照小偷的公钥加密后，结果被小偷解密了。数字签名的作用就是防止信息被篡改，小红说她的公钥是（22,7）的同时，使用私钥给这段信息（通常使用MD5值计算签名）加上签名，小明得到公钥（22,7）和签名13，小明拿到签名后利用公钥计算出信息是否被篡改。</p><div img-uploading-status=""  image-package-7"="" data-index="7" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="6" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164715242-1848354139.png" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164715242-1848354139.png" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><h1>9、加密的实际作用</h1></div></div></div><div img-uploading-status=""  image-package-8"="" data-index="8" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="7" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164720866-1967554200.jpg" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164720866-1967554200.jpg" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;">本文使用的很小的数来进行加密原理的讲解，为了是读者可以方便进行计算。</p></div></div></div><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">在实际使用中（n,e）都是特别大的数，其中n的长度都在768以上，1024长度被认为是基本安全的。</p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;">（1230186684530117755130494958384962720772853569595334792197322452151726400507263657518745202199786469389956474942774063845925192557326303453731548268507917026122142913461670429214311602221240479274737794080665351419597459856902143413=</p><p style="margin-top: 10px; margin-bottom: 10px;">33478071698956898786044169848212690817704794983713768568912431388982883793878002287614711652531743087737814467999489</p><p style="margin-top: 10px; margin-bottom: 10px;">&#215;</p><p style="margin-top: 10px; margin-bottom: 10px;">36746043666799590428244633799627952632279158164343087642676032283815739666511279233373417143396810270092798736308917）</p></blockquote><h1>10、写在最后</h1><div img-uploading-status=""  image-package-9"="" data-index="9" style="font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><div><div><img alt="8" loading="lazy" data-src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164726898-1771510767.jpg" src="https://img2024.cnblogs.com/blog/1834368/202604/1834368-20260407164726898-1771510767.jpg" lazyloaded=""  medium-zoom-image"="" style="border: 0px; max-width: 100%; height: auto !important; cursor: zoom-in; transition: transform 300ms cubic-bezier(0.2, 0, 0.2, 1) !important;" /><p style="margin-top: 10px; margin-bottom: 10px;"><strong>或许看到这里，大家心里还有许多疑惑：</strong></p></div></div></div><ul style="margin-left: 2.5rem; padding-left: 0px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><li style="list-style: inherit;"><em>1）</em>为什么小明和小红建立共享密钥时，通过几次幂运算和钟算就能得到一样的共享密钥？</li><li style="list-style: inherit;"><em>2）</em>为什么RSA加密算法要用两个质数？</li><li style="list-style: inherit;"><em>3）</em>为什么通过公钥加密的信息可以通过私钥解开？</li></ul><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">加密算法的背后，是一道道迷人的数学难题。<strong>而RSA加密算法之所以被广泛运用，是因为一个名为整数分解的古老数学问题，你可以轻易找到两个很大的质数相乘得到一个结果n，但是要将这个结果n分解回两个质数就变得极其困难</strong>。尽管这个所谓的&#8220;整数分解&#8221;问题被研究了数个世纪，还没人能找到一个足够高效的通用方法解决它，并对标准RSA钟大小造成危害。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">数学史中充满了未解决的问题，尽管这些迷人的问题缺乏任何实际应用，却单靠其美学特质就吸引了数学家进行深入探究。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">令人颇感惊讶的是，许多这类迷人但显然无用的问题后来都有了很大的实用价值，这一价值只有在问题被研究数个世纪后才得以破解。整数分解这一问题由来已久。对其最早的严肃研究似乎是在17世纪，由数学家费马（Fermat）和梅森（Mersenne）进行的。欧拉（Euler）和高斯（Gauss）两位数学&#8220;泰斗&#8221;也在接下来的世纪里对这一问题做出了贡献。但直到公钥加密于20世纪70年代被发明，分解大数字的困难才成为一个实际应用的关键。</p><h1>11、本文小结</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">最后总结一下。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>首先：</strong>我们通过一个诈骗短信的例子，引出了加密的原理就是信息+密钥，密钥就是对信息进行加解密的一串数字。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>然后：</strong>通过颜料混合把戏形象的演示了如何建立共享密钥。在使用乘法建立共享密钥的过程中，学习了钟算和幂运算，接着我们了解了RSA加密算法的过程，通过两个质数生成公钥和私钥。</p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;"><strong>最后：</strong>我们根据公钥进行信息加密，再通过私钥完成信息解密。</p><h1>12、参考资料</h1><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[1]&nbsp;<a href="http://www.52im.net/thread-217-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">探讨组合加密算法在IM中的应用</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[2]&nbsp;<a href="http://www.52im.net/thread-219-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一文读懂常用加解密算法与网络通讯安全</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[3]&nbsp;<a href="http://www.52im.net/thread-653-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">非对称加密技术的原理与应用实践</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[4]&nbsp;<a href="http://www.52im.net/thread-2866-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">你知道，HTTPS用的是对称加密还是非对称加密？</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[5]&nbsp;<a href="http://www.52im.net/thread-4015-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">IM聊天系统安全手段之通信连接层加密技术</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[6]&nbsp;<a href="http://www.52im.net/thread-4026-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">IM聊天系统安全手段之传输内容端到端加密技术</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[7]&nbsp;<a href="http://www.52im.net/thread-4552-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">信创必学，一文读懂什么是国密算法的</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[8]&nbsp;<a href="http://www.52im.net/thread-327-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">传输层安全协议SSL/TLS的Java平台实现简介和Demo演示</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[9]&nbsp;<a href="http://www.52im.net/thread-283-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">理论联系实际：一套典型的IM通信协议设计详解（含安全层设计）</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[10]&nbsp;<a href="http://www.52im.net/thread-310-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">微信新一代通信安全解决方案：基于TLS1.3的MMTLS详解</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[11]&nbsp;<a href="http://www.52im.net/thread-215-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">来自阿里OpenIM：打造安全可靠即时通讯服务的技术实践分享</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[12]&nbsp;<a href="http://www.52im.net/thread-763-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">简述实时音视频聊天中端到端加密（E2EE）的工作原理</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[13]&nbsp;<a href="http://www.52im.net/thread-764-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">移动端安全通信的利器&#8212;&#8212;端到端加密（E2EE）技术详解</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[14]&nbsp;<a href="http://www.52im.net/thread-970-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">通俗易懂：一篇掌握即时通讯的消息传输安全原理</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[15]&nbsp;<a href="http://www.52im.net/thread-2027-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一分钟理解 HTTPS 到底解决了什么问题</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[16]&nbsp;<a href="http://www.52im.net/thread-2446-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一篇读懂HTTPS：加密原理、安全逻辑、数字证书等</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[17]&nbsp;<a href="http://www.52im.net/thread-4104-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">基于Netty的IM聊天加密技术学习：一文理清常见的加密概念、术语等</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[18]&nbsp;<a href="http://www.52im.net/thread-4142-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">手把手教你为基于Netty的IM生成自签名SSL/TLS证书</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[19]&nbsp;<a href="http://www.52im.net/thread-4783-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">即时通讯初学者必知必会的20个网络编程和通信安全知识点</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[20]&nbsp;<a href="http://www.52im.net/thread-4792-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">零基础IM开发入门(五)：什么是IM系统的端到端加密？</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[21]&nbsp;<a href="http://www.52im.net/thread-4636-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">微信团队分享：来看看微信十年前的IM消息收发架构，你做到了吗</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[22]&nbsp;<a href="http://www.52im.net/thread-3065-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">零基础IM开发入门(一)：什么是IM系统？</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[23]&nbsp;<a href="http://www.52im.net/thread-3393-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一套亿级用户的IM架构技术干货(上篇)：整体架构、服务拆分等</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[24]&nbsp;<a href="http://www.52im.net/thread-4764-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">转转平台IM系统架构设计与实践(一)：整体架构设计</a></p><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">[25]&nbsp;<a href="http://www.52im.net/thread-4564-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">一套分布式IM即时通讯系统的技术选型和架构设计</a></p><blockquote style="background-image: none; border-top: none; border-right: none; border-bottom: none; border-left-width: 3px; border-left-color: #e2dfdf; margin-right: 0px; margin-left: 0px; background-color: #eeeeee; width: 896px; color: #555555; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif;"><p style="margin-top: 10px; margin-bottom: 10px;"><strong>即时通讯技术学习：</strong></p><p style="margin-top: 10px; margin-bottom: 10px;">- 移动端IM开发入门文章：《<a href="http://www.52im.net/thread-464-1-1.html" rel="noopener nofollow" target="_blank" style="color: #1d58d1; text-decoration-line: none;">新手入门一篇就够：从零开发移动端IM</a>》</p><p style="margin-top: 10px; margin-bottom: 10px;">- 开源IM框架源码：<a href="https://github.com/JackJiang2011/MobileIMSDK" rel="noopener nofollow" target="_blank" style="color: #1d58d1; text-decoration-line: none;">https://github.com/JackJiang2011/MobileIMSDK</a>（<a href="https://gitee.com/jackjiang/MobileIMSDK" rel="noopener nofollow" target="_blank" style="color: #1d58d1; text-decoration-line: none;">备用地址点此</a>）</p></blockquote><p style="margin-top: 10px; margin-bottom: 10px; font-family: &quot;PingFang SC&quot;, &quot;Microsoft YaHei&quot;, &quot;Helvetica Neue&quot;, Helvetica, Arial, sans-serif; background-color: #ffffff;">（<strong>本文已同步发布于：</strong><a href="http://www.52im.net/thread-4899-1-1.html" target="_blank" rel="noopener nofollow" style="color: #1d58d1; text-decoration-line: none;">http://www.52im.net/thread-4899-1-1.html</a>）</p><img src ="http://www.blogjava.net/jb2011/aggbug/451768.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/jb2011/" target="_blank">Jack Jiang</a> 2026-04-09 12:29 <a href="http://www.blogjava.net/jb2011/archive/2026/04/09/451768.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Linux 查看本机软件硬件信息的命令</title><link>http://www.blogjava.net/paulwong/archive/2026/03/23/451765.html</link><dc:creator>paulwong</dc:creator><author>paulwong</author><pubDate>Mon, 23 Mar 2026 03:45:00 GMT</pubDate><guid>http://www.blogjava.net/paulwong/archive/2026/03/23/451765.html</guid><wfw:comment>http://www.blogjava.net/paulwong/comments/451765.html</wfw:comment><comments>http://www.blogjava.net/paulwong/archive/2026/03/23/451765.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/paulwong/comments/commentRss/451765.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/paulwong/services/trackbacks/451765.html</trackback:ping><description><![CDATA[<h1><br /></h1>
  <h2>🖥️ 硬件信息</h2>
  <ul>
    <li><strong>CPU 信息</strong>
      <ul>
        <li><code>lscpu</code> &#8594; 显示 CPU 架构、核心数、线程数</li>
        <li><code>cat /proc/cpuinfo</code> &#8594; 查看详细 CPU 型号、频率</li>
      </ul>
    </li>
    <li><strong>内存信息</strong>
      <ul>
        <li><code>free -h</code> &#8594; 显示内存使用情况</li>
        <li><code>cat /proc/meminfo</code> &#8594; 查看详细内存参数</li>
      </ul>
    </li>
    <li><strong>硬盘信息</strong>
      <ul>
        <li><code>lsblk</code> &#8594; 查看磁盘分区和挂载</li>
        <li><code>df -h</code> &#8594; 查看磁盘使用情况</li>
        <li><code>fdisk -l</code> &#8594; 查看磁盘分区表</li>
      </ul>
    </li>
    <li><strong>PCI/USB 设备</strong>
      <ul>
        <li><code>lspci</code> &#8594; 列出所有 PCI 设备</li>
        <li><code>lsusb</code> &#8594; 列出所有 USB 设备</li>
      </ul>
    </li>
    <li><strong>主板/BIOS</strong>
      <ul>
        <li><code>dmidecode</code> &#8594; 显示 BIOS、主板、内存插槽等信息</li>
      </ul>
    </li>
  </ul>
  <h2>📦 软件信息</h2>
  <ul>
    <li><strong>操作系统版本</strong>
      <ul>
        <li><code>cat /etc/os-release</code> &#8594; 查看发行版信息</li>
        <li><code>uname -a</code> &#8594; 查看内核版本和架构</li>
      </ul>
    </li>
    <li><strong>已安装软件</strong>
      <ul>
        <li>Debian/Ubuntu: <code>dpkg -l</code> 或 <code>apt list --installed</code></li>
        <li>RHEL/CentOS/AlmaLinux: <code>rpm -qa</code> 或 <code>dnf list installed</code></li>
      </ul>
    </li>
    <li><strong>服务与进程</strong>
      <ul>
        <li><code>systemctl list-units --type=service</code> &#8594; 查看正在运行的服务</li>
        <li><code>ps aux</code> &#8594; 查看当前进程</li>
      </ul>
    </li>
    <li><strong>网络信息</strong>
      <ul>
        <li><code>ip addr</code> &#8594; 查看网卡和 IP 地址</li>
        <li><code>ss -tuln</code> &#8594; 查看端口监听情况</li>
      </ul>
    </li>
  </ul>
  <h2>🔍 综合工具</h2>
  <ul>
    <li><code>inxi -Fx</code> &#8594; 一次性显示完整的硬件和系统信息</li>
    <li><code>neofetch</code> &#8594; 美观地显示系统信息</li>
  </ul><img src ="http://www.blogjava.net/paulwong/aggbug/451765.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/paulwong/" target="_blank">paulwong</a> 2026-03-23 11:45 <a href="http://www.blogjava.net/paulwong/archive/2026/03/23/451765.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item></channel></rss>