Git: налаштувати пульт лише для отримання даних?


132

Коли я запускаюсь git remote -vв одному з моїх сховищ Git, у якому налаштовано віддалений (и), я бачу, що кожен пульт має і функції отримання, і push:

$ git remote -v
<remote-name> ssh://host/path/to/repo (fetch)
<remote-name> ssh://host/path/to/repo (push)

Для віддалених користувачів, які вказують на розробників-однолітків, немає потреби натискати, і Git все одно відмовиться переходити на неоголене сховище. Чи є якийсь спосіб налаштувати ці пульти як "лише для вибору" без push-адреси чи можливостей?


4
@sehe, nope, ти не можеш. Якщо не вказана URL-адреса push, натискання використовуватимуть URL-адресу отримання.
— yoyo

Відповіді:


191

Я не думаю, що ви можете видалити push-адресу, ви можете лише змінити її на щось інше, ніж URL-адресу для витягування. Тому я думаю, що найближче, що ти знайдеш, - це щось подібне:

$ git remote set-url --push origin no-pushing
$ git push
fatal: 'no-pushing' does not appear to be a git repository
fatal: The remote end hung up unexpectedly

Ви встановлюєте push-адресу на no-pushing, доки у вашій робочій папці немає папки з тим самим іменем, git не зможе знайти. Ви по суті змушуєте git використовувати місце, яке не існує.


14
Так, ви можете подумати, що "git remote set-url --delete --push. *" Зробить трюк, але якщо ви видалите URL-адресу push, то він за замовчуванням повернеться до URL-адреси отримання.
— yoyo

6
Я особисто вважаю за краще використовувати щось на кшталт " ВИЗНАЧЕНО ", більш помітне. Але це лише питання смаку.
— П’єр-Олів'є Варес

@ П'єр-Олів'єВарес Що з "DONTPUSH" ?! :)
— Алі Шакіба

FYI, після цього ваш файл конфігурації git повинен виглядати приблизно так: (Зверніть увагу на новий параметр pushurl ) [віддалене "походження"] отримання = + refs / heads / *: refs / Remotes / origin / * url = ssh: // host / шлях / до / repo pushurl = ssh: // host / no-
— pushing

1
Подібно до @ Pierre-OlivierVares, я пішов із собою git remote set-url --push origin -- --read-only--- відзначте додаткові, --щоб дозволити ім'я з провідними тире. Мені це стало зрозумілішим.
— lindes

13

Окрім зміни URL-адреси push на щось недійсне (наприклад, git remote set-url --push origin DISABLED), можна також використовувати pre-pushгачок.

Одним із швидких способів зупинитися git pushє /usr/bin/falseпозначення гачка:

$ ln -s /usr/bin/false .git/hooks/pre-push
$ git push
error: failed to push some refs to '...'

Використання гачка дозволяє при бажанні більш тонко контролювати натискання. Ознайомтеся .git/hooks/pre-push.sampleз прикладом того, як запобігти натисканням комітетів незавершеного виробництва.

Щоб запобігти натисканню на певну гілку або обмежити натискання на одну гілку, це у прикладі гачка:

$ cat .git/hooks/pre-push
#!/usr/bin/sh

# An example hook script to limit pushing to a single remote.
#
# This hook is called with the following parameters:
#
# $1 -- Name of the remote to which the push is being done
# $2 -- URL to which the push is being done
#
# If this script exits with a non-zero status nothing will be pushed.

remote="$1"
url="$2"

[[ "$remote" == "origin" ]]

Тестовий репо з декількома дистанційними:

$ git remote -v
origin  ../gitorigin (fetch)
origin  ../gitorigin (push)
upstream        ../gitupstream (fetch)
upstream        ../gitupstream (push)

Натискання на originдозволено:

$ git push origin
Enumerating objects: 3, done.
Counting objects: 100% (3/3), done.
Writing objects: 100% (3/3), 222 bytes | 222.00 KiB/s, done.
Total 3 (delta 0), reused 0 (delta 0)
To ../gitorigin
 * [new branch]      master -> master

Натискання на будь-який інший пульт не дозволено:

$ git push upstream
error: failed to push some refs to '../gitupstream'

Зауважте, що pre-pushсценарій гака може бути змінений, щоб, серед іншого, надрукувати повідомлення для stderr, кажучи, що натискання було вимкнено.


Гарна ідея! Без більш досконалого сценарію ви відключите натискання на всі віддалені Тхо.
— v01pe

1
@ v01pe так. Я оновив відповідь, щоб включити приклад сценарію. Насправді не потрібно багато для фільтрації натискань на одну гілку. Оболонка oneliner могла б зробити.
— Родольфо Карвальо

4

Загальне твердження "Git відмовиться переходити на неоголене сховище" не відповідає дійсності. Git буде відмовлятись від перенаправлення до неочищеного віддаленого сховища лише у тому випадку, якщо ви намагаєтесь натиснути зміни, які знаходяться на тій самій гілці, що і перевірена робоча директорія віддаленого сховища.

Ця відповідь дає просте пояснення: https://stackoverflow.com/a/2933656/1866402

(Я додаю це як відповідь, оскільки в мене ще недостатньо репутації, щоб додати коментарі)


оголене сховище не має перевіреного робочого каталогу за визначенням. Ви можете натиснути на певну гілку на ній.,
— Ед Рандалл,

1

Якщо ви вже маєте дистанційне налаштування і просто хочете завадити собі робити щось на кшталт випадкового натискання безпосередньо на masterабо release/production, ви можете запобігти цьому git config.

# prevent pushing to branch: master
$ git config branch.master.pushRemote no_push

# prevent pushing to branch: release/production
$ git config branch.release/production.pushRemote no_push

Для запису no_pushне є спеціальною назвою. Це лише назва будь-якої неіснуючої гілки. Таким чином, ви можете використовувати, $ git config branch.master.pushRemote create_a_pr_and_do_not_push_directly_to_masterі це буде добре працювати.

Більше інформації: git-config pushRemote


0

Якщо у вас є контроль над сховищем, ви можете досягти цього, використовуючи дозволи. Користувач, який отримує сховище, не повинен мати дозволу на запис у головне сховище.


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