news 2026/6/6 12:58:56

Python + Snap7 实现西门子 S7-1200/1500 数据采集

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Python + Snap7 实现西门子 S7-1200/1500 数据采集

1. Snap7 简介

Snap7 是一个开源的西门子 S7 PLC 通信库,支持 S7-200/300/400/1200/1500 全系列。它原生支持 C++,但提供了 Python、C#、Node.js 等语言的绑定。

优点:

  • 开源免费,无需额外授权
  • 支持多平台(Windows/Linux/macOS)
  • 性能好,支持多 PLC 并发连接
  • 协议层兼容,不依赖 TIA Portal

2. 环境准备

2.1 安装 python-snap7

pipinstallpython-snap7

2.2 S7-1200/1500 PLC 端设置

在 TIA Portal 中进行以下配置才能让上位机通过 S7 协议通信:

  1. 允许 PUT/GET 通信(S7-1500 需特别注意)
  • 在设备组态 → 保护与安全 → 编译块时支持仿真/PUT/GET 通信 → 勾选
  1. 优化块访问 → 标准访问
  • DB 块属性中,取消"优化的块访问"(否则直接读写需要按符号名,Snap7 读写按地址偏移)
  1. 防火墙设置
  • 确保 PLC 的以太网口防火墙允许 S7 通信(端口 102)

特别注意:S7-1200 固件 4.0+ 默认关闭 PUT/GET,需在 TIA Portal 中显式开启。

3. 快速开始:连接与读取

3.1 创建客户端并连接

importsnap7# 创建客户端client=snap7.client.Client()# 参数:PLC 的 IP 地址,机架号,槽号# S7-1200 通常 rack=0, slot=1# S7-1500 通常 rack=0, slot=0client.connect('192.168.0.1',0,1)# 检查连接状态ifclient.get_connected():print(f"已连接到 PLC:{client.get_cpu_state()}")else:print("连接失败")

3.2 读取 DB 块数据

DB 块是 S7 中最常用的数据存储区,上位机和 PLC 通过 DB 交换数据。

defread_db_block(client,db_number,start_offset,byte_count):""" 读取 DB 块数据 :param client: snap7 客户端 :param db_number: DB 块编号 :param start_offset: 起始字节偏移 :param byte_count: 读取的字节数 :return: bytes 对象 """try:data=client.db_read(db_number,start_offset,byte_count)returndataexceptsnap7.snap7exceptions.Snap7Exceptionase:print(f"读取 DB{db_number}失败:{e}")returnNone# 示例:读取 DB1 从偏移 0 开始的 10 个字节data=read_db_block(client,1,0,10)ifdata:print(f"原始字节:{data.hex()}")

3.3 字节数据解析工具函数

PLC 中常见的数据类型及其字节长度:

类型长度(字节)Python 解析方法
Bool1 (bit)位运算提取
Byte1int.from_bytes()
Int2int.from_bytes()
DInt4int.from_bytes()
Real4struct.unpack(‘>f’)
String可变bytes.decode()
importstructdefparse_int(data,offset=0):"""解析 S7 Int (有符号 16 位)"""returnint.from_bytes(data[offset:offset+2],byteorder='big',signed=True)defparse_dint(data,offset=0):"""解析 S7 DInt (有符号 32 位)"""returnint.from_bytes(data[offset:offset+4],byteorder='big',signed=True)defparse_real(data,offset=0):"""解析 S7 Real (32 位浮点数)"""returnstruct.unpack('>f',data[offset:offset+4])[0]defparse_word(data,offset=0):"""解析 S7 Word (无符号 16 位)"""returnint.from_bytes(data[offset:offset+2],byteorder='big')defparse_dword(data,offset=0):"""解析 S7 DWord (无符号 32 位)"""returnint.from_bytes(data[offset:offset+4],byteorder='big')defparse_byte_array(data,offset=0,length=1):"""解析 Byte 数组"""returnlist(data[offset:offset+length])# 使用示例raw=client.db_read(1,0,40)# 一次读取 40 字节temp_value=parse_real(raw,0)# Real 类型温度值,偏移 0pressure=parse_int(raw,4)# Int 类型压力值,偏移 4status_flags=parse_dword(raw,6)# DWord 状态标志,偏移 6

3.4 完整示例:读取 PLC 中的设备运行数据

