Thursday, March 18, 2010

Setup a Git server on Windows machine, with MSysGit and CopSSH.

Update: Gitblit is an easier choice to do this!

I switched to Git from SVN recently, not for fun or fashion but for performance. I was involved in a big project with thousands of files and dozens of sub-projects. The result was, each operation takes longer time than I could bear. I'm not a patient person, so I tried to find better solutions and there Git is :)

I work for a big company and therefore a centralized-repository working pattern is best suited to my team. I have to prepare a central server before we can really switch to Git. But it seems Git was born in Linux and is not so friendly to Windows, which is the mandatory platform I have to use. The gift-MSysGit ripped git-daemon, therefore the simplest, though not the best, option is gone. I googled around, with a cygwin solution and a MSysGit one. I have a small team, so I don't need Gitosis yet, and MSysGit impressed me a lot, so tried the 2nd way.

Tim Davis did a great job making the solution work, but the description is somehow confusing to me, as I'm both new to Git and SSH. So I present my steps here, hope it helps people with just M$ Windows background.

You'll need 2 WinXP boxes (or virtual boxes) doing the setup, 1 as server and 1 as client. I used CopSSH 5.4p1 (file name Copssh_3.1.0_Installer.exe), and MSysGit 1.7.0.2 (file name Git-1.7.0.2-preview20100309.exe). Putty 0.60 is used to generate keys and test connections.

On Server Box

1. install CopSSH
Be sure to install it to a folder without space in its name. I used C:\SSH. Then just press next until it finishes.


2. install MSysGit

Be sure to install it to a folder without space in its name. I used C:\Git. The default values suits me well.
3. Config CopSSH
a. I would like to user a separate user for git access. So create a user from command line


net user git userspassword /add

b. Then, goto "Start | Programs | Copssh | 01. Activate a user" to activate the user.

Note, you should clear the 2nd checkbox, we'll generate keys later.

c. goto C:\SSH\etc folder, open the sshd_config file using wordpad (or notepad2), don't use notepad, it's a UNIX format file. Remove the leading # character for item "PasswordAuthentication" and change the "yes" to "no". Also you can review the rest of the config file and change if necessary. For me, most of the default settings works fine.


d. Goto C:\SSH\home\git\.ssh folder, create a file named authorized_keys. Open this file using wordpad.

e. Install/extract Putty if you have not. Invoke PUTTYGEN.EXE to generate a pair of keys:
I used a 4096 bit SSH2 key. Save the private key to a folder and remember it. We'll use it later. Copy the content in the text box labelled with "Public key for pasting...." to the wordpad window you opened at step d, and save it, close the wordpad.

f. (Re)Start SSH Server. You can either reboot your PC, or use below command line:
net stop opensshserver
net start opensshserver

g. Now it's ready to test SSH connection. Invoke Putty.EXE, put localhost as host name, if you changed port in step c, don't forget to change it here. Navigate to Connection/SSH/Auth node, press the "Browse" button to select the private file you generated and stored in step e, as shown below:
You can save the settings to save you some typing next time. Google it if you don't know how. Now press "Open" button, you will see a warning window on first connection, press "Yes" to accept the key. Then a block terminal window pops up, with prompt "login as:", input "git" (without quote), and you should be prompted for a key-phrase if you set it when you saved the private key. Note, this is not the password of the git user you created during step a!!!. And with some luck (which you don't need if you know what you are doing), you should see some window similar to this:

If you've made it, congratulations, the hardest part is behind you. If you don't see it, then please review carefully what you have missed.

h. invoke a command window if you have not (where have you executed those "net xxx" commands?), and type
cd /d %USERPROFILE%
echo export HOME=/c/SSH/home/git > .bashrc

i. goto C:\SSH\home\git folder, open the .bashrc file (yes, the same name as in the above line). Insert below line to the first line: (AGAIN, THIS IS A UNIX FILE!)
export PATH=/cygdrive/c/Git/bin:/cygdrive/c/Git/libexec/git-core:$PATH

NOTE, above "export PATH=..." must be in the same line!



4. setup a Git repository.

goto C:\SSH\home\git and make a folder named test.git. Right click the folder and select "Git Bash" from context menu. (What? You did not choose the explorer integration? Goto start menu, find Git|Git Bash, and use command line to goto this folder). Then input below lines:
$ git init --bare
Initialized empty Git repository in C:/SSH/home/git/test.git/

Now the server setup is DONE. You might need a cup of coffee of a cake to ease your nerve.

