Napotkałem ten sam problem z witryną, którą hostowałem w hostowanym pakiecie hostingu. Oni również dają ci ssh
dostęp, ale niestety nie mają git
zainstalowanego i nawet nie dają ci dostępu do uruchamiania gcc
, co utrudnia pobranie i zainstalowanie git dla twojego użytkownika.
Jedynym sposobem na obejście tych ograniczeń było skopiowanie plików binarnych git z innego komputera, który je miał. Być może to samo rozwiązanie zadziałałoby dla Ciebie i Twojego współdzielonego hosta GoDaddy. Oto co zrobiłem:
Najpierw dowiedz się, jaką architekturę ma Twój serwer. W moim przypadku był to 32-bit (i386). Oto kilka sposobów, aby to zrozumieć:
# uname -a
Linux ___.myserverhosts.com 2.6.18-128.1.6.el5PAE #1 SMP Wed Apr 1 10:02:22 EDT 2009 i686 i686 i386 GNU/Linux
# file /bin/echo
/bin/echo: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), for GNU/Linux 2.6.9, dynamically linked (uses shared libs), for GNU/Linux 2.6.9, stripped
Następnie musisz znaleźć inny komputer z systemem Linux o tej samej architekturze i zainstalowanym na nim git. Nie muszą nawet uruchamiać tej samej dystrybucji lub wersji systemu Linux, o ile mają taką samą architekturę i można znaleźć potrzebne pliki binarne i biblioteki.
Aby znaleźć lokalizację głównego pliku binarnego git:
> which git
/usr/local/bin/git
Niektóre inne ważne pliki binarne (jak git-receive-pack
) również znajdują się w tym samym katalogu, więc zalecamy po prostu skopiowanie wszystkich, /usr/local/bin/git*
aby upewnić się, że otrzymujesz wszystko, czego potrzebujesz.
Inne ważne pliki, od których zależy git, znajdują się w katalogu „libexec” gdzieś w systemie źródłowym. Jeśli nie skopiujesz ich, może pojawić się zaskakujący komunikat o błędzie podczas próby wykonania git push
, podobnie jak ja:
git: 'index-pack' is not a git-command. See 'git --help'.
Aby znaleźć katalog zawierający podstawowe biblioteki git na docelowym hoście, możesz użyć tego:
> git --exec-path
/usr/local/libexec/git-core
Polecam najpierw skopiować te pliki, a następnie spróbować uruchomić git, aby sprawdzić, czy narzeka na brakujące biblioteki współdzielone. Jeśli tak się nie stanie, jesteś (prawdopodobnie) dobry. Jeśli tak, czytaj dalej. (Nie ma potrzeby kopiowania przez biblioteki współdzielone, jeśli już istnieją na hoście docelowym i są poprawną wersją.)
Można kopiować pliki z scp
, rsync
, ftp
, czy cokolwiek innego są wygodne. Użyłem scp
czegoś takiego:
> ssh target_host 'mkdir -p ~/bin ~/libexec'
> scp /usr/local/bin/git* target_host:~/bin
> scp -r /usr/local/libexec/git-core target_host:~/libexec
Następnie ssh do target_host. Musisz dodać kilka takich wierszy do ~/.bashrc
:
export PATH=$PATH:~/bin
export LD_LIBRARY_PATH=~/lib
export GIT_EXEC_PATH=~/libexec/git-core
Jeśli zapomnisz ten krok, możesz być zaskoczony tym błędem, gdy wykonujesz git push
:
git-receive-pack: command not found
Jest to udokumentowane w Git FAQ na git.or.cz:
Zasadniczo problem polega na tym, że 'git-receive-pack' nie znajduje się w domyślnej zmiennej $ PATH na zdalnym końcu.
...
- Upewnij się, że masz skonfigurowaną prawidłową ścieżkę
.bashrc
(nie tylko .bash_profile
)
GIT_EXEC_PATH
jest udokumentowany na man git
:
--exec-path
Path to wherever your core git programs are installed.
This can also be controlled by setting the GIT_EXEC_PATH
environment variable. If no path is given, git will print
the current setting and then exit.
Źródło nowego ~/.bashrc
. Teraz spróbuj uruchomić git
.
Oto, co dał mi pierwszy raz:
> git
git: error while loading shared libraries: libcrypto.so.4: cannot open shared object file: No such file or directory
Udało mi się ustalić lokalizację bibliotek współdzielonych do skopiowania, uruchamiając to na komputerze źródłowym:
> ldd /usr/local/bin/git
libz.so.1 => /usr/lib/libz.so.1 (0xb7fcf000)
libcrypto.so.4 => /lib/libcrypto.so.4 (0xb7ee4000)
libpthread.so.0 => /lib/tls/libpthread.so.0 (0xb7ed2000)
libc.so.6 => /lib/tls/libc.so.6 (0xb7da6000)
libgssapi_krb5.so.2 => /usr/lib/libgssapi_krb5.so.2 (0xb7d92000)
libkrb5.so.3 => /usr/lib/libkrb5.so.3 (0xb7d2d000)
libcom_err.so.2 => /lib/libcom_err.so.2 (0xb7d2a000)
libk5crypto.so.3 => /usr/lib/libk5crypto.so.3 (0xb7d08000)
libresolv.so.2 => /lib/libresolv.so.2 (0xb7cf5000)
libdl.so.2 => /lib/libdl.so.2 (0xb7cf1000)
/lib/ld-linux.so.2 (0xb7fe8000)
W moim przypadku miałem tylko skopiować /lib/libcrypto.so.4
na na ~/lib
na mój target_host
i wszystko było w porządku.
Teraz powinieneś pracować git
na swoim wspólnym serwerze hostingowym i powinieneś być w stanie na niego naciskać!
Teraz musisz albo utworzyć nowe repozytorium git i drzewo pracy na swoim serwerze, albo skopiować istniejące repozytorium / drzewo pracy.
Nawiasem mówiąc, nie sądzę, aby w tym przypadku na serwerze było to, czego potrzebujesz, ponieważ powiedziałeś, że chcesz wdrożyć rzeczywiste pliki treści (w przeciwieństwie do samych config HEAD objects/ refs/
plików, które byłyby zawarte w nagim repozytorium), ilekroć chcesz robisz git push
.
toolmantim.com wyjaśnia różnicę między zwykłym repozytorium git a zwykłym repozytorium:
Domyślne repozytorium git zakłada, że będziesz go używać jako katalogu roboczego, więc git przechowuje rzeczywiste pliki repozytorium w katalogu .git obok wszystkich plików projektu. Zdalne repozytoria nie potrzebują kopii plików w systemie plików w przeciwieństwie do kopii roboczych, wszystko czego potrzebują to delta i binarne elementy tego samego repozytorium. To właśnie „gołe” znaczy git. Tylko samo repozytorium.
Zakładam na chwilę, że już utworzyłeś katalog w swoim target_host
miejscu, w którym chcesz wdrożyć swoją stronę internetową (lub cokolwiek, co wdrażasz). Nazwijmy ten katalog ~/www/my_site
. Być może masz nawet ftp na wszystkich swoich plikach ~/www/my_site already
. (Nieważne, czy masz, czy nie jest to ważne.) Przyjmuję również na chwilę, że nie skopiowałeś już podkatalogu .git ~/www/my_site
(jeśli tak, to powinno działać dobrze).
Ponieważ na serwerze docelowym nie ma już zainicjowanego repozytorium git, pierwszym krokiem byłoby utworzenie jednego:
> cd ~/www/my_site
> git init
Następnie z dowolnego hosta, który ma repozytorium z najnowszymi zmianami, które chcesz wdrożyć (jak sądzę, z twojego pudełka programistycznego), po prostu musisz zrobić coś takiego, aby wdrożyć:
> git push --all ssh://username@target_host:port/~/www/my_site/.git
Możesz zobaczyć takie ostrzeżenie, jeśli Twoje repozytorium target_host
nie jest jeszcze aktualne:
> warning: updating the current branch
> warning: Updating the currently checked out branch may cause confusion,
> warning: as the index and work tree do not reflect changes that are in HEAD.
> warning: As a result, you may see the changes you just pushed into it
> warning: reverted when you run 'git diff' over there, and you may want
> warning: to run 'git reset --hard' before starting to work to recover.
> warning:
> warning: You can set 'receive.denyCurrentBranch' configuration variable to
> warning: 'refuse' in the remote repository to forbid pushing into its
> warning: current branch.
> warning: To allow pushing into the current branch, you can set it to 'ignore';
> warning: but this is not recommended unless you arranged to update its work
> warning: tree to match what you pushed in some other way.
> warning:
> warning: To squelch this message, you can set it to 'warn'.
> warning:
> warning: Note that the default will change in a future version of git
> warning: to refuse updating the current branch unless you have the
> warning: configuration variable set to either 'ignore' or 'warn'.
(W normalnym git
wykorzystaniu nigdy widzisz tę wiadomość, jak sądzę, bo jesteś normalnie popychanie do gołych repozytoriach. Ale ponieważ nasza zdalnego repozytorium w tym przypadku jest to normalny repo zarówno z drzewa pracy i indeksu, git
jest zrozumiałe zaniepokojenie, że może coś zepsuć.)
Myślę jednak, że możemy bezpiecznie ustawić opcję „ignoruj” na twoim serwerze, ponieważ prawdopodobnie nie będziesz dokonywał żadnych zmian bezpośrednio w repozytorium. (Wszystkie zatwierdzenia powinny prawdopodobnie pochodzić z repozytorium programisty, a następnie zostać przekazane na serwer).
Więc ustaw dalej, aby nie wyświetlać ostrzeżenia za każdym razem, gdy naciskasz:
> ssh target_host 'cd ~/www/my_site/; git config receive.denyCurrentBranch ignore'
Te push
się jedynie aktualizacje indeks jednak NIE pliki w drzewie samej pracy. Aktualizacja tych plików to jednak tylko część tego, co próbujemy zrobić, więc nasze zadanie nie jest zakończone, dopóki nie wypiszemy git
zawartości indeksu do samego drzewa pracy, w następujący sposób:
> ssh target_host 'cd ~/www/my_site/; git reset --hard'
(Uwaga: wszelkie zmiany, które mogły zostać wprowadzone w drzewie pracy na serwerze, zostaną zastąpione przez zawartość repozytorium).
Postępowałem również zgodnie z sugestią Mattikusa i stworzyłem pilota dla mojego serwera:
> git remote add h9 ssh://username@target_host:port/~/www/my_site/.git
Teraz muszę tylko wdrożyć:
> git push --all --force h9
> ssh remote_host 'cd ~/www/my_site/; git reset --hard'
Posunąłem się nawet tak daleko, że wrzuciłem te polecenia do skryptu, który nazwałem, script/deploy
więc za każdym razem, gdy chcę wdrożyć, mam tylko jedno polecenie do uruchomienia.
Daj mi znać, jeśli znajdziesz jakieś błędy w tej instrukcji lub znasz lepsze rozwiązanie.