python-snap7
python-snap7 is a pure Python S7 communication library for Siemens PLCs, implementing the full protocol stack (TPKT, COTP, S7) in Python. As of version 3.0.0, it no longer requires the underlying Snap7 C library. It provides an interface for connecting to and interacting with Siemens S7-300, S7-400, S7-1200, and S7-1500 PLCs. The library is actively maintained with a moderate release cadence, with major versions introducing significant architectural changes.
Common errors
-
ModuleNotFoundError: No module named 'snap7.snap7'
cause Attempting to import the old C-binding wrapper module (`snap7.snap7`) which was removed in version 3.0.0.fixUpdate your import statements to use the new pure Python client: `from snap7.client import Client`. -
snap7.snap7exceptions.Snap7Exception: error while connecting: 10060
cause This usually indicates a connection timeout or refusal. Common reasons include incorrect IP/rack/slot, PLC not reachable, PLC not configured for PUT/GET communication, or firewall blocking the connection.fix1. Verify `plc_ip`, `plc_rack`, `plc_slot` are correct. 2. Ping the PLC's IP address. 3. Ensure PUT/GET communication is enabled in the PLC's TIA Portal project. 4. Check network firewalls on both the client and PLC side. -
TypeError: 'str' object cannot be interpreted as a buffer
cause Passing a string directly to functions expecting a bytearray or bytes object (e.g., `db_write`, `mb_write`).fixConvert your string data to a `bytearray` or `bytes` object before passing it to the write functions. Example: `data_to_write = bytearray(b'Hello')` or `data_to_write = 'Hello'.encode('ascii')`.
Warnings
- breaking Version 3.0.0 is a complete rewrite in pure Python, removing the dependency on the Snap7 C library. This changes internal architecture and some import paths.
- breaking Version 2.0.0 introduced significant code restructuring with potential, though not fully documented, API changes for method arguments and internal types.
- gotcha Older versions of `python-snap7` (pre-3.0.0) required the Snap7 C shared library (`libsnap7.so` on Linux, `snap7.dll` on Windows) to be installed and accessible in the system's PATH or library search paths.
- gotcha Siemens PLCs often require specific settings (e.g., 'Permit access with PUT/GET communication from remote partner (PLC, HMI, SCADA)') to allow external communication. Without this, `python-snap7` connections will fail.
Install
-
pip install python-snap7
Imports
- Client
import snap7.snap7
from snap7.client import Client
Quickstart
import snap7
from snap7.snap7types import S7AreaDB
import os
# Configure PLC connection details
plc_ip = os.environ.get('PLC_IP', '192.168.0.100') # Placeholder IP
plc_rack = int(os.environ.get('PLC_RACK', '0'))
plc_slot = int(os.environ.get('PLC_SLOT', '1'))
client = snap7.client.Client()
try:
client.connect(plc_ip, plc_rack, plc_slot)
if client.get_connected():
print(f"Successfully connected to PLC at {plc_ip}")
# Example: Read 10 bytes from Data Block (DB) number 10, starting at byte 0
db_number = 10
start_byte = 0
size = 10
data_buffer = client.db_read(db_number, start_byte, size)
print(f"Read from DB{db_number}, Start:{start_byte}, Size:{size}: {data_buffer}")
# Example: Write 10 bytes to Data Block (DB) number 10, starting at byte 0
# Make sure the PLC is configured to allow writes.
# new_data = bytearray([0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A])
# client.db_write(db_number, start_byte, new_data)
# print(f"Wrote to DB{db_number}, Start:{start_byte}, Size:{size}: {new_data}")
else:
print("Failed to connect to PLC.")
except Exception as e:
print(f"An error occurred: {e}")
finally:
if client.get_connected():
client.disconnect()
print("Disconnected from PLC.")