科学上网

因为公司之前网络自带梯子,自己一直也没搞代理服务器就也没有在机器上配置梯子,最近换了办公地网络没有梯子了。一开始觉得自己能接受,查阅外网的文档慢点就慢点吧,结果真让自己怀疑人生了,时不时问身边人,你可以打开github吗?是我们网又坏了吗?还有就是自己chrome浏览器的数据不能同步很不方便。于是,决定给机器配下梯子!

关于撕我们所处的环境为什么有GFW这种东西,在github上看到一句话“We don’t dismantle the wall, we just find a hole to bypass then instead. Don’t ask us how to bypass, we don’t know. And don’t ask us what a wall is, it’s not a continuous vertical brick or stone structure that encloses or divides an area of land.”。

原理

如图,代理服务器我们需要找一个IP没有被GFW Block掉的境外节点服务器在上面搭建一个shadowsocks协议的代理服务。代理服务器软件有很多python的,go的等等,这里安利一个go项目gost。服务端代理服务器和本地client通信协议一定是shadowsocks,其它协议不行吗?当然可以!但是GFW能认出来呀,然后把你Block掉。shadowsocks协议现在也很敏感了,个人用不要被认为有sale行为就好。 服务端是shdowscoks协议,但是我们的浏览器和其他软件支持的代理协议一般有socks4,socks5,http,https等协议,不能直接用,所以我们要在本地启动一个进程和服务端以shadowsocks协议通信,然后该进程再向本地开放socks5,https等代理协议,我们的浏览器和其他软件就可以直接用了。这个进程程序就是我们看到的很多shadowsocks客户端程序,它就是两边握手byte by byte的转发。 最后,我们在浏览器里使用设置一下浏览器的代理就好了,chrome/firefox代理设置管理,这里安利SwitchyOmega,linux/mac终端走代理可以设置http_proxy/https_proxy环境变量。

shadowsocks客户端方案

本地shdowsocks客户端,网上有很多,大致分两种,CLI形式和GUI形式,GUI的看上去方便,但是linux涉及图形的软件就是各种问题,下了一个QT的试了一下果然各种库问题。果断转CLI,这里再次安利gost。 有一个问题就是随着开机启动需要我们自己解决,linux下配置自启动大家各种脚本写init等等。但是经验告诉我,这么随意的改home目录以外的东西,我这mint又用不过半年了,还有就是发现脚本启动gost用一段时间gost有不响应的情况(可能和网有关系挂掉了)简单的脚本不能重启gost,写复杂好费事。然后想到了docker,机器本来就装了docker,gost放到一个守护容器里面让docker帮我管理就好了,gost是挂掉还是什么docker帮我重启。实践发现确实比我自己手动脚本启动好使,目前一周了没出现不响应的情况。

docker run -d --name gost --restart unless-stopped --log-opt max-size=10m -p 1080:1080 \
ginuerzh/gost -L socks5://:1080 -F ss://aes-256-cfb:password@xx.xx.xx.xx:port

chrome代理设置

chrome代理管理用的SwitchyOmega,值得一提实践中的一个问题就是,我们访问国内网站不想走代理绕一圈回来,访问国外网站要走代理。不能来回手点设置那些网站走代理那些网站不走代理,很烦。解决方法就是设置Switchomega的自动切换规则,参考的这个wiki,自动更新GFW的block list挺好的。

总结

花了一个多小时时间,看了几个项目,找到了自己觉得比较适合自己linuxmint的方案,分享在这里。

阅读全文

SD卡速度规格详解及使用场景对照

SD卡速度规格详解及使用场景对照

SD卡的速度等级由多个不同的标准组成,分别针对最低写入速度总线传输速度应用性能。以下是详细的对照表和使用建议:

1. 核心速度等级对照表

标识图标 全称/含义 最低持续写入速度 主要应用场景
Class 2 Speed Class 2 2 MB/s 早期SD卡,仅适合低分辨率视频或音频存储(现已淘汰)
Class 4 Speed Class 4 4 MB/s 普通标清视频、非高清照片存储(现已较少见)
Class 6 Speed Class 6 6 MB/s 高清视频录制、普通数码相机
Class 10 Speed Class 10 10 MB/s 1080P全高清视频录制、单反相机连拍(经典入门标准)
U1 UHS Speed Class 1 10 MB/s 等同于Class 10,用于1080P视频、普通4K视频
U3 UHS Speed Class 3 30 MB/s 高码率4K视频、8K视频基础、高速连拍、专业摄影
V6 Video Speed Class 6 6 MB/s 低码率视频录制(较少见)
V10 Video Speed Class 10 10 MB/s 1080P视频录制
V30 Video Speed Class 30 30 MB/s 主流4K视频、高像素连拍(目前最通用的中高端标准)
V60 Video Speed Class 60 60 MB/s 高码率4K/8K视频、RAW格式高速连拍、双卡槽写入
V90 Video Speed Class 90 90 MB/s 极致专业视频(如8K 60fps)、高码率RAW连拍、电影制作

