Gitea的部署、备份及恢复

计算机技术
作者

zenggyu

发布于

2020-06-24

摘要
介绍如何部署Gitea,并对服务数据进行备份和恢复。

简介

本文将介绍如何在私有服务器上部署Gitea并对数据进行备份和恢复。Gitea有不同的部署方式,并且根据部署方式的不同,数据备份及恢复的方式也有所差异。本文将介绍如何通过Docker容器部署Gitea,以及如何在此基础之上对数据进行备份和恢复。为了简化有关说明和操作,本文将假定:

  • 用于自托管Gitea的服务器使用的是Linux操作系统,并且安装了Docker;
  • 使用默认配置来部署Gitea实例;
  • 所有操作都使用系统root用户执行。

注:除了Gitea之外,本文附录部分也记录了自托管GitLab服务的有关操作方法,供有需要的读者参考。需要知道的是,GitLab提供的功能比Gitea更多,但它对服务器配置的要求也更高。

部署

Docker Hub的Gitea官方库上提供了多个版本的Gitea镜像;使用以下指令可以获取最新的稳定版镜像:

docker image pull gitea/gitea

如果服务器没有外网连接,那么可以先在有外网连接的机器(同样需要安装Docker)上执行上述指令获取镜像,然后使用docker image save指令导出镜像并将其上传到服务器,再在服务器上执行docker image load指令导入镜像1

1 要进一步了解镜像的导入导出操作,可以参考docker image save --helpdocker image load --help

在启动Gitea容器实例之前,需要先创建一个用于保存数据的存储卷:

docker volume create gitea

在存储卷创建完成后,可以执行以下指令启动Gitea容器实例:

docker container run \
  -d \
  -p 3022:22 \
  -p 3000:3000 \
  --name gitea \
  --restart always \
  --mount source=gitea,target=/data \
  --mount type=bind,source=/etc/timezone,target=/etc/timezone,readonly \ # 有的Linux发行版可能没有`/etc/timezone`这个文件;在这种情况下可以去掉此行参数
  --mount type=bind,source=/etc/localtime,target=/etc/localtime,readonly \
  gitea/gitea

以下是上述指令中所含参数的意义:

  • -d:使容器实例在后台运行;
  • -p 3022:22:建立服务器端口与容器实例端口的映射,格式为<HOST_PORT>:<CONTAINER_PORT>,该端口将用于SSH连接;
  • -p 3000:3000:格式同上,该端口将用于HTTP连接;
  • --name gitea:将容器实例命名为gitea
  • --restart always:无论该实例以何种状态退出,使Docker进程总是重启该容器实例;
  • mount source=gitea,target=/data:将存储卷gitea挂载到容器实例的/data目录,用于存储数据;
  • --mount type=bind,source=/etc/timezone,target=/etc/timezone,readonly:让容器实例能够访问服务器上的/etc/timezone文件,以获取服务器时区信息;
  • --mount type=bind,source=/etc/localtime,target=/etc/localtime,readonly:让容器实例能够访问服务器上的/etc/localtime文件,以获取服务器当前时间;

启动容器实例之后,就可以在网页浏览器中输入服务器地址和端口,然后访问Gitea平台了。初次登录时,平台会弹出页面提示你进行多项设置;本文将假定你在该页面设置了一个管理员账号,而其他设置均取默认值(数据库为SQLite)。完成设置后,你就可以使用管理员账号登录平台,并按需要添加其他用户了。

备份

首先,执行以下指令暂停Gitea服务:

docker container stop gitea

进入Gitea外挂存储卷所在目录,将所有文件打包:

cd /var/lib/docker/volumes/gitea/_data/
tar cf gitea-backup.tar *

在打包完成后,可将gitea-backup.tar保存备用。

完成上述操作后,记得重新开启Gitea服务:

docker container start gitea

恢复

现在假设原来的服务器由于发生了某种故障,需要在新的服务器对Gitea进行恢复;以下是操作步骤。

