Python使用GitLabAPI

GitLab API使用

因为目前需要开发一个和gitlab相关的需求,需要使用到GitLab的API,而我采用的思路是使用python的第三方库(python-gitlab)。

GitLab官方文档:GitLab

Python-gitlab官方文档:python-gitlab

注意事项:

GitLab 11.0后不支持 API v3,需要先查看 GitLab版本:

GitLab版本 ≥ 11.0 安装

pip install python-gitlab

否则安装

pip install python-gitlab==1.4.0

可以不安装这个可以,可以直接调用GitLab提供的API,具体参考:GitLab API Documentation 或者GitLab中Help中的API

获取Toke

使用API之前需要获取Token,用于免密登录。

GitLab 8.8.5获取Token

Python使用GitLabAPI_第1张图片

GitLab15.3.0获取Token

Python使用GitLabAPI_第2张图片
Python使用GitLabAPI_第3张图片

及时保存Token,后续Token不能复制,只能重新生成。

测试

直接调用GitLab API

import requests
import urllib.parse

url = 'https://gitlab.example.com/'  # 你的GitLab地址
url = urllib.parse.urljoin(url, '/api/v3/projects')
params = {
    'private_token': 'xxx',  # 你的Private token
}
data = requests.get(url, params)
print(data.json())
# [{'id': 93, 'description': 'xxx', 'default_branch': 'develop', 'public': False, 'archived': False, 'visibility_level': 10, 'ssh_url_to_repo': '[email protected]:xxx/xxx.git', 'http_url_to_repo': 'https://gitlab.example.com/xxx/xxx.git', 'web_url': 'https://gitlab.example.com/xxx/xxx', 'name': 'xxx', 'name_with_namespace': 'xxx / xxx', 'path': 'xxx', 'path_with_namespace': 'xxx/xxx', 'issues_enabled': True, 'merge_requests_enabled': True, 'wiki_enabled': True, 'snippets_enabled': False, 'created_at': '2015-04-28T10:30:22.126Z', 'last_activity_at': '2020-12-28T02:35:55.104Z', 'namespace': {'id': 29, 'name': 'xxx', 'path': 'xxx', 'owner_id': None, 'created_at': '2015-04-27T10:18:20.834Z', 'updated_at': '2015-04-27T10:18:20.834Z', 'description': '', 'avatar': {'url': None}}}]

调用python-gitlab

import gitlab

url = 'https://gitlab.example.com/'
private_token = 'xxx'
gl = gitlab.Gitlab(url, private_token, api_version='3')
print(gl.projects.list())

鉴权

如果页面有这样的登录框需要鉴权,否则报错 401 Authorization Required

Python使用GitLabAPI_第4张图片

使用这个来登录

import gitlab

url = 'https://gitlab.example.com/'
private_token = 'xxx'
http_username = 'xxx'
http_password = 'xxx'
gl = gitlab.Gitlab(url, private_token, http_username=http_username, http_password=http_password)
print(gl.projects.list())

使用案例

import os
import time
import gitlab
import zipfile


def loginGitlab(gitlabUrl, token, userID=None, userPwd=None):
    """
    使用Token登录GitLab
    登陆账号可以默认不填,如果出现需要使用对话框登录的话需要填写,用于鉴权
    :param gitlabUrl: GitLab地址
    :param token: GitLab登陆账号Token
    :param userID: GitLab账号
    :param userPwd: GitLab密码
    :return: GitLab登录连接
    """
    gl = gitlab.Gitlab(gitlabUrl, private_token=token, http_username=userID, http_password=userPwd)
    return gl


def getItem(gl, ItemName):
    """
    通过项目名称,获取对应项目信息
    :param gl: GitLab登录连接
    :param ItemName: 项目名称
    :return: 项目信息
    """
    projectNameDir = {item.name: item.id for item in gl.projects.list(all=True, recursive=True)}
    project = gl.projects.get(projectNameDir[ItemName])
    return project


def createDir(dirName):
    """
    创建项目对应文件夹
    :param dirName: 项目的文件夹
    :return:
    """
    if not os.path.isdir(dirName):
        # print("\033[0;32;40m开始创建目录: \033[0m{0}".format(dirName))
        os.makedirs(dirName)
        time.sleep(0.1)


def downloadFiles(project, rootPath, companyBranchName):
    """
    下载项目文件
    :param project:需要下载的项目信息
    :param rootPath: 下载文件存放地址
    :param companyBranchName:客户公司对应的开发分支
    :return:
    """
    info = project.repository_tree(all=True, recursive=True, ref=companyBranchName)
    if not os.path.isdir(rootPath):
        os.makedirs(rootPath)
    fileList = []
    os.chdir(rootPath)
    # 调用创建目录的函数并生成文件名列表
    for info_dir in range(len(info)):
        if info[info_dir]['type'] == 'tree':
            dirName = info[info_dir]['path']
            createDir(dirName)
        else:
            fileName = info[info_dir]['path']
            fileList.append(fileName)
    for fileInfo in fileList:
        getFile = project.files.get(file_path=fileInfo, ref=companyBranchName)
        content = getFile.decode()
        with open(fileInfo, 'wb') as code:
            # print("\033[0;32;40m开始下载文件: \033[0m{0}".format(fileInfo))
            code.write(content)


def packFiles(dirpath):
    """
    项目文件打包
    :param dirpath: 本地项目文件地址
    :return:包文件地址
    """
    output_name = f"{dirpath}.zip"
    parent_name = os.path.dirname(dirpath)
    zip = zipfile.ZipFile(output_name, "w", zipfile.ZIP_DEFLATED)
    # 多层级压缩
    for root, dirs, files in os.walk(dirpath):
        for file in files:
            if str(file).startswith("~$"):
                continue
            filepath = os.path.join(root, file)
            writepath = os.path.relpath(filepath, parent_name)
            zip.write(filepath, writepath)
    zip.close()
    return output_name


def uploadPackFile(packagePath, companyName, companyItem):
    def delFile(path):
        for i in os.listdir(path):
            file_data = path + "\\" + i
            if os.path.isfile(file_data):
                os.remove(file_data)
            else:
                delFile(file_data)
    filesPath, _ = os.path.split(packagePath)
    fileDirPath = r"{}\{}_{}".format(filesPath, companyName, companyItem)
    delFile(fileDirPath)
    # os.rmdir(fileDirPath)


if __name__ == '__main__':
    ##########配置项############
    gitlabUrl = 'http://xxxxxxxx'
    token = ''  # 账号 Token
    targetPath = r'E:\GitlabDownloadTest'

    ##########################
    rootPath = r'{}/{}_{}'.format(targetPath, companyName, companyItem)
    gl = loginGitlab(gitlabUrl, token)
    project = getItem(gl, companyItem)
    downloadFiles(project, rootPath, companyBranch)
    packPath = packFiles(rootPath)
    uploadPackFile(packPath, companyName, companyItem)

你可能感兴趣的:(Python,tools,python,git,github)