Como configurar um repo git existente para ser compartilhado por um grupo UNIX

98

Eu tenho um repositório git existente (um simples) que até agora só podia ser escrito por mim. Quero abri-lo para algum grupo de usuários do UNIX, foo, para que todos os membros de foo possam enviar por push. Estou ciente de que posso configurar facilmente um novo repositório git com:

git init --bare --shared=group repodir
chgrp -R foo repodir

Mas preciso da operação equivalente para um diretório de repositório existente .

Pistos
fonte
4
uma excelente resposta para essa pergunta no ServerFault (outro site StackOverflow).
Zearin

Respostas:

114

Tente isso para fazer um repositório existente repodirfuncionar para usuários no grupo foo:

chgrp -R foo repodir                 # set the group
chmod -R g+rw repodir                # allow the group to read/write
chmod g+s `find repodir -type d`     # new files get group id of directory
git init --bare --shared=all repodir # sets some important variables in repodir/config ("core.sharedRepository=2" and "receive.denyNonFastforwards=true")
David Underhill
fonte
14
Eu acrescentaria que você provavelmente também deve definir config.sharedRepository = true na configuração do repo. kernel.org/pub/software/scm/git/docs/git-config.html
Pistos
1
Isso é muito parecido com o que eu estava fazendo sozinho, mas eu queria obter alguma confirmação externa. Obrigado. :) Eu também esperava que houvesse um clone git --shared = group do tipo, mas a opção --shared do clone faz algo completamente diferente.
Pistos
5
Você pode usar o git init --sharedcomando em um repo existente para definir o valor de configuração. Você também precisa chmodexecutar o comando para obter as permissões dos arquivos corretas.
Spencer
1
Para confirmar isso também ajuda se você estiver em uma bagunça porque alguém fez um git pulletc. como root em vez de como www-dataou o que quer que seja o proprietário e, como resultado, você obtém error: insufficient permission for adding an object to repository database .git/objects. Achei que tivesse corrigido a propriedade de todos os arquivos / diretórios que estavam errados usando finde -type d/ type -f, mas apenas esse método eliminou o erro (provavelmente porque um arquivo em algum subdiretório não era gravável em grupo?)
William Turrell
1
O umask do usuário ainda parece se aplicar a arquivos recém-criados. É isso que você esperava? Eu acho que a documentação do core.sharedRepositorymencionaria isso - parece inútil sem os usuários tornando todos os seus grupos de arquivos graváveis.
Sam Brightman
47

No dir repo, execute os seguintes comandos:

git config core.sharedRepository group
chgrp -R foo repodir
chmod -R g+w repodir

Editar: para resolver a confusão frequente, groupé uma palavra-chave real, você não deve substituí-la pelo nome do grupo.

Kixorz
fonte
25
Onde groupNÃO está o nome do grupo :)
Pierre de LESPINAY
7
Os arquivos de objeto e pacote devem ser imutáveis; eles devem ter permissões 444 / r - r - r--.
CB Bailey
3
Depois de tentar git config core.sharedRepository devem seguida, digitando git configeu chegar fatal: bad config value for 'core.sharedrepository' in .git/configem git version 1.7.0.4(e possivelmente versões depois)
Kzqai
3
git config core.sharedRepository group groupnão é o nome do grupo, mas o valor real!
kixorz
Se você cometeu o erro de usar o nome do seu grupo em vez de "grupo", apenas abra .git / config no editor de texto e edite a linha core.sharedRepository para dizer "grupo".
Tom
43

Mesclando as respostas @David Underhill e @kixorz , fiz minha própria solução (definitiva).

É para repositórios básicos e não básicos. Existem apenas pequenas diferenças entre eles, mas desta forma é mais clara.

BARE REPOSITORY

cd <repo.git>/                            # Enter inside the git repo
git config core.sharedRepository group    # Update the git's config
chgrp -R <group-name> .                   # Change files and directories' group
chmod -R g+w .                            # Change permissions
chmod g-w objects/pack/*                  # Git pack files should be immutable
find -type d -exec chmod g+s {} +         # New files get directory's group id

Onde:

  • <repo.git>é o diretório do repositório vazio, normalmente no servidor (por exemplo my_project.git/).
  • <group-name>é o nome do grupo para usuários git (por exemplo, usuários ).

REPOSITÓRIO NON-BARE

cd <project_dir>/                         # Enter inside the project directory
git config core.sharedRepository group    # Update the git's config
chgrp -R <group-name> .                   # Change files and directories' group
chmod -R g+w .                            # Change permissions
chmod g-w .git/objects/pack/*             # Git pack files should be immutable
find -type d -exec chmod g+s {} +         # New files get directory's group id

Onde:

  • <project_dir>é o diretório do projeto que contém a .gitpasta.
  • <group-name>é o nome do grupo para usuários git (por exemplo, usuários ).
Andrea
fonte
Como Charles disse, também faça: chmod g-w objects/pack/*(se for um repositório não .git/
vazio
aqui, como podemos encontrar o nome do grupo ou como criar o nome do grupo?
Sujithrao
'chmod g + s find . -type d' gera um errounable to execute /bin/chmod: Argument list too long
Dr.X
Como @ Dr.X observou, chmod g+s `find . -type d`não é escalonável. Usofind -type d -exec chmod g+s {} +
hagello de
Acho que todos os objetos soltos também devem ser somente leitura com base no estado pré-compartilhado. Talvez algo parecido chmod g-w objects/*/*. Não tenho certeza sobre o subdiretório info, pois está vazio para este repositório.
Eric
3

Isso provavelmente não é necessário, mas vale a pena ressaltar que git init --bare --sharedtambém define a opção denyNonFastForwards .

git config receive.denyNonFastForwards true

O significado desta opção é o seguinte:

receive.denyNonFastForwards

Se você rebase commits que você já fez push e então tentar empurrar novamente, ou então tentar enviar um commit para um branch remoto que não contém o commit para o qual o branch remoto aponta atualmente, você será negado. Em geral, essa é uma boa política; mas no caso do rebase, você pode determinar que sabe o que está fazendo e pode forçar a atualização do branch remoto com um sinalizador -f para seu comando push.

(de http://git-scm.com/book/en/v2/Customizing-Git-Git-Configuration )

nerfologista
fonte
1

Além das respostas acima sobre permitir que um grupo leia / escreva, você também precisa adicionar o usuário ao grupo (diga "foo").

sudo usermod -a -G [groupname] [username]

Nota: você terá que primeiro criar o usuário se ele não existir

Sarvagya Kumar
fonte