aia 0.9.13 → 0.9.14

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: d5d9ca1e0f36d50857345bcad1268359e8435c16ba2c159d68482c070de59207
4
- data.tar.gz: 20e10d41131b850e7320613f0959d8c94589e48422bc5ba948954c614c094c12
3
+ metadata.gz: 91bd0c834c03dafa5c71d9d5e608db37ecd398c897e806361069aabee36d8abc
4
+ data.tar.gz: d275ec9393e55f3b39978fffd97a9eecf36021786ef579cdae0746488b0fe401
5
5
  SHA512:
6
- metadata.gz: bb7913215b44a686db90c9e9e4a69a00024611c0a28f7f06da4290ad7781ef9685288845ea17f3c4180f74badf4d0829a462596a0280aed91354b6d54a36f975
7
- data.tar.gz: 1701b67da9e0aa8afa4cd1815422989544c191e50a38f58205984b1d96033d4a6dea27fe1b9efceb9307b231848fd9cc6440bd83203a9b03dfa7c5dbee700fd2
6
+ metadata.gz: b2f00745bd78ffba8a434497946aa4a2116b7d0cfe805f8a5b132869af70e6698b490f8361a7589da875dc8d64a9869cd5c22b588347cabeefa10b0f8585e196
7
+ data.tar.gz: e4334b5fb5d25851aa3a1c29af391f82b6fc9ecbf1f6bc52edf999475e29b62ecf40395c246200f5ff525c1e0d8d3dd51330a4738d4b2b20f08594c9d0969431
data/.version CHANGED
@@ -1 +1 @@
1
- 0.9.13
1
+ 0.9.14
data/CHANGELOG.md CHANGED
@@ -3,6 +3,50 @@
3
3
 
4
4
  ## Released
5
5
 
6
+ ### [0.9.14] 2025-09-19
7
+
8
+ #### New Features
9
+ - **NEW FEATURE**: Added `//checkpoint` directive to create named snapshots of conversation context
10
+ - **NEW FEATURE**: Added `//restore` directive to restore context to a previous checkpoint
11
+ - **NEW FEATURE**: Enhanced `//context` (and `//review`) directive to display checkpoint markers in conversation history
12
+ - **NEW FEATURE**: Added `//cp` alias for checkpoint directive
13
+
14
+ #### Improvements
15
+ - **ENHANCEMENT**: Context manager now tracks checkpoint positions for better context visualization
16
+ - **ENHANCEMENT**: Checkpoint system uses auto-incrementing integer names when no name is provided
17
+ - **ENHANCEMENT**: Restore directive defaults to last checkpoint when no name specified
18
+ - **ENHANCEMENT**: Clear context now also clears all checkpoints
19
+
20
+ #### Bug Fixes
21
+ - **BUG FIX**: Fixed `//help` directive that was showing empty list of directives
22
+ - **BUG FIX**: Help directive now displays all directives from all registered modules
23
+ - **BUG FIX**: Help directive now shows proper descriptions and aliases for all directives
24
+ - **BUG FIX**: Help directive organizes directives by category for better readability
25
+
26
+ #### Technical Changes
27
+ - Enhanced ContextManager with checkpoint storage and restoration capabilities
28
+ - Added checkpoint_positions method to track checkpoint locations in context
29
+ - Refactored help directive to collect directives from all registered modules
30
+ - Added comprehensive test coverage for checkpoint and restore functionality
31
+
32
+ ### [0.9.13] 2025-09-02
33
+ #### New Features
34
+ - **NEW FEATURE**: Added `--metrics` flag to show token counts for each model
35
+ - **NEW FEATURE**: Added `--cost` flag to enable cost estimation for each model
36
+
37
+ #### Improvements
38
+ - **DEPENDENCY**: Removed versionaire dependency, simplifying version management
39
+ - **ENHANCEMENT**: Improved test suite reliability and coverage
40
+ - **ENHANCEMENT**: Updated Gemfile.lock with latest dependency versions
41
+
42
+ #### Bug Fixes
43
+ - **BUG FIX**: Fixed version handling issues by removing external versioning dependency
44
+
45
+ #### Technical Changes
46
+ - Simplified version management by removing versionaire gem
47
+ - Enhanced test suite with improved assertions and coverage
48
+ - Updated various gem dependencies to latest stable versions
49
+
6
50
  ### [0.9.12] 2025-08-28
