MH-Z19B not work with Mycodo Python but works with

TLDR; MHZ19B not working. Orange laser light shows up (blinks). UedaTakeyuki/mh-z19 library reads data just fine. Mycodo library errors.

Pi Zero W - sigh, equipment hard to find

The MH-Z19B is connected directly to the Pi as follows:

Red (VIN) connected to 5V on Pi
Black (GND) connected to GND on Pi
Blue (RX) connected to TXD on Pi
Green (TX) connected to RXD on Pi

Reviewed: MH-Z19B Wiring Sanity Check
Disabled Bluetooth and uninstalled Py libraries
/boot/config.txt:

# Disable Bluetooth
dtoverlay=disable-bt
[all]
enable_uart=1

Read the several discussions on this topic before which has led to several troubleshooting methods.

FYI, I am a software engineer so have been through the python code to troubleshoot.

If I configure the port as /dev/serial0 the following errors are generated:
Jun 09 10:54:21 raspberrypi python[327]: 2023-06-09 10:54:21,997 get_measurement() found
Jun 09 10:54:22 raspberrypi python[327]: 2023-06-09 10:54:22,006 listener() not found
Jun 09 10:54:22 raspberrypi python[327]: 2023-06-09 10:54:22,003 Input controller with ID 6a3d18a1-c77a-421b-8a71-8be78a91bf88 activated.
Jun 09 10:54:22 raspberrypi python[327]: 2023-06-09 10:54:22,012 Activated in 3178.4 ms
Jun 09 10:54:23 raspberrypi python[327]: 2023-06-09 10:54:23,046 No response
Jun 09 10:54:23 raspberrypi python[327]: 2023-06-09 10:54:23,270 Adding measurements to InfluxDB with ID 6a3d18a1-c77a-421b-8a71-8be78a91bf88: {}

ls -la /dev/ser*
lrwxrwxrwx 1 root tty 7 Jun 9 10:22 /dev/serial0 → ttyAMA0
lrwxrwxrwx 1 root root 5 Jun 9 10:22 /dev/serial1 → ttyS0

Configured with /dev/ttyS0

Jun 09 10:59:25 raspberrypi python[327]: 2023-06-09 10:59:25,310 Opening serial
Jun 09 10:59:25 raspberrypi python[327]: Traceback (most recent call last):
Jun 09 10:59:25 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialposix.py”, line 398, in _reconfigure_port
Jun 09 10:59:25 raspberrypi python[327]: orig_attr = termios.tcgetattr(self.fd)
Jun 09 10:59:25 raspberrypi python[327]: termios.error: (5, ‘Input/output error’)
Jun 09 10:59:25 raspberrypi python[327]: During handling of the above exception, another exception occurred:
Jun 09 10:59:25 raspberrypi python[327]: Traceback (most recent call last):
Jun 09 10:59:25 raspberrypi python[327]: File “/home/tledwar/Mycodo/mycodo/inputs/mh_z19b.py”, line 139, in initialize
Jun 09 10:59:25 raspberrypi python[327]: self.ser = serial.Serial(
Jun 09 10:59:25 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialutil.py”, line 244, in init
Jun 09 10:59:25 raspberrypi python[327]: self.open()
Jun 09 10:59:25 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialposix.py”, line 332, in open
Jun 09 10:59:25 raspberrypi python[327]: self._reconfigure_port(force_update=True)
Jun 09 10:59:25 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialposix.py”, line 401, in _reconfigure_port
Jun 09 10:59:25 raspberrypi python[327]: raise SerialException(“Could not configure port: {}”.format(msg))
Jun 09 10:59:25 raspberrypi python[327]: serial.serialutil.SerialException: Could not configure port: (5, ‘Input/output error’)
Jun 09 10:59:25 raspberrypi python[327]: 2023-06-09 10:59:25,330 Error initializing, trying again in 5 seconds: ‘NoneType’ object has no attribute ‘write’
Jun 09 10:59:25 raspberrypi python[327]: Traceback (most recent call last):
Jun 09 10:59:25 raspberrypi python[327]: File “/var/mycodo-root/mycodo/abstract_base_controller.py”, line 57, in try_initialize
Jun 09 10:59:25 raspberrypi python[327]: self.initialize()
Jun 09 10:59:25 raspberrypi python[327]: File “/home/tledwar/Mycodo/mycodo/inputs/mh_z19b.py”, line 153, in initialize
Jun 09 10:59:25 raspberrypi python[327]: self.abcoff()
Jun 09 10:59:25 raspberrypi python[327]: File “/home/tledwar/Mycodo/mycodo/inputs/mh_z19b.py”, line 201, in abcoff
Jun 09 10:59:25 raspberrypi python[327]: self.ser.write(bytearray([0xff, 0x01, 0x79, 0x00, 0x00, 0x00, 0x00, 0x00, 0x86]))
Jun 09 10:59:25 raspberrypi python[327]: AttributeError: ‘NoneType’ object has no attribute ‘write’
Jun 09 10:59:30 raspberrypi python[327]: 2023-06-09 10:59:30,345 Opening serial
Jun 09 10:59:30 raspberrypi python[327]: Traceback (most recent call last):
Jun 09 10:59:30 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialposix.py”, line 398, in _reconfigure_port
Jun 09 10:59:30 raspberrypi python[327]: orig_attr = termios.tcgetattr(self.fd)
Jun 09 10:59:30 raspberrypi python[327]: termios.error: (5, ‘Input/output error’)
Jun 09 10:59:30 raspberrypi python[327]: During handling of the above exception, another exception occurred:
Jun 09 10:59:30 raspberrypi python[327]: Traceback (most recent call last):
Jun 09 10:59:30 raspberrypi python[327]: File “/home/tledwar/Mycodo/mycodo/inputs/mh_z19b.py”, line 139, in initialize
Jun 09 10:59:30 raspberrypi python[327]: self.ser = serial.Serial(
Jun 09 10:59:30 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialutil.py”, line 244, in init
Jun 09 10:59:30 raspberrypi python[327]: self.open()
Jun 09 10:59:30 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialposix.py”, line 332, in open
Jun 09 10:59:30 raspberrypi python[327]: self._reconfigure_port(force_update=True)
Jun 09 10:59:30 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialposix.py”, line 401, in _reconfigure_port
Jun 09 10:59:30 raspberrypi python[327]: raise SerialException(“Could not configure port: {}”.format(msg))
Jun 09 10:59:30 raspberrypi python[327]: serial.serialutil.SerialException: Could not configure port: (5, ‘Input/output error’)
Jun 09 10:59:30 raspberrypi python[327]: 2023-06-09 10:59:30,372 Error initializing, trying again in 5 seconds: ‘NoneType’ object has no attribute ‘write’
Jun 09 10:59:30 raspberrypi python[327]: Traceback (most recent call last):
Jun 09 10:59:30 raspberrypi python[327]: File “/var/mycodo-root/mycodo/abstract_base_controller.py”, line 57, in try_initialize
Jun 09 10:59:30 raspberrypi python[327]: self.initialize()
Jun 09 10:59:30 raspberrypi python[327]: File “/home/tledwar/Mycodo/mycodo/inputs/mh_z19b.py”, line 153, in initialize
Jun 09 10:59:30 raspberrypi python[327]: self.abcoff()
Jun 09 10:59:30 raspberrypi python[327]: File “/home/tledwar/Mycodo/mycodo/inputs/mh_z19b.py”, line 201, in abcoff
Jun 09 10:59:30 raspberrypi python[327]: self.ser.write(bytearray([0xff, 0x01, 0x79, 0x00, 0x00, 0x00, 0x00, 0x00, 0x86]))
Jun 09 10:59:30 raspberrypi python[327]: AttributeError: ‘NoneType’ object has no attribute ‘write’

Jun 09 10:59:35 raspberrypi python[327]: 2023-06-09 10:59:35,388 Opening serial
Jun 09 10:59:35 raspberrypi python[327]: Traceback (most recent call last):
Jun 09 10:59:35 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialposix.py”, line 398, in _reconfigure_port
Jun 09 10:59:35 raspberrypi python[327]: orig_attr = termios.tcgetattr(self.fd)
Jun 09 10:59:35 raspberrypi python[327]: termios.error: (5, ‘Input/output error’)
Jun 09 10:59:35 raspberrypi python[327]: During handling of the above exception, another exception occurred:
Jun 09 10:59:35 raspberrypi python[327]: Traceback (most recent call last):
Jun 09 10:59:35 raspberrypi python[327]: File “/home/tledwar/Mycodo/mycodo/inputs/mh_z19b.py”, line 139, in initialize
Jun 09 10:59:35 raspberrypi python[327]: self.ser = serial.Serial(
Jun 09 10:59:35 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialutil.py”, line 244, in init
Jun 09 10:59:35 raspberrypi python[327]: self.open()
Jun 09 10:59:35 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialposix.py”, line 332, in open
Jun 09 10:59:35 raspberrypi python[327]: self._reconfigure_port(force_update=True)
Jun 09 10:59:35 raspberrypi python[327]: File “/var/mycodo-root/env/lib/python3.9/site-packages/serial/serialposix.py”, line 401, in _reconfigure_port
Jun 09 10:59:35 raspberrypi python[327]: raise SerialException(“Could not configure port: {}”.format(msg))
Jun 09 10:59:35 raspberrypi python[327]: serial.serialutil.SerialException: Could not configure port: (5, ‘Input/output error’)
Jun 09 10:59:35 raspberrypi python[327]: 2023-06-09 10:59:35,420 Initialization errored 3 times; giving up. Maybe the following traceback can help diagnose the issue.
Jun 09 10:59:35 raspberrypi python[327]: Traceback (most recent call last):
Jun 09 10:59:35 raspberrypi python[327]: File “/var/mycodo-root/mycodo/abstract_base_controller.py”, line 57, in try_initialize
Jun 09 10:59:35 raspberrypi python[327]: self.initialize()
Jun 09 10:59:35 raspberrypi python[327]: File “/home/tledwar/Mycodo/mycodo/inputs/mh_z19b.py”, line 153, in initialize
Jun 09 10:59:35 raspberrypi python[327]: self.abcoff()
Jun 09 10:59:35 raspberrypi python[327]: File “/home/tledwar/Mycodo/mycodo/inputs/mh_z19b.py”, line 201, in abcoff
Jun 09 10:59:35 raspberrypi python[327]: self.ser.write(bytearray([0xff, 0x01, 0x79, 0x00, 0x00, 0x00, 0x00, 0x00, 0x86]))
Jun 09 10:59:35 raspberrypi python[327]: AttributeError: ‘NoneType’ object has no attribute ‘write’
Jun 09 10:59:35 raspberrypi python[327]: 2023-06-09 10:59:35,458 get_measurement() found
Jun 09 10:59:35 raspberrypi python[327]: 2023-06-09 10:59:35,459 Input controller with ID 6a3d18a1-c77a-421b-8a71-8be78a91bf88 activated.
Jun 09 10:59:35 raspberrypi python[327]: 2023-06-09 10:59:35,464 listener() not found
Jun 09 10:59:35 raspberrypi python[327]: 2023-06-09 10:59:35,511 Activated in 12692.9 ms
Jun 09 10:59:35 raspberrypi python[327]: 2023-06-09 10:59:35,540 Error 101: Device not set up. See Error Codes - Mycodo for more info.

ls -la /dev/ttyS0
crw-rw---- 1 root dialout 4, 64 Jun 9 10:22 /dev/ttyS0

UedaTakeyuki library:
sudo python3 -m mh_z19
{“co2”: 931}

Data was received.

Reviewing UedaTakeyuki code:
if os.path.exists(‘/dev/serial0’):
partial_serial_dev = ‘serial0’
elif pimodel == “3 Model B” or pimodel == “4 Model B” or pimodel_strict == “Zero W”:
partial_serial_dev = ‘ttyS0’
else:
partial_serial_dev = ‘ttyAMA0’

So this confirms that ttyS0 was used in his library by default.

Checked their Serial call:

def connect_serial():
return serial.Serial(serial_dev,
baudrate=9600,
bytesize=serial.EIGHTBITS,
parity=serial.PARITY_NONE,
stopbits=serial.STOPBITS_ONE,
timeout=1.0)

Using this information, I modified the Mycodo inputs/mh_z19b.py file to basically use the same call:

    if is_device(self.input_dev.uart_location):
        try:
            self.ser = serial.Serial(
                port='/dev/ttyS0',
                baudrate=9600,
                bytesize=serial.EIGHTBITS,
                parity=serial.PARITY_NONE,
                stopbits=serial.STOPBITS_ONE,
                timeout=1.0,
                writeTimeout=5)
        except serial.SerialException:
            self.logger.exception('Opening serial')

But the error remained the same.

I hear about people using a resistor between the Vin and the Tx but not sure that is needed because the non Mycodo library works fine.

Any help is greatly appreciated!

Lots of software debugging today between the third party software and the Mycodo software.

First learned that the third party software is working on serial0.

Also confirmed that to make it work the Getty serial service has to be stopped and started between calls to get measurements.

I will write up a bug report with working solutions soon.

Issue created: Cannot Connect to MH_Z19B Sensor - code fix attached · Issue #1315 · kizniche/Mycodo · GitHub

I was recently having the same log errors: Checksum, no response, traceback, etc. I tried several things like extending reading times, even bought a new one to make sure it was not the sensor. Same issues. Finally determined I had a voltage issue. Replaced my power supply with a 5V 15W power supply and that solved the problem.