Measure Electrical Conductivity in Siemens, Total Dissolved Solids in PPM, and Salinity in PSU.

An electrically isolated I2C sensor device, a waterproof temperature sensor, and an electrical conductivity probe. It measures the conductivity of a solution and converts it into Siemens (S) total dissolved solids and salinity. The firmware allows for single or dual-point calibration with temperature compensation.


  • EC range: 0.5 - 12.88 mS/cm
  • Accuracy: ± 5%
  • Temperature range: -55 - 125 C
  • Interface: I2C
  • Current use: ~10mA peak, low idle current ~1mA
  • Voltage range: 3.3 - 5.0V


I2C Connections

If you use the Qwiic connector, it is keyed and can only be inserted one way.

  • Black = GND
  • Red = 3.3/5 V
  • Blue = SDA
  • Yellow = SCL

A 2.54mm through-hole header is available and it is also castellated to allow for attached to another board. The pins are as follows:

EC Probe Interface Master device
GND Ground connection
3.3/5v 3.3 - 5 V power source

EC Probe Connections

A BNC connector is used to connect the conductivity probe to the EC Probe Interface. Ensure the connector is fully inserted and the twist-lock is fully locked.

Probe Selection

Any 2-electrode probe with a BNC connector can be used.

Temperature Probe Connections

The temperature probe comes with a 3-wire connector that can only be connected one way.

I2C Bus Pull-ups

There only needs to be one device with active pull-up resistors. Each board comes with the resistors active. Several boards can typically be connected with active resistors, however if connection problems are present, choose one board to keep the resistors active and disable to rest.

Each device comes with 4.7k resistor pullups on the I2C bus. They pass through a 3-pad solder paste jumper. The outer pads are connected to the middle pad by thin traces. To disable the pullups, use a utility knife to cut both traces. To re-enable the pullups, connect all three pads together with solder.

solder paste jumper

Getting Started

To start using the device, you need to install a library for your board/platform.

  • Arduino IDE: go to the library manager (Sketch / Include Library / Manage Libraries...) and search for Isolated EC Probe Interface.

  • PlatformIO: install the library using the library manager (PlatformIO / PlatformIO Home / Libraries) and search for Isolated EC Probe Interface.

  • search for Isolated EC Probe Interface in the Libraries section of the IDE.

  • Raspberry Pi: clone the GitHub repo. The library is located in the python/RaspberryPi directory. Have a look at the README for instructions. Be sure to read the section below for instructions.

  • Rust: Download/install/documentation for the crate

Raspberry Pi

Before you can begin, you will need to enable software I2C. The Pi's hardware I2C implementation has a clock-stretching bug that will prevent it from working reliably. For reliable communication, you need to start the I2C-GPIO system using the following commnads. From a terminal, type:

  1. sudo nano /boot/config.txt and scroll to the bottom

  2. Add dtoverlay=i2c-gpio,i2c_gpio_sda=<pin>,i2c_gpio_scl=<pin> replacing <pin> with whatever pin you'd like to use. Refer here for the pin functions, you will need to use the orange GPIO xx labels in the picture to locate the pins.

  3. ctrl + x to exit, y to save, and enter to confirm the filename.

  4. reboot

The shell Example

An interactive shell interface is provided and is a quick and easy way to get started using the device. You will find the equivalent commands in the code area below when applicable. Upload it to your device, start a serial terminal and you will get a > prompt where you can enter commands and receive a response like a terminal or REPL. It is often quicker to experiment with things this way rather than rewriting, compiling, and uploading new versions every time.

Changing the I2C Address

If needed, the I2C address can be changed programatically by calling setI2CAddress. The device will permanently change the address and continue to use it after a power reset. If you forget the new address, you will need to use an I2C bus scanner to recover it.

Class Initialization

For C++, these options are available in the begin method.

  • Raspberry Pi Python: You can optionally pass the I2C address and/or bus.
    • Default: ec = uFire_EC()
    • Custom I2C Address: ec = uFire_EC(address=0x4C)
    • I2C System Bus: ec = uFire_EC(i2c_bus=3)
    • I2C System Bus Address: ec = uFire_EC(i2c_bus=3, address=0x4C)
  • Rust: Always pass the I2C system bus, and I2C address.
    • Default: let mut ec = EcProbe::new("/dev/i2c-3", 0x3c);

If you are using a Raspberry Pi 4, it creates the I2C-GPIO device as i2c-7 rather than i2c-3 like a Raspberry Pi 3 does. So you'll need to start the class using this:

ec = uFire_EC(7)


There are two options to calibrate the device; single or dual point.

Single Point

  • only requires one point to calibrate
  • less accurate
  • accuracy decreases as the farther away you get from the calibration point

Steps to calibrate

  1. Select a calibration solution in the middle of the expected range of measurements.
  2. reset the device to remove any previous calibration data.
  3. Submerge the probe in the calibration solution. Make sure there are no air bubbles on the probe's surface.
  4. Observe the values and wait for them to stabilize.
  5. Call calibrateProbe to perform the calibration.

After, you can use getCalibrateOffset to get the calibration data the device generated. As long as there is calibration data, it will be automatically used for subsequent measurements. setCalibrateOffset can be used to set a user-selected value.

Dual Point

  • accurate over the low and high range of points
  • requires two points to calibrate

Steps to calibrate

  1. Select a calibration solution near the low and high end of expected measurements.
  2. reset the device to remove any previous calibration data.
  3. Submerge the probe in the low calibration solution. Make sure there are no air bubbles on the probe's surface.
  4. Observe the values and wait for them to stabilize.
  5. Call calibrateProbeLow to perform the calibration.
  6. Repeat steps 3 - 4 for the high solution, then calling calibrateProbeHigh.
  7. The device will automatically begin to use the calibration data once the high and low points are determined.

After calibration, the calibration data is accesible as a pair of low/high points by calling getCalibrateHighReference/getCalibrateLowReference and getCalibrateLowReading/getCalibrateHighReading.

All four points can be set directly, without the device measuring anything, by calling setDualPointCalibration.


Once the probe has been calibrated, a reading can be taken.

After the measurement is taken, the following class variables are updated:

Temperature Compensation

Conductivity naturally changes with temperature.

Temperature compensation is used to calculate what the measured conductivity would be if it were measured at a different temperature. This is just an approximation and is determined by a standard formula which is implemented in the device's firmware. By default, 25 C is the temperature all measurements are compensated to.

To set the temperature used for compensation, call setTempConstant and pass the temperature to use.

The values passed to setTempConstant will be saved and used automatically.

Measurement Time

Each EC measurement takes 750 ms for version 2 devices and 500 ms for version 3. A temperature measurement takes 750ms.

Blocking Measurement Time

The library uses delay to wait for the device to finish taking the measurement. This can be configured by called setBlocking(false);. You can then continue work in your application whiling waiting. To update all the measured values, call readData


The most common issues are with calibration:

  • if you are getting erroneous values, call reset and see if the measurements return to a more reasonable value
  • make sure your measurement solution isn't out of range of the device

More Help

If you have any questions, find a bug, or have any suggestions, go to this project's GitHub page and submit an Issue or Pull Request. Or you can send an email to