7
51
 
8
52
  #### New Features
data/README.md CHANGED
@@ -334,7 +334,9 @@ Directives are special commands in prompt files that begin with `//` and provide
334
334
  | Directive | Description | Example |
335
335
  |-----------|-------------|---------|
336
336
  | `//config` | Set configuration values | `//config model = gpt-4` |
337
- | `//context` | Show context for this conversation | `//context` |
337
+ | `//context` | Show context for this conversation with checkpoint markers | `//context` |
338
+ | `//checkpoint` | Create a named checkpoint of current context | `//checkpoint save_point` |
339
+ | `//restore` | Restore context to a previous checkpoint | `//restore save_point` |
338
340
  | `//include` | Insert file contents | `//include path/to/file.txt` |
339
341
  | `//shell` | Execute shell commands | `//shell ls -la` |
340
342
  | `//robot` | Show the pet robot ASCII art w/versions | `//robot` |
@@ -346,7 +348,7 @@ Directives are special commands in prompt files that begin with `//` and provide
346
348
  | `//model` | Show current model configuration | `//model` |
347
349
  | `//available_models` | List available models | `//available_models` |
348
350
  | `//tools` | Show a list of available tools and their description | `//tools` |
349
- | `//review` | Review current context | `//review` |
351
+ | `//review` | Review current context with checkpoint markers | `//review` |
350
352
 
351
353
  Directives can also be used in the interactive chat sessions.
352
354
 
@@ -379,6 +381,64 @@ Your prompt content here...
379
381
  Analyze the above information and provide insights.
380
382
  ```
381
383
 
384
+ #### Context Management with Checkpoints
385
+
386
+ AIA provides powerful context management capabilities in chat mode through checkpoint and restore directives:
387
+
388
+ ```bash
389
+ # Create a checkpoint with automatic naming (1, 2, 3...)
390
+ //checkpoint
391
+
392
+ # Create a named checkpoint
393
+ //checkpoint important_decision
394
+
395
+ # Restore to the last checkpoint
396
+ //restore
397
+
398
+ # Restore to a specific checkpoint
399
+ //restore important_decision
400
+
401
+ # View context with checkpoint markers
402
+ //context
403
+ ```
404
+
405
+ **Example Chat Session:**
406
+ ```
407
+ You: Tell me about Ruby programming
408
+ AI: Ruby is a dynamic programming language...
409
+
410
+ You: //checkpoint ruby_basics
411
+
412
+ You: Now explain object-oriented programming
413
+ AI: Object-oriented programming (OOP) is...
414
+
415
+ You: //checkpoint oop_concepts
416
+
417
+ You: Actually, let's go back to Ruby basics
418
+ You: //restore ruby_basics
419
+
420
+ You: //context
421
+ === Chat Context ===
422
+ Total messages: 4
423
+ Checkpoints: ruby_basics, oop_concepts
424
+
425
+ 1. [System]: You are a helpful assistant
426
+ 2. [User]: Tell me about Ruby programming
427
+ 3. [Assistant]: Ruby is a dynamic programming language...
428
+
429
+ 📍 [Checkpoint: ruby_basics]
430
+ ----------------------------------------
431
+ 4. [User]: Now explain object-oriented programming
432
+ === End of Context ===
433
+ ```
434
+
435
+ **Key Features:**
436
+ - **Auto-naming**: Checkpoints without names use incrementing integers (1, 2, 3...)
437
+ - **Named checkpoints**: Use meaningful names like `//checkpoint before_refactor`
438
+ - **Default restore**: `//restore` without a name restores to the last checkpoint
439
+ - **Context visualization**: `//context` shows checkpoint markers in conversation history
440
+ - **Clean slate**: `//clear` removes all context and checkpoints
441
+
382
442
  #### Custom Directive Examples
383
443
 
