Як змусити натиснути скидання до віддаленого сховища?


94

Наша віддалена головна гілка якось заплуталася. Поточний код розробки знаходиться у головній гілці разом із останніми комітами. Очевидно, що код розробки не готовий для головної гілки.

Так що на моєму локальному сховищі, я зробив скидання до останньої мітки, git reset --hard (Tag). Зараз головна гілка правильна в моєму локальному сховищі. Тепер, коли я намагаюся перенести зміни на віддалене сховище,, git push origin masterя отримую повідомлення про помилку:

To (REMOTE GIT REPOSITORY LOCATION)
 ! [rejected]        master -> master (non-fast-forward)
error: failed to push some refs to '(REMOTE GIT REPOSITORY LOCATION)'
To prevent you from losing history, non-fast-forward updates were rejected
Merge the remote changes (e.g. 'git pull') before pushing again.  See the
'Note about fast-forwards' section of 'git push --help' for details.

Тож, оглянувшись навколо, я з’ясував --forceваріант. Отже, я примусово натиснув на віддалене сховище git push --force origin master, і все одно отримав помилку:

Total 0 (delta 0), reused 0 (delta 0)
remote: error: denying non-fast-forward refs/heads/master (you should pull first)
To (REMOTE GIT REPOSITORY LOCATION)
 ! [remote rejected] master -> master (non-fast-forward)
error: failed to push some refs to '(REMOTE GIT REPOSITORY LOCATION)'

Я не можу зробити тягу на master, оскільки він містить код розробки, який не може бути на master.


3
Думаю, повідомлення означає, що ви не маєте права робити швидкий просування вперед.
свик

3
Ви мали рацію, дякую. У файлі конфігурації для сховища на пульті дистанційного керування, denyNonFastforwards = true. Я змінив його на false, відсунув свої зміни, а потім змінив його на true. Ще раз дякую за допомогу.
Семвелл

2
@samwell, будь ласка, позначте відповідь svick прийнятою
hultqvist

@samwell відповідь свика працювала у вас чи ні?
Songo

Для тих, хто потребує детальної інформації про те, як відключити denyNonFastForwards, як це зробив Семвелл, більше інструкцій можна знайти тут:
stackoverflow.com/a/43721579/2073804

Відповіді:


152

Повідомлення означає, що вам заборонено робити нешвидкий перехід вперед.

Ваш віддалений репозиторій, швидше за все, denyNonFastforwards = trueзнаходиться у своєму конфігу Якщо ви це зміните, це git push --forceмає спрацювати.

Щоб змінити налаштування, вам потрібен доступ до машини з віддаленим сховищем. Звідти робіть git config receive.denynonfastforwards false.


1
Чи можете ви зробити git configдля сервера? Або, можливо, ви використовували це метафорично. Щоб пограти з цими ідеями, я створив тестове репо в /opt/git(мій простір сервера git), а потім змінив це налаштування в /opt/git/the_repo/the_repo.git/config. Але як тільки зробив, git push --force origin SHA:branchпрацював як потрібно.
HankCa

4
Повідомлення про помилку матиме рядок, який починається з "помилка: не вдалося висунути деякі посилання до <вашого сховища>", де <ваше сховище> - шлях, що закінчується на .git, який є каталогом, що містить файл під назвою "config". У цьому "конфігураційному" файлі ви можете встановити denyNonFastforwards = false
наждак

1
Коментар @ emery цінний. Іноді для папки на сервері початкове значення буде встановлене на зразок /srv/git/repo.git. Це конфігурація, для якої встановлено denyNonFastForwards, а не папка програми.
Елайджа Лінн,

1
@hsalimi Якщо у вас немає доступу до сервера, вам потрібно зв’язатися з адміністратором сервера і попросити їх тимчасово вимкнути його, щоб ви могли змусити натискати, а потім знову вмикати. Навряд чи більшість з них можуть це зробити. Це може бути частіше у внутрішньому середовищі з власною командою хостингу.
Елайджа Лінн,

1
Спочатку це засмучує, але краса в тому, що пульт повністю захищений за замовчуванням, і якщо ви як розробник навмисно і правильно робите перебази, ви можете замінити цю конфігурацію, щоб дозволити небезпечну поведінку. Перебазування - це те, що кожен користувач git повинен знати, як робити - і знати, коли цього не робити. doc1 doc2
moodboom

15

Пульт не дозволяє швидко перемотувати вперед.

Найкращий варіант - до git revertвсіх комітів, яких там не повинно бути, і будьте обережнішими в майбутньому.

git revert [commit]створить новий коміт, який скасовує все, що було [commit]зроблено.


Деякі налаштування віддаленого сховища заблокували всі зміни, що не перемотуються вперед.
Семвелл

Якщо ви зробите це і вам потрібно повторно застосувати коміти, історія не видаляється при скасуванні, а лише зміна коду, і ви не зможете вибирати комміти або об'єднувати
mtpultz