Special notes no 2003 server. It seems the sshd will experience error if the user account used to login is not a member of administrator (thanks for the comment from Raphael). So if you experience problem, try to add the user's account to administrator group and try again.


On Client PC

Setting up multiple accounts


I just realized that I forgot the part on how to make your repository accessible to multiple users. It's simple once you have gone through above steps: adding another user is just to generate another key-pair, and put the public-key into the authorized-key file. That's all. Then the new user can access your repository. (just follow the client setup, no other server settings needs to be changed).



I know a better way is to use Gitosis, but I'm not able to run it without cygwin yet :(


1. Install MSysGit, as on server. You can choose any folder you like (better a folder without space in it's path).

2. Test connection, using Putty. Change the host name and port as in your environment. Don't forget the Connection | SSH | Auth node setting. Copy the private key file to client machine and point the file in this node. Then press "Open" button, you should find it similar to what you have experienced at step g above. But this time, after you logged in, you are actually logged in to another computer! After you logged in, type "git", and see if you have the familiar git help screen before you. If you see

-bash: git: command not found
then please check if you have step i done correctly.

3. Opne a command window, type


cd /d %USERPROFILE%
md .ssh

Then use windows explorer to open this folder. create a files (id_rsa.pub) if they don't exist.

4. Fire up PuttyGen.EXE again, load the private key you used at step 2. Paste the content of the text box to file id_ras.pub, and use menu "Conversions | Export OpenSSH key" to save to the folder you created at step 3, in name "id_rsa". Now the folder %USERPROFILE"\.ssh should have at least 2 files: id_rsa and id_rsa.pub

input "yes" to accept the remote key. Then you should get an echo "something"

6. Now we are ready to clone the empty project we created at server


$ git clone ssh://git@tst/SSH/home/git/test.git

Initialized empty Git repository in D:/g/gt/test/.git/
warning: You appear to have cloned an empty repository.


Now you can make some change and push it back

$cd test
$vim readme.txt
$git add readme.txt
$git commit -a -m "first commit"



[master (root-commit) f216dfe] first commit











1 files changed, 1 insertions(+), 0 deletions(-)
















create mode 100644 readme.txt




$ git push origin master
Counting objects: 3, done.
Writing objects: 100% (3/3), 236 bytes, done.
Total 3 (delta 0), reused 0 (delta 0)
To ssh://git@oti-tst/SSH/home/git/test.git
* [new branch] master -> master


Congratulations, you can clone and push back. It's not as hard as it sounds, after all :D


5. create a empty folder and invoke the Git Bash and navigate to that folder. Type







ssh git@your.remote.host "echo something"

33 comments:

  1. This was really useful. Thanks!

    ReplyDelete
  2. This comment has been removed by the author.

    ReplyDelete
  3. This comment has been removed by the author.

    ReplyDelete
  4. very helpful.

    a few notes from my side:

    1. using windows 2003, copssh 3.1.1 encountered sshd.exe: *** fatal error - could not load user32, Win32 error 1114. Solved by putting user/git into administrators group.

    2. I used 1024 for puttygen. 4096 was very... tiring.

    3. I started with a new .bashrc in server home/git because the #comments in .bashrc causes massive command not found reply.

    and again. Thank you very much.

    ReplyDelete
  5. Wat about if we want to have multiple accounts? we ahve to setup more ssh user?
    anything about setting up web client too such as gitorious or gitosis

    ReplyDelete
  6. For multiple users, there are 2 solutions. The easier one (maybe the harder one?) is to setup Gitosis. But unfortunately it needs cygwin, and I'm not able to run it without cygwin yet.

    The 2nd one is easier if you have a small group and have gone through above steps. You ask every one who needs write access to your repository to generate a pair of keys and send public key to you. You can just put the key in the authorized_keys file. That's all, you don't need to setup another windows account anymore.

    ReplyDelete
  7. really nice. but I got a problem. I'm on Windows 7.

    when I try to launch the command git.. I obtain this error message :

    /usr/bin/git.exe: error while loading shared libraries: pthreadGC2.dll:
    cannot open shared object file: No such file or directory


    if I launch the command from msys.bat (came with msysgit) it works. (but I'm logged with the user : SvcCOPSSH and not git)

    ReplyDelete
  8. oups.. wrong error message : it's

    git@admin-PC /cygdrive/c/msysgit/msysgit
    $ git
    /cygdrive/c/msysgit/msysgit/bin/git.exe: error while loading shared libraries: libiconv2.dll: cannot open shared object file: No such file or directory

    ReplyDelete
  9. I don't have win7 thus can not re-produce your problem. But I encounter this problem when I use windows 2003. Promote your "git" user to administrator should solve the problem.

    ReplyDelete
  10. still the same problem. I'll reinstall it and try again. What is the worst case if I have the default account ? (SvcCOPSSH) instead of git ?

    ReplyDelete
  11. oups. it worst. I reinstall Copssh and now I got this error

    C:\Windows\system32>net start opensshserver
    System error 1069 has occurred.

    The service did not start due to a logon failure.


    Lucky me I did that in VirtualBox.

    ReplyDelete
  12. When you connect through Putty, you don't put any windows login there, CopSSH will verify your pub/private key pairs and start a shell under the user name you specified in CopSSH and put you in that sheel session.
    To start CopSSH service, you need a windows account. That's why two accounts, and they can share 1 if you like, though it's not a good idea.

    All the magic git is doing is to use the SSH stream to pass data. So basically this means, once you can connect through Putty, and you can start git on server, everything should work.

    I hope this msg helps you do troubleshooting.

    ReplyDelete
  13. one question. I can understand the CopSSh installation. We want a ssh server on Windows. Fine. wsysgit on the client and server.. I can understand too. but could I just create a repository with wsysgit on the server and change the permissions on the folder for the user git ?

    ReplyDelete
  14. I found my problem. the PATH variable. I needed to add : mingw\lib

    git@admin-PC /home/git
    $ echo $PATH
    /cygdrive/c/msysgit/msysgit/:/cygdrive/c/msysgit/msysgit/git:/cygdrive/c/msysgit/msysgit/libexec/git-core/:/bin:/cygdrive/c/Windows/System32:/cygdrive/c/Windows:.:/cygdrive/c/msysgit/msysgit/mingw/bin/

    ReplyDelete
  15. I'm glad you figured it out by urself. I don't have any folder similar to mingw/lib on my installation, might be OS difference. On winxp, most of the dll&exe files are located under the "bin" folder.

    If you want to control access, you have to use a different users for logged in users, then you can use windows standard access permission control to handle the rest. If you need more fine-grained tweak, you have to map pubkey to win-user. In general this model works for small team within more or less trusted zone. If you want better solution, I guess you have to go for cygwin+gitosis.

    ReplyDelete
  16. Thank you for your write up on hosting a Git repository. It went very smooth for me up until I tried to clone the bare repository. I was getting the following error.

    fatal: protocol error: bad line length character: decl

    After some searching I found a forum that mentions that if there are any extra characters returned from an SSH command that it could cause this error message. I tried it out with the command

    $ ssh my-username@my-server-address echo testing commands

    and I got 30 or so messages that looked to be setting environment variables and looked something like this

    declare -x ALLUSERPROFILE="C:\\Docume....
    declare -x COMPUTERNAME="E1234"

    with

    testing commands

    at the bottom. I checked my .bashrc and .bash_profile file for commands that would produce this and realized that 'export' and 'PATH=/cygdrive/c/Git/bin:/cygdrive/c/Git/libexec/git-core:$PATH' need to be on the same line. That's what I get for not carefully following instructions (Step 3i). The 'export' without any argument was causing all the environment variables to be displayed to the screen with each SSH command. The only reason I post it here is to prevent others who are following somewhat blindly, like me, from wasting time on such a simple mistake.

    ReplyDelete
  17. tcmaster, I follow your idea and came out with a guide : cygwin + gitosis on Windows

    http://jerabi.com/sdionne/blog/2010/09/06/git-repository-server-gitosis-on-win7-working/

    ReplyDelete
  18. Hi Brikki, thanks for the input and sorry for the confusion. I did put the export in the same line as the rest of the PATH=..., but since it's too long, browser will wrap it and causes confusion. I'll update the content to mention this.

    ReplyDelete
  19. Hello,

    I am setting things on Windows 2003 server.
    I followed your steps well.
    But when I try to clone repository with following commnand

    git clone -v ssh://Administrator@localhost/SSH/home/Administrator/test.git e:/gt1/

    it gives me following output

    cloning into e:/gt1...
    fatal: protocol error: bad line length character: Micr

    When I write following in GIT Bash shell

    $ SSH Administrator@Ganesh

    It returns following.

    Microsoft Windows[Version 5.2.3790]
    (C)Copyright 1985-2003 Microsoft Corp.

    is it something that might be creating problem?

    in above error it shows "Micr" is it taking from "Microsoft"???

    Can anyone here has any idea about it?

    Thanks.

    ReplyDelete
  20. it seems you are not having bash as shell but cmd.exe instead. Maybe you shall check your .bashrc and .bash_profile file to see if all the settings are correct, it's in home folder by default. Also checkout Briki's reply in this thread, it might help.

    ReplyDelete
  21. I had so much trouble installation gitosis, that I did a blog about that. To help others to follow a procedure that should work 100%.

    Maybe you cna find a step that you missed. http://jerabi.com/sdionne/blog/2010/09/06/git-repository-server-gitosis-on-win7-working/

    ReplyDelete
  22. Hello survivant and Anonymus,

    Thanks for reply.
    I checked .bashrc and .bash_profile and it seems fine to me.

    Also in my .bashrc line with export command is on 1 single line only as per said by Brikki.

    Also when I used following command

    SSH Administrator@Ganesh echo testing commands

    It gives me following as output.

    Microsoft Windows[Version 5.2.3790]
    (C)Copyright 1985-2003 Microsoft Corp.

    Is there any other way to check the problem?

    Thanks in advance.

    ReplyDelete
  23. To debug this issue, you need to understand how the communication is done. Git is using console stream to transfer data. So a shell (bash) that support this is very important. From what you have described, it seems the key exchange and validation has already passed. So when OpenSSH is trying to start a shell, it started cmd.exe instead of the bash. Please check the if the openssh is configured correctly.

    Also, if above did not help, can you try to empty the .bashrc (backup it first), and put some command like "ls -l -a" (similar command like windows' "dir /a") and see what happens? (remember this is actually a unix file, try use some editor that supports unix line ending)

    ReplyDelete
  24. Hello tcmaster,
    Thanks for the reply.

    I found the problem in COPSSH control panel I changed shell from Windows to Linux and that error go away..

    Now coming other problem.. when I clone repository it starts cloning it but than hangs..

    how to track it?

    in new folder it creates repository with ".git" folder

    but when I right click on it and select "GIT bash here" it opens shell in that directory with (unknown) beside it as given below

    Administrator@Ganesh /e/websites/gtClone/gt1 (unknown)

    but actually it should show (master) instead.

    Does anyone know to track this?

    Thanks in advance.

    ReplyDelete
  25. It seems you made too much config to SSH server before it works. With the info you provided, it's really hard to identify where is the problem. Just remember, git uses ssh stream to transfer data. If you have have config the server to insert any any unexpected info in response, it won't work.

    A hint, when using git clone, there is a --verbose parameter, which might show you what is git doing. Hope this helps.

    ReplyDelete
  26. thank you very much. It's working just great !

    ReplyDelete
  27. Gitosis requires some fixes to be useful on real world projects. Specifically: adding support for spaces in filenames and fixing Find usage syntax (for Windows). I made a patch kit and submitted it to the author. Sadly, he has a rather peculiar notion that spaces in filenames are errors (and therefore he will never support them). He's a nice guy with a great product, but that is a pitifully small minded attitude.

    ReplyDelete
  28. Gitosis sounds like a deadly social disease! ;-)

    ReplyDelete
  29. Fantastic work. We stand on your shoulders.

    Anyone know how to move the git repositories out of the ssh/home folder on the root drive where I installed them? I'd prefer to have all my repos on a data drive. Thanks again!

    ReplyDelete
  30. Never mind :) - I found it: https://www.itefix.no/i2/node/12281

    ReplyDelete
  31. It was ok. ,
    I have created Server in Virtual XP. now when it restarted and login back it shows only git user no default. Administrator user i can access.

    how to switch back to Administrator?

    ReplyDelete
    Replies
    1. Sorry, I don't quite understand what you mean. But if you are still struggling on this approach, check out a much easier new way: http://java2cs2.blogspot.de/2012/08/setup-gitblit-on-windows-server-2003.html

      Delete
  32. in your process,

    i. goto C:\SSH\home\git folder, open the .bashrc file (yes, the same name as in the above line). Insert below line to the first line: (AGAIN, THIS IS A UNIX FILE!)
    export PATH=/cygdrive/c/Git/bin:/cygdrive/c/Git/libexec/git-core:$PATH

    should be like:

    i. goto C:\SSH\home\git folder, open the .bashrc file (yes, the same name as in the above line). Insert below line to the first line: (AGAIN, THIS IS A UNIX FILE!)
    export PATH=/cygdrive/c/SSH/bin:/cygdrive/c/SSH/libexec/git-core:$PATH

    but whole your article is wonder!! thanks!

    ReplyDelete