<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE sect2 SYSTEM "../../../dtd/dblite.dtd">

<sect2 lang="en" id="git-shell(1)">
    <title>git-shell(1)</title>
    <date>2024-07-02</date>
<revhistory><revision><date>2024-07-02</date></revision></revhistory>
<indexterm>
<primary>git-shell(1)</primary>
</indexterm>
<simplesect id="git-shell(1)__name">
<title>NAME</title>
<simpara>git-shell - Restricted login shell for Git-only SSH access</simpara>
</simplesect>
<simplesect id="git-shell(1)__synopsis">
<title>SYNOPSIS</title>
<blockquote>
<literallayout><emphasis>chsh</emphasis> -s $(command -v git-shell) &lt;user&gt;
<emphasis>git clone</emphasis> &lt;user&gt;<emphasis>@localhost:/path/to/repo.git</emphasis>
<emphasis>ssh</emphasis> &lt;user&gt;<emphasis>@localhost</emphasis></literallayout>
</blockquote>
</simplesect>
<simplesect id="git-shell(1)__description">
<title>DESCRIPTION</title>
<simpara>This is a login shell for SSH accounts to provide restricted Git access.
It permits execution only of server-side Git commands implementing the
pull/push functionality, plus custom commands present in a subdirectory
named <emphasis>git-shell-commands</emphasis> in the user's home directory.</simpara>
</simplesect>
<simplesect id="git-shell(1)__commands">
<title>COMMANDS</title>
<simpara><emphasis>git shell</emphasis> accepts the following commands after the <emphasis>-c</emphasis> option:</simpara>
<variablelist>
<varlistentry>
<term>
<emphasis>git receive-pack &lt;argument&gt;</emphasis>
</term>
<term>
<emphasis>git upload-pack &lt;argument&gt;</emphasis>
</term>
<term>
<emphasis>git upload-archive &lt;argument&gt;</emphasis>
</term>
<listitem>
<simpara>
        Call the corresponding server-side command to support
        the client's <emphasis>git push</emphasis>, <emphasis>git fetch</emphasis>, or <emphasis>git archive --remote</emphasis>
        request.
</simpara>
</listitem>
</varlistentry>
<varlistentry>
<term>
<emphasis>cvs server</emphasis>
</term>
<listitem>
<simpara>
        Imitate a CVS server.  See <xref linkend="git-cvsserver(1)" />.
</simpara>
</listitem>
</varlistentry>
</variablelist>
<simpara>If a <emphasis>~/git-shell-commands</emphasis> directory is present, <emphasis>git shell</emphasis> will
also handle other, custom commands by running
"<emphasis>git-shell-commands/&lt;command&gt; &lt;arguments&gt;</emphasis>" from the user's home
directory.</simpara>
</simplesect>
<simplesect id="git-shell(1)__interactive_use">
<title>INTERACTIVE USE</title>
<simpara>By default, the commands above can be executed only with the <emphasis>-c</emphasis>
option; the shell is not interactive.</simpara>
<simpara>If a <emphasis>~/git-shell-commands</emphasis> directory is present, <emphasis>git shell</emphasis>
can also be run interactively (with no arguments).  If a <emphasis>help</emphasis>
command is present in the <emphasis>git-shell-commands</emphasis> directory, it is
run to provide the user with an overview of allowed actions.  Then a
"git&gt; " prompt is presented at which one can enter any of the
commands from the <emphasis>git-shell-commands</emphasis> directory, or <emphasis>exit</emphasis> to close
the connection.</simpara>
<simpara>Generally this mode is used as an administrative interface to allow
users to list repositories they have access to, create, delete, or
rename repositories, or change repository descriptions and
permissions.</simpara>
<simpara>If a <emphasis>no-interactive-login</emphasis> command exists, then it is run and the
interactive shell is aborted.</simpara>
</simplesect>
<simplesect id="git-shell(1)__examples">
<title>EXAMPLES</title>
<simpara>To disable interactive logins, displaying a greeting instead:</simpara>
<screen>$ chsh -s /usr/bin/git-shell
$ mkdir $HOME/git-shell-commands
$ cat &gt;$HOME/git-shell-commands/no-interactive-login &lt;&lt;\EOF
#!/bin/sh
printf '%s\n' "Hi $USER! You've successfully authenticated, but I do not"
printf '%s\n' "provide interactive shell access."
exit 128
EOF
$ chmod +x $HOME/git-shell-commands/no-interactive-login</screen>
<simpara>To enable git-cvsserver access (which should generally have the
<emphasis>no-interactive-login</emphasis> example above as a prerequisite, as creating
the git-shell-commands directory allows interactive logins):</simpara>
<screen>$ cat &gt;$HOME/git-shell-commands/cvs &lt;&lt;\EOF
if ! test $# = 1 &amp;&amp; test "$1" = "server"
then
        echo &gt;&amp;2 "git-cvsserver only handles \"server\""
        exit 1
fi
exec git cvsserver server
EOF
$ chmod +x $HOME/git-shell-commands/cvs</screen>
</simplesect>
<simplesect id="git-shell(1)__see_also">
<title>SEE ALSO</title>
<simpara>ssh(1),
<xref linkend="git-daemon(1)" />,
contrib/git-shell-commands/README</simpara>
</simplesect>
<simplesect id="git-shell(1)__git">
<title>GIT</title>
<simpara>Part of the <xref linkend="git(1)" /> suite</simpara>
</simplesect>
</sect2>
