|
24 | 24 |
|
25 | 25 | (def ^:private logger-tag "[CHAT]") |
26 | 26 |
|
| 27 | +(defn ^:private new-content-id [] |
| 28 | + (str (random-uuid))) |
| 29 | + |
27 | 30 | (defn default-model [db config] |
28 | 31 | (llm-api/default-model db config)) |
29 | 32 |
|
|
600 | 603 | :on-first-response-received (fn [& _] |
601 | 604 | (assert-chat-not-stopped! chat-ctx) |
602 | 605 | (doseq [message user-messages] |
603 | | - (add-to-history! message)) |
| 606 | + (add-to-history! (assoc message :content-id (:user-content-id chat-ctx)))) |
604 | 607 | (send-content! chat-ctx :system {:type :progress |
605 | 608 | :state :running |
606 | 609 | :text "Generating"})) |
|
622 | 625 |
|
623 | 626 | (finish-chat-prompt! :idle chat-ctx)) |
624 | 627 | :finish (do |
625 | | - (add-to-history! {:role "assistant" :content [{:type :text :text @received-msgs*}]}) |
| 628 | + (add-to-history! {:role "assistant" |
| 629 | + :content [{:type :text :text @received-msgs*}]}) |
626 | 630 | (finish-chat-prompt! :idle chat-ctx)))) |
627 | 631 | :on-prepare-tool-call (fn [{:keys [id full-name arguments-text]}] |
628 | 632 | (assert-chat-not-stopped! chat-ctx) |
|
919 | 923 | :id (:id message-content) |
920 | 924 | :total-time-ms (:total-time-ms message-content)}])) |
921 | 925 |
|
| 926 | +(defn ^:private send-chat-contents! [messages chat-ctx] |
| 927 | + (doseq [message messages] |
| 928 | + (doseq [chat-content (message-content->chat-content (:role message) (:content message))] |
| 929 | + (send-content! chat-ctx |
| 930 | + (:role message) |
| 931 | + chat-content)))) |
| 932 | + |
922 | 933 | (defn ^:private handle-command! [{:keys [command args]} chat-ctx] |
923 | 934 | (let [{:keys [type on-finished-side-effect] :as result} (f.commands/handle-command! command args chat-ctx)] |
924 | 935 | (case type |
925 | 936 | :chat-messages (do |
926 | 937 | (doseq [[chat-id {:keys [messages title]}] (:chats result)] |
927 | | - (doseq [message messages] |
928 | | - (let [new-chat-ctx (assoc chat-ctx :chat-id chat-id)] |
929 | | - (doseq [chat-content (message-content->chat-content (:role message) (:content message))] |
930 | | - (send-content! new-chat-ctx |
931 | | - (:role message) |
932 | | - chat-content)) |
933 | | - (when title |
934 | | - (send-content! new-chat-ctx :system (assoc-some |
935 | | - {:type :metadata} |
936 | | - :title title)))))) |
| 938 | + (let [new-chat-ctx (assoc chat-ctx :chat-id chat-id)] |
| 939 | + (send-chat-contents! messages new-chat-ctx) |
| 940 | + (when title |
| 941 | + (send-content! new-chat-ctx :system (assoc-some |
| 942 | + {:type :metadata} |
| 943 | + :title title))))) |
937 | 944 | (finish-chat-prompt! :idle chat-ctx)) |
938 | 945 | :new-chat-status (finish-chat-prompt! (:status result) chat-ctx) |
939 | | - :send-prompt (prompt-messages! [{:role "user" :content (:prompt result)}] (assoc chat-ctx :on-finished-side-effect on-finished-side-effect)) |
| 946 | + :send-prompt (prompt-messages! [{:role "user" |
| 947 | + :content (:prompt result)}] |
| 948 | + (assoc chat-ctx :on-finished-side-effect on-finished-side-effect)) |
940 | 949 | nil))) |
941 | 950 |
|
942 | 951 | (defn prompt |
|
995 | 1004 | :db* db* |
996 | 1005 | :metrics metrics |
997 | 1006 | :config config |
| 1007 | + :user-content-id (new-content-id) |
998 | 1008 | :messenger messenger} |
999 | 1009 | decision (message->decision message db config) |
1000 | 1010 | hook-outputs* (atom []) |
|
1014 | 1024 | user-messages)] |
1015 | 1025 | (swap! db* assoc-in [:chats chat-id :status] :running) |
1016 | 1026 | (send-content! chat-ctx :user {:type :text |
| 1027 | + :content-id (:user-content-id chat-ctx) |
1017 | 1028 | :text (str message "\n")}) |
1018 | 1029 | (case (:type decision) |
1019 | 1030 | :mcp-prompt (send-mcp-prompt! decision chat-ctx) |
|
1098 | 1109 | [{:keys [chat-id]} db* metrics] |
1099 | 1110 | (swap! db* update :chats dissoc chat-id) |
1100 | 1111 | (db/update-workspaces-cache! @db* metrics)) |
| 1112 | + |
| 1113 | +(defn rollback-chat |
| 1114 | + "Remove messages from chat in db until content-id matches. |
| 1115 | + Then notify to clear chat and then the kept messages." |
| 1116 | + [{:keys [chat-id content-id]} db* messenger] |
| 1117 | + (let [all-messages (get-in @db* [:chats chat-id :messages]) |
| 1118 | + new-messages (vec (take-while #(not= (:content-id %) content-id) all-messages))] |
| 1119 | + (swap! db* assoc-in [:chats chat-id :messages] new-messages) |
| 1120 | + (messenger/chat-cleared |
| 1121 | + messenger |
| 1122 | + {:chat-id chat-id |
| 1123 | + :messages true}) |
| 1124 | + (send-chat-contents! |
| 1125 | + new-messages |
| 1126 | + {:chat-id chat-id |
| 1127 | + :messenger messenger}) |
| 1128 | + {})) |
0 commit comments