Compare commits
3 Commits
da300f75fe
...
master_sna
| Author | SHA1 | Date | |
|---|---|---|---|
| 6879a75f09 | |||
| 18f2f6f461 | |||
| 928f08cc57 |
63
AGENTS.md
63
AGENTS.md
@@ -98,3 +98,66 @@ Successfully implemented a new menu item and functionality for generating theme
|
||||
The implementation maintains backward compatibility while adding valuable feedback functionality to improve prompt generation quality over time.
|
||||
|
||||
Too many tests, so I moved all of them into the tests directory.
|
||||
|
||||
---
|
||||
|
||||
# Task: Implement feedback_historic.json cyclic buffer system (30 items)
|
||||
|
||||
## Changes Made
|
||||
|
||||
### 1. Added Feedback Historic System
|
||||
- Created `feedback_historic.json` file to store previous feedback words (without weights)
|
||||
- Implemented a cyclic buffer system with 30-item capacity (feedback00-feedback29)
|
||||
- When new feedback is generated (6 words), they become feedback00-feedback05
|
||||
- All existing items shift down by 6 positions
|
||||
- Items beyond feedback29 are discarded
|
||||
|
||||
### 2. Updated Class Initialization
|
||||
- Added `feedback_historic` attribute to `JournalPromptGenerator` class
|
||||
- Updated `__init__` method to load `feedback_historic.json`
|
||||
- Added `_load_feedback_historic()` method to load historic feedback words
|
||||
- Added `_save_feedback_historic()` method to save historic feedback words (keeping only first 30)
|
||||
|
||||
### 3. Enhanced Feedback Words Management
|
||||
- Updated `add_feedback_words_to_history()` method to:
|
||||
- Extract just the words from current feedback words (no weights)
|
||||
- Add 6 new words to the historic buffer
|
||||
- Shift all existing words down by 6 positions
|
||||
- Maintain 30-item limit by discarding oldest items
|
||||
- Updated `update_feedback_words()` to automatically call `add_feedback_words_to_history()`
|
||||
|
||||
### 4. Improved AI Prompt Generation
|
||||
- Updated `generate_theme_feedback_words()` method to include historic feedback words in API call
|
||||
- The prompt now includes three sections:
|
||||
1. Previous prompts (historic prompts)
|
||||
2. Current feedback themes (with weights)
|
||||
3. Historic feedback themes (just words, no weights)
|
||||
- This helps the AI avoid repeating previously used theme words
|
||||
|
||||
### 5. Data Structure Design
|
||||
- Historic feedback words are stored as a list of dictionaries with keys (feedback00, feedback01, etc.)
|
||||
- Each dictionary contains only the word (no weight field)
|
||||
- Structure mirrors `prompts_historic.json` but for feedback words
|
||||
- 30-item limit provides sufficient history while preventing excessive repetition
|
||||
|
||||
## Testing
|
||||
- Created comprehensive test to verify cyclic buffer functionality
|
||||
- Tested that new items are added at the beginning (feedback00-feedback05)
|
||||
- Verified that existing items shift down correctly
|
||||
- Confirmed 30-item limit is enforced (oldest items are dropped)
|
||||
- Tested that historic feedback words are included in AI prompts
|
||||
- Verified that weights are not stored in historic buffer (only words)
|
||||
|
||||
## Result
|
||||
Successfully implemented a feedback historic cyclic buffer system that:
|
||||
1. Stores previous feedback words in `feedback_historic.json` (30-item limit)
|
||||
2. Automatically adds new feedback words to history when they are updated
|
||||
3. Includes historic feedback words in AI prompts to avoid repetition
|
||||
4. Maintains consistent data structure with the rest of the system
|
||||
5. Provides a memory of previous theme words to improve AI suggestions over time
|
||||
|
||||
The system now has a complete feedback loop where:
|
||||
- Historic prompts and feedback words inform new theme word generation
|
||||
- New theme words are rated by users and become current feedback words
|
||||
- Current feedback words are added to the historic buffer
|
||||
- Historic feedback words help avoid repetition in future theme word generation
|
||||
|
||||
16
README.md
16
README.md
@@ -67,8 +67,8 @@ daily-journal-prompt/
|
||||
├── test_project.py # Test suite for the project
|
||||
├── requirements.txt # Python dependencies
|
||||
├── ds_prompt.txt # AI prompt template for generating journal prompts
|
||||
├── historic_prompts.json # History of previous 60 prompts (JSON format)
|
||||
├── pool_prompts.json # Pool of available prompts for selection (JSON format)
|
||||
├── prompts_historic.json # History of previous 60 prompts (JSON format)
|
||||
├── prompts_pool.json # Pool of available prompts for selection (JSON format)
|
||||
├── example.env # Example environment configuration
|
||||
├── .env # Your actual environment configuration (gitignored)
|
||||
├── settings.cfg # Configuration file for prompt settings and pool size
|
||||
@@ -83,8 +83,8 @@ daily-journal-prompt/
|
||||
- **test_project.py**: Test suite to verify project setup
|
||||
- **requirements.txt**: Python dependencies (openai, python-dotenv, rich)
|
||||
- **ds_prompt.txt**: The core prompt template that instructs the AI to generate new journal prompts
|
||||
- **historic_prompts.json**: JSON array containing the last 60 generated prompts (cyclic buffer)
|
||||
- **pool_prompts.json**: JSON array containing the pool of available prompts for selection
|
||||
- **prompts_historic.json**: JSON array containing the last 60 generated prompts (cyclic buffer)
|
||||
- **prompts_pool.json**: JSON array containing the pool of available prompts for selection
|
||||
- **example.env**: Template for your environment configuration
|
||||
- **.env**: Your actual environment variables (not tracked in git for security)
|
||||
- **settings.cfg**: Configuration file for prompt settings (length, count) and pool size
|
||||
@@ -185,19 +185,19 @@ python generate_prompts.py --help
|
||||
|
||||
1. User chooses to fill the prompt pool.
|
||||
2. The system reads the template from `ds_prompt.txt`
|
||||
3. It loads the previous 60 prompts from the fixed length cyclic buffer `historic_prompts.json`
|
||||
3. It loads the previous 60 prompts from the fixed length cyclic buffer `prompts_historic.json`
|
||||
4. The AI generates some number of new prompts, attempting to minimize repetition
|
||||
5. The new prompts are used to fill the prompt pool to the `settings.cfg` configured value.
|
||||
|
||||
### Prompt Selection Process
|
||||
|
||||
1. A `settings.cfg` configurable number of prompts are drawn from the prompt pool and displayed to the user.
|
||||
2. User selects one prompt for his/her journal writing session, which is added to the `historic_prompts.json` cyclic buffer.
|
||||
2. User selects one prompt for his/her journal writing session, which is added to the `prompts_historic.json` cyclic buffer.
|
||||
3. All prompts which were displayed are removed from the prompt pool permanently.
|
||||
|
||||
## 📝 Prompt Examples
|
||||
|
||||
The tool generates prompts like these (from `historic_prompts.json`):
|
||||
The tool generates prompts like these (from `prompts_historic.json`):
|
||||
|
||||
- **Memory-based**: "Describe a memory you have that is tied to a specific smell..."
|
||||
- **Creative Writing**: "Invent a mythological creature for a modern urban setting..."
|
||||
@@ -234,7 +234,7 @@ You can modify `ds_prompt.txt` to change the prompt generation parameters:
|
||||
|
||||
## 🔄 Maintaining Prompt History
|
||||
|
||||
The `historic_prompts.json` file maintains a rolling history of the last 60 prompts. This helps:
|
||||
The `prompts_historic.json` file maintains a rolling history of the last 60 prompts. This helps:
|
||||
|
||||
1. **Avoid repetition**: The AI references previous prompts to generate new, diverse topics
|
||||
2. **Track usage**: See what types of prompts have been generated
|
||||
|
||||
@@ -1,14 +0,0 @@
|
||||
Request for generation of writing prompts for journaling
|
||||
|
||||
Payload:
|
||||
The previous 60 prompts have been provided as a JSON array for reference.
|
||||
|
||||
Guidelines:
|
||||
Using the attached JSON of writing prompts, you should try to pick out four unique and intentionally vague single-word themes that apply to some portion of the list.
|
||||
Then add two more single word themes that are fairly different from the other four for a total of six words.
|
||||
|
||||
Expected Output:
|
||||
Output as a JSON list with just the six words, in lowercase.
|
||||
Despite the provided history being a keyed list or dictionary, the expected return JSON will be a simple list with no keys.
|
||||
Respond ONLY with valid JSON. No explanations, no markdown, no backticks.
|
||||
|
||||
@@ -1,20 +0,0 @@
|
||||
Request for generation of writing prompts for journaling
|
||||
|
||||
Payload:
|
||||
The previous 60 prompts have been provided as a JSON array for reference.
|
||||
|
||||
Guidelines:
|
||||
Please generate some number of individual writing prompts in English following these guidelines.
|
||||
Topics can be diverse, and the whole batch should have no outright repetition.
|
||||
These are meant to inspire one to two pages of writing in a journal as exercise.
|
||||
|
||||
Prompt History:
|
||||
The provided history brackets two mechanisms.
|
||||
The history will allow for reducing repetition, however some thematic overlap is acceptable. Try harder to avoid overlap with lower indices in the array.
|
||||
As the user discards prompts, the themes will be very slowly steered, so it's okay to take some inspiration from the history.
|
||||
|
||||
Expected Output:
|
||||
Output as a JSON list with the requested number of elements.
|
||||
Despite the provided history being a keyed list or dictionary, the expected return JSON will be a simple list with no keys.
|
||||
Respond ONLY with valid JSON. No explanations, no markdown, no backticks.
|
||||
|
||||
@@ -1,26 +0,0 @@
|
||||
[
|
||||
{
|
||||
"feedback00": "memory",
|
||||
"weight": 3
|
||||
},
|
||||
{
|
||||
"feedback01": "reflection",
|
||||
"weight": 4
|
||||
},
|
||||
{
|
||||
"feedback02": "perspective",
|
||||
"weight": 1
|
||||
},
|
||||
{
|
||||
"feedback03": "ritual",
|
||||
"weight": 6
|
||||
},
|
||||
{
|
||||
"feedback04": "invention",
|
||||
"weight": 6
|
||||
},
|
||||
{
|
||||
"feedback05": "solitude",
|
||||
"weight": 6
|
||||
}
|
||||
]
|
||||
@@ -1,12 +0,0 @@
|
||||
# settings.cfg
|
||||
# This controls how many prompts are presented and consumed from the pool, as well as how much to pre-cache.
|
||||
# This is used to maintain functionality offline for some number of iterations.
|
||||
|
||||
[prompts]
|
||||
min_length = 500
|
||||
max_length = 1000
|
||||
num_prompts = 3
|
||||
|
||||
# Pool size can affect the prompts if is too high. Default 20.
|
||||
[prefetch]
|
||||
cached_pool_volume = 20
|
||||
119
demonstrate_feedback_historic.py
Normal file
119
demonstrate_feedback_historic.py
Normal file
@@ -0,0 +1,119 @@
|
||||
#!/usr/bin/env python3
|
||||
"""
|
||||
Demonstration of the feedback_historic.json cyclic buffer system.
|
||||
"""
|
||||
|
||||
import json
|
||||
import os
|
||||
import sys
|
||||
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
|
||||
|
||||
from generate_prompts import JournalPromptGenerator
|
||||
|
||||
def demonstrate_system():
|
||||
"""Demonstrate the feedback historic system."""
|
||||
print("="*70)
|
||||
print("DEMONSTRATION: Feedback Historic Cyclic Buffer System")
|
||||
print("="*70)
|
||||
|
||||
# Create a temporary .env file
|
||||
with open(".env.demo", "w") as f:
|
||||
f.write("DEEPSEEK_API_KEY=demo_key\n")
|
||||
f.write("API_BASE_URL=https://api.deepseek.com\n")
|
||||
f.write("MODEL=deepseek-chat\n")
|
||||
|
||||
# Initialize generator
|
||||
generator = JournalPromptGenerator(config_path=".env.demo")
|
||||
|
||||
print("\n1. Initial state:")
|
||||
print(f" - feedback_words: {len(generator.feedback_words)} items")
|
||||
print(f" - feedback_historic: {len(generator.feedback_historic)} items")
|
||||
|
||||
# Create some sample feedback words
|
||||
sample_words_batch1 = [
|
||||
{"feedback00": "memory", "weight": 5},
|
||||
{"feedback01": "time", "weight": 4},
|
||||
{"feedback02": "nature", "weight": 3},
|
||||
{"feedback03": "emotion", "weight": 6},
|
||||
{"feedback04": "change", "weight": 2},
|
||||
{"feedback05": "connection", "weight": 4}
|
||||
]
|
||||
|
||||
print("\n2. Adding first batch of feedback words...")
|
||||
generator.update_feedback_words(sample_words_batch1)
|
||||
print(f" - Added 6 feedback words")
|
||||
print(f" - feedback_historic now has: {len(generator.feedback_historic)} items")
|
||||
|
||||
# Show the historic items
|
||||
print("\n Historic feedback words (no weights):")
|
||||
for i, item in enumerate(generator.feedback_historic):
|
||||
key = list(item.keys())[0]
|
||||
print(f" {key}: {item[key]}")
|
||||
|
||||
# Add second batch
|
||||
sample_words_batch2 = [
|
||||
{"feedback00": "creativity", "weight": 5},
|
||||
{"feedback01": "reflection", "weight": 4},
|
||||
{"feedback02": "growth", "weight": 3},
|
||||
{"feedback03": "transformation", "weight": 6},
|
||||
{"feedback04": "journey", "weight": 2},
|
||||
{"feedback05": "discovery", "weight": 4}
|
||||
]
|
||||
|
||||
print("\n3. Adding second batch of feedback words...")
|
||||
generator.update_feedback_words(sample_words_batch2)
|
||||
print(f" - Added 6 more feedback words")
|
||||
print(f" - feedback_historic now has: {len(generator.feedback_historic)} items")
|
||||
|
||||
print("\n Historic feedback words after second batch:")
|
||||
print(" (New words at the top, old words shifted down)")
|
||||
for i, item in enumerate(generator.feedback_historic[:12]): # Show first 12
|
||||
key = list(item.keys())[0]
|
||||
print(f" {key}: {item[key]}")
|
||||
|
||||
# Demonstrate the cyclic buffer by adding more batches
|
||||
print("\n4. Demonstrating cyclic buffer (30 item limit)...")
|
||||
print(" Adding 5 more batches (30 more words total)...")
|
||||
|
||||
for batch_num in range(3, 8):
|
||||
batch_words = []
|
||||
for j in range(6):
|
||||
batch_words.append({f"feedback{j:02d}": f"batch{batch_num}_word{j+1}", "weight": 3})
|
||||
generator.update_feedback_words(batch_words)
|
||||
|
||||
print(f" - feedback_historic now has: {len(generator.feedback_historic)} items (max 30)")
|
||||
print(f" - Oldest items have been dropped to maintain 30-item limit")
|
||||
|
||||
# Show the structure
|
||||
print("\n5. Checking file structure...")
|
||||
if os.path.exists("feedback_historic.json"):
|
||||
with open("feedback_historic.json", "r") as f:
|
||||
data = json.load(f)
|
||||
print(f" - feedback_historic.json exists with {len(data)} items")
|
||||
print(f" - First item: {data[0]}")
|
||||
print(f" - Last item: {data[-1]}")
|
||||
print(f" - Items have keys (feedback00, feedback01, etc.) but no weights")
|
||||
|
||||
# Clean up
|
||||
os.remove(".env.demo")
|
||||
if os.path.exists("feedback_words.json"):
|
||||
os.remove("feedback_words.json")
|
||||
if os.path.exists("feedback_historic.json"):
|
||||
os.remove("feedback_historic.json")
|
||||
|
||||
print("\n" + "="*70)
|
||||
print("SUMMARY:")
|
||||
print("="*70)
|
||||
print("✓ feedback_historic.json stores previous feedback words (no weights)")
|
||||
print("✓ Maximum of 30 items (feedback00-feedback29)")
|
||||
print("✓ When new feedback is generated (6 words):")
|
||||
print(" - They become feedback00-feedback05 in the historic buffer")
|
||||
print(" - All existing items shift down by 6 positions")
|
||||
print(" - Items beyond feedback29 are discarded")
|
||||
print("✓ Historic feedback words are included in AI prompts for")
|
||||
print(" generate_theme_feedback_words() to avoid repetition")
|
||||
print("="*70)
|
||||
|
||||
if __name__ == "__main__":
|
||||
demonstrate_system()
|
||||
|
||||
@@ -2,14 +2,16 @@ Request for generation of writing prompts for journaling
|
||||
|
||||
Payload:
|
||||
The previous 60 prompts have been provided as a JSON array for reference.
|
||||
The previous 6 feedback themes have been provided. You will not re-use any of these most-recently used words here.
|
||||
The current 6 feedback themes have been provided. You will not re-use any of these most-recently used words here.
|
||||
The previous 30 feedback themes are also provided. You should try to avoid re-using these unless it really makes sense to.
|
||||
|
||||
Guidelines:
|
||||
Using the attached JSON of writing prompts, you should try to pick out 4 unique and intentionally vague single-word themes that apply to some portion of the list. They can range from common to uncommon words.
|
||||
Then add 2 more single word divergent themes that are less related to the historic prompts and are somewhat different from the other 4 for a total of 6 words.
|
||||
These 2 divergent themes give the user the option to steer away from existing themes.
|
||||
Examples for the divergent themes could be the option to add a theme like technology when the other themes are related to beauty, or mortality when the other themes are very positive.
|
||||
Be creative, don't just use my example. A high temperature AI request is preferred in both divergent themes and derivative themes.
|
||||
Be creative, don't just use my example.
|
||||
A very high temperature AI response is warranted here to generate a large vocabulary.
|
||||
|
||||
Expected Output:
|
||||
Output as a JSON list with just the six words, in lowercase.
|
||||
|
||||
92
feedback_historic.json
Normal file
92
feedback_historic.json
Normal file
@@ -0,0 +1,92 @@
|
||||
[
|
||||
{
|
||||
"feedback00": "labyrinth"
|
||||
},
|
||||
{
|
||||
"feedback01": "residue"
|
||||
},
|
||||
{
|
||||
"feedback02": "tremor"
|
||||
},
|
||||
{
|
||||
"feedback03": "effigy"
|
||||
},
|
||||
{
|
||||
"feedback04": "quasar"
|
||||
},
|
||||
{
|
||||
"feedback05": "gossamer"
|
||||
},
|
||||
{
|
||||
"feedback06": "resonance"
|
||||
},
|
||||
{
|
||||
"feedback07": "erosion"
|
||||
},
|
||||
{
|
||||
"feedback08": "surrender"
|
||||
},
|
||||
{
|
||||
"feedback09": "excess"
|
||||
},
|
||||
{
|
||||
"feedback10": "chaos"
|
||||
},
|
||||
{
|
||||
"feedback11": "fabric"
|
||||
},
|
||||
{
|
||||
"feedback12": "palimpsest"
|
||||
},
|
||||
{
|
||||
"feedback13": "lacuna"
|
||||
},
|
||||
{
|
||||
"feedback14": "efflorescence"
|
||||
},
|
||||
{
|
||||
"feedback15": "tessellation"
|
||||
},
|
||||
{
|
||||
"feedback16": "sublimation"
|
||||
},
|
||||
{
|
||||
"feedback17": "vertigo"
|
||||
},
|
||||
{
|
||||
"feedback18": "artifact"
|
||||
},
|
||||
{
|
||||
"feedback19": "mycelium"
|
||||
},
|
||||
{
|
||||
"feedback20": "threshold"
|
||||
},
|
||||
{
|
||||
"feedback21": "cartography"
|
||||
},
|
||||
{
|
||||
"feedback22": "spectacle"
|
||||
},
|
||||
{
|
||||
"feedback23": "friction"
|
||||
},
|
||||
{
|
||||
"feedback24": "mutation"
|
||||
},
|
||||
{
|
||||
"feedback25": "echo"
|
||||
},
|
||||
{
|
||||
"feedback26": "repair"
|
||||
},
|
||||
{
|
||||
"feedback27": "velocity"
|
||||
},
|
||||
{
|
||||
"feedback28": "syntax"
|
||||
},
|
||||
{
|
||||
"feedback29": "divergence"
|
||||
}
|
||||
]
|
||||
@@ -1,26 +1,26 @@
|
||||
[
|
||||
{
|
||||
"feedback00": "echo",
|
||||
"feedback00": "labyrinth",
|
||||
"weight": 3
|
||||
},
|
||||
{
|
||||
"feedback01": "artifact",
|
||||
"feedback01": "residue",
|
||||
"weight": 3
|
||||
},
|
||||
{
|
||||
"feedback02": "velocity",
|
||||
"weight": 0
|
||||
"feedback02": "tremor",
|
||||
"weight": 3
|
||||
},
|
||||
{
|
||||
"feedback03": "syntax",
|
||||
"weight": 0
|
||||
"feedback03": "effigy",
|
||||
"weight": 3
|
||||
},
|
||||
{
|
||||
"feedback04": "divergence",
|
||||
"weight": 6
|
||||
"feedback04": "quasar",
|
||||
"weight": 3
|
||||
},
|
||||
{
|
||||
"feedback05": "oblivion",
|
||||
"weight": 6
|
||||
"feedback05": "gossamer",
|
||||
"weight": 3
|
||||
}
|
||||
]
|
||||
@@ -31,6 +31,7 @@ class JournalPromptGenerator:
|
||||
self.historic_prompts = []
|
||||
self.pool_prompts = []
|
||||
self.feedback_words = []
|
||||
self.feedback_historic = []
|
||||
self.prompt_template = ""
|
||||
self.settings = {}
|
||||
|
||||
@@ -43,6 +44,7 @@ class JournalPromptGenerator:
|
||||
self._load_historic_prompts()
|
||||
self._load_pool_prompts()
|
||||
self._load_feedback_words()
|
||||
self._load_feedback_historic()
|
||||
|
||||
def _load_config(self):
|
||||
"""Load configuration from environment file."""
|
||||
@@ -122,13 +124,13 @@ class JournalPromptGenerator:
|
||||
def _load_historic_prompts(self):
|
||||
"""Load historic prompts from JSON file."""
|
||||
try:
|
||||
with open("historic_prompts.json", "r") as f:
|
||||
with open("prompts_historic.json", "r") as f:
|
||||
self.historic_prompts = json.load(f)
|
||||
except FileNotFoundError:
|
||||
self.console.print("[yellow]Warning: historic_prompts.json not found, starting with empty history[/yellow]")
|
||||
self.console.print("[yellow]Warning: prompts_historic.json not found, starting with empty history[/yellow]")
|
||||
self.historic_prompts = []
|
||||
except json.JSONDecodeError:
|
||||
self.console.print("[yellow]Warning: historic_prompts.json is corrupted, starting with empty history[/yellow]")
|
||||
self.console.print("[yellow]Warning: prompts_historic.json is corrupted, starting with empty history[/yellow]")
|
||||
self.historic_prompts = []
|
||||
|
||||
def _save_historic_prompts(self):
|
||||
@@ -137,19 +139,19 @@ class JournalPromptGenerator:
|
||||
if len(self.historic_prompts) > 60:
|
||||
self.historic_prompts = self.historic_prompts[:60]
|
||||
|
||||
with open("historic_prompts.json", "w") as f:
|
||||
with open("prompts_historic.json", "w") as f:
|
||||
json.dump(self.historic_prompts, f, indent=2)
|
||||
|
||||
def _load_pool_prompts(self):
|
||||
"""Load pool prompts from JSON file."""
|
||||
try:
|
||||
with open("pool_prompts.json", "r") as f:
|
||||
with open("prompts_pool.json", "r") as f:
|
||||
self.pool_prompts = json.load(f)
|
||||
except FileNotFoundError:
|
||||
self.console.print("[yellow]Warning: pool_prompts.json not found, starting with empty pool[/yellow]")
|
||||
self.console.print("[yellow]Warning: prompts_pool.json not found, starting with empty pool[/yellow]")
|
||||
self.pool_prompts = []
|
||||
except json.JSONDecodeError:
|
||||
self.console.print("[yellow]Warning: pool_prompts.json is corrupted, starting with empty pool[/yellow]")
|
||||
self.console.print("[yellow]Warning: prompts_pool.json is corrupted, starting with empty pool[/yellow]")
|
||||
self.pool_prompts = []
|
||||
|
||||
def _load_feedback_words(self):
|
||||
@@ -164,14 +166,35 @@ class JournalPromptGenerator:
|
||||
self.console.print("[yellow]Warning: feedback_words.json is corrupted, starting with empty feedback words[/yellow]")
|
||||
self.feedback_words = []
|
||||
|
||||
def _load_feedback_historic(self):
|
||||
"""Load historic feedback words from JSON file."""
|
||||
try:
|
||||
with open("feedback_historic.json", "r") as f:
|
||||
self.feedback_historic = json.load(f)
|
||||
except FileNotFoundError:
|
||||
self.console.print("[yellow]Warning: feedback_historic.json not found, starting with empty feedback history[/yellow]")
|
||||
self.feedback_historic = []
|
||||
except json.JSONDecodeError:
|
||||
self.console.print("[yellow]Warning: feedback_historic.json is corrupted, starting with empty feedback history[/yellow]")
|
||||
self.feedback_historic = []
|
||||
|
||||
def _save_feedback_words(self):
|
||||
"""Save feedback words to JSON file."""
|
||||
with open("feedback_words.json", "w") as f:
|
||||
json.dump(self.feedback_words, f, indent=2)
|
||||
|
||||
def _save_feedback_historic(self):
|
||||
"""Save historic feedback words to JSON file (keeping only first 30)."""
|
||||
# Keep only the first 30 feedback words (newest are at the beginning)
|
||||
if len(self.feedback_historic) > 30:
|
||||
self.feedback_historic = self.feedback_historic[:30]
|
||||
|
||||
with open("feedback_historic.json", "w") as f:
|
||||
json.dump(self.feedback_historic, f, indent=2)
|
||||
|
||||
def _save_pool_prompts(self):
|
||||
"""Save pool prompts to JSON file."""
|
||||
with open("pool_prompts.json", "w") as f:
|
||||
with open("prompts_pool.json", "w") as f:
|
||||
json.dump(self.pool_prompts, f, indent=2)
|
||||
|
||||
def add_prompts_to_pool(self, prompts: List[str]):
|
||||
@@ -237,21 +260,53 @@ class JournalPromptGenerator:
|
||||
self.historic_prompts = updated_prompts
|
||||
self._save_historic_prompts()
|
||||
|
||||
def _prepare_prompt(self) -> str:
|
||||
"""Prepare the full prompt with historic context."""
|
||||
# Format historic prompts for the AI
|
||||
if self.historic_prompts:
|
||||
historic_context = json.dumps(self.historic_prompts, indent=2)
|
||||
full_prompt = f"{self.prompt_template}\n\nPrevious prompts:\n{historic_context}"
|
||||
else:
|
||||
full_prompt = self.prompt_template
|
||||
def add_feedback_words_to_history(self):
|
||||
"""
|
||||
Add current feedback words to the historic feedback words cyclic buffer.
|
||||
The 6 new feedback words become feedback00-feedback05, all others shift down,
|
||||
and feedback29 is discarded (keeping only 30 items total).
|
||||
"""
|
||||
# Extract just the words from the current feedback words
|
||||
# Current feedback_words structure: [{"feedback00": "word", "weight": 3}, ...]
|
||||
new_feedback_words = []
|
||||
|
||||
# Add feedback words if available
|
||||
if self.feedback_words:
|
||||
feedback_context = json.dumps(self.feedback_words, indent=2)
|
||||
full_prompt = f"{full_prompt}\n\nFeedback words:\n{feedback_context}"
|
||||
for i, feedback_item in enumerate(self.feedback_words):
|
||||
# Get the word from the feedback item (key is feedback00, feedback01, etc.)
|
||||
feedback_key = f"feedback{i:02d}"
|
||||
if feedback_key in feedback_item:
|
||||
word = feedback_item[feedback_key]
|
||||
# Create new feedback word object with just the word (no weight)
|
||||
new_feedback_words.append({
|
||||
feedback_key: word
|
||||
})
|
||||
|
||||
return full_prompt
|
||||
# If we don't have 6 feedback words, we can't add them to history
|
||||
if len(new_feedback_words) != 6:
|
||||
self.console.print(f"[yellow]Warning: Expected 6 feedback words, got {len(new_feedback_words)}. Not adding to history.[/yellow]")
|
||||
return
|
||||
|
||||
# Shift all existing feedback words down by 6 positions
|
||||
# We'll create a new list starting with the 6 new feedback words
|
||||
updated_feedback_historic = new_feedback_words
|
||||
|
||||
# Add all existing feedback words, shifting their numbers down by 6
|
||||
for i, feedback_dict in enumerate(self.feedback_historic):
|
||||
if i >= 24: # We only keep 30 feedback words total (00-29), and we've already added 6
|
||||
break
|
||||
|
||||
# Get the feedback word
|
||||
feedback_key = list(feedback_dict.keys())[0]
|
||||
word = feedback_dict[feedback_key]
|
||||
|
||||
# Create feedback word with new number (shifted down by 6)
|
||||
new_feedback_key = f"feedback{i+6:02d}"
|
||||
updated_feedback_historic.append({
|
||||
new_feedback_key: word
|
||||
})
|
||||
|
||||
self.feedback_historic = updated_feedback_historic
|
||||
self._save_feedback_historic()
|
||||
self.console.print("[green]Added 6 feedback words to history[/green]")
|
||||
|
||||
def _parse_ai_response(self, response_content: str) -> List[str]:
|
||||
"""
|
||||
@@ -550,10 +605,15 @@ class JournalPromptGenerator:
|
||||
historic_context = json.dumps(self.historic_prompts, indent=2)
|
||||
full_prompt = f"{feedback_template}\n\nPrevious prompts:\n{historic_context}"
|
||||
|
||||
# Add feedback words if available
|
||||
# Add current feedback words if available (with weights)
|
||||
if self.feedback_words:
|
||||
feedback_context = json.dumps(self.feedback_words, indent=2)
|
||||
full_prompt = f"{full_prompt}\n\nPrevious feedback themes:\n{feedback_context}"
|
||||
full_prompt = f"{full_prompt}\n\nCurrent feedback themes (with weights):\n{feedback_context}"
|
||||
|
||||
# Add historic feedback words if available (just words, no weights)
|
||||
if self.feedback_historic:
|
||||
feedback_historic_context = json.dumps(self.feedback_historic, indent=2)
|
||||
full_prompt = f"{full_prompt}\n\nHistoric feedback themes (just words):\n{feedback_historic_context}"
|
||||
else:
|
||||
self.console.print("[yellow]Warning: No historic prompts available for feedback analysis[/yellow]")
|
||||
return []
|
||||
@@ -681,6 +741,9 @@ class JournalPromptGenerator:
|
||||
self._save_feedback_words()
|
||||
self.console.print(f"[green]Updated feedback words with {len(new_feedback_items)} items[/green]")
|
||||
|
||||
# Also add the new feedback words to the historic buffer
|
||||
self.add_feedback_words_to_history()
|
||||
|
||||
def display_prompts(self, prompts: List[str]):
|
||||
"""Display generated prompts in a nice format."""
|
||||
self.console.print("\n" + "="*60)
|
||||
|
||||
@@ -1,182 +0,0 @@
|
||||
[
|
||||
{
|
||||
"prompt00": "Recall a piece of art\u2014a painting, song, film\u2014that initially confused or repelled you, but that you later came to appreciate or love. Describe your first, negative reaction in detail. Then, trace the journey to understanding. What changed in you or your context that allowed a new interpretation? Write about the value of sitting with discomfort and the rewards of having your internal syntax for beauty challenged and expanded."
|
||||
},
|
||||
{
|
||||
"prompt01": "Imagine your life as a vast, intricate tapestry. Describe the overall scene it depicts. Now, find a single, loose thread\u2014a small regret, an unresolved question, a path not taken. Write about gently pulling on that thread. What part of the tapestry begins to unravel? What new pattern or image is revealed\u2014or destroyed\u2014by following this divergence? Is the act one of repair or deconstruction?"
|
||||
},
|
||||
{
|
||||
"prompt02": "Recall a dream that felt more real than waking life. Describe its internal logic, its emotional palette, and its lingering aftertaste. Now, write a 'practical guide' for navigating that specific dreamscape, as if for a tourist. What are the rules? What should one avoid? What treasures might be found? By treating the dream as a tangible place, what insights do you gain about the concerns of your subconscious?"
|
||||
},
|
||||
{
|
||||
"prompt03": "Describe a public space you frequent (a library, a cafe, a park) at the exact moment it opens or closes. Capture the transition from emptiness to potential, or from activity to stillness. Focus on the staff or custodians who facilitate this transition\u2014the unseen architects of these daily cycles. Write from the perspective of the space itself as it breathes in or out its human occupants. What residue of the day does it hold in the quiet?"
|
||||
},
|
||||
{
|
||||
"prompt04": "Listen to a piece of music you know well, but focus exclusively on a single instrument or voice that usually resides in the background. Follow its thread through the entire composition. Describe its journey: when does it lead, when does it harmonize, when does it fall silent? Now, write a short story where this supporting element is the main character. How does shifting your auditory focus create a new narrative from familiar material?"
|
||||
},
|
||||
{
|
||||
"prompt05": "Describe your reflection in a window at night, with the interior light creating a double exposure of your face and the dark world outside. What two versions of yourself are superimposed? Write a conversation between the 'inside' self, defined by your private space, and the 'outside' self, defined by the anonymous night. What do they want from each other? How does this liminal artifact\u2014the glass\u2014both separate and connect these identities?"
|
||||
},
|
||||
{
|
||||
"prompt06": "Imagine you are a diver exploring the deep ocean of your own memory. Choose a specific, vivid memory and describe it as a submerged landscape. What creatures (emotions) swim there? What is the water pressure (emotional weight) like? Now, imagine a small, deliberate act of forgetting\u2014letting a single detail of that memory dissolve into the murk. How does this selective oblivion change the entire ecosystem of that recollection? Does it create space for new growth, or does it feel like a loss of truth?"
|
||||
},
|
||||
{
|
||||
"prompt07": "Recall a conversation that ended in a misunderstanding that was never resolved. Re-write the exchange, but introduce a single point of divergence\u2014one person says something slightly different, or pauses a moment longer. How does this tiny change alter the entire trajectory of the conversation and potentially the relationship? Explore the butterfly effect in human dialogue."
|
||||
},
|
||||
{
|
||||
"prompt08": "Spend 15 minutes in complete silence, actively listening for the absence of a specific sound that is usually present (e.g., traffic, refrigerator hum, birds). Describe the quality of this crafted silence. What smaller sounds emerge in the void? How does your mind and body react to the deliberate removal of this sonic artifact? Explore the concept of oblivion as an active, perceptible state rather than a mere lack."
|
||||
},
|
||||
{
|
||||
"prompt09": "Describe a skill or talent you possess that feels like it's fading from lack of use\u2014a language getting rusty, a sport you no longer play, an instrument gathering dust. Perform or practice it now, even if clumsily. Chronicle the physical and mental sensations of re-engagement. What echoes of proficiency remain? Is the knowledge truly gone, or merely dormant? Write about the relationship between mastery and oblivion."
|
||||
},
|
||||
{
|
||||
"prompt10": "Choose a common word (e.g., 'home,' 'work,' 'friend') and dissect its personal syntax. What rules, associations, and exceptions have you built around its meaning? Now, deliberately break one of those rules. Use the word in a context or with a definition that feels wrong to you. Write a paragraph that forces this new usage. How does corrupting your own internal language create space for new understanding?"
|
||||
},
|
||||
{
|
||||
"prompt11": "Contemplate a personal habit or pattern you wish to change. Instead of focusing on breaking it, imagine it diverging\u2014mutating into a new, slightly different pattern. Describe the old habit in detail, then design its evolved form. What small, intentional twist could redirect its energy? Write about a day living with this divergent habit. How does a shift in perspective, rather than eradication, alter your relationship to it?"
|
||||
},
|
||||
{
|
||||
"prompt12": "Describe a routine journey you make (a commute, a walk to the store) but narrate it as if you are a traveler in a foreign, slightly surreal land. Give fantastical names to ordinary landmarks. Interpret mundane events as portents or rituals. What hidden narrative or mythic structure can you impose on this familiar path? How does this reframing reveal the magic latent in the everyday?"
|
||||
},
|
||||
{
|
||||
"prompt13": "Imagine a place from your childhood that no longer exists in its original form\u2014a demolished building, a paved-over field, a renovated room. Reconstruct it from memory with all its sensory details. Now, write about the process of its erasure. Who decided it should change? What was lost in the transition, and what, if anything, was gained? How does the ghost of that place still influence the geography of your memory?"
|
||||
},
|
||||
{
|
||||
"prompt14": "You find an old, functional algorithm\u2014a recipe card, a knitting pattern, a set of instructions for assembling furniture. Follow it to the letter, but with a new, meditative attention to each step. Describe the process not as a means to an end, but as a ritual in itself. What resonance does this deliberate, prescribed action have? Does the final product matter, or has the value been in the structured journey?"
|
||||
},
|
||||
{
|
||||
"prompt15": "Imagine knowledge and ideas spread through a community not like a virus, but like a mycelium\u2014subterranean, cooperative, nutrient-sharing. Recall a time you learned something profound from an unexpected or unofficial source. Trace the hidden network that brought that wisdom to you. How many people and experiences were unknowingly part of that fruiting? Write a thank you to this invisible web."
|
||||
},
|
||||
{
|
||||
"prompt16": "Imagine your creative or problem-solving process is a mycelial network. A question or idea is dropped like a spore onto this vast, hidden web. Describe the journey of this spore as it sends out filaments, connects with distant nodes of memory and knowledge, and eventually fruits as an 'aha' moment or a new creation. How does this model differ from a linear, step-by-step algorithm? What does it teach you about patience and indirect growth?"
|
||||
},
|
||||
{
|
||||
"prompt17": "You are an archaeologist of the future, excavating the site of your own desk or kitchen counter. Treat the mundane objects you find as sacred artifacts. Create a detailed cartography of their arrangement. What does their spatial relationship suggest about the rituals of their user? What story does the wear pattern on a specific spot tell? Write your excavation report, inferring a civilization's values from its domestic debris."
|
||||
},
|
||||
{
|
||||
"prompt18": "Create a cartography of a significant year in your life, but map it as a celestial chart rather than a landmass. What were the major constellations (events, people) and how were they arranged? What were the dark spaces between them? Trace the orbital paths of your passions and fears. Now, imagine drawing navigation lines between these stars to create a new constellation with a name that defines that year's core lesson. What shape does it form?"
|
||||
},
|
||||
{
|
||||
"prompt19": "Consider the mycelium of your social world\u2014the vast, often invisible network of connections, acquaintances, and weak ties that underpin your community. Choose one person you know only peripherally. Imagine the intricate web of relationships and experiences that connects you to them, however faintly. Write a speculative biography of this person based on the subtle, subliminal cues you've gathered. How does this exercise in connection alter your sense of isolation or belonging?"
|
||||
},
|
||||
{
|
||||
"prompt20": "Imagine you are a cartographer of your own mind. Draw a map of a recent emotional landscape, labeling its features: the Swamp of Indecision, the Peak of Sudden Joy, the Quiet Forest of Contentment. What are the borders and territories? What hidden paths connect them? Now, consider the mycelial network of thoughts and memories beneath the surface, unseen but connecting everything. How does mapping the internal terrain change your relationship to its weather?"
|
||||
},
|
||||
{
|
||||
"prompt21": "\"Examine the syntax of a city block you know well. Read its buildings like sentences, its intersections like punctuation, the flow of traffic like grammar. What is the block's dominant tense (past, present, future)? Its mood? Now, rewrite one element\u2014change a shop's sign in your mind, imagine a tree where there is concrete, slow the traffic to a standstill. Describe the block under this new syntactic rule. How does re-parsing a familiar place change your relationship to it?\","
|
||||
},
|
||||
{
|
||||
"prompt22": "\"Describe the velocity of your thoughts first thing in the morning as you lie in bed before rising. Are they slow and viscous, or do they race ahead to the day? Trace the arc of this mental speed as you move through your morning routine. What actions slow it down? What triggers accelerate it? Write about attempting to deliberately modulate this internal tempo. How does controlling the speed of thought affect your anxiety, creativity, or presence?\","
|
||||
},
|
||||
{
|
||||
"prompt23": "\"Recall a conversation where the emotional velocity shifted dramatically\u2014from calm to stormy, from slow to fast, or vice versa. Map this shift. What was the catalyst word, glance, or silence? Describe the before and after as different climates. How did you navigate the change in pace? Write the dialogue not as it was spoken, but as you felt it in your body\u2014a script of accelerations and decelerations. What does this teach you about the thermodynamics of human interaction?\","
|
||||
},
|
||||
{
|
||||
"prompt24": "\"Stand perfectly still in a busy place (a park, a train station, a street corner). Observe the velocity of the world flowing around you\u2014people, vehicles, pigeons, leaves. Describe this flow as a force of nature. Now, focus on the small, still points within the chaos: a statue, a person sitting on a bench, a building's corner. Write about the experience of being a temporary still point. How does this shift in perspective affect your sense of self within the collective motion? What echoes of past stillness does it evoke?\","
|
||||
},
|
||||
{
|
||||
"prompt25": "\"You are given a box labeled 'Syntactic Fragments.' Inside are torn pieces of paper, each with a phrase that seems part of a larger, unknown set of rules (e.g., 'if the moon is high,' 'always counter-clockwise,' 'except on Sundays'). Arrange a few of these fragments into a new, personal rule for living. Write the full 'rule' they inspire, and then describe a day lived deliberately according to this strange, assembled syntax. What new logic emerges? How does it alter your perception of order and meaning?\","
|
||||
},
|
||||
{
|
||||
"prompt26": "\"Find an artifact of velocity in your world\u2014a worn-out shoe sole, a smoothed-down stair railing, a particular bend in a path where the grass is beaten down. Examine it as an archaeologist would. What story of repeated motion, pressure, and passage does it tell? Who or what created this evidence of speed or frequent travel? Write from the perspective of the path or object itself, chronicling the countless transits it has silently witnessed and absorbed.\","
|
||||
},
|
||||
{
|
||||
"prompt27": "\"Describe a moment when you felt a sudden, overwhelming sense of velocity\u2014not just physical speed, but the feeling of life accelerating, decisions piling up, or time slipping through your fingers. Where were you? What triggered this sensation? Explore the contrast between the frantic pace and your desire for stillness. How did you respond? Did you try to brake, or did you surrender to the momentum? Reflect on what this experience taught you about your relationship with time and urgency.\","
|
||||
},
|
||||
{
|
||||
"prompt28": "Analyze the syntax of a recurring dream or nightmare. What are its consistent elements (settings, characters, actions) and its variables? What is the underlying grammatical rule of this dreamscape? Write a new 'scene' in this dream's language, adhering to its strange logic. What might this internal syntax be trying to construct or communicate?"
|
||||
},
|
||||
{
|
||||
"prompt29": "Find an object in nature that serves as an artifact of a process\u2014a smooth stone (water's work), a seashell (a creature's former home), a fallen leaf (a season's turn). Describe it as evidence. What story of transformation, pressure, or time does it tell? Write from the perspective of the elemental force that created it, explaining its methodology."
|
||||
},
|
||||
{
|
||||
"prompt30": "Recall a phrase or sentence someone said to you long ago that has become a kind of mental echo, recurring at unexpected times. Why has it stuck? How has its meaning morphed with each repetition in your mind? Write a letter to the person who said it (you don't have to send it) explaining how their words have lived on inside you, far beyond their original intent."
|
||||
},
|
||||
{
|
||||
"prompt31": "Listen for an echo in your physical environment\u2014your voice in a stairwell, a sound bouncing off a building. Describe its decay, its distortion. Now, consider an echo in your life: a piece of advice that returns to you, a pattern repeating, a consequence of an old action rippling forward. Personify this echo. What message is it trying to deliver through its repetition?"
|
||||
},
|
||||
{
|
||||
"prompt32": "Describe a conversation you had where the words spoken were just the surface syntax. What was the true dialogue happening beneath\u2014in the pauses, the glances, the body language? Decode that subtext. Write the exchange as two columns: the spoken words on the left, and the real, unspoken meaning on the right. What does this reveal about the art of human communication?"
|
||||
},
|
||||
{
|
||||
"prompt33": "You are handed a key to a room you didn't know existed. Describe the threshold: the door's material, the lock's sound, the feel of the key turning. Cross into the room. What does it contain? Focus not on fantastical treasures, but on things that feel intimately, unsettlingly familiar, as if they've been waiting for you. What does this space ask you to remember or acknowledge?"
|
||||
},
|
||||
{
|
||||
"prompt34": "Imagine you discover a forgotten artifact in your attic or basement\u2014a ticket stub, a faded postcard, a broken toy. Describe it with the reverence of an archaeologist. What story does this object tell about a past version of you or your family? Now, write the narrative of the day it was first acquired or used. How does this echo of a former life resonate with your present? Consider the weight of memory that physical objects can hold."
|
||||
},
|
||||
{
|
||||
"prompt35": "Recall a time you were an outsider, entering a group or situation where you didn't know the rules. Describe the sensory details of that space and the subtle cues you missed. How did you learn to navigate? Did you assimilate, remain on the periphery, or leave? Reflect on the wisdom gained from being the novice, and the empathy it might foster for other outsiders you encounter."
|
||||
},
|
||||
{
|
||||
"prompt36": "Write a review of today as if it were a product, a film, or a restaurant. Give it a star rating. Detail its pros and cons, its pacing, its standout features, and its flaws. Who would you recommend it to? Be both brutally honest and strangely objective. How does framing your lived experience as something to be critiqued change your perception of its value?"
|
||||
},
|
||||
{
|
||||
"prompt37": "Describe a piece of furniture in your home not by its appearance, but by its function in your emotional geography. Is your bed an island of respite? Is your kitchen table a stage for negotiation? Is a certain chair a vessel for contemplation? Narrate a typical interaction with this piece. What secrets has it absorbed? If it were to be replaced, what intangible quality would be hardest to replicate?"
|
||||
},
|
||||
{
|
||||
"prompt38": "Document the journey of a single breath. Start with the intention to inhale. Follow the air's path into your body, the expansion, the microscopic exchange. Then, trace the exhale out into the room, imagining its dispersal into the wider atmosphere. Where might its molecules travel next? Anchor yourself in this most fundamental rhythm. How does focusing on this autonomic process alter your sense of time and connection to the biosphere?"
|
||||
},
|
||||
{
|
||||
"prompt39": "Describe your shadow at three different times today: dawn, noon, and dusk. Note its length, its sharpness, its behavior. Personify it. Is it a loyal follower, a stretched parody, a separate entity with its own agenda? Write a monologue from your shadow's perspective. What does it think of your daily pursuits? What does it see that you miss? Explore the duality of being both the caster and the cast."
|
||||
},
|
||||
{
|
||||
"prompt40": "Contemplate the concept of 'repair.' Choose something in your environment that is broken, frayed, or worn\u2014a relationship, an object, a habit. Describe the damage with forensic honesty. Now, instead of replacing or discarding it, imagine meticulously repairing it. What tools and materials would you need? What skills must you learn? Describe the slow, patient process of restoration. How does the value of the thing change when it bears the visible marks of its mending?"
|
||||
},
|
||||
{
|
||||
"prompt41": "Imagine you are tasked with archiving the contents of a single drawer in your home for a future museum of ordinary life. Select the drawer and catalog each item with the care of a curator. For each object, write a brief label explaining its function, origin, and emotional significance. What story does this collection tell about its owner? What might an archaeologist in 2224 misinterpret? Reflect on the biography of a life told through these accumulated fragments."
|
||||
},
|
||||
{
|
||||
"prompt42": "Document the sounds of a single hour in your life, from the most prominent noise to the nearly inaudible background hum. Create a soundscape in words. Then, imagine composing a piece of music based on this sonic profile. What instruments would you use? What would the tempo and mood be? How does listening to your life as music change your perception of its rhythm and harmony?"
|
||||
},
|
||||
{
|
||||
"prompt43": "You are asked to contribute an item to a time capsule that will be opened in 100 years. The item should represent the essence of daily life in your community now. What do you choose, and why? Write the explanatory note that will accompany it. Consider the mundane artifacts that future historians might prize. What message are you implicitly sending about what you value, fear, or find ordinary?"
|
||||
},
|
||||
{
|
||||
"prompt44": "Describe the process of waiting for something important. Break down the physical sensations: the checking of clocks, the fidgeting, the way the room seems to change. Chronicle the internal monologue that cycles through hope, doubt, rehearsal, and resignation. How do you pass the time? Find meaning in the liminal space of anticipation itself, separate from the outcome you await."
|
||||
},
|
||||
{
|
||||
"prompt45": "You receive a package with no return address. Inside is an object that seems intimately connected to you, but you cannot recall ever owning it. Describe the object with forensic detail\u2014its weight, its material, any inscriptions. How does handling it make you feel? Write the story of its imagined journey to your doorstep. What mystery does it represent, and will you try to solve it or simply let it be?"
|
||||
},
|
||||
{
|
||||
"prompt46": "Describe your relationship with a particular type of weather (e.g., thunderstorms, fog, blistering heat). Do you seek it out or avoid it? Recall a specific, vivid encounter with this weather that left a mark on you. How does your body respond to its approach? Personify this weather as a recurring character in your life story. What role does it play\u2014antagonist, comforter, catalyst for change?"
|
||||
},
|
||||
{
|
||||
"prompt47": "Recall a time you were profoundly lost, either literally or metaphorically. Describe the landscape of that disorientation\u2014the fading landmarks, the growing panic or curiosity, the quality of the light. How did you eventually find your way, or decide on a direction? Explore what that period of being untethered taught you about navigation, trust, and the value of sometimes not knowing where you are going."
|
||||
},
|
||||
{
|
||||
"prompt48": "You are tasked with designing a new public holiday that addresses a modern need for connection or reflection. What is its name, and on what date does it fall? Describe its rituals, symbols, and traditional foods. How do people prepare for it, and what activities are encouraged or forbidden? Write a personal account of experiencing this holiday for the first time, focusing on the emotions it evokes and the societal gaps it aims to fill."
|
||||
},
|
||||
{
|
||||
"prompt49": "Choose a street you walk down often. Today, walk it with the mission of noticing five things you've never seen before. They can be tiny: a crack in the pavement shaped like a continent, a particular stain on a wall, a hidden doorbell. Document each discovery in detail. Then, reflect on the phenomenon of selective attention. What had you been filtering out, and why? How does this exercise change your sense of the familiar path?"
|
||||
},
|
||||
{
|
||||
"prompt50": "Imagine you could host a dinner party for three fictional characters from different books, films, or myths. Who would you invite and why? Don't just list them. Set the scene: the table setting, the menu, the lighting. Write the conversation that unfolds. What would they argue about? What surprising common ground might they find? How would their presence challenge or affirm your own worldview? Let the dialogue reveal their core natures."
|
||||
},
|
||||
{
|
||||
"prompt51": "Describe a taste you loved as a child but have since grown indifferent to or now dislike. Recreate the sensory memory of that taste with precision. What was its context? Who was with you? Now, analyze the shift. Did your palate change, or did the associations sour? Is there a way to reclaim the innocent pleasure of that taste, or is its loss a necessary marker of growing up? Explore the nostalgia and slight grief in outgrowing a flavor."
|
||||
},
|
||||
{
|
||||
"prompt52": "Contemplate the concept of 'waste' in your daily life. Choose one item destined for the trash or recycling. Trace its journey backwards from your hand to its origins as raw material. Then, project its journey forward after it leaves your custody. What systems does it touch? What hands might process it? Write a biography of this discarded object, granting it dignity and narrative. How does this perspective alter your sense of responsibility and connection?"
|
||||
},
|
||||
{
|
||||
"prompt53": "Invent a small, personal ritual you could perform to mark the transition from one part of your day to another (e.g., work to home, waking to activity). Describe each step with deliberate, sensory care. What object is involved? What words, if any, are said? How does your posture change? The goal isn't superstition, but mindfulness. Write about performing this ritual for a week. What subtle shifts in your awareness might it create? How does deliberately carving out a threshold affect your experience of time?"
|
||||
},
|
||||
{
|
||||
"prompt54": "Consider a piece of music that feels like a physical space to you\u2014a song you can walk into. Describe the architecture of this auditory landscape. What is the floor made of? How high is the ceiling? What color is the light? Where are the shadows? What happens to your body and breath as you move through its sections\u2014the verses, the chorus, the bridge? Is it a place of refuge, confrontation, or memory? Explore how sound can build an environment you inhabit, not just hear."
|
||||
},
|
||||
{
|
||||
"prompt55": "Describe your ideal sanctuary\u2014not a grand fantasy, but a realistically attainable space you could create. Detail its location, size, lighting, furnishings, and most importantly, its rules (e.g., 'no devices,' 'only music without words,' 'must contain something living'). What specific activities would you do there? What state of mind does this space architecturally encourage? How would visiting it regularly change the rhythm of your weeks?"
|
||||
},
|
||||
{
|
||||
"prompt56": "Describe a skill or piece of knowledge you possess that you learned in an unconventional, self-taught, or accidental way. Detail the messy, non-linear process of that learning. Who or what were your unlikely teachers? Celebrate the inefficiency and personal quirks of your method. How does this 'uncurated' knowledge differ in feel and application from something you were formally taught?"
|
||||
},
|
||||
{
|
||||
"prompt57": "Think of a skill or piece of knowledge you possess that feels almost instinctual, something you can do without conscious thought (like riding a bike, typing, or a native language's grammar). Deconstruct this automatic competence. Describe the first clumsy attempts to learn it, the plateau of frustration, the moment it 'clicked' into muscle memory. Explore the duality of this knowledge: how it is both a part of you and a separate tool. What does this ingrained ability allow you to forget, and what freedom does that forgetfulness grant?"
|
||||
},
|
||||
{
|
||||
"prompt58": "Choose a natural element you feel a kinship with\u2014fire, stone, water, wind, or earth. Personify it deeply: give it desires, memories, a voice. Write a monologue from its perspective about its ancient, slow existence and its observations of human brevity and frenzy. Then, write about a moment in your life when you felt most aligned with this element's essence. How does connecting with this primal force alter your sense of time and scale?"
|
||||
},
|
||||
{
|
||||
"prompt59": "Imagine you could preserve one hour from your recent memory in a vial, to be re-experienced fully at a future date. Which hour would you choose? Describe it not just as events, but as a full sensory immersion: the light, the sounds, the emotional texture, the quality of the air. Why is this particular slice of time worth encapsulating? What fears or hopes do you have about opening that vial years from now? Write about the desire to hold onto a fleeting feeling, and the wisdom or melancholy that might come from revisiting it."
|
||||
}
|
||||
]
|
||||
@@ -1,22 +0,0 @@
|
||||
[
|
||||
"Imagine you are a translator for a species that communicates through scent. Describe the complex 'sentence' of a specific place's aroma\u2014a bakery, a forest after rain, a subway station. Break down its notes as if they were clauses and modifiers. Now, attempt to translate this olfactory message into a human language. What is inevitably lost in translation? What unique wisdom might this scent-language contain about the world?",
|
||||
"You are given a single, unmarked key. Instead of wondering what lock it fits, you decide to carry it with you for a week as a totem. Describe its weight in your pocket, the sound it makes against other items. How does its silent, potential purpose affect your daily decisions and observations? Does it begin to feel like it unlocks something metaphorical within your routine? Write about the power of an unanswered question made physical.",
|
||||
"Recall a time you witnessed a complete stranger perform a small, unexpected act of kindness. Describe the scene in detail, focusing on the body language of both the giver and receiver. Now, imagine the vast, invisible network of causality that led to that precise moment. Trace one possible thread backwards through the stranger's day. How does acknowledging the depth of every fleeting interaction change your perception of anonymity?",
|
||||
"Describe a piece of clothing you own that has been repaired\u2014a darned sock, a patched knee, a re-soled shoe. Focus on the repair itself. Is it visible or hidden? Skillful or clumsy? Does it match or contrast? Write the biography of this mended object, giving voice to both the original fabric and the intervention. What story of wear, care, and continuation does it tell? How is its value different from something pristine?",
|
||||
"Contemplate a door in your life that is currently closed\u2014literal or metaphorical. Describe the door itself: its material, its handle, the sound it makes when shut. Now, instead of focusing on what's behind it or the desire to open it, write about the quality of the threshold it creates. What exists in the space of not-knowing? How does this closed door shape the rooms you currently occupy? Explore the architecture of limitation.",
|
||||
"You discover your life is being gently edited by a benign, unseen force. Small, insignificant details are being erased: the memory of a cloud's shape, the name of a minor character in a book, the specific feeling of a Tuesday in March. Describe the sensation of these minor oblivions. Do you feel lighter or impoverished? Would you try to stop the edits, or trust the process? Write about the curation of a life through subtle forgetting.",
|
||||
"Choose a common machine in your home (a refrigerator, a washing machine, a router). Spend ten minutes listening to its operational sounds. Describe its sonic signature\u2014its rhythms, clicks, and hums. Now, imagine writing its user manual, but from its own perspective. What are its instructions for human cohabitation? What does it need to function well? How does this shift in agency alter your relationship with the 'dumb' object?",
|
||||
"Map a significant personal relationship as a shared garden. What have you each planted? What has grown wild? What requires constant tending, and what is delightfully low-maintenance? Describe the current season of this garden. Are you harvesting, weeding, or letting it lie fallow? Write about a conversation you might have while working side-by-side in this metaphorical space. What does this horticultural model reveal about partnership?",
|
||||
"Describe a time you followed a set of instructions perfectly, but the outcome was a glorious or disastrous failure. Recreate the process step-by-step, with the growing sense of divergence from the expected path. Where did the rupture between plan and reality occur? Was it in the materials, the environment, or something ineffable? Explore the hidden variables that live in the gap between theory and practice, and what the 'failure' taught you that success could not.",
|
||||
"You are tasked with creating a museum exhibit about an ordinary day in your life. Choose three 'artifacts' from today (a coffee mug, a crumpled to-do list, a specific text message). For each, write the museum placard that explains its significance to future visitors. What narrative about early 21st century life do these curated fragments tell? What essential truths would they miss entirely?",
|
||||
"Listen to a song from a genre you typically avoid. Do not judge it; instead, dissect it as an anthropologist would. What are its conventions? What emotional need might it serve for its primary audience? Can you find one element\u2014a rhythm, a vocal inflection, an instrumental break\u2014that you can appreciate on its own terms? Write about the experience of analyzing taste instead of surrendering to it.",
|
||||
"Imagine your mind has a 'search function' like a computer. Perform a search for a specific memory using fragmented keywords (e.g., 'yellow,' 'laughter,' 'rain'). Describe the 'results' that surface\u2014are they accurate? Are there unexpected associations? What memories are seemingly 'deleted' or unindexed? Explore the messy, non-linear, and poetic way human memory actually retrieves information compared to digital precision.",
|
||||
"Describe a recurring thought or worry that circles in your mind. Give it a shape, a color, a texture. Now, imagine deliberately placing that thought on a small leaf and setting it adrift on a slow-moving stream. Narrate its journey away from you. What does the landscape look like as it floats further? How does the space in your mind feel once it is occupied by the image of the receding leaf instead of the thought itself?",
|
||||
"Choose a tool you use regularly (a pen, a knife, a software program). Write a love letter to this tool from the perspective of the task it performs. For example, let 'the written sentence' thank the pen. Be specific about the qualities that make this tool an ideal partner. Then, write a brief breakup letter from the same perspective, citing the tool's flaws. How does this personification deepen your appreciation for designed objects?",
|
||||
"You are given a notebook with the rule that you can only write in it while moving\u2014walking, on a train, in a car (as a passenger). Document your first entry. How does the kinetic state affect your handwriting, your thought flow, and your observations? What do you notice about the world that you might miss while stationary? Explore the link between physical motion and mental velocity, and the unique quality of thoughts captured in transit.",
|
||||
"Recall a piece of advice you were given that you deliberately chose to ignore. Reconstruct the moment it was offered. Why did you reject it? Was it the source, the timing, or the content itself? Now, with the benefit of hindsight, was your divergence from that path wise or foolish? Or does the binary of wise/foolish not apply? Write a letter to your past self about the value of both heeding and disregarding guidance.",
|
||||
"Describe your childhood home's kitchen at a specific, non-eventful time\u2014perhaps a Tuesday evening. Use all senses to capture its mundane essence. Now, imagine that space empty, all the furniture and appliances gone, leaving only the ghosts of their impressions on the floor. What echoes of activity can you still perceive in the bare room? Write about the persistence of memory in architecture and the haunting quality of absence.",
|
||||
"Contemplate a small, daily obligation that feels like a chore (making the bed, doing dishes, answering emails). Perform it tomorrow with the reverence of a sacred ritual. Describe each micro-action with exaggerated care and attention. Does this shift in mindset transform the experience? Does it reveal a hidden rhythm or satisfaction, or simply make the task take longer? Explore the boundary between drudgery and mindfulness.",
|
||||
"You find an old, blank map. Instead of filling it with geographical features, you decide to map the territories of your own personality. Chart the continents of your passions, the islands of secret skills, the treacherous swamps of your fears, the well-trod roads of habit. Where are the borders fuzzy? Where are there unexplored regions? Creating this cartography, what do you discover about the landscape of your self that you usually take for granted?",
|
||||
"Describe a habit you have that is essentially a personal ritual, though you may not have named it as such (your morning coffee routine, the way you arrange your desk, your pre-sleep phone scroll). Break it down into its component actions. What need does this sequence fulfill beyond its practical outcome? What would happen if you skipped a step? Write an ode to this small, automatic ceremony that structures your day and provides a subtle anchor of identity."
|
||||
]
|
||||
182
prompts_historic.json
Normal file
182
prompts_historic.json
Normal file
@@ -0,0 +1,182 @@
|
||||
[
|
||||
{
|
||||
"prompt00": "Choose a common phrase you use often (e.g., \"I'm fine,\" \"Just a minute,\" \"Don't worry about it\"). Dissect it. What does it truly mean when you say it? What does it conceal? What convenience does it provide? Now, for one day, vow not to use it. Chronicle the conversations that become longer, more awkward, or more honest as a result."
|
||||
},
|
||||
{
|
||||
"prompt01": "Recall a time you received a gift that was perfectly, inexplicably right for you. Describe the gift and the giver. What made it so resonant? Was it an understanding of a secret wish, a reflection of an unseen part of you, or a tool you didn't know you needed? Explore the magic of being seen and understood through the medium of an object."
|
||||
},
|
||||
{
|
||||
"prompt02": "Map a friendship as a shared garden. What did each of you plant in the initial soil? What has grown wild? What requires regular tending? Have there been seasons of drought or frost? Are there any beautiful, stubborn weeds? Write a gardener's diary entry about the current state of this plot, reflecting on its history and future."
|
||||
},
|
||||
{
|
||||
"prompt03": "Describe a skill you have that is entirely non-verbal\u2014perhaps riding a bike, kneading dough, tuning an instrument by ear. Attempt to write a manual for this skill using only metaphors and physical sensations. Avoid technical terms. Can you translate embodied knowledge into prose? What is lost, and what is poetically gained?"
|
||||
},
|
||||
{
|
||||
"prompt04": "Recall a scent that acts as a master key, unlocking a flood of specific, detailed memories. Describe the scent in non-scent words: is it sharp, round, velvety, brittle? Now, follow the key into the memory palace it opens. Don't just describe the memory; describe the architecture of the connection itself. How is scent wired so directly to the past?"
|
||||
},
|
||||
{
|
||||
"prompt05": "Imagine you are a translator for a species that communicates through subtle shifts in temperature. Describe a recent emotional experience as a thermal map. Where in your body did the warmth of joy concentrate? Where did the cold front of anxiety settle? How would you translate this silent, somatic language into words for someone who only understands degrees and gradients?"
|
||||
},
|
||||
{
|
||||
"prompt06": "Find a surface covered in a fine layer of dust\u2014a windowsill, an old book, a forgotten picture frame. Describe this 'residue' of time and neglect. What stories does the pattern of settlement tell? Write about the act of wiping it away. Is it an erasure of history or a renewal? What clean surface is revealed, and does it feel like a loss or a gain?"
|
||||
},
|
||||
{
|
||||
"prompt07": "Build a 'gossamer' bridge in your mind between two seemingly disconnected concepts: for example, baking bread and forgiveness, or traffic patterns and anxiety. Describe the fragile, translucent strands of logic or metaphor you use to connect them. Walk across this bridge. What new landscape do you find on the other side? Does the bridge hold, or dissolve after use?"
|
||||
},
|
||||
{
|
||||
"prompt08": "Map a personal 'labyrinth' of procrastination or avoidance. What are its enticing entryways (\"I'll just check...\")? Its circular corridors of rationalization? Its terrifying center (the task itself)? Describe one recent journey into this maze. What finally provided the thread to lead you out, or what made you decide to sit in the center and confront the Minotaur?"
|
||||
},
|
||||
{
|
||||
"prompt09": "Craft a mental 'effigy' of a piece of advice you were given that you've chosen to ignore. Give it form and substance. Do you keep it on a shelf, bury it, or ritually dismantle it? Write about the act of holding this representation of rejected wisdom. Does making it concrete help you understand your refusal, or simply honor the intention of the giver?"
|
||||
},
|
||||
{
|
||||
"prompt10": "Recall a decision point that felt like standing at the mouth of a 'labyrinth,' with multiple winding paths ahead. Describe the initial confusion and the method you used to choose an entrance (logic, intuition, chance). Now, with hindsight, map the path you actually took. Were there dead ends or unexpected centers? Did the labyrinth lead you out, or deeper into understanding?"
|
||||
},
|
||||
{
|
||||
"prompt11": "Contemplate a 'quasar'\u2014an immensely luminous, distant celestial object. Use it as a metaphor for a source of guidance or inspiration in your life that feels both incredibly powerful and remote. Who or what is this distant beacon? Describe the 'light' it emits and the long journey it takes to reach you. How do you navigate by this ancient, brilliant, but fundamentally untouchable signal?"
|
||||
},
|
||||
{
|
||||
"prompt12": "Describe a piece of music that left a 'residue' in your mind\u2014a melody that loops unbidden, a lyric that sticks, a rhythm that syncs with your heartbeat. How does this auditory artifact resurface during quiet moments? What emotional or memory-laden dust has it collected? Write about the process of this mental replay, and whether you seek to amplify it or gently brush it away."
|
||||
},
|
||||
{
|
||||
"prompt13": "Recall a 'failed' experiment from your past\u2014a recipe that flopped, a project abandoned, a relationship that didn't work. Instead of framing it as a mistake, analyze it as a valuable trial that produced data. What did you learn about the materials, the process, or yourself? How did the outcome diverge from your hypothesis? Write a lab report for this experiment, focusing on the insights gained rather than the desired product. How does this reframe 'failure'?"
|
||||
},
|
||||
{
|
||||
"prompt14": "Chronicle the life cycle of a rumor or piece of gossip that reached you. Where did you first hear it? How did it mutate as it passed to you? What was your role\u2014conduit, amplifier, skeptic, terminator? Analyze the social algorithm that governs such information transfer. What need did this rumor feed in its listeners? Write about the velocity and distortion of unverified stories through a community."
|
||||
},
|
||||
{
|
||||
"prompt15": "Recall a time you had to translate\u2014not between languages, but between contexts: explaining a job to family, describing an emotion to someone who doesn't share it, making a technical concept accessible. Describe the words that failed you and the metaphors you crafted to bridge the gap. What was lost in translation? What was surprisingly clarified? Explore the act of building temporary, fragile bridges of understanding between internal and external worlds."
|
||||
},
|
||||
{
|
||||
"prompt16": "You discover a forgotten corner of a digital space you own\u2014an old blog draft, a buried folder of photos, an abandoned social media profile. Explore this digital artifact as an archaeologist would a physical site. What does the layout, the language, the imagery tell you about a past self? Reconstruct the mindset of the person who created it. How does this digital echo compare to your current identity? Is it a charming relic or an unsettling ghost?"
|
||||
},
|
||||
{
|
||||
"prompt17": "You are tasked with archiving a sound that is becoming obsolete\u2014the click of a rotary phone, the chirp of a specific bird whose habitat is shrinking, the particular hum of an old appliance. Record a detailed description of this sound as if for a future museum. What are its frequencies, its rhythms, its emotional connotations? Now, imagine the silence that will exist in its place. What other, newer sounds will fill that auditory niche? Write an elegy for a vanishing sonic fingerprint."
|
||||
},
|
||||
{
|
||||
"prompt18": "Craft a mental effigy of a habit, fear, or desire you wish to understand better. Describe this symbolic representation in detail\u2014its materials, its posture, its expression. Now, perform a symbolic action upon it: you might place it in a drawer, bury it in the garden of your mind, or set it adrift on an imaginary river. Chronicle this ritual. Does the act of creating and addressing the effigy change your relationship to the thing it represents, or does it merely make its presence more tangible?"
|
||||
},
|
||||
{
|
||||
"prompt19": "Describe a labyrinth you have constructed in your own mind\u2014not a physical maze, but a complex, recurring thought pattern or emotional state you find yourself navigating. What are its winding corridors (rationalizations), its dead ends (frustrations), and its potential center (understanding or acceptance)? Map one recent journey through this internal labyrinth. What subtle tremor of insight or fear guided your turns? How do you find your way out, or do you choose to remain within, exploring its familiar, intricate paths?"
|
||||
},
|
||||
{
|
||||
"prompt20": "Examine a family tradition or ritual as if it were an ancient artifact. Break down its syntax: the required steps, the symbolic objects, the spoken phrases. Who are the keepers of this tradition? How has it mutated or diverged over generations? Participate in or recall this ritual with fresh eyes. What unspoken values and histories are encoded within its performance? What would be lost if it faded into oblivion?"
|
||||
},
|
||||
{
|
||||
"prompt21": "Observe a plant growing in an unexpected place\u2014a crack in the sidewalk, a gutter, a wall. Chronicle its struggle and persistence. Imagine the velocity of its growth against all odds. Write from the plant's perspective about its daily existence: the foot traffic, the weather, the search for sustenance. What can this resilient life form teach you about finding footholds and thriving in inhospitable environments?"
|
||||
},
|
||||
{
|
||||
"prompt22": "Imagine your creative process as a room with many thresholds. Describe the room where you generate raw ideas\u2014its mess, its energy. Then, describe the act of crossing the threshold into the room where you refine and edit. What changes in the atmosphere? What do you leave behind at the door, and what must you carry with you? Write about the architecture of your own creativity."
|
||||
},
|
||||
{
|
||||
"prompt23": "You are given a seed. It is not a magical seed, but an ordinary one from a fruit you ate. Instead of planting it, you decide to carry it with you for a week as a silent companion. Describe its presence in your pocket or bag. How does knowing it is there, a compact potential for an entire mycelial network of roots and a tree, subtly influence your days? Write about the weight of unactivated futures."
|
||||
},
|
||||
{
|
||||
"prompt24": "Recall a time you had to learn a new system or language quickly\u2014a job, a software, a social circle. Describe the initial phase of feeling like an outsider, decoding the basic algorithms of behavior. Then, focus on the precise moment you felt you crossed the threshold from outsider to competent insider. What was the catalyst? A piece of understood jargon? A successfully completed task? Explore the subtle architecture of belonging."
|
||||
},
|
||||
{
|
||||
"prompt25": "You find an old, annotated map\u2014perhaps in a book, or a tourist pamphlet from a trip long ago. Study the marks: circled sites, crossed-out routes, notes in the margin. Reconstruct the journey of the person who held this map. Where did they plan to go? Where did they actually go, based on the evidence? Write the travelogue of that forgotten expedition, blending the cartographic intention with the likely reality."
|
||||
},
|
||||
{
|
||||
"prompt26": "You encounter a door that is usually locked, but today it is slightly ajar. This is not a grand, mysterious portal, but an ordinary door\u2014to a storage closet, a rooftop, a neighbor's garden gate. Write about the potent allure of this minor threshold. Do you push it open? What mundane or profound discovery lies on the other side? Explore the magnetism of accessible secrets in a world of usual boundaries."
|
||||
},
|
||||
{
|
||||
"prompt27": "Recall a piece of practical advice you received that functioned like a simple life algorithm: 'When X happens, do Y.' Examine a recent situation where you deliberately chose not to follow that algorithm. What prompted the deviation? What was the outcome? Describe the feeling of operating outside of a previously trusted internal program. Did the mutation feel like a mistake or an evolution?"
|
||||
},
|
||||
{
|
||||
"prompt28": "Describe a piece of clothing you own that has been altered or mended multiple times. Trace the history of each repair. Who performed them, and under what circumstances? How does the garment's story of damage and restoration mirror larger cycles of wear and renewal in your own life? What does its continued use, despite its patched state, say about your relationship with impermanence and care?"
|
||||
},
|
||||
{
|
||||
"prompt29": "You find an old, hand-drawn map that leads to a place in your neighborhood. Follow it. Does it lead you to a spot that still exists, or to a location now utterly changed? Describe the journey of reconciling the cartography of the past with the terrain of the present. What has been erased? What endures? What ghosts of previous journeys do you feel along the way?"
|
||||
},
|
||||
{
|
||||
"prompt30": "Consider a skill you are learning. Break down its initial algorithm\u2014the basic, rigid steps you must follow. Now, describe the moment when practice leads to mutation: the algorithm begins to dissolve into intuition, muscle memory, or personal style. Where are you in this process? Can you feel the old, clunky code still running beneath the new, fluid performance? Write about the uncomfortable, fruitful space between competence and mastery."
|
||||
},
|
||||
{
|
||||
"prompt31": "Analyze the unspoken social algorithm of a group you belong to\u2014your family, your friend circle, your coworkers. What are the input rules (jokes that are allowed, topics to avoid)? What are the output expectations (laughter, support, problem-solving)? Now, imagine introducing a mutation: you break a minor, unwritten rule. Chronicle the system's response. Does it self-correct, reject the input, or adapt?"
|
||||
},
|
||||
{
|
||||
"prompt32": "Imagine your daily routine is a genetic sequence. Identify a habitual behavior that feels like a dominant gene. Now, imagine a spontaneous mutation occurring in this sequence\u2014one small, random change in the order or execution of your day. Follow the consequences. Does this mutation prove beneficial, harmful, or neutral? Does it replicate and become part of your new code? Write about the evolution of a personal habit through chance."
|
||||
},
|
||||
{
|
||||
"prompt33": "Your memory is a vast, dark archive. Choose a specific memory and imagine you are its archivist. Describe the process of retrieving it: locating the correct catalog number, the feel of the storage medium, the quality of the playback. Now, describe the process of conservation\u2014what elements are fragile and in need of repair? Do you restore it to its original clarity, or preserve its current, faded state? What is the ethical duty of a self-archivist?"
|
||||
},
|
||||
{
|
||||
"prompt34": "Examine a mended object in your possession\u2014a book with tape, a garment with a patch, a glued-together mug. Describe the repair not as a flaw, but as a new feature, a record of care and continuity. Write the history of its breaking and its fixing. Who performed the repair, and what was their state of mind? How does the object's value now reside in its visible history of damage and healing?"
|
||||
},
|
||||
{
|
||||
"prompt35": "Imagine you are a cartographer of sound. Map the auditory landscape of your current environment. Label the persistent drones, the intermittent rhythms, the sudden percussive events. What are the quiet zones? Where do sounds overlap to create new harmonies or dissonances? Now, imagine mutating one sound source\u2014silencing a hum, amplifying a whisper, changing a rhythm. How does this single alteration redraw the entire sonic map and your emotional response to the space?"
|
||||
},
|
||||
{
|
||||
"prompt36": "Contemplate the concept of a 'watershed'\u2014a geographical dividing line. Now, identify a watershed moment in your own life: a decision, an event, or a realization that divided your experience into 'before' and 'after.' Describe the landscape of the 'before.' Then, detail the moment of the divide itself. Finally, look out over the 'after' territory. How did the paths available to you fundamentally diverge at that ridge line? What rivers of consequence began to flow in new directions?"
|
||||
},
|
||||
{
|
||||
"prompt37": "Observe a spiderweb, a bird's nest, or another intricate natural construction. Describe it not as a static object, but as the recorded evidence of a process\u2014a series of deliberate actions repeated to create a functional whole. Imagine you are an archaeologist from another planet discovering this artifact. What hypotheses would you form about the builder's intelligence, needs, and methods? Write your field report."
|
||||
},
|
||||
{
|
||||
"prompt38": "Walk through a familiar indoor space (your home, your office) in complete darkness, or with your eyes closed if safe. Navigate by touch, memory, and sound alone. Describe the experience. Which objects and spaces feel different? What details do you notice that vision usually overrides? Write about the knowledge held in your hands and feet, and the temporary oblivion of the visual world. How does this shift in primary sense redefine your understanding of the space?"
|
||||
},
|
||||
{
|
||||
"prompt39": "You discover a single, worn-out glove lying on a park bench. Describe it in detail\u2014its color, material, signs of wear. Write a speculative history for this artifact. Who owned it? How was it lost? From the glove's perspective, narrate its journey from a department store shelf to this moment of abandonment. What human warmth did it hold, and what does its solitary state signify about loss and separation?"
|
||||
},
|
||||
{
|
||||
"prompt40": "Find a body of water\u2014a puddle after rain, a pond, a riverbank. Look at your reflection, then disturb the surface with a touch or a thrown pebble. Watch the image shatter and slowly reform. Use this as a metaphor for a period of personal disruption in your life. Describe the 'shattering' event, the chaotic ripple period, and the gradual, never-quite-identical reformation of your sense of self. What was lost in the distortion, and what new facets were revealed?"
|
||||
},
|
||||
{
|
||||
"prompt41": "You are handed a map of a city you know well, but it is from a century ago. Compare it to the modern layout. Which streets have vanished into oblivion, paved over or renamed? Which buildings are ghosts on the page? Choose one lost place and imagine walking its forgotten route today. What echoes of its past life\u2014sounds, smells, activities\u2014can you almost perceive beneath the contemporary surface? Write about the layers of history that coexist in a single geographic space."
|
||||
},
|
||||
{
|
||||
"prompt42": "What is something you've been putting off and why?"
|
||||
},
|
||||
{
|
||||
"prompt43": "Recall a piece of art\u2014a painting, song, film\u2014that initially confused or repelled you, but that you later came to appreciate or love. Describe your first, negative reaction in detail. Then, trace the journey to understanding. What changed in you or your context that allowed a new interpretation? Write about the value of sitting with discomfort and the rewards of having your internal syntax for beauty challenged and expanded."
|
||||
},
|
||||
{
|
||||
"prompt44": "Imagine your life as a vast, intricate tapestry. Describe the overall scene it depicts. Now, find a single, loose thread\u2014a small regret, an unresolved question, a path not taken. Write about gently pulling on that thread. What part of the tapestry begins to unravel? What new pattern or image is revealed\u2014or destroyed\u2014by following this divergence? Is the act one of repair or deconstruction?"
|
||||
},
|
||||
{
|
||||
"prompt45": "Recall a dream that felt more real than waking life. Describe its internal logic, its emotional palette, and its lingering aftertaste. Now, write a 'practical guide' for navigating that specific dreamscape, as if for a tourist. What are the rules? What should one avoid? What treasures might be found? By treating the dream as a tangible place, what insights do you gain about the concerns of your subconscious?"
|
||||
},
|
||||
{
|
||||
"prompt46": "Describe a public space you frequent (a library, a cafe, a park) at the exact moment it opens or closes. Capture the transition from emptiness to potential, or from activity to stillness. Focus on the staff or custodians who facilitate this transition\u2014the unseen architects of these daily cycles. Write from the perspective of the space itself as it breathes in or out its human occupants. What residue of the day does it hold in the quiet?"
|
||||
},
|
||||
{
|
||||
"prompt47": "Listen to a piece of music you know well, but focus exclusively on a single instrument or voice that usually resides in the background. Follow its thread through the entire composition. Describe its journey: when does it lead, when does it harmonize, when does it fall silent? Now, write a short story where this supporting element is the main character. How does shifting your auditory focus create a new narrative from familiar material?"
|
||||
},
|
||||
{
|
||||
"prompt48": "Describe your reflection in a window at night, with the interior light creating a double exposure of your face and the dark world outside. What two versions of yourself are superimposed? Write a conversation between the 'inside' self, defined by your private space, and the 'outside' self, defined by the anonymous night. What do they want from each other? How does this liminal artifact\u2014the glass\u2014both separate and connect these identities?"
|
||||
},
|
||||
{
|
||||
"prompt49": "Imagine you are a diver exploring the deep ocean of your own memory. Choose a specific, vivid memory and describe it as a submerged landscape. What creatures (emotions) swim there? What is the water pressure (emotional weight) like? Now, imagine a small, deliberate act of forgetting\u2014letting a single detail of that memory dissolve into the murk. How does this selective oblivion change the entire ecosystem of that recollection? Does it create space for new growth, or does it feel like a loss of truth?"
|
||||
},
|
||||
{
|
||||
"prompt50": "Recall a conversation that ended in a misunderstanding that was never resolved. Re-write the exchange, but introduce a single point of divergence\u2014one person says something slightly different, or pauses a moment longer. How does this tiny change alter the entire trajectory of the conversation and potentially the relationship? Explore the butterfly effect in human dialogue."
|
||||
},
|
||||
{
|
||||
"prompt51": "Spend 15 minutes in complete silence, actively listening for the absence of a specific sound that is usually present (e.g., traffic, refrigerator hum, birds). Describe the quality of this crafted silence. What smaller sounds emerge in the void? How does your mind and body react to the deliberate removal of this sonic artifact? Explore the concept of oblivion as an active, perceptible state rather than a mere lack."
|
||||
},
|
||||
{
|
||||
"prompt52": "Describe a skill or talent you possess that feels like it's fading from lack of use\u2014a language getting rusty, a sport you no longer play, an instrument gathering dust. Perform or practice it now, even if clumsily. Chronicle the physical and mental sensations of re-engagement. What echoes of proficiency remain? Is the knowledge truly gone, or merely dormant? Write about the relationship between mastery and oblivion."
|
||||
},
|
||||
{
|
||||
"prompt53": "Choose a common word (e.g., 'home,' 'work,' 'friend') and dissect its personal syntax. What rules, associations, and exceptions have you built around its meaning? Now, deliberately break one of those rules. Use the word in a context or with a definition that feels wrong to you. Write a paragraph that forces this new usage. How does corrupting your own internal language create space for new understanding?"
|
||||
},
|
||||
{
|
||||
"prompt54": "Contemplate a personal habit or pattern you wish to change. Instead of focusing on breaking it, imagine it diverging\u2014mutating into a new, slightly different pattern. Describe the old habit in detail, then design its evolved form. What small, intentional twist could redirect its energy? Write about a day living with this divergent habit. How does a shift in perspective, rather than eradication, alter your relationship to it?"
|
||||
},
|
||||
{
|
||||
"prompt55": "Describe a routine journey you make (a commute, a walk to the store) but narrate it as if you are a traveler in a foreign, slightly surreal land. Give fantastical names to ordinary landmarks. Interpret mundane events as portents or rituals. What hidden narrative or mythic structure can you impose on this familiar path? How does this reframing reveal the magic latent in the everyday?"
|
||||
},
|
||||
{
|
||||
"prompt56": "Imagine a place from your childhood that no longer exists in its original form\u2014a demolished building, a paved-over field, a renovated room. Reconstruct it from memory with all its sensory details. Now, write about the process of its erasure. Who decided it should change? What was lost in the transition, and what, if anything, was gained? How does the ghost of that place still influence the geography of your memory?"
|
||||
},
|
||||
{
|
||||
"prompt57": "You find an old, functional algorithm\u2014a recipe card, a knitting pattern, a set of instructions for assembling furniture. Follow it to the letter, but with a new, meditative attention to each step. Describe the process not as a means to an end, but as a ritual in itself. What resonance does this deliberate, prescribed action have? Does the final product matter, or has the value been in the structured journey?"
|
||||
},
|
||||
{
|
||||
"prompt58": "Imagine knowledge and ideas spread through a community not like a virus, but like a mycelium\u2014subterranean, cooperative, nutrient-sharing. Recall a time you learned something profound from an unexpected or unofficial source. Trace the hidden network that brought that wisdom to you. How many people and experiences were unknowingly part of that fruiting? Write a thank you to this invisible web."
|
||||
},
|
||||
{
|
||||
"prompt59": "Imagine your creative or problem-solving process is a mycelial network. A question or idea is dropped like a spore onto this vast, hidden web. Describe the journey of this spore as it sends out filaments, connects with distant nodes of memory and knowledge, and eventually fruits as an 'aha' moment or a new creation. How does this model differ from a linear, step-by-step algorithm? What does it teach you about patience and indirect growth?"
|
||||
}
|
||||
]
|
||||
4
prompts_pool.json
Normal file
4
prompts_pool.json
Normal file
@@ -0,0 +1,4 @@
|
||||
[
|
||||
"Describe preparing and eating a meal alone with the attention of a sacred ritual. Focus on each step: selecting ingredients, the sound of chopping, the aromas, the arrangement on the plate, the first bite. Write about the difference between eating for fuel and eating as an act of communion with yourself. What thoughts arise in the space of this deliberate solitude?",
|
||||
"Recall a rule you were taught as a child\u2014a practical safety rule, a social manner, a household edict. Examine its original purpose. Now, trace how your relationship to that rule has evolved. Do you follow it rigidly, have you modified it, or do you ignore it entirely? Write about the journey from external imposition to internalized (or rejected) law."
|
||||
]
|
||||
@@ -1,7 +0,0 @@
|
||||
#!/bin/bash
|
||||
|
||||
#cp baseline_files/ds_prompt.txt .
|
||||
cp baseline_files/feedback_words.json .
|
||||
cp baseline_files/historic_prompts.json .
|
||||
cp baseline_files/pool_prompts.json .
|
||||
#cp baseline_files/settings.cfg .
|
||||
26
run.sh
26
run.sh
@@ -35,9 +35,7 @@ fi
|
||||
|
||||
# Parse command line arguments
|
||||
INTERACTIVE=false
|
||||
SIMPLE=false
|
||||
STATS=false
|
||||
POOL_STATS=false
|
||||
FILL_POOL=false
|
||||
HELP=false
|
||||
|
||||
@@ -47,18 +45,10 @@ while [[ $# -gt 0 ]]; do
|
||||
INTERACTIVE=true
|
||||
shift
|
||||
;;
|
||||
-s | --simple)
|
||||
SIMPLE=true
|
||||
shift
|
||||
;;
|
||||
--stats)
|
||||
STATS=true
|
||||
shift
|
||||
;;
|
||||
--pool-stats)
|
||||
POOL_STATS=true
|
||||
shift
|
||||
;;
|
||||
--fill-pool)
|
||||
FILL_POOL=true
|
||||
shift
|
||||
@@ -80,37 +70,27 @@ if [ "$HELP" = true ]; then
|
||||
echo ""
|
||||
echo "Options:"
|
||||
echo " -i, --interactive Run in interactive mode (with rich interface)"
|
||||
echo " -s, --simple Run simple version (no rich dependency)"
|
||||
echo " --stats Show prompt history statistics"
|
||||
echo " --pool-stats Show prompt pool statistics"
|
||||
echo " --stats Show combined statistics (pool and history)"
|
||||
echo " --fill-pool Fill prompt pool using AI (makes API call)"
|
||||
echo " -h, --help Show this help message"
|
||||
echo ""
|
||||
echo "Examples:"
|
||||
echo " ./run.sh # Draw prompts from pool (default)"
|
||||
echo " ./run.sh -i # Interactive mode"
|
||||
echo " ./run.sh -s # Simple version"
|
||||
echo " ./run.sh --stats # Show history statistics"
|
||||
echo " ./run.sh --pool-stats # Show pool statistics"
|
||||
echo " ./run.sh --stats # Show combined statistics"
|
||||
echo " ./run.sh --fill-pool # Fill prompt pool using AI"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
if [ "$STATS" = true ]; then
|
||||
echo "📊 Showing history statistics..."
|
||||
echo "📊 Showing combined statistics..."
|
||||
python3 generate_prompts.py --stats
|
||||
elif [ "$POOL_STATS" = true ]; then
|
||||
echo "📊 Showing pool statistics..."
|
||||
python3 generate_prompts.py --pool-stats
|
||||
elif [ "$FILL_POOL" = true ]; then
|
||||
echo "🔄 Filling prompt pool using AI..."
|
||||
python3 generate_prompts.py --fill-pool
|
||||
elif [ "$INTERACTIVE" = true ]; then
|
||||
echo "🎮 Starting interactive mode..."
|
||||
python3 generate_prompts.py --interactive
|
||||
elif [ "$SIMPLE" = true ]; then
|
||||
echo "⚡ Running simple version..."
|
||||
python3 simple_generate.py
|
||||
else
|
||||
echo "✨ Drawing prompts from pool..."
|
||||
python3 generate_prompts.py
|
||||
|
||||
@@ -1,319 +0,0 @@
|
||||
#!/usr/bin/env python3
|
||||
"""
|
||||
Simple Daily Journal Prompt Generator
|
||||
A lightweight version without rich dependency.
|
||||
"""
|
||||
|
||||
import os
|
||||
import json
|
||||
import sys
|
||||
import argparse
|
||||
import configparser
|
||||
from datetime import datetime
|
||||
from typing import List, Dict, Any
|
||||
|
||||
from openai import OpenAI
|
||||
from dotenv import load_dotenv
|
||||
|
||||
|
||||
class SimplePromptGenerator:
|
||||
"""Simple version without rich dependency."""
|
||||
|
||||
def __init__(self, config_path: str = ".env"):
|
||||
"""Initialize the generator with configuration."""
|
||||
self.config_path = config_path
|
||||
self.client = None
|
||||
self.historic_prompts = []
|
||||
self.pool_prompts = []
|
||||
self.prompt_template = ""
|
||||
self.settings = {}
|
||||
|
||||
# Load configuration
|
||||
self._load_config()
|
||||
self._load_settings()
|
||||
|
||||
# Load data files
|
||||
self._load_prompt_template()
|
||||
self._load_historic_prompts()
|
||||
self._load_pool_prompts()
|
||||
|
||||
def _load_config(self):
|
||||
"""Load configuration from environment file."""
|
||||
load_dotenv(self.config_path)
|
||||
|
||||
# Get API key
|
||||
self.api_key = os.getenv("DEEPSEEK_API_KEY") or os.getenv("OPENAI_API_KEY")
|
||||
if not self.api_key:
|
||||
print("Error: No API key found in .env file")
|
||||
print("Please add DEEPSEEK_API_KEY or OPENAI_API_KEY to your .env file")
|
||||
sys.exit(1)
|
||||
|
||||
# Get API base URL (default to DeepSeek)
|
||||
self.base_url = os.getenv("API_BASE_URL", "https://api.deepseek.com")
|
||||
|
||||
# Get model (default to deepseek-chat)
|
||||
self.model = os.getenv("MODEL", "deepseek-chat")
|
||||
|
||||
# Initialize OpenAI client
|
||||
self.client = OpenAI(
|
||||
api_key=self.api_key,
|
||||
base_url=self.base_url
|
||||
)
|
||||
|
||||
def _load_settings(self):
|
||||
"""Load settings from settings.cfg configuration file."""
|
||||
config = configparser.ConfigParser()
|
||||
|
||||
# Set default values
|
||||
self.settings = {
|
||||
'min_length': 500,
|
||||
'max_length': 1000,
|
||||
'num_prompts': 6
|
||||
}
|
||||
|
||||
try:
|
||||
config.read('settings.cfg')
|
||||
|
||||
if 'prompts' in config:
|
||||
prompts_section = config['prompts']
|
||||
|
||||
# Load min_length
|
||||
if 'min_length' in prompts_section:
|
||||
self.settings['min_length'] = int(prompts_section['min_length'])
|
||||
|
||||
# Load max_length
|
||||
if 'max_length' in prompts_section:
|
||||
self.settings['max_length'] = int(prompts_section['max_length'])
|
||||
|
||||
# Load num_prompts
|
||||
if 'num_prompts' in prompts_section:
|
||||
self.settings['num_prompts'] = int(prompts_section['num_prompts'])
|
||||
|
||||
except FileNotFoundError:
|
||||
print("Warning: settings.cfg not found, using default values")
|
||||
except ValueError as e:
|
||||
print(f"Warning: Invalid value in settings.cfg: {e}, using default values")
|
||||
except Exception as e:
|
||||
print(f"Warning: Error reading settings.cfg: {e}, using default values")
|
||||
|
||||
def _load_prompt_template(self):
|
||||
"""Load the prompt template from ds_prompt.txt and update with config values."""
|
||||
try:
|
||||
with open("ds_prompt.txt", "r") as f:
|
||||
template = f.read()
|
||||
|
||||
# Replace hardcoded values with config values
|
||||
template = template.replace(
|
||||
"between 500 and 1000 characters",
|
||||
f"between {self.settings['min_length']} and {self.settings['max_length']} characters"
|
||||
)
|
||||
|
||||
# Replace the number of prompts (6) with config value
|
||||
template = template.replace(
|
||||
"Please generate 6 writing prompts",
|
||||
f"Please generate {self.settings['num_prompts']} writing prompts"
|
||||
)
|
||||
|
||||
self.prompt_template = template
|
||||
except FileNotFoundError:
|
||||
print("Error: ds_prompt.txt not found")
|
||||
sys.exit(1)
|
||||
|
||||
def _load_historic_prompts(self):
|
||||
"""Load historic prompts from JSON file."""
|
||||
try:
|
||||
with open("historic_prompts.json", "r") as f:
|
||||
self.historic_prompts = json.load(f)
|
||||
except (FileNotFoundError, json.JSONDecodeError):
|
||||
print("Warning: Starting with empty prompt history")
|
||||
self.historic_prompts = []
|
||||
|
||||
def _save_historic_prompts(self):
|
||||
"""Save historic prompts to JSON file (keeping only last 60)."""
|
||||
# Keep only the last 60 prompts
|
||||
if len(self.historic_prompts) > 60:
|
||||
self.historic_prompts = self.historic_prompts[-60:]
|
||||
|
||||
with open("historic_prompts.json", "w") as f:
|
||||
json.dump(self.historic_prompts, f, indent=2)
|
||||
|
||||
def _prepare_prompt(self) -> str:
|
||||
"""Prepare the full prompt with historic context."""
|
||||
if self.historic_prompts:
|
||||
historic_context = json.dumps(self.historic_prompts, indent=2)
|
||||
full_prompt = f"{self.prompt_template}\n\nPrevious prompts:\n{historic_context}"
|
||||
else:
|
||||
full_prompt = self.prompt_template
|
||||
|
||||
return full_prompt
|
||||
|
||||
def _parse_ai_response(self, response_content: str) -> List[str]:
|
||||
"""Parse the AI response to extract new prompts."""
|
||||
try:
|
||||
# Try to parse as JSON
|
||||
data = json.loads(response_content)
|
||||
|
||||
# Check if data is a list (new format)
|
||||
if isinstance(data, list):
|
||||
# Return the list of prompt strings directly
|
||||
# Ensure we have the correct number of prompts
|
||||
if len(data) >= self.settings['num_prompts']:
|
||||
return data[:self.settings['num_prompts']]
|
||||
else:
|
||||
print(f"Warning: AI returned {len(data)} prompts, expected {self.settings['num_prompts']}")
|
||||
return data
|
||||
elif isinstance(data, dict):
|
||||
# Fallback for old format: dictionary with newprompt0, newprompt1, etc.
|
||||
print("Warning: AI returned dictionary format, expected list format")
|
||||
new_prompts = []
|
||||
for i in range(self.settings['num_prompts']):
|
||||
key = f"newprompt{i}"
|
||||
if key in data:
|
||||
new_prompts.append(data[key])
|
||||
return new_prompts
|
||||
else:
|
||||
print(f"Warning: AI returned unexpected data type: {type(data)}")
|
||||
return []
|
||||
|
||||
except json.JSONDecodeError:
|
||||
# If not valid JSON, try to extract prompts from text
|
||||
print("Warning: AI response is not valid JSON, attempting to extract prompts...")
|
||||
|
||||
# Look for patterns in the text
|
||||
lines = response_content.strip().split('\n')
|
||||
new_prompts = []
|
||||
|
||||
for i, line in enumerate(lines[:self.settings['num_prompts']]):
|
||||
line = line.strip()
|
||||
if line and len(line) > 50:
|
||||
new_prompts.append(line)
|
||||
|
||||
return new_prompts
|
||||
|
||||
def generate_prompts(self) -> List[str]:
|
||||
"""Generate new journal prompts using AI."""
|
||||
print("\nGenerating new journal prompts...")
|
||||
|
||||
# Prepare the prompt
|
||||
full_prompt = self._prepare_prompt()
|
||||
|
||||
try:
|
||||
# Call the AI API
|
||||
print("Calling AI API...")
|
||||
response = self.client.chat.completions.create(
|
||||
model=self.model,
|
||||
messages=[
|
||||
{"role": "system", "content": "You are a creative writing assistant that generates journal prompts. Always respond with valid JSON."},
|
||||
{"role": "user", "content": full_prompt}
|
||||
],
|
||||
temperature=0.7,
|
||||
max_tokens=2000
|
||||
)
|
||||
|
||||
response_content = response.choices[0].message.content
|
||||
|
||||
except Exception as e:
|
||||
print(f"Error calling AI API: {e}")
|
||||
return []
|
||||
|
||||
# Parse the response
|
||||
new_prompts = self._parse_ai_response(response_content)
|
||||
|
||||
if not new_prompts:
|
||||
print("Error: Could not parse any prompts from AI response")
|
||||
return []
|
||||
|
||||
# Note: Prompts are NOT added to historic_prompts here
|
||||
# They will be added only when the user chooses one
|
||||
|
||||
return new_prompts
|
||||
|
||||
def display_prompts(self, prompts: List[Dict[str, str]]):
|
||||
"""Display generated prompts in a simple format."""
|
||||
print("\n" + "="*60)
|
||||
print("✨ NEW JOURNAL PROMPTS GENERATED ✨")
|
||||
print("="*60 + "\n")
|
||||
|
||||
for i, prompt_dict in enumerate(prompts, 1):
|
||||
# Extract prompt text
|
||||
prompt_key = list(prompt_dict.keys())[0]
|
||||
prompt_text = prompt_dict[prompt_key]
|
||||
|
||||
print(f"Prompt #{i}:")
|
||||
print("-" * 40)
|
||||
print(prompt_text)
|
||||
print("-" * 40 + "\n")
|
||||
|
||||
def show_history_stats(self):
|
||||
"""Show statistics about prompt history."""
|
||||
total_prompts = len(self.historic_prompts)
|
||||
|
||||
print("\nPrompt History Statistics:")
|
||||
print("-" * 30)
|
||||
print(f"Total prompts in history: {total_prompts}")
|
||||
print(f"History capacity: 60 prompts")
|
||||
print(f"Available slots: {max(0, 60 - total_prompts)}")
|
||||
|
||||
def save_prompt_to_file(self, prompt_dict: Dict[str, str], filename: str = None):
|
||||
"""Save a prompt to a text file."""
|
||||
prompt_key = list(prompt_dict.keys())[0]
|
||||
prompt_text = prompt_dict[prompt_key]
|
||||
|
||||
if not filename:
|
||||
timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
|
||||
filename = f"journal_prompt_{timestamp}.txt"
|
||||
|
||||
with open(filename, "w") as f:
|
||||
f.write(f"Journal Prompt - {datetime.now().strftime('%Y-%m-%d %H:%M:%S')}\n")
|
||||
f.write("="*50 + "\n\n")
|
||||
f.write(prompt_text)
|
||||
f.write("\n\n" + "="*50 + "\n")
|
||||
f.write("Happy writing! ✍️\n")
|
||||
|
||||
print(f"Prompt saved to {filename}")
|
||||
|
||||
|
||||
def main():
|
||||
"""Main entry point for the simple script."""
|
||||
parser = argparse.ArgumentParser(description="Generate journal prompts using AI (simple version)")
|
||||
parser.add_argument(
|
||||
"--stats", "-s",
|
||||
action="store_true",
|
||||
help="Show history statistics"
|
||||
)
|
||||
parser.add_argument(
|
||||
"--save", "-S",
|
||||
type=int,
|
||||
help="Save a specific prompt number to file"
|
||||
)
|
||||
parser.add_argument(
|
||||
"--config", "-c",
|
||||
default=".env",
|
||||
help="Path to configuration file (default: .env)"
|
||||
)
|
||||
|
||||
args = parser.parse_args()
|
||||
|
||||
# Initialize generator
|
||||
generator = SimplePromptGenerator(config_path=args.config)
|
||||
|
||||
if args.stats:
|
||||
generator.show_history_stats()
|
||||
else:
|
||||
# Generate prompts
|
||||
new_prompts = generator.generate_prompts()
|
||||
if new_prompts:
|
||||
generator.display_prompts(new_prompts)
|
||||
|
||||
# Save specific prompt if requested
|
||||
if args.save:
|
||||
prompt_num = args.save
|
||||
if 1 <= prompt_num <= len(new_prompts):
|
||||
generator.save_prompt_to_file(new_prompts[prompt_num - 1])
|
||||
else:
|
||||
print(f"Error: Prompt number must be between 1 and {len(new_prompts)}")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
|
||||
@@ -7,8 +7,8 @@ import json
|
||||
import sys
|
||||
import os
|
||||
|
||||
# Add the current directory to the Python path
|
||||
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
|
||||
# Add the parent directory to the Python path
|
||||
sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
|
||||
|
||||
from generate_prompts import JournalPromptGenerator
|
||||
|
||||
|
||||
@@ -6,8 +6,8 @@ Test script to verify feedback_words integration
|
||||
import sys
|
||||
import os
|
||||
|
||||
# Add current directory to path
|
||||
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
|
||||
# Add the parent directory to the Python path
|
||||
sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
|
||||
|
||||
from generate_prompts import JournalPromptGenerator
|
||||
|
||||
@@ -29,17 +29,6 @@ def test_feedback_words_loading():
|
||||
else:
|
||||
print("No feedback words loaded (this might be expected if file is empty)")
|
||||
|
||||
# Test _prepare_prompt method
|
||||
print("\nTesting _prepare_prompt method...")
|
||||
prompt = generator._prepare_prompt()
|
||||
print(f"Prompt length: {len(prompt)} characters")
|
||||
|
||||
# Check if feedback words are included in the prompt
|
||||
if generator.feedback_words and "Feedback words:" in prompt:
|
||||
print("✓ Feedback words are included in the prompt")
|
||||
else:
|
||||
print("✗ Feedback words are NOT included in the prompt")
|
||||
|
||||
# Test _prepare_prompt_with_count method
|
||||
print("\nTesting _prepare_prompt_with_count method...")
|
||||
prompt_with_count = generator._prepare_prompt_with_count(3)
|
||||
|
||||
@@ -1,55 +0,0 @@
|
||||
#!/usr/bin/env python3
|
||||
"""
|
||||
Test to demonstrate the fix for the AttributeError when API returns list instead of dict.
|
||||
"""
|
||||
|
||||
import json
|
||||
from generate_prompts import JournalPromptGenerator
|
||||
|
||||
def test_original_error_case():
|
||||
"""Test the exact error case: API returns a list instead of a dict."""
|
||||
|
||||
print("Testing the original error case: API returns list instead of dict")
|
||||
print("="*60)
|
||||
|
||||
# Create a mock generator
|
||||
generator = JournalPromptGenerator()
|
||||
|
||||
# Simulate API returning a list (which could happen with null/malformed data)
|
||||
list_response = json.dumps([]) # Empty list
|
||||
|
||||
print("\n1. Testing with empty list []:")
|
||||
try:
|
||||
result = generator._parse_ai_response(list_response)
|
||||
print(f" Result: Successfully parsed {len(result)} prompts (no AttributeError)")
|
||||
except AttributeError as e:
|
||||
print(f" ERROR: AttributeError occurred: {e}")
|
||||
except Exception as e:
|
||||
print(f" Other error: {type(e).__name__}: {e}")
|
||||
|
||||
# Test with list containing dictionaries (another possible malformed response)
|
||||
list_with_dicts = json.dumps([
|
||||
{"some_key": "some value"},
|
||||
{"another_key": "another value"}
|
||||
])
|
||||
|
||||
print("\n2. Testing with list of dictionaries:")
|
||||
try:
|
||||
result = generator._parse_ai_response(list_with_dicts)
|
||||
print(f" Result: Successfully parsed {len(result)} prompts (no AttributeError)")
|
||||
except AttributeError as e:
|
||||
print(f" ERROR: AttributeError occurred: {e}")
|
||||
except Exception as e:
|
||||
print(f" Other error: {type(e).__name__}: {e}")
|
||||
|
||||
# Test with None/null data (worst case)
|
||||
print("\n3. Testing with None/null data (simulated):")
|
||||
# We can't directly test None since json.loads would fail, but our code
|
||||
# handles the case where data might be None after parsing
|
||||
|
||||
print("\n" + "="*60)
|
||||
print("Test complete! The fix prevents AttributeError for list responses.")
|
||||
|
||||
if __name__ == "__main__":
|
||||
test_original_error_case()
|
||||
|
||||
@@ -1,91 +0,0 @@
|
||||
#!/usr/bin/env python3
|
||||
"""
|
||||
Test the new format where AI returns a list and keys are generated locally.
|
||||
"""
|
||||
|
||||
import json
|
||||
import sys
|
||||
import os
|
||||
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
|
||||
|
||||
from generate_prompts import JournalPromptGenerator
|
||||
|
||||
def test_new_format():
|
||||
"""Test the new format where AI returns a list and keys are generated locally."""
|
||||
|
||||
print("Testing new format: AI returns list, keys generated locally")
|
||||
print("="*60)
|
||||
|
||||
# Create a mock generator
|
||||
generator = JournalPromptGenerator(config_path=".env")
|
||||
|
||||
# Create a mock AI response in the new list format
|
||||
mock_ai_response = [
|
||||
"Write about a childhood memory that still makes you smile.",
|
||||
"Describe your perfect day from start to finish.",
|
||||
"What is something you've been putting off and why?",
|
||||
"Imagine you could have a conversation with any historical figure.",
|
||||
"Write a letter to your future self one year from now.",
|
||||
"Describe a place that feels like home to you."
|
||||
]
|
||||
|
||||
# Convert to JSON string
|
||||
json_response = json.dumps(mock_ai_response)
|
||||
|
||||
print("\n1. Testing _parse_ai_response with list format:")
|
||||
result = generator._parse_ai_response(json_response)
|
||||
print(f" Result type: {type(result)}")
|
||||
print(f" Number of prompts: {len(result)}")
|
||||
print(f" First prompt: {result[0][:50]}...")
|
||||
|
||||
# Verify it's a list of strings
|
||||
assert isinstance(result, list), "Result should be a list"
|
||||
assert all(isinstance(prompt, str) for prompt in result), "All items should be strings"
|
||||
|
||||
print("\n2. Testing add_prompts_to_pool with list of strings:")
|
||||
|
||||
# Get initial pool size
|
||||
initial_pool_size = len(generator.pool_prompts)
|
||||
print(f" Initial pool size: {initial_pool_size}")
|
||||
|
||||
# Add prompts to pool
|
||||
generator.add_prompts_to_pool(result)
|
||||
|
||||
# Check new pool size
|
||||
new_pool_size = len(generator.pool_prompts)
|
||||
print(f" New pool size: {new_pool_size}")
|
||||
print(f" Added {new_pool_size - initial_pool_size} prompts")
|
||||
|
||||
# Check that prompts in pool have keys
|
||||
print(f"\n3. Checking that prompts in pool have generated keys:")
|
||||
for i, prompt_dict in enumerate(generator.pool_prompts[-len(result):]):
|
||||
prompt_key = list(prompt_dict.keys())[0]
|
||||
prompt_text = prompt_dict[prompt_key]
|
||||
print(f" Prompt {i+1}: Key='{prompt_key}', Text='{prompt_text[:30]}...'")
|
||||
assert prompt_key.startswith("poolprompt"), f"Key should start with 'poolprompt', got '{prompt_key}'"
|
||||
|
||||
print("\n4. Testing draw_prompts_from_pool:")
|
||||
drawn_prompts = generator.draw_prompts_from_pool(count=2)
|
||||
print(f" Drawn {len(drawn_prompts)} prompts from pool")
|
||||
print(f" Pool size after drawing: {len(generator.pool_prompts)}")
|
||||
|
||||
# Check drawn prompts have keys
|
||||
for i, prompt_dict in enumerate(drawn_prompts):
|
||||
prompt_key = list(prompt_dict.keys())[0]
|
||||
prompt_text = prompt_dict[prompt_key]
|
||||
print(f" Drawn prompt {i+1}: Key='{prompt_key}', Text='{prompt_text[:30]}...'")
|
||||
|
||||
print("\n" + "="*60)
|
||||
print("✅ All tests passed! New format works correctly.")
|
||||
print("\nSummary:")
|
||||
print("- AI returns prompts as a JSON list (no keys)")
|
||||
print("- _parse_ai_response returns List[str]")
|
||||
print("- add_prompts_to_pool generates keys locally (poolprompt000, poolprompt001, etc.)")
|
||||
print("- draw_prompts_from_pool returns List[Dict[str, str]] with generated keys")
|
||||
|
||||
return True
|
||||
|
||||
if __name__ == "__main__":
|
||||
test_new_format()
|
||||
|
||||
|
||||
@@ -201,7 +201,7 @@ def test_python_scripts():
|
||||
"""Test that Python scripts are syntactically valid."""
|
||||
print("\nTesting Python scripts...")
|
||||
|
||||
scripts_to_test = ["generate_prompts.py", "simple_generate.py"]
|
||||
scripts_to_test = ["generate_prompts.py"]
|
||||
all_valid = True
|
||||
|
||||
for script in scripts_to_test:
|
||||
|
||||
@@ -1,98 +0,0 @@
|
||||
#!/usr/bin/env python3
|
||||
"""
|
||||
Test script to verify the prompt numbering logic.
|
||||
"""
|
||||
|
||||
import json
|
||||
import configparser
|
||||
|
||||
def get_num_prompts():
|
||||
"""Get the number of prompts from settings.cfg or default."""
|
||||
config = configparser.ConfigParser()
|
||||
num_prompts = 6 # Default value
|
||||
|
||||
try:
|
||||
config.read('settings.cfg')
|
||||
if 'prompts' in config and 'num_prompts' in config['prompts']:
|
||||
num_prompts = int(config['prompts']['num_prompts'])
|
||||
except (FileNotFoundError, ValueError):
|
||||
pass
|
||||
|
||||
return num_prompts
|
||||
|
||||
def test_renumbering():
|
||||
"""Test the renumbering logic."""
|
||||
|
||||
# Get number of prompts from config
|
||||
num_prompts = get_num_prompts()
|
||||
|
||||
# Create a sample historic prompts list
|
||||
historic_prompts = []
|
||||
for i in range(60):
|
||||
historic_prompts.append({
|
||||
f"prompt{i:02d}": f"Old prompt {i}"
|
||||
})
|
||||
|
||||
print(f"Original prompts: {len(historic_prompts)}")
|
||||
print(f"First prompt key: {list(historic_prompts[0].keys())[0]}")
|
||||
print(f"Last prompt key: {list(historic_prompts[-1].keys())[0]}")
|
||||
print(f"Number of prompts from config: {num_prompts}")
|
||||
|
||||
# Simulate adding new prompts (as the current code would create them)
|
||||
new_prompts = []
|
||||
for i in range(num_prompts):
|
||||
new_prompts.append({
|
||||
f"prompt{len(historic_prompts) + i:02d}": f"New prompt {i}"
|
||||
})
|
||||
|
||||
print(f"\nNew prompts to add: {len(new_prompts)}")
|
||||
for i, prompt in enumerate(new_prompts):
|
||||
print(f" New prompt {i}: {list(prompt.keys())[0]}")
|
||||
|
||||
# Prepend new prompts (reverse to maintain order)
|
||||
for prompt in reversed(new_prompts):
|
||||
historic_prompts.insert(0, prompt)
|
||||
|
||||
print(f"\nAfter prepending: {len(historic_prompts)} prompts")
|
||||
print(f"First 3 prompts keys:")
|
||||
for i in range(3):
|
||||
print(f" {i}: {list(historic_prompts[i].keys())[0]}")
|
||||
|
||||
# Renumber all prompts
|
||||
renumbered_prompts = []
|
||||
for i, prompt_dict in enumerate(historic_prompts):
|
||||
prompt_key = list(prompt_dict.keys())[0]
|
||||
prompt_text = prompt_dict[prompt_key]
|
||||
|
||||
new_prompt_key = f"prompt{i:02d}"
|
||||
renumbered_prompts.append({
|
||||
new_prompt_key: prompt_text
|
||||
})
|
||||
|
||||
print(f"\nAfter renumbering: {len(renumbered_prompts)} prompts")
|
||||
print(f"First 10 prompts keys:")
|
||||
for i in range(10):
|
||||
print(f" prompt{i:02d}: {list(renumbered_prompts[i].keys())[0]} = {renumbered_prompts[i][f'prompt{i:02d}'][:30]}...")
|
||||
|
||||
# Keep only first 60
|
||||
if len(renumbered_prompts) > 60:
|
||||
renumbered_prompts = renumbered_prompts[:60]
|
||||
|
||||
print(f"\nAfter keeping only first 60: {len(renumbered_prompts)} prompts")
|
||||
print(f"First prompt: {list(renumbered_prompts[0].keys())[0]} = {renumbered_prompts[0]['prompt00'][:30]}...")
|
||||
print(f"Last prompt: {list(renumbered_prompts[-1].keys())[0]} = {renumbered_prompts[-1]['prompt59'][:30]}...")
|
||||
|
||||
# Verify the range
|
||||
for i in range(60):
|
||||
expected_key = f"prompt{i:02d}"
|
||||
actual_key = list(renumbered_prompts[i].keys())[0]
|
||||
if expected_key != actual_key:
|
||||
print(f"ERROR: Expected {expected_key}, got {actual_key}")
|
||||
return False
|
||||
|
||||
print("\n✅ All tests passed! Prompt numbering is correct.")
|
||||
return True
|
||||
|
||||
if __name__ == "__main__":
|
||||
test_renumbering()
|
||||
|
||||
@@ -6,7 +6,9 @@ Test the error handling with a valid response.
|
||||
import sys
|
||||
import os
|
||||
import json
|
||||
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
|
||||
|
||||
# Add the parent directory to the Python path
|
||||
sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
|
||||
|
||||
from generate_prompts import JournalPromptGenerator
|
||||
|
||||
|
||||
Reference in New Issue
Block a user