1.将Gerrit的项目名称导入到一个文件内,如下命令是将所有以Platform/AC8015开头的项目名称导入到gerrit_repo.xml文件中,使用这个命令必须将ssh-key公钥放置到appuser账户中。
ssh -p 29418 appuser@Gerrit地址 gerrit ls-projects | grep "Platform/AC8015" > gerrit_repo.xml
2.运行python脚本以gerrit_repo.xml生成replication.config配置文件,并且去除Gerrit仓库路径中的单个字符,生成gitlab_repo.xml文件。
Python文件内容:
# 打开 gerrit_repo.xml 文件
with open("C:/Desktop/脚本/gitlab_create_repos/gerrit_repo.xml", "r") as infile:
# 读取每一行的内容
lines = infile.readlines()
# 打开输出文件
with open("C:/Desktop/脚本/gitlab_create_repos/replication.config", "w") as outfile:
# 打开 gitlab_repo.xml 文件
with open("C:/Desktop/脚本/gitlab_create_repos/gitlab_repo.xml", "w") as xmlfile:
# 遍历每一行
for line in lines:
# 去除行中的单个字符和多余的 /
parts = [p.strip() for p in line.split('/')]
new_parts = [p for p in parts if len(p) > 1]
# 替换小数点为 -
path1 = "/".join(new_parts).replace(".", "-")
path2 = "/".join(new_parts)
# 写入 replication.config 文件
outfile.write("[remote \"" + line.strip() + "\"]\n")
outfile.write("projects = " + line.strip() + "\n")
outfile.write("url = ssh://git@10.30.4.54:2289/" + path1 + ".git\n")
outfile.write("push = +refs/heads/*:refs/heads/*\n")
outfile.write("push = +refs/tags/*:refs/tags/*\n")
outfile.write("push = +refs/changes/*:refs/changes/*\n")
outfile.write("threads = 3\n\n")
# 写入 gitlab_repo.xml 文件
xmlfile.write(path2 + "\n")
3.python脚本创建Gitlab仓库,如果创建不成功会将错误仓库路径写入error_Path.txt中。
如果有创建不成功的仓库,那需要用户手动操作。
创建仓库不成功错误目前只遇到一种,是仓库路径冲突。
例如:
AC8010/device/autochips/common
AC8010/device/autochips/common/carlink
创建这两个仓库,先创建common仓库,就不能创建carlink仓库,因为common是仓库不能作为群组来使用。如果先创建carlink仓库,那么就会显示common路径被占用。
就需要手动操作,将其更改路径,并且更改replication.config配置文件。
脚本内容:
import gitlab
# 使用GitLab API的类
class GitlabAPI:
# 初始化函数,传入GitLab的URL和访问令牌
def __init__(self, url, token):
# 创建GitLab对象
self.gl = gitlab.Gitlab(url, private_token=token)
# 创建GitLab仓库的函数,传入仓库路径
def create_project(self, repo_path):
try:
# 解析仓库路径,获取仓库名称和命名空间名称
parts = repo_path.strip().split('/')
project_name = parts[-1]
namespace_parts = parts[:-1]
namespace_id = None
# 遍历命名空间路径,检查每个部分是否存在
for part in namespace_parts:
if not part:
continue
if namespace_id is None:
try:
# 尝试获取该组
namespace = self.gl.groups.get(part, include_subgroups=True)
namespace_id = namespace.id
except gitlab.exceptions.GitlabGetError as e:
if e.response_code == 404:
# 组不存在,创建它
namespace = self.gl.groups.create({'name': part, 'path': part})
namespace_id = namespace.id
else:
try:
# 尝试获取该子组
subgroup_path = "/".join(namespace_parts[:namespace_parts.index(part)+1])
subgroup = self.gl.groups.get(subgroup_path, include_subgroups=True)
namespace_id = subgroup.id
except gitlab.exceptions.GitlabGetError as e:
if e.response_code == 404:
# 子组不存在,创建它
parent_path = "/".join(namespace_parts[:namespace_parts.index(part)])
parent = self.gl.groups.get(parent_path, include_subgroups=True)
subgroup = self.gl.groups.create({'name': part, 'path': part, 'parent_id': parent.id})
namespace_id = subgroup.id
# 创建仓库并输出成功信息
project = self.gl.projects.create({'name': project_name, 'namespace_id': namespace_id})
print(f"Project '{project_name}' created in namespace '{'/'.join(namespace_parts)}'")
# 出错时,输出错误信息并将仓库路径写入错误文件
except Exception as e:
print(f'Error creating project in GitLab: {str(e)}')
with open("C:/Desktop/脚本/gitlab_create_repos/error_Path.txt", "a") as error_file:
error_file.write(f"{repo_path}\n")
# 在主函数中调用GitLab API,从文件中读取仓库路径并创建仓库
if __name__ == "__main__":
# 创建GitLab API对象
gl_api = GitlabAPI('http://gitlab地址', 'gitlab用户token')
# 打开包含仓库路径的文件
with open("C:/Desktop/脚本/gitlab_create_repos/gitlab_repo.xml", "r") as f:
#去除每行开头和结尾的空格和换行符,并将剩余的内容作为参数传递给 create_project
for line in f:
gl_api.create_project(line.strip())
更改gitlab地址与gitlab用户token,直接运行脚本即可,就会自动创建仓库。
还有地址如果没有也需要更改
C:/Desktop/脚本/gitlab_create_repos/gitlab_repo.xml
C:/Desktop/脚本/gitlab_create_repos/error_Path.txt
之后将replication.config文件写入到gerrit的replication.config文件内,然后重新加载replication插件,等待同步成功。