Existe uma " exportação de git "(como"exportação de svn")?
tenho estado a pensar se existe uma boa solução de "exportação de git" que cria uma cópia de uma árvore sem o directório do repositório .git
. Há pelo menos três métodos que conheço:
-
git clone
seguido da remoção da pasta do repositório.git
. -
git checkout-index
alude a esta funcionalidade, mas começa com "basta ler a árvore desejada no índice..."o que não sei bem como fazer. -
git-export
é um script de terceiros que essencialmente, umgit clone
entra num local temporário seguido dersync --exclude='.git'
para o destino final.
svn export
pode ser a opção 1, porque ambos requerem que o directório de destino esteja vazio primeiro. Mas a opção 2 parece ainda melhor, assumindo que consigo descobrir o que significa ler uma árvore no índice.
30 answers
git archive
. Se você realmente precisa apenas da árvore expandida você pode fazer algo assim.
git archive master | tar -x -C /somewhere/else
A maior parte do tempo que eu preciso para 'exportar' algo do git, eu quero um arquivo comprimido em qualquer caso para que eu faça algo assim.
git archive master | bzip2 >source-tree.tar.bz2
Arquivo ZIP:
git archive --format zip --output /full/path/to/zipfile.zip master
git help archive
Para mais detalhes, é bastante flexível.
Esteja ciente de que mesmo que o arquivo não conterá o.git diretório, ele irá, No entanto, conter outros arquivos git-específicos escondidos como .gitignore,.gitatributes, etc. Se não os quiser no pacote, certifique-se que utiliza o atributo export-ignore em A.gitattributes file e commit this antes de fazer o seu arquivo. Leia mais...
Nota: Se estiver interessado em exportar o índice, o comando é
git checkout-index -a -f --prefix=/destination/path/
(ver a resposta do Greg Para mais detalhes)
git checkout-index -a -f --prefix=/destination/path/
A barra no final do caminho é importante, caso contrário, irá resultar em que os arquivos estão em /destino com um prefixo de 'caminho'.
Uma vez que numa situação normal o índice contém o conteúdo do repositório, não há nada de especial a fazer para "ler a árvore desejada no índice". Já lá está.
A bandeira -a
é necessária para verificar todos os ficheiros no índice (Não tenho a certeza o que significa omitir esta bandeira nesta situação, já que não faz o que eu quero). A bandeira -f
obriga a substituir quaisquer ficheiros existentes na saída, o que este comando normalmente não faz.
git archive
também funciona com repositório remoto.
git archive --format=tar \
--remote=ssh://remote_server/remote_repository master | tar -xf -
Para exportar um caminho particular dentro do repo adicione todos os caminhos que desejar como último argumento ao git, por exemplo:
git archive --format=tar \
--remote=ssh://remote_server/remote_repository master path1/ path2/ | tar -xv
Uma resposta de caso especial se o repositório estiver hospedado no GitHub.
Usa apenas svn export
.
svn
acessíveis para que possa usar svn export
como normalmente faria com alguns ajustes no seu url do GitHub.
Por exemplo, para exportar um repositório inteiro, observe como trunk
no URL substitui master
(ou qualquer que seja o o ramo principal do projecto está definido para):
svn export https://github.com/username/repo-name/trunk/
E você pode exportar um único arquivo ou mesmo um determinado caminho ou pasta:
svn export https://github.com/username/repo-name/trunk/src/lib/folder
Exemplo com jQuery JavaScript Library
O ramo HEAD
ou o ramo principal estará disponível usando trunk
:
svn ls https://github.com/jquery/jquery/trunk
O não-HEAD
Os ramos estarão acessíveis sob /branches/
:
svn ls https://github.com/jquery/jquery/branches/2.1-stable
Todas as marcas sob /tags/
da mesma forma:
svn ls https://github.com/jquery/jquery/tags/2.1.3
Do Manual do Git:
Usar o git-checkout-index para "exportar uma árvore inteira"
A capacidade do prefixo basicamente faz com que seja trivial usar o git-checkout-index como uma função de "exportação como árvore". Basta ler a árvore desejada no índice, e fazer:
$ git checkout-index --prefix=git-export-dir/ -a
Escrevi uma embalagem simples à volta {[1] } que podes usar assim:
git export ~/the/destination/dir
Se a pasta de destino já existir, terá de adicionar -f
ou --force
.
A instalação é simples; basta largar o script algures no seu PATH
, e certificar-se de que é executável.
Parece que isto é menos um problema com o Git do que com o SVN. Git só coloca um .a pasta git na raiz do repositório, enquanto o SVN coloca A.pasta svn em cada subdiretório. Então "exportação svn" evita a magia recursiva da linha de comandos, enquanto que com a recursão Git não é necessário.
O equivalente a
svn export . otherpath
Dentro de um acordo de recompra existente está
git archive branchname | (cd otherpath; tar x)
O equivalente a
svn export url otherpath
É
git archive --remote=url branchname | (cd otherpath; tar x)
Uso extensivamente submódulos git. Este trabalha para mim.
rsync -a ./FROM/ ./TO --exclude='.*'
Se não estás a excluir ficheiros com .gitattributes
export-ignore
então tenta.git checkout
mkdir /path/to/checkout/
git --git-dir=/path/to/repo/.git --work-tree=/path/to/checkout/ checkout -f -q
- f
Ao verificar os caminhos a partir do índice, não falhe depois de não se encontrar os itens; em vez disso, os itens não incorporados são ignorados.
E
- q
Evitar a verbose
Para além disso, poderá obter qualquer ramificação ou etiqueta ou de uma revisão de Commit específica, como no SVN, apenas adicionando o SHA1 (o SHA1 no Git é o equivalente ao número de revisão em SVN)
mkdir /path/to/checkout/
git --git-dir=/path/to/repo/.git --work-tree=/path/to/checkout/ checkout 2ef2e1f2de5f3d4f5e87df7d8 -f -q -- ./
O /path/to/checkout/
deve estar vazio, o Git não irá apagar nenhum ficheiro, mas irá sobrepor os ficheiros com o mesmo nome sem qualquer aviso
Actualização:
Para evitar o problema da decapitação ou para deixar intacto o repositório de trabalho ao usar o checkout para exportação com tags, branches ou SHA1, você precisa adicionar -- ./
no final
O dash duplo --
diz ao git que tudo depois dos traços são caminhos ou ficheiros, e também neste caso diz git checkout
para não alterar o HEAD
Exemplos:
Este comando irá obter apenas o directório libs e também o ficheiro readme.txt
desse commit
git --git-dir=/path/to/repo/.git --work-tree=/path/to/checkout/ checkout fef2e1f2de5f3d4f5e87df7d8 -f -q -- ./libs ./docs/readme.txt
Isto irá criar (sobrepor) {[14] } dois commits por trás da cabeça HEAD^2
git --git-dir=/path/to/repo/.git --work-tree=/path/to/checkout/ checkout HEAD^2 -f -q -- ./my_file_2_behind_HEAD.txt
Para obter a exportação de outro ramo
git --git-dir=/path/to/repo/.git --work-tree=/path/to/checkout/ checkout myotherbranch -f -q -- ./
Repare que {[16] } é relativo à raiz do repositório
Isto vai copiar todo o conteúdo, menos o .ficheiros dot. Eu uso isso para exportar projetos clonados git para o meu aplicativo git repo sem o .tretas.
Bash simples funciona muito bem.Cp-R./ path-to-git-repo /path/to/destination /
Atingi esta página frequentemente ao procurar uma forma de exportar um repositório git. A minha resposta a esta pergunta considera três propriedades que a exportação de svn tem por design em comparação com o git, uma vez que o svn segue uma abordagem centralizada do repositório:
- minimiza o tráfego para um local de repositório remoto, não exportando todas as revisões
- não inclui meta-informação na pasta de exportação
-
Exportar um determinado ramo usando svn é realizado por especificando o caminho apropriado
git clone --depth 1 --branch master git://git.somewhere destination_path rm -rf destination_path/.git
Ao construir uma determinada versão, é útil clonar um ramo estável como por exemplo --branch stable
ou --branch release/0.9
.
Tão simples como o clone, depois apaga o .pasta git:
git clone url_of_your_repo path_to_export && rm -rf path_to_export/.git
Só quero salientar que, no caso de seres
- exportar uma sub-pasta do repositório (foi assim que usei a funcionalidade de exportação do SVN)
- não há problema em copiar tudo desde essa pasta até ao destino de implantação
- e já que você já tem uma cópia de todo o repositório no lugar.
Então você pode apenas usar cp foo [destination]
em vez do git-archive master foo | -x -C [destination]
mencionado.
Para os utilizadores do GitHub, o método git archive --remote
não irá funcionar directamente, dado que o URL de exportação é efémero. Você deve perguntar ao GitHub a URL, e então baixar essa URL. curl
torna isso Fácil:
curl -L https://api.github.com/repos/VENDOR/PROJECT/tarball | tar xzf -
Isto dar-lhe-á o código exportado numa pasta local. Exemplo:
$ curl -L https://api.github.com/repos/jpic/bashworks/tarball | tar xzf -
$ ls jpic-bashworks-34f4441/
break conf docs hack LICENSE mlog module mpd mtests os README.rst remote todo vcs vps wepcrack
Editar
Se você quiser o código colocado em um diretório específico, existente (em vez do Aleatório do github):
curl -L https://api.github.com/repos/VENDOR/PROJECT/tarball | \
tar xzC /path/you/want --strip 1
Você pode arquivar um repo remoto em qualquer ficheiro de envio como zip.
git archive --format=zip --output=archive.zip --remote=USERNAME@HOSTNAME:PROJECTNAME.git HASHOFGITCOMMIT
Sim, Este é um comando limpo e limpo para arquivar o seu código sem qualquer inclusão do git no arquivo e é bom para passar sem se preocupar com qualquer histórico de commit do git.
git archive --format zip --output /full/path/to/zipfile.zip master
Bash-implementação do git-export.
Eu segmentei o .os processos de criação e remoção de arquivos vazios em sua própria função, com o objetivo de reutilizá-los na implementação do 'Git-archive' (será postado mais tarde).Eu também adicionei o '.o ficheiro do gitattributes para o processo, a fim de remover os ficheiros não procurados da pasta de exportação de destino. Incluiu a verbosidade no processo enquanto fazia a função' git-export ' mais eficiente.
EMPTY_FILE=".vazio";
function create_empty () {
## Processing path (target-dir):
TRG_PATH="${1}";
## Component(s):
EXCLUDE_DIR=".git";
echo -en "\nAdding '${EMPTY_FILE}' files to empty folder(s): ...";
find ${TRG_PATH} -not -path "*/${EXCLUDE_DIR}/*" -type d -empty -exec touch {}/${EMPTY_FILE} \;
#echo "done.";
## Purging SRC/TRG_DIRs variable(s):
unset TRG_PATH EMPTY_FILE EXCLUDE_DIR;
return 0;
}
declare -a GIT_EXCLUDE;
function load_exclude () {
SRC_PATH="${1}";
ITEMS=0; while read LINE; do
# echo -e "Line [${ITEMS}]: '${LINE%%\ *}'";
GIT_EXCLUDE[((ITEMS++))]=${LINE%%\ *};
done < ${SRC_PATH}/.gitattributes;
GIT_EXCLUDE[${ITEMS}]="${EMPTY_FILE}";
## Purging variable(s):
unset SRC_PATH ITEMS;
return 0;
}
function purge_empty () {
## Processing path (Source/Target-dir):
SRC_PATH="${1}";
TRG_PATH="${2}";
echo -e "\nPurging Git-Specific component(s): ... ";
find ${SRC_PATH} -type f -name ${EMPTY_FILE} -exec /bin/rm '{}' \;
for xRULE in ${GIT_EXCLUDE[@]}; do
echo -en " '${TRG_PATH}/{${xRULE}}' files ... ";
find ${TRG_PATH} -type f -name "${xRULE}" -exec /bin/rm -rf '{}' \;
echo "done.'";
done;
echo -e "done.\n"
## Purging SRC/TRG_PATHs variable(s):
unset SRC_PATH; unset TRG_PATH;
return 0;
}
function git-export () {
TRG_DIR="${1}"; SRC_DIR="${2}";
if [ -z "${SRC_DIR}" ]; then SRC_DIR="${PWD}"; fi
load_exclude "${SRC_DIR}";
## Dynamically added '.empty' files to the Git-Structure:
create_empty "${SRC_DIR}";
GIT_COMMIT="Including '${EMPTY_FILE}' files into Git-Index container."; #echo -e "\n${GIT_COMMIT}";
git add .; git commit --quiet --all --verbose --message "${GIT_COMMIT}";
if [ "${?}" -eq 0 ]; then echo " done."; fi
/bin/rm -rf ${TRG_DIR} && mkdir -p "${TRG_DIR}";
echo -en "\nChecking-Out Index component(s): ... ";
git checkout-index --prefix=${TRG_DIR}/ -q -f -a
## Reset: --mixed = reset HEAD and index:
if [ "${?}" -eq 0 ]; then
echo "done."; echo -en "Resetting HEAD and Index: ... ";
git reset --soft HEAD^;
if [ "${?}" -eq 0 ]; then
echo "done.";
## Purging Git-specific components and '.empty' files from Target-Dir:
purge_empty "${SRC_DIR}" "${TRG_DIR}"
else echo "failed.";
fi
## Archiving exported-content:
echo -en "Archiving Checked-Out component(s): ... ";
if [ -f "${TRG_DIR}.tgz" ]; then /bin/rm ${TRG_DIR}.tgz; fi
cd ${TRG_DIR} && tar -czf ${TRG_DIR}.tgz ./; cd ${SRC_DIR}
echo "done.";
## Listing *.tgz file attributes:
## Warning: Un-TAR this file to a specific directory:
ls -al ${TRG_DIR}.tgz
else echo "failed.";
fi
## Purgin all references to Un-Staged File(s):
git reset HEAD;
## Purging SRC/TRG_DIRs variable(s):
unset SRC_DIR; unset TRG_DIR;
echo "";
return 0;
}
Resultado:
$ git-export /tmp/rel-1.0.0
Adicionando".ficheiros ' vazios para pastas vazias: ... terminar.
Componente(s) do Índice de verificação: ... terminar.
Recolocar a cabeça e o índice:... terminar.
Purging Git-Specific component(s):...
' / tmp/rel-1, 0 / {.ficheiros ' buildpath}'... terminar.'
' / tmp/rel-1, 0 / {.ficheiros do projecto}... terminar.'
' / tmp/rel-1, 0 / {.ficheiros do gitignore... terminar.'
' / tmp/rel-1, 0 / {.ficheiros ... terminar.'
' / tmp/rel-1, 0 / {.os ficheiros GITATTRIBUTES}'... terminar.'
' / tmp/rel-1, 0 / {*.ficheiros... terminar.'
'/tmp/rel-1.0.0/ {*~}' ficheiros ... terminar.'
' / tmp/rel-1, 0 / {.*~}' arquivo ... terminar.'
' / tmp/rel-1, 0 / {*.ficheiros swp}... terminar.'
' / tmp/rel-1, 0 / {*.ficheiros swo... terminar.'
' / tmp/rel-1, 0 / {.DS_Store}" arquivo ... terminar.'
' / tmp/rel-1, 0 / {.configuração dos ficheiros'... terminar.'
' / tmp/rel-1, 0 / {.ficheiros vazios ... terminar.'
Feito.Componente(s) de arquivamento: ... terminar.
-rw-r--r-- 1 roda de administração 25445901 3 Nov 12:57 /tmp/rel-1.0.0.TGZ
Incorporei agora a funcionalidade ' git archive 'num único processo que faz uso da função' create_empty ' e de outras funcionalidades.
function git-archive () {
PREFIX="${1}"; ## sudo mkdir -p ${PREFIX}
REPO_PATH="`echo "${2}"|awk -F: '{print $1}'`";
RELEASE="`echo "${2}"|awk -F: '{print $2}'`";
USER_PATH="${PWD}";
echo "$PREFIX $REPO_PATH $RELEASE $USER_PATH";
## Dynamically added '.empty' files to the Git-Structure:
cd "${REPO_PATH}"; populate_empty .; echo -en "\n";
# git archive --prefix=git-1.4.0/ -o git-1.4.0.tar.gz v1.4.0
# e.g.: git-archive /var/www/htdocs /repos/domain.name/website:rel-1.0.0 --explode
OUTPUT_FILE="${USER_PATH}/${RELEASE}.tar.gz";
git archive --verbose --prefix=${PREFIX}/ -o ${OUTPUT_FILE} ${RELEASE}
cd "${USER_PATH}";
if [[ "${3}" =~ [--explode] ]]; then
if [ -d "./${RELEASE}" ]; then /bin/rm -rf "./${RELEASE}"; fi
mkdir -p ./${RELEASE}; tar -xzf "${OUTPUT_FILE}" -C ./${RELEASE}
fi
## Purging SRC/TRG_DIRs variable(s):
unset PREFIX REPO_PATH RELEASE USER_PATH OUTPUT_FILE;
return 0;
}
Nota:
- MASTER_DIR = uma verificação com os seus submódulos também verificados
- DEST_DIR = onde esta exportação irá acabar Se tiveres rsync, acho que serias capaz de fazer a mesma coisa com ainda menos dor de bola.
Pressupostos:
- Você precisa de correr isto a partir da pasta-mãe do MASTER_DIR (i. e. do CD MASTER_DIR .. )
- DEST_DIR is presumido como tendo sido criado. Isto é muito fácil de modificar para incluir a criação de um DEST_DIR se quiser
CD MASTER_DIR & & tar-zcvf ../DEST_DIR / export.alcatrao.GZ -- exclude=".git*" . && disco ../ DEST_DIR / & & tar xvfz export.alcatrao.GZ & rm export.alcatrao.gz
Isto irá copiar os ficheiros numa gama de commits (C A G) para um ficheiro tar. Nota: Isto só vai obter os arquivos commited. Não o repositório inteiro. Ligeiramente modificado a partir de aqui
Exemplo Histórico De Commit
A --> B --> C - > D - > E - > F --> G --> H --> I
git diff-tree -r --no-commit-id --name-only --diff-filter=ACMRT C~..G | xargs tar -rf myTarFile.tar
Página de Manual do git-diff-tree
-r --> repetir em sub-árvores
--no-commit-id --> git diff-tree produz uma linha com o ID de commit quando aplicável. Esta bandeira suprimiu o resultado do ID de commit.
--name-only --> Show only names of changed files.
--diff-filter=ACMRT -- > seleccione apenas estes ficheiros. veja aqui a lista completa dos ficheiros
C..G --> ficheiros nesta gama de commits
C~ --> incluir ficheiros do Commit C. não apenas ficheiros desde o Commit C.
/ xargs tar-rf myTarFile -- > saídas para tar
A minha preferência seria ter um alvo dist no seu Makefile (ou outro sistema de compilação) que exporta um arquivo distribuível do seu código (.tar.bz2, .postal, .jar, ou o que for apropriado). Se você estiver usando Autotools GNU ou os sistemas MakeMaker do Perl, eu acho que isso existe para você automaticamente. Caso contrário, recomendo vivamente a sua inclusão.
ETA (2012-09-06): Uau, más notas. Eu ainda acredito que é melhor construir suas distribuições com a sua compilação ferramentas em vez de sua ferramenta de controle de código fonte. Acredito na construção de artefactos com ferramentas. No meu trabalho atual, o nosso produto principal é construído com um alvo formiga. Estamos no meio de mudar os sistemas de controle de código fonte, e a presença deste alvo ant significa menos um aborrecimento na migração.#!/bin/sh
[ $# -eq 2 ] || echo "USAGE $0 REPOSITORY DESTINATION" && exit 1
REPOSITORY=$1
DESTINATION=$2
TMPNAME="/tmp/$(basename $REPOSITORY).$$"
git clone $REPOSITORY $TMPNAME
rm -rf $TMPNAME/.git
mkdir -p $DESTINATION
cp -r $TMPNAME/* $DESTINATION
rm -rf $TMPNAME
gitss() {
URL=[url:path]
TMPFILE="`/bin/tempfile`"
if [ "$1" = "" ]; then
echo -e "Use: gitss repo [tree/commit]\n"
return
fi
if [ "$2" = "" ]; then
TREEISH="HEAD"
else
TREEISH="$2"
fi
echo "Getting $1/$TREEISH..."
git archive --format=zip --remote=$URL/$1 $TREEISH > $TMPFILE && unzip $TMPFILE && echo -e "\nDone\n"
rm $TMPFILE
}
Alias for .gitconfig, a mesma configuração necessária (tome cuidado ao executar o comando dentro .git projects, it ALWAYS jumps to the base dir previously {[[6]} as said here , until this is fixed I personally preferred the função
ss = !env GIT_TMPFILE="`/bin/tempfile`" sh -c 'git archive --format=zip --remote=[url:path]/$1 $2 \ > $GIT_TMPFILE && unzip $GIT_TMPFILE && rm $GIT_TMPFILE' -
Eu acho que o post de @Aredridel Estava mais próximo, mas há um pouco mais disso - então eu vou adicionar isso aqui; a coisa é, em svn
, Se você está em uma subpasta de um repo, e você faz:
/media/disk/repo_svn/subdir$ svn export . /media/disk2/repo_svn_B/subdir
Então svn
irá exportar todos os arquivos que estão sob controle de revisão (que também poderia ter recém-Adicionado; ou status Modificado) - e, se você tiver outros "lixo" no diretório (e eu não estou contando .svn
subpastas aqui, mas visível coisas como .o
arquivos), vai não ser exportada; somente os arquivos registrados pelo Acordo de repo SVN serão exportados. Para mim, uma coisa boa é que esta exportação também inclui arquivos com alterações locais que ainda não foram comprometidos ; e outra coisa boa é que os prazos dos arquivos exportados são os mesmos que os originais. Ou, como svn help export
diz:
- exporta uma árvore de directórios limpa da cópia de trabalho indicada por PATH1, na revisão REV, se for indicado, caso contrário no trabalho, em PATH2. ... Se o REV não for especificado, todos os locais as mudanças serão preservadas. Os ficheiros que não estão sob controlo de versões irão não ser copiado.
Para perceber que git
não irá preservar as datas, compare a saída destes comandos (numa subpasta de um git
repo da sua escolha):
/media/disk/git_svn/subdir$ ls -la .
... e:
/media/disk/git_svn/subdir$ git archive --format=tar --prefix=junk/ HEAD | (tar -t -v --full-time -f -)
... e eu, em qualquer caso, reparo que git archive
faz com que todos os prazos do arquivo sejam os mesmos! Diz:
Arquivo Git comporta-se de forma diferente quando é dado um ID de árvore versus quando é dado um ID de commit ou ID de marca. No primeiro caso, o a hora atual é usada como a hora de modificação de cada arquivo no arquivo. Neste último caso, o tempo de compromisso registado no objeto de commit referenciado é usado em vez disso.
... mas aparentemente ambos os casos definem o " tempo de modificação de cada arquivo"; Assim Não preservando as datas reais desses arquivos!
Assim, a fim de também preserve os tempestamps, aqui está um script bash
, que na verdade é um "one-liner", embora um pouco complicado - assim abaixo é publicado em várias linhas:
/media/disk/git_svn/subdir$ git archive --format=tar master | (tar tf -) | (\
DEST="/media/diskC/tmp/subdirB"; \
CWD="$PWD"; \
while read line; do \
DN=$(dirname "$line"); BN=$(basename "$line"); \
SRD="$CWD"; TGD="$DEST"; \
if [ "$DN" != "." ]; then \
SRD="$SRD/$DN" ; TGD="$TGD/$DN" ; \
if [ ! -d "$TGD" ] ; then \
CMD="mkdir \"$TGD\"; touch -r \"$SRD\" \"$TGD\""; \
echo "$CMD"; \
eval "$CMD"; \
fi; \
fi; \
CMD="cp -a \"$SRD/$BN\" \"$TGD/\""; \
echo "$CMD"; \
eval "$CMD"; \
done \
)
Note que se assume que está a exportar o conteúdo no directório "actual" (acima, /media/disk/git_svn/subdir
) - e o destino para o qual está a exportar está um pouco inconveniente, mas está na variável de Ambiente DEST
. Lembre-se que, com este programa, deverá criar a pasta DEST
manualmente, antes de executar o programa acima do guião.
Depois do script ser executado, você deve ser capaz de comparar:
ls -la /media/disk/git_svn/subdir
ls -la /media/diskC/tmp/subdirB # DEST
... e espero ver o mesmo horário (para aqueles arquivos que estavam sob controle de versão).
Espero que isto ajude alguém. Saúde!De longe a maneira mais fácil que eu vi para fazê-lo (e funciona também em janelas) é git bundle
:
git bundle create /some/bundle/path.bundle --all
Veja esta resposta para mais detalhes: Como posso copiar o meu repositório de git da minha máquina do windows para uma máquina linux através de uma unidade usb?
Se você precisa de submódulos também, isso deve fazer o truque: https://github.com/meitar/git-archive-all.sh/wiki
Como eu entendo a pergunta, é mais sobre baixar apenas um determinado estado do servidor, sem história, e sem dados de outros ramos, em vez de extrair um estado de um repositório local (como muitos anwsers aqui fazem).
Isso pode ser feito assim:
git clone -b someBranch --depth 1 --single-branch git://somewhere.com/repo.git \
&& rm -rf repo/.git/
-
--single-branch
está disponível desde o Git 1.7.10 (abril de 2012). - É (era?) alegadamente defeituoso, mas para o caso de uma exportação, as questões mencionadas não devem questao.
Tenho a seguinte função de utilidade na minha.ficheiro bashrc: cria um pacote da ramificação actual num repositório git.
function garchive()
{
if [[ "x$1" == "x-h" || "x$1" == "x" ]]; then
cat <<EOF
Usage: garchive <archive-name>
create zip archive of the current branch into <archive-name>
EOF
else
local oname=$1
set -x
local bname=$(git branch | grep -F "*" | sed -e 's#^*##')
git archive --format zip --output ${oname} ${bname}
set +x
fi
}
A opção 1 não parece muito eficiente. E se não houver espaço no cliente para fazer um clone e então remover a pasta .git
?
git archive
(porque necessita de enviar um ficheiro .gitattributes
, e eu não quero gravar isto exclusão no repositório).
Aqui partilho a minha solução, semelhante à Opção 3, mas sem a necessidade de git clone
:
tmp=`mktemp`
git ls-tree --name-only -r HEAD > $tmp
rsync -avz --files-from=$tmp --exclude='fonts/*' . raspberry:
Mudar a linha rsync
para uma linha equivalente de compressão também funcionará como uma git archive
mas com uma espécie de opção de exclusão (como é pedido aqui).
Eu tenho outra solução que funciona bem se você tiver uma cópia local do repositório na máquina onde você gostaria de criar a exportação. Neste caso, mova-se para esta pasta do repositório e indique este comando:
GIT_WORK_TREE=outputdirectory git checkout -f
Isto é particularmente útil se você gerenciar um site com um repositório git e gostaria de obter uma versão limpa em /var/www/
. Neste caso, adicione este comando num script .git/hooks/post-receive
(hooks/post-receive
num repositório simples, o que é mais adequado neste situação)