GuideGit

Git cherry-pick: flytta en AI-fix till rätt gren

Flytta en granskad AI-fix med Git cherry-pick. Prova -x, konflikter, intervall, -n och merge med -m samt kontrollera patchar innan du delar ändringen.

Publicerad · Senast granskad

En grön kub vid en förgrening mellan mörka metallskenor med mindre svarta block längs skenorna.
Cherry-pick tillämpar en vald commits ändring på den gren där du står och skapar normalt en ny commit.
Kort sagt

Rädda den granskade fixen, inte hela AI-försöket. Med Git cherry-pick för du över en commits ändring till din målgren. Kontrollera ursprung, diff och beteende innan du föreslår att ändringen ska delas.

1. Avgränsa fixen innan du byter gren

AI-agenten har arbetat i en försöksgren. Det mesta ska bort, men kontrollen av ett tomt formulärfält är användbar. Läs den commitens hela diff: följer ett nytt paket, en omdöpt funktion eller en ändrad datamodell med? En liten commit kan fortfarande bero på tidigare arbete. Skriv ett eget godkännandekriterium: tom inmatning ska stoppas och giltig inmatning ska fungera.

Git cherry-pick i Git 2.56.0 tillämpar ändringen och skapar normalt en ny commit på den aktuella grenen. Källcommiten tas inte bort. Börja med rent arbetsläge. Använder du en separat AI-katalog kan guiden om Git worktree hjälpa dig att hålla arbetet isär. Behöver du först identifiera rätt commit, följ Git bisect för AI-fel.

2. Skapa ditt eget lokala prov

Kör blocken i ordning i samma PowerShell-terminal. Du behöver Git installerat. Provet skapar en ny katalog i systemets temporärmapp; använd den inte som instruktion att skriva över ett befintligt projekt. Funktionen GitOk stoppar blocket om ett Git-kommando misslyckas. De kommande konflikterna anropas separat eftersom ett stopp då är avsiktligt.

Det här är ditt läsarprov med förväntat facit, inte terminalutdata från redaktionen. Inga kommandoflöden har körts av redaktionen. Exemplet använder textfiler för att göra ändringarna synliga; i din app behöver du dessutom köra tester för formulärets verkliga beteende. Fortsätt bara om utfallet stämmer med beskrivningen.

$ErrorActionPreference = 'Stop'
function GitOk {
    & git @args
    if ($LASTEXITCODE -ne 0) { throw 'Git stoppade; undersok felet innan du fortsatter' }
}
$provKatalog = Join-Path ([System.IO.Path]::GetTempPath()) ('cherry-pick-prov-' + [guid]::NewGuid())
New-Item -ItemType Directory -Path $provKatalog | Out-Null
Set-Location $provKatalog
$utf8 = New-Object System.Text.UTF8Encoding($false)
GitOk --version
GitOk init -b main
GitOk config user.name 'Cherryprov'
GitOk config user.email 'cherryprov@example.invalid'
GitOk config core.autocrlf false
[System.IO.File]::WriteAllText("$provKatalog/kontroll.txt", "tomt tillats`n", $utf8)
GitOk add -- kontroll.txt
GitOk commit -m 'Bas for formularkontroll'
$bas = git rev-parse HEAD
GitOk switch -c ai/forsok
[System.IO.File]::WriteAllText("$provKatalog/kontroll.txt", "tomt stoppas`n", $utf8)
GitOk add -- kontroll.txt
GitOk commit -m 'Stoppa tom inmatning'
$fix = git rev-parse HEAD
[System.IO.File]::WriteAllText("$provKatalog/experiment.txt", "ska inte med`n", $utf8)
GitOk add -- experiment.txt
GitOk commit -m 'Ogranskat AI-experiment'
GitOk log --oneline -2
GitOk show $fix

Din kontrollpunkt är två skilda commits: en som ändrar kontroll.txt och en som lägger till experiment.txt. Läs patchen för den sparade variabeln fix. Den ska bara ändra raden om tom inmatning. Välj inte grenspetsen av bekvämlighet: i det här provet är den just det ogranskade experimentet.

3. Kopiera den enskilda commiten med -x

