environmental-sensor

module
v0.0.0-...-8943c89 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 8, 2026 License: GPL-3.0

README

MCP9808 Temperature Logger

GoDoc Go Report Card

Log temperature from an MCP9808 sensor connected to a Raspberry Pi.

Send temperature to AWS IoT Core (RIP Google Cloud IoT Core, which I used before it was decommissioned 😭), which can then be saved and plotted using the web app in the web directory. Running make will build all binaries locally. Running make web-image will build a Docker image that can be deployed to Cloud Run to serve the web app.

Run the iotcorelogger binary on the Raspberry Pi:

make

# Example device.json:
# {
#   "endpoint": "endpoint-name",
#   "device_id": "my-device",
#   "cert_path": "my-device.x509",
#   "priv_key_path": "my-device.pem"
# }
./out/iotcorelogger -aws-device device.json

The device file specifies how to connect to AWS IoT Core's MQTT broker.

Prerequisites

iotcorelogger sensor and job configuration

The iotcorelogger program is told which sensors to use and the frequency at which to take measurements via a JSON job spec. A job has:

  • A cronspec
  • An operation, which must be one of "SETUP", "SENSE", or "SHUTDOWN"
  • A list of sensors

Example of a simple config that gets a measurement from an MCP9808 temperature sensor every 2 minutes:

{
  "jobs": [
    {
      "cronspec": "0 */2 * * * *",
      "operation": "SENSE",
      "sensors": ["mcp9808"]
    }
  ]
}

Example of a more complex config that gets particulate matter measurements from an SDS011 sensor every 2 minutes, but that runs setup and shutdown jobs before taking measurements.

{
  "jobs": [
    {
      "cronspec": "35 1-59/2 * * * *",
      "operation": "SETUP",
      "sensors": [
        "sds011"
      ]
    },
    {
      "cronspec": "0 0-59/2 * * * *",
      "operation": "SENSE",
      "sensors": [
        "sds011"
      ]
    },
    {
      "cronspec": "8 0-59/2 * * * *",
      "operation": "SHUTDOWN",
      "sensors": [
        "sds011"
      ]
    }
  ]
}

The device receives this config from an AWS IoT Core Device Shadow. See Device Shadow service documentation here.

When a device connects to the MQTT broker it will either create a shadow if one doesn't exist, or fetch the current desired config from the shadow. Set the desired config in the device's shadow configuration to push it to the device; the device will receive and apply the new config any time it is changed.

Setting up Google Cloud IoT Core logging

TODO(mtraver) Re-write for AWS IoT Core

Google Cloud setup

The scripts at https://github.com/mtraver/provisioning are useful for creating the CA key and cert and device-specific keys and certs described below.

  • Create an IoT Core registry. The IoT Core quickstart provides more info. The registry includes:
    • A Pub/Sub topic for telemetry (you'll need to create the topic if it doesn't already exist)
    • A Pub/Sub topic for state (you'll need to create the topic if it doesn't already exist)
    • A CA cert for verifying device certs. This can be self-signed.
  • Add devices to the registry. This requires a device-specific cert that chains to the CA cert. The key and cert can be made with the scripts in the repo linked above. Heed the information there about key handling and about the device ID (the device ID you use when making the cert must be the same as the one you set when adding the device to the registry).
  • Create a subscription to the registry's telemetry topic. Configure it to push to the /push-handlers/telemetry endpoint of the web app. This is how IoT Core is tied to the web app.

The end-to-end flow is like this:

  1. A device sends a payload (in this case a protobuf; see measurement.proto) to IoT Core.
  2. IoT Core publishes the payload as a Pub/Sub message to the registry's telemetry Pub/Sub topic.
  3. Pub/Sub pushes the message to the web app's endpoint, as configured in the subscription to the topic.
  4. The web app receives the request, decodes the payload, and writes it to the database.
Client program

The program in cmd/iotcorelogger runs on the Raspberry Pi and sends data to Google Cloud IoT Core. cmd/README has information on building and configuring iotcorelogger.

TODO(mtraver) add info on systemd config

Running and deploying the web app

Environment variables

The web app expects the following environment variables to be set. Define them in a file called .env and the make run-web command below will pick them up.

In production, you'll need to make sure that they are available to the container via env var config, secrets config, or whatever other method you like.

TODO(mtraver) add descriptions of the env vars

  • AWS_REGION
  • AWS_ROLE_ARN
  • IGNORED_DEVICES
  • INFLUXDB_BUCKET
  • INFLUXDB_ORG
  • INFLUXDB_SERVER
  • INFLUXDB_TOKEN
  • PUBSUB_AUDIENCE
  • PUBSUB_VERIFICATION_TOKEN

For local development you'll need to set GOOGLE_CLOUD_PROJECT to your GCP project ID. In production on Cloud Run it's fetched automatically.

For local development you'll also want to put a key for a service account that allows reading from Google Cloud Datastore and Google Cloud IoT Core in a dir called keys and then set the GOOGLE_APPLICATION_CREDENTIALS env var, e.g.:

GOOGLE_APPLICATION_CREDENTIALS=/keys/my-key.json

In production GOOGLE_APPLICATION_CREDENTIALS isn't necessary because the service will have the proper permissions granted to it.

Build and run locally

Did you make your .env file and put your service account key in keys? Do that first (see above).

PROJECT=my-gcp-project-id \
REPO=my-artifact-repository-repo-name \
SERVICE=my-cloud-run-service-name \
make web-image

PROJECT=my-gcp-project-id \
REPO=my-artifact-repository-repo-name \
SERVICE=my-cloud-run-service-name \
make run-web
Build on Google Cloud Build

This will build the image remotely and push it to Google Artifact Repository.

PROJECT=my-gcp-project-id \
REPO=my-artifact-repository-repo-name \
SERVICE=my-cloud-run-service-name \
make web-image-remote
Deploying to Cloud Run

Deploy the image built with make web-image-remote to Cloud Run and make sure that the env vars (aside from GOOGLE_CLOUD_PROJECT and GOOGLE_APPLICATION_CREDENTIALS) are made available to it.

Subsequent deploys can be done using this make command:

PROJECT=my-gcp-project-id \
REPO=my-artifact-repository-repo-name \
SERVICE=my-cloud-run-service-name \
make deploy-web

make deploy-web doesn't set env vars so it can't be used for the first deploy.

Directories

Path Synopsis
Package aqi computes US EPA Air Quality Index values for PM2.5 and PM10.
Package aqi computes US EPA Air Quality Index values for PM2.5 and PM10.
cmd
api command
Binary api implements the gRPC service MeasurementService.
Binary api implements the gRPC service MeasurementService.
apiclient command
Binary apiclient is a command line tool for calling the gRPC service MeasurementService.
Binary apiclient is a command line tool for calling the gRPC service MeasurementService.
csvtogcp command
iotcorelogger command
Program iotcorelogger reads from sensors and publishes the measurements to AWS IoT Core over MQTT.
Program iotcorelogger reads from sensors and publishes the measurements to AWS IoT Core over MQTT.
lambda command
Binary lambda is an AWS Lambda function that receives IoT telemetry messages and re-publishes them to Google Cloud Pub/Sub.
Binary lambda is an AWS Lambda function that receives IoT telemetry messages and re-publishes them to Google Cloud Pub/Sub.
readtemp command
Program readtemp reads the temperature from an MCP9808 sensor and prints it to stdout.
Program readtemp reads the temperature from an MCP9808 sensor and prints it to stdout.
Package measurementpbutil provides utility functions for working with the generated protobuf type Measurement.
Package measurementpbutil provides utility functions for working with the generated protobuf type Measurement.
web
db

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL