How so show SSH key in git log? - linux

We are using git with gitolite and sometimes my users change there names with
git config --global user.name
so I would like to see some more details in the log to find out if someone has change the name setting but is still the same workstation (ssh key). Anyway to do this?

IMO, the ssh keys in commit messages will be a complete overkill. You don't want your commit messages to look up completely screwed some x days later, just because each of them contain different ssh keys.
You should have a look at git notes to supplement your commits with additonal information. In the notes, you can add the committer's Username and other environment variables.
Worst case, you can add the ssh keys in git notes, though I am not sure how that stops malicious users who currently fake commits in some other user's name from trying to hack around and get hold of some other user's ssh keys.
More importantly, if developers are doing this in complicity with each other, the ssh keys will be completely insufficient.
Assuming you are on linux, you can get the username using
printenv | grep USER
You can similarly choose other details you need from the environment that you need to put into the git note.
Next, you can write a post-commit hook which automatically adds all this information post every commit.

In the gitolite 3.x you can IIRC add a VREF constraint that committer (or author) matches SSH key used, or HTTP auth user (I guess it uses the username part of user.email, or whole of user.email).
Though this is discouraged as a pre-receive hook (i.e. block), you can set up post-receive hook instead to log and compare committers with auth usernames.

Related

Change the Account that is used to git pull origin

I have tried to check several SO questions and answers but still unable to resolve my concern. The scenario is this:
User A with Git Account A git cloned repo to freshly installed server.
Because of this, the git account that was registered on the server was User A.
(If I understood it correctly. please correct me if I am wrong in this part)
Now I would like to use User B with Git Account B as commiter/puller/pusher to the server.
What I tried was to change the user and email with the following command:
git config --global user.name "userb"
git config --global user.email "userb#gmail.com"
git config --local user.name "userb"
git config --local user.email "userb#gmail.com"
git config user.name "userb"
git config user.email "userb#gmail.com"
On 3 separate occasions. Still unable to resolve my concern. I can see the updated user and email with command git config --list, git config user.name and git config user.email so I know that the value did change.
If this is not possible, I am also considering to remove the accounts all together and enter the user/email and password when pulling/pushing without removing the git history.
You are doing the wrong thing. You are trying to change the user name used to mark your commits, instead you have to reset your git user account credentials.
Under Linux issue git config --unset credential.helper, under Windows remove the credentials by the Windows Credentials Manager.
User A with Git Account A git cloned repo to freshly installed server.
Because of this, the git account that was registered on the server was User A.
No. There are two common / standard transport mechanisms that a Git client (like git clone) will use to talk to a Git server:
https: the client provides a user name and additional authentication data (password, token, whatever); or
ssh: the client provides a public key; the server looks up the public key to determine who the client claims to be,1 and challenges the client with a task that can only be completed by someone holding the corresponding private key, so that if the client does complete the task, the claim must have been accurate.
These mechanisms are provided not by Git itself, but by some sort of access wrapper: a web server, or an sshd.
At this point, the client is authenticated to the server, and only now does Git itself actually enter the picture. The server's Git software hands to the client every commit in the server's repository (so that the client has all the commits), and shows to the client all the branch names (which the client then changes into remote-tracking names, so that the client has all the commits and no branches at all). Then the client disconnects from the server, creates one branch in the new Git repository, and is done.
The only thing retained here is the URL that the client used to reach the server. This URL is retained in the Git repository the client just created. Unless the server keeps logs (via its web server and/or sshd),2 the server now has no record at all of the client.
The next time the client needs to talk to the server, the client provides the URL, which it has saved conveniently under the short name origin.3 This URL may contain a user name, especially if you used an https:// URL.
So: check the URL, using git remote -v, to find out which protocol you are using and whether, if that protocol is https://, there is a user name embedded in the URL. If so, you can edit or remove that user name. If not, and the URL is an https:// URL, proceed with Antonio Petricca's answer. If the URL is an ssh:// one, look into ssh authentication.
1On some servers, the user logs in using their own account, but for the usual GitHub, GitLab, and Bitbucket setups, the user provides the generic user name git. Hence the server has to use this public-key trick to figure out who the user is claiming to be.
2Most servers do keep logs, but that's up to the server, and they're used at most for auditing and security. It does not affect future attempts to connect to the server, unless, e.g., the people running the server find your connection alarming and block it.
3You can choose some other name, but there is no reason to do that, and presumably you did not.

