← Back to list

MicroNotes VIII: Designing Microservices for the Edge — Lessons from Fish Farming

Notes from Sam Newman’s Microservices Workshop — Bangkok 2025

Vorrawut Judasri · 2025-12-08 02:45 · 0 claps · 6.7 min read
#microservices #software-development #software-engineering #sam-newman #services
Open on Medium ↗

MicroNotes VIII: Designing Microservices for the Edge — Lessons from Fish Farming

Notes from Sam Newman’s Microservices Workshop — Bangkok 2025

Coordination is sorted. But what if your microservices aren’t sitting in a nice data center with perfect connectivity? What if they’re out in the real world where the internet cuts out, devices are tiny, and everything is working against you?

We’ll explores a real-world scenario: designing a microservice architecture for fish farming. It’s not about fish farming. It’s about the architectural challenges that come up when you’re dealing with IoT devices, edge computing, and unreliable connectivity.

The Scenario: Fish Farming Monitoring

Imagine a company called Livestock Insights (the company’s headquarters in Scotland, actually operating all over the world). They provide software and hardware for fish farmers. Their main product, Fishy Watch, monitors the health of fish and water conditions.

Sam met someone ten years ago who worked in fish farming in Norway. They had software ten years ago that could identify sea lice on farmed salmon and would then use carefully laser-based technology to shoot the parasites off the fish. In this exercise, they’re not doing lasers because that feels far-fetched, but that technology exists now.

The setup:

  • Fish farms have multiple enclosures
  • Each enclosure has hardware devices monitoring:
  • Water quality (pH, salinity, oxygen levels, particulates)
  • Weather conditions
  • Underwater cameras (image recognition for fish size, parasite detection)
  • Customers might have multiple fish farms in different locations

Interesting features:

  • They have a feature with that camera. It’s an early feature where they can do face recognition of fish so they can track the life of individual fish. Sam’s not sure if it’s a bit of fun, but it gives them a rough idea of how big the fish are, if they’re looking healthy, and so on.
  • They’re doing things like mussel farming, for example. They don’t mean to harvest the mussels. Mussel farming is easy. Throw a rope in the water.

Requirements:

  • Dashboards to view and analyze data
  • Alerts when thresholds are reached (e.g., oxygen levels dropping)
  • Long-term data storage for trends
  • Real-time monitoring (need to know quickly when water quality is problematic)
  • Support for different types of fish

