被动散热小主机夏天温度较高,影响SSD和HDD寿命以及系统稳定性,内部没有风扇位置,没有4pin风扇接口,只能外接USB风扇,但外接USB风扇只能常开,虽风量大散热效果不错但使用一段时间后积灰严重,DIY一种自动根据CPU温度控制USB风扇开关的方案。
1、使用外设以及整体方案介绍
通过python脚本,读取系统实时温度信息,串口控制开关风扇。
usb串口继电器:USB串口模块和继电器的组合,能通过串口命令控制继电器开/关,就是一个开关设备,淘宝十块钱左右,如下图:
此类设备一般不提供供电能力,只是一个开关。通过给串口发送固定命令开启/关闭继电器开关,从而控制风扇。将风扇供电的一路接入继电器的COM口和NO口,这样继电器吸合后该路就可导通,打开风扇。
2、Python3脚本
import serial
import time
from datetime import datetime
# 请确认以下串口号和波特率与实际设备相符合
SERIAL_PORT = '/dev/ttyUSB0' # 例如: /dev/ttyUSB0
BAUD_RATE = 9600
#风扇开启
THRESHOLD_CEILING = 49.5
#风扇关闭
THRESHOLD_FLOOR = 45.0
COMMAND_OPEN = bytes.fromhex("A00101A2")
COMMAND_CLOSE = bytes.fromhex("A00100A1")
def write_log(log):
timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
with open("fan.log", "a") as f:
f.write(f"[{timestamp}] {log}\n")
# 初始化串口连接
try:
ser = serial.Serial(SERIAL_PORT, BAUD_RATE, timeout=1)
write_log(f"串口 {SERIAL_PORT} 打开成功")
write_log(f"当前温度阈值为{THRESHOLD_CEILING}")
except serial.SerialException as e:
write_log(f"无法打开串口 {SERIAL_PORT}: {e}")
exit(1)
def set_fan(state):
"""
控制 USB 继电器开关风扇
state: True 表示开启风扇,False 表示关闭风扇
"""
if state:
# 根据继电器指令格式调整 (例如: b'ON\r\n')
command = COMMAND_OPEN
else:
command = COMMAND_CLOSE
try:
ser.write(command)
# 如果继电器有回复,可以读取回复做进一步处理
time.sleep(0.1) # 延时等待继电器处理命令
response = ser.readline().decode().strip()
if response:
write_log(f"设备回复: {response}")
except Exception as e:
write_log(f"发送指令时出现错误: {e}")
def get_ssd_temp(sysfs_path="/sys/class/hwmon/hwmon0/temp1_input"):
try:
with open(sysfs_path, "r") as file:
# 读取的值为字符串,去除换行后转换为整数
temp_millic = int(file.read().strip())
# 转换为摄氏度
temp_celsius = temp_millic / 1000.0
return temp_celsius
except FileNotFoundError:
write_log(f"文件 {sysfs_path} 不存在,请检查路径是否正确。")
return None
except Exception as e:
write_log(f"读取温度出现错误: {e}")
return None
fanState = False
while True:
temp = get_ssd_temp()
if temp is None:
write_log("温度获取失败,跳过本次检测")
time.sleep(2)
continue
if temp >= THRESHOLD_CEILING and not fanState:
write_log(f"温度 {temp}°C 超过阈值{THRESHOLD_CEILING},打开风扇")
fanState = True
elif fanState and temp < THRESHOLD_FLOOR:
write_log(f"温度 {temp}°C 低于阈值{THRESHOLD_FLOOR},关闭风扇")
fanState = False
set_fan(fanState)
time.sleep(2) # 每2秒检测一次
注意事项:
SERIAL_PORT: 根据你的真实情况修改,
BAUD_RATE:根据你的usb串口继电器情况修改
COMMAND_OPEN:根据你的usb串口继电器情况修改
COMMAND_CLOSE:根据你的usb串口继电器情况修改
THRESHOLD_CEILING:设置开启风扇温度上限
THRESHOLD_FLOOR:设置关闭风扇温度下限
sysfs_path:确认你的系统温度信息文件是否正确
python环境安装 serial模块
4、部署环境
你可以在系统内安装python3并安装serial模块,后台运行脚本并设置开机自启动,具体如何开机启动,请AI咨询,不再讨论。如果有安装docker,推荐docker部署环境,更方便自启动管理,不跟系统环境冲突。如下介绍docker方法。
拉区python官方镜像
使用compose.xml:
version: '3.8'
services:
python:
image: python:latest
container_name: my-python-env
volumes:
- /vol1/1000/DockerStorage/python:/app
- /etc/localtime:/etc/localtime:ro
working_dir: /app
command: /bin/sh -c "pip install pyserial && python3 Fan.py"
stdin_open: true
restart: always
tty: true
devices:
- "/dev/ttyUSB0:/dev/ttyUSB0"
/vol1/1000/DockerStorage/python替换为你脚本文件Fan.py存放路径
/dev/ttyUSB0 替换为你继电器设备
或者直接命令启动容器:
docker run -dit \
--name my-python-env \
-v /vol1/1000/DockerStorage/python:/app \
-v /etc/localtime:/etc/localtime:ro \
-w /app \
--device /dev/ttyUSB0:/dev/ttyUSB0 \
--restart always \
python:latest \
/bin/sh -c "pip install pyserial && python3 Fan.py"
5、更进一步
目前这种只有开关状态的温控还是不够智能,可以通过串口输出PWM信号,外接MOS模块驱动pwm风扇,实现转速调节,但这样成本就高了,如果你有这种应用场景,可自行尝试。