# Objective Closes EP-9 - Describe the objective or issue this PR addresses. - If you're fixing a specific issue, use "Fixes #X" for each issue as [described in the GitHub docs](https://docs.github.com/en/issues/tracking-your-work-with-issues/using-issues/linking-a-pull-request-to-an-issue#linking-a-pull-request-to-an-issue-using-a-keyword). ## Solution - Describe the solution used to achieve the objective above. ## Testing - Did you test these changes? If so, how? - Are there any parts that need more testing? - How can other people (reviewers) test your changes? Is there anything specific they need to know? - If relevant, what platforms did you test these changes on, and are there any important ones you can't test? ## Self-Review Checklist: - [x] I've reviewed my own diff for quality, security, and reliability - [x] Unsafe blocks (if any) have justifying comments - [x] The content adheres to Zed's UI standards ([UX/UI](https://github.com/zed-industries/zed/blob/main/CONTRIBUTING.md#uiux-checklist) and [icon](https://github.com/zed-industries/zed/blob/main/crates/icons/README.md) guidelines) - [x] Tests cover the new/changed behavior - [x] Performance impact has been considered and is acceptable ## Showcase > This section is optional. If this PR does not include a visual change or does not add a new user-facing feature, you can delete this section. - Help others understand the result of this PR by showcasing your awesome work! - If this PR includes a visual change, consider adding a screenshot, GIF, or video - A before/after comparison is very useful for changes to existing features! While a showcase should aim to be brief and digestible, you can use a toggleable section to save space on longer showcases: <details> <summary>Click to view showcase</summary> My super cool demos here </details> --- Release Notes: - N/A or Added/Fixed/Improved ... --------- Co-authored-by: Oleksiy Syvokon <oleksiy.syvokon@gmail.com> Co-authored-by: Oleksiy Syvokon <oleksiy@zed.dev>
101 lines
3.3 KiB
Rust
101 lines
3.3 KiB
Rust
use crate::{
|
|
PredictionProvider,
|
|
example::{ActualCursor, Example},
|
|
format_prompt::{TeacherJumpsPrompt, TeacherPrompt},
|
|
repair,
|
|
};
|
|
use anyhow::{Context as _, Result};
|
|
use zeta_prompt::{
|
|
ZetaFormat, parse_zeta2_model_output, parse_zeta2_model_output_as_patch, parsed_output_to_patch,
|
|
};
|
|
|
|
pub fn run_parse_output(example: &mut Example) -> Result<()> {
|
|
example
|
|
.prompt_inputs
|
|
.as_ref()
|
|
.context("prompt_inputs required")?;
|
|
|
|
let to_parse: Vec<_> = example
|
|
.predictions
|
|
.iter()
|
|
.enumerate()
|
|
.filter(|(_, p)| !p.actual_output.is_empty())
|
|
.map(|(ix, p)| (ix, p.actual_output.clone(), p.provider))
|
|
.collect();
|
|
|
|
for (ix, actual_output, provider) in to_parse {
|
|
let (actual_patch, actual_cursor) =
|
|
parse_prediction_output(example, &actual_output, provider)?;
|
|
example.predictions[ix].actual_patch = Some(actual_patch);
|
|
example.predictions[ix].actual_cursor = actual_cursor;
|
|
}
|
|
|
|
Ok(())
|
|
}
|
|
|
|
pub fn parse_prediction_output(
|
|
example: &Example,
|
|
actual_output: &str,
|
|
provider: PredictionProvider,
|
|
) -> Result<(String, Option<ActualCursor>)> {
|
|
match provider {
|
|
PredictionProvider::Teacher(_, _) | PredictionProvider::TeacherNonBatching(_, _) => {
|
|
TeacherPrompt::parse(example, actual_output)
|
|
}
|
|
PredictionProvider::TeacherJumps(_) | PredictionProvider::TeacherJumpsNonBatching(_) => {
|
|
TeacherJumpsPrompt::parse(example, actual_output)
|
|
}
|
|
PredictionProvider::Zeta2(version) => parse_zeta2_output(example, actual_output, version),
|
|
PredictionProvider::Repair => repair::parse(example, actual_output),
|
|
_ => anyhow::bail!(
|
|
"parse-output only supports Teacher and Zeta2 providers, got {:?}",
|
|
provider
|
|
),
|
|
}
|
|
}
|
|
|
|
fn parse_zeta2_output(
|
|
example: &Example,
|
|
actual_output: &str,
|
|
format: ZetaFormat,
|
|
) -> Result<(String, Option<ActualCursor>)> {
|
|
let prompt_inputs = example
|
|
.prompt_inputs
|
|
.as_ref()
|
|
.context("prompt_inputs required")?;
|
|
|
|
if format == ZetaFormat::V0615HashRegions {
|
|
return Ok((
|
|
parse_zeta2_model_output_as_patch(actual_output, format, prompt_inputs)?,
|
|
None,
|
|
));
|
|
}
|
|
|
|
let parsed = parse_zeta2_model_output(actual_output, format, prompt_inputs)?;
|
|
let range_in_excerpt = parsed.range_in_excerpt.clone();
|
|
let excerpt = prompt_inputs.cursor_excerpt.as_ref();
|
|
let editable_region_offset = range_in_excerpt.start;
|
|
let editable_region_start_line = excerpt[..editable_region_offset].matches('\n').count();
|
|
|
|
let mut new_text = parsed.new_editable_region.clone();
|
|
if !new_text.is_empty() && !new_text.ends_with('\n') {
|
|
new_text.push('\n');
|
|
}
|
|
|
|
let cursor_offset = parsed.cursor_offset_in_new_editable_region;
|
|
let formatted_diff = parsed_output_to_patch(prompt_inputs, parsed)?;
|
|
|
|
let actual_cursor = cursor_offset.map(|editable_region_cursor_offset| {
|
|
ActualCursor::from_editable_region(
|
|
&example.spec.cursor_path,
|
|
editable_region_cursor_offset,
|
|
&new_text,
|
|
excerpt,
|
|
editable_region_offset,
|
|
editable_region_start_line,
|
|
)
|
|
});
|
|
|
|
Ok((formatted_diff, actual_cursor))
|
|
}
|