importsnap7importstructimporttimeclassS7Client:"""西门子 PLC 数据采集客户端封装"""def__init__(self,ip,rack=0,slot=1):self.client=snap7.client.Client()self.ip=ip self.rack=rack self.slot=slotdefconnect(self):try:self.client.connect(self.ip,self.rack,self.slot)print(f"[+] 已连接到{self.ip}")returnTrueexceptExceptionase:print(f"[-] 连接失败:{e}")returnFalsedefdisconnect(self):self.client.disconnect()defread_device_data(self):""" 从 DB10 读取设备运行数据 字节分配(与 PLC 程序员约定好的): Offset 0-3: Real 温度 Offset 4-7: Real 压力 Offset 8-9: Int 转速 Offset 10-13: DInt 累计运行时间(秒) Offset 14: Byte 设备状态(0=停止,1=运行,2=故障) Offset 15: Byte 报警代码 """try:data=self.client.db_read(10,0,16)return{'temperature':struct.unpack('>f',data[0:4])[0],'pressure':struct.unpack('>f',data[4:8])[0],'speed':int.from_bytes(data[8:10],'big',signed=True),'run_time':int.from_bytes(data[10:14],'big',signed=True),'status':data[14],'alarm_code':data[15],}exceptsnap7.snap7exceptions.Snap7Exceptionase:print(f"读取设备数据失败:{e}")returnNonedefread_multi_db(self,db_configs):""" 批量读取多个 DB 块 db_configs: [(db_num, start, size), ...] """results={}fordb_num,start,sizeindb_configs:data=self.client.db_read(db_num,start,size)results[db_num]=datareturnresults# ========== 使用示例 ==========if__name__=='__main__':plc=S7Client('192.168.0.1',rack=0,slot=1)ifplc.connect():try:whileTrue:data=plc.read_device_data()ifdata:print(f"温度:{data['temperature']:.1f}°C | "f"压力:{data['pressure']:.2f}MPa | "f"转速:{data['speed']}RPM | "f"状态:{data['status']}")time.sleep(1)# 每秒采集一次exceptKeyboardInterrupt:print("\n停止采集")finally:plc.disconnect()

4. 写入数据到 PLC

除了读取,Snap7 同样支持写入操作。

defwrite_real(client,db_number,offset,value):"""向 PLC DB 块写入 Real 类型数据"""data=struct.pack('>f',value)client.db_write(db_number,offset,data)defwrite_int(client,db_number,offset,value):"""向 PLC DB 块写入 Int 类型数据"""data=int.to_bytes(value,2,byteorder='big',signed=True)client.db_write(db_number,offset,data)defwrite_bool(client,db_number,byte_offset,bit_offset,value):"""向 PLC DB 块写入 Bool 类型数据"""# 先读取当前字节current=client.db_read(db_number,byte_offset,1)byte_val=current[0]ifvalue:byte_val|=(1<<bit_offset)else:byte_val&=~(1<<bit_offset)client.db_write(db_number,byte_offset,bytes([byte_val]))# 写入示例write_real(client,10,0,25.5)# DB10.0 写温度write_int(client,10,8,1500)# DB10.8 写转速write_bool(client,10,20,3,True)# DB10.20.3 写一个启停位

5. 读取 I/O 区数据

除了 DB 块,S7 还有 I/Q/M 等存储区。

# 读取输入映像区 PIW(过程映像输入)# 从字节偏移 0 开始,读 4 个字节input_data=client.ab_read(0,4)# 读取输出映像区 PQW(过程映像输出)output_data=client.as_read(0,4)# 读取 M 存储区(中间变量)m_data=client.read_area(snap7.types.Areas.MK,0,0,10)

6. 常见问题与排查

问题原因解决方案
连接超时IP/机架/槽号配置错误确认 PLC IP,Ping 测试,核对 rack/slot
DB block not foundDB 号不存在或未下载检查 TIA Portal 中的 DB 编号
wrong DB length读取长度超出 DB 实际大小缩小读取范围或增大 DB 大小
读出的数值不对字节序或数据类型解析错误S7 是大端 (>f),确认数据类型长度
无法连接 S7-1200 v4+未开启 PUT/GET 通信在 TIA Portal 保护设置中勾选允许

7. 完整代码获取

本文所有代码已整理为可直接运行的 Python 脚本。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/6/6 12:58:39

Altium Develop 初体验:从一个初学者视角看云端硬件设计协作

作为一个刚开始接触 硬件设计 流程的初学者&#xff0c;我之前对 PCB 设计工具的理解基本停留在“画原理图、画 PCB、导出 Gerber 文件”这些步骤上。项目文件通常保存在本地电脑里&#xff0c;遇到需要分享的时候&#xff0c;就把整个工程文件夹压缩后发给别人。 Altium 现在…

作者头像 李华
网站建设 2026/6/6 12:58:26

告别卡顿!Mem Reduct:轻量级Windows内存优化工具全攻略

告别卡顿&#xff01;Mem Reduct&#xff1a;轻量级Windows内存优化工具全攻略 【免费下载链接】memreduct Lightweight real-time memory management application to monitor and clean system memory on your computer. 项目地址: https://gitcode.com/gh_mirrors/me/memre…

作者头像 李华
网站建设 2026/6/6 12:58:19

新手福音:在快马平台上手把手学习dhnvr416h-hd视频处理技术

快速体验 打开 InsCode(快马)平台 https://www.inscode.net输入框内输入如下内容&#xff1a; 请生成一个适合新手学习dhnvr416h-hd基础技术的演示项目。核心功能包括&#xff1a;一个简单的视频播放器界面&#xff0c;用于加载本地示例视频&#xff1b;集成基础的dhnvr416h-…

作者头像 李华
网站建设 2026/6/6 12:55:24

滚筒洗衣机延时门锁原理:PTC与双金属片的热力学安全设计

1. 项目概述&#xff1a;一个被忽视的“安全卫士”在工程师的日常工作中&#xff0c;我们常常聚焦于处理器、通信协议、电源拓扑这些“高大上”的模块&#xff0c;却容易忽略那些看似简单、实则精妙的机电一体化小部件。滚筒洗衣机的自动延时门锁&#xff0c;就是这样一个典型。…

作者头像 李华