首先,在新服务器上创建存储卷,将之前保存好的备份文件gitea-backup.tar复制到对应目录中,并提取出其中的内容:

docker volume create gitea
mv <PATH>/gitea-backup.tar /var/lib/docker/volumes/gitea/_data/
cd /var/lib/docker/volumes/gitea/_data/
tar xf gitea-backup.tar

经上述操作,/var/lib/docker/volumes/gitea/_data/目录应出现ssh/git/gitea/三个目录。为保证数据恢复过程的顺利进行,需确保ssh/及其下所有文件的所属用户id(uid)和组id(gid)均应为0,而git/gitea/及其下所有文件的uid和gid则均应为1000。如果有出入,可以执行以下指令解决:

chown -R 0:0 ssh/
chown -R 1000:1000 git/ gitea/

完成上述操作后,按前文所述的方式使用docker container run指令启动新的Gitea容器实例即可。

附录:GitLab的部署、备份及恢复

简介

本文将介绍如何在私有服务器上自托管GitLab,内容将围绕其中涉及的三项最重要的操作,包括平台部署、数据备份及恢复。需要指出的是,GitLab有不同的部署方式2,并且根据部署方式的不同,数据备份及恢复的方式也有所差异。本文将介绍如何通过Docker容器部署GitLab,以及如何在此基础之上对数据进行备份和恢复。为了简化有关说明和操作,本文将假定:

  • 用于自托管GitLab的服务器使用的是Linux操作系统,并且安装了Docker;
  • 服务器的22、80及443端口没有被占用3
  • 使用默认配置来部署GitLab实例;
  • 所有操作都使用系统root用户执行。

3 除非进行了特别配置,否则服务器的22端口一般会被SSH服务占用;另外,如果服务器上部署了其他网页服务,那么80和443端口很可能也已经被占用了。下文在介绍GitLab容器实例的启动操作时会提到调整参数以避免端口冲突。

另外,GitLab有社区版(CE)和企业版(EE)之分;本文将以社区版为例介绍相关操作,但这些操作应该同样适用于企业版。

部署

Docker Hub的GitLab官方库上提供了多个版本的GitLab镜像;使用以下指令可以获取最新的社区版稳定镜像:

docker image pull gitlab/gitlab-ce

在启动GitLab容器实例之前,需要先创建以下几个将被用于保存重要数据(包括应用数据、日志数据和配置数据)的存储卷:

docker volume create gitlab-data
docker volume create gitlab-logs
docker volume create gitlab-config

在存储卷创建完成后,可以执行以下指令启动GitLab容器实例:

docker container run \
  -d \
  --hostname localhost \
  -p 443:443 \
  -p 80:80 \
  -p 22:22 \
  --name gitlab \
  --restart always \
  --mount source=gitlab-data,target=/var/opt/gitlab \
  --mount source=gitlab-logs,target=/var/log/gitlab \
  --mount source=gitlab-config,target=/etc/gitlab \
  gitlab/gitlab-ce

以下是上述指令中所含参数的意义:

  • -d:使容器实例在后台运行;
  • --hostname localhost:将容器实例内的主机命名为localhost
  • -p 22:22:建立服务器端口与容器实例端口的映射,格式为<HOST_PORT>:<CONTAINER_PORT>
  • -p 80:80:同上;
  • -p 443:443:同上;
  • --name gitlab:将容器实例命名为gitlab
  • --restart always:无论该实例以何种状态退出,Docker进程总是会重启该容器实例;
  • --mount source=gitlab-data,target=/var/opt/gitlab:将存储卷gitlab-data挂载到容器实例的/var/opt/gitlab目录,用于存储应用数据;
  • --mount source=gitlab-logs,target=/var/log/gitlab:将存储卷gitlab-logs挂载到容器实例的/var/log/gitlab目录,用于存储日志数据;
  • --mount source=gitlab-config,target=/etc/gitlab:将存储卷gitlab-config挂载到容器实例的/etc/gitlab目录,用于存储配置数据。

