Skip to content

YNU-864: Learn and protocol reconciliation#158

Open
ihsraham wants to merge 2 commits into
docs/reorg-for-v1from
feat/ynu-864-learn-protocol-reconciliation
Open

YNU-864: Learn and protocol reconciliation#158
ihsraham wants to merge 2 commits into
docs/reorg-for-v1from
feat/ynu-864-learn-protocol-reconciliation

Conversation

@ihsraham
Copy link
Copy Markdown
Collaborator

@ihsraham ihsraham commented May 19, 2026

Summary

Reconciles the Learn and Protocol docs with the current Nitrolite v1 behavior and terminology.

Changes

  • Replaces old Clearnode/Custody/dispute wording in Learn and Protocol pages with Nitronode, ChannelHub, and current channel lifecycle language.
  • Adds a no-code What Changed Since 0.5.3 Learn page before the code migration page so returning builders can learn the v1 mental model first.
  • Clarifies that v1 server-push events are not the public docs path today; Learn flow pages now describe explicit query/response confirmation.
  • Reduces escrow deposit and escrow withdrawal Learn pages to route-preserving status pages instead of builder-facing operation guides.
  • Adds Learn pages for the v1 glossary and migration from @erc7824/nitrolite@0.5.3.
  • Updates the Learn index and sidebar only enough to expose the new Learn pages.

Rationale

The Learn pages should teach the current builder path without implying unfinished escrow/migration operations are ready for public app workflows. The escrow routes stay in place to avoid broken links, but now describe current documentation status and preserve only the transition-name context readers need when they encounter protocol/API references. The Protocol updates keep the conceptual model accurate while avoiding operational instructions for paths that are not productized for docs.yellow.org yet.

The new 0.5.3 mental model page is intentionally pre-code: it explains that Clearnode is now Nitronode, Custody is now ChannelHub, old auth handshakes are legacy/compat concepts, and app code should think in home channels, app sessions, signed state, and checkpointing. It does not replace the existing code migration docs; it links readers onward when they are ready to migrate code.

Validation

  • rg -n "Clearnode|clearnode|DISPUTE|DISPUTED|ChannelUpdate|BalanceUpdate" docs/nitrolite/learn docs/nitrolite/protocol returns only intentional 0.5.3 migration/mental-model context.
  • rg -n "Submitted by|how to work with escrow|step-by-step" docs/nitrolite/learn/protocol-flows/escrow-* returns no hits.
  • rg -n "auth_request|auth_challenge|auth_verify" docs/nitrolite/learn/whats-new-from-0.5.3.mdx frames these only as legacy/compat concepts.
  • rg -n "server-push|push notification|ChannelUpdate|BalanceUpdate" docs/nitrolite/learn/whats-new-from-0.5.3.mdx does not present server-push as active v1 behavior.
  • git diff --check
  • npm run build succeeds. Existing broken-link and broken-anchor warnings remain; the follow-up Build/SDK + IA cleanup PR owns those.

Review Status

Independently re-reviewed against docs/reorg-for-v1; scope and validation match the changes above. Ready for review.

@ihsraham ihsraham requested a review from dpatsora as a code owner May 19, 2026 05:38
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented May 19, 2026

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 179e8ebe-6e7f-431d-81ee-d6e874c3260a

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/ynu-864-learn-protocol-reconciliation

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.


Transitions that map to `OPERATE` do not require on-chain checkpointing under normal operation.

Escrow and migration transition names are included for protocol accuracy. Their public app-builder workflow is not documented yet.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it is worth mentioning not only that migration and escrow are not documented, but that they are not implemented by the Nitronode, although protocol already describes them.

Comment on lines 49 to 53
## Node Liquidity and Cross-Chain Trust

Each User channel is opened with a Node. To maintain cross-chain functionality, the Node MUST hold sufficient liquidity on each supported blockchain to satisfy off-chain state allocations.
Each User channel is opened with a Node. Cross-chain functionality depends on the Node operator maintaining enough liquidity on each supported blockchain to satisfy off-chain state allocations.

When a User with home chain A transfers assets to a User with home chain B, the Node receives the amount on chain A and allocates from its own balance to the recipient on chain B. If the recipient later enforces state on chain B and the Node lacks sufficient liquidity there, on-chain enforcement will fail.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As a matter of fact, liquidity also matters for single-chain operations, because during transfer sender's funds are not returned to the node immediately, but after some lag when sender's state is enforced on-chain.
I think we should mention it here as well.

| Cooperative close | A participant submits a state with the `CLOSE` intent, signed by all participants. |
| Unilateral close | After challenge expiry, any party MAY call close without additional signatures. Funds are released according to the last enforced state's allocations. |

It is not possible to close an already `CLOSED` or `MIGRATED_OUT` channel. In both close paths, locked funds are set to zero and the channel lifecycle ends.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Generally, I think we should leave cross-chain functionality docs, because the protocol is already defined - it is the Nitronode, which does not implement the cross-chain funtionality.