12

Кроки для постійного включення силового натискання в наступному стилі

git push -f myrepo my-branch

Відредагуйте файл із назвою "config" у папці, що закінчується на ".git" у віддаленому сховищі

У командному рядку git, що виводиться з невдалого натискання, знайдіть рядок, де написано щось на зразок:

error: failed to push some refs to 'ssh://user@some-remote-server.mycompany.com/srv/git/myrepo.git

тоді

ssh user@some-remote-server.mycompany.com
cd /srv/git/myrepo.git
vi config

Встановіть для параметра "denyNonFastforwards" значення false

У "конфігурації" встановіть

[receive]
        denyNonFastforwards = false

Тепер ви можете натискати з локальної машини за допомогою -f

git push -f myrepo my-branch

Як це зробити без доступу до SSH для оголення репозиторію git?
Володимир Вуканац

Можливо, скористайтеся командою git revert, як пропонує Річо? Якщо спочатку створити резервну копію поточного стану репо, ви все одно можете об’єднати свій код, рухаючись вперед.
наждак

git revertце якось складно, коли у вас є злиття. Якщо бути більш складним, у моєму випадку є 3 злиття, з яких одне з дуже старим ~ 20 комітом відхилено від розробки, 2-е - це злиття від майстра - некрасиво, як пекло.
Володимир Вуканац

1
Можливо, рішення полягає в тому, щоб скинути бажаний стан, зробити резервну копію (схованку), витягнути ще раз і застосувати резервну копію (схованку).
Володимир Вуканац

1
mrW ви все ще можете об'єднати базу коду, яку ви хочете, на повернуту / витягнуту базу коду
наждак

11

Спробуйте використати -fпрапор і поставити його після назви віддаленого відділення.

git push origin master -f


1
Ні, і це теж не спрацювало. Я теж спробував git push -f origin masterі той самий результат. Обидва рази, коли я спробував, я отримав другу версію повідомлення про помилку.
Семвелл

2

Вам заборонено робити git push, який не перемотується вперед.

  1. Якщо пульт дистанційного керування є GitHub, перейдіть до https://github.com/$USER/$REPO/settings/branchesта скасуйте захист відповідної гілки.

    введіть тут опис зображення

    Для цього потрібно бути адміністратором репо.

  2. Якщо пульт - це ваш власний git-сервер, запустіть git config receive.denynonfastforwards falseтам.


Майте на увазі, що для екземплярів Git Hub Enterprise натискання до гілки за замовчуванням (зазвичай "master") можна відключити на рівні екземпляра. Це означає, що навіть якщо "master" не захищений, і навіть якщо ви адміністратор сайту, ви не зможете виконувати примусові натискання на гілку за замовчуванням. Припускаючи, що у вас є дозволи, ви можете тимчасово обійти це, переключивши гілку за замовчуванням на щось інше, зробивши примусове натискання, а потім переключившись назад.
Крістофер Хантер,


0

Проблема виникає, оскільки поточна гілка не налаштована належним чином для PULL . Спочатку перевірте, чи правильно налаштовано гілку вище за течією, використовуючи - git remote show origin. Ви можете знайти його в розділі - Локальні гілки , налаштовані для «мерзотника тягнути»: . Якщо ні, налаштуйте його за допомогою:

git config branch.MYBRANCH.merge refs/heads/MYBRANCH

Вкажіть відповідну назву філії для власника місця - МІБРАН


0

Я використовую цю групу команд для скидання мого віддаленого репо, це повторно ініціалізує ваше локальне репо та зв’яже з вашим віддаленим репо, а потім змусить оновити оновлення.

Я думаю, що такий спосіб не спрацює у вашому випадку, але може бути корисним для когось іншого

перейдіть до вихідної папки, потім запустіть команди: зверніть увагу, що https://github.com/*.gitце ваше віддалене посилання на репо

git init
git remote add origin https://github.com/*.git
git add .
git commit -m "initial commit"
git push origin master -f
git push --set-upstream origin master

**Note: this will clear all your git history on your master branch**


0

Для мене підказка @svick вказувала у правильному напрямку. Оскільки git-сервер, який я хотів змінити, насправді є моєю скринькою, я увійшов у нього і зробив a, git config --global receive.denynonfastforwards falseщоб змінити всі репозиторії, щоб прийняти примусове натискання non-ff. Не вийшло нестандартно. Я виявив, що в конфігурі вже receive.denynonfastforwards=trueвстановлено, і його неможливо стерти git config --global --unset receive.denynonfastforwards. vi configОднак редагування в репо вручну ( ) працювало.


0

Я вирішив, видаливши головну гілку із захищеної, а також за замовчуванням, що трохи перевищує встановлені правила гілок у налаштуваннях сховища.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.