【问题标题】:Download files through GitLab API that has been manually uploaded通过 GitLab API 下载已手动上传的文件
【发布时间】:2019-07-05 18:17:14
【问题描述】:

我们有一个自托管的 GitLab 服务器,并且正在致力于自动化我们的构建和发布。在使用 GitLab CI 之前,我们已经构建了许多旧版本。其中一些应该包含在某个软件的发布包中。这些版本不在​​任何易于访问的服务器上,因此如果可以从我们的 GitLab 服务器访问它们将非常容易。

可以从 API 访问标签并从构建作业中获取工件。似乎无法手动添加构建工件,因此无法将其用于旧版本。

可以将文件上传到标签的发行说明。这些通过网页下载非常简单,但我找不到任何通过 API 下载这些的方法。有这个 API 端点:

https://docs.gitlab.com/ee/api/projects.html#upload-a-file

但没有“下载文件”。

有没有一种简单的方法可以将文件上传到我们自托管的 GitLab,然后通过 API 下载它们?

我们所有的存储库都将可见性设置为私有。如果您在未登录的情况下尝试访问这样的链接:

http://www.example.com/group/my-project/uploads/443568a8641b1b48fc983daea27d36c0/myfile.zip

然后你会被重定向到登录页面。

【问题讨论】:

    标签: gitlab gitlab-ci gitlab-api


    【解决方案1】:

    无法从 GitLab API 下载文件。这是 GitLab 跟踪此功能的问题:

    https://gitlab.com/gitlab-org/gitlab/issues/25838

    -----

    作为目前的解决方法,我使用 python 脚本来简单地登录到页面并获取文件。这需要用户的用户名和密码。我设置了一个新用户,该用户只能访问需要它的特定项目,因此在该项目的构建脚本中使用它应该足够安全。

    import argparse
    import sys
    import mechanize
    
    def login_and_download(url, user, password):
        br = mechanize.Browser()
        br.set_handle_robots(False)
        br.open(url)
        br.select_form(id = 'new_user')
        br['user[login]'] = user
        br['user[password]'] = password
        response = br.submit()
        filename = url.split('/')[-1] #Last part of url
        with open(filename, 'wb') as f:
            f.write(response.get_data())
    
    def main():
        parser = argparse.ArgumentParser(description = 'Downloads files from a private git repo')
        parser.add_argument('url',  help = 'The URL to download')
        parser.add_argument('user',  help = 'The username to use')
        parser.add_argument('password',  help = 'The password to use')
        args = parser.parse_args()
    
        if len(sys.argv) == 1:
            parser.print_help()
            sys.exit(1)
    
        login_and_download(args.url, args.user, args.password)
    
    if __name__ == '__main__':
        main()
    

    【讨论】:

      【解决方案2】:

      这是另一个 python 脚本示例,仍然来自 issue 25838

      它翻译curl 调用:

      curl --request GET 'http://127.0.0.1:3000/root/my-project/uploads/d3d527ac296ae1b636434f44c7f57272/IMG_3935.jpg' \
           --header 'Authorization: Bearer YOUR_API_TOKEN'
      
      import requests
      from bs4 import BeautifulSoup
      
      with requests.Session() as http_session:
      
          # my login page url
          login_url = [LOGIN_URL]
          login_page = http_session.get(login_url)
          login_inputs = BeautifulSoup(login_page.content, features='html.parser').find_all('input')
      
          # get the authenticity token from the login page
          for login_input in login_inputs:
              if 'token' in login_input['name']:
                  auth_token = login_input['value']
                  break
      
          # send some user-agent header just in case
          headers = {"User-Agent":"Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/51.0.2704.103 Safari/537.36"}
      
          # see your login page source for the required data ...
          data = {
              "username": [MYUSERNAME],
              "password": [MYPASSWORD],
              "authenticity_token": auth_token,
              "remember_me": "1",
              "commit": "Sign in"
          }
      
          # ... as well as the login endpoint
          login_endpoint = [LOGIN_ENDPOINT_URL]
      
          # authenticate
          http_session.post(login_endpoint, data=data, headers=headers)
      
          # myfile_url is the url for my wanted file
          myfiledata = http_session.get(myfile_url).content
      
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2014-02-01
        • 1970-01-01
        • 2018-10-06
        • 1970-01-01
        • 1970-01-01
        • 2021-07-22
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多