Therefore, my comment applies not only to this place, but to all other cross-chain concepts that were removed from protocol section.

@philanton , @ihsraham , WDYT?

An escrow is not a separate protocol entity with its own state. It is an on-chain record derived from a channel state transition.

## Cross-Chain Deposit
:::caution Builder workflow not documented yet
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This caution and all other similar mentions in the documentation should say that escrow and migration are supported by the protocol, but not implemented by the Nitronode.


| Path | Use when |
| --- | --- |
| **Compat first** | You need the smallest migration and want familiar helper shapes while moving to the v1 package family. |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It should be explicitly mentioned here that staying with compat is NOT a long-term decision. Compat is just a step for an application to adapt to v1 quickly, but the full migration is still needed for better DX.


1. Pick compat-first or native v1.
2. Replace package imports.
3. Review amount units for every transfer, deposit, withdrawal, and app-session call.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is reviewing amounts a requirement if migrating with compat? I thought it performs the necessary formatting under the hood.

If there's an ongoing transition, the Clearnode will return a relevant error and the submission is rejected.
If there's an ongoing transition, the Nitronode will return a relevant error and the submission is rejected.

**Atomic Operations**: `escrow_deposit`, `escrow_withdrawal`, and `home-chain migration` operations are considered as one atomic operation. This means that if, for example, an escrow deposit was started with `initiate_escrow_deposit` transition, then no other states will be issued apart from `finalize_escrow_deposit`. Only after finalization can a `transfer` (or other non-`finalize_escrow_deposit` transition) be accepted by the Node.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it is better to keep the previous version (red). The new version only vaguely describes the atomicity.


| Term | Meaning |
| --- | --- |
| **App session** | An off-chain application-specific state funded from a channel through `commit` transitions and settled back through `release` transitions. |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So, "App session [is a] ... state ..."? This should be reformulated to include application specific logic, other users, collecting signatures etc.

| **Channel** | A user-node relationship for one asset, with signed state updates and an on-chain enforcement path. |
| **Channel state** | The signed record of channel version, transition, ledgers, and participant signatures. |
| **ChannelHub** | The v1 on-chain entrypoint for channel creation, deposits, withdrawals, checkpoints, challenges, and close operations. |
| **Checkpoint** | An on-chain submission that records a valid signed state without necessarily closing the channel. |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We use these terms interchangiably.

Suggested change
| **Checkpoint** | An on-chain submission that records a valid signed state without necessarily closing the channel. |
| **Checkpoint / enforcement** | An on-chain submission that records a valid signed state without necessarily closing the channel. |

| **Non-home ledger** | The secondary ledger used when a cross-chain operation is in progress. It is empty during ordinary same-chain operation. |
| **Pending state** | A Node-issued state with only the Node signature. It becomes enforceable only after the user acknowledges it. |
| **Quorum** | The signature threshold required by an app session before an app-state update is accepted. |
| **Session key** | A scoped signing key an application can use for app-session updates without asking the wallet to sign every step. |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There is a concept of a state channel session key as well, not only for an app session.

| `void` | No channel exists yet. |
| `open` | The channel exists and can accept normal state updates. |
| `challenged` | A challenge is active and the response window is running. |
| `closing` | The channel is in the close path after a final state or expired challenge. |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The channel does NOT have closing status after a challenge was expired. The status does not change after expiration - it only does after a channel was closed.

closing is only for when the Node has issued the finalization state.

# Challenge-Response & Disputes

In this guide, you will learn how Yellow Network resolves disputes and ensures your funds are always recoverable.
Challenge-response is the on-chain fallback that lets a participant enforce the latest valid channel state if the counterparty stops cooperating.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is this called "challenge-response", and not just "challenge" concept?

Comment on lines 19 to +28
## Why Challenge-Response Matters

In any off-chain system, a critical question arises: **What if someone tries to cheat?**
In any off-chain system, a critical question arises: what if someone tries to settle an old state?

<Tooltip content={tooltipDefinitions.channel}>State channels</Tooltip> solve this with a challenge-response mechanism:
<Tooltip content={tooltipDefinitions.channel}>State channels</Tooltip> answer this with versioned, signed states:

1. Anyone can submit a <Tooltip content={tooltipDefinitions.channelState}>state</Tooltip> to the blockchain
2. Counterparties have time to respond with a newer state
3. The newest valid state always wins
4. Funds are distributed according to that state

---
1. A participant submits a signed <Tooltip content={tooltipDefinitions.channelState}>state</Tooltip> on-chain.
2. The counterparty has a challenge window to respond with a newer valid state.
3. The newest valid state wins.
4. Funds are released according to the final accepted state.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually, "settle an old state" and "challenge" are unrelated.
Settling an old state is guarded by versioning system, which declines the state with a version less than or equal to an already enforced one.

