Foundry has moved past a single Licenses proof.
The local workspace can now present Licenses, Agreements, Open Access, Serials Management, and ILL from the same Lattice shell. Each app is selected by Loom runtime state, loaded as an independently published module-federation artifact, and routed through Envoy to the real backend or platform support surface that capability needs.
That is a different shape from a traditional FOLIO Stripes deployment. We are not rebuilding one large static UI bundle every time the application set changes. The app shell stays small and stable. The apps are separately published artifacts.
The current app suite
The first screenshot is the most important one. It shows the ILL app open, with the Lattice Apps menu expanded. The menu is not a hard-coded demo list. It is driven by the workspace runtime descriptor returned by Loom.

Lattice running ILL with the Apps menu expanded. The visible app set is assembled from the activated workspace capabilities, not from a monolithic static Stripes build.
This evening’s work made that menu more than a set of text links. FOLIO UI modules already declare their icons in package.json under stripes.icons, with matching files in the module’s icons/ directory. Foundry was not carrying that structural metadata through the wrapping path.
The fix was generic:
- the publisher reads each module’s
stripes.iconsdeclaration; - the generated wrapper copies the module’s SVG and PNG icon assets into stable artifact-relative
icons/paths; - the generated Stripes island passes those icons into
stripes.icons; - the artifact manifests record the available icons;
- operational descriptors expose app icon metadata to Loom;
- Lattice resolves the selected app icon through the same artifact origin as the remote entry.
That is why the Apps menu can show module icons before the remote application itself has loaded. It is also why the grey placeholder square in the ILL Borrow Requests header became a real ILL icon: Stripes AppIcon can now see the icon map it expected all along.
Open Access and Serials are real workspace apps
Open Access is now descriptor-mounted as an explicit optional capability. It is loaded from the published ui-oa artifact, talks to the real mod-oa backend profile, and uses the same shell/runtime contract as the other apps.

Open Access running as a Foundry workspace app. The app is not baked into Lattice; it is selected at runtime and loaded as an MFE artifact.
Serials Management follows the same pattern. The current verification covers authenticated MFE loading plus reference data and core create, read, update, and list API behavior. Orders and inventory workflows remain future optional integration work, but the local Foundry shape is now capable of presenting the Serials app itself.

Serials Management running in the same Lattice shell. Foundry is proving app composition capability without turning the shell into a module-specific bundle.
The interesting point is not that these are screenshots. The interesting point is that the screenshots are all produced by the same runtime contract:
- install the operational catalog;
- enable capabilities for the workspace;
- reconcile the workspace;
- publish routes and tenant/module setup;
- let Lattice load whatever Loom says is active.
Licenses, Agreements, Open Access, Serials Management, and ILL are different modules with different source repositories, release versions, backend services, routes, reference data, and UI assumptions. Foundry’s job is to keep those differences in descriptors, artifacts, and capability activation state rather than in the app shell.
Module federation changes the cost model
FOLIO’s traditional Stripes deployment model pushes a lot of weight into a static UI build. The set of enabled apps, module versions, branding, and deployment assumptions all tend to collapse into generated bundles. That makes small changes expensive. If a module changes, or the app set changes, the platform has to rebuild and redistribute a large composed frontend.
Foundry deliberately separates those concerns.
Lattice is the runtime shell. It knows how to ask Loom for the workspace runtime descriptor and how to load a remote module-federation entry. It does not need to know, at build time, whether a workspace will activate Licenses, Agreements, ILL, Open Access, Serials Management, or some later module profile.
The publisher is the supply chain. It wraps FOLIO UI module releases into independently published MFE artifacts. Those artifacts live under immutable release paths such as:
releases/licenses/v12.1.1/adapter-0.1.3/
releases/agreements/v12.1.1/adapter-0.1.3/
releases/open-access/v3.0.0/adapter-0.1.3/
releases/ill/v2.1.3/adapter-0.1.3/
releases/serials-management/v2.1.1/adapter-0.1.3/
Loom is the control plane. It records what is available, what a workspace has activated, and what runtime composition and routes follow from that activation.
Envoy is the data plane. It routes browser and API traffic according to the current workspace runtime state.
The result is that changing the app set is a control-plane/runtime decision. It is not a reason to rebuild the shell.
The Docker footprint matters
The other screenshot is less glamorous, but it matters just as much.

The local Docker footprint for this five-app Foundry workspace. It includes the Foundry kernel, identity, data plane, platform services, Postgres, artifact host, and the active backend modules.
To run a comparable app set through a conventional Okapi or Eureka-shaped local deployment, the container count tends to grow quickly. You need the platform runtime, identity, routing, module registry or discovery, the selected business modules, and then the supporting utility modules that those business modules expect.
Foundry is trying to keep that developer shape small enough to be ordinary.
In this local setup, the always-on kernel is:
- Lattice static artifacts;
- Loom;
- Envoy;
- Zitadel;
foundry-platform-services;- shared Postgres;
- a small artifact-host container for local static serving.
The optional business capabilities then add their real backend modules: mod-licenses, mod-agreements, mod-oa, mod-serials-management, and mod-ill.
Some FOLIO-era utility behaviour, such as settings, tags, acquisition units, and tenant interface discovery, is handled by foundry-platform-services as platform support, not by pulling in a long tail of extra utility modules just to make the UI usable. That is not a mock response hidden in the gateway. It is a deliberate platform boundary.
This is the practical point: the current five-app setup is small enough to run on a single developer laptop and still exercise real MFE loading, real auth, real routing, real tenant enablement, real reference data loading, and real module APIs.
What changed this evening
The evening’s work was mostly about turning “it loads” into a cleaner, more general app-suite experience.
The main changes were:
- ILL, Licenses, Agreements, Open Access, and Serials Management now use icon-aware
adapter-0.1.3MFE artifacts. - The publisher carries declared FOLIO module icons through wrapper generation and artifact manifests.
- The adapter passes icon maps into the Stripes runtime context.
- Loom preserves descriptor icon metadata in the workspace runtime document.
- Lattice resolves app icons through the configured artifact origin and shows them in the Apps menu.
- The Apps menu was tightened so app rows are icon plus name, without redundant
Workspace appsubtitles. - Header controls were hardened against global CSS injected by Stripes modules, so the Apps button and user menu keep their shell styling after navigation.
- Browser QA now checks route loading, launcher icons, redundant-description removal, and shell-control styling after each MFE route opens.
This is still not the end state. A production Foundry deployment needs fuller operational hardening, Kubernetes executor work, stronger identity and authorization boundaries, upgrade planning, and more domain-specific verification for optional workflows.
But it is a real milestone: Foundry can now present a multi-app FOLIO/K-Int workspace from independently published frontend artifacts, with a compact local runtime and without rebuilding a giant static Stripes bundle for every composition change.