VidStr - Decentralized Video Platform
VidStr is a decentralized, censorship-resistant video sharing platform built on the Nostr protocol. It enables users to upload, share, and discover videos without central authority control. Videos are stored on Blossom servers with metadata distributed across multiple Nostr relays.
Technical Overview
- Protocol
- Nostr (Notes and Other Stuff Transmitted by Relays)
- Architecture
- Client-side only, no backend server required. Pure static site with WebSocket connections to Nostr relays.
- Storage
- Videos: Blossom decentralized file servers. Metadata: Distributed across Nostr relay network. Local: Browser IndexedDB.
- Identity
- Nostr cryptographic keypair (secp256k1). Public key (npub) is your identity. Private key (nsec) signs your content.
Nostr Protocol Support (NIPs)
- NIP-01: Basic protocol flow, event signing and verification
- NIP-04: Encrypted Direct Messages (legacy AES-256-CBC)
- NIP-05: DNS-based identity verification
- NIP-07: Browser extension signers (Alby, nos2x, Flamingo)
- NIP-17: Private Direct Messages with gift-wrapping (metadata protection)
- NIP-19: Bech32-encoded identifiers (npub, note, naddr, nevent, nprofile)
- NIP-25: Reactions (like/dislike/emoji on videos)
- NIP-36: Content warnings for sensitive material
- NIP-50: Full-text search via specialized relays
- NIP-51: Lists and playlists (kind 30005 video collections)
- NIP-57: Lightning zaps (Bitcoin micropayments to creators)
- NIP-65: Relay list metadata (user-configurable relay preferences)
- NIP-71: Video events (kinds 21, 22, 34235, 34236)
- NIP-92: Media attachments with imeta tags
- NIP-94: File metadata specifications
- NIP-96: File storage server authentication
Video Event Kinds (NIP-71)
Kind 21: Regular Horizontal Video
- Type
- Regular Event (immutable)
- Orientation
- Horizontal/Landscape
- Editable
- No
- Format
- Uses imeta tags for video metadata
- Use Case
- Standard YouTube-style videos, tutorials, movies
Kind 22: Regular Vertical Video
- Type
- Regular Event (immutable)
- Orientation
- Vertical/Portrait
- Editable
- No
- Format
- Uses imeta tags for video metadata
- Use Case
- TikTok/Instagram Reels style shorts, stories
Kind 34235: Addressable Horizontal Video
- Type
- Addressable Event (replaceable)
- Orientation
- Horizontal/Landscape
- Editable
- Yes (publish new event with same d tag)
- Format
- Uses imeta tags plus d tag identifier
- Use Case
- Videos that may need metadata corrections, URL migrations, or updates
Kind 34236: Addressable Vertical Video
- Type
- Addressable Event (replaceable)
- Orientation
- Vertical/Portrait
- Editable
- Yes (publish new event with same d tag)
- Format
- Uses imeta tags plus d tag identifier
- Use Case
- Editable short-form videos
Legacy Format Support
VidStr maintains backwards compatibility with older NIP-71 video events that use separate url/m/x/dim/thumb tags instead of imeta. These legacy events are automatically detected and parsed correctly, ensuring all historical content remains accessible.
Multi-Relay Architecture
Default Relay Configuration (9 relays)
- wss://relay.damus.io - General purpose, high availability relay
- wss://nos.lol - Community-focused relay
- wss://relay.primal.net - Primal's infrastructure relay
- wss://relay.snort.social - Snort's relay network
- wss://relay.ditto.pub - Media-focused relay for content
- wss://nostr.wine - Content distribution relay
- wss://nostr.mom - Community relay
- wss://relay.mostr.pub - Bridge relay (Mastodon integration)
- wss://nostr21.com - Bitcoin-focused relay
Search Relays (NIP-50)
- wss://search.nos.today - Full-text search support
- wss://relay.noswhere.com - Full-text search support
Query Strategy
- Read Strategy
- Query ALL read-enabled relays in parallel. Each relay returns up to 100 events. Results are deduplicated by event ID and sorted chronologically. Top 20 most recent displayed per page.
- Write Strategy
- Publish to ALL write-enabled relays simultaneously. Ensures maximum distribution and redundancy across the network.
- Timeout
- 5 seconds per relay to prevent slow relays from blocking UI
- Benefits
- Maximum content discovery, redundancy, censorship resistance
- Trade-offs
- Increased bandwidth usage, slightly longer initial load times
User Configuration
Users can customize their relay list in Settings. Add/remove relays and toggle read/write permissions per relay. When logged in, relay configuration is published as NIP-65 event (kind 10002) and synced across devices.
Core Features
Video Upload
- Upload with Nostr account or anonymously
- Anonymous uploads generate ephemeral keypair (displayed once)
- Files uploaded to Blossom servers with NIP-96 authentication
- Metadata published as Nostr events to configured relays
- Support for all video formats (browser-dependent)
- Optional thumbnail upload
- Hashtag tagging for categorization
- Content warnings for sensitive material
- Choose regular (immutable) or addressable (editable) format
- File cloning prevents permission errors on mobile devices
Playlists (NIP-51)
- Create video collections using kind 30005 events
- Support for all video kinds: 21, 22, 34235, 34236
- Reference regular videos with e tags, addressable with a tags
- Add titles, descriptions, and cover images
- Edit and delete playlists (addressable events)
- Browse global playlists or from followed users
- Add videos to multiple playlists
Reactions (NIP-25)
- Kind 7 reaction events
- Like (+), dislike (-), custom emoji
- Custom text reactions (max 20 characters)
- Toggle reactions on/off
- Real-time reaction counts
- References video with e tag (regular) or a tag (addressable)
Comments
- Kind 1 reply events with e and p tags
- Nested reply support
- Real-time updates
- Rich text with URLs and Nostr mentions
- Comment on any video
Direct Messages
- NIP-04: Legacy encrypted DMs (AES-256-CBC, metadata visible)
- NIP-17: Modern gift-wrapped DMs (XChaCha20, metadata protected)
- End-to-end encryption with NIP-44
- File attachments via Blossom
- Real-time message delivery
- Conversation management
Search & Discovery
- Full-text search via NIP-50 relays
- Hashtag browsing (#tag URLs)
- Global feed (all videos from all relays)
- Following feed (videos from followed users)
- Profile pages with all user videos
- Related video suggestions
- Client-side filtering fallback for non-NIP-50 relays
Lightning Zaps (NIP-57)
- Send Bitcoin micropayments to video creators
- Send zaps to user profiles
- WebLN browser wallet integration
- Nostr Wallet Connect (NWC) support
- LNURL invoice generation
- QR code display for mobile wallets
- Zap receipts (kind 9735) for verification
- Display total sats received per video
- Requires lud16 or lud06 in profile metadata
User Profiles
- Kind 0 metadata events
- Display name, bio, avatar, banner
- Website links and social verification (NIP-05)
- Lightning address display (lud16/lud06)
- Video gallery view
- Follow/unfollow functionality
- Editable by profile owner
How VidStr Works
Step 1: Identity & Authentication
Users authenticate with a Nostr keypair. Three options available:
- Generate New Keys: Create fresh keypair in browser. Keys stored in IndexedDB or extension.
- Browser Extension: Use Alby, nos2x, Flamingo, or other NIP-07 signers. Most secure option.
- Import Existing Keys: Import nsec or hex private key from another client.
- Anonymous Mode: Generate ephemeral keypair per upload. Keys shown once after upload.
No email, no password, no central account database. Your keypair is your identity across the entire Nostr ecosystem.
Step 2: Video Upload Process
- User selects video file from device
- File immediately cloned to memory (prevents permission errors)
- Video dimensions detected to determine orientation
- User adds metadata: title, description, hashtags, thumbnail
- File uploaded to Blossom server (https://blossom.primal.net/)
- Upload authenticated with Nostr signature (NIP-96)
- Server returns URL, SHA-256 hash, mime type, dimensions
- Nostr event created with imeta tags containing all metadata
- Event signed with user's private key
- Event published to all write-enabled relays
- Event ID returned, video now discoverable network-wide
Step 3: Video Discovery
Global Feed
- Client queries all read-enabled relays in parallel
- Filter: kinds [21, 22, 34235, 34236], limit 100, until current_time
- Each relay returns up to 100 most recent video events
- Events deduplicated by event ID (same video from multiple relays)
- Events sorted by created_at timestamp (newest first)
- Top 20 displayed to user
- Infinite scroll loads next page with until=oldest_displayed_timestamp
Search
- Query sent to NIP-50 search relays with search parameter
- Also query regular relays as fallback
- Client-side filtering for non-NIP-50 relays
- Results combined and deduplicated
- Matches on title, description, or hashtags
Following Feed
- Fetch user's kind 3 follow list event
- Extract pubkeys from p tags
- Query videos with authors filter
- Display chronologically
Step 4: Video Playback
- User clicks video thumbnail
- Navigate to video page with event ID or naddr
- Fetch video event from relays
- Parse imeta tags or legacy url tags
- Load video URL in HTML5 video player
- Display metadata: title, description, creator profile
- Load reactions, comments, zap count from relays
- Enable user interactions (react, comment, zap, share)
Step 5: User Interactions
Reactions
- Create kind 7 event with content: "+", "-", or emoji
- Add e tag (for regular videos) or a tag (for addressable videos)
- Add p tag with video author pubkey
- Sign and publish to write-enabled relays
Comments
- Create kind 1 event with comment text in content
- Add e tag referencing video event ID (root)
- Add e tag for reply-to comment (if replying to comment)
- Add p tags for video author and comment author
- Sign and publish
Zaps
- Fetch creator's lud16 or lud06 from profile metadata
- Generate LNURL invoice via creator's lightning service
- Display invoice as QR code and copyable text
- Pay via WebLN (browser extension) or external wallet
- Zap receipt (kind 9735) published by recipient's lightning service
- Receipt references original video event
File Storage (Blossom Protocol)
- Protocol
- Blossom - Decentralized file hosting with Nostr authentication
- Authentication
- NIP-96 style event signatures. Sign upload request with Nostr keys.
- Content Addressing
- Files identified by SHA-256 hash. Same file = same URL across all servers.
- Metadata
- Stored in imeta tags: url, hash (x), mime type (m), dimensions (dim), duration, bitrate, image (thumbnail)
- Fallbacks
- Multiple server URLs can be specified for redundancy
- Server Used
- https://blossom.primal.net/ (default)
Security & Privacy
Encryption
- Event Signing
- Schnorr signatures on secp256k1 curve. All events cryptographically signed and verified.
- Direct Messages (NIP-04)
- AES-256-CBC encryption. Legacy format with visible metadata (sender, recipient, timestamp).
- Direct Messages (NIP-17)
- XChaCha20-Poly1305 encryption (NIP-44). Gift-wrapped to hide all metadata. Only recipient can decrypt.
- File Integrity
- SHA-256 hashing ensures files cannot be tampered with. Hash stored in event metadata.
Privacy Features
- No Central Server: VidStr is pure client-side. No tracking, no analytics.
- Anonymous Posting: Upload without account using ephemeral keys.
- Local Storage Only: All data in browser IndexedDB. Never sent to central server.
- Keys Never Shared: Private keys stay on your device or extension.
- Relay Privacy: Individual relay operators can see IP addresses and event metadata.
- Encrypted DMs: End-to-end encryption ensures only sender and recipient can read.
- No KYC: No email, phone number, or identity verification required.
Technology Stack
Frontend Technologies
- Framework
- React 18.x with TypeScript
- Routing
- React Router v6 with BrowserRouter
- Styling
- TailwindCSS 3.x utility-first CSS
- Components
- shadcn/ui (Radix UI primitives with Tailwind styling). 48+ accessible components.
- State Management
- TanStack Query for server state. React Context for global state.
- Build Tool
- Vite for fast development and optimized production builds
Nostr Integration
- Core Library
- Nostrify - Modern Nostr framework for web and Deno
- React Integration
- @nostrify/react - React hooks and context providers
- Authentication
- @nostrify/react/login - Multi-account management
- Utilities
- nostr-tools v2.13+ - NIP-19 encoding, event creation, signature verification
Lightning Payment Integration
- WebLN
- @webbtc/webln-types - Browser extension wallet interface
- NWC
- @getalby/sdk - Nostr Wallet Connect for remote wallet control
- QR Codes
- qrcode library - Generate Lightning invoice QR codes
Data Storage
- Local Database
- IndexedDB via idb library - Stores accounts, settings, cached events
- Encrypted Messages
- Custom encrypted message store for NIP-04 and NIP-17 DMs
- Configuration
- localStorage for theme, relay list, and app preferences
Deployment & Hosting
- Type
- Static site (no server-side code)
- Build Output
- HTML, CSS, JavaScript, and static assets in /dist directory
- Hosting Requirements
- Any static file host. HTTPS required for WebSocket connections.
- CDN Compatible
- Yes, works with Cloudflare, Netlify, Vercel, etc.
- No Backend Needed
- All logic runs in browser. Direct WebSocket connections to Nostr relays.
- Current Deployment
- https://vidstr.shakespeare.wtf
API Reference (Nostr Protocol)
VidStr has no traditional REST API. All communication uses the Nostr protocol over WebSockets.
Query Videos
REQ <subscription-id>
{
"kinds": [21, 22, 34235, 34236],
"limit": 100,
"until": <unix-timestamp>
}
Publish Video
EVENT {
"kind": 21,
"content": "Video description",
"tags": [
["imeta",
"url https://blossom.server/file.mp4",
"m video/mp4",
"dim 1920x1080",
"x <sha256-hash>",
"image https://blossom.server/thumb.jpg",
"duration 120.5"
],
["title", "Video Title"],
["published_at", "<unix-timestamp>"],
["t", "hashtag"],
["alt", "Accessibility description"]
],
"created_at": <unix-timestamp>,
"pubkey": "<author-public-key>",
"id": "<event-id>",
"sig": "<signature>"
}
React to Video
EVENT {
"kind": 7,
"content": "+",
"tags": [
["e", "<video-event-id>"],
["p", "<video-author-pubkey>"],
["k", "<video-kind>"]
],
"created_at": <unix-timestamp>,
"pubkey": "<reactor-public-key>",
"id": "<event-id>",
"sig": "<signature>"
}
Known Limitations
- Relay Dependency: Content availability depends on relay uptime and retention policies
- No Global Moderation: Decentralized nature means no platform-wide content moderation
- Relay Policies: Individual relays may filter or block certain content
- File Size Limits: Blossom servers may have upload size restrictions
- Bandwidth Usage: Querying 10 relays simultaneously increases data usage
- Browser Storage: IndexedDB quota limitations vary by browser
- Discovery: New relays or content may take time to propagate
- Key Management: Lost private keys cannot be recovered
Getting Started Guide
For Users
- Visit https://vidstr.shakespeare.wtf
- Click "Log in" or "Sign up" to create/connect Nostr identity
- Optional: Configure relays in Settings (default relays work fine)
- Click "Upload" button to share your first video
- Browse global feed or search for content
- Follow creators, react to videos, leave comments
- Zap sats to support creators you enjoy
For Developers
- Click "Edit with Shakespeare" badge to fork the project
- Modify code in Shakespeare IDE (AI-assisted development)
- Add custom features or integrate with your services
- Deploy to your own domain
- Connect to your own relays
- Customize branding and UI
Troubleshooting
- Q: Videos not loading?
- A: Check relay connections in Settings > Relays. Try adding more relays. Some may be offline or rate-limiting. Verify you have at least 1 read-enabled relay.
- Q: Can't upload videos?
- A: Ensure logged in (unless anonymous). Check Blossom server accessibility. Try different browser if permission errors occur. Verify you have at least 1 write-enabled relay.
- Q: Upload fails with "permission" error?
- A: This is a browser file access issue. VidStr now clones files to memory immediately. Try: 1) Refresh page, 2) Use different browser, 3) Check browser permissions, 4) Try smaller file.
- Q: Search not working?
- A: Enable NIP-50 search relays (wss://search.nos.today, wss://relay.noswhere.com) in Settings. Regular relays don't support full-text search.
- Q: Lost my keys?
- A: Private keys cannot be recovered. No password reset exists in decentralized system. Always back up nsec securely. For anonymous posts, keys shown once after upload.
- Q: Zaps not working?
- A: Ensure recipient has lightning address (lud16 or lud06 in profile). Connect WebLN wallet or configure NWC. Check wallet has funds and connection.
- Q: Videos from days ago missing in feed?
- A: This is due to multi-relay query behavior. Each relay returns its 100 most recent videos. If some relays lack recent content, you may see time gaps. Increase relays or adjust query strategy in code.
- Q: Can I delete a video?
- A: You can publish kind 5 deletion request, but relays are not required to honor it. Addressable events (34235/34236) can be "edited" to empty content. Regular events (21/22) are immutable.
Project Metadata
- Name
- VidStr
- Version
- 2026.02.02.2
- Release Date
- 2026-02-02
- License
- MIT Open Source
- Repository
- nostr://npub14rg4vrt2v374q95ezeeydu3hkdhmzglcj950mggacap4x0lv0gyq04wun7/git.shakespeare.diy/vidstr
- Deployment URL
- https://vidstr.shakespeare.wtf
- Built With
- Shakespeare.diy AI-powered development platform
- Maintainer
- stl1988 (npub14rg4vrt2v374q95ezeeydu3hkdhmzglcj950mggacap4x0lv0gyq04wun7)
Additional Resources
- Nostr Protocol: https://nostr.com
- NIPs Repository: https://github.com/nostr-protocol/nips
- NIP-71 Video Events: https://github.com/nostr-protocol/nips/blob/master/71.md
- Blossom Specification: https://github.com/hzrd149/blossom
- Lightning Network: https://lightning.network
- Nostrify Documentation: https://nostrify.dev
- Shakespeare Builder: https://shakespeare.diy