2. 总线传输速度层级 (UHS)

这代表了SD卡与读卡器/相机之间的理论最大传输带宽,影响照片/视频从卡导出到电脑的速度。

标准 理论最大读取速度 说明
UHS-I 104 MB/s 最常见,单排金手指。满足绝大多数消费级需求。
UHS-II 312 MB/s 双排金手指(底部多一排触点)。需配合UHS-II读卡器使用,导出速度极快,适合专业摄影师。
UHS-III 624 MB/s 较新标准,双排金手指,速度翻倍,目前高端专业设备开始支持。

3. 应用性能等级 (A-Class) - 主要针对手机/microSD

等级 含义 适用场景
A1 随机读取/写入性能提升 适合在手机上运行APP、存储游戏数据。
A2 随机读写性能大幅提升(IOPS更高) 推荐用于Android手机、Switch、无人机,能显著提升APP加载速度和系统流畅度。

选购建议与使用场景匹配

📷 场景一:普通家用 / 行车记录仪 / 监控摄像头

  • 推荐规格Class 10U1 / V10
  • 理由:这类设备对持续写入速度要求不高,10MB/s 足以应对1080P视频循环覆盖。
  • 注意:监控/行车记录仪需选择“高耐久(High Endurance)”系列,因为它们是7x24小时不断写入。

📸 场景二:日常摄影 / 旅行 / 1080P 或 基础 4K 视频

  • 推荐规格U3 / V30 + UHS-I
  • 理由:V30保证30MB/s的持续写入,能稳定录制4K视频不卡顿。UHS-I接口足以应付日常照片导入。这是目前性价比最高、最通用的选择。

🎥 场景三:专业视频创作 / 8K视频 / 高码率4K

  • 推荐规格V60V90 + UHS-II
  • 理由:拍摄高码率视频(如4K 120fps或8K)时,数据量巨大,V60/V90能防止缓冲区溢出(爆红/停止录制)。UHS-II接口能实现秒传大量素材,节省后期时间。
  • 注意:必须搭配支持UHS-II的读卡器和电脑接口(USB 3.1/3.2 Gen 2或Thunderbolt)。

📱 场景四:手机扩容 / Switch / 无人机 / 运动相机

  • 推荐规格microSDXC + A2 + V30/U3
  • 理由
    • A2:确保在手机或Switch上运行大型游戏和APP时加载速度快。
    • V30/U3:确保在GoPro、大疆无人机等设备上录制4K高清视频不掉帧。
    • 耐用性:运动相机建议使用“加固版”或“高耐用”系列,以抵抗高温和震动。

阅读全文

Windows终端设置

修改默认终端

  • 生效范围cmd和powershell

启动cmd或者powershell,窗口上栏,右键属性,默认终端应用程序,可以修改为其他终端。

恢复成windows的默认,其他终端没有这个选项入口,所有需要用命令行启动,再次找到这个入口改回去。

Start-Process "conhost.exe" -ArgumentList "cmd"
阅读全文

RHEL系Linux更新内核

ELRepo 简介

项目主页:http://elrepo.org

Enterprise Linux 软件包的 RPM 存储库。ELRepo 支持 Red Hat Enterprise Linux (RHEL) 及其衍生产品,如CentOS Linux、AlmaLinux 和 Rocky Linux。

启用 ELRepo

从 CentOS 8 开始,ELRepo 已经加入到官方软件仓库中,名称为 “elrepo-release”。

AlmaLinux 和 Rocky Linux 同样适用。

启用 ELRepo 只需要执行命令:

dnf -y install elrepo-release

升级内核

查询 ELRepo 中的 kernel 版本

yum --disablerepo="*" --enablerepo="elrepo-kernel" list available
yum --disablerepo="*" --enablerepo="elrepo-kernel" list available --showduplicates #查看所有版本

kernel-ml 中的 ml 是英文 “mainline stable” 的缩写,elrepo-kernel 中列出来的是最新的稳定主线版本。
kernel-lt 中的 lt 是英文 “long term support” 的缩写,elrepo-kernel 中列出来的长期支持版本。