Read only access to svn repository via ssh (svn+ssh)

We desire to make subversion repositories read only. Doing this for a single repository in a subversion instance did not work regarding ssh. ssh access appears to bypass the controls of svn.
Followed the suggestions here:
Read-only access of Subversion repository
Write access should be restricted but that did not happen.
The repository is still write accessible despite changes to the repository for read only.
The easiest way to restrict access (assuming there are no users who require write access) is to remove the w (write) bit on the files in the SVN repo.
chmod -R gou-w /path/to/svn-repo
That will prevent writes at the filesystem / OS level.
If some users still require access, you can create separate svn+ssh endpoints for each user class that map to different users on the host server, using group write vs other write bits to determine which group has access to affect writes:
mkgrp writers-grp
chgrp -R writers-grp /path/to/svn-repo
chmod ug+w /path/to/svn-repo
chmod o-w /path/to/svn-repo
I would then register the SSH keys for writers against the writing user on the server, and prevent password access.
The "read-only" users could be allowed a well-known password.
This isn't as "clever" or "elegant" as configuring the SVN server configs, but it works pretty darned well as long as the users keep their SSH keys secret.
Restrict commit access with a start-commit hook.
Description
The start-commit hook is run before the commit transaction is even
created. It is typically used to decide whether the user has commit
privileges at all.
If the start-commit hook program returns a nonzero exit value, the
commit is stopped before the commit transaction is even created, and
anything printed to stderr is marshalled back to the client.
Input Parameter(s)
The command-line arguments passed to the hook program, in order, are:
Repository path
Authenticated username attempting the commit
Colon-separated list of capabilities that a client passes to the server, including depth, mergeinfo, and log-revprops (new in
Subversion 1.5).
Common uses
Access control (e.g., temporarily lock out commits for some reason).
A means to allow access only from clients that have certain
capabilities.

Store credentials for git commands using HTTP

I would like to store Git credentials for git pulls permenantly on a linux machine, and git credential.helper doesn't work ( I think because I'm not using SSH ) - I get that error "Fatal: could not read password for 'http://....': No such device or address". Given that I'm not the administrator of the repository and only HTTP is allowed for authentication, and fortunately I don't care about the safety of the password. What can I do to put the git pull command in a bash file and avoid prompting the user for password?
I hope there is a way around it.
Two things wrong with this question:
Most repositories such as GitHub require HTTPS. Even if you try to clone over
HTTP, it just switches it on the backend to HTTPS and pushes require it as
well.
Pulls don’t require a password, unless it’s a private repo. Like #1, since
you’ve given no info about your repo it’s hard to comment further on this.
Now, what I do is this:
git config --global credential.helper store
Then the first time you push it will ask for your credentials. Once you’ve
entered them they are stored in ~/.git-credentials. Note that they are stored
in plain text, you have been advised.
I'm assuming that your repository requires authentication for pulls, or else git wouldn't ask you for a password for the pull.
The recommended way to bypass the user password prompt is to create an SSH key on that machine, add the public key to the git server, then use the SSH url for the remote instead of the HTTP/S url. But since you specifically said:
I don't care about the safety of the password
you can actually just specify the password inline for the git pull like this:
git pull http://username:password#mygithost.com/my/repository

Modifying the gitolite repository url

I have gitolite installed. I'm able to administer it fine. I've added a few new repos, and a few pub keys. Installed as 'git#domain.com' and a repo added for a user as repo.git.
Does it have to be git#domain.com:repo.git to access, or is there a way to indicate the user in the url?
Possibly something like user#domain.com:repo.git or git.domain.com/user/repo.git for example?
No, it has to be git#domain.com because the user is always the same: the git account you are using to install and administer gitolite on your server.
The actual user is deduced from the public key you are using when making your ssh call.
If you registered that key with the user.pub file representing said public key named after the user's login, then gitolite will be able to identify you.
For more, see "how gitolite uses ssh".
If you look in the authorized_keys file, you'll see entries like this (I chopped off the ends of course; they're pretty long lines):
command="[path]/gitolite-shell sitaram",[more options] ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEA18S2t...
command="[path]/gitolite-shell usertwo",[more options] ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEArXtCT...
First, it finds out which of the public keys in this file match the incoming login.
Once the match has been found, it will run the command given on that line; e.g., if I logged in, it would run [path]/gitolite-shell sitaram.
So the first thing to note is that such users do not get "shell access", which is good!
When gitolite-shell gets control, it looks at the first argument ("sitaram", "usertwo", etc) to determine who you are. It then looks at the SSH_ORIGINAL_COMMAND variable to find out which repository you want to access, and whether you're reading or writing.
Now that it has a user, repository, and access requested (read/write), gitolite looks at its config file, and either allows or rejects the request.