384
444
  You can extend AIA with custom directives by creating Ruby files that define new directive methods:
@@ -271,21 +271,93 @@ Inserts a fun ASCII robot character for visual breaks in prompts.
271
271
 
272
272
  ## Context Management Directives
273
273
 
274
+ ### `//checkpoint`
275
+ Create a named checkpoint of the current conversation context.
276
+
277
+ **Syntax**: `//checkpoint [name]`
278
+
279
+ **Examples**:
280
+ ```markdown
281
+ //checkpoint # Auto-named checkpoint (1, 2, 3...)
282
+ //checkpoint important_decision # Named checkpoint
283
+ //checkpoint before_refactor # Descriptive name
284
+ ```
285
+
286
+ **Features**:
287
+ - **Auto-naming**: If no name provided, uses incrementing integers (1, 2, 3...)
288
+ - **Named checkpoints**: Use meaningful names for easy identification
289
+ - **Deep copying**: Safely stores complete conversation state
290
+ - **Chat mode only**: Only available during interactive chat sessions
291
+
292
+ **Usage**:
293
+ - `//checkpoint` - Create an auto-named checkpoint
294
+ - `//checkpoint name` - Create a checkpoint with specific name
295
+
296
+ **Aliases**: `//cp`
297
+
298
+ ### `//restore`
299
+ Restore conversation context to a previously saved checkpoint.
300
+
301
+ **Syntax**: `//restore [name]`
302
+
303
+ **Examples**:
304
+ ```markdown
305
+ //restore # Restore to last checkpoint
306
+ //restore important_decision # Restore to named checkpoint
307
+ //restore 1 # Restore to auto-named checkpoint
308
+ ```
309
+
310
+ **Features**:
311
+ - **Default behavior**: Without a name, restores to the most recent checkpoint
312
+ - **Named restoration**: Restore to any previously saved checkpoint
313
+ - **Context truncation**: Removes all messages added after the checkpoint
314
+ - **Client refresh**: Automatically refreshes AI client context
315
+
316
+ **Usage**:
317
+ - `//restore` - Restore to the last checkpoint created
318
+ - `//restore name` - Restore to a specific named checkpoint
319
+ - Returns error message if checkpoint doesn't exist
320
+
274
321
  ### `//clear`
275
322
  Clear conversation context in chat mode.
276
323
 
277
324
  **Syntax**: `//clear`
278
325
 
279
- **Usage**: Only available during chat sessions. Clears the conversation history while keeping the session active.
326
+ **Usage**: Only available during chat sessions. Clears the conversation history and all checkpoints while keeping the session active.
280
327
 
281
328
  ### `//review`
282
- Display current conversation context.
329
+ Display current conversation context with checkpoint markers.
283
330
 
284
331
  **Syntax**: `//review`
285
332
 
286
333
  **Aliases**: `//context`
287
334
 
288
- Shows the current context manager state, including conversation history and metadata.
335
+ **Example Output**:
336
+ ```
337
+ === Chat Context ===
338
+ Total messages: 5
339
+ Checkpoints: ruby_basics, oop_concepts
340
+
341
+ 1. [System]: You are a helpful assistant
342
+ 2. [User]: Tell me about Ruby programming
343
+ 3. [Assistant]: Ruby is a dynamic programming language...
344
+
345
+ 📍 [Checkpoint: ruby_basics]
346
+ ----------------------------------------
347
+ 4. [User]: Now explain object-oriented programming
348
+ 5. [Assistant]: Object-oriented programming (OOP) is...
349
+
350
+ 📍 [Checkpoint: oop_concepts]
351
+ ----------------------------------------
352
+ === End of Context ===
353
+ ```
354
+
355
+ **Features**:
356
+ - Shows complete conversation history with message numbers
357
+ - Displays checkpoint markers (📍) at their exact positions
358
+ - Lists all available checkpoints
359
+ - Truncates long messages for readability (200 characters)
360
+ - Shows total message count and checkpoint summary
289
361
 
290
362
  ## Model and Information Directives
291
363
 
data/docs/guides/chat.md CHANGED
@@ -112,19 +112,71 @@ You: How do I handle user authentication?
112
112
  AI: For your Flask application, here are several authentication options...
