MCPcopy Create free account
hub / github.com/atomicdotdev/atomic / merge_items_into_section

Function merge_items_into_section

atomic-agent/src/learnings.rs:528–604  ·  view source on GitHub ↗

Merge new items into existing section headings without duplicating headings. If `### Repo` already exists in the section, new repo items are appended under the existing heading. If a heading doesn't exist yet, it's created.

(
    existing_content: &str,
    new_items: &HashMap<String, Vec<String>>,
)

Source from the content-addressed store, hash-verified

526/// If `### Repo` already exists in the section, new repo items are appended
527/// under the existing heading. If a heading doesn't exist yet, it's created.
528fn merge_items_into_section(
529 existing_content: &str,
530 new_items: &HashMap<String, Vec<String>>,
531) -> String {
532 let start_idx = match existing_content.find(SECTION_START) {
533 Some(idx) => idx + SECTION_START.len(),
534 None => return existing_content.to_string(),
535 };
536
537 let end_marker_idx = match existing_content[start_idx..].find(SECTION_END) {
538 Some(idx) => start_idx + idx,
539 None => return existing_content.to_string(),
540 };
541
542 let before_section = &existing_content[..start_idx];
543 let section_body = &existing_content[start_idx..end_marker_idx];
544 let after_section = &existing_content[end_marker_idx..];
545
546 // Parse existing section into heading → items
547 let mut sections: Vec<(String, Vec<String>)> = Vec::new();
548 let mut current_heading: Option<String> = None;
549 let mut current_items: Vec<String> = Vec::new();
550
551 for line in section_body.lines() {
552 let trimmed = line.trim();
553 if trimmed.starts_with("### ") {
554 // Save previous heading if any
555 if let Some(heading) = current_heading.take() {
556 sections.push((heading, std::mem::take(&mut current_items)));
557 }
558 current_heading = Some(trimmed.to_string());
559 } else if trimmed.starts_with("- ") {
560 current_items.push(trimmed.to_string());
561 }
562 }
563 if let Some(heading) = current_heading {
564 sections.push((heading, current_items));
565 }
566
567 // Merge new items into existing headings or append new headings
568 let mut merged_headings: std::collections::HashSet<String> = std::collections::HashSet::new();
569 for (heading, items) in sections.iter_mut() {
570 if let Some(new) = new_items.get(heading) {
571 items.extend(new.iter().cloned());
572 merged_headings.insert(heading.clone());
573 }
574 }
575
576 // Add headings that didn't exist yet
577 // Use a stable order: Repo first, then Workflow
578 for heading in &["### Repo", "### Workflow"] {
579 let heading = heading.to_string();
580 if !merged_headings.contains(&heading) {
581 if let Some(items) = new_items.get(&heading) {
582 sections.push((heading, items.clone()));
583 }
584 }
585 }

Calls 10

iter_mutMethod · 0.80
extendMethod · 0.80
getMethod · 0.65
lenMethod · 0.45
linesMethod · 0.45
pushMethod · 0.45
iterMethod · 0.45
insertMethod · 0.45
cloneMethod · 0.45
containsMethod · 0.45