Skip to content
Open
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
190 changes: 190 additions & 0 deletions docs/learn/advanced/managing-session-keys.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,190 @@
---
sidebar_position: 1
title: Managing Session Keys
description: Create, list, and revoke session keys with complete API examples
keywords: [session keys, authentication, API, create, revoke, manage]
---

# Managing Session Keys

This guide covers the operational details of creating, listing, and revoking session keys via the Clearnode API.

:::info Prerequisites
Before diving into session key management, make sure you understand the core concepts: what session keys are, how applications and allowances work, and the expiration rules. See **[Session Keys](../core-concepts/session-keys)** for the conceptual foundation.
:::

---

## How to Manage Session Keys

### Clearnode

#### Create and Configure

To create a session key, use the `auth_request` method during authentication. This registers the session key with its configuration:

**Request:**

```json
{
"req": [
1,
"auth_request",
{
"address": "0x1234567890abcdef...",
"session_key": "0x9876543210fedcba...",
"application": "Chess Game",
"allowances": [
{
"asset": "usdc",
"amount": "100.0"
},
{
"asset": "eth",
"amount": "0.5"
}
],
"scope": "app.create",
"expires_at": 1762417328
},
1619123456789
],
"sig": ["0x5432abcdef..."]
}
```

**Parameters:**

- `address` (required): The wallet address that owns this session key
- `session_key` (required): The address of the session key to register
- `application` (optional): Name of the application using this session key (defaults to "clearnode" if not provided)
- `allowances` (optional): Array of asset allowances specifying spending limits
- `scope` (optional): Permission scope (e.g., "app.create", "ledger.readonly"). **Note:** This feature is not yet implemented
- `expires_at` (required): Unix timestamp (in seconds) when this session key expires

:::note
When authenticating with an already registered session key, you must still fill in all fields in the request, at least with arbitrary values. This is required by the request itself, however, the values will be ignored as the system uses the session key configuration stored during initial registration. This behavior will be improved in future versions.
:::

#### List Active Session Keys

Use the `get_session_keys` method to retrieve all active (non-expired) session keys for the authenticated user:

**Request:**

```json
{
"req": [1, "get_session_keys", {}, 1619123456789],
"sig": ["0x9876fedcba..."]
}
```

**Response:**

```json
{
"res": [
1,
"get_session_keys",
{
"session_keys": [
{
"id": 1,
"session_key": "0xabcdef1234567890...",
"application": "Chess Game",
"allowances": [
{
"asset": "usdc",
"allowance": "100.0",
"used": "45.0"
},
{
"asset": "eth",
"allowance": "0.5",
"used": "0.0"
}
],
"scope": "app.create",
"expires_at": "2024-12-31T23:59:59Z",
"created_at": "2024-01-01T00:00:00Z"
}
]
},
1619123456789
],
"sig": ["0xabcd1234..."]
}
```

**Response Fields:**

- `id`: Unique identifier for the session key record
- `session_key`: The address of the session key
- `application`: Application name this session key is authorized for
- `allowances`: Array of allowances with usage tracking:
- `asset`: Symbol of the asset (e.g., "usdc", "eth")
- `allowance`: Maximum amount the session key can spend
- `used`: Amount already spent by this session key
- `scope`: Permission scope (omitted if empty)
- `expires_at`: When this session key expires (ISO 8601 format)
- `created_at`: When the session key was created (ISO 8601 format)

#### Revoke a Session Key

To immediately invalidate a session key, use the `revoke_session_key` method:

**Request:**

```json
{
"req": [
1,
"revoke_session_key",
{
"session_key": "0xabcdef1234567890..."
},
1619123456789
],
"sig": ["0x9876fedcba..."]
}
```

**Response:**

```json
{
"res": [
1,
"revoke_session_key",
{
"session_key": "0xabcdef1234567890..."
},
1619123456789
],
"sig": ["0xabcd1234..."]
}
```

**Permission Rules:**

- A wallet can revoke any of its session keys
- A session key can revoke itself
- A session key with `application: "clearnode"` can revoke other session keys belonging to the same wallet
- A non-"clearnode" session key cannot revoke other session keys (only itself)

**Important Notes:**

- Revocation is **immediate and cannot be undone**
- After revocation, any operations attempted with the revoked session key will fail with a validation error
- The revoked session key will no longer appear in the `get_session_keys` response
- Revocation is useful for security purposes when a session key may have been compromised

**Error Cases:**

- Session key does not exist, belongs to another wallet, or is expired: `"operation denied: provided address is not an active session key of this user"`
- Non-"clearnode" session key attempting to revoke another session key: `"operation denied: insufficient permissions for the active session key"`

### Nitrolite SDK

The Nitrolite SDK provides a higher-level abstraction for managing session keys. For detailed information on using session keys with the Nitrolite SDK, please refer to the SDK documentation.

8 changes: 8 additions & 0 deletions docs/learn/core-concepts/_category_.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
{
"label": "Core Concepts",
"position": 3,
"collapsible": false,
"collapsed": false
}


177 changes: 177 additions & 0 deletions docs/learn/core-concepts/app-sessions.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,177 @@
---
sidebar_position: 2
title: App Sessions
description: Multi-party application channels with custom governance and state management
keywords: [app sessions, multi-party, governance, quorum, NitroRPC]
---

# App Sessions

App sessions are off-chain channels built on top of the unified balance that enable multi-party applications with custom governance rules.

**Goal**: Understand how app sessions work for building multi-party applications.

---

## What is an App Session?

An **app session** is a temporary shared account where multiple participants can:

- Lock funds from their unified balance
- Execute application-specific logic (games, escrow, predictions)
- Redistribute funds based on outcomes
- Close and release funds back to unified balances

Think of it as a programmable escrow with custom voting rules.

---

## App Session vs Payment Channel

| Feature | Payment Channel | App Session |
|---------|-----------------|-------------|
| **Participants** | Always 2 | 2 or more |
| **Governance** | Both must sign | Quorum-based |
| **Fund source** | On-chain deposit | Unified balance |
| **Mid-session changes** | Via resize (on-chain) | Via intent (off-chain) |
| **Use case** | Transfers | Applications |

---

## App Session Definition

Every app session starts with a **definition** that specifies the rules:

| Field | Description |
|-------|-------------|
| `protocol` | Version (`NitroRPC/0.4` recommended) |
| `participants` | Wallet addresses (order matters for signatures) |
| `weights` | Voting power per participant |
| `quorum` | Minimum weight required for state updates |
| `challenge` | Dispute window in seconds |
| `nonce` | Unique identifier (typically timestamp) |

The `app_session_id` is computed deterministically from the definition using `keccak256(JSON.stringify(definition))`.

---

## Governance with Quorum

The quorum system enables flexible governance patterns.

### How It Works

1. Each participant has a **weight** (voting power)
2. State updates require signatures with total weight ≥ **quorum**
3. Not everyone needs to sign—just enough to meet quorum

### Common Patterns

| Pattern | Setup | Use Case |
|---------|-------|----------|
| **Unanimous** | `weights: [50, 50]`, `quorum: 100` | Both must agree |
| **Trusted Judge** | `weights: [0, 0, 100]`, `quorum: 100` | App determines outcome |
| **2-of-3 Escrow** | `weights: [40, 40, 50]`, `quorum: 80` | Any two can proceed |
| **Weighted DAO** | `weights: [20, 25, 30, 25]`, `quorum: 51` | Majority by stake |

---

## Session Lifecycle

```mermaid
stateDiagram-v2
[*] --> Open: create_app_session
Open --> Open: submit_app_state
Open --> Closed: close_app_session
Closed --> [*]
```

### 1. Creation

- Funds locked from participants' unified balances
- All participants with non-zero allocations must sign
- Status becomes `open`, version starts at `1`

### 2. State Updates

- Redistribute funds with `submit_app_state`
- Version must increment by exactly 1
- Quorum of signatures required

### 3. Closure

- Final allocations distributed to unified balances
- Session becomes `closed` (cannot reopen)
- Quorum of signatures required

---

## Intent System (NitroRPC/0.4)

The intent system enables dynamic fund management during active sessions:

| Intent | Purpose | Rule |
|--------|---------|------|
| **OPERATE** | Redistribute existing funds | Sum unchanged |
| **DEPOSIT** | Add funds from unified balance | Sum increases |
| **WITHDRAW** | Remove funds to unified balance | Sum decreases |

:::info Allocations Are Final State
Allocations always represent the **final state**, not the delta. The Clearnode computes deltas internally.
:::

---

## Fund Flow

```mermaid
graph TB
subgraph Unified["Unified Balances"]
UA["Alice: 200 USDC"]
UB["Bob: 200 USDC"]
end

subgraph Session["App Session"]
SA["Alice: 100 USDC"]
SB["Bob: 100 USDC"]
end

UA -->|"create (lock)"| SA
UB -->|"create (lock)"| SB

SA -->|"close (release)"| UA
SB -->|"close (release)"| UB

style Unified fill:#e1f5ff,stroke:#333
style Session fill:#ffe1f5,stroke:#333
```

---

## Protocol Versions

| Version | Status | Key Features |
|---------|--------|--------------|
| **NitroRPC/0.2** | Legacy | Basic state updates only |
| **NitroRPC/0.4** | Current | Intent system (OPERATE, DEPOSIT, WITHDRAW) |

Always use `NitroRPC/0.4` for new applications. Protocol version is set at creation and cannot be changed.

---

## Best Practices

1. **Set appropriate challenge periods**: 1 hour minimum, 24 hours recommended
2. **Include commission participants**: Apps often have a judge that takes a small fee
3. **Plan for disputes**: Design allocations that can be verified by third parties
4. **Version carefully**: Each state update must be exactly `current + 1`

---

## Deep Dive

For complete API specifications and implementation details:

- **[App Session Methods](/docs/protocol/off-chain/app-sessions)** — Full API reference
- **[Communication Flows](/docs/protocol/communication-flows#app-session-lifecycle-flow)** — Sequence diagrams
- **[Implementation Checklist](/docs/protocol/implementation-checklist#state-management)** — Building app session support
Loading