{"id":40935331,"url":"https://github.com/gsauthof/co2mon2pg","last_synced_at":"2026-01-22T04:15:25.885Z","repository":{"id":138877153,"uuid":"606926482","full_name":"gsauthof/co2mon2pg","owner":"gsauthof","description":"Stream CO2 USB monitor data to PostgreSQL","archived":false,"fork":false,"pushed_at":"2023-03-11T13:35:27.000Z","size":7,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":3,"default_branch":"master","last_synced_at":"2024-01-26T23:37:44.763Z","etag":null,"topics":["co2","co2-measurements","co2meter-exporter","co2monitor"],"latest_commit_sha":null,"homepage":"","language":"Python","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/gsauthof.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null}},"created_at":"2023-02-27T00:00:10.000Z","updated_at":"2023-02-27T00:07:41.000Z","dependencies_parsed_at":null,"dependency_job_id":"e0d4c2a7-bc23-4bb0-9aae-d226d638440b","html_url":"https://github.com/gsauthof/co2mon2pg","commit_stats":{"total_commits":5,"total_committers":1,"mean_commits":5.0,"dds":0.0,"last_synced_commit":"dde1854d47cda32dc38963953c01ba033562d0d7"},"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/gsauthof/co2mon2pg","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsauthof%2Fco2mon2pg","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsauthof%2Fco2mon2pg/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsauthof%2Fco2mon2pg/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsauthof%2Fco2mon2pg/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/gsauthof","download_url":"https://codeload.github.com/gsauthof/co2mon2pg/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gsauthof%2Fco2mon2pg/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28653970,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-22T01:17:37.254Z","status":"online","status_checked_at":"2026-01-22T02:00:07.137Z","response_time":144,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["co2","co2-measurements","co2meter-exporter","co2monitor"],"created_at":"2026-01-22T04:15:25.433Z","updated_at":"2026-01-22T04:15:25.880Z","avatar_url":"https://github.com/gsauthof.png","language":"Python","funding_links":[],"categories":[],"sub_categories":[],"readme":"This repository contains co2mon2pg, a Python program that streams\nCO2 concentration (and temperature) readings of certain devices to a PostgreSQL\ndatabase or stdout (CSV).\n\n2023, Georg Sauthoff\n\n\n## Quickstart\n\n1. Copy `co2mon2pg.py` to `/usr/local/bin/co2mon2pg`\n2. Copy `co2mon2pq.service` to `/etc/systemd/system`\n3. Create metricsdb user\n4. systemctl daemon-reload\n5. Create metricsdb Postgres database and metrics table,\n   similar to this [schema](https://github.com/gsauthof/lorawan#table-schema)\n   (i.e. only the time, device_id and pl columns are required)\n6. Copy `99-co2mon.rules` to `/etc/udev/rules.d`\n7. Plugin CO2Mon deivce\n8. Start service `systemctl enable --now co2mon2pq`\n\nSome steps of the setup are available as an Ansible role, in this repository.\nExample usage:\n\n```\nansible-playbook -i hosts co2mon.yml --diff\n```\n\n## Grafana Integration\n\nUsing the Postgres datasource, the collected data can be\nintegrated into a Grafana panel with a query like this:\n\n```\nSELECT\n  $__timeGroupAlias(\"time\",$__interval),\n  avg((pl-\u003e'co2_ppm')::int) AS \"CO2\",\n  device_id\nFROM metrics\nWHERE\n  $__timeFilter(\"time\")\nGROUP BY 1, device_id\nORDER BY 1\n```\n\nNB: The temperature field is named `temp_C`.\n\n\n## CSV Output\n\nFor Telegraf integration (using the [execd telegraf plugin][13]), troubleshooting etc.\none can call `co2mon2pg.py` from the command line like this:\n\n```\n./co2mon2pg.py --csv\n```\n\nIn that mode it writes all readings in CSV format to stdout.\n\nExample output:\n\n```\n1677453865,1302,20.600000000000023\n1677453925,1147,20.537500000000023\n1677453986,987,20.475000000000023\n```\n\n\n## Supported Devices\n\nco2mon2pg supports certain CO2 monitor USB devices that identify as:\n\n```\nvendor_id     : 0x04d9\nproduct_id    : 0xa052\nrelease_number: 0x0200\nserial_number : 2.00\n```\n\nNB: There are older devices with release number `0x0100` and serial number\n`1.40` that obfuscate their payload ([see also][2]). See the Related Projects Section\nfor details on how to decode such payload.\n\nI tested it with the 'TFA AIRCO2NTROL MINI CO2 Monitor' (EAN 4009816027351,\n[Kat.-Nr. 31.5006.02][14], ID-NR. 31.010 180) which I bought via and from Amazon.de.\n\nThe 'TFA AIRCO2NTROL MINI CO2 Monitor' device seems to be a rebranded version of\n[ZyAura's ZGm053U][1].\n\n## Related Projects\n\n- [Reverse-Engineering a low-cost USB CO₂ monitor][3] (hackaday.io, 2015), entertaining reverse engineering journey of the release 1 device, including Wiresharking the USB traffic and transcribing the descrambling code with IDA\n- [CO2MeterHacking][4] (revspace.nl, 2014-2018), reverse engineering documentation\nof a similar device that exposes the payload over a RJ45 serial port (without obfuscation)\n- [dmage/co2mon][5] - C program that reads from release 1 and 2 devices, uses hidapi library, packaged by Fedora\n- [JsBergbau/TFACO2AirCO2ntrol_CO2Meter][6] - Python 3 script based on the hackaday findings, supports release 1 and 2 devices. A release 2 device is assumed when the checksum is valid, before applying descrambling. It directly accesses a hidraw device without using the hidapi library.\n- [vshmoylov/libholtekco2][7] - C program that supports only release 1 devices, also uses hidapi library, looks like it also runs under Windows, but comes without any makefile\n- [heinemml/CO2Meter][8] - Python 2/3 script, supports release 1 and 2 devices, detects release 2 by checking the position of the `0xd` sentinel, also uses a hidraw device, instead of using the hidapi Python package\n- [vit1251/rs-co2mon][9] - Rust program, only support release 1 devices, also uses hidapi library\n- [MiniMon][10] (sourceforge, no VCS repository) - Python program, supports release 1 and 2 devices via hidraw, similar to heinemml/CO2Meter\n\nOf the co2mon interfacing Python programs, co2mon2pg is the only\none that uses the hidapi library.\nIn contrast to many other software, co2mon2pg doesn't support\nrelease 1 devices (although adding support is straight forward).\nMore importantly, co2mon2pg's main distinguishing feature is that\nit supports writing the sensor data to a PostgreSQL database.\n\n\n## Device Documentation\n\n- [ZyAura ZG01 CO2 Module User Manual][12] (2013), NB: as of 2023,\n  ZyAura markets the ZG09 CO2 module\n- [CO2 device RS232 serial communication protocol application note AN146-RAD-0401][11] (2012)\n\n\n[1]: https://www.zyaura.com/product-detail/zgm053u/\n[2]: https://github.com/dmage/co2mon/issues/41#issuecomment-1430523844\n[3]: https://hackaday.io/project/5301/logs?sort=oldest\n[4]: https://revspace.nl/CO2MeterHacking\n[5]: https://github.com/dmage/co2mon\n[6]: https://github.com/JsBergbau/TFACO2AirCO2ntrol_CO2Meter\n[7]: https://github.com/vshmoylov/libholtekco2\n[8]: https://github.com/heinemml/CO2Meter\n[9]: https://github.com/vit1251/rs-co2mon\n[10]: https://sourceforge.net/projects/minimon/files/\n[11]: http://co2meters.com/Documentation/AppNotes/AN146-RAD-0401-serial-communication.pdf\n[12]: https://revspace.nl/images/2/2e/ZyAura_CO2_Monitor_Carbon_Dioxide_ZG01_Module_english_manual-1.pdf\n[13]: https://github.com/influxdata/telegraf/blob/master/plugins/inputs/execd/README.md\n[14]: https://www.tfa-dostmann.de/produkt/co2-monitor-airco2ntrol-3000-31-5000/\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgsauthof%2Fco2mon2pg","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgsauthof%2Fco2mon2pg","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgsauthof%2Fco2mon2pg/lists"}