安装 kernel

yum --disablerepo="*" --enablerepo=elrepo-kernel install kernel-ml kernel-ml-core kernel-ml-devel kernel-ml-modules  kernel-ml-modules-extra

慎重装kernel-ml-headers包,会和发行版的kernel-headers包冲突

Error:
 Problem: package kernel-ml-headers-6.16.6-1.el8.elrepo.x86_64 from elrepo-kernel conflicts with kernel-headers < 6.16.6-1.el8.elrepo provided by kernel-headers-4.18.0-553.34.1.el8_10.x86_64 from @System
  - cannot install the best candidate for the job
  - problem with installed package kernel-headers-4.18.0-553.34.1.el8_10.x86_64

elrepo官方提示:

There is no need to install the kernel-lt-headers package. It is only necessary if you intend to rebuild glibc and, thus, the entire operating system. If there is a need to have the kernel headers installed, you should use the current distributed kernel-headers package as that is related to the current version of glibc. When you see a message like “your kernel headers for kernel xxx cannot be found …”, you most likely need the kernel-lt-devel package, not the kernel-lt-headers package.

kernel-headers包是给用户态程序用的,个人理解为类似libc标准库里的*unix规范接口函数,不同版本内核间相当稳定,所以使用发行版的即可。
kernel-devel包是给开发内核态程序\内核模块用的,不通版本内核间就有差异,所以需要单独装。

所以常规仅仅是使用新版本内核,不需要装kernel-ml-headers,保持使用发行版的kernel-headers,而且升级发行版的kernel版本时kernel-headers也可能不会一起更新,kernel-headers在需要时才会更新。

发行版源的其他软件,都依赖发行版的kernel-headers,忽略冲突安装可能造成其他软件安装失败,https://www.rockylinux.cn/notes/rocky-linux-9-nei-he-sheng-ji-zhi-6.html

查询安装的 kernel 包

rpm -qa|grep kernel

查看和设置默认启动项

grubby 是一个命令行工具,用于更新和显示有关 grub2 和 zipl 引导加载程序的配置文件的信息。它主要设计用于安装新内核并需要查找有关当前引导环境的信息的脚本。同时也可以对启动内核的各项信息参数进行修改。

在 CentOS 8 在已经自带该命令,如果没有通过 yum install grubby 来安装即可。

查看当前的默认启动内核:

grubby --default-kernel
/boot/vmlinuz-5.15.4-1.el8.elrepo.x86_64

查看系统安装的全部内核:

grubby --info=ALL

index=0
kernel="/boot/vmlinuz-5.15.4-1.el8.elrepo.x86_64"
args="ro crashkernel=auto net.ifnames=0 $tuned_params"
root="UUID=56c34ece-6010-480e-aeac-dea98b8ffcd3"
initrd="/boot/initramfs-5.15.4-1.el8.elrepo.x86_64.img $tuned_initrd"
title="Rocky Linux (5.15.4-1.el8.elrepo.x86_64) 8.5 (Green Obsidian)"
id="032ed95ba9c0471381bbb6b416eff523-5.15.4-1.el8.elrepo.x86_64"
index=1
kernel="/boot/vmlinuz-4.18.0-348.2.1.el8_5.x86_64"
args="ro crashkernel=auto net.ifnames=0 $tuned_params"
root="UUID=56c34ece-6010-480e-aeac-dea98b8ffcd3"
initrd="/boot/initramfs-4.18.0-348.2.1.el8_5.x86_64.img $tuned_initrd"
title="Rocky Linux (4.18.0-348.2.1.el8_5.x86_64) 8.5 (Green Obsidian)"
id="032ed95ba9c0471381bbb6b416eff523-4.18.0-348.2.1.el8_5.x86_64"
index=2
kernel="/boot/vmlinuz-4.18.0-348.el8.x86_64"
args="ro crashkernel=auto net.ifnames=0 $tuned_params intel_iommu=on"
root="UUID=56c34ece-6010-480e-aeac-dea98b8ffcd3"
initrd="/boot/initramfs-4.18.0-348.el8.x86_64.img $tuned_initrd"
title="AlmaLinux (4.18.0-348.el8.x86_64) 8.5 (Arctic Sphynx)"
id="032ed95ba9c0471381bbb6b416eff523-4.18.0-348.el8.x86_64"
index=3
kernel="/boot/vmlinuz-0-rescue-032ed95ba9c0471381bbb6b416eff523"
args="ro crashkernel=auto net.ifnames=0"
root="UUID=56c34ece-6010-480e-aeac-dea98b8ffcd3"
initrd="/boot/initramfs-0-rescue-032ed95ba9c0471381bbb6b416eff523.img"
title="AlmaLinux (0-rescue-032ed95ba9c0471381bbb6b416eff523) 8.5 (Arctic Sphynx)"
id="032ed95ba9c0471381bbb6b416eff523-0-rescue"