113
113
  ```
114
114
 
115
+ #### Context Checkpoints
116
+ Create savepoints in your conversation to easily return to specific moments:
117
+
118
+ ```
119
+ You: Let's explore different authentication approaches for Flask.
120
+ AI: I can help you explore various authentication methods...
121
+
122
+ You: //checkpoint auth_start
123
+
124
+ You: Tell me about JWT authentication.
125
+ AI: JWT (JSON Web Tokens) authentication is a stateless approach...
126
+
127
+ You: //checkpoint jwt_discussion
128
+
129
+ You: What about OAuth integration?
130
+ AI: OAuth provides a robust framework for authentication...
131
+
132
+ You: Actually, let's go back to the JWT discussion
133
+ You: //restore jwt_discussion
134
+
135
+ You: //context
136
+ === Chat Context ===
137
+ Total messages: 6
138
+ Checkpoints: auth_start, jwt_discussion
139
+
140
+ 1. [System]: You are a helpful assistant
141
+ 2. [User]: Let's explore different authentication approaches for Flask.
142
+ 3. [Assistant]: I can help you explore various authentication methods...
143
+
144
+ 📍 [Checkpoint: auth_start]
145
+ ----------------------------------------
146
+ 4. [User]: Tell me about JWT authentication.
147
+ 5. [Assistant]: JWT (JSON Web Tokens) authentication is a stateless approach...
148
+
149
+ 📍 [Checkpoint: jwt_discussion]
150
+ ----------------------------------------
151
+ === End of Context ===
152
+ ```
153
+
154
+ **Checkpoint Commands**:
155
+ - `//checkpoint` - Create auto-numbered checkpoint (1, 2, 3...)
156
+ - `//checkpoint name` - Create named checkpoint
157
+ - `//restore` - Restore to last checkpoint
158
+ - `//restore name` - Restore to specific checkpoint
159
+ - `//cp name` - Short alias for checkpoint
160
+
161
+ **Use Cases for Checkpoints**:
162
+ - **Exploring alternatives**: Save before trying different approaches
163
+ - **Debugging conversations**: Return to working state after errors
164
+ - **Session branching**: Explore multiple conversation paths
165
+ - **Learning sessions**: Bookmark important explanations
166
+
115
167
  #### Context Inspection
116
168
  ```
117
- You: /context
118
- # Shows current conversation history and metadata
169
+ You: //context
170
+ # Shows current conversation history with checkpoint markers
171
+
172
+ You: //review
173
+ # Alternative command for context inspection
119
174
  ```
120
175
 
121
176
  #### Context Clearing
122
177
  ```
123
- You: /clear
124
- # Clears conversation history while keeping session active
125
-
126
- You: /new
127
- # Starts a completely fresh session
178
+ You: //clear
179
+ # Clears conversation history and all checkpoints while keeping session active
128
180
  ```
129
181
 
130
182
  ### Tool Integration in Chat
@@ -3,11 +3,13 @@
3
3
  module AIA
4
4
  # Manages the conversation context for chat sessions.
5
5
  class ContextManager
6
- attr_reader :context
6
+ attr_reader :context, :checkpoints
7
7
 
8
8
  # Initializes the ContextManager with an optional system prompt.
9
9
  def initialize(system_prompt: nil)
10
10
  @context = []
11
+ @checkpoints = {}
12
+ @checkpoint_counter = 0
11
13
  add_system_prompt(system_prompt) if system_prompt && !system_prompt.strip.empty?
12
14
  end
13
15
 
@@ -43,6 +45,10 @@ module AIA
43
45
  @context = []
44
46
  end
45
47
 
48
+ # Clear all checkpoints when clearing context
49
+ @checkpoints.clear
50
+ @checkpoint_counter = 0
51
+
46
52
  # Attempt to clear the LLM client's context as well
47
53
  begin
48
54
  if AIA.config.client && AIA.config.client.respond_to?(:clear_context)
@@ -61,6 +67,60 @@ module AIA
61
67
  end
62
68
  end
63
69
 
70
+ # Creates a checkpoint of the current context with an optional name.
71
+ #
72
+ # @param name [String, nil] The name of the checkpoint. If nil, uses an incrementing integer.
73
+ # @return [String] The name of the created checkpoint.
74
+ def create_checkpoint(name: nil)
75
+ if name.nil?
76
+ @checkpoint_counter += 1
77
+ name = @checkpoint_counter.to_s
78
+ end
79
+
80
+ # Store a deep copy of the current context and its position
81
+ @checkpoints[name] = {
82
+ context: @context.map(&:dup),
83
+ position: @context.size
84
+ }
85
+ @last_checkpoint_name = name
86
+ name
87
+ end
88
+
89
+ # Restores the context to a previously saved checkpoint.
90
+ #
91
+ # @param name [String, nil] The name of the checkpoint to restore. If nil, uses the last checkpoint.
92
+ # @return [Boolean] True if restore was successful, false otherwise.
93
+ def restore_checkpoint(name: nil)
94
+ name = @last_checkpoint_name if name.nil?
95
+
96
+ return false if name.nil? || !@checkpoints.key?(name)
97
+
98
+ # Restore the context from the checkpoint
99
+ checkpoint_data = @checkpoints[name]
100
+ @context = checkpoint_data[:context].map(&:dup)
101
+ true
102
+ end
103
+
104
+ # Returns the list of available checkpoint names.
105
+ #
106
+ # @return [Array<String>] The names of all checkpoints.
107
+ def checkpoint_names
108
+ @checkpoints.keys
109
+ end
110
+
111
+ # Returns checkpoint information mapped to context positions.
112
+ #
113
+ # @return [Hash<Integer, Array<String>>] Position to checkpoint names mapping.
114
+ def checkpoint_positions
115
+ positions = {}
116
+ @checkpoints.each do |name, data|
117
+ position = data[:position]
118
+ positions[position] ||= []
119
+ positions[position] << name
120
+ end
121
+ positions
122
+ end
123
+
64
124
  private
65
125
 
66
126
  # Adds or replaces the system prompt at the beginning of the context.
@@ -34,7 +34,7 @@ module AIA
34
34
  # Display details for all configured models
35
35
  puts
36
36
  models = Array(AIA.config.model)
37
-
37
+
38
38
  if models.size == 1
39
39
  puts "Current Model:"
40
40
  puts "=============="
@@ -48,10 +48,10 @@ module AIA
48
48
  puts
49
49
  puts "Model Details:"
50
50
  puts "-" * 50
51
-
51
+
52
52
  models.each_with_index do |model_name, index|
53
53
  puts "#{index + 1}. #{model_name}#{index == 0 ? ' (primary)' : ''}"
54
-
54
+
55
55
  # Try to get model details if available
56
56
  begin
57
57
  # Access the model details from RubyLLM's model registry
@@ -98,16 +98,89 @@ module AIA
98
98
  end
99
99
 
100
100
  def self.review(args, context_manager = nil)
101
- ap context_manager.get_context
101
+ return "Error: Context manager not available for //review directive." if context_manager.nil?
102
+
103
+ context = context_manager.get_context
104
+ checkpoint_positions = context_manager.checkpoint_positions
105
+
106
+ # Display context with checkpoint markers
107
+ puts "\n=== Chat Context ==="
108
+ puts "Total messages: #{context.size}"
109
+
110
+ if checkpoint_positions.any?
111
+ puts "Checkpoints: #{context_manager.checkpoint_names.join(', ')}"
112
+ end
113
+
114
+ puts "\n"
115
+
116
+ context.each_with_index do |message, index|
117
+ # Check if there's a checkpoint at this position
118
+ if checkpoint_positions[index]
119
+ checkpoint_names = checkpoint_positions[index].join(', ')
120
+ puts "📍 [Checkpoint: #{checkpoint_names}]"
121
+ puts "-" * 40
122
+ end
123
+
124
+ # Display the message
125
+ role_display = message[:role].capitalize
126
+ content_preview = message[:content].to_s
127
+
128
+ # Truncate long content for display
129
+ if content_preview.length > 200
130
+ content_preview = content_preview[0..197] + "..."
131
+ end
132
+
133
+ puts "#{index + 1}. [#{role_display}]: #{content_preview}"
134
+ puts ""
135
+ end
136
+
137
+ # Check if there's a checkpoint at the end (after all messages)
138
+ if checkpoint_positions[context.size]
139
+ checkpoint_names = checkpoint_positions[context.size].join(', ')
140
+ puts "📍 [Checkpoint: #{checkpoint_names}]"
141
+ puts "-" * 40
142
+ end
143
+
144
+ puts "=== End of Context ==="
102
145
  ''
