KATHA कथा

Kommunication And Threading Handler Architecture

Rich chat features for the Yakmesh network.

v1.0.0

The Art of Storytelling

In Sanskrit, कथा (katha) means "story" or "narrative" — the ancient art of passing knowledge through conversation. From the great epics recited around fires to intimate talks between teacher and student, katha represents the living tradition of shared understanding.

The KATHA protocol embodies this tradition: messages flow like stories, reactions capture emotional resonance, threads weave deeper discussions, and typing indicators show when someone is composing their thoughts.

Overview

KATHA provides the rich chat layer for Yakmesh, bringing modern messaging features to decentralized communication:

Text Messages

Rich text with 4000 char limit, reply threading, and edit history

Reactions

Emoji reactions with 20 unique emojis per message

Typing Indicators

5-second ephemeral presence showing who's composing

Media Embeds

Images, GIFs, and files up to 10MB with integrity verification

✓✓

Read Receipts

Batched acknowledgments showing who's seen your message

Threading

Reply to specific messages, creating focused conversations

Messages

Every chat message is a KathaMessage:

import { KathaMessage } from './mesh/katha.js';

// Create a message
const msg = new KathaMessage({
  channelId: 'general',
  senderId: myNodeId,
  content: 'Hello, Yakmesh!',
});

// Reply to a message
const reply = new KathaMessage({
  channelId: 'general',
  senderId: myNodeId,
  content: 'Great point!',
  replyTo: msg.id,  // Links to parent message
});

// Validate before sending
const { valid, errors } = msg.validate();
if (valid) {
  channel.addMessage(msg);
}

Reactions

React to messages with emoji:

import { KathaReaction } from './mesh/katha.js';

// Add a reaction
const reaction = new KathaReaction({
  messageId: msg.id,
  channelId: 'general',
  userId: myNodeId,
  emoji: '👍',
  add: true,  // false to remove
});

// Apply to channel
channel.applyReaction(reaction);

// Check reaction counts
const counts = msg.getReactionCounts();
// { '👍': 3, '❤️': 1, '🎉': 2 }

// Check if user reacted
if (msg.hasUserReaction('👍', myNodeId)) {
  console.log('You already reacted!');
}
Limits: 20 unique emojis per message, 1 reaction per user per emoji.

Typing Indicators

Show when users are composing messages:

import { KathaTyping } from './mesh/katha.js';

// Start typing
const typing = new KathaTyping({
  channelId: 'general',
  userId: myNodeId,
});

// Send to mesh...
hub.handleEvent(typing.toJSON());

// Stop typing (explicit)
const stopTyping = new KathaTyping({
  channelId: 'general',
  userId: myNodeId,
  stop: true,
});

// Or let it expire automatically (5 seconds)
// The channel cleans up expired typing indicators

Media Embeds

Share images, GIFs, and files with integrity verification:

import { KathaMedia, KATHA_CONFIG } from './mesh/katha.js';
import { readFileSync } from 'fs';

// Create from buffer
const imageBuffer = readFileSync('photo.jpg');
const media = KathaMedia.fromBuffer(imageBuffer, {
  channelId: 'general',
  senderId: myNodeId,
  filename: 'photo.jpg',
  mimeType: 'image/jpeg',
  mediaType: KATHA_CONFIG.mediaTypes.IMAGE,
  caption: 'Check out this view!',
});

// Verify integrity on receive
if (media.verify()) {
  const buffer = media.toBuffer();
  // Display or save the image
}
Media Types:
  • IMAGE - Static images (JPEG, PNG, WebP)
  • GIF - Animated GIFs
  • FILE - Any file attachment

Maximum size: 10MB. Data is base64 encoded with SHA3-256 hash for verification.

Read Receipts

Track who has read messages (batched for efficiency):

import { KathaReadReceipt } from './mesh/katha.js';

// Batch multiple read acknowledgments
const receipt = new KathaReadReceipt({
  channelId: 'general',
  userId: myNodeId,
  lastReadId: latestMessageId,  // Everything up to this message
});

// Or list specific messages
receipt.addMessage('msg-1');
receipt.addMessage('msg-2');
receipt.addMessage('msg-3');

// Check who read a message
const readers = channel.getReadBy(messageId);
// ['user-1', 'user-2', 'user-3']

Edit & Delete

import { KathaEdit, KathaDelete } from './mesh/katha.js';

// Edit a message (only sender can edit)
const edit = new KathaEdit({
  messageId: msg.id,
  channelId: 'general',
  userId: myNodeId,
  newContent: 'Updated: Hello, Yakmesh!',
});
channel.editMessage(edit);
// msg.editedAt is now set

// Delete a message (only sender can delete)
const del = new KathaDelete({
  messageId: msg.id,
  channelId: 'general',
  userId: myNodeId,
});
channel.deleteMessage(del);
// If message has replies, content becomes '[deleted]'

Channel Management

KathaChannel manages all chat state for a single channel:

import { KathaChannel, KathaMessage } from './mesh/katha.js';

const channel = new KathaChannel('general');

// Add messages
channel.addMessage(msg1);
channel.addMessage(msg2);

// Get messages with filters
const recent = channel.getMessages({ limit: 50 });
const before = channel.getMessages({ before: timestamp });
const after = channel.getMessages({ after: timestamp });
const topLevel = channel.getMessages({ threadOnly: false });

// Get thread replies
const replies = channel.getThreadReplies(parentMessageId);

// Track typing
channel.setTyping('user-1', true);
const typingUsers = channel.getTypingUsers();

// Channel stats
const stats = channel.getStats();
// { channelId, messageCount, threadCount, typingUsers }

KathaHub - Multi-Channel Manager

KathaHub manages multiple channels and handles incoming events:

import { KathaHub, KATHA_CONFIG } from './mesh/katha.js';

const hub = new KathaHub();

// Channels are created on demand
const general = hub.getChannel('general');
const random = hub.getChannel('random');

// Handle incoming events from the mesh
hub.handleEvent(incomingMessage);

// Register event handlers
hub.on(KATHA_CONFIG.messageTypes.TEXT, (event, result) => {
  console.log('New message:', event.content);
});

hub.on(KATHA_CONFIG.messageTypes.REACTION_ADD, (event, result) => {
  console.log(${event.userId} reacted with );
});

hub.on(KATHA_CONFIG.messageTypes.TYPING_START, (event) => {
  showTypingIndicator(event.userId, event.channelId);
});

// Global stats
const stats = hub.getStats();
// { channelCount: 2, totalMessages: 150, channels: {...} }

// Cleanup on shutdown
hub.cleanup();

Message Types

Type Value Description
TEXTkatha:textChat message
REACTION_ADDkatha:reaction:addAdd emoji reaction
REACTION_REMOVEkatha:reaction:removeRemove emoji reaction
TYPING_STARTkatha:typing:startUser started typing
TYPING_STOPkatha:typing:stopUser stopped typing
READ_RECEIPTkatha:readRead acknowledgment
EDITkatha:editMessage edit
DELETEkatha:deleteMessage deletion
MEDIAkatha:mediaImage/GIF/file attachment

Integration with GUMBA

KATHA messages travel through GUMBA bundles for private rooms:

// KATHA message
const msg = new KathaMessage({
  channelId: bundleId,
  senderId: myMemberId,
  content: 'Private room message',
});

// Wrap in GUMBA content envelope
const envelope = bundle.encrypt(msg.toJSON());

// Send through mesh
network.broadcast(envelope);