golang 接口(interface)最佳实践

接口定义 应该定义在接口所使用的包中,而非接口实现的包中。 以io包中的io.Reader/io.Wirter为例,接口定义在io包中,而他的实现bytes.Buffer、os.File等都是在不同包中。 接口实现应该返回具体类型 应该返回对应的结构体或指针,这样实现类如果扩展新的方法就可以直接添加,无需改动接口定义部分,更加灵活。 //为了方便演示,本实例代码未遵循「接口需要在使用包中声明」规范 package demo import "fmt" type Demo interface { show() error } type MyDemo struct { } //这里的返回值应该是 `MyDemo` 或 `*MyDemo` 而非 `Demo` func NewMyDemo() *MyDemo { return &MyDemo{} } func (md *MyDemo) show() error { fmt.Println("show") return nil } 接口应该什么时候定义 在当前模块有依赖外部服务的时候,这时候就会定义一个接口,来对外部的依赖资源进行抽象解耦,屏蔽接口的实现。相反,依赖的提供方在不知道使用方需求的时候,定义接口也就没什么意义。

June 11, 2022 · 1 min · 云溪

树莓派变身旁路由,扩展家中网络

由于家中网络覆盖存在死角,手中有一个树莓派,就准备刷入「openwrt」作为旁路由,扩展家中的无线网络。 整体思路如下,用树莓派的自带网口桥接主路由网络,然后通过树莓派无线网卡发射无线网络,从而达到扩展网络的目的。 如果你也正巧有类似的需求可以通过下面清单,准备所需材料: 树莓派 读卡器 TF 卡 台式机/笔记本(用于调试网络) 网线一根 下载镜像 镜像推荐:OpenWrt-Rpi ,这款镜像支持绝大多数的常见设备,并且镜像集成了很多很好用的功能,也免去了刷官方固件,后续自己折腾安装软件的过程。 进入固件下载 页面能够看到支持设备的列表,找到自己的设备,点击固件下载,进入你设备的固件下载页。 我这边是树莓派 3B 下载的为: immortalwrt-bcm27xx-bcm2710-rpi-3-ext4-factory.img.gz 到此镜像就已经下载好了,下面就是将下载好的镜像,写入树莓派的 TF 卡。 写入镜像 将 TF 卡插入读卡器,并将读卡器插入电脑上,镜像写入工具使用的为: Win32 Disk Imager 如果没有的话可以自行下载。打开 Win32DiskImager 软件,选择下载好的 「openwrt] 镜像和对应 TF 卡的盘符,点 Write 按钮开始写入镜像。 看到写入完成的提示后,将 TF 卡拔出插入树莓派,将准备的网线插入树莓派网口,并网线的另一端连接到电脑上,将树莓派开机。 openwrt 配置 接口配置 树莓派开机后,电脑端输入 192.168.1.1 可以看到路由器的登录页面。 镜像的默认密码为: password ,输入密码后进入系统后,点击「网络-接口」进行接口设置,系统默认已经创建好了 LAN 接口,点击 LAN 接口的修改,进行配置,具体配置如下: 传输协议:静态地址 IPv4 地址: 前三位与主路由地址相同,最后一位写一个内网中没有分配的地址即可。我这里为:192.168.1.100,需要注意的是此地址也是后续登录路由器管理界面的地址。 IPv4 子网掩码: 255.255.255.0 IPv4 网关: 主路由网关,我这里为 192.168.1.1 DNS 服务器1:114.114.114.114 DNS 服务器1:8.8.8.8 上述配置完成后,拉到页面底部点击 保存&应用 应用配置,配置应用成功后,重新登录路由器,此时再用192....

May 3, 2022 · 1 min · 云溪

NGINX与PHP-FPM 是如何通讯的

Nginx、CGI、FastCGI、php-fpm关系,介绍了 NGINX PHP-FPM FastCGI 之间的关系。 本问介绍一下 NGINX 与 PHP-FPM 是如何进行通讯的,NGINX 是如何将请求转发到 PHP-FPM,PHP-FPM 有事如何知道该区找哪个脚本执行相应的代码逻辑。 建立连接 NGINX 通过 fastcgi_pass 与 PHP-FPM 建立连接,fastcgi_pass 有两种方式进行配置 通过 TCP 连接 fastcgi_pass 127.0.0.1:9000; 优势: 将 PHP-FPM 与 NGINX 进行解耦,可以动态的扩展 PHP-FPM 的服务数量 劣势: 由于将服务暴露到外网,会带来一些安全相关的风险 通过 UNIX socket 连接 fastcgi_pass unix:/var/run/php-fpm.sock; 优势: 进程间通讯,效率更高 劣势 NGINX 和 PHP-FPM 必须在同一系统环境内 两种建立连接的方式都需要 PHP-FPM 配置进行配合,如果 NGINX 采用 TCP 连接,则 PHP-FPM 也需要进行 TCP 的监听,反之亦然。 传递参数 PHP 在处理业务的时候需要一些参数比如:用户的 quey 和 请求 URL…,这些参数 NGINX 是如何传递给 PHP-FPM 的呢?...