103
146
  end
104
147
 
148
+ def self.checkpoint(args, context_manager = nil)
149
+ if context_manager.nil?
150
+ return "Error: Context manager not available for //checkpoint directive."
151
+ end
152
+
153
+ name = args.empty? ? nil : args.join(' ').strip
154
+ checkpoint_name = context_manager.create_checkpoint(name: name)
155
+ "Checkpoint '#{checkpoint_name}' created."
156
+ end
157
+
158
+ def self.restore(args, context_manager = nil)
159
+ if context_manager.nil?
160
+ return "Error: Context manager not available for //restore directive."
161
+ end
162
+
163
+ name = args.empty? ? nil : args.join(' ').strip
164
+
165
+ if context_manager.restore_checkpoint(name: name)
166
+ restored_name = name || context_manager.checkpoint_names.last
167
+ "Context restored to checkpoint '#{restored_name}'."
168
+ else
169
+ if name
170
+ "Error: Checkpoint '#{name}' not found. Available checkpoints: #{context_manager.checkpoint_names.join(', ')}"
171
+ else
172
+ "Error: No checkpoints available to restore."
173
+ end
174
+ end
175
+ end
176
+
105
177
  # Set up aliases - these work on the module's singleton class
106
178
  class << self
107
179
  alias_method :cfg, :config
108
180
  alias_method :temp, :temperature
109
181
  alias_method :topp, :top_p
110
182
  alias_method :context, :review
183
+ alias_method :ckp, :checkpoint
111
184
  end
112
185
  end
113
186
  end
@@ -85,30 +85,163 @@ module AIA
85
85
  puts "===================="
86
86
  puts
87
87
 
