- 所有文章/
托管简单 Git 服务器的一些尝试
本文目录
前言 #
本文是我打算为 stagit 配置一个简单的 Git 服务器作为后端的尝试,如果仅仅在局域网内玩一下是可以的,对于公网上的服务器还不够安全的,最终我并没有使用此方法。
文中仅在局域网测试,未绑定域名,请勿在公网服务器尝试,以免被骇。
设置用户 #
添加一个新用户,仅用于操作 Git 存储库
# 添加用户
sudo adduser git
# 切换用户
su git && cd && pwd
# 会输出
/home/git
# 设置 SSH 公钥目录
mkdir .ssh \
&& chmod 700 .ssh \
&& touch .ssh/authorized_keys \
&& chmod 600 .ssh/authorized_keys
生成或添加自己的 SSH 公钥(生成部分略)
# 比如 https://github.com/torvalds.keys
curl https://github.com/[username].keys -o ssh.keys \
cat ssh.keys >> ~/.ssh/authorized_keys
rm ssh.keys
初始化存储库 #
将每个单独的存储库都放在 git 用户目录下,比如
/home/git/repo1.git # 远程存储库 1
/home/git/repo2.git # 远程存储库 2
初始化裸存储库
git init --bare repo1.git
尝试提交 #
假设本地存储库 repo1 已经有一些提交记录
# 格式 ssh://<username>@<hostname>:<ssh-port><repo-path>
# 比如
git remote add origin ssh://git@192.168.1.101:22222/home/git/repo1.git
git push origin master
设置 Git Shell #
Git Shell 是一个为 Git 命令设计的轻量级 shell,它限制文中 git 用户对系统的访问权限,只允许它执行 Git 命令。
# 切换回普通用户
su [your-username]
# 一般情况下应该输出为空
cat /etc/shells | grep git-shell
# 输出 git shell 路径
which git-shell
# 添加一行 git shell 路径
sudo vim /etc/shells
# 设置 git 用户的默认 shell
sudo chsh git -s $(which git-shell)
禁止 SSH 转发 #
现在用户仍然可以通过 SSH 转发来访问任何可达的 Git 服务器,建议禁止 SSH 转发
echo -n "no-port-forwarding,no-X11-forwarding,no-agent-forwarding,no-pty " | cat - ~/.ssh/authorized_keys > temp && mv temp ~/.ssh/authorized_keys
禁用交互式 Shell #
以前我们访问 GitHub 服务器的时候,可以看到用户 Shell 被禁用的提示信息:
ssh -T git@github.com
Hi DejavuMoe! You've successfully authenticated, but GitHub does not provide shell access.
在我们搭建的 Git 服务器上,也可以设置
# 切换到 git 用户
su git
# 创建 git shell 执行命令目录
mkdir $HOME/git-shell-commands
# 设置禁用交互式 Shell 提示
cat > $HOME/git-shell-commands/no-interactive-login << EOF
#!/bin/sh
printf '%s\n' "Hi Dejavu Moe! You've successfully authenticated to your personal git server, "
printf '%s\n' "but we do not provide interactive shell access."
exit 128
EOF
# 赋予可执行权限
chmod +x $HOME/git-shell-commands/no-interactive-login
现在可以测试一下
ssh -T git@192.168.1.101 -p22222
# 输出
Hi Dejavu Moe! You've successfully authenticated to your personal git server,
but we do not provide interactive shell access.
Git Daemon 配置 #
上面通过 SSH 访问的 Git 服务器访问地址类似这样,看起来又长又臭
ssh://git@192.168.1.101:22222/home/git/repo1.git
我们可以使用 Git Daemon 守护进程守护 Git 服务器,现在的访问地址类似这样
这个地址适合在局域网分享 Git 存储库,没有身份认证和鉴权
# git://<hostname>:9418/<repo-name>
git://192.168.1.101:9418/repo1.git
git daemon
在Debian 或 Ubuntu 上是作为 git core
的一部分安装的,用法为:
git daemon [--reuseaddr] [--base-path=<path>] [--export-all] [--verbose] [--enable=<service>] [--max-connections=<n>] [--timeout=<seconds>] [--init-timeout=<seconds>] [--strict-paths] [--user=<user>] [--group=<group>] [--detach] [--pid-file=<file>] [--syslog] [--listen=<address>] [--port=<port>] [<directory>...]
对于每个参数的详细说明可以去问 ChatGPT
创建一个 Systemd 服务
sudo vim /etc/systemd/system/git-daemon.service
示例
[Unit]
Description=Start Git Daemon
[Service]
ExecStart=/usr/bin/git daemon --reuseaddr --base-path=/home/git/ ---max-connections=20 --detach --syslog --listen=0.0.0.0 --listen=::0 --port=9418 /home/git/
Restart=always
RestartSec=500ms
StandardOutput=syslog
StandardError=syslog
SyslogIdentifier=git-daemon
User=git
Group=git
[Install]
WantedBy=multi-user.target
然后
# 重载配置
sudo systemctl daemon-reload
# 开机自启 git daemon
sudo systemctl enable git-daemon
# 启动 git daemon
sudo systemctl start git-daemon
# 查看 git daemon 状态
sudo systemctl status git-daemon
在每个存储库添加一个文件即可让 git daemon 访问,比如
cd /home/git/repo1.git && touch git-daemon-export-ok
上面的 git daemon 命令带上 --export-all
参数运行,就不必在每个存储库里创建 git-daemon-export-ok
了。最户,在服务器上开放 9418/tcp
端口,就可以在其他机器访问了
git clone git://192.168.1.101:9418/repo1.git
参考信息: