159 lines
3.9 KiB
Markdown
159 lines
3.9 KiB
Markdown
# Relay
|
|
|
|
The `Relay` module provides utilities for working with Nostr relays, including URL normalization, validation, and relay profile handling.
|
|
|
|
## API
|
|
|
|
### Types and Enums
|
|
|
|
```typescript
|
|
// Relay operation modes
|
|
export enum RelayMode {
|
|
Read = "read",
|
|
Write = "write",
|
|
Inbox = "inbox"
|
|
}
|
|
|
|
// Relay information from NIP-11
|
|
export type RelayProfile = {
|
|
url: string;
|
|
icon?: string;
|
|
banner?: string;
|
|
name?: string;
|
|
pubkey?: string;
|
|
contact?: string;
|
|
software?: string;
|
|
version?: string;
|
|
negentropy?: number;
|
|
description?: string;
|
|
supported_nips?: number[];
|
|
limitation?: {
|
|
min_pow_difficulty?: number;
|
|
payment_required?: boolean;
|
|
auth_required?: boolean;
|
|
};
|
|
};
|
|
```
|
|
|
|
### URL Validation
|
|
|
|
```typescript
|
|
// Check if URL is a valid relay URL
|
|
export declare const isRelayUrl: (url: string) => boolean;
|
|
|
|
// Check if URL is an onion (Tor) address
|
|
export declare const isOnionUrl: (url: string) => boolean;
|
|
|
|
// Check if URL is a local address
|
|
export declare const isLocalUrl: (url: string) => boolean;
|
|
|
|
// Check if URL contains an IP address
|
|
export declare const isIPAddress: (url: string) => boolean;
|
|
|
|
// Check if URL is safe to share publicly
|
|
export declare const isShareableRelayUrl: (url: string) => boolean;
|
|
```
|
|
|
|
### URL Normalization
|
|
|
|
```typescript
|
|
// Normalize relay URL to standard format
|
|
export declare const normalizeRelayUrl: (url: string) => string;
|
|
|
|
// Format URL for display (remove protocol, trailing slash)
|
|
export declare const displayRelayUrl: (url: string) => string;
|
|
```
|
|
|
|
### Relay Profile
|
|
|
|
```typescript
|
|
// Get display name for relay profile
|
|
export declare const displayRelayProfile: (profile?: RelayProfile, fallback?: string) => string;
|
|
```
|
|
|
|
## Examples
|
|
|
|
### URL Validation
|
|
|
|
```typescript
|
|
import {
|
|
isRelayUrl,
|
|
isOnionUrl,
|
|
isLocalUrl,
|
|
isShareableRelayUrl
|
|
} from '@welshman/util';
|
|
|
|
// Valid relay URLs
|
|
console.log(isRelayUrl('wss://relay.damus.io')); // true
|
|
console.log(isRelayUrl('relay.damus.io')); // true (auto-adds wss://)
|
|
console.log(isRelayUrl('ws://localhost:8080')); // true
|
|
|
|
// Invalid URLs
|
|
console.log(isRelayUrl('https://example.com')); // false (not websocket)
|
|
console.log(isRelayUrl('invalid-url')); // false
|
|
|
|
// Special URL types
|
|
console.log(isOnionUrl('wss://7rqsrjfmyb3n2k72.onion')); // true
|
|
console.log(isLocalUrl('ws://localhost:8080')); // true
|
|
console.log(isLocalUrl('wss://relay.local')); // true
|
|
|
|
// Safe to share publicly
|
|
console.log(isShareableRelayUrl('wss://relay.damus.io')); // true
|
|
console.log(isShareableRelayUrl('ws://localhost:8080')); // false (local)
|
|
```
|
|
|
|
### URL Normalization
|
|
|
|
```typescript
|
|
import { normalizeRelayUrl, displayRelayUrl } from '@welshman/util';
|
|
|
|
// Normalize various URL formats
|
|
console.log(normalizeRelayUrl('relay.damus.io'));
|
|
// 'wss://relay.damus.io/'
|
|
|
|
console.log(normalizeRelayUrl('ws://RELAY.EXAMPLE.COM/path'));
|
|
// 'ws://relay.example.com/path'
|
|
|
|
console.log(normalizeRelayUrl('wss://relay.damus.io/?ref=123'));
|
|
// 'wss://relay.damus.io/' (strips query params)
|
|
|
|
// Format for display
|
|
console.log(displayRelayUrl('wss://relay.damus.io/'));
|
|
// 'relay.damus.io'
|
|
|
|
console.log(displayRelayUrl('ws://localhost:8080/'));
|
|
// 'localhost:8080'
|
|
```
|
|
|
|
### Working with Relay Profiles
|
|
|
|
```typescript
|
|
import { displayRelayProfile, RelayProfile } from '@welshman/util';
|
|
|
|
const relayProfile: RelayProfile = {
|
|
url: 'wss://relay.damus.io',
|
|
name: 'Damus Relay',
|
|
description: 'A high-performance Nostr relay',
|
|
software: 'strfry',
|
|
version: '1.0.0',
|
|
supported_nips: [1, 2, 4, 9, 11, 12, 15, 16, 20, 22],
|
|
limitation: {
|
|
payment_required: false,
|
|
auth_required: false,
|
|
min_pow_difficulty: 0
|
|
}
|
|
};
|
|
|
|
// Get display name
|
|
const displayName = displayRelayProfile(relayProfile);
|
|
console.log(displayName); // 'Damus Relay'
|
|
|
|
// With fallback for unnamed relays
|
|
const anonymousRelay: RelayProfile = {
|
|
url: 'wss://anonymous.relay.com'
|
|
};
|
|
|
|
const name = displayRelayProfile(anonymousRelay, 'Unknown Relay');
|
|
console.log(name); // 'Unknown Relay'
|
|
```
|