Byt till main innan du väljer commiten. -x lägger enligt cherry-pick-manualen till källans commit-id i meddelandet vid konfliktfri kopiering. Det ger spårbarhet när båda grenarnas historik är tillgänglig för granskaren. Behåll därför försöksgrenen under granskningen; en referens till ett otillgängligt privat försök hjälper mottagaren mindre.

GitOk switch main
GitOk status --short
GitOk cherry-pick -x $fix
GitOk log -1 --format='%H%n%B'
Get-Content kontroll.txt
Test-Path experiment.txt
GitOk cherry -v main ai/forsok
GitOk log --cherry-pick --right-only --no-merges --oneline 'main...ai/forsok'

Facit: kontroll.txt innehåller tomt stoppas, medan filkontrollen för experiment.txt ger False. Läs meddelandets ursprungsnotering. I Git cherry betyder minus att patchen har en motsvarighet i main och plus att motsvarighet saknas. Fixen ska ha minus och experimentet plus. Jämförelsen bygger på diff med blanktecken och radnummer borttagna, inte på lika commit-id.

Git log med --cherry-pick utesluter motsvarande patchpar i en symmetrisk differens. Med höger sida och utan merges ska listan här innehålla experimentet, inte fixen. Använd kontrollen innan du försöker kopiera samma fix igen. Den bedömer patchlikhet, inte om ditt formulär fungerar; kör även dina beteendetester.

4. Lös en konflikt eller avbryt försöket

Nu ändrar du samma rad på två grenar med olika avsikt. Skapa först båda versionerna och starta kopieringen. Förväntat facit är att Git stannar med konflikt i kontroll.txt. Om kommandot i stället lyckas ska du undersöka varför ditt prov avviker innan du kör nästa block.

GitOk switch -c ai/konflikt
[System.IO.File]::WriteAllText("$provKatalog/kontroll.txt", "tomt stoppas med forklaring`n", $utf8)
GitOk add -- kontroll.txt
GitOk commit -m 'Forklara varfor tom inmatning stoppas'
$konfliktFix = git rev-parse HEAD
GitOk switch main
[System.IO.File]::WriteAllText("$provKatalog/kontroll.txt", "tomt stoppas med lokal text`n", $utf8)
GitOk add -- kontroll.txt
GitOk commit -m 'Lokal formulering pa main'
$foreKonflikt = git rev-parse HEAD
git cherry-pick -x $konfliktFix
if ($LASTEXITCODE -eq 0) { throw 'Forvantad konflikt saknas' }
GitOk status --short
Get-Content kontroll.txt

Cherry-pick-manualen beskriver --abort som återgång till läget före sekvensen. Prova det först. Därefter startar du samma konflikt igen och löser den med en medvetet vald kombination. Att acceptera hela AI-versionen utan läsning skulle i det här exemplet tappa den lokala formuleringen.

GitOk cherry-pick --abort
if ((git rev-parse HEAD) -ne $foreKonflikt) { throw 'Kontrollera atergangen' }
Get-Content kontroll.txt
git cherry-pick -x $konfliktFix
if ($LASTEXITCODE -eq 0) { throw 'Forvantad konflikt saknas' }
[System.IO.File]::WriteAllText("$provKatalog/kontroll.txt", "tomt stoppas med lokal text och forklaring`n", $utf8)
GitOk add -- kontroll.txt
GitOk diff --cached
git -c core.editor=true cherry-pick --continue
if ($LASTEXITCODE -ne 0) { throw 'Fortsattningen stoppade; las status' }
GitOk log -1 --format='%B'
Get-Content kontroll.txt

Facit efter abort är den lokala texten och samma HEAD som före försöket. Efter --continue ska den kombinerade raden finnas i en ny commit. Inställningen core.editor=true accepterar meddelandet utan en interaktiv redigerare i detta prov. Läs det efteråt: manualens löfte om automatisk ursprungsnotering med -x gäller konfliktfria fall. Dokumentera källcommit och din konfliktlösning i granskningsunderlaget.

5. Flytta ett avgränsat intervall

Två fristående filer får representera två godkända ändringar. Git revisions definierar bas..sista som commits nåbara från sista, med basens historia utesluten. I det linjära provet blir det exakt A och B. Kontrollera listan innan kopieringen; en förgrenad projekthistorik kan ge ett större urval än du tänkt.