Challenge, on the other hand, is useful when the other party (either user or Node) is unresponsive for a specific action, or trust was broken. In such case the channel can be closed unilaterally after the challenge period has passed and if it was not resolved by a counterparty with a newer valid state.

| Guarantee | How it is achieved |
| --- | --- |
| **Fund custody** | ChannelHub holds channel funds on-chain, not Nitronode. |
| **State validity** | Only valid signed states can advance the channel. |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
| **State validity** | Only valid signed states can advance the channel. |
| **State validity** | Only valid (singed by both states with a greater version and a correct intent) states can advance the channel. |

Comment on lines +54 to +55
3. **Response window**: a counterparty can submit a newer valid state.
4. **Resolution**: after timeout, the latest accepted state can be closed.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This sounds like if a newer state was accepted during challenge, the channel will still close, but with that latter state.
Instead, there should be a fork: "Resolved: a channel is resolved with a newer valid state, and channel lifecycle continues", or "Timed-out: if no valid state is submitted to counter-act the challenge during the specific period, the channel can be closed with the state it was challenged with".

### States are signed

With the default SimpleConsensus adjudicator, both parties must sign every state. If someone signed a state, they can't later claim they didn't agree.
The default v1 channel path requires both user and node signatures for enforceable states. A party that signed a state cannot later deny that signature.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As a matter of fact, for a state to be valid, it must be signed by both a user and the Node. Therefore, this sentence should be reformulated.

Comment on lines +90 to +93
| `checkpoint()` | Record a valid state without forcing closure. | Stays `open`. |
| `challenge()` | Start the on-chain dispute path. | Changes to `challenged`. |

Use checkpoint for safety snapshots. Use challenge when you need to force settlement.

---
Use checkpoint for safety snapshots. Use challenge when you need to force settlement because a counterparty is not cooperating.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

checkpoint(...) ChannelHub method can only be used with intent: OPERATE states. I would actually replace "checkpoint" term with "enforce" in all docs codebase, as "checkpoint" term collides with the same name ChannelHub function.
Also, there is no single function that updates the latest state on the ChannelHub - all functions are used.

| **Nitronode goes offline** | Challenge with the latest signed state, then close after timeout. |
| **You lose state history** | An older state can be defeated by a newer valid state if the counterparty has it. |
| **Counterparty submits a stale state** | Submit a newer valid state during the challenge window. |
| **Block reorg occurs** | Replay confirmed chain state from the last trusted block. |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

During the reorg, the dropped transaction is guaranteed to be included in the new chain fork soon. No need for a user to do anything.

| --- | --- |
| **Nitronode goes offline** | Challenge with the latest signed state, then close after timeout. |
| **You lose state history** | An older state can be defeated by a newer valid state if the counterparty has it. |
| **Counterparty submits a stale state** | Submit a newer valid state during the challenge window. |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we should add 2 separate cases:

Suggested change
| **Counterparty submits a stale state** | Submit a newer valid state during the challenge window. |
| **Counterparty submits a stale state** | Update the channel on-chain by submitting a the latest valid state. |
| **Counterparty challenges with a stale state** | Resolve the challenge by submitting the latest valid state during the challenge window. |

| --- | --- |
| **Challenge** | Starts on-chain dispute resolution. |
| **Response** | A newer valid state defeats an older challenged state. |
| **Timeout** | After expiry, the accepted state can be closed. |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
| **Timeout** | After expiry, the accepted state can be closed. |
| **Challenge duration** | A time during which it is possible to resolve the challenge. After it expires, the channel can be closed with the state it was challenged with. |

5. **No ongoing operation** exists for this channel (the Nitronode will deny the request otherwise).

:::note
The "no ongoing operation" requirement applies to ALL operations except `finalize_escrow_deposit`, `finalize_escrow_withdrawal`, and `finalize_migration`.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The note names finalize_escrow_deposit, finalize_escrow_withdrawal, and finalize_migration — these are RPC method names, a different layer from the transition literals (escrow_deposit, escrow_withdraw, migrate) introduced in the glossary and intent mapping. A reader coming from those new pages won't know these are the same operations at a different abstraction level. Suggest labelling them: (RPC operation names — see transition literals in the Glossary). Same issue at home-channel-withdrawal.mdx:54.


**[App Session Deposit](./protocol-flows/app-session-deposit.mdx)**: Depositing funds into app sessions.

## Migration
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The body structure here implies the reading order: Core Concepts → Protocol Flows → Migration. But the Quick Reference table at lines 72–74 places Glossary and migration pages before Protocol Flows entries. A reader using the table as a reading guide follows a different order than the section structure suggests. Given the PR's intent that the What Changed page is pre-code orientation for returning builders, the table order (migration before protocol flows) is more useful — the body section placement is the one to reconcile upward, moving Migration before Protocol Flows.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants