Skip to content

Repository files navigation

soil-telemetry-api

REST service that ingests soil moisture readings from field sensors and persists them to Postgres. TypeScript on Express, Sequelize for the data layer, Docker Compose for the runtime.

The interesting part is the layering: routes hold no logic, the controller only translates HTTP, and the service depends on a repository interface rather than Sequelize. Swapping Postgres for anything else means writing one new class and changing one line in routes/sensorRoutes.ts.

Stack

  • Node 18, TypeScript 5
  • Express 4
  • Sequelize 6 + PostgreSQL 15
  • Docker + Docker Compose

Layout

routes/        HTTP surface, wires the dependency graph
controllers/   request/response translation only
services/      business logic, depends on ISensorRepository
repositories/  ISensorRepository + Sequelize implementation
models/        Sequelize model definition
config/        database connection, Dockerfile, compose file
src/           app assembly and bootstrap

Dependencies are injected through constructors and the graph is built once in routes/sensorRoutes.ts. Nothing below the controller layer knows Express exists.

API

POST /api/sensor

{ "moisture": 42.5 }

Returns 201 with the stored row. Missing moisture returns 400, a write failure 500.

GET /api/sensor

Returns every stored reading as an array. No pagination or filtering yet.

Schema

Table sensor_data, created by sequelize.sync() on boot:

Column Type Note
id integer primary key, auto increment
moisture float not null
createdAt timestamp
updatedAt timestamp

Configuration

Read from the environment via dotenv:

Variable Purpose
POSTGRES_DB database name
POSTGRES_USER database user
POSTGRES_PASSWORD database password
PORT HTTP port, defaults to 3000

Create a .env next to the compose file. It is gitignored.

Note that config/database.ts pins the database host to db, the compose service name, so the app expects to run inside the compose network. Running it bare with npm run dev against a local Postgres means changing that host.

Running

docker compose -f config/docker-compose.yml up --build

Brings up Postgres 15 with a named volume and the API on port 3000. The container runs npm install && npm run build on start, so source changes need a restart, not a rebuild.

Without Docker:

npm install
npm run dev     # ts-node + nodemon
npm run build   # tsc to dist/
npm start       # node dist/server.js

License

ISC

About

REST service that ingests soil moisture readings from field sensors and persists them to Postgres. TypeScript, Express, Sequelize, Docker Compose.

Topics

Resources

Stars

0 stars

Watchers

1 watching

Forks

Releases

Packages

Contributors

Languages