This commit is contained in:
narawat lamaiin
2024-07-15 21:19:55 +07:00
parent 180bd16018
commit fdc50d1b90
9 changed files with 2396 additions and 591 deletions

View File

@@ -1,7 +1,6 @@
module util
export clearhistory, addNewMessage, formatLLMtext, iterativeprompting,
formatLLMtext_llama3instruct, formatLLMtext_phi3instruct
export clearhistory, addNewMessage, chatHistoryToString
using UUIDs, Dates, DataStructures, HTTP, MQTTClient, JSON3
using GeneralUtils
@@ -114,222 +113,242 @@ function addNewMessage(a::T1, name::String, text::T2;
end
""" Convert a single chat dictionary into LLM model instruct format.
# Llama 3 instruct format example
<|system|>
You are a helpful AI assistant.<|end|>
<|user|>
I am going to Paris, what should I see?<|end|>
<|assistant|>
Paris, the capital of France, is known for its stunning architecture, art museums."<|end|>
<|user|>
What is so great about #1?<|end|>
<|assistant|>
# Arguments
- `name::T`
message owner name e.f. "system", "user" or "assistant"
- `text::T`
# Return
- `formattedtext::String`
text formatted to model format
# Example
```jldoctest
julia> using Revise
julia> using YiemAgent
julia> d = Dict(:name=> "system",:text=> "You are a helpful, respectful and honest assistant.",)
julia> formattedtext = YiemAgent.formatLLMtext_phi3instruct(d[:name], d[:text])
```
Signature
"""
function formatLLMtext_phi3instruct(name::T, text::T) where {T<:AbstractString}
formattedtext =
"""
<|$name|>
$text<|end|>\n
"""
return formattedtext
end
""" Convert a single chat dictionary into LLM model instruct format.
# Llama 3 instruct format example
<|begin_of_text|>
<|start_header_id|>system<|end_header_id|>
You are a helpful assistant.
<|eot_id|>
<|start_header_id|>user<|end_header_id|>
Get me an icecream.
<|eot_id|>
<|start_header_id|>assistant<|end_header_id|>
Go buy it yourself at 7-11.
<|eot_id|>
# Arguments
- `name::T`
message owner name e.f. "system", "user" or "assistant"
- `text::T`
# Return
- `formattedtext::String`
text formatted to model format
# Example
```jldoctest
julia> using Revise
julia> using YiemAgent
julia> d = Dict(:name=> "system",:text=> "You are a helpful, respectful and honest assistant.",)
julia> formattedtext = YiemAgent.formatLLMtext_llama3instruct(d[:name], d[:text])
"<|begin_of_text|>\n <|start_header_id|>system<|end_header_id|>\n You are a helpful, respectful and honest assistant.\n <|eot_id|>\n"
```
Signature
"""
function formatLLMtext_llama3instruct(name::T, text::T) where {T<:AbstractString}
formattedtext =
if name == "system"
"""
<|begin_of_text|>
<|start_header_id|>$name<|end_header_id|>
$text
<|eot_id|>
"""
else
"""
<|start_header_id|>$name<|end_header_id|>
$text
<|eot_id|>
"""
function chatHistoryToString(a)
chatHistoryStr = ""
for i in a.chathistory
name = i[:name]
text = i[:text]
chatHistoryStr *= "$name> $text"
end
return formattedtext
return chatHistoryStr
end
""" Convert a chat messages in vector of dictionary into LLM model instruct format.
# Arguments
- `messages::Vector{Dict{Symbol, T}}`
message owner name e.f. "system", "user" or "assistant"
- `formatname::T`
format name to be used
# Return
- `formattedtext::String`
text formatted to model format
# Example
```jldoctest
julia> using Revise
julia> using YiemAgent
julia> chatmessage = [
Dict(:name=> "system",:text=> "You are a helpful, respectful and honest assistant.",),
Dict(:name=> "user",:text=> "list me all planets in our solar system.",),
Dict(:name=> "assistant",:text=> "I'm sorry. I don't know. You tell me.",),
]
julia> formattedtext = YiemAgent.formatLLMtext(chatmessage, "llama3instruct")
"<|begin_of_text|>\n <|start_header_id|>system<|end_header_id|>\n You are a helpful, respectful and honest assistant.\n <|eot_id|>\n <|start_header_id|>user<|end_header_id|>\n list me all planets in our solar system.\n <|eot_id|>\n <|start_header_id|>assistant<|end_header_id|>\n I'm sorry. I don't know. You tell me.\n <|eot_id|>\n"
```
# """ Convert a single chat dictionary into LLM model instruct format.
# # Llama 3 instruct format example
# <|system|>
# You are a helpful AI assistant.<|end|>
# <|user|>
# I am going to Paris, what should I see?<|end|>
# <|assistant|>
# Paris, the capital of France, is known for its stunning architecture, art museums."<|end|>
# <|user|>
# What is so great about #1?<|end|>
# <|assistant|>
# # Arguments
# - `name::T`
# message owner name e.f. "system", "user" or "assistant"
# - `text::T`
# # Return
# - `formattedtext::String`
# text formatted to model format
# # Example
# ```jldoctest
# julia> using Revise
# julia> using YiemAgent
# julia> d = Dict(:name=> "system",:text=> "You are a helpful, respectful and honest assistant.",)
# julia> formattedtext = YiemAgent.formatLLMtext_phi3instruct(d[:name], d[:text])
# ```
# Signature
"""
function formatLLMtext(messages::Vector{Dict{Symbol, T}},
formatname::String="llama3instruct") where {T<:Any}
f = if formatname == "llama3instruct"
formatLLMtext_llama3instruct
elseif formatname == "mistral"
# not define yet
elseif formatname == "phi3instruct"
formatLLMtext_phi3instruct
else
error("$formatname template not define yet")
end
# """
# function formatLLMtext_phi3instruct(name::T, text::T) where {T<:AbstractString}
# formattedtext =
# """
# <|$name|>
# $text<|end|>\n
# """
str = ""
for t in messages
str *= f(t[:name], t[:text])
end
# add <|assistant|> so that the model don't generate it and I don't need to clean it up later
if formatname == "phi3instruct"
str *= "<|assistant|>\n"
end
return str
end
# return formattedtext
# end
"""
# """ Convert a single chat dictionary into LLM model instruct format.
Arguments\n
-----
# # Llama 3 instruct format example
# <|begin_of_text|>
# <|start_header_id|>system<|end_header_id|>
# You are a helpful assistant.
# <|eot_id|>
# <|start_header_id|>user<|end_header_id|>
# Get me an icecream.
# <|eot_id|>
# <|start_header_id|>assistant<|end_header_id|>
# Go buy it yourself at 7-11.
# <|eot_id|>
# # Arguments
# - `name::T`
# message owner name e.f. "system", "user" or "assistant"
# - `text::T`
# # Return
# - `formattedtext::String`
# text formatted to model format
# # Example
# ```jldoctest
# julia> using Revise
# julia> using YiemAgent
# julia> d = Dict(:name=> "system",:text=> "You are a helpful, respectful and honest assistant.",)
# julia> formattedtext = YiemAgent.formatLLMtext_llama3instruct(d[:name], d[:text])
# "<|begin_of_text|>\n <|start_header_id|>system<|end_header_id|>\n You are a helpful, respectful and honest assistant.\n <|eot_id|>\n"
# ```
# Signature
# """
# function formatLLMtext_llama3instruct(name::T, text::T) where {T<:AbstractString}
# formattedtext =
# if name == "system"
# """
# <|begin_of_text|>
# <|start_header_id|>$name<|end_header_id|>
# $text
# <|eot_id|>
# """
# else
# """
# <|start_header_id|>$name<|end_header_id|>
# $text
# <|eot_id|>
# """
# end
# return formattedtext
# end
# """ Convert a chat messages in vector of dictionary into LLM model instruct format.
# # Arguments
# - `messages::Vector{Dict{Symbol, T}}`
# message owner name e.f. "system", "user" or "assistant"
# - `formatname::T`
# format name to be used
# # Return
# - `formattedtext::String`
# text formatted to model format
# # Example
# ```jldoctest
# julia> using Revise
# julia> using YiemAgent
# julia> chatmessage = [
# Dict(:name=> "system",:text=> "You are a helpful, respectful and honest assistant.",),
# Dict(:name=> "user",:text=> "list me all planets in our solar system.",),
# Dict(:name=> "assistant",:text=> "I'm sorry. I don't know. You tell me.",),
# ]
# julia> formattedtext = YiemAgent.formatLLMtext(chatmessage, "llama3instruct")
# "<|begin_of_text|>\n <|start_header_id|>system<|end_header_id|>\n You are a helpful, respectful and honest assistant.\n <|eot_id|>\n <|start_header_id|>user<|end_header_id|>\n list me all planets in our solar system.\n <|eot_id|>\n <|start_header_id|>assistant<|end_header_id|>\n I'm sorry. I don't know. You tell me.\n <|eot_id|>\n"
# ```
# # Signature
# """
# function formatLLMtext(messages::Vector{Dict{Symbol, T}},
# formatname::String="llama3instruct") where {T<:Any}
# f = if formatname == "llama3instruct"
# formatLLMtext_llama3instruct
# elseif formatname == "mistral"
# # not define yet
# elseif formatname == "phi3instruct"
# formatLLMtext_phi3instruct
# else
# error("$formatname template not define yet")
# end
# str = ""
# for t in messages
# str *= f(t[:name], t[:text])
# end
# # add <|assistant|> so that the model don't generate it and I don't need to clean it up later
# if formatname == "phi3instruct"
# str *= "<|assistant|>\n"
# end
# return str
# end
# """
# Arguments\n
# -----
Return\n
-----
# Return\n
# -----
Example\n
-----
```jldoctest
julia>
```
# Example\n
# -----
# ```jldoctest
# julia>
# ```
TODO\n
-----
[] update docstring
[PENDING] implement the function
# TODO\n
# -----
# [] update docstring
# [PENDING] implement the function
Signature\n
-----
"""
function iterativeprompting(a::T, prompt::String, verification::Function) where {T<:agent}
msgMeta = GeneralUtils.generate_msgMeta(
a.config[:externalService][:text2textinstruct],
senderName= "iterativeprompting",
senderId= a.id,
receiverName= "text2textinstruct",
)
# Signature\n
# -----
# """
# function iterativeprompting(a::T, prompt::String, verification::Function) where {T<:agent}
# msgMeta = GeneralUtils.generate_msgMeta(
# a.config[:externalService][:text2textinstruct],
# senderName= "iterativeprompting",
# senderId= a.id,
# receiverName= "text2textinstruct",
# )
outgoingMsg = Dict(
:msgMeta=> msgMeta,
:payload=> Dict(
:text=> prompt,
)
)
# outgoingMsg = Dict(
# :msgMeta=> msgMeta,
# :payload=> Dict(
# :text=> prompt,
# )
# )
success = nothing
result = nothing
critique = ""
# success = nothing
# result = nothing
# critique = ""
# iteration loop
while true
# send prompt to LLM
response = GeneralUtils.sendReceiveMqttMsg(outgoingMsg)
error("--> iterativeprompting")
# check for correctness and get feedback
success, _critique = verification(response)
# # iteration loop
# while true
# # send prompt to LLM
# response = GeneralUtils.sendReceiveMqttMsg(outgoingMsg)
# error("--> iterativeprompting")
# # check for correctness and get feedback
# success, _critique = verification(response)
if success
result = response
break
else
# add critique to prompt
critique *= _critique * "\n"
replace!(prompt, "Critique: ..." => "Critique: $critique")
end
end
# if success
# result = response
# break
# else
# # add critique to prompt
# critique *= _critique * "\n"
# replace!(prompt, "Critique: ..." => "Critique: $critique")
# end
# end
return (success=success, result=result)
end
# return (success=success, result=result)
# end