ollama_chat 0.0.71 → 0.0.72
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 +4 -4
- data/CHANGES.md +28 -0
- data/README.md +42 -40
- data/lib/ollama_chat/chat.rb +105 -63
- data/lib/ollama_chat/clipboard.rb +32 -6
- data/lib/ollama_chat/config_handling.rb +18 -6
- data/lib/ollama_chat/file_editing.rb +61 -0
- data/lib/ollama_chat/information.rb +42 -40
- data/lib/ollama_chat/input_content.rb +3 -9
- data/lib/ollama_chat/message_editing.rb +1 -9
- data/lib/ollama_chat/message_list.rb +3 -30
- data/lib/ollama_chat/ollama_chat_config/default_config.yml +34 -0
- data/lib/ollama_chat/pager.rb +40 -0
- data/lib/ollama_chat/personae_management.rb +296 -0
- data/lib/ollama_chat/redis_cache.rb +2 -2
- data/lib/ollama_chat/tool_calling.rb +4 -3
- data/lib/ollama_chat/tools/copy_to_clipboard.rb +21 -5
- data/lib/ollama_chat/tools/execute_grep.rb +1 -1
- data/lib/ollama_chat/tools/generate_password.rb +3 -3
- data/lib/ollama_chat/tools/get_time.rb +55 -59
- data/lib/ollama_chat/tools/insert_into_editor.rb +68 -0
- data/lib/ollama_chat/tools/open_file_in_editor.rb +0 -1
- data/lib/ollama_chat/tools/run_tests.rb +2 -2
- data/lib/ollama_chat/tools/weather/dwd_sensor.rb +2 -2
- data/lib/ollama_chat/tools/write_file.rb +5 -2
- data/lib/ollama_chat/tools.rb +1 -0
- data/lib/ollama_chat/utils/chooser.rb +1 -1
- data/lib/ollama_chat/version.rb +1 -1
- data/lib/ollama_chat/vim.rb +4 -4
- data/lib/ollama_chat.rb +4 -1
- data/ollama_chat.gemspec +5 -5
- data/spec/ollama_chat/chat_spec.rb +0 -1
- data/spec/ollama_chat/clipboard_spec.rb +3 -3
- data/spec/ollama_chat/input_content_spec.rb +5 -4
- data/spec/ollama_chat/message_editing_spec.rb +4 -3
- data/spec/ollama_chat/tools/copy_to_clipboard_spec.rb +39 -7
- data/spec/ollama_chat/tools/insert_into_editor_spec.rb +126 -0
- data/spec/spec_helper.rb +1 -1
- metadata +13 -3
- /data/lib/ollama_chat/{env_config.rb → oc.rb} +0 -0
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: aba37f4f59280b1d21b76df79cb20b1e6d4f1b7e05fd91dfd6940368ff8a168f
|
|
4
|
+
data.tar.gz: 88d8d50a503c98973159f2874c0f04a4139e27469363c77b66560e0a965cf890
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 9bc913077bc16ded309925188841e5f803521df0582a47c747fd20c31b03b4a15cfdabf324f683a910d3f9de4f2003b8b31867a4da052e84c072736033f613a2
|
|
7
|
+
data.tar.gz: 9df32e077b73b959ddff9754241fe10a507b8b861e917c59dd6a6032ed4eb4d520ce8bf3047d4401f06e528c17de55d2cba12d26137d52b8fc69eeddf0d17045
|
data/CHANGES.md
CHANGED
|
@@ -1,5 +1,33 @@
|
|
|
1
1
|
# Changes
|
|
2
2
|
|
|
3
|
+
## 2026-03-04 v0.0.72
|
|
4
|
+
|
|
5
|
+
- Introduced `OllamaChat::PersonaeManagement` module and `/persona` command
|
|
6
|
+
with subcommands `add`, `delete`, `edit`, `list`, `play`, `file`, `info`,
|
|
7
|
+
`load`.
|
|
8
|
+
- Added `/config reload` subcommand to `OllamaChat::Chat`; handler
|
|
9
|
+
`reload_config` in `OllamaChat::ConfigHandling` prompts for confirmation,
|
|
10
|
+
calls `save_conversation`, then restarts with `exec($0,*ARGV)`.
|
|
11
|
+
- Added `-p` command‑line option (`-p PERSONA`) to load personas at startup.
|
|
12
|
+
- Created `OllamaChat::Pager` module for pager functionality.
|
|
13
|
+
- Created `OllamaChat::FileEditing` module; refactored `edit_config`,
|
|
14
|
+
`compose`, `revise_last` to use `edit_file`; added `vim(server_name = nil)`
|
|
15
|
+
returning `OllamaChat::Vim` and `perform_insert(text:, content:)`.
|
|
16
|
+
- Added LLM‑driven tool `insert_into_editor`
|
|
17
|
+
(`lib/ollama_chat/tools/insert_into_editor.rb`) with RSpec tests; default
|
|
18
|
+
config (`default_config.yml`) now enables confirmation flag for this tool.
|
|
19
|
+
- Enhanced `copy_to_clipboard` tool: accepts optional `text` parameter,
|
|
20
|
+
includes helper `last_message_content`, returns `true` on success, updated
|
|
21
|
+
error messages, added test for custom text.
|
|
22
|
+
- Added `bytes_written` tracking to `write_file` tool; fixed return hash key.
|
|
23
|
+
- Added visual separator for tool output.
|
|
24
|
+
- Renamed `env_config.rb` to `oc.rb`; updated requires accordingly.
|
|
25
|
+
- Added `save_history` call after conversation backup to persist history before
|
|
26
|
+
restart.
|
|
27
|
+
- Updated documentation and help messages to reflect new commands and options.
|
|
28
|
+
- Standardised type hints across codebase, replacing generic Boolean comments
|
|
29
|
+
with explicit `[ true, false ]`.
|
|
30
|
+
|
|
3
31
|
## 2026-02-26 v0.0.71
|
|
4
32
|
|
|
5
33
|
- Add new clipboard utilities: `tools/copy_to_clipboard.rb` and
|
data/README.md
CHANGED
|
@@ -58,6 +58,7 @@ Usage: ollama_chat [OPTIONS]
|
|
|
58
58
|
-u URL the ollama base url, OLLAMA_URL
|
|
59
59
|
-m MODEL the ollama model to chat with, OLLAMA_CHAT_MODEL, ?selector
|
|
60
60
|
-s SYSTEM the system prompt to use as a file, OLLAMA_CHAT_SYSTEM, ?selector
|
|
61
|
+
-p PERSONA load a persona via name/file for roleplay at startup
|
|
61
62
|
-c CHAT a saved chat conversation to load
|
|
62
63
|
-C COLLECTION name of the collection used in this conversation
|
|
63
64
|
-D DOCUMENT load document and add to embeddings collection (multiple)
|
|
@@ -151,46 +152,47 @@ subject - the young, blue-eyed cat.
|
|
|
151
152
|
The following commands can be given inside the chat, if prefixed by a `/`:
|
|
152
153
|
|
|
153
154
|
```
|
|
154
|
-
/reconnect
|
|
155
|
-
/copy
|
|
156
|
-
/paste
|
|
157
|
-
/markdown
|
|
158
|
-
/stream
|
|
159
|
-
/location
|
|
160
|
-
/voice [change]
|
|
161
|
-
/last [n]
|
|
162
|
-
/list [n]
|
|
163
|
-
/clear [what]
|
|
164
|
-
/clobber
|
|
165
|
-
/drop [n]
|
|
166
|
-
/model
|
|
167
|
-
/system [show]
|
|
168
|
-
/prompt
|
|
169
|
-
/
|
|
170
|
-
/
|
|
171
|
-
/
|
|
172
|
-
/
|
|
173
|
-
/
|
|
174
|
-
/
|
|
175
|
-
/
|
|
176
|
-
/
|
|
177
|
-
/
|
|
178
|
-
/
|
|
179
|
-
/
|
|
180
|
-
/
|
|
181
|
-
/
|
|
182
|
-
/
|
|
183
|
-
/
|
|
184
|
-
/
|
|
185
|
-
/
|
|
186
|
-
/
|
|
187
|
-
/
|
|
188
|
-
/
|
|
189
|
-
/
|
|
190
|
-
/
|
|
191
|
-
/
|
|
192
|
-
/
|
|
193
|
-
/
|
|
155
|
+
/reconnect reconnect to current ollama server
|
|
156
|
+
/copy to copy last response to clipboard
|
|
157
|
+
/paste to paste content
|
|
158
|
+
/markdown toggle markdown output
|
|
159
|
+
/stream toggle stream output
|
|
160
|
+
/location toggle location submission
|
|
161
|
+
/voice [change] toggle voice output or change the voice
|
|
162
|
+
/last [n] show the last n / 1 system/assistant message
|
|
163
|
+
/list [n] list the last n / all conversation exchanges
|
|
164
|
+
/clear [what] clear what=messages|links|history|tags|all
|
|
165
|
+
/clobber clear the conversation, links, and collection
|
|
166
|
+
/drop [n] drop the last n exchanges, defaults to 1
|
|
167
|
+
/model change the model
|
|
168
|
+
/system [show] change/show system prompt
|
|
169
|
+
/prompt prefill user prompt with preset prompts
|
|
170
|
+
/persona add|delete|edit|file|info|list|load|play manage and load/play personas for roleplay
|
|
171
|
+
/regenerate the last answer message
|
|
172
|
+
/collection [clear|change] change (default) collection or clear
|
|
173
|
+
/info show information for current session
|
|
174
|
+
/config [edit|reload] output/edit/reload current configuration ("/Users/flori/.config/ollama_chat/config.yml")
|
|
175
|
+
/document_policy pick a scan policy for document references
|
|
176
|
+
/think choose ollama think mode setting for models
|
|
177
|
+
/think_loud enable to think out loud instead of silently
|
|
178
|
+
/import source import the source's content
|
|
179
|
+
/summarize [n] source summarize the source's content in n words
|
|
180
|
+
/embedding toggle embedding paused or not
|
|
181
|
+
/embed source embed the source's content
|
|
182
|
+
/web [n] query query web & for n(=1) results (policy: importing)
|
|
183
|
+
/links [clear] display (or clear) links used in the chat
|
|
184
|
+
/save filename store conversation messages
|
|
185
|
+
/load filename load conversation messages
|
|
186
|
+
/compose compose content using an EDITOR
|
|
187
|
+
/input [pattern] select and read content from a file (default: **/*)
|
|
188
|
+
/context [pattern...] collect context with glob patterns
|
|
189
|
+
/revise_last edit the last response in an external editor
|
|
190
|
+
/output filename save last response to filename
|
|
191
|
+
/pipe command write last response to command's stdin
|
|
192
|
+
/tools [enable|disable|on|off] list enabled, enable/disable tools, support on/off
|
|
193
|
+
/vim insert the last message into a vim server
|
|
194
|
+
/quit to quit
|
|
195
|
+
/help [me] to view this help (me = interactive ai help)
|
|
194
196
|
```
|
|
195
197
|
|
|
196
198
|
### Using `ollama_chat_send` to send input to a running `ollama_chat`
|
data/lib/ollama_chat/chat.rb
CHANGED
|
@@ -47,15 +47,18 @@ class OllamaChat::Chat
|
|
|
47
47
|
include OllamaChat::MessageOutput
|
|
48
48
|
include OllamaChat::Clipboard
|
|
49
49
|
include OllamaChat::MessageFormat
|
|
50
|
+
include OllamaChat::Pager
|
|
50
51
|
include OllamaChat::History
|
|
51
52
|
include OllamaChat::ServerSocket
|
|
52
53
|
include OllamaChat::KramdownANSI
|
|
54
|
+
include OllamaChat::FileEditing
|
|
53
55
|
include OllamaChat::Conversation
|
|
54
56
|
include OllamaChat::InputContent
|
|
55
57
|
include OllamaChat::MessageEditing
|
|
56
58
|
include OllamaChat::LocationHandling
|
|
57
59
|
include OllamaChat::ToolCalling
|
|
58
60
|
include OllamaChat::ConfigHandling
|
|
61
|
+
include OllamaChat::PersonaeManagement
|
|
59
62
|
|
|
60
63
|
# Initializes a new OllamaChat::Chat instance with the given command-line
|
|
61
64
|
# arguments.
|
|
@@ -85,7 +88,7 @@ class OllamaChat::Chat
|
|
|
85
88
|
# @raise [RuntimeError] If the Ollama API version is less than 0.9.0, indicating
|
|
86
89
|
# incompatibility with required API features
|
|
87
90
|
def initialize(argv: ARGV.dup)
|
|
88
|
-
@opts = go 'f:u:m:s:c:C:D:MESVh', argv
|
|
91
|
+
@opts = go 'f:u:m:s:p:c:C:D:MESVh', argv
|
|
89
92
|
@opts[?h] and exit usage
|
|
90
93
|
@opts[?V] and exit version
|
|
91
94
|
@messages = OllamaChat::MessageList.new(self)
|
|
@@ -113,6 +116,7 @@ class OllamaChat::Chat
|
|
|
113
116
|
@enabled_tools = default_enabled_tools
|
|
114
117
|
@tool_call_results = {}
|
|
115
118
|
init_chat_history
|
|
119
|
+
setup_personae_directory
|
|
116
120
|
@opts[?S] and init_server_socket
|
|
117
121
|
rescue ComplexConfig::AttributeMissing, ComplexConfig::ConfigurationSyntaxError => e
|
|
118
122
|
fix_config(e)
|
|
@@ -155,38 +159,15 @@ class OllamaChat::Chat
|
|
|
155
159
|
# messages associated with this instance
|
|
156
160
|
attr_reader :messages
|
|
157
161
|
|
|
158
|
-
# The start method initializes the chat session by displaying information
|
|
159
|
-
#
|
|
160
|
-
# with the chat.
|
|
162
|
+
# The start method initializes the chat session by displaying information,
|
|
163
|
+
# then prompts the user for input to begin interacting with the chat.
|
|
161
164
|
def start
|
|
162
165
|
info
|
|
163
|
-
if messages.size > 1
|
|
164
|
-
messages.list_conversation(2)
|
|
165
|
-
end
|
|
166
166
|
STDOUT.puts "\nType /help to display the chat help."
|
|
167
167
|
|
|
168
168
|
interact_with_user
|
|
169
169
|
end
|
|
170
170
|
|
|
171
|
-
# The vim method creates and returns a new Vim instance for interacting with
|
|
172
|
-
# a Vim server.
|
|
173
|
-
#
|
|
174
|
-
# This method initializes a Vim client that can be used to insert text into
|
|
175
|
-
# Vim buffers or open files in a running Vim server. It derives the server
|
|
176
|
-
# name from the provided argument or uses a default server name based on the
|
|
177
|
-
# current working directory.
|
|
178
|
-
#
|
|
179
|
-
# @param server_name [ String, nil ] the name of the Vim server to connect to
|
|
180
|
-
# If nil or empty, a default server name is derived from the current
|
|
181
|
-
# working directory
|
|
182
|
-
#
|
|
183
|
-
# @return [ OllamaChat::Vim ] a new Vim instance configured with the
|
|
184
|
-
# specified server name
|
|
185
|
-
def vim(server_name = nil)
|
|
186
|
-
clientserver = config.vim?&.clientserver
|
|
187
|
-
OllamaChat::Vim.new(server_name, clientserver:)
|
|
188
|
-
end
|
|
189
|
-
|
|
190
171
|
# The debug method accesses the debug configuration setting.
|
|
191
172
|
#
|
|
192
173
|
# @return [TrueClass, FalseClass] the current debug mode status
|
|
@@ -222,6 +203,7 @@ class OllamaChat::Chat
|
|
|
222
203
|
copy_to_clipboard
|
|
223
204
|
:next
|
|
224
205
|
when %r(^/paste$)
|
|
206
|
+
@parse_content = false
|
|
225
207
|
paste_from_clipboard
|
|
226
208
|
when %r(^/markdown$)
|
|
227
209
|
markdown.toggle
|
|
@@ -385,18 +367,73 @@ class OllamaChat::Chat
|
|
|
385
367
|
tools_support.set(false, show: true)
|
|
386
368
|
end
|
|
387
369
|
:next
|
|
388
|
-
when %r(^/config(?:\s+(edit))?$)
|
|
370
|
+
when %r(^/config(?:\s+(edit|reload))?$)
|
|
389
371
|
case $1
|
|
390
372
|
when 'edit'
|
|
391
373
|
edit_config
|
|
374
|
+
when 'reload'
|
|
375
|
+
reload_config
|
|
392
376
|
else
|
|
393
377
|
display_config
|
|
394
378
|
end
|
|
395
379
|
:next
|
|
380
|
+
when %r(^/persona(?:\s+(add|delete|edit|file|info|list|load|play))?$)
|
|
381
|
+
@parse_content = false
|
|
382
|
+
case $1
|
|
383
|
+
when 'add'
|
|
384
|
+
if result = add_persona
|
|
385
|
+
result
|
|
386
|
+
else
|
|
387
|
+
:next
|
|
388
|
+
end
|
|
389
|
+
when 'delete'
|
|
390
|
+
if result = delete_persona
|
|
391
|
+
result
|
|
392
|
+
else
|
|
393
|
+
:next
|
|
394
|
+
end
|
|
395
|
+
when 'edit'
|
|
396
|
+
if result = edit_persona
|
|
397
|
+
result
|
|
398
|
+
else
|
|
399
|
+
:next
|
|
400
|
+
end
|
|
401
|
+
when 'file'
|
|
402
|
+
if pathname = choose_filename('**/*.md')
|
|
403
|
+
pathname.read
|
|
404
|
+
else
|
|
405
|
+
:next
|
|
406
|
+
end
|
|
407
|
+
when 'info'
|
|
408
|
+
info_persona
|
|
409
|
+
:next
|
|
410
|
+
when 'list'
|
|
411
|
+
list_personae
|
|
412
|
+
:next
|
|
413
|
+
when 'load'
|
|
414
|
+
if result = load_personae
|
|
415
|
+
result
|
|
416
|
+
else
|
|
417
|
+
:next
|
|
418
|
+
end
|
|
419
|
+
when 'play'
|
|
420
|
+
if pathname = choose_filename('**/*.md')
|
|
421
|
+
play_persona_file(pathname)
|
|
422
|
+
else
|
|
423
|
+
:next
|
|
424
|
+
end
|
|
425
|
+
else
|
|
426
|
+
if result = play_persona.full?
|
|
427
|
+
result
|
|
428
|
+
else
|
|
429
|
+
:next
|
|
430
|
+
end
|
|
431
|
+
end
|
|
396
432
|
when %r(^/quit$), nil
|
|
397
433
|
STDOUT.puts "Goodbye."
|
|
398
434
|
:return
|
|
399
435
|
when %r(^/help me$)
|
|
436
|
+
@parse_content = false
|
|
400
437
|
config.prompts.help % { commands: display_chat_help_message }
|
|
401
438
|
when %r(^/)
|
|
402
439
|
display_chat_help
|
|
@@ -563,46 +600,51 @@ class OllamaChat::Chat
|
|
|
563
600
|
# interaction.
|
|
564
601
|
def interact_with_user
|
|
565
602
|
loop do
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
603
|
+
if persona_result = setup_persona_from_opts
|
|
604
|
+
@parse_content = false
|
|
605
|
+
content = persona_result
|
|
606
|
+
else
|
|
607
|
+
@parse_content = true
|
|
608
|
+
type = :terminal_input
|
|
609
|
+
input_prompt = bold { color(172) { message_type(@images) + " user" } } + bold { "> " }
|
|
610
|
+
begin
|
|
611
|
+
if content = handle_tool_call_results?
|
|
612
|
+
@parse_content = false
|
|
613
|
+
else
|
|
614
|
+
content = enable_command_completion do
|
|
615
|
+
if prefill_prompt = @prefill_prompt.full?
|
|
616
|
+
Reline.pre_input_hook = -> {
|
|
617
|
+
Reline.insert_text prefill_prompt.gsub(/\n*\z/, '')
|
|
618
|
+
@prefill_prompt = nil
|
|
619
|
+
}
|
|
620
|
+
else
|
|
621
|
+
Reline.pre_input_hook = nil
|
|
622
|
+
end
|
|
623
|
+
Reline.readline(input_prompt, true)&.chomp
|
|
581
624
|
end
|
|
582
|
-
|
|
625
|
+
end
|
|
626
|
+
rescue Interrupt
|
|
627
|
+
if message = server_socket_message
|
|
628
|
+
type = message.type.full?(:to_sym) || :socket_input
|
|
629
|
+
content = message.content
|
|
630
|
+
@parse_content = message.parse
|
|
631
|
+
STDOUT.puts color(112) { "Received a server socket message. Processing now…" }
|
|
632
|
+
else
|
|
633
|
+
raise
|
|
583
634
|
end
|
|
584
635
|
end
|
|
585
|
-
rescue Interrupt
|
|
586
|
-
if message = server_socket_message
|
|
587
|
-
type = message.type.full?(:to_sym) || :socket_input
|
|
588
|
-
content = message.content
|
|
589
|
-
@parse_content = message.parse
|
|
590
|
-
STDOUT.puts color(112) { "Received a server socket message. Processing now…" }
|
|
591
|
-
else
|
|
592
|
-
raise
|
|
593
|
-
end
|
|
594
|
-
end
|
|
595
636
|
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
|
|
599
|
-
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
637
|
+
if type == :terminal_input
|
|
638
|
+
case next_action = handle_input(content)
|
|
639
|
+
when :next
|
|
640
|
+
next
|
|
641
|
+
when :redo
|
|
642
|
+
redo
|
|
643
|
+
when :return
|
|
644
|
+
return
|
|
645
|
+
when String
|
|
646
|
+
content = next_action
|
|
647
|
+
end
|
|
606
648
|
end
|
|
607
649
|
end
|
|
608
650
|
|
|
@@ -11,25 +11,29 @@ module OllamaChat::Clipboard
|
|
|
11
11
|
# its content to the system clipboard using the command specified in
|
|
12
12
|
# the configuration (config.copy).
|
|
13
13
|
#
|
|
14
|
-
# @param content [
|
|
14
|
+
# @param content [true, false] If true, copies the content of the message;
|
|
15
15
|
# if false, copies the entire message object (default: false)
|
|
16
16
|
#
|
|
17
17
|
# @raise [OllamaChat::OllamaChatError] if the clipboard command specified
|
|
18
18
|
# in config.copy is not found in the system's PATH
|
|
19
19
|
# @raise [OllamaChat::OllamaChatError] if no assistant message is available
|
|
20
20
|
# to copy to the clipboard
|
|
21
|
-
def perform_copy_to_clipboard(content: false)
|
|
22
|
-
|
|
21
|
+
def perform_copy_to_clipboard(text: nil, content: false)
|
|
22
|
+
text ||= last_message_content(content:)
|
|
23
|
+
if text
|
|
23
24
|
copy = `which #{config.copy}`.chomp
|
|
24
25
|
if copy.present?
|
|
25
26
|
IO.popen(copy, 'w') do |clipboard|
|
|
26
|
-
clipboard.write(
|
|
27
|
+
clipboard.write(text)
|
|
27
28
|
end
|
|
29
|
+
true
|
|
28
30
|
else
|
|
29
|
-
raise OllamaChat::OllamaChatError,
|
|
31
|
+
raise OllamaChat::OllamaChatError,
|
|
32
|
+
"#{config.copy.inspect} command not found in system's path!"
|
|
30
33
|
end
|
|
31
34
|
else
|
|
32
|
-
raise OllamaChat::OllamaChatError,
|
|
35
|
+
raise OllamaChat::OllamaChatError,
|
|
36
|
+
"No text available to copy to the system clipboard."
|
|
33
37
|
end
|
|
34
38
|
end
|
|
35
39
|
|
|
@@ -67,6 +71,26 @@ module OllamaChat::Clipboard
|
|
|
67
71
|
|
|
68
72
|
private
|
|
69
73
|
|
|
74
|
+
# Returns the content of the last assistant message.
|
|
75
|
+
#
|
|
76
|
+
# This private helper method finds the most recent message from the assistant
|
|
77
|
+
# in the messages array and returns its content. It is used by
|
|
78
|
+
# `perform_copy_to_clipboard` when no custom text is provided.
|
|
79
|
+
#
|
|
80
|
+
# @param content [true, false] If true, returns the content of the message;
|
|
81
|
+
# if false, returns nil if no assistant message is found (default: false)
|
|
82
|
+
#
|
|
83
|
+
# @return [String, nil] The content of the last assistant message, or nil if
|
|
84
|
+
# no assistant message is found
|
|
85
|
+
#
|
|
86
|
+
# @example
|
|
87
|
+
# # Assuming @messages contains assistant messages
|
|
88
|
+
# last_message_content
|
|
89
|
+
# # => "This is the last assistant response"
|
|
90
|
+
def last_message_content(content: false)
|
|
91
|
+
@messages.find_last(content:) { _1.role == 'assistant' }&.content
|
|
92
|
+
end
|
|
93
|
+
|
|
70
94
|
# Copies the last assistant message to the system clipboard.
|
|
71
95
|
#
|
|
72
96
|
# This method is the interface for copying assistant messages to the
|
|
@@ -74,8 +98,10 @@ module OllamaChat::Clipboard
|
|
|
74
98
|
# handles any OllamaChat::OllamaChatError exceptions by printing the error
|
|
75
99
|
# message to standard error and does not re-raise the exception.
|
|
76
100
|
def copy_to_clipboard
|
|
101
|
+
|
|
77
102
|
perform_copy_to_clipboard
|
|
78
103
|
STDOUT.puts "The last response has been successfully copied to the system clipboard."
|
|
104
|
+
true
|
|
79
105
|
rescue OllamaChat::OllamaChatError => e
|
|
80
106
|
STDERR.puts e.message
|
|
81
107
|
end
|
|
@@ -83,18 +83,30 @@ module OllamaChat::ConfigHandling
|
|
|
83
83
|
# 3. If editing was successful, prompts the user to restart
|
|
84
84
|
# `ollama_chat` if desired.
|
|
85
85
|
def edit_config
|
|
86
|
-
|
|
87
|
-
STDERR.puts "Need the environment variable var EDITOR defined to use an editor"
|
|
88
|
-
return
|
|
89
|
-
end
|
|
90
|
-
result = system Shellwords.join([ editor, @ollama_chat_config.filename ])
|
|
91
|
-
if result
|
|
86
|
+
if result = edit_file(@ollama_chat_config.filename)
|
|
92
87
|
if ask?(prompt: "Do you want to restart #{progname}? (y/n) ") =~ /\Ay/i
|
|
93
88
|
save_conversation(OC::XDG_CACHE_HOME + 'backup.json')
|
|
89
|
+
save_history
|
|
94
90
|
exec($0, *ARGV)
|
|
91
|
+
else
|
|
92
|
+
STDOUT.puts "Skipped reloading the config."
|
|
95
93
|
end
|
|
96
94
|
else
|
|
97
95
|
STDERR.puts "Editor returned a non-zero status!"
|
|
98
96
|
end
|
|
99
97
|
end
|
|
98
|
+
|
|
99
|
+
# Reloads the current configuration by restarting the process.
|
|
100
|
+
#
|
|
101
|
+
# @example Restarting the app after confirmation
|
|
102
|
+
# config.reload_config # => restarts if user answers "y"
|
|
103
|
+
def reload_config
|
|
104
|
+
if ask?(prompt: "Do you want to restart #{progname}? (y/n) ") =~ /\Ay/i
|
|
105
|
+
save_conversation(OC::XDG_CACHE_HOME + 'backup.json')
|
|
106
|
+
save_history
|
|
107
|
+
exec($0, *ARGV)
|
|
108
|
+
else
|
|
109
|
+
STDOUT.puts "Skipped reloading the config."
|
|
110
|
+
end
|
|
111
|
+
end
|
|
100
112
|
end
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
# Module for editing files using the configured editor
|
|
2
|
+
module OllamaChat::FileEditing
|
|
3
|
+
# Opens a file in the configured editor for editing.
|
|
4
|
+
#
|
|
5
|
+
# @param filename [String, Pathname] Path to the file to edit
|
|
6
|
+
# @return [true, false, nil] Exit status if successful, nil if editor not
|
|
7
|
+
# configured
|
|
8
|
+
def edit_file(filename)
|
|
9
|
+
unless editor = OC::EDITOR?
|
|
10
|
+
STDERR.puts "Need the environment variable var EDITOR defined to use an editor"
|
|
11
|
+
return
|
|
12
|
+
end
|
|
13
|
+
system Shellwords.join([ editor, filename ])
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
# The vim method creates and returns a new Vim instance for interacting with
|
|
17
|
+
# a Vim server.
|
|
18
|
+
#
|
|
19
|
+
# This method initializes a Vim client that can be used to insert text into
|
|
20
|
+
# Vim buffers or open files in a running Vim server. It derives the server
|
|
21
|
+
# name from the provided argument or uses a default server name based on the
|
|
22
|
+
# current working directory.
|
|
23
|
+
#
|
|
24
|
+
# @param server_name [ String, nil ] the name of the Vim server to connect to
|
|
25
|
+
# If nil or empty, a default server name is derived from the current
|
|
26
|
+
# working directory
|
|
27
|
+
#
|
|
28
|
+
# @return [ OllamaChat::Vim ] a new Vim instance configured with the
|
|
29
|
+
# specified server name
|
|
30
|
+
def vim(server_name = nil)
|
|
31
|
+
clientserver = config.vim?&.clientserver
|
|
32
|
+
OllamaChat::Vim.new(server_name, clientserver:)
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
# Inserts provided **text** into Vim using the configured editor client.
|
|
36
|
+
#
|
|
37
|
+
# @param [String, nil] text – Text to insert; if `nil`, defaults to the
|
|
38
|
+
# last response.
|
|
39
|
+
#
|
|
40
|
+
# @param [true, false] content – Treat input as content‑mode (`true`) or
|
|
41
|
+
# plain text (`false`).
|
|
42
|
+
#
|
|
43
|
+
# @return [true, false] true if insertion succeeded; otherwise raises
|
|
44
|
+
# OllamaChat::OllamaChatError.
|
|
45
|
+
#
|
|
46
|
+
# @raise [OllamaChat::OllamaChatError]
|
|
47
|
+
# * Raised when no text is available and insertion cannot proceed.
|
|
48
|
+
# * Also raised if the underlying Vim client reports a failure.
|
|
49
|
+
def perform_insert(text: nil, content: false)
|
|
50
|
+
text ||= last_message_content(content:)
|
|
51
|
+
if text
|
|
52
|
+
unless vim.insert(text)
|
|
53
|
+
raise OllamaChat::OllamaChatError, "Inserting text into editor failed!"
|
|
54
|
+
end
|
|
55
|
+
true
|
|
56
|
+
else
|
|
57
|
+
raise OllamaChat::OllamaChatError,
|
|
58
|
+
"No text available to copy to the system clipboard."
|
|
59
|
+
end
|
|
60
|
+
end
|
|
61
|
+
end
|