查看特定内核的具体信息:

grubby --info=/boot/vmlinuz-4.18.0-348.el8.x86_64
index=1
kernel="/boot/vmlinuz-4.18.0-348.el8.x86_64"
args="ro crashkernel=auto net.ifnames=0 $tuned_params"
root="UUID=56c34ece-6010-480e-aeac-dea98b8ffcd3"
initrd="/boot/initramfs-4.18.0-348.el8.x86_64.img $tuned_initrd"
title="AlmaLinux (4.18.0-348.el8.x86_64) 8.5 (Arctic Sphynx)"
id="032ed95ba9c0471381bbb6b416eff523-4.18.0-348.el8.x86_64"

设置新的默认启动内核:

使用路径来指定内核,可以使用 –set-default=kernel-path

grubby --set-default=/boot/vmlinuz-4.18.0-348.el8.x86_64
The default is /boot/loader/entries/032ed95ba9c0471381bbb6b416eff523-4.18.0-348.el8.x86_64.conf with index 1 and kernel /boot/vmlinuz-4.18.0-348.el8.x86_64

grubby --default-kernel
/boot/vmlinuz-4.18.0-348.el8.x86_64

使用 index 来指定内核,则使用 –set-default-index=entry-index

grubby --set-default-index=1
The default is /boot/loader/entries/032ed95ba9c0471381bbb6b416eff523-4.18.0-348.el8.x86_64.conf with index 1 and kernel /boot/vmlinuz-4.18.0-348.el8.x86_64

grubby --default-kernel
/boot/vmlinuz-4.18.0-348.el8.x86_64

重启后生效

reboot

删除旧内核(可选)

从启动项中删除旧内核

grubby --remove-kernel=/boot/vmlinuz-4.18.0-348.el8.x86_64

删除旧内核文件

# 删除旧内核
yum remove kernel-4.18.0 kernel-core-4.18.0 kernel-modules-4.18.0 kernel-devel-4.18.0
# 需要注意,是否同时删除一些依赖包。

Kernel相关的RPM包说明

kernel-core
提供内核的二进制镜像、所有与 initramfs相关的对象来引导系统,以及确保核心功能的最小内核模块数量。

kernel-modules
提供 kernel-core 中不存在的其余内核模块。

kernel-modules-extra
为罕见硬件提供内核模块。默认禁用模块的加载。

kernel-debug
提供了启用了许多调试选项的内核,以便进行内核诊断,以降低性能为代价。

kernel-tools
提供了操作 Linux 内核和支持文档的工具。

kernel-devel
提供了内核标头和 makefile,来足以针对 kernel 软件包构建模块。

kernel-abi-stablelists
提供与 RHEL 内核 ABI 相关的信息,包括外部 Linux 内核模块所需的内核符号列表和 yum 插件以协助执行。

kernel-headers
包括指定 Linux 内核和用户空间库以及程序间接口的 C 标头文件。头文件定义构建大多数标准程序所需的结构和常量。

安装ELRepo历史版本内核

官方的elrepo, lt和ml都只有当前版本的包。

如果要指定安装指定版本的内核,可以从这里https://mirrors.coreix.net/elrepo-archive-archive/kernel/下载RPM包。

例如rockylinux8目前了mainline是6.x,安装高版本的5.x:

wget -c https://mirrors.coreix.net/elrepo-archive-archive/kernel/el8/x86_64/RPMS/kernel-ml-5.19.9-1.el8.elrepo.x86_64.rpm
wget -c https://mirrors.coreix.net/elrepo-archive-archive/kernel/el8/x86_64/RPMS/kernel-ml-core-5.19.9-1.el8.elrepo.x86_64.rpm
wget -c https://mirrors.coreix.net/elrepo-archive-archive/kernel/el8/x86_64/RPMS/kernel-ml-devel-5.19.9-1.el8.elrepo.x86_64.rpm
wget -c https://mirrors.coreix.net/elrepo-archive-archive/kernel/el8/x86_64/RPMS/kernel-ml-modules-5.19.9-1.el8.elrepo.x86_64.rpm
wget -c https://mirrors.coreix.net/elrepo-archive-archive/kernel/el8/x86_64/RPMS/kernel-ml-modules-extra-5.19.9-1.el8.elrepo.x86_64.rpm

