mirror of
https://github.com/discourse/discourse-ai.git
synced 2025-07-30 01:43:27 +00:00
FIX: Persona editor keeps dirty data after persisting a single field (#1219)
This commit is contained in:
parent
371146cdfe
commit
1b05da704e
@ -32,8 +32,17 @@ export default class PersonaEditor extends Component {
|
|||||||
@tracked isSaving = false;
|
@tracked isSaving = false;
|
||||||
@tracked availableForcedTools = [];
|
@tracked availableForcedTools = [];
|
||||||
|
|
||||||
|
dirtyFormData = null;
|
||||||
|
|
||||||
@cached
|
@cached
|
||||||
get formData() {
|
get formData() {
|
||||||
|
// This is to recover a dirty state after persisting a single form field.
|
||||||
|
// It's meant to be consumed only once.
|
||||||
|
if (this.dirtyFormData) {
|
||||||
|
const data = this.dirtyFormData;
|
||||||
|
this.dirtyFormData = null;
|
||||||
|
return data;
|
||||||
|
} else {
|
||||||
const data = this.args.model.toPOJO();
|
const data = this.args.model.toPOJO();
|
||||||
|
|
||||||
if (data.tools) {
|
if (data.tools) {
|
||||||
@ -42,6 +51,7 @@ export default class PersonaEditor extends Component {
|
|||||||
|
|
||||||
return data;
|
return data;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
get chatPluginEnabled() {
|
get chatPluginEnabled() {
|
||||||
return this.siteSettings.chat_enabled;
|
return this.siteSettings.chat_enabled;
|
||||||
@ -144,15 +154,15 @@ export default class PersonaEditor extends Component {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@action
|
@action
|
||||||
async toggleEnabled(value, { set }) {
|
async toggleEnabled(dirtyData, value, { set }) {
|
||||||
set("enabled", value);
|
set("enabled", value);
|
||||||
await this.persistField("enabled", value);
|
await this.persistField(dirtyData, "enabled", value);
|
||||||
}
|
}
|
||||||
|
|
||||||
@action
|
@action
|
||||||
async togglePriority(value, { set }) {
|
async togglePriority(dirtyData, value, { set }) {
|
||||||
set("priority", value);
|
set("priority", value);
|
||||||
await this.persistField("priority", value, true);
|
await this.persistField(dirtyData, "priority", value, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
@action
|
@action
|
||||||
@ -172,7 +182,7 @@ export default class PersonaEditor extends Component {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@action
|
@action
|
||||||
async removeUpload(form, currentUploads, upload) {
|
async removeUpload(form, dirtyData, currentUploads, upload) {
|
||||||
const updatedUploads = currentUploads.filter(
|
const updatedUploads = currentUploads.filter(
|
||||||
(file) => file.id !== upload.id
|
(file) => file.id !== upload.id
|
||||||
);
|
);
|
||||||
@ -180,7 +190,7 @@ export default class PersonaEditor extends Component {
|
|||||||
form.set("rag_uploads", updatedUploads);
|
form.set("rag_uploads", updatedUploads);
|
||||||
|
|
||||||
if (!this.args.model.isNew) {
|
if (!this.args.model.isNew) {
|
||||||
await this.persistField("rag_uploads", updatedUploads);
|
await this.persistField(dirtyData, "rag_uploads", updatedUploads);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -232,14 +242,16 @@ export default class PersonaEditor extends Component {
|
|||||||
return updatedOptions;
|
return updatedOptions;
|
||||||
}
|
}
|
||||||
|
|
||||||
async persistField(field, newValue, sortPersonas) {
|
async persistField(dirtyData, field, newValue, sortPersonas) {
|
||||||
this.args.model.set(field, newValue);
|
|
||||||
|
|
||||||
if (!this.args.model.isNew) {
|
if (!this.args.model.isNew) {
|
||||||
|
const updatedDirtyData = Object.assign({}, dirtyData);
|
||||||
|
updatedDirtyData[field] = newValue;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const args = {};
|
const args = {};
|
||||||
args[field] = newValue;
|
args[field] = newValue;
|
||||||
|
|
||||||
|
this.dirtyFormData = updatedDirtyData;
|
||||||
await this.args.model.update(args);
|
await this.args.model.update(args);
|
||||||
if (sortPersonas) {
|
if (sortPersonas) {
|
||||||
this.#sortPersonas();
|
this.#sortPersonas();
|
||||||
@ -274,7 +286,7 @@ export default class PersonaEditor extends Component {
|
|||||||
<form.Field
|
<form.Field
|
||||||
@name="enabled"
|
@name="enabled"
|
||||||
@title={{i18n "discourse_ai.ai_persona.enabled"}}
|
@title={{i18n "discourse_ai.ai_persona.enabled"}}
|
||||||
@onSet={{this.toggleEnabled}}
|
@onSet={{fn this.toggleEnabled data}}
|
||||||
as |field|
|
as |field|
|
||||||
>
|
>
|
||||||
<field.Toggle />
|
<field.Toggle />
|
||||||
@ -283,7 +295,7 @@ export default class PersonaEditor extends Component {
|
|||||||
<form.Field
|
<form.Field
|
||||||
@name="priority"
|
@name="priority"
|
||||||
@title={{i18n "discourse_ai.ai_persona.priority"}}
|
@title={{i18n "discourse_ai.ai_persona.priority"}}
|
||||||
@onSet={{this.togglePriority}}
|
@onSet={{fn this.togglePriority data}}
|
||||||
@tooltip={{i18n "discourse_ai.ai_persona.priority_help"}}
|
@tooltip={{i18n "discourse_ai.ai_persona.priority_help"}}
|
||||||
as |field|
|
as |field|
|
||||||
>
|
>
|
||||||
@ -499,7 +511,7 @@ export default class PersonaEditor extends Component {
|
|||||||
@target={{data}}
|
@target={{data}}
|
||||||
@targetName="AiPersona"
|
@targetName="AiPersona"
|
||||||
@updateUploads={{fn this.updateUploads form}}
|
@updateUploads={{fn this.updateUploads form}}
|
||||||
@onRemove={{fn this.removeUpload form field.value}}
|
@onRemove={{fn this.removeUpload form data field.value}}
|
||||||
@allowImages={{@personas.resultSetMeta.settings.rag_images_enabled}}
|
@allowImages={{@personas.resultSetMeta.settings.rag_images_enabled}}
|
||||||
/>
|
/>
|
||||||
</field.Custom>
|
</field.Custom>
|
||||||
|
@ -71,6 +71,34 @@ RSpec.describe "Admin AI persona configuration", type: :system, js: true do
|
|||||||
expect(persona.name).not_to eq("Test Persona 1")
|
expect(persona.name).not_to eq("Test Persona 1")
|
||||||
end
|
end
|
||||||
|
|
||||||
|
it "enabling a persona doesn't reset other fields" do
|
||||||
|
persona = Fabricate(:ai_persona, enabled: false)
|
||||||
|
updated_name = "Update persona 1"
|
||||||
|
|
||||||
|
visit "/admin/plugins/discourse-ai/ai-personas/#{persona.id}/edit"
|
||||||
|
|
||||||
|
form.field("name").fill_in(updated_name)
|
||||||
|
form.field("enabled").toggle
|
||||||
|
|
||||||
|
try_until_success { expect(persona.reload.enabled).to eq(true) }
|
||||||
|
|
||||||
|
expect(form.field("name").value).to eq(updated_name)
|
||||||
|
end
|
||||||
|
|
||||||
|
it "toggling a persona's priority doesn't reset other fields" do
|
||||||
|
persona = Fabricate(:ai_persona, priority: false)
|
||||||
|
updated_name = "Update persona 1"
|
||||||
|
|
||||||
|
visit "/admin/plugins/discourse-ai/ai-personas/#{persona.id}/edit"
|
||||||
|
|
||||||
|
form.field("name").fill_in(updated_name)
|
||||||
|
form.field("priority").toggle
|
||||||
|
|
||||||
|
try_until_success { expect(persona.reload.priority).to eq(true) }
|
||||||
|
|
||||||
|
expect(form.field("name").value).to eq(updated_name)
|
||||||
|
end
|
||||||
|
|
||||||
it "can navigate the AI plugin with breadcrumbs" do
|
it "can navigate the AI plugin with breadcrumbs" do
|
||||||
visit "/admin/plugins/discourse-ai/ai-personas"
|
visit "/admin/plugins/discourse-ai/ai-personas"
|
||||||
expect(page).to have_css(".d-breadcrumbs")
|
expect(page).to have_css(".d-breadcrumbs")
|
||||||
|
Loading…
x
Reference in New Issue
Block a user