Reusable by design

Business logic that travels with your project.

Build a capability once, check it with the compiler, and compose it into the next application. Zelyra packages keep interfaces typed, effects visible and project setup reproducible.

Source tree: 1.2.40 Latest published stable: v1.2.40 Local-first · offline checks

Three ways to compose

Start where your project is.

A shared file, a local package or a signed source artifact: choose the reuse level that fits the team and deployment you already have.

01

Project imports

Split a growing application into readable source files. Import paths are resolved within the project and checked together with the application. import "./billing.zyl" as billing

02

Local packages

Give a reusable capability its own manifest, version, public exports and effect ceiling. Lock the source and use it through a package namespace. import "pkg:money" as money

03

Signed source packages

Publish a source artifact and a deterministic index for controlled distribution. Add or update is explicit; checking and running a locked project can stay offline. Package guide

A concrete business example

One tax rule. A result you can inspect.

The package owns the calculation; the invoice application owns the document and customer workflow. The boundary is a typed function, so each side can evolve without copying the calculation.

Package: money_rules

Keep the calculation reusable.

The function accepts exact Decimal values, declares its input contract and returns the calculated gross amount. Zelyra checks the package and its caller as one dependency graph.

Invoice appnet + rate
money_rulestyped calculation
Invoice totalgross amount

The reusable package function

Compiler-checked example
pub fn calculate_gross(net: Decimal, rate: Decimal) -> Decimal
    requires { net >= decimal("0.00") && rate >= decimal("0.00") }
    ensures { result >= net }
{
    tax = (net * rate) / decimal("100.00")
    return net + tax
}
CheckedThis function passed `zelyra check` as part of a local package, and the sample application printed 1487.5. Use `decimal("…")` for Decimal literals and ordinary assignment syntax.

The application calls the package

main.zyl
import "pkg:money" as money

fn main() {
    gross = money::calculate_gross(decimal("1250.00"), decimal("19.00"))
    print(gross)
}

From source to shared capability

A short, repeatable workflow.

Start with a local package. The manifest names the package; the application manifest declares the path and compatible version.

Create the package

Generate a small starter module without overwriting existing files.

zelyra module init packages/money --name money --version 0.1.0

Declare the dependency

Add a local path and version range to the project manifest.

[dependencies.money]
path = "packages/money"

Lock the source

Record the resolved package source so team members can reproduce the same dependency state.

zelyra package lock .

Check and inspect

Type-check the application, inspect exports and review the module dependency plan.

zelyra check main.zyl
zelyra module list main.zyl

Included in the workflow

See what you compose.

Package tooling gives teams a concrete view of source, exported symbols, effects, settings and distribution before a module becomes part of an application.

↗

Module inventory and plan

`module list` and `module plan` describe aliases, public exports, source checksums and the selected dependency graph in stable text or JSON.

✓

Compiler-checked interfaces

Only explicitly public symbols cross the package boundary. Types, imports, contracts and declared capabilities are checked by Zelyra.

⚙

Typed package settings

Describe supported settings in the manifest and configure them per application. Secret values are referenced through environment variables.

⬇

Bundle analysis

Inspect the source closure and unresolved references before packaging. Use the report to complete and validate deployment-specific configuration.

Trust you can inspect

A signature identifies a publisher key. You decide whether to trust it.

A lockfile checksum makes source changes visible. A trusted signing key authenticates the signed artifact. Neither is a substitute for reviewing code, granting application capabilities deliberately or testing the package in your own project.

Read package security details
01Review the package source and manifest before updating a lock.
02Trust publisher keys explicitly; signature verification does not execute package code.
03Keep application capabilities and database permissions under the application owner’s control.
04Use a static package index hosted by your organization when you need controlled distribution.

A growing module landscape

Package the work your teams repeat.

A module can capture a business rule, a data adapter or a reusable workflow. Keep each package focused, give it a typed public interface and compose larger applications from those parts.

Business logic

Money, billing and validation

Centralize calculations and rules that must behave consistently across invoices, offers and reports.

Data exchange

CSV, ODBC and external systems

Keep parsing, mapping and validation close to a typed interface so each application can decide how to authorize and run it.

Documents and delivery

PDF, email and exports

Compose document generation and delivery capabilities with the application’s own permissions, outbox and deployment configuration.

Turn one useful rule into a shared building block.

Start with the checked tax example, then explore the module guide and real multi-package project.

Open the example project