# rpm -ivh --oldpackage kernel-ml-*
rpm -ivh kernel-ml-*

文章参考

https://sysin.org/blog/centos-8-upgrade-kernel/

阅读全文

本地Lambda函数几行代码实现MCP Server

文章视频教程: https://www.bilibili.com/video/BV1wWd8YNEZY/?vd_source=e14a954d1c7739b152548d58bf125603

MCP+Lambda

MCP服务器充当MCP客户端与Lambda函数之间的桥梁,使生成式AI模型能够访问和运行Lambda函数作为工具。

社区项目 https://github.com/danilop/MCP2Lambda

但是目前MCP在安全方面还比较弱,所以社区MCP工具基本都是本地工具,Lambda能不能也本地部署。

Refunc是基于K8S的一个本地化的Lambda平台,可以实现本地部署Lambda函数。

MCP+Refunc

Refunc社区跟进MCP发展,实现了任意函数通过MCP开放调用。

https://github.com/refunc/mcp-server

部署 Refunc

refunc-system 命名空间下部署所有 Refunc 组件。

kubectl apply -f https://raw.githubusercontent.com/refunc/mcp-server/refs/heads/main/deploy/play-all-in-one.yaml

接着,将 Refunc 服务代理到本地。

kubectl port-forward svc/aws-api 8000:http --address 0.0.0.0 -n refunc-system
kubectl port-forward svc/mcp-server 8001:http --address 0.0.0.0 -n refunc-system

注意:演示部署中的数据是非持久化的。

创建函数

使用 refunc-cli 创建一个函数。

pip install -U refunc-cli
mkdir mcp-demo && cd mcp-demo
rfctl init

main.py 中编写任意代码,演示将回显一条问候消息。

AWS_DEFAULT_ENDPOINT=http://127.0.0.1:8000 rfctl create

注意:您需要一个 Python 3 环境。

创建 MCP 端点

编辑 lambda.yaml 并粘贴以下代码。

metadata:
  name: mcp-demo
  namespace: refunc-system
spec:
  build:
    source: .
    manifest: requirements.txt
    language: python
    architecture: x86_64
  handler: main.lambda_handler
  timeout: 120
  runtime: "python3.10"
  concurrency: 1
  environment:
    ENV_TEST: TEST
#  url:
#    cors:
#      allowCredentials: true
#      allowHeaders: "*"
#      allowMethods: "*"
#      allowOrigins: "*"
#      exposeHeaders: "*"
#      maxAge: 300
  events:
    # - name: hourly
    #   type: cron
    #   mapping:
    #     cron: 0 * * * *
    #     location: Asia/Shanghai
    #     args:
    #       var1: value1
    #     saveLog: false
    #     saveResult: false
    - name: mcp
      type: mcp
      mapping:
        args:
          token: mcp-demo
          tools:
            - name: echo-hello
              desc: Echo a hello msg
              schema:
                type: object
                properties: {}
                required: []
        saveLog: false
        saveResult: false

接下来,运行以下命令更新配置:

AWS_DEFAULT_ENDPOINT=http://127.0.0.1:8000 rfctl update-config

演示的 MCP SSE 端点为:http://127.0.0.1:8001/refunc-system/mcp-demo/test/mcp-demo/sse

Refunc MCP SSE URL 路径格式为:/namespace/<token-secret-name>/<token>/<func-name>/sse

Refunc MCP 事件规范

- name: mcp
  type: mcp # 事件类型必须为 mcp。
  mapping:
    args:
      token: mcp-demo # 可以在 play-all-in-one.yaml 中找到的 token 秘钥名称。
      tools: # MCP 工具
        - name: echo-hello # MCP 工具名称
          desc: Echo a hello msg # MCP 工具描述
          schema: # MCP 工具参数,用有效的 JSON Schema 描述。
            type: object
            properties: {}
            required: []
    saveLog: false
    saveResult: false

事件的tools字段是一个数组,您可以通过一个函数实现多个tool。在调用函数时,Refunc 会添加两个内置参数:_call_type_call_method,其中 _call_method 是tool的名称。_call_type会表示调用来自MCP的什么类型,Tool、Resource或者Prompts。

阅读全文