hashgraph / hashgraph/guardian

Guardian API support for stateless custom UI

Open
#5,048 2 comments 0 reactions 0 assignees View on GitHub
Dominant language
TypeScript
Stars
146
Forks
186
Avg merge
2d 15h
Merged PRs (30d)
116

Description

### Problem description
Guardian is designed as a stateful workflow engine, where tasks such as document creation, token minting, and verification occur asynchronously through background workers. The Guardian UI is tightly coupled with this stateful model, updating itself based on internal notifications and messaging services.

However, when integrating Guardian into external systems such as National Carbon Registries (NCR), a stateless custom UI is often required. These systems frequently contain functionality outside the scope of Guardian workflow policies (e.g. token transfers and retirements) and cannot rely on Guardian’s built-in UI. As a result, integrating Guardian workflows into a stateless frontend leads to several obstacles:

- Developers must wrap Guardian workflow logic with custom REST APIs
- Guardian only allows one active session per user, making it incompatible with typical multi-tab or multi-device usage
- Custom UIs must duplicate Guardian’s state-handling behavior, including syncing document updates and listening for state changes
- Data views (e.g., filtered tables) become difficult to implement, as Guardian requires multiple sequential state-altering API calls, which conflict with stateless design principles

This makes Guardian difficult to use as a backend for stateless UIs and limits its adoption in real-world systems that demand modular, stateless architectures.

#### Example conflicting scenario:

##### Overview:
- A system with a custom UI which uses Guardian workflow as a backend has a table view with filters to list data from Guardian side
- Since Guardian does not allow multiple logins/sessions for the same user, the system is allowing multiple logins through its own user management service while maintaining a single session per user with Guardian for communication

##### User behaviour:
Step 1: User “A” logs in to the system using “Device A”, navigates to the table view page, apply filters (filter set “A”) and loads data.

Step 2: User “A” logs in to the system using “Device B”, navigates to the table view page, apply different set of filters (filter set “B”) and loads data.

Step 3: User “A” refresh the page on “Device A” (with same set of filters maintained in context).

##### Expectation:
- User “A” must see different results for filter set “A” and set “B” on two devices initially
- After the refresh on Device “A”, the original data must not change

##### Actual result:
- User “A” gets different results for filter set “A” and set “B” on two devices initially
- After the refresh, the results on “Device A” is same as “Device B”

##### Reason:

To get the filtered data from Guardian, it is required to set the filters first using a single API call, and then to issue another API call to get the actual data. Because of Guardian’s stateful nature, this does not cause any issue and is handled internally.

Since this is done in two steps externally, in the initial state, the two devices see correct data in their respective tables. But, since the last filter application happened for “Device B” with filter set “B”, now the state of the Guardian has been updated for the latest filters. So, when the table data on “Device A” was refreshed, the response data contained the results for filter set “B”, which caused the filters and the response data to be incorrect in the Custom UI view.

As explained, the main reason is that the custom UI being a part of a stateless system and Guardian being a stateful system while the two systems being unable to synchronize their states correctly due to limitations to do so.

### Requirements
- Provide stateless-compatible API endpoints in Guardian that:
- Accept full request context (e.g., filter parameters) in a single call
- Avoid reliance on mutable server-side session state
- Expose document and workflow event updates through external-friendly mechanisms (e.g., webhooks or async polling APIs) to allow stateless UIs to respond to changes
- Make it possible to use Guardian workflows via external custom UIs without having to mirror Guardian’s stateful behavior or internal messaging system

### Definition of done
- Guardian provides a clear method for integrating workflows into stateless systems
- Stateless external UIs can:
- Trigger and query workflow actions in a single REST request
- Get notified of document and token state changes via registering callback functions or webhooks with Guardian
- External systems can pass an event ID with each API call made to Guardian which are processed asynchronously, so that they can be verified (in case the stateful nature cannot be changed to a full stateless implementation, so that asynchronous tasks can be verified externally for their completion)

### Acceptance criteria
- Stateless API endpoints can be used to trigger and retrieve workflow actions in a single request
- Multiple simultaneous sessions (e.g., same user in two browser tabs) do not overwrite each other's state or filters
- Document or token updates trigger notifications externally (via webhook or similar)
- Sample project or guide demonstrates integrating a Guardian workflow with a stateless custom UI
- External systems (e.g., NCR platforms) can operate their UI without needing to adopt Guardian's stateful UI framework

Contributor guide

Open the contributing guide

Research direction

Start by tracing Guardian’s existing stateful REST workflow and session APIs, along with the internal notification and messaging paths described in the issue. Define how full request context, concurrent sessions, external event notifications, and event IDs should work before identifying the affected entry points. Done means the acceptance criteria are met and a sample stateless custom UI integration is documented.

Written by the indexing model from the issue text.

Assessment

Tech stack
typescript
Domain
api, backend
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
25/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.