{"id":8528,"library":"pytest-embedded-serial","title":"pytest-embedded-serial: Serial Port Testing for Pytest Embedded","description":"pytest-embedded-serial is a pytest plugin that extends the core pytest-embedded framework, enabling robust testing of embedded devices over serial communication. It provides fixtures and functionalities to interact with serial ports, facilitating automated tests for embedded systems. Currently at version 2.7.0, it is part of the pytest-embedded ecosystem maintained by Espressif Systems, which typically follows a regular release cadence with semantic versioning.","status":"active","version":"2.7.0","language":"en","source_language":"en","source_url":"https://github.com/espressif/pytest-embedded","tags":["pytest","embedded","serial","testing","hardware","espressif"],"install":[{"cmd":"pip install pytest-embedded-serial","lang":"bash","label":"Install stable version"}],"dependencies":[{"reason":"This plugin extends the core pytest-embedded framework.","package":"pytest-embedded","optional":false},{"reason":"Underlying library for serial communication. While not a direct pip dependency of pytest-embedded-serial (it is usually handled by pytest-embedded's installation or implicitly via its internal components), it's essential for serial functionality.","package":"pyserial"}],"imports":[{"note":"pytest-embedded-serial extends the Dut fixture provided by pytest-embedded. You typically import Dut from pytest_embedded and the serial functionalities are automatically available if pytest-embedded-serial is installed and enabled.","symbol":"Dut","correct":"from pytest_embedded import Dut"},{"note":"While SerialDut is available for direct import, the recommended way to interact with serial capabilities in tests is through the `dut: Dut` fixture, which pytest-embedded-serial enhances.","wrong":"from pytest_embedded.dut import SerialDut","symbol":"SerialDut","correct":"from pytest_embedded_serial.dut import SerialDut"}],"quickstart":{"code":"import pytest\nfrom pytest_embedded import Dut\nimport os\n\n# Assuming a device is connected via serial port\n# You can specify the port via CLI: pytest --port /dev/ttyUSB0 (or COMx on Windows)\n# Or set it via an environment variable or pytest.ini\n\ndef test_serial_communication(dut: Dut):\n    # Ensure the 'serial' service is enabled, e.g., via CLI: pytest --embedded-services serial\n    # or by default if pytest-embedded-serial is installed.\n\n    # Example: Write data to the serial port and expect a response\n    # Replace with actual device interaction logic\n    dut.write('hello device')\n    dut.expect_exact('echo: hello device', timeout=5)\n    print(\"Device responded to 'hello device'.\")\n\n    # Accessing underlying serial object (for advanced use cases)\n    # The dut.serial object is an instance of Serial from pytest_embedded_serial.serial\n    # It's generally preferred to use dut.write and dut.expect for standard interactions.\n    # serial_port = dut.serial\n    # print(f\"Connected to serial port: {serial_port.port} at baudrate: {serial_port.baud}\")\n\n    dut.write('get status')\n    dut.expect(r'Status: (\\w+)', timeout=5)\n    status = dut.match.group(1).decode('utf-8')\n    print(f\"Device status: {status}\")\n\n    assert status == 'OK'\n","lang":"python","description":"This quickstart demonstrates how to write a basic pytest-embedded test that utilizes serial communication. It uses the `dut` fixture, which is automatically enhanced by `pytest-embedded-serial` when installed. The example shows writing commands to the device under test (DUT) and expecting specific responses using `dut.write()` and `dut.expect_exact()`. The `serial` service is often automatically enabled when the package is installed, or can be explicitly enabled via `pytest --embedded-services serial` CLI option."},"warnings":[{"fix":"Upgrade your Python environment to version 3.10 or later. Update your `pytest-embedded` and `pytest-embedded-serial` installations: `pip install -U 'pytest-embedded~=2.0' 'pytest-embedded-serial~=2.0'`.","message":"Python 3.7, 3.8, and 3.9 are no longer supported by the pytest-embedded ecosystem, including pytest-embedded-serial. Projects using these older Python versions must upgrade to Python 3.10 or newer.","severity":"breaking","affected_versions":"pytest-embedded>=2.0.0"},{"fix":"Ensure you are using the latest stable version of `pytest-embedded` and `pytest-embedded-serial` to benefit from the fix. `pip install -U pytest-embedded pytest-embedded-serial`.","message":"File descriptor leaks can occur when using `pytest-embedded-serial` in conjunction with `pytest-lazy-fixture` in older versions of `pytest-embedded`, leading to resource exhaustion.","severity":"gotcha","affected_versions":"< pytest-embedded 2.1.2 (fixed in commit #234 around Nov 2023)"},{"fix":"For performance-critical tests or scenarios requiring true parallelism, consider using Python's `multiprocessing` module instead of `threading`. The APIs are often similar.","message":"The `pytest-embedded` framework (and by extension `pytest-embedded-serial`) uses internal threading. When conducting performance tests, using Python's `threading` module might lead to performance degradation due to the Global Interpreter Lock (GIL).","severity":"gotcha","affected_versions":"All versions"}],"env_vars":null,"last_verified":"2026-04-16T00:00:00.000Z","next_check":"2026-07-15T00:00:00.000Z","problems":[{"fix":"Add your user to the appropriate group (e.g., 'dialout') and then log out and back in for the changes to take effect. On Linux: `sudo usermod -a -G dialout $USER`. Ensure the port path is correct (`/dev/ttyUSB0` or `COMx` on Windows).","cause":"The current user does not have read/write permissions for the specified serial port. This is a common issue on Linux-based systems where serial ports are owned by the 'dialout' or 'uucp' group.","error":"serial.serialutil.SerialException: [Errno 13] could not open port /dev/ttyUSB0: [Errno 13] Permission denied: '/dev/ttyUSB0'"},{"fix":"Verify the correct serial port name for your operating system (e.g., check device manager on Windows, `ls /dev/tty*` on Linux). Ensure the device is properly connected and its drivers are installed.","cause":"The specified serial port does not exist or is not connected. This could be due to an incorrect port name, a disconnected device, or a missing driver.","error":"serial.serialutil.SerialException: No such file or directory: '/dev/ttyS99'"},{"fix":"Increase the `timeout` parameter in `dut.expect()` or `dut.expect_exact()` calls. Verify the expected pattern matches the device's actual output, considering line endings or other formatting. Debug the device's firmware to ensure it sends the expected response.","cause":"The expected pattern was not received from the serial device within the allotted timeout period. This could be due to the device not responding, an incorrect expected pattern, or a too-short timeout.","error":"pexpect.exceptions.TIMEOUT: Timeout exceeded in command 'dut.expect('...')'"}]}