FEATURE: Merge discourse-automation (#26432)

Automation (previously known as discourse-automation) is now a core plugin.
This commit is contained in:
Osama Sayegh
2024-04-03 18:20:43 +03:00
committed by GitHub
parent 2190c9b957
commit 3d4faf3272
314 changed files with 21182 additions and 10 deletions

View File

@ -0,0 +1,187 @@
# frozen_string_literal: true
require_relative "../discourse_automation_helper"
describe DiscourseAutomation::AdminAutomationsController do
fab!(:automation)
before { SiteSetting.discourse_automation_enabled = true }
describe "#show" do
context "when logged in as an admin" do
before { sign_in(Fabricate(:admin)) }
it "shows the automation" do
get "/admin/plugins/discourse-automation/automations/#{automation.id}.json"
expect(response.status).to eq(200)
expect(response.parsed_body["automation"]["id"]).to eq(automation.id)
end
end
context "when logged in as a regular user" do
before { sign_in(Fabricate(:user)) }
it "raises a 404" do
get "/admin/plugins/discourse-automation/automations/#{automation.id}.json"
expect(response.status).to eq(404)
end
end
end
describe "#update" do
context "when logged in as an admin" do
before { sign_in(Fabricate(:admin)) }
it "updates the automation" do
put "/admin/plugins/discourse-automation/automations/#{automation.id}.json",
params: {
automation: {
trigger: "another-trigger",
},
}
expect(response.status).to eq(200)
end
describe "invalid field’s component" do
it "errors" do
put "/admin/plugins/discourse-automation/automations/#{automation.id}.json",
params: {
automation: {
script: automation.script,
trigger: automation.trigger,
fields: [{ name: "foo", component: "bar" }],
},
}
expect(response.status).to eq(422)
end
end
context "with required field" do
before do
DiscourseAutomation::Scriptable.add("test_required") do
field :foo, component: :text, required: true
end
automation.update!(script: "test_required")
end
it "errors" do
put "/admin/plugins/discourse-automation/automations/#{automation.id}.json",
params: {
automation: {
script: automation.script,
trigger: automation.trigger,
fields: [
{ name: "foo", component: "text", target: "script", metadata: { value: nil } },
],
},
}
expect(response.status).to eq(422)
end
end
context "when changing trigger and script of an enabled automation" do
it "forces the automation to be disabled" do
expect(automation.enabled).to eq(true)
put "/admin/plugins/discourse-automation/automations/#{automation.id}.json",
params: {
automation: {
script: "bar",
trigger: "foo",
enabled: true,
},
}
expect(automation.reload.enabled).to eq(false)
end
end
context "when changing trigger of an enabled automation" do
it "forces the automation to be disabled" do
expect(automation.enabled).to eq(true)
put "/admin/plugins/discourse-automation/automations/#{automation.id}.json",
params: {
automation: {
script: automation.script,
trigger: "foo",
enabled: true,
},
}
expect(automation.reload.enabled).to eq(false)
end
end
context "when changing script of an enabled automation" do
it "disables the automation" do
expect(automation.enabled).to eq(true)
put "/admin/plugins/discourse-automation/automations/#{automation.id}.json",
params: {
automation: {
trigger: automation.trigger,
script: "foo",
enabled: true,
},
}
expect(automation.reload.enabled).to eq(false)
end
end
context "with invalid field’s metadata" do
it "errors" do
put "/admin/plugins/discourse-automation/automations/#{automation.id}.json",
params: {
automation: {
script: automation.script,
trigger: automation.trigger,
fields: [{ name: "sender", component: "users", metadata: { baz: 1 } }],
},
}
expect(response.status).to eq(422)
end
end
end
context "when logged in as a regular user" do
before { sign_in(Fabricate(:user)) }
it "raises a 404" do
put "/admin/plugins/discourse-automation/automations/#{automation.id}.json",
params: {
automation: {
trigger: "another-trigger",
},
}
expect(response.status).to eq(404)
end
end
end
describe "#destroy" do
fab!(:automation)
context "when logged in as an admin" do
before { sign_in(Fabricate(:admin)) }
it "destroys the automation" do
delete "/admin/plugins/discourse-automation/automations/#{automation.id}.json"
expect(DiscourseAutomation::Automation.find_by(id: automation.id)).to eq(nil)
end
end
context "when logged in as a regular user" do
before { sign_in(Fabricate(:user)) }
it "raises a 404" do
delete "/admin/plugins/discourse-automation/automations/#{automation.id}.json"
expect(response.status).to eq(404)
end
end
end
end

View File

@ -0,0 +1,32 @@
# frozen_string_literal: true
require_relative "../discourse_automation_helper"
describe DiscourseAutomation::AppendLastCheckedByController do
before { SiteSetting.discourse_automation_enabled = true }
describe "#post_checked" do
fab!(:post)
fab!(:topic) { post.topic }
it "updates the topic custom fields" do
freeze_time
admin = Fabricate(:admin)
sign_in(admin)
put "/append-last-checked-by/#{post.id}.json"
expect(response.status).to eq(200)
expect(topic.custom_fields[DiscourseAutomation::TOPIC_LAST_CHECKED_BY]).to eq(admin.username)
topic_last_checked_at =
Time.parse(topic.custom_fields[DiscourseAutomation::TOPIC_LAST_CHECKED_AT])
expect(topic_last_checked_at).to be_within_one_second_of(Time.zone.now)
end
it "returns error if user can not edit the post" do
sign_in(Fabricate(:user))
put "/append-last-checked-by/#{post.id}.json"
expect(response.status).to eq(403)
end
end
end

View File

@ -0,0 +1,103 @@
# frozen_string_literal: true
require_relative "../discourse_automation_helper"
describe DiscourseAutomation::AdminAutomationsController do
before { SiteSetting.discourse_automation_enabled = true }
describe "#trigger" do
fab!(:automation)
describe "access" do
context "when user is not logged in" do
before { sign_out }
it "raises a 404" do
post "/automations/#{automation.id}/trigger.json"
expect(response.status).to eq(404)
end
end
context "when user is logged in" do
context "when user is admin" do
before do
Jobs.run_immediately!
sign_in(Fabricate(:admin))
end
it "triggers the automation" do
list = capture_contexts { post "/automations/#{automation.id}/trigger.json" }
expect(list.length).to eq(1)
expect(list[0]["kind"]).to eq("api_call")
end
end
context "when user is moderator" do
before { sign_in(Fabricate(:moderator)) }
it "raises a 404" do
post "/automations/#{automation.id}/trigger.json"
expect(response.status).to eq(404)
end
end
context "when user is regular" do
before { sign_in(Fabricate(:user)) }
it "raises a 404" do
post "/automations/#{automation.id}/trigger.json"
expect(response.status).to eq(404)
end
end
end
context "when using a user api key" do
before { sign_out }
let(:admin) { Fabricate(:admin) }
let(:api_key) { Fabricate(:api_key, user: admin) }
it "works" do
post "/automations/#{automation.id}/trigger.json",
params: {
context: {
foo: :bar,
},
},
headers: {
HTTP_API_KEY: api_key.key,
}
expect(response.status).to eq(200)
expect(Jobs::DiscourseAutomationTrigger.jobs.size).to eq(1)
end
end
end
describe "params as context" do
fab!(:admin)
fab!(:automation) { Fabricate(:automation, trigger: "api_call") }
before do
Jobs.run_immediately!
sign_in(admin)
end
it "passes the params" do
list =
capture_contexts do
post "/automations/#{automation.id}/trigger.json", params: { foo: "1", bar: "2" }
end
expect(list.length).to eq(1)
first = list.first
expect(first["foo"]).to eq("1")
expect(first["bar"]).to eq("2")
expect(response.status).to eq(200)
end
end
end
end

View File

@ -0,0 +1,47 @@
# frozen_string_literal: true
require_relative "../discourse_automation_helper"
describe DiscourseAutomation::UserGlobalNoticesController do
fab!(:user_1) { Fabricate(:user) }
before { SiteSetting.discourse_automation_enabled = true }
describe "#destroy" do
let!(:notice_1) do
DiscourseAutomation::UserGlobalNotice.create!(
user_id: user_1.id,
notice: "foo",
identifier: "bar",
)
end
context "when user is not logged in" do
it "raises a 403" do
delete "/user-global-notices/#{notice_1.id}.json"
expect(response.status).to eq(403)
end
end
context "when user is owner of the notice" do
before { sign_in(user_1) }
it "destroys the notice" do
delete "/user-global-notices/#{notice_1.id}.json"
expect(DiscourseAutomation::UserGlobalNotice.count).to eq(0)
end
end
context "when user is not owner of the notice" do
before { sign_in(Fabricate(:user)) }
it "raises a 404" do
delete "/user-global-notices/#{notice_1.id}.json"
expect(response.status).to eq(404)
end
end
end
end