Constraints:

  • Fish farming happens on ships or coasts, not in your living room
  • Patchy cell signal in these locations
  • Devices are low-powered (less powerful than a Raspberry Pi)
  • Hardware devices already exist (you’re designing the software architecture

Future considerations:

  • They’re thinking about going more generic and doing something similar for cattle and dairy herds. There are some things they care about. Water levels are important. If you’re monitoring cattle, you need to know water levels. But there are some generic ideas there.
  • They’re thinking about using it for monitoring aquariums as well.

The Core Challenge: Unreliable Connectivity

The biggest challenge here is connectivity. You can’t assume devices always have a connection to the cloud. Cell signal is patchy. Networks go down.

Getting data from devices back to your system requires a different approach. You need patterns that handle intermittent connections.

Common Solution: Store and Forward

Most teams working on this scenario came up with a similar solution:

**store and forward.**

The pattern:

  1. Devices send data to a local broker/queue at the farm
  2. Local broker stores the data
  3. When connectivity is available, forward data to cloud broker
  4. Cloud services consume from cloud broker

Why this works:

  • If connectivity is lost, data is stored locally
  • When connectivity returns, data is forwarded
  • Devices don’t need to know about connectivity issues
  • You can prioritize what gets sent first

Two types of data:

  • Time-sensitive: alerts, critical water quality issues
  • Less time-sensitive: regular monitoring data, trends

Once you’ve got the store-and-forward pattern, the next question is:

what protocol should devices use to communicate?

Communication Protocols: MQTT for IoT

For IoT devices, MQTT is often the right choice.

Why MQTT?

  • Lightweight messaging protocol designed for IoT
  • Works well on low-powered devices
  • Can do both event-driven and request-response
  • Designed for devices that aren’t very powerful

MQTT broker bridging: You can bridge MQTT brokers. A broker at the farm connects devices locally, then forwards to a cloud-based broker when possible.

Common pattern in industrial IoT.

Then there’s another question: where should processing happen?

Local Processing vs Cloud Processing

The question is where alerting should happen.

Option 1: Cloud-based alerting

  • Alerts processed in the cloud
  • Problem: if connectivity is lost, alerts don’t work
  • Simpler architecture

Option 2: Local alerting

  • Alerts processed at the farm
  • Works even if connectivity is lost
  • More complex

Tradeoff: local intelligence = resilience but added complexity.

Mesh Networks: Handling Device Communication

Some teams considered mesh networks (like Zigbee).

The idea: devices form a peer-to-peer mesh network. If one device can reach the gateway, others can route through it.

Considerations:

  • Distance between enclosures
  • Distance from the farm to other locations
  • Different signals travel different distances

Not all data is equally important.

Data Prioritization

You might want to:

  • Prioritize critical alerts
  • Send time-sensitive data first
  • Batch less important data

Handled in the publisher or with queue priorities.

The Architecture Pattern

Common elements across teams:

  1. Edge layer: devices in enclosures
  2. Farm gateway: local broker/queue, handles store and forward
  3. Cloud layer: cloud broker, services, dashboards

Communication flow:

  • Devices → Local broker (MQTT)
  • Local broker → Cloud broker (when connected)
  • Cloud broker → Services
  • Services → Dashboards, alerts, storage

Key Architectural Decisions

1. Store and forward at the edge Don’t assume connectivity. Have local storage that forwards when possible.

2. Use appropriate protocols MQTT for IoT devices. HTTP/REST for cloud. Different protocols for different needs.

3. Consider data loss tolerance Some data can be lost, some can’t. Make tradeoffs.

4. Separate concerns Edge = data collection + local storage. Cloud = processing + analytics.

5. Handle failures gracefully Local broker filling up, devices crashing, days of downtime — plan for it.

Lessons for Microservices at the Edge

1. Connectivity is not guaranteed Intermittent connectivity is the norm.

2. Devices have constraints Choose protocols and patterns that respect these.

3. Not all data is equal Critical alerts > trend data.

4. Local processing has tradeoffs Resilience vs complexity.

5. Protocols matter MQTT for devices, HTTP/gRPC for cloud.

6. Broker bridging is useful Solid pattern for edge → cloud.

Beyond Fish Farming

Applies to:

  • Industrial IoT
  • Remote monitoring
  • Edge computing
  • Any situation with unreliable connectivity

Not about fish. It’s about real-world microservices with real-world constraints.

What to Remember

When your microservices need to work at the edge (like IoT devices, remote locations, or places with unreliable connectivity), the rules change. Here’s what matters:

Don’t assume connectivity. Devices might be offline for hours or days. You need store-and-forward patterns. Devices send data to a local broker or queue. When connectivity is available, that data gets forwarded to the cloud. If connectivity is lost, data is stored locally until it can be sent.

Use appropriate protocols. MQTT is designed for IoT devices. It’s lightweight, works on low-powered devices, and can handle both event-driven and request-response patterns. For cloud services, you might use HTTP or gRPC. Different protocols for different needs.

Prioritize data. Not all data is equally important. Critical alerts need to get through quickly. Regular monitoring data can wait. You might use different queues or priorities for different types of data.

Consider local processing. If you want alerting to work when connectivity is lost, you need intelligence at the edge. That means more complexity, but also more resilience. It’s a tradeoff.

Design for failure. Think through scenarios like connectivity being down for days, local storage filling up, or devices crashing.

The fish farming scenario isn’t really about fish. It’s about designing microservices that work in the real world, where connectivity is unreliable, devices are constrained, and you need to handle failure gracefully. These patterns apply wherever you have edge devices, IoT, or unreliable connectivity. The principles are universal.

“The edge isn’t a constraint. It’s a reality.”

Design for it, and your system will work everywhere.

***All Notes


***I: What Are Microservices? II: Forget Service Size — Focus on What Your Team Can Manage III: Microservices Aren’t About Technology — They’re About Team Autonomy IV: Nobody Cares About Your Microservices — Only the Outcome V: Information Hiding — The Discipline That Makes Microservices Work VI: Request-Response vs Event-Driven — Choosing How Services Talk VII: Distributed Transactions Are Sad — Use Sagas Instead VIII: Designing Microservices for the Edge — Lessons from Fish Farming IX: Testing Microservices — Beyond the Test Pyramid X: Migrating to Microservices — Changing the Wheels While the Car Is Moving XI: Domain-Driven Design — Speaking the Same Language XII: Breaking Apart Databases — When Data Becomes the Problem XIII: Resiliency, Observability, and the Reality of Distributed Systems



메타데이터
post_id
96dee74b2ae7
slug
micronotes-viii-designing-microservices-for-the-edge-lessons-from-fish-farming-96dee74b2ae7
url
https://medium.com/@vortj/micronotes-viii-designing-microservices-for-the-edge-lessons-from-fish-farming-96dee74b2ae7
canonical_url
https://medium.com/@vortj/micronotes-viii-designing-microservices-for-the-edge-lessons-from-fish-farming-96dee74b2ae7
author_url
https://medium.com/@vortj
status
ok
fetched_at
2026-06-12 18:14:10