88
- directives = self.methods(false).map(&:to_s).reject do |m|
89
- ['run', 'initialize', 'private?', 'descriptions', 'aliases', 'build_aliases'].include?(m)
90
- end.sort
91
-
92
- build_aliases(directives)
88
+ # Manual descriptions for all directives
89
+ directive_descriptions = {
90
+ # Configuration directives
91
+ 'config' => 'View or set configuration values',
92
+ 'model' => 'View or change the AI model',
93
+ 'temperature' => 'Set the temperature parameter for AI responses',
94
+ 'top_p' => 'Set the top_p parameter for AI responses',
95
+ 'clear' => 'Clear the conversation context',
96
+ 'review' => 'Display the current conversation context with checkpoint markers',
97
+ 'checkpoint' => 'Create a named checkpoint of the current context',
98
+ 'restore' => 'Restore context to a previous checkpoint',
99
+
100
+ # Utility directives
101
+ 'tools' => 'List available tools',
102
+ 'next' => 'Set the next prompt in the sequence',
103
+ 'pipeline' => 'Set or view the prompt workflow sequence',
104
+ 'terse' => 'Add instruction for concise responses',
105
+ 'robot' => 'Display ASCII robot art',
106
+
107
+ # Execution directives
108
+ 'ruby' => 'Execute Ruby code',
109
+ 'shell' => 'Execute shell commands',
110
+ 'say' => 'Use text-to-speech to speak the text',
111
+
112
+ # Web and File directives
113
+ 'webpage' => 'Fetch and include content from a webpage',
114
+ 'include' => 'Include content from a file',
115
+ 'include_file' => 'Include file content (internal use)',
116
+ 'included_files' => 'List files that have been included',
117
+ 'included_files=' => 'Set the list of included files',
118
+
119
+ # Model directives
120
+ 'available_models' => 'List all available AI models',
121
+ 'compare' => 'Compare responses from multiple models',
122
+ 'help' => 'Show this help message',
123
+
124
+ # Aliases (these get their descriptions from main directive)
125
+ 'cfg' => nil, # alias for config
126
+ 'temp' => nil, # alias for temperature
127
+ 'topp' => nil, # alias for top_p
128
+ 'context' => nil, # alias for review
129
+ 'cp' => nil, # alias for checkpoint
130
+ 'workflow' => nil, # alias for pipeline
131
+ 'rb' => nil, # alias for ruby
132
+ 'sh' => nil, # alias for shell
133
+ 'web' => nil, # alias for webpage
134
+ 'website' => nil, # alias for webpage
135
+ 'import' => nil, # alias for include
136
+ 'models' => nil, # alias for available_models
137
+ 'all_models' => nil, # alias for available_models
138
+ 'am' => nil, # alias for available_models
139
+ 'llms' => nil, # alias for available_models
140
+ 'available' => nil, # alias for available_models
141
+ 'cmp' => nil, # alias for compare
142
+ }
143
+
144
+ # Get all registered directive modules from the Registry
145
+ all_modules = [
146
+ AIA::Directives::WebAndFile,
147
+ AIA::Directives::Utility,
148
+ AIA::Directives::Configuration,
149
+ AIA::Directives::Execution,
150
+ AIA::Directives::Models
151
+ ]
152
+
153
+ all_directives = {}
154
+ excluded_methods = ['run', 'initialize', 'private?', 'descriptions', 'aliases', 'build_aliases',
155
+ 'desc', 'method_added', 'register_directive_module', 'process',
156
+ 'directive?', 'prefix_size']
157
+
158
+ # Collect directives from all modules
159
+ all_modules.each do |mod|
160
+ methods = mod.methods(false).map(&:to_s).reject { |m| excluded_methods.include?(m) }
161
+
162
+ methods.each do |method|
163
+ # Skip if this is an alias (has nil description)
164
+ next if directive_descriptions.key?(method) && directive_descriptions[method].nil?
165
+
166
+ description = directive_descriptions[method] || method.gsub('_', ' ').capitalize
167
+
168
+ all_directives[method] = {
169
+ module: mod.name.split('::').last,
170
+ description: description,
171
+ aliases: []
172
+ }
173
+ end
174
+ end
93
175
 
94
- directives.each do |directive|
95
- next unless descriptions[directive]
176
+ # Manually map known aliases
177
+ alias_mappings = {
178
+ 'config' => ['cfg'],
179
+ 'temperature' => ['temp'],
180
+ 'top_p' => ['topp'],
181
+ 'review' => ['context'],
182
+ 'checkpoint' => ['cp'],
183
+ 'pipeline' => ['workflow'],
184
+ 'ruby' => ['rb'],
185
+ 'shell' => ['sh'],
186
+ 'webpage' => ['web', 'website'],
187
+ 'include' => ['import'],
188
+ 'available_models' => ['models', 'all_models', 'am', 'llms', 'available'],
189
+ 'compare' => ['cmp']
190
+ }
191
+
192
+ # Apply alias mappings
193
+ alias_mappings.each do |directive, aliases|
194
+ if all_directives[directive]
195
+ all_directives[directive][:aliases] = aliases
196
+ end
197
+ end
96
198
 
97
- others = aliases[directive]
199
+ # Sort and display directives by category
200
+ categories = {
201
+ 'Configuration' => ['config', 'model', 'temperature', 'top_p', 'clear', 'review', 'checkpoint', 'restore'],
202
+ 'Utility' => ['tools', 'next', 'pipeline', 'terse', 'robot', 'help'],
203
+ 'Execution' => ['ruby', 'shell', 'say'],
204
+ 'Web & Files' => ['webpage', 'include'],
205
+ 'Models' => ['available_models', 'compare']
206
+ }
207
+
208
+ categories.each do |category, directives|
209
+ puts "#{category}:"
210
+ puts "-" * category.length
211
+
212
+ directives.each do |directive|
213
+ info = all_directives[directive]
214
+ next unless info
215
+
216
+ if info[:aliases] && !info[:aliases].empty?
217
+ with_prefix = info[:aliases].map { |m| PromptManager::Prompt::DIRECTIVE_SIGNAL + m }
218
+ alias_text = " (aliases: #{with_prefix.join(', ')})"
219
+ else
220
+ alias_text = ""
221
+ end
98
222
 