March 8, 2022 · 1 min · 云溪

安全传输层协议(TLS)介绍

TLS 介绍 TLS (和 SSL) 协议位于应用程序协议层和 TCP/IP 层之间,可以在其中保护应用程序数据并将其发送到传输层。 由于协议在应用程序层和传输层之间工作,因此 TLS 和 SSL 可以支持多个应用程序层协议。 TLS 和 SSL 假定使用面向连接的传输(通常为 TCP), 可以预防如下风险: 消息篡改 消息拦截 消息伪造 TLS 握手 介绍 TLS 整个握手流程如下图所示 客户端请求(clinet hello) 这个阶段主要发送信息如下: 客户端支持的 TLS 版本号 客户端随机数Random 客户端支持的加密方法 客户端支持的压缩算法 服务端响应(server hello) 服务端支持的 TLS 版本号 服务端随机数Random 服务端支持的加密方法 服务端支持的压缩算法 服务端证书发送 服务端发送 server hello 后会发送证书,通常他们俩者在同一个网络包中,即同一个 TLS 记录层消息中。 证书验证(可选) 客户端拿到服务端证书,到证书办法机构的服务器(OCSP responder)验证证书是否可用 Client Key exchange 在此阶段客户端也会生成一个随机数,加上 clinet hello, server hello 生成的随机数一共三个随机数 作为 pre-master,发送给服务器,服务器端收到pre-master算出main master。而客户端当然也能自己通过pre-master算出main master。如此以来双方就算出了对称密钥。 客户端 finished 一个 Finished 消息一直会在一个 change cipher spec 消息后立即发送,以证明密钥交换和认证过程是成功的。一个 change cipher spec 消息必须在其它握手消息和结束消息之间被接收。...

February 17, 2022 · 1 min · 云溪

从 IOS 进入 H5 页面过慢,理解 OSCP

问题分析 近期系统出现了部分 IOS 进入 H5 页面很慢的情况,而 Android 进入却正常。 在排除调程序和网络的问题后,最终把问题定位到 SSL 证书上。要想了解整个问题所在,需要从 TLS 协议开始说起 TLS 握手流程如下图所示 问题就出在客户验证证书这里,这里验证证书是通过 在线证书状态协议(OCSP),进行验证的。OCSP 验证原理也比较简单,就是拿证书信息到证书颁发机构的 OCSP 服务器做校验。 由于我们使用的是国外机构颁发的证书,因此验证证书的服务器也在国外,由于国内网络环境受限的因素,验证服务器无法访问,从而导致整个网站的访问卡在了证书校验这一步,无法正常的完成 TLS 握手。 找到了原因解决的方法也就迎刃而解了,我们把站点证书换成了国内机构颁发的,成功的解决了问题。 问题验证 在苹果官网找到了如下说明,佐证了上述猜想 对 TLS 证书信任状态的评估依照既定的行业标准(如 RFC 5280 所列)执行,且整合了新出现的标准,如 RFC 6962(证书透明度)。在 iOS 11 或更高版本以及 macOS 10.13 或更高版本中,Apple 设备会随撤销及受限证书的当前列表来进行定期更新。该列表由 Apple 信任的每个内建根证书颁发机构及其从属的 CA 签发者所发布的证书撤销清单 (CRL) 聚合而成,列表还可能根据 Apple 的要求酌情包括其他限制。每当使用网络 API 函数进行安全连接时都会使用此信息。如果需要单独列出的 CA 撤销证书太多,信任评估可能需要在线证书状态响应 (OCSP),否则将无法通过信任评估。 其他一些症状 症状1 IOS 有的进入速度很快,有的进入很慢 出现上述问题的原因是:验证服务器一般都是通过 CDN 分发的,有可能部分 IP 未被限制 症状2 IOS 进入慢的用户,更换网络环境可以更快的进入。 运营商的限制策略不同,导致更换网络提供商后有可能解决问题。 一些疑问 问题出现的时候 Android 并未收到影响,一直进入速度都很快,如果说验证证书的服务器出现问题,为什么 Android 不受影响呢?...

February 16, 2022 · 1 min · 云溪