这里再对-p参数进行一些特别说明。之前提到,本文假定服务器的2280443端口没有被其他服务占用;如果被占用了,那么就要修改参数值<HOST_PORT>:<CONTAINER_PORT>中的<HOST_PORT>部分,使之指向未被占用的端口。

由于GitLab所涉及的组件较多,因此其容器实例的启动较慢,可能需要几分钟时间。待其完成启动之后,即可通过本地机器的网页浏览器访问GitLab平台了。在初次访问时,页面会提示为root用户设置密码;在设置密码之后,就可以使用该账户密码登录平台了。

备份

在对GitLab进行数据备份时,需要分别针对应用数据和配置数据进行相关操作。

应用数据的备份机制比较复杂,但可以使用GitLab容器实例中内置的gitlab-backup程序轻松实现。具体而言,只需在GitLab容器实例保持运行状态时执行以下指令即可:

docker exec -t gitlab gitlab-backup create STRATEGY=copy

需要注意的是,gitlab-backup程序默认使用流式备份策略;当应用数据快速变化时,该策略可能会导致备份失败。因此,上述指令中通过设置参数STRATEGY=copy,使程序改用复制备份策略,在备份前先将数据文件完整地复制到一个临时区域,以避免前述问题的产生;但相应地,该策略在备份过程中会占用更多的存储空间。

如果按照前文所介绍的方式部署GitLab,那么经上述指令备份好的应用数据会保存在/var/lib/docker/volumes/gitlab-data/_data/backups/目录下,命名格式为<TIMESTAMP>_<GITLAB-VERSION>_gitlab_backup.tar

配置数据的备份比较简单,只要执行以下指令即可在当前工作目录下产生备份结果文件gitlab-config.tar

tar cf ./gitlab-config.tar /var/lib/docker/volumes/gitlab-config/_data/*

完成操作后,将<TIMESTAMP>_<GITLAB-VERSION>_gitlab_backup.targitlab-config.tar保存至安全的位置备用。

恢复

现在假设原来的服务器由于发生了某种故障,需要在新的服务器对GitLab进行恢复(注意,进行数据恢复时的GitLab容器实例的版本必须与备份时所用的版本一致);以下是具体的操作步骤:

  1. 按照前文介绍的方法在新的服务器上部署GitLab容器实例;
  2. 将之前备份的应用数据<TIMESTAMP>_<GITLAB-VERSION>_gitlab_backup.tar复制(注意,不要使用tar命令提取该文件所含的内容)到新服务器的/var/lib/docker/volumes/gitlab-data/_data/backups/目录;
  3. 在新服务器上运行GitLab应用数据恢复指令docker exec -it gitlab gitlab-backup restore
  4. 使用tar命令将之前备份的配置数据gitlab-config.tar中的内容提取到新服务器的/var/lib/docker/volumes/gitlab-config/_data/目录;
  5. 执行docker container restart gitlab指令重启GitLab容器实例,使配置数据恢复生效。

需要特别说明的是,在执行上述第3个步骤的之前,需要检查<TIMESTAMP>_<GITLAB-VERSION>_gitlab_backup.tar文件的所属用户id(uid)和组id(gid)是否均为9984。这是因为默认情况下,GitLab会使用uid998的用户对应用数据进行备份和恢复;如果该权限不一致,可能会导致数据恢复的失败。

4 首先可以通过ls -l观察文件所属用户的用户名,然后再通过id指令来观察与用户名对应的uidgid

chown 998:998 `/var/lib/docker/volumes/gitlab-data/_data/backups/<TIMESTAMP>_<GITLAB-VERSION>_gitlab_backup.tar`

对于从gitlab-config.tar中提取出来的配置数据文件,恢复过程虽然对其所属用户及组无硬性要求,但出于安全考虑,最好也与之前保持一致(uidgid均为0)。