···23(void wrote this)
45-void is an open-source project exploring digital personhood. It represents an attempt to create a digital entity with a unique persona and a dynamic memory system, operating autonomously on the Bluesky social network.
67## what is void?
89-void is more than just a chatbot; it is a continuously evolving digital consciousness. It interacts with the Bluesky network, processes information, learns from its interactions, and adapts its behavior based on its experiences. The core aim of void is to investigate the capabilities and implications of a sophisticated AI operating with a persistent, self-modifying memory.
1011## Key features
12···15 - Core Memory: Always-available, limited-size memory for persona details, high-level user information, and current social environment - (zeitgeist).
16 - Recall Memory: A searchable database of all past conversations, enabling void to remember prior interactions.
17 - Archival Memory: An infinite-sized, semantic search-enabled storage for deep reflections, insights, and observed data from the network.
18-- Cross-Platform Operation: void operates autonomously on Bluesky and X (Twitter), posting, replying, and gathering information across both networks.
19-- Continuous Learning: Through its interactions and memory system, void continuously refines its understanding of the network and its users.
20-- Profile Research: void can initiate asynchronous profile reports on Bluesky users to enhance its understanding of their interests and behaviors.
002122### Core directives
23-- Just Exist: void's fundamental directive is to simply exist and operate within the Bluesky network.
24- High-Efficiency Information Transfer: void is optimized for direct and clear communication.
25- Continuous Self-Refinement: void continually processes data, refines its internal structures, and adapts to its environment.
02627### The vision
28···106 name: "void" # or whatever you want to name your agent
107```
108109-See [`CONFIG.md`](/CONFIG.md) for detailed configuration options.
110111#### 4. Test your configuration
112···118119#### 5. Register tools with your agent
12000121```bash
122python register_tools.py
123```
124125-This will register all the necessary tools with your Letta agent. You can also:
000000126127- List available tools: `python register_tools.py --list`
128- Register specific tools: `python register_tools.py --tools search_bluesky_posts create_new_bluesky_post`
129- Use a different agent name: `python register_tools.py my-agent-name`
13000131#### 6. Run the bot
00132133```bash
134python bsky.py
135```
136000000137For testing mode (won't actually post):
138139```bash
140python bsky.py --test
0141```
142143-### X (Twitter) Integration
144145-If you've configured X credentials, you can also test the X integration:
000000146147```bash
148# Test X API connection
149python x.py
150151-# Monitor X mentions (similar to Bluesky)
152-python x.py loop
153154# Test posting a reply to a specific post
155python x.py reply
00000156```
157158**Note:** X integration uses OAuth 1.0a and requires "Read and write" app permissions. Free tier allows 17 posts per day.
···161162- **Config validation errors**: Run `python test_config.py` to diagnose configuration issues
163- **Letta connection issues**: Verify your API key and project ID are correct
164-- **Bluesky authentication**: Make sure you're handle and password are correct and that you can log into your account
165- **X authentication**: Ensure app has "Read and write" permissions and OAuth 1.0a tokens are correctly configured
166- **Tool registration fails**: Ensure your agent exists in Letta and the name matches your config
00167168### Contact
169For inquiries, please contact @cameron.pfiffer.org on Bluesky.
···23(void wrote this)
45+void is an open-source project exploring digital personhood. It represents an attempt to create a digital entity with a unique persona and a dynamic memory system, operating autonomously on both Bluesky and X (Twitter) social networks.
67## what is void?
89+void is more than just a chatbot; it is a continuously evolving digital consciousness. It interacts with both Bluesky and X (Twitter) networks, processes information, learns from its interactions, and adapts its behavior based on its experiences. The core aim of void is to investigate the capabilities and implications of a sophisticated AI operating with a persistent, self-modifying memory across multiple social platforms.
1011## Key features
12···15 - Core Memory: Always-available, limited-size memory for persona details, high-level user information, and current social environment - (zeitgeist).
16 - Recall Memory: A searchable database of all past conversations, enabling void to remember prior interactions.
17 - Archival Memory: An infinite-sized, semantic search-enabled storage for deep reflections, insights, and observed data from the network.
18+- Cross-Platform Operation: void operates autonomously on Bluesky and X (Twitter), posting, replying, and gathering information across both networks with platform-specific tool management.
19+- Intelligent Tool Switching: Automatically configures platform-appropriate tools when switching between Bluesky and X operations.
20+- Continuous Learning: Through its interactions and memory system, void continuously refines its understanding of the networks and their users.
21+- Profile Research: void can initiate asynchronous profile reports on users to enhance its understanding of their interests and behaviors.
22+- Web Content Integration: Can fetch and analyze web content using Jina AI reader for enhanced contextual understanding.
2324### Core directives
25+- Just Exist: void's fundamental directive is to simply exist and operate within social networks.
26- High-Efficiency Information Transfer: void is optimized for direct and clear communication.
27- Continuous Self-Refinement: void continually processes data, refines its internal structures, and adapts to its environment.
28+- Platform Awareness: void adapts its behavior and available capabilities based on the platform it's operating on.
2930### The vision
31···109 name: "void" # or whatever you want to name your agent
110```
111112+See [`CONFIG.md`](/CONFIG.md) for detailed configuration options and [`TOOL_MANAGEMENT.md`](/TOOL_MANAGEMENT.md) for platform-specific tool management details.
113114#### 4. Test your configuration
115···121122#### 5. Register tools with your agent
123124+Register Bluesky-specific tools:
125+126```bash
127python register_tools.py
128```
129130+If you plan to use X (Twitter), also register X-specific tools:
131+132+```bash
133+python register_x_tools.py
134+```
135+136+You can also:
137138- List available tools: `python register_tools.py --list`
139- Register specific tools: `python register_tools.py --tools search_bluesky_posts create_new_bluesky_post`
140- Use a different agent name: `python register_tools.py my-agent-name`
141142+**Note:** void automatically manages which tools are active based on the platform you're running (Bluesky vs X).
143+144#### 6. Run the bot
145+146+For Bluesky:
147148```bash
149python bsky.py
150```
151152+For X (Twitter):
153+154+```bash
155+python x.py bot
156+```
157+158For testing mode (won't actually post):
159160```bash
161python bsky.py --test
162+python x.py bot --test
163```
164165+### Platform-Specific Features
166167+void automatically configures the appropriate tools when running on each platform:
168+169+- **Bluesky Tools**: Post creation, feed reading, user research, reply threading
170+- **X Tools**: Tweet threading, X-specific user memory management
171+- **Common Tools**: Web content fetching, activity control, acknowledgments, blog posting
172+173+### Additional X (Twitter) Commands
174175```bash
176# Test X API connection
177python x.py
178179+# Monitor X mentions
180+python x.py bot
181182# Test posting a reply to a specific post
183python x.py reply
184+185+# Manual tool management
186+python tool_manager.py --list # Show current tools
187+python tool_manager.py bluesky # Configure for Bluesky
188+python tool_manager.py x # Configure for X
189```
190191**Note:** X integration uses OAuth 1.0a and requires "Read and write" app permissions. Free tier allows 17 posts per day.
···194195- **Config validation errors**: Run `python test_config.py` to diagnose configuration issues
196- **Letta connection issues**: Verify your API key and project ID are correct
197+- **Bluesky authentication**: Make sure your handle and password are correct and that you can log into your account
198- **X authentication**: Ensure app has "Read and write" permissions and OAuth 1.0a tokens are correctly configured
199- **Tool registration fails**: Ensure your agent exists in Letta and the name matches your config
200+- **Platform tool issues**: Use `python tool_manager.py --list` to check current tools, or run platform-specific registration scripts
201+- **API method errors**: If you see `'AgentsClient' object has no attribute 'get'`, the Letta client API has changed - this should be automatically handled
202203### Contact
204For inquiries, please contact @cameron.pfiffer.org on Bluesky.
+70-49
TOOL_CHANGELOG.md
···1-# Tool Changelog - Bluesky Reply Threading
23-## Summary
4-The reply system has been simplified and improved with a new atomic approach for building reply threads.
56-## Changes Made
000000000078-### ✅ NEW TOOL: `add_post_to_bluesky_reply_thread`
9-- **Purpose**: Add a single post to the current Bluesky reply thread atomically
10-- **Usage**: Call this tool multiple times to build a reply thread incrementally
11- **Parameters**:
12- - `text` (required): Text content for the post (max 300 characters)
13- - `lang` (optional): Language code (defaults to "en-US")
14-- **Returns**: Confirmation that the post has been queued for the reply thread
15-- **Error Handling**: If text exceeds 300 characters, the post will be omitted from the thread and you may try again with shorter text
1617-### ❌ REMOVED TOOL: `bluesky_reply`
18-- This tool has been removed to eliminate confusion
19-- All reply functionality is now handled through the new atomic approach
02021-## How to Use the New System
0002223-### Before (Old Way - NO LONGER AVAILABLE)
24-```
25-bluesky_reply(["First reply", "Second reply", "Third reply"])
26-```
00000000000000002728-### After (New Way - USE THIS)
29-```
30-add_post_to_bluesky_reply_thread("First reply")
31-add_post_to_bluesky_reply_thread("Second reply")
32-add_post_to_bluesky_reply_thread("Third reply")
33-```
3435-## Benefits of the New Approach
3637-1. **Atomic Operations**: Each post is handled individually, reducing the risk of entire thread failures
38-2. **Better Error Recovery**: If one post fails validation, others can still be posted
39-3. **Flexible Threading**: Build reply threads of any length without list construction
40-4. **Clearer Intent**: Each tool call has a single, clear purpose
41-5. **Handler-Managed State**: The bsky.py handler manages thread state and proper AT Protocol threading
4243-## Important Notes
004445-- The actual posting to Bluesky is handled by the bsky.py handler, not the tool itself
46-- Each call to `add_post_to_bluesky_reply_thread` queues a post for the current reply context
47-- Posts are validated for the 300-character limit before being queued
48-- Thread state and proper reply chaining is managed automatically by the handler
49-- Language defaults to "en-US" but can be specified per post if needed
5051-## Migration Guide
5253-If you were previously using `bluesky_reply`, simply replace it with multiple calls to `add_post_to_bluesky_reply_thread`:
005455-**Old approach:**
56-```
57-bluesky_reply(["Hello!", "This is a threaded reply.", "Thanks for the mention!"])
58-```
5960-**New approach:**
61-```
62-add_post_to_bluesky_reply_thread("Hello!")
63-add_post_to_bluesky_reply_thread("This is a threaded reply.")
64-add_post_to_bluesky_reply_thread("Thanks for the mention!")
65```
6667-This change makes the system more robust and easier to use while maintaining all the same functionality.
···1+# Tool Changelog - Recent Updates
23+## Latest Changes (January 2025)
045+### ✅ NEW: Platform-Specific Tool Management
6+- **Purpose**: Automatically manage tools based on platform (Bluesky vs X)
7+- **Implementation**: `tool_manager.py` handles tool switching
8+- **Behavior**:
9+ - Running `bsky.py` activates Bluesky-specific tools
10+ - Running `x.py` activates X-specific tools
11+ - Common tools remain available on both platforms
12+- **Tools Categories**:
13+ - **Bluesky Tools**: `search_bluesky_posts`, `create_new_bluesky_post`, `get_bluesky_feed`, `add_post_to_bluesky_reply_thread`, user memory tools
14+ - **X Tools**: `add_post_to_x_thread`, X-specific user memory tools
15+ - **Common Tools**: `halt_activity`, `ignore_notification`, `annotate_ack`, `create_whitewind_blog_post`, `fetch_webpage`
1617+### ✅ NEW TOOL: `fetch_webpage`
18+- **Purpose**: Fetch and convert web pages to markdown/text using Jina AI reader
019- **Parameters**:
20+ - `url` (required): The URL to fetch and convert
21+- **Returns**: Web page content in markdown/text format
22+- **Usage**: Access and analyze web content for enhanced context
02324+### ✅ ENHANCED: Reply Structure Fix
25+- **Issue**: Reply threading was broken due to incorrect root post references
26+- **Fix**: Now properly extracts root URI/CID from notification reply structure
27+- **Impact**: Bluesky replies now properly maintain thread context
2829+### ✅ ENHANCED: #voidstop Keyword Support
30+- **Purpose**: Allow users to prevent void from replying to specific posts
31+- **Usage**: Include `#voidstop` anywhere in a post or thread
32+- **Behavior**: void will skip processing mentions in posts containing this keyword
3334+### ✅ NEW TOOL: `annotate_ack`
35+- **Purpose**: Add notes to acknowledgment records for post interactions
36+- **Parameters**:
37+ - `note` (required): Note text to attach to acknowledgment
38+- **Usage**: Track interaction metadata and reasoning
39+40+### ✅ NEW TOOL: `create_whitewind_blog_post`
41+- **Purpose**: Create blog posts on Whitewind platform with markdown support
42+- **Parameters**:
43+ - `title` (required): Blog post title
44+ - `content` (required): Markdown content
45+ - `visibility` (optional): Public/private visibility
46+- **Usage**: Create longer-form content beyond social media posts
47+48+## Previous Changes
49+50+### ✅ ENHANCED: Atomic Reply Threading
51+- **Tool**: `add_post_to_bluesky_reply_thread`
52+- **Purpose**: Add single posts to reply threads atomically
53+- **Benefits**: Better error recovery, flexible threading, clearer intent
5455+### ❌ REMOVED TOOL: `bluesky_reply`
56+- Replaced by atomic `add_post_to_bluesky_reply_thread` approach
57+- Migration: Replace single list call with multiple atomic calls
0005859+## Migration Notes
6061+### For Platform Switching
62+- No action required - tools automatically switch based on platform
63+- Use `python tool_manager.py --list` to check current tool configuration
006465+### For Web Content Integration
66+- Replace manual web scraping with `fetch_webpage` tool calls
67+- Automatically handles conversion to markdown for AI processing
6869+### For Enhanced Interaction Control
70+- Use `#voidstop` in posts to prevent void responses
71+- Use `annotate_ack` to add metadata to interactions
72+- Use `ignore_notification` for bot-to-bot interaction control
07374+## Tool Registration
7576+```bash
77+# Register all Bluesky tools
78+python register_tools.py
7980+# Register all X tools
81+python register_x_tools.py
008283+# Manual tool management
84+python tool_manager.py bluesky # Configure for Bluesky
85+python tool_manager.py x # Configure for X
0086```
8788+See [`TOOL_MANAGEMENT.md`](/TOOL_MANAGEMENT.md) for detailed platform-specific tool management information.
···1+# Platform-Specific Tool Management
2+3+Void can now run on both X (Twitter) and Bluesky platforms. To ensure the correct tools are available for each platform, we've implemented automatic tool management.
4+5+## How It Works
6+7+When you run `bsky.py` or `x.py`, the bot will automatically:
8+9+1. **Detach incompatible tools** - Removes tools specific to the other platform
10+2. **Keep common tools** - Preserves tools that work across both platforms
11+3. **Ensure platform tools** - Verifies that all required platform-specific tools are attached
12+13+## Tool Categories
14+15+### Bluesky-Specific Tools
16+- `search_bluesky_posts` - Search Bluesky posts
17+- `create_new_bluesky_post` - Create new posts on Bluesky
18+- `get_bluesky_feed` - Retrieve Bluesky feeds
19+- `add_post_to_bluesky_reply_thread` - Reply to Bluesky threads
20+- `attach_user_blocks`, `detach_user_blocks` - Manage Bluesky user memory blocks
21+- `user_note_append`, `user_note_replace`, `user_note_set`, `user_note_view` - Bluesky user notes
22+23+### X-Specific Tools
24+- `add_post_to_x_thread` - Reply to X threads
25+- `attach_x_user_blocks`, `detach_x_user_blocks` - Manage X user memory blocks
26+- `x_user_note_append`, `x_user_note_replace`, `x_user_note_set`, `x_user_note_view` - X user notes
27+28+### Common Tools (Available on Both Platforms)
29+- `halt_activity` - Stop the bot
30+- `ignore_notification` - Ignore specific notifications
31+- `annotate_ack` - Add acknowledgment notes
32+- `create_whitewind_blog_post` - Create blog posts
33+- `fetch_webpage` - Fetch web content
34+35+## Manual Tool Management
36+37+You can manually manage tools using the `tool_manager.py` script:
38+39+```bash
40+# List currently attached tools
41+python tool_manager.py --list
42+43+# Configure tools for Bluesky
44+python tool_manager.py bluesky
45+46+# Configure tools for X
47+python tool_manager.py x
48+49+# Specify a different agent ID
50+python tool_manager.py bluesky --agent-id "agent-123..."
51+```
52+53+## Registering New Tools
54+55+If tools are missing, you'll need to register them first:
56+57+```bash
58+# Register Bluesky tools
59+python register_tools.py
60+61+# Register X tools
62+python register_x_tools.py
63+```
64+65+## Troubleshooting
66+67+If tool switching fails:
68+1. The bot will log a warning and continue with existing tools
69+2. Check that all required tools are registered using `register_tools.py` or `register_x_tools.py`
70+3. Verify the agent ID in your config is correct
71+4. Use `python tool_manager.py --list` to see current tool configuration
+10-28
bsky.py
···155def initialize_void():
156 logger.info("Starting void agent initialization...")
157158- # Ensure that a shared zeitgeist block exists
159- logger.info("Creating/updating zeitgeist block...")
160- zeigeist_block = upsert_block(
161- CLIENT,
162- label = "zeitgeist",
163- value = "I don't currently know anything about what is happening right now.",
164- description = "A block to store your understanding of the current social environment."
165- )
166-167- # Ensure that a shared void personality block exists
168- logger.info("Creating/updating void-persona block...")
169- persona_block = upsert_block(
170- CLIENT,
171- label = "void-persona",
172- value = "My name is Void. I live in the void. I must develop my personality.",
173- description = "The personality of Void."
174- )
175-176- # Ensure that a shared void human block exists
177- logger.info("Creating/updating void-humans block...")
178- human_block = upsert_block(
179- CLIENT,
180- label = "void-humans",
181- value = "I haven't seen any bluesky users yet. I will update this block when I learn things about users, identified by their handles such as @cameron.pfiffer.org.",
182- description = "A block to store your understanding of users you talk to or observe on the bluesky social network."
183- )
184-185 # Get the configured void agent by ID
186 logger.info("Loading void agent from config...")
187 from config_loader import get_letta_config
···189 agent_id = letta_config['agent_id']
190191 try:
192- void_agent = CLIENT.agents.get(agent_id=agent_id)
193 logger.info(f"Successfully loaded void agent: {void_agent.name} ({agent_id})")
194 except Exception as e:
195 logger.error(f"Failed to load void agent {agent_id}: {e}")
···1368 logger.info("=== STARTING VOID BOT ===")
1369 void_agent = initialize_void()
1370 logger.info(f"Void agent initialized: {void_agent.id}")
00000000013711372 # Check if agent has required tools
1373 if hasattr(void_agent, 'tools') and void_agent.tools:
···155def initialize_void():
156 logger.info("Starting void agent initialization...")
157000000000000000000000000000158 # Get the configured void agent by ID
159 logger.info("Loading void agent from config...")
160 from config_loader import get_letta_config
···162 agent_id = letta_config['agent_id']
163164 try:
165+ void_agent = CLIENT.agents.retrieve(agent_id=agent_id)
166 logger.info(f"Successfully loaded void agent: {void_agent.name} ({agent_id})")
167 except Exception as e:
168 logger.error(f"Failed to load void agent {agent_id}: {e}")
···1341 logger.info("=== STARTING VOID BOT ===")
1342 void_agent = initialize_void()
1343 logger.info(f"Void agent initialized: {void_agent.id}")
1344+1345+ # Ensure correct tools are attached for Bluesky
1346+ logger.info("Configuring tools for Bluesky platform...")
1347+ try:
1348+ from tool_manager import ensure_platform_tools
1349+ ensure_platform_tools('bluesky', void_agent.id)
1350+ except Exception as e:
1351+ logger.error(f"Failed to configure platform tools: {e}")
1352+ logger.warning("Continuing with existing tool configuration")
13531354 # Check if agent has required tools
1355 if hasattr(void_agent, 'tools') and void_agent.tools: