Back to Research
Diagram of the Lana modular core with REST API, Kafka, GraphQL, and RabbitMQ integrations to core banking, reporting, compliance, and external custody systems
Engineering May 7, 2026 · Tim Normark

Digital Asset Banking Built for Your Infrastructure

When we set out to build a modern core banking platform, a microservice architecture might have seemed like the natural path. We took a different one.

The system needed to support institutional-scale banking environments, with digital assets as a first-class capability.

At the time, microservices were the prevailing approach for systems that needed flexibility and scale.

But the constraints of this domain pointed in a different direction.

Our system needed to:

Integrate into infrastructure already in place at the institutions using it

Remain straightforward and safe to operate, where complexity directly translates into cost and risk

Support financial operations where accuracy and consistency are critical

Those constraints changed the problem.

We built Lana as a modular monolith: a single system with strong internal boundaries. Here’s why.

Simplicity

Operational simplicity is part of the product

The first constraint was operational simplicity and safety.

How do we ensure that operating the system remains simple and safe for the client?

If the client cannot run the system reliably, everything else becomes irrelevant.

Every additional service becomes another component the client has to deploy, monitor, and support.

Lana runs as one coherent system by default. Deployment, monitoring, and recovery are handled as one unit. There is no internally distributed application topology to coordinate across separately deployed services.

This keeps the system straightforward to operate, even in large institutional environments, and reduces the long-term operational burden for the client.

But operational simplicity should not come at the expense of scaling flexibility.

Strong module boundaries still preserve flexibility in how the system is deployed and scaled. Specific workloads, such as background processing and asynchronous jobs, can be separated when scale or operational demands justify it.

Unlike a microservice architecture, distributed deployment complexity is introduced selectively where it provides clear value, rather than becoming the default from the start.

Integration

Integration on the client’s terms

The second constraint was integration.

How do we ensure that the system fits into the client’s existing environment, rather than forcing a specific architecture?

Integration requirements vary. Some clients operate event-driven systems. Others rely on synchronous APIs. Many use both.

Because Lana runs as a single system, it does not depend on an internal integration model between services. No broker or communication pattern is imposed by the architecture.

This allows integration to be defined at the system boundary.

Capabilities can be exposed through event streams such as Kafka or RabbitMQ, or through REST APIs, depending on what fits the client’s environment.

The integration model stays flexible. The delivery mechanism adapts to the client’s infrastructure.

Diagram of Lana surrounded by external systems — core banking, compliance, ACH, custody, CRM, data warehouse, and reporting — connected via REST API, GraphQL, SFTP, webhooks, gRPC, Kafka, and RabbitMQ Consistency

Ensuring consistent financial operations

The third constraint was consistency.

How do we ensure that ledgers and customer balances remain correct, even as operations span multiple domains?

If ledgers and balances are not correct, the system is not usable.

Core banking operations involve customer state, product rules, approvals, accounting, controls, and audit. These flows need predictable behavior. Some require atomic execution across multiple modules.

Splitting these operations across multiple services often turns a single business operation into a distributed workflow spanning several components.

In Lana, operations that require strong consistency can execute within a single transaction across carefully defined boundaries when appropriate. They either succeed fully or fail as a whole.

This avoids large amounts of compensating workflow logic and keeps complexity where it belongs: in the business logic.

Side-by-side comparison: a single atomic operation across Approvals, Ledger, Accounts, and Audit modules within Lana, versus a distributed orchestration of separate services requiring retries and compensations Modularity

Modularity that supports real product needs

The fourth constraint was modularity that holds over time.

How do we ensure that the system can adapt to different product needs without becoming tangled over time?

Different clients require different capabilities. Some need custody, while others rely on external providers. Product scope varies, and it changes over time.

In Lana, modules are real architectural units with controlled relationships and explicit contracts. These boundaries are enforced by the compiler.

Dependency direction is defined. Cycles are prevented. Public contracts, including events, are validated at compile time. Violations fail immediately.

The same level of modularity can be achieved with microservices, but it requires substantially more coordination between services and teams.

In Lana, these guarantees are part of the system itself.

This allows capabilities to be included or left out without hidden coupling. The platform can be configured to match the client’s product scope without accumulating unintended dependencies.

Evolution

Fast and safe system evolution

The final constraint was change over time.

How do we evolve the system without turning every change into a multi-step rollout across components?

Changes often span multiple domains. A new approval step affects validation, accounting, audit, and APIs.

In many systems, this requires careful sequencing across services and managing compatibility during rollout.

In Lana, it remains a single change.

The full flow is updated, tested end-to-end, and deployed as a unit. There is no cross-service coordination, no version compatibility to manage, and no partial rollout risk.

A single codebase allows system-wide changes to be made and verified together.

This also enables more effective AI-driven development workflows. Engineers and AI agents can reason about the system as a whole, follow execution paths across modules, and safely apply changes without having to manage as much context and complexity at once.

This reduces the cost of change and increases confidence in every release.

Side-by-side comparison: a new approval rule applied as a single coordinated change across Lana's modules, versus a fragmented rollout where validation, accounting, audit, and API services drift across versions and pending updates Conclusion

Why this architecture fits Lana

Microservices are effective in environments with very large teams or strict service ownership boundaries.

Lana is built for institutional-scale banking environments and client-controlled infrastructure.

It is designed for financial operations that span multiple domains, where predictable behavior, integration flexibility, and operational simplicity are critical.

What this enables

1

Operational simplicity for real deployments: one coherent system to deploy and operate in client-controlled environments.

2

Flexible integration into existing infrastructure: works with Kafka, RabbitMQ, or REST-based integrations without imposing a specific internal architecture.

3

Consistent financial operations: critical flows remain predictable instead of becoming distributed workflows across multiple components.

4

Configurable capability boundaries with enforceable guarantees: capabilities can be included or left out without hidden coupling, enforced through explicit module boundaries.

5

Fast and safe system evolution: system-wide changes can be developed, verified, and deployed with lower coordination overhead and reduced cognitive complexity.

Resources

Further reading:

Shopify’s architecture: Deconstructing the monolith

A real-world example of a large-scale system that focused on strong internal boundaries within a monolith instead of distributing complexity across services.

Microservices

Martin Fowler’s overview of microservices, including the challenges of defining boundaries, maintaining consistency across services, and managing the operational complexity of distributed systems.

Microservices on-premises is an epic mismatch

Dejan Glozic’s perspective on why microservices are often poorly suited for software deployed into client-controlled environments, where operational complexity becomes the client’s responsibility.

Stay Updated

Subscribe to the Bitcoin Banking Standard for monthly insights on Bitcoin banking trends and regulatory developments.