diff --git a/lib/ai_bot/artifact_update_strategies/diff.rb b/lib/ai_bot/artifact_update_strategies/diff.rb index 4a0ff28d2..b75f78bca 100644 --- a/lib/ai_bot/artifact_update_strategies/diff.rb +++ b/lib/ai_bot/artifact_update_strategies/diff.rb @@ -95,9 +95,9 @@ def extract_search_replace_blocks(content) blocks = [] remaining = content - pattern = /<<+\s*SEARCH\s*\n(.*?)\n=+\s*\n(.*?)\n>>+\s*REPLACE/m + pattern = /<<+\s*SEARCH\s*\n(.*?)\n==+\s*(\n(.*?))?\n>>+\s*REPLACE/m while remaining =~ pattern - blocks << { search: $1.strip, replace: $2.strip } + blocks << { search: $1.strip, replace: $3.to_s.strip } remaining = $' end diff --git a/spec/lib/modules/ai_bot/artifact_update_strategies/diff_spec.rb b/spec/lib/modules/ai_bot/artifact_update_strategies/diff_spec.rb index c2426ad43..689984cf7 100644 --- a/spec/lib/modules/ai_bot/artifact_update_strategies/diff_spec.rb +++ b/spec/lib/modules/ai_bot/artifact_update_strategies/diff_spec.rb @@ -108,6 +108,34 @@ expect(artifact.versions.last.css).to eq("body {\n color: red;\n}") end + it "can handle removal with blank blocks" do + original_css = <<~CSS + body { + color: red; + } + .button { + color: blue; + } + CSS + + artifact.update!(css: original_css) + + response = <<~RESPONSE + [CSS] + <<<<<<< SEARCH + body { + color: red; + } + ======= + >>>>>>> REPLACE + [/CSS] + RESPONSE + + DiscourseAi::Completions::Llm.with_prepared_responses([response]) { strategy.apply } + + expect(artifact.versions.last.css.strip).to eq(".button {\n color: blue;\n}") + end + it "tracks failed searches" do original_css = ".button { color: blue; }" artifact.update!(css: original_css)