99
- if others.empty?
100
- others_line = ""
101
- else
102
- with_prefix = others.map { |m| PromptManager::Prompt::DIRECTIVE_SIGNAL + m }
103
- others_line = "\tAliases:#{with_prefix.join(' ')}\n"
223
+ puts " //#{directive}#{alias_text}"
224
+ puts " #{info[:description]}"
225
+ puts
104
226
  end
227
+ end
105
228
 
106
- puts <<~TEXT
107
- //#{directive} #{descriptions[directive]}
108
- #{others_line}
109
- TEXT
229
+ # Show any uncategorized directives
230
+ categorized = categories.values.flatten
231
+ uncategorized = all_directives.keys - categorized - ['include_file', 'included_files', 'included_files=']
232
+
233
+ if uncategorized.any?
234
+ puts "Other:"
235
+ puts "------"
236
+ uncategorized.sort.each do |directive|
237
+ info = all_directives[directive]
238
+ puts " //#{directive}"
239
+ puts " #{info[:description]}"
240
+ puts
241
+ end
110
242
  end
111
243
 
244
+ puts "\nTotal: #{all_directives.size} directives available"
112
245
  ""
113
246
  end
114
247
 
data/lib/aia/session.rb CHANGED
@@ -407,10 +407,12 @@ module AIA
407
407
 
408
408
  def process_chat_directive(follow_up_prompt)
409
409
  directive_output = @directive_processor.process(follow_up_prompt, @context_manager)
410
-
410
+
411
411
  return handle_clear_directive if follow_up_prompt.strip.start_with?("//clear")
412
+ return handle_checkpoint_directive(directive_output) if follow_up_prompt.strip.start_with?("//checkpoint")
413
+ return handle_restore_directive(directive_output) if follow_up_prompt.strip.start_with?("//restore")
412
414
  return handle_empty_directive_output if directive_output.nil? || directive_output.strip.empty?
413
-
415
+
414
416
  handle_successful_directive(follow_up_prompt, directive_output)
415
417
  end
416
418
 
@@ -438,6 +440,31 @@ module AIA
438
440
  nil
439
441
  end
440
442
 
443
+ def handle_checkpoint_directive(directive_output)
444
+ @ui_presenter.display_info(directive_output)
445
+ nil
446
+ end
447
+
448
+ def handle_restore_directive(directive_output)
449
+ # If the restore was successful, we also need to refresh the client's context
450
+ if directive_output.start_with?("Context restored")
451
+ # Try to clear and rebuild the client's context
452
+ if AIA.config.client && AIA.config.client.respond_to?(:clear_context)
453
+ AIA.config.client.clear_context
454
+ end
455
+
456
+ # Optionally reinitialize the client for a clean state
457
+ begin
458
+ AIA.config.client = AIA::RubyLLMAdapter.new
459
+ rescue => e
460
+ STDERR.puts "Error reinitializing client after restore: #{e.message}"
461
+ end
462
+ end
463
+
464
+ @ui_presenter.display_info(directive_output)
465
+ nil
466
+ end
467
+
441
468
  def handle_empty_directive_output
442
469
  nil
443
470
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: aia
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.9.13
4
+ version: 0.9.14
5
5
  platform: ruby
6
6
  authors:
7
7
  - Dewayne VanHoozer
@@ -433,7 +433,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
433
433
  - !ruby/object:Gem::Version
434
434
  version: '0'
435
435
  requirements: []
436
- rubygems_version: 3.7.1
436
+ rubygems_version: 3.6.9
437
437
  specification_version: 4
438
438
  summary: Multi-model AI CLI with dynamic prompts, consensus responses, shell & Ruby
439
439
  integration, and seamless chat workflows.