$intervallBas = git rev-parse HEAD
GitOk switch -c ai/intervall
[System.IO.File]::WriteAllText("$provKatalog/a.txt", "godkand A`n", $utf8)
GitOk add -- a.txt
GitOk commit -m 'Godkand A'
[System.IO.File]::WriteAllText("$provKatalog/b.txt", "godkand B`n", $utf8)
GitOk add -- b.txt
GitOk commit -m 'Godkand B'
$sista = git rev-parse HEAD
$urval = $intervallBas + '..' + $sista
GitOk log --reverse --oneline $urval
GitOk switch main
GitOk cherry-pick -x $urval
Get-Content a.txt, b.txt
GitOk log -2 --oneline

Ditt facit är båda filernas godkända rader och två nya commits på main. Stoppa om förhandslistan innehåller något annat än de två avsedda ändringarna. Finns ett beroende mellan commits ska du granska dem tillsammans; ett intervall är ett urval av historik, inte ett kvalitetsomdöme om AI-koden.

6. Prova innehållet utan commit med -n

Med -n läggs ändringen i arbetskatalog och index utan en ny commit, enligt cherry-pick-manualen. Det passar när du vill granska eller anpassa resultatet innan du sparar. Provet använder rent läge även här. Det gör jämförelsen tydlig och hindrar att du blandar in något annat eget pågående arbete.

GitOk switch -c ai/prov-utan-commit
[System.IO.File]::WriteAllText("$provKatalog/extra.txt", "granska innan commit`n", $utf8)
GitOk add -- extra.txt
GitOk commit -m 'Extra kontroll'
$extra = git rev-parse HEAD
GitOk switch main
$foreProv = git rev-parse HEAD
GitOk cherry-pick -n $extra
if ((git rev-parse HEAD) -ne $foreProv) { throw 'HEAD andrades ovantat' }
GitOk diff --cached
Get-Content extra.txt
GitOk commit -m 'Ta in den granskade extrakontrollen'

Facit före sista kommandot är oförändrat HEAD och extra.txt synlig i indexdiffen. Den sista raden sparar ditt granskade innehåll. Lägg ditt eget teststeg före den raden i ett verkligt projekt. En lyckad applicering säger bara att ändringen gick att lägga in, inte att dess krav eller säkerhet är granskade.

7. Välj förälder om källan är en merge

En merge har flera föräldrar. Cherry-pick behöver då -m för att spela upp ändringen relativt vald huvudlinjeförälder, numrerad från 1. Siffran är inget grennamn. Skapa en kontrollerad merge och jämför första föräldern med den sparade basen innan du väljer 1.

$mergeBas = git rev-parse HEAD
GitOk switch -c ai/merge-del
[System.IO.File]::WriteAllText("$provKatalog/merge.txt", "mergeandring`n", $utf8)
GitOk add -- merge.txt
GitOk commit -m 'Andring for mergeprovet'
GitOk switch -c ai/merge-resultat $mergeBas
GitOk merge --no-ff ai/merge-del -m 'Samla AI-andringen'
$merge = git rev-parse HEAD
GitOk log -1 --format='%H %P' $merge
if ((git rev-parse ($merge + '^1')) -ne $mergeBas) { throw 'Kontrollera foraldrarna' }
GitOk diff ($merge + '^1') $merge
GitOk switch main
GitOk cherry-pick -x -m 1 $merge
Get-Content merge.txt

Facit är att diffen mot första föräldern visar merge.txt och att filen sedan finns på main. I ditt projekt ska du läsa just den diffen: den kan omfatta fler ändringar än den enskilda fix du ville rädda. Välj i så fall hellre den avgränsade ursprungliga commiten efter att ha granskat beroendena.

8. Lämna vidare ett kontrollerat resultat

Samla källcommit, målgren, granskad diff och det beteende du provat i din pull request. För formulärexemplet ska både tom och giltig inmatning ingå i kontrollen. Behåll källreferenserna tills granskningen är klar. Om en redan delad fix senare måste ångras tar guiden om Git revert vid. Cherry-pick-provet här avslutas lokalt och innehåller ingen push.

Källor och avgränsning

Källorna kontrollerade 23 oktober 2026. Guiden utgår från Git 2.56.0. Exemplen är läsarens lokala prov med förväntat facit; inga kommandoflöden har körts av redaktionen. Filinnehållet är konstruerat och ersätter inte projektets egna beteendetester.