I’m trying to use this breakout board for the SCD41 with an ESP32 running ESPHome, using the built in scd4x platform. While other I2C devices work, I get the message “Communication failed! Is the sensor connected?” with the SCD41. I tried the breakout with a raspberry pi and this python library and it worked without issue. I also tried everything obvious I could think of, like explicitly specifying the address or only trying to measure one parameter. After triple checking my wiring and continuity, I’m pretty stumped. Is there any reason this breakout wouldn’t be compatible with ESP32? I thought any I2C host could talk to any device.
Without config & logs nobody can help you…
esphome:
name: ada-bedroom-air-quality
esp32:
board: esp32dev
framework:
type: arduino
# Enable logging
logger:
# Enable Home Assistant API
api:
ota:
password: [redacted]
wifi:
ssid: !secret wifi_ssid
password: !secret wifi_password
# Enable fallback hotspot (captive portal) in case wifi connection fails
ap:
ssid: "Ada-Bedroom-Air-Quality"
password: [redacted]
captive_portal:
i2c:
sda: 21
scl: 22
scan: true
sensor:
- platform: scd4x
co2:
name: "Ada's Room CO2"
temperature:
name: "Ada's Room Temperature"
humidity:
name: "Ada's Room Humidity"
- platform: sgp40
name: "Ada's Room VOC"
This is the config I used, pretty much standard. Like I said originally, I tried tweaking various options here but nothing seemed to fix it. The logs are also what you’d expect, all normal except for the communication failed message. Provided here for completeness
[11:35:14][C][wifi:488]: WiFi:
[11:35:14][C][wifi:350]: Local MAC: [redacted]
[11:35:14][C][wifi:351]: SSID: [redacted]
[11:35:14][C][wifi:352]: IP Address: [redacted]
[11:35:14][C][wifi:354]: BSSID: [redacted]
[11:35:14][C][wifi:355]: Hostname: 'ada-bedroom-air-quality'
[11:35:14][C][wifi:357]: Signal strength: -63 dB ▂▄▆█
[11:35:14][C][wifi:361]: Channel: 3
[11:35:14][C][wifi:362]: Subnet: 255.255.255.0
[11:35:14][C][wifi:363]: Gateway: 192.168.0.1
[11:35:14][C][wifi:364]: DNS1: 192.168.0.1
[11:35:14][C][wifi:365]: DNS2: 0.0.0.0
[11:35:14][C][logger:233]: Logger:
[11:35:14][C][logger:234]: Level: DEBUG
[11:35:14][C][logger:235]: Log Baud Rate: 115200
[11:35:14][C][logger:236]: Hardware UART: UART0
[11:35:14][C][i2c.arduino:037]: I2C Bus:
[11:35:14][C][i2c.arduino:038]: SDA Pin: GPIO21
[11:35:14][C][i2c.arduino:039]: SCL Pin: GPIO22
[11:35:14][C][i2c.arduino:040]: Frequency: 50000 Hz
[11:35:14][C][i2c.arduino:043]: Recovery: bus successfully recovered
[11:35:14][C][scd4x:121]: scd4x:
[11:35:14][C][scd4x:122]: Address: 0x62
[11:35:14][W][scd4x:126]: Communication failed! Is the sensor connected?
[11:35:14][C][scd4x:139]: Automatic self calibration: OFF
[11:35:14][C][scd4x:144]: Ambient pressure compensation disabled
[11:35:14][C][scd4x:145]: Altitude compensation: 0m
[11:35:14][C][scd4x:147]: Temperature offset: 4.00 °C
[11:35:14][C][scd4x:148]: Update Interval: 60.0s
[11:35:14][C][scd4x:149]: CO2 'Ada's Room CO2'
[11:35:14][C][scd4x:149]: Device Class: 'carbon_dioxide'
[11:35:14][C][scd4x:149]: State Class: 'measurement'
[11:35:14][C][scd4x:149]: Unit of Measurement: 'ppm'
[11:35:14][C][scd4x:149]: Accuracy Decimals: 0
[11:35:14][C][scd4x:149]: Icon: 'mdi:molecule-co2'
[11:35:14][C][scd4x:150]: Temperature 'Ada's Room Temperature'
[11:35:14][C][scd4x:150]: Device Class: 'temperature'
[11:35:14][C][scd4x:150]: State Class: 'measurement'
[11:35:14][C][scd4x:150]: Unit of Measurement: '°C'
[11:35:14][C][scd4x:150]: Accuracy Decimals: 2
[11:35:14][C][scd4x:150]: Icon: 'mdi:thermometer'
[11:35:14][C][scd4x:151]: Humidity 'Ada's Room Humidity'
[11:35:14][C][scd4x:151]: Device Class: 'humidity'
[11:35:14][C][scd4x:151]: State Class: 'measurement'
[11:35:14][C][scd4x:151]: Unit of Measurement: '%'
[11:35:14][C][scd4x:151]: Accuracy Decimals: 2
[11:35:14][C][scd4x:151]: Icon: 'mdi:water-percent'
[11:35:15][C][sgp40:267]: SGP40:
[11:35:15][C][sgp40:268]: Address: 0x59
[11:35:15][C][sgp40:269]: store_baseline: 1
[11:35:15][C][sgp40:281]: Serial number: 54360397
[11:35:15][C][sgp40:282]: Minimum Samples: 45.000000
[11:35:15][C][sgp40:284]: Update Interval: 60.0s
[11:35:15][C][sgp40:291]: Compensation: No source configured
[11:35:15][C][captive_portal:144]: Captive Portal:
[11:35:15][C][ota:082]: Over-The-Air Updates:
[11:35:15][C][ota:083]: Address: ada-bedroom-air-quality.local:3232
[11:35:15][C][ota:086]: Using Password.
[11:35:15][C][api:134]: API Server:
[11:35:15][C][api:135]: Address: ada-bedroom-air-quality.local:6053
[11:35:15][C][api:139]: Using noise encryption: NO
[11:35:15][C][mdns:084]: mDNS:
[11:35:15][C][mdns:085]: Hostname: ada-bedroom-air-quality
The SGP40 works without issue, it’s only the SCD41 module I’m having issues with. Like I said, it works fine with a pi.
I’m missing the log part with the results of the i2c scan something like:
[13:52:12][I][i2c.arduino:054]: Results from i2c bus scan:
[13:52:12][I][i2c.arduino:060]: Found i2c device at address 0x3C
And how did you connect the sensor to the ESP?
The problem seems to have resolved itself. I think there may be an issue with the board I was using, I connected the sensors to an identical esp32 devboard and the SCD41 jumped to life. Alternatively, maybe there was a bad connection I inadvertently fixed in the process, although I could have sworn I checked every connection. Thanks anyway for your time @jsuanet. In case anyone in the future is googling, this setup is now working fine using the provided config and no additional pull up resistors in the circuit.
Same issue with VERY_VERBOSE logs
INFO Successfully compiled program.
INFO Resolving IP address of scd43-basement.local
INFO -> 192.168.1.82
INFO Uploading .esphome/build/scd43-basement/.pioenvs/scd43-basement/firmware.bin (830848 bytes)
Uploading: [============================================================] 100% Done...
INFO Waiting for result...
INFO OTA successful
INFO Successfully uploaded program.
INFO Starting log output from scd43-basement.local using esphome API
INFO Successfully connected to scd43-basement.local
[20:21:17][I][app:102]: ESPHome version 2022.6.3 compiled on Aug 16 2022, 20:20:00
[20:21:17][C][wifi:491]: WiFi:
[20:21:17][C][wifi:353]: Local MAC: 84:F7:03:5F:CE:A0
[20:21:17][C][wifi:354]: SSID: 'ATT8GlU9XN'
[20:21:17][C][wifi:355]: IP Address: 192.168.1.82
[20:21:17][C][wifi:357]: BSSID: F8:2C:18:8E:FA:B5
[20:21:17][C][wifi:358]: Hostname: 'scd43-basement'
[20:21:17][C][wifi:360]: Signal strength: -43 dB ▂▄▆█
[20:21:17][V][wifi:362]: Priority: 0.0
[20:21:17][C][wifi:364]: Channel: 11
[20:21:17][C][wifi:365]: Subnet: 255.255.255.0
[20:21:17][C][wifi:366]: Gateway: 192.168.1.254
[20:21:17][C][wifi:367]: DNS1: 192.168.1.254
[20:21:17][C][wifi:368]: DNS2: 0.0.0.0
[20:21:18][C][logger:275]: Logger:
[20:21:18][C][logger:276]: Level: VERY_VERBOSE
[20:21:18][C][logger:277]: Log Baud Rate: 115200
[20:21:18][C][logger:278]: Hardware UART: UART0
[20:21:18][C][i2c.idf:047]: I2C Bus:
[20:21:18][C][i2c.idf:048]: SDA Pin: GPIO1
[20:21:18][C][i2c.idf:049]: SCL Pin: GPIO0
[20:21:18][C][i2c.idf:050]: Frequency: 50000 Hz
[20:21:18][C][i2c.idf:053]: Recovery: bus successfully recovered
[20:21:18][I][i2c.idf:063]: Results from i2c bus scan:
[20:21:18][I][i2c.idf:069]: Found i2c device at address 0x62
[20:21:18][C][scd4x:094]: scd4x:
[20:21:18][C][scd4x:095]: Address: 0x62
[20:21:18][W][scd4x:105]: Unable to read sensor firmware version
[20:21:18][C][scd4x:112]: Automatic self calibration: ON
[20:21:18][C][scd4x:121]: Ambient pressure compensation disabled
[20:21:18][C][scd4x:122]: Altitude compensation: 0m
[20:21:18][C][scd4x:127]: Measurement mode: periodic (5s)
[20:21:18][C][scd4x:139]: Temperature offset: 4.00 °C
[20:21:18][C][scd4x:140]: Update Interval: 60.0s
[20:21:18][C][scd4x:141]: CO2 'scd43 CO2'
[20:21:18][C][scd4x:141]: Device Class: 'carbon_dioxide'
[20:21:18][C][scd4x:141]: State Class: 'measurement'
[20:21:18][C][scd4x:141]: Unit of Measurement: 'ppm'
[20:21:18][C][scd4x:141]: Accuracy Decimals: 0
[20:21:18][C][scd4x:141]: Icon: 'mdi:molecule-co2'
[20:21:18][C][scd4x:142]: Temperature 'scd43 Temperature'
[20:21:18][C][scd4x:142]: Device Class: 'temperature'
[20:21:18][C][scd4x:142]: State Class: 'measurement'
[20:21:18][C][scd4x:142]: Unit of Measurement: '°C'
[20:21:18][C][scd4x:142]: Accuracy Decimals: 2
[20:21:18][C][scd4x:142]: Icon: 'mdi:thermometer'
[20:21:18][C][scd4x:143]: Humidity 'scd43 Humidity'
[20:21:18][C][scd4x:143]: Device Class: 'humidity'
[20:21:18][C][scd4x:143]: State Class: 'measurement'
[20:21:18][C][scd4x:143]: Unit of Measurement: '%'
[20:21:18][C][scd4x:143]: Accuracy Decimals: 2
[20:21:18][C][scd4x:143]: Icon: 'mdi:water-percent'
[20:21:18][C][mdns:084]: mDNS:
[20:21:18][C][mdns:085]: Hostname: scd43-basement
[20:21:18][V][mdns:086]: Services:
[20:21:18][V][mdns:088]: - _esphomelib, _tcp, 6053
[20:21:18][V][mdns:090]: TXT: version = 2022.6.3
[20:21:18][V][mdns:090]: TXT: mac = 84f7035fcea0
[20:21:18][V][mdns:090]: TXT: platform = ESP32
[20:21:18][V][mdns:090]: TXT: board = esp32-c3-devkitm-1
[20:21:18][C][ota:085]: Over-The-Air Updates:
[20:21:18][C][ota:086]: Address: scd43-basement.local:3232
[20:21:18][C][ota:089]: Using Password.
[20:21:18][C][api:138]: API Server:
[20:21:18][C][api:139]: Address: scd43-basement.local:6053
[20:21:18][C][api:141]: Using noise encryption: YES
[20:21:20][D][api:102]: Accepted ::FFFF:192.168.1.91
[20:21:20][VV][api.socket:693]: ::FFFF:192.168.1.91: Handshake complete!
[20:21:20][VV][api.service:337]: on_hello_request: HelloRequest {
client_info: 'Home Assistant 2022.8.1'
}
[20:21:20][V][api.connection:843]: Hello from client: 'Home Assistant 2022.8.1 (::FFFF:192.168.1.91)'
[20:21:20][VV][api.service:013]: send_hello_response: HelloResponse {
api_version_major: 1
api_version_minor: 6
server_info: 'scd43-basement (esphome v2022.6.3)'
name: 'scd43-basement'
}
[20:21:20][VV][api.service:346]: on_connect_request: ConnectRequest {
password: ''
}
[20:21:20][D][api.connection:861]: Home Assistant 2022.8.1 (::FFFF:192.168.1.91): Connected successfully
[20:21:20][VV][api.service:019]: send_connect_response: ConnectResponse {
invalid_password: NO
}
[20:21:20][VV][api.service:391]: on_device_info_request: DeviceInfoRequest {}
[20:21:20][VV][api.service:049]: send_device_info_response: DeviceInfoResponse {
uses_password: NO
name: 'scd43-basement'
mac_address: '84:F7:03:5F:CE:A0'
esphome_version: '2022.6.3'
compilation_time: 'Aug 16 2022, 20:20:00'
model: 'esp32-c3-devkitm-1'
has_deep_sleep: NO
project_name: ''
project_version: ''
webserver_port: 0
}
[20:21:20][VV][api.service:400]: on_list_entities_request: ListEntitiesRequest {}
[20:21:20][VV][api.service:132]: send_list_entities_sensor_response: ListEntitiesSensorResponse {
object_id: 'scd43_co2'
key: 3367911371
name: 'scd43 CO2'
unique_id: 'scd43-basementsensorscd43_co2'
icon: 'mdi:molecule-co2'
unit_of_measurement: 'ppm'
accuracy_decimals: 0
force_update: NO
device_class: 'carbon_dioxide'
state_class: STATE_CLASS_MEASUREMENT
legacy_last_reset_type: LAST_RESET_NONE
disabled_by_default: NO
entity_category: ENTITY_CATEGORY_NONE
}
[20:21:20][VV][api.service:132]: send_list_entities_sensor_response: ListEntitiesSensorResponse {
object_id: 'scd43_temperature'
key: 2337085905
name: 'scd43 Temperature'
unique_id: 'scd43-basementsensorscd43_temperature'
icon: 'mdi:thermometer'
unit_of_measurement: '°C'
accuracy_decimals: 2
force_update: NO
device_class: 'temperature'
state_class: STATE_CLASS_MEASUREMENT
legacy_last_reset_type: LAST_RESET_NONE
disabled_by_default: NO
entity_category: ENTITY_CATEGORY_NONE
}
[20:21:20][VV][api.service:132]: send_list_entities_sensor_response: ListEntitiesSensorResponse {
object_id: 'scd43_humidity'
key: 1595359302
name: 'scd43 Humidity'
unique_id: 'scd43-basementsensorscd43_humidity'
icon: 'mdi:water-percent'
unit_of_measurement: '%'
accuracy_decimals: 2
force_update: NO
device_class: 'humidity'
state_class: STATE_CLASS_MEASUREMENT
legacy_last_reset_type: LAST_RESET_NONE
disabled_by_default: NO
entity_category: ENTITY_CATEGORY_NONE
}
[20:21:20][VV][api.service:306]: send_list_entities_button_response: ListEntitiesButtonResponse {
object_id: 'scd41_factory_reset'
key: 2736634639
name: 'scd41 factory reset'
unique_id: 'scd43-basementbuttonscd41_factory_reset'
icon: ''
disabled_by_default: NO
entity_category: ENTITY_CATEGORY_NONE
device_class: ''
}
[20:21:20][VV][api.service:055]: send_list_entities_done_response: ListEntitiesDoneResponse {}
[20:21:20][VV][api.service:409]: on_subscribe_states_request: SubscribeStatesRequest {}
[20:21:20][VV][api.service:471]: on_subscribe_homeassistant_services_request: SubscribeHomeassistantServicesRequest {}
[20:21:20][VV][api.service:140]: send_sensor_state_response: SensorStateResponse {
key: 3367911371
state: nan
missing_state: YES
}
[20:21:20][VV][api.service:498]: on_subscribe_home_assistant_states_request: SubscribeHomeAssistantStatesRequest {}
[20:21:20][VV][api.service:140]: send_sensor_state_response: SensorStateResponse {
key: 2337085905
state: nan
missing_state: YES
}
[20:21:20][VV][api.service:140]: send_sensor_state_response: SensorStateResponse {
key: 1595359302
state: nan
missing_state: YES
}
When I try to factory reset:
[20:23:35][D][button:013]: 'scd41 factory reset' Pressed.
[20:23:35][VV][i2c.idf:164]: 0x62 TX 3F86
[20:23:36][VV][i2c.idf:204]: TX to 62 failed: timeout
[20:23:36][E][scd4x:240]: Failed to stop measurements
[20:23:36][V][component:199]: Component api took a long time for an operation (1.01 s).
[20:23:36][V][component:200]: Components should block for at most 20-30ms.
[20:23:36][VV][api.service:373]: on_ping_request: PingRequest {}
[20:23:36][VV][api.service:043]: send_ping_response: PingResponse {}
[20:23:39][VV][scheduler:196]: Running interval '' with interval=60000 last_execution=95003 (now=155004)
[20:23:49][VV][api.service:373]: on_ping_request: PingRequest {}
[20:23:49][VV][api.service:043]: send_ping_response: PingResponse {}
[20:23:51][VV][api.service:373]: on_ping_request: PingRequest {}
[20:23:51][VV][api.service:043]: send_ping_response: PingResponse {}
If you have the sensor on a 3v pin, move it over to a 5v pin. Too little power can cause issues.
Hello,
this are my parameter. It works ok. My question is:
ambient_pressure_compensation: 998 <--- is this right ? in my town wie have 1.025,1 hPa.
- platform: template
name: "Calibrate Zero (20 minutes at 400ppm)"
id: calibrate_zero
entity_category: diagnostic
on_press:
- scd4x.perform_forced_calibration:
value: 419 # outside average April 2022
id: scd41
what happen if i trigger - scd4x.perform_forced_calibration: ?
can i see the scd41 is ready with new calibration ?
captive_portal:
sensor:
- platform: scd4x
id: scd41
i2c_id: bus_a
altitude_compensation: 129m
co2:
name: co2
id: co2
humidity:
name: "Luftfeuchtigkeit"
id: humidity
temperature:
name: "Raumtemperatur"
id: temperature
temperature_offset: 0.80
automatic_self_calibration: true # der Sensor kalibriert sich automatisch selbst - dauert wochen
measurement_mode: low_power_periodic # alle 30 Sekunden wird ein Wert gemessen
ambient_pressure_compensation: 998 # Aktiviert die Kompensation gemessener CO₂-Werte basierend auf dem gegebenen Umgebungsdruck in mBar
# in 63906 = 1.022,0 h Pascal = 1,022 mbar
update_interval: 60s
# creates a button to calibrate the sensor - this will reset the zero point so use it only when it's been 20 minutes either outside
# or in a room you know the co2 level is at a minimum
button:
- platform: template
name: "Calibrate Zero (20 minutes at 400ppm)"
id: calibrate_zero
entity_category: diagnostic
on_press:
- scd4x.perform_forced_calibration:
value: 419 # outside average April 2022
id: scd41
# this will expose a switch to home assistant to turn on and off the ABC
switch:
- platform: template
name: "Reset SCL41"
id: reset_scl41
turn_on_action:
- scd4x.factory_reset: scd41
- platform: template
name: "Template Switch"
id: temp1
turn_on_action:
- switch.turn_on: cal1
turn_off_action:
- switch.turn_off: cal1
- platform: template
name: "Automatic Baseline Calibration"
id: cal1
entity_category: diagnostic
optimistic: true
on_turn_on:
- switch.turn_on: temp1
on_turn_off:
- switch.turn_off: temp1
web_server: # creates a web server where you can access all this stuff without home assistant (good for debugging or working headless (no HA))
port: 80
include_internal: true
ota: true
binary_sensor: # exposes online status
- platform: status
name: "Sensor Status"
text_sensor:
- platform: wifi_info
ip_address: # exposes the IP Address when connected
internal: true
id: wifi_ip_addr
name: "IP Address"
ssid: # exposes the SSID when connected
internal: true
id: wifi_ssid