How to make git not ask for password at pull?

I have the following setup:
A server (centOS) with git and a repository for a project on the same server.
What I need to do is to be able to pull from the repository without being asked for password (because is annoying).
Note: I am logged as root when I pull.
Can anyone help me with that?
There are a few options, depending on what your requirements are, in particular your security needs. For both HTTP and SSH, there is password-less, or password required access.
HTTP
==============
Password-Less
Useful for fetch only requirements, by default push is disabled. Perfect if anonymous cloning is the intention. You definitely shouldn't enable push for this type of configuration. The man page for git-http-backend contains good information, online copy at http://www.kernel.org/pub/software/scm/git/docs/git-http-backend.html. It provides an example of how to configure apache to provide this.
User/password in .netrc or url embedded
Where .netrc files are using in the form:
machine <hostname> login <username> password <password>
And embedded urls would be in the form:
http://user:pass#hostname/repo
Since git won't do auth for you, you will need to configure a webserver such as apache to perform the auth, before passing the request onto the git tools. Also keep in mind that using the embedded method is a security risk, even if you use https since it is part of the url being requested.
If you want to be able to pull non-interactive, but prevent anonymous users from accessing the git repo, this should be a reasonably lightweight solution using apache for basic auth and preferably the .netrc file to store credentials. As a small gotcha, git will enable write access once authentication is being used, so either use anonymous http for read-only, or you'll need to perform some additional configuration if you want to prevent the non-interactive user from having write access.
See:
httpd.apache.org/docs/2.4/mod/mod_auth_basic.html for more on configuring basic auth
www.kernel.org/pub/software/scm/git/docs/git-http-backend.html for some examples on the apache config needed.
SSH
==============
Passphrase-Less
Opens up for security issues, since anyone who can get a hold of the ssh private key can now update the remote git repo as this user. If you want to use this non-interactively, I'd recommend installing something like gitolite to make it a little easier to ensure that those with the ssh private key can only pull from the repo, and it requires a different ssh key pair to update the repo.
See github.com/sitaramc/gitolite/ for more on gitolite.
stromberg.dnsalias.org/~strombrg/ssh-keys.html - for creating password less ssh keys:
May also want to cover managing multiple ssh keys: www.kelvinwong.ca/2011/03/30/multiple-ssh-private-keys-identityfile/
Passphase protected
Can use ssh-agent to unlock on a per-session basis, only really useful for interactive fetching from git. Since you mention root and only talk about performing 'git pull', it sounds like your use case is non-interactive. This is something that might be better combined with gitolite (github.com/sitaramc/gitolite/).
Summary
==============
Using something like gitolite will abstract a lot of the configuration away for SSH type set ups, and is definitely recommended if you think you might have additional repositories or need to specify different levels of access. It's logging and auditing are also very useful.
If you just want to be able to pull via http, the git-http-backend man page should contain enough information to configure apache to do the needful.
You can always combine anonymous http(s) for clone/pull, with passphrase protected ssh access required for full access, in which case there is no need to set up gitolite, you'll just add the ssh public key to the ~/.ssh/authorized_keys file.
See the answer to this question. You should use the SSH access instead of HTTPS/GIT and authenticate via your SSH public key. This should also work locally.
If you're using ssh access, you should have ssh agent running, add your key there and register your public ssh key on the repo end. Your ssh key would then be used automatically. This is the preferred way.
If you're using https access, you one would either
use a .netrc file that contains the credentials or
provide user/pass in the target url in the form https://user:pass#domain.tld/repo
With any of these three ways, it shouldn't ask for a password.

Resources