work in progress
This commit is contained in:
parent
fd7ccfd0ab
commit
30ebe562ea
|
@ -190,7 +190,7 @@ module DiscourseAi
|
||||||
update_blk.call("", cancel, build_placeholder(tool.summary, ""))
|
update_blk.call("", cancel, build_placeholder(tool.summary, ""))
|
||||||
|
|
||||||
result =
|
result =
|
||||||
tool.invoke do |progress|
|
tool.invoke(**tool.parameters) do |progress|
|
||||||
placeholder = build_placeholder(tool.summary, progress)
|
placeholder = build_placeholder(tool.summary, progress)
|
||||||
update_blk.call("", cancel, placeholder)
|
update_blk.call("", cancel, placeholder)
|
||||||
end
|
end
|
||||||
|
|
|
@ -243,14 +243,16 @@ module DiscourseAi
|
||||||
arguments[name.to_sym] = value if value
|
arguments[name.to_sym] = value if value
|
||||||
end
|
end
|
||||||
|
|
||||||
tool_klass.new(
|
instance = tool_klass.new(
|
||||||
arguments,
|
|
||||||
tool_call_id: function_id || function_name,
|
tool_call_id: function_id || function_name,
|
||||||
persona_options: options[tool_klass].to_h,
|
persona_options: options[tool_klass].to_h,
|
||||||
bot_user: bot_user,
|
bot_user: bot_user,
|
||||||
llm: llm,
|
llm: llm,
|
||||||
context: context,
|
context: context,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
instance.parameters = arguments
|
||||||
|
instance
|
||||||
end
|
end
|
||||||
|
|
||||||
def strip_quotes(value)
|
def strip_quotes(value)
|
||||||
|
|
|
@ -35,7 +35,8 @@ module DiscourseAi
|
||||||
super(*args, **kwargs)
|
super(*args, **kwargs)
|
||||||
end
|
end
|
||||||
|
|
||||||
def invoke
|
def invoke(**parameters)
|
||||||
|
@parameters = parameters
|
||||||
result = runner.invoke
|
result = runner.invoke
|
||||||
if runner.custom_raw
|
if runner.custom_raw
|
||||||
self.custom_raw = runner.custom_raw
|
self.custom_raw = runner.custom_raw
|
||||||
|
|
|
@ -4,6 +4,8 @@ module DiscourseAi
|
||||||
module AiBot
|
module AiBot
|
||||||
module Tools
|
module Tools
|
||||||
class DallE < Tool
|
class DallE < Tool
|
||||||
|
attr_reader :prompts, :aspect_ratio
|
||||||
|
|
||||||
def self.signature
|
def self.signature
|
||||||
{
|
{
|
||||||
name: name,
|
name: name,
|
||||||
|
@ -32,19 +34,14 @@ module DiscourseAi
|
||||||
"dall_e"
|
"dall_e"
|
||||||
end
|
end
|
||||||
|
|
||||||
def prompts
|
|
||||||
parameters[:prompts]
|
|
||||||
end
|
|
||||||
|
|
||||||
def aspect_ratio
|
|
||||||
parameters[:aspect_ratio]
|
|
||||||
end
|
|
||||||
|
|
||||||
def chain_next_response?
|
def chain_next_response?
|
||||||
false
|
false
|
||||||
end
|
end
|
||||||
|
|
||||||
def invoke
|
def invoke(prompts:, aspect_ratio: "square")
|
||||||
|
@prompts = prompts
|
||||||
|
@aspect_ratio = aspect_ratio
|
||||||
|
|
||||||
# max 4 prompts
|
# max 4 prompts
|
||||||
max_prompts = prompts.take(4)
|
max_prompts = prompts.take(4)
|
||||||
progress = prompts.first
|
progress = prompts.first
|
||||||
|
|
|
@ -4,6 +4,8 @@ module DiscourseAi
|
||||||
module AiBot
|
module AiBot
|
||||||
module Tools
|
module Tools
|
||||||
class Google < Tool
|
class Google < Tool
|
||||||
|
attr_reader :query
|
||||||
|
|
||||||
def self.signature
|
def self.signature
|
||||||
{
|
{
|
||||||
name: name,
|
name: name,
|
||||||
|
@ -27,12 +29,9 @@ module DiscourseAi
|
||||||
[option(:base_query, type: :string)]
|
[option(:base_query, type: :string)]
|
||||||
end
|
end
|
||||||
|
|
||||||
def query
|
def invoke(query:)
|
||||||
parameters[:query].to_s.strip
|
query = query.to_s.strip
|
||||||
end
|
@query = query
|
||||||
|
|
||||||
def invoke
|
|
||||||
query = self.query
|
|
||||||
|
|
||||||
yield(query)
|
yield(query)
|
||||||
|
|
||||||
|
|
|
@ -4,6 +4,8 @@ module DiscourseAi
|
||||||
module AiBot
|
module AiBot
|
||||||
module Tools
|
module Tools
|
||||||
class Time < Tool
|
class Time < Tool
|
||||||
|
attr_reader :timezone
|
||||||
|
|
||||||
def self.signature
|
def self.signature
|
||||||
{
|
{
|
||||||
name: name,
|
name: name,
|
||||||
|
@ -23,11 +25,8 @@ module DiscourseAi
|
||||||
"time"
|
"time"
|
||||||
end
|
end
|
||||||
|
|
||||||
def timezone
|
def invoke(timezone:)
|
||||||
parameters[:timezone].to_s
|
@timezone = timezone
|
||||||
end
|
|
||||||
|
|
||||||
def invoke
|
|
||||||
time =
|
time =
|
||||||
begin
|
begin
|
||||||
::Time.now.in_time_zone(timezone)
|
::Time.now.in_time_zone(timezone)
|
||||||
|
@ -37,7 +36,6 @@ module DiscourseAi
|
||||||
time = ::Time.now if !time
|
time = ::Time.now if !time
|
||||||
|
|
||||||
@last_time = time.to_s
|
@last_time = time.to_s
|
||||||
|
|
||||||
{ args: { timezone: timezone }, time: time.to_s }
|
{ args: { timezone: timezone }, time: time.to_s }
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -40,18 +40,16 @@ module DiscourseAi
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
attr_accessor :custom_raw
|
attr_accessor :custom_raw, :parameters
|
||||||
attr_reader :tool_call_id, :persona_options, :bot_user, :llm, :context, :parameters
|
attr_reader :tool_call_id, :persona_options, :bot_user, :llm, :context
|
||||||
|
|
||||||
def initialize(
|
def initialize(
|
||||||
parameters,
|
|
||||||
tool_call_id: "",
|
tool_call_id: "",
|
||||||
persona_options: {},
|
persona_options: {},
|
||||||
bot_user:,
|
bot_user:,
|
||||||
llm:,
|
llm:,
|
||||||
context: {}
|
context: {}
|
||||||
)
|
)
|
||||||
@parameters = parameters
|
|
||||||
@tool_call_id = tool_call_id
|
@tool_call_id = tool_call_id
|
||||||
@persona_options = persona_options
|
@persona_options = persona_options
|
||||||
@bot_user = bot_user
|
@bot_user = bot_user
|
||||||
|
|
|
@ -4,6 +4,8 @@ module DiscourseAi
|
||||||
module AiBot
|
module AiBot
|
||||||
module Tools
|
module Tools
|
||||||
class WebBrowser < Tool
|
class WebBrowser < Tool
|
||||||
|
attr_reader :url
|
||||||
|
|
||||||
def self.signature
|
def self.signature
|
||||||
{
|
{
|
||||||
name: name,
|
name: name,
|
||||||
|
@ -24,15 +26,9 @@ module DiscourseAi
|
||||||
"web_browser"
|
"web_browser"
|
||||||
end
|
end
|
||||||
|
|
||||||
def url
|
def invoke(url:)
|
||||||
return @url if defined?(@url)
|
url = "https://#{url}" if !url.start_with?("http")
|
||||||
@url = parameters[:url]
|
@url = url
|
||||||
@url = "https://#{@url}" if !@url.start_with?("http")
|
|
||||||
|
|
||||||
@url
|
|
||||||
end
|
|
||||||
|
|
||||||
def invoke
|
|
||||||
send_http_request(url, follow_redirects: true) do |response|
|
send_http_request(url, follow_redirects: true) do |response|
|
||||||
if response.code == "200"
|
if response.code == "200"
|
||||||
html = read_response_body(response)
|
html = read_response_body(response)
|
||||||
|
|
|
@ -5,7 +5,7 @@ RSpec.describe DiscourseAi::AiBot::Tools::Google do
|
||||||
let(:bot_user) { DiscourseAi::AiBot::EntryPoint.find_user_from_model(llm_model.name) }
|
let(:bot_user) { DiscourseAi::AiBot::EntryPoint.find_user_from_model(llm_model.name) }
|
||||||
let(:llm) { DiscourseAi::Completions::Llm.proxy("custom:#{llm_model.id}") }
|
let(:llm) { DiscourseAi::Completions::Llm.proxy("custom:#{llm_model.id}") }
|
||||||
let(:progress_blk) { Proc.new {} }
|
let(:progress_blk) { Proc.new {} }
|
||||||
let(:search) { described_class.new({ query: "some search term" }, bot_user: bot_user, llm: llm) }
|
let(:search) { described_class.new(bot_user: bot_user, llm: llm) }
|
||||||
|
|
||||||
before do
|
before do
|
||||||
SiteSetting.ai_bot_enabled = true
|
SiteSetting.ai_bot_enabled = true
|
||||||
|
@ -22,7 +22,7 @@ RSpec.describe DiscourseAi::AiBot::Tools::Google do
|
||||||
"https://www.googleapis.com/customsearch/v1?cx=cx&key=abc&num=10&q=some%20search%20term",
|
"https://www.googleapis.com/customsearch/v1?cx=cx&key=abc&num=10&q=some%20search%20term",
|
||||||
).to_return(status: 200, body: json_text, headers: {})
|
).to_return(status: 200, body: json_text, headers: {})
|
||||||
|
|
||||||
info = search.invoke(&progress_blk).to_json
|
info = search.invoke(query: "some search term", &progress_blk).to_json
|
||||||
|
|
||||||
expect(search.results_count).to eq(0)
|
expect(search.results_count).to eq(0)
|
||||||
expect(info).to_not include("oops")
|
expect(info).to_not include("oops")
|
||||||
|
@ -33,7 +33,6 @@ RSpec.describe DiscourseAi::AiBot::Tools::Google do
|
||||||
|
|
||||||
search =
|
search =
|
||||||
described_class.new(
|
described_class.new(
|
||||||
{ query: "some search term" },
|
|
||||||
bot_user: bot_user,
|
bot_user: bot_user,
|
||||||
llm: llm,
|
llm: llm,
|
||||||
persona_options: {
|
persona_options: {
|
||||||
|
@ -48,7 +47,7 @@ RSpec.describe DiscourseAi::AiBot::Tools::Google do
|
||||||
"https://www.googleapis.com/customsearch/v1?cx=cx&key=abc&num=10&q=site:discourse.org%20some%20search%20term",
|
"https://www.googleapis.com/customsearch/v1?cx=cx&key=abc&num=10&q=site:discourse.org%20some%20search%20term",
|
||||||
).to_return(status: 200, body: json_text, headers: {})
|
).to_return(status: 200, body: json_text, headers: {})
|
||||||
|
|
||||||
search.invoke(&progress_blk)
|
search.invoke(query: "some search term", &progress_blk)
|
||||||
end
|
end
|
||||||
|
|
||||||
it "can generate correct info" do
|
it "can generate correct info" do
|
||||||
|
@ -80,7 +79,7 @@ RSpec.describe DiscourseAi::AiBot::Tools::Google do
|
||||||
"https://www.googleapis.com/customsearch/v1?cx=cx&key=abc&num=10&q=some%20search%20term",
|
"https://www.googleapis.com/customsearch/v1?cx=cx&key=abc&num=10&q=some%20search%20term",
|
||||||
).to_return(status: 200, body: json_text, headers: {})
|
).to_return(status: 200, body: json_text, headers: {})
|
||||||
|
|
||||||
info = search.invoke(&progress_blk).to_json
|
info = search.invoke(query: "some search term", &progress_blk).to_json
|
||||||
|
|
||||||
expect(search.results_count).to eq(2)
|
expect(search.results_count).to eq(2)
|
||||||
expect(info).to include("title1")
|
expect(info).to include("title1")
|
||||||
|
|
|
@ -19,8 +19,8 @@ RSpec.describe DiscourseAi::AiBot::Tools::WebBrowser do
|
||||||
"<html><head><title>Test</title></head><body><p>This is a simplified version of the webpage content.</p></body></html>",
|
"<html><head><title>Test</title></head><body><p>This is a simplified version of the webpage content.</p></body></html>",
|
||||||
)
|
)
|
||||||
|
|
||||||
tool = described_class.new({ url: url }, bot_user: bot_user, llm: llm)
|
tool = described_class.new(bot_user: bot_user, llm: llm)
|
||||||
result = tool.invoke
|
result = tool.invoke(url: url)
|
||||||
|
|
||||||
expect(result).to have_key(:text)
|
expect(result).to have_key(:text)
|
||||||
expect(result[:text]).to eq(processed_text)
|
expect(result[:text]).to eq(processed_text)
|
||||||
|
@ -33,8 +33,8 @@ RSpec.describe DiscourseAi::AiBot::Tools::WebBrowser do
|
||||||
# Simulating a failed request
|
# Simulating a failed request
|
||||||
stub_request(:get, url).to_return(status: [500, "Internal Server Error"])
|
stub_request(:get, url).to_return(status: [500, "Internal Server Error"])
|
||||||
|
|
||||||
tool = described_class.new({ url: url }, bot_user: bot_user, llm: llm)
|
tool = described_class.new(bot_user: bot_user, llm: llm)
|
||||||
result = tool.invoke
|
result = tool.invoke(url: url)
|
||||||
|
|
||||||
expect(result).to have_key(:error)
|
expect(result).to have_key(:error)
|
||||||
expect(result[:error]).to include("Failed to retrieve the web page")
|
expect(result[:error]).to include("Failed to retrieve the web page")
|
||||||
|
@ -48,8 +48,8 @@ RSpec.describe DiscourseAi::AiBot::Tools::WebBrowser do
|
||||||
simple_html = "<html><body><p>Simple content.</p></body></html>"
|
simple_html = "<html><body><p>Simple content.</p></body></html>"
|
||||||
stub_request(:get, url).to_return(status: 200, body: simple_html)
|
stub_request(:get, url).to_return(status: 200, body: simple_html)
|
||||||
|
|
||||||
tool = described_class.new({ url: url }, bot_user: bot_user, llm: llm)
|
tool = described_class.new(bot_user: bot_user, llm: llm)
|
||||||
result = tool.invoke
|
result = tool.invoke(url: url)
|
||||||
|
|
||||||
expect(result[:text]).to eq("Simple content.")
|
expect(result[:text]).to eq("Simple content.")
|
||||||
end
|
end
|
||||||
|
@ -59,8 +59,8 @@ RSpec.describe DiscourseAi::AiBot::Tools::WebBrowser do
|
||||||
"<html><head><script>console.log('Ignore me')</script></head><body><style>body { background-color: #000; }</style><p>Only relevant content here.</p></body></html>"
|
"<html><head><script>console.log('Ignore me')</script></head><body><style>body { background-color: #000; }</style><p>Only relevant content here.</p></body></html>"
|
||||||
stub_request(:get, url).to_return(status: 200, body: complex_html)
|
stub_request(:get, url).to_return(status: 200, body: complex_html)
|
||||||
|
|
||||||
tool = described_class.new({ url: url }, bot_user: bot_user, llm: llm)
|
tool = described_class.new(bot_user: bot_user, llm: llm)
|
||||||
result = tool.invoke
|
result = tool.invoke(url: url)
|
||||||
|
|
||||||
expect(result[:text]).to eq("Only relevant content here.")
|
expect(result[:text]).to eq("Only relevant content here.")
|
||||||
end
|
end
|
||||||
|
@ -70,8 +70,8 @@ RSpec.describe DiscourseAi::AiBot::Tools::WebBrowser do
|
||||||
"<html><body><div><section><p>Nested paragraph 1.</p></section><section><p>Nested paragraph 2.</p></section></div></body></html>"
|
"<html><body><div><section><p>Nested paragraph 1.</p></section><section><p>Nested paragraph 2.</p></section></div></body></html>"
|
||||||
stub_request(:get, url).to_return(status: 200, body: nested_html)
|
stub_request(:get, url).to_return(status: 200, body: nested_html)
|
||||||
|
|
||||||
tool = described_class.new({ url: url }, bot_user: bot_user, llm: llm)
|
tool = described_class.new(bot_user: bot_user, llm: llm)
|
||||||
result = tool.invoke
|
result = tool.invoke(url: url)
|
||||||
|
|
||||||
expect(result[:text]).to eq("Nested paragraph 1. Nested paragraph 2.")
|
expect(result[:text]).to eq("Nested paragraph 1. Nested paragraph 2.")
|
||||||
end
|
end
|
||||||
|
@ -86,8 +86,8 @@ RSpec.describe DiscourseAi::AiBot::Tools::WebBrowser do
|
||||||
stub_request(:get, initial_url).to_return(status: 302, headers: { "Location" => final_url })
|
stub_request(:get, initial_url).to_return(status: 302, headers: { "Location" => final_url })
|
||||||
stub_request(:get, final_url).to_return(status: 200, body: redirect_html)
|
stub_request(:get, final_url).to_return(status: 200, body: redirect_html)
|
||||||
|
|
||||||
tool = described_class.new({ url: initial_url }, bot_user: bot_user, llm: llm)
|
tool = described_class.new(bot_user: bot_user, llm: llm)
|
||||||
result = tool.invoke
|
result = tool.invoke(url: initial_url)
|
||||||
|
|
||||||
expect(result[:url]).to eq(final_url)
|
expect(result[:url]).to eq(final_url)
|
||||||
expect(result[:text]).to eq("Redirected content.")
|
expect(result[:text]).to eq("Redirected content.")
|
||||||
|
|
Loading…
Reference in New Issue