Git değiştirildiyse git içindeki dosya ve dizin izinlerini nasıl geri yükleyebilirim?


278

Git kasam var. Tüm dosya izinleri git'in düşündüklerinden farklıdır, bu nedenle hepsi değiştirilmiş olarak görünür.

Dosyaların içeriğine dokunmadan (sadece izinleri değiştirmek istiyorum) tüm dosya izinlerini git olması gerektiğini düşündüğü şekilde nasıl ayarlayabilirim?


Yanıtlar:


572

Git, dosya iletimini izler ve kullanarak yamalar oluştururken izin değişikliklerini gösterir git diff -p. Yani ihtiyacımız olan tek şey:

  1. ters yama oluştur
  2. sadece izin değişikliklerini dahil et
  3. yamayı çalışma kopyamıza uygulayın

Tek astar olarak:

git diff -p -R --no-ext-diff --no-color \
    | grep -E "^(diff|(old|new) mode)" --color=never  \
    | git apply

Ayrıca git config bir takma ad olarak ekleyebilirsiniz ...

git config --global --add alias.permission-reset '!git diff -p -R --no-ext-diff --no-color | grep -E "^(diff|(old|new) mode)" --color=never | git apply'

... ve şu yolla çağırabilirsiniz:

git permission-reset

Eğer kabuk ise bash, tırnak işareti 'yerine "tırnak işareti kullandığınızdan emin olun !git, aksi takdirde gitçalıştırdığınız son komutla değiştirilir .

Basitçe kullanarak Bunu belirttiğin için @Mixologic için Thx -Rüzerinde git diff, hantal sedkomut artık gereklidir.


3
OS X'deyim, bu çalışmıyor. Sorunun git uygulamasında olduğunu belirledim. Dosya izinleri değişikliklerini uygulamaz.
pepper_chico

15
Oh, işe yaradı, depo kökünden farklı bir dizinden uygulamaya çalışıyordum. git uygula sadece orada çalışır.
pepper_chico

6
Sed yapmak ters yapmak yerine sadece "git diff -p -R" yapmak için bir nedeni var mı?
Mixologic

6
@RobQuist muhqu'in komutu kullanılırken yerel değişikliklerim kaldırılmadı
oturum açma

17
Ben alıyorumfatal: unrecognized input
Tieme

120

Deneyin git config core.fileMode false

Gönderen git configadam sayfası:

core.fileMode

False olursa, dizin ve çalışan kopya arasındaki yürütülebilir bit farkları yok sayılır; FAT gibi bozuk dosya sistemlerinde kullanışlıdır. Bkz. Git-update-index (1) .

Git-clone (1) veya git-init (1), havuz oluşturulduğunda uygun olması durumunda core.fileMode öğesini problayacak ve varsayılan olarak true olacaktır.


Teşekkürler, ben bunu yaptım. Çok cvs izinleri izlememesi için kullanılır, bu yüzden bu çalışır.
Dale Forester

3
@shovas: Bunun yardımcı olduğuna sevindim. Linux ve Windows arasında depo paylaşırken de benzer bir sorun yaşadım. BTW: bu sorunuza cevap verdiyse, lütfen yanıtı doğru olarak işaretleyin.
Tim Henigan

O olması mümkün mü git checkout origin/mastersetleri dosya izinleri benim yerel çalışma kopyasına sunucuya işledi? ArangoDB için V8'i her oluşturduğumda, dosya izinleri değiştirilir, böylece erişim tüm yapı klasörüne reddedilir (yükseltilmiş haklarla bile; Windows 7+). Oluşturma işlemine devam edebilmek için önce tüm yerel dosya izinlerini düzeltmem gerekiyor. Bunu da core.filemode falsedüzeltebilir misiniz? Git'in Windows makinemde Linux izinlerini ayarladığından şüpheleniyorum. Derleme komut dosyaları onları koruyabilir ve yeni oluşturulan dosyalara aynı izinleri uygulayabilir ...
CodeManX

Im ayarlamak filemodeiçin herhangi bir olumsuz olup olmadığını merak false!
kevoroid

11

Git, yürütülebilir komut dosyaları dışındaki dosya izinlerini depolamaz. Dosya sahipliğini ve izinlerini kaydetmek için git-cache-meta gibi bir şey kullanmayı düşünün .

Git yalnızca iki tür modu depolayabilir: 755 (yürütülebilir) ve 644 (yürütülebilir değil). Dosyanız 444 olsaydı depolardı 644.


14
Üzgünüm, ama bu yanlış. Git gerçekten de izinleri izler.
Will

4
Kabaca doğrudur, bkz. Git.wiki.kernel.org/index.php/ContentLimitations . Ayarlanan tam izinler, sunucuya ve muhtemelen istemciye umaskve bir yapılandırma ayarına bağlı olarak görünür , bkz. Stackoverflow.com/a/12735291/125150 .
Motti Strom

12
@ Hayır, hayır. Yorumunuzun çok fazla oy aldığını düşünemiyorum.
eis

@ Bu, kabaca doğrudur. Dokümanlar başına...a mode of 100644, which means it’s a normal file. Other options are 100755, which means it’s an executable file; and 120000, which specifies a symbolic link. The mode is taken from normal UNIX modes but is much less flexible — these three modes are the only ones that are valid for files (blobs) in Git (although other modes are used for directories and submodules).
esmail

9
git diff -p \
| grep -E '^(diff|old mode|new mode)' \
| sed -e 's/^old/NEW/;s/^new/old/;s/^NEW/new/' \
| git apply

çoğu durumda çalışır, ancak meld gibi harici fark araçlarınız varsa --no-ext-diff

git diff --no-ext-diff -p \
    | grep -E '^(diff|old mode|new mode)' \
    | sed -e 's/^old/NEW/;s/^new/old/;s/^NEW/new/' \
    | git apply

benim durumumda gerekliydi



0

Windows'ta cygwin'den git kullanıyorum, git applyçözüm benim için çalışmıyor. İşte benim çözümüm, chmodizinlerini sıfırlamak için her dosyada çalıştırın .

#!/bin/bash
IFS=$'\n'
for c in `git diff -p |sed -n '/diff --git/{N;s/diff --git//g;s/\n/ /g;s# a/.* b/##g;s/old mode //g;s/\(.*\) 100\(.*\)/chmod \2 \1/g;p}'`
do
        eval $c
done
unset IFS


-1

git diff -pmuhqu'in cevabında kullanılan tüm tutarsızlıkları göstermeyebilir.

  • Cygwin'de sahip olmadığım dosyalar için gördüm
  • eğer mod değişiklikleri tamamen göz ardı edilir core.filemodeise false(MSysGit için varsayılan budur)

Bu kod bunun yerine meta verileri doğrudan okur:

(set -o errexit pipefail nounset;
git ls-tree HEAD -z | while read -r -d $'\0' mask type blob path
do
    if [ "$type" != "blob" ]; then continue; fi;
    case "$mask" in
    #do not touch other bits
    100644) chmod a-x "$path";;
    100755) chmod a+x "$path";;
    *) echo "invalid: $mask $type $blob\t$path" >&2; false;;
    esac
done)

Üretim sınıfı olmayan bir astar (maskeleri tamamen değiştirir):

git ls-tree HEAD | perl -ne '/^10(0\d{3}) blob \S+\t(.+)$/ && { system "chmod",$1,$2 || die }'

("$ '\ 0'" kredisi http://transnum.blogspot.ru/2008/11/bashs-read-built-in-supports-0-as.html adresine verilir )


-2

Yapılacak en kolay şey izinleri geri değiştirmek. @Kroger'ın belirttiği gibi git sadece yürütülebilir bitleri izler. Yani muhtemelen chmod -x filenamedüzeltmek için koşmanız gerekiyor (ya +xda gerekli olan buysa).


İşte bir örnek git show: diff --git a / OpenWatch / src / org / ale / openwatch / fb / FBUtils.java b / OpenWatch / src / org / ale / openwatch / fb / FBUtils.java dizini cd6fa6a..e5b0935 100644 Bu kalın yazı tipinde dosya izinleri vardır.
Conrado

Bu da benim için en kolay görünüyordu. Ne yazık ki, Conrado ile aynı sorunla karşılaştım - iznini olarak 100644değiştiremedim 100755. Ben bir aşağı oy hak ettiğini sanmıyorum; Git aşağı oylanmalıdır. Çok farklı seviyelerde çok farklı şekillerde kırılmış ...
jww

-2

etckeeperAracı izinleri ile işleyebilir:

etckeeper init -d /mydir

Bunu başka dizinler için de kullanabilirsiniz /etc.

Paket yöneticinizi kullanarak yükleyin veya yukarıdaki linkten kaynak alın.


4
İzinleri neye ayarlar? Git meta verilerini okumuyor veya Git'i çağırmıyorsa, OP'nin istediği şeyi yapmaz.
ivan_pozdeev
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.