Kirim permintaan tarik di GitHub hanya untuk komit terbaru

280

Saya melakukan proyek pada github dan berhasil membuat perubahan pada master lokal saya dan mendorong ke asal di github. Saya ingin mengirim permintaan tarik, tetapi hanya ingin memasukkan komit terakhir. UI permintaan tarik di github.com menunjukkan 9 commit terakhir dan saya tidak tahu cara memfilternya.

Saya mencoba memahami apakah saya harus membuat cabang lokal baru, periksa itu dan entah bagaimana mengatur ulang atau rebase ke hulu? Kemudian terapkan komit terakhir saya dari tuan saya dengan id ke cabang lokal baru dan gunakan itu untuk permintaan tarik?

Saya mencoba untuk mendapatkan konsep yang benar dan mencari tahu baris perintah yang tepat untuk melakukan apa yang saya butuhkan.

Kevin Hakanson
sumber
Dan apa yang terjadi jika Anda melakukan permintaan tarik dengan semua komitmen lainnya? Saya pikir git cukup pintar untuk mengabaikan (atau melewatkan) komitmen yang sudah ditariknya?
jayarjo
3
Agaknya hulu belum menerima, atau tidak mau, intervensi dilakukan.
Michael Scott Cuthbert
@jayarjo I misalnya membuat perubahan lain yang tidak ingin saya kirim ke hulu. Perubahan untuk git mengabaikan repositori utama tidak perlu misalnya. Tidak ada yang mudah dengan git.
Martin
Terkait: Beberapa detail bagus tentang bagaimana permintaan tarik berbeda di Git (perangkat lunak) dan GitHub (layanan web)
RBT

Jawaban:

302

Anda pada dasarnya perlu membuat cabang baru & memetik ceri komit yang ingin Anda tambahkan.

Catatan: Anda mungkin membutuhkan ini sebelum perintah checkout / cherry-pick

git remote add upstream <git repository>

git remote update

git checkout -b <new-branch-name> upstream/master

git cherry-pick <SHA hash of commit>

git push origin <new-branch-name>

Setelah itu, Anda akan melihat <new-branch-name>cabang di github, beralih ke sana dan dapat mengirimkan permintaan tarik dengan perubahan yang Anda inginkan.

Kevin Hakanson
sumber
32
Saya juga perlu git remote add upstream <git repository>dan git remote updatesebelum menjalankan git checkout -b upstream upstream / master.
plainjimbo
6
Ini berfungsi, tetapi bukan bagaimana Anda seharusnya melakukannya, karena sekarang cabang hulu dan hulu / master Anda berbeda dan akan selalu berbeda jika menggabungkan permintaan tarik Anda bukan hal pertama yang dilakukan hulu. Untuk alasan itu Anda sebaiknya memilih melakukan stackoverflow.com/a/5256304/1904815 .
JonnyJD
2
Untuk menguraikan: Ini bukan masalah teknis, tetapi masalah logis. Saat Anda ingin melakukan apa pun dengan upstream (seperti penggabungan dari sana), Anda perlu menambahkan cabang "real-upstream" atau mengatur ulang upstream Anda (tidak meninggalkan cabang lokal untuk permintaan tarik Anda untuk perubahan tambahan).
JonnyJD
15
Mengapa saya perlu cabang tambahan, hanya untuk membuat PR untuk satu baris kode yang diubah ?! Apakah ada orang di github yang memikirkan hal ini?
CodeManX
2
@ JonHanna Tidak ... mengapa Anda harus menggabungkan cabang sama sekali? Mengapa Anda tidak bisa hanya menggabungkan komit?
Kevin Krumwiede
57

Buat cabang baru mulai dari komit terbaru, yang juga dalam repositori asal:

git branch new-branch origin/master
git checkout new-branch

Kemudian gunakan git cherry-pickuntuk mendapatkan komit tunggal yang Anda inginkan permintaan tariknya. Jika cabang dengan komit ini dipanggil featuredan komit yang Anda inginkan adalah komit terbaru di cabang ini, ini akan menjadi

git cherry-pick feature

Dengan asumsi tambalan ini berlaku tanpa konflik, Anda sekarang memiliki cabang tempat Anda dapat melakukan permintaan tarik.

Pada langkah kedua, Anda sekarang perlu memutuskan apa yang harus dilakukan dengan featurecabang Anda . Jika Anda belum mempublikasikan perubahan Anda di cabang ini, prosedur terbaik mungkin rebasing cabang ini pada cabang-baru (dan menghapus komit terakhir, jika ini tidak dilakukan secara otomatis oleh git rebase).

Lars Noschinski
sumber
Saya menerima pesan ini setelah sakura. tidak ada yang ditambahkan untuk melakukan tetapi file yang tidak dilacak ada (gunakan "git add" untuk melacak). Semuanya ada di tuanku, tetapi aku harus membuat rantingku dari hulu.
Kevin Hakanson
5
Jika featuresudah berkomitmen origin/master, tidak ada yang terjadi selama cherry-pick. Cabang baru harus dari upstream/master(yaitu, jawaban Kevin
Hakanson
26

Saya berakhir dalam situasi di mana saya telah bercabang dua garpu dan ingin mengajukan permintaan tarik kembali ke proyek asli.

Saya punya:

  • orignal_project
  • forked_project (dibuat dari proyek asli di SHA: 9685770)
  • my_fork (dibuat dari proyek bercabang di SHA: 207e29b)
  • komit di fork saya (SHA: b67627b) yang ingin saya kirimkan kembali ke proyek asli

Untuk melakukan ini, saya:

  1. menciptakan cabang baru dari SHA di mana proyek asli bercabang dua
  2. menarik semua dari proyek asli
  3. cherry memilih komit yang ingin saya kirim sebagai permintaan tarik
  4. mendorong semuanya ke github

Perintah git adalah sesuatu seperti:

  1. git branch my-feature-request 9685770
  2. git checkout permintaan-fitur-saya
  3. git pull https://github.com/original_project/original_project.git
  4. git cherry-pick b67627b
  5. git push origin-my-feature-request

Kemudian saya memilih permintaan fitur-saya sebagai cabang untuk permintaan tarik saya ke proyek asli.

John Naegle
sumber
6

Ini hampir berhasil untuk saya:

git checkout -b upstream upstream/master

git cherry-pick <SHA hash of commit>

git push origin upstream

Satu-satunya perbedaan adalah ini:

git push origin upstream:upstream

Saya perlu mengubah baris terakhir sehingga git push akan membuat cabang hulu di repo GitHub saya sehingga saya bisa membuat PR dari situ.

hi_tech_lowlife
sumber
5

Saya sudah membuat komitmen yang saya ingin dapat mengisolasi sebagai permintaan tarik kembali ke cabang saat ini.

Jadi saya memeriksa cabang baru

git checkout -b isolated-pull

Dan di sinilah solusi saya berbeda dengan @Kevin Hakanson , karena saya perlu mengatur ulang cabang ini ke tempat dalam sejarah yang ingin saya bedakan

git reset --hard [sha-to-diff-by]

Dan ceri-pilih komit dari mana saya ingin membuat permintaan tarik terisolasi

git cherry-pick [my-isolated-commit-sha]

Akhirnya dorong ke atas ke jarak jauh

git push origin isolated-pull

Dan tarik permintaan dat shi.

irbanana
sumber
1

Solusi untuk membuat cabang baru (sementara), memetik ceri dan membuat permintaan tarik untuk cabang itu tidak memuaskan saya. Saya tidak ingin mengubah repositori saya untuk membuat set komit tersedia, jadi saya datang dengan alternatif berikut:

Pertama buat file tambalan untuk semua komitmen yang menarik:

git format-patch -1 <sha>

Jika komit minat terjadi menjadi yang terakhir yang dapat Anda gunakan HEADsebagai gantinya <sha>.

Sekarang, Anda dapat mengirim tambalan ke pengelola repositori sumber, yang dapat menerapkannya:

git branch new-branch <master or some older commit where the fork diverged>
git checkout new-branch

git am < <the patch>
...

git checkout master
git merge new-branch

Akhirnya ini akan terlihat sama seperti jika cabang sementara digabung oleh permintaan tarik, tetapi tanpa memiliki cabang tambahan di repositori-fork.

Johannes Jendersie
sumber
0

Berdasarkan jawaban @ kevin-hakanson, saya menulis skrip bash kecil ini untuk mempermudah proses ini. Ini akan menambahkan repo hulu jika belum ada (meminta Anda untuk URL) kemudian meminta kedua nama cabang baru untuk membuat dan tag / SHA dari komit untuk cherry pick ke cabang itu. Ini memeriksa apa cabang atau komit Anda saat ini kemudian menyimpan perubahan apa pun sehingga Anda dapat checkout cabang baru. Strategi penggabungan menjaga perubahan dari komit yang dipilih cherry. Setelah mendorong cabang baru ke origin(diasumsikan sebagai nama repo jarak jauh Anda), cabang atau komit Anda sebelumnya diperiksa kembali dan perubahan Anda sebelumnya muncul dari simpanan.

if ! git remote | grep -q upstream; then
    read -p "Upstream git repo URL: " upstream
    git remote add upstream $upstream
    git remote update
fi

read -p "Feature branch name: " feature_branch
# note: giving "master" is the same as giving the SHA it points to
read -p "SHA of commit to put on branch: " sha

current_branch=$(git rev-parse --abbrev-ref HEAD)
if [ "$current_branch" == "HEAD" ]; then
    # detached HEAD; just get the commit SHA
    current_branch=$(git rev-parse --short HEAD)
fi
git stash
git checkout -b $feature_branch upstream/master
git cherry-pick --strategy=recursive -X theirs $sha
git push origin $feature_branch
git checkout $current_branch
git stash pop

(Ini telah bekerja untuk saya dalam beberapa tes sederhana, tapi saya bukan seorang programmer bash atau ahli git, jadi beri tahu saya jika ada kasus yang saya lewatkan yang dapat diotomatisasikan dengan lebih baik!)

Nathan
sumber