Downloadable file source is not setting a user agent; rejected by gitlab
Summary
When using the downloadable file source to fetch a source archive from gitlab.com, BuildStream exits with an error. Gitlab rejects our request with a "403 Forbidden" error. It appears this is a recent new behaviour, and it appears to stem from BuildStream's use of the default user agent with urllib.request. Using a different user agent, gitlab.com allows us to download the file normally.
It would be good practice to set a user agent, which will help to differentiate BuildStream from other scripts downloading files.
Steps to reproduce
Create a buildstream project with the following elements...
gitlab-tar-file.bst:
kind: manual
build-depends:
- base.bst
sources:
- kind: tar
url: https://gitlab.com/BuildStream/buildstream/-/archive/1.4.1/buildstream-1.4.1.tar.gz
bst.bst:
kind: import
description: |
Alpine Linux base runtime
sources:
- kind: tar
# This is a post doctored, trimmed down system image
# of the Alpine linux distribution.
#
url: https://bst-integration-test-images.ams3.cdn.digitaloceanspaces.com/integration-tests-base.v1.x86_64.tar.xz
ref: 3eb559250ba82b64a68d86d0636a6b127aa5f6d25d3601a79f79214dc9703639
In your project, run bst track gitlab-tar-file.bst.
What is the current bug behavior?
BuildStream exits with the following output:
[--:--:--][????????][track:gitlab-tar-file.bst ] START gitlab-tar-issue/gitlab-tar-file/????????-track.148575.log
[--:--:--][????????][track:gitlab-tar-file.bst ] START Tracking https://gitlab.com/BuildStream/buildstream/-/archive/1.4.1/buildstream-1.4.1.tar.gz
[00:00:00][????????][track:gitlab-tar-file.bst ] FAILURE Tracking https://gitlab.com/BuildStream/buildstream/-/archive/1.4.1/buildstream-1.4.1.tar.gz
[00:00:00][????????][track:gitlab-tar-file.bst ] FAILURE tar source at gitlab-tar-file.bst [line 7 column 2]: Error mirroring https://gitlab.com/BuildStream/buildstream/-/archive/1.4.1/buildstream-1.4.1.tar.gz: HTTP Error 403: Forbidden
Printing the last 20 lines from log file:
/home/dylan/.cache/buildstream/logs/gitlab-tar-issue/gitlab-tar-file/????????-track.148575.log
======================================================================
[--:--:--] START gitlab-tar-file.bst: Track
[--:--:--] LOG gitlab-tar-file.bst: Build environment for element gitlab-tar-file.bst
HOME: /tmp
LC_ALL: C
LOGNAME: tomjon
MAKEFLAGS: -j8
PATH: /usr/bin:/bin:/usr/sbin:/sbin
SHELL: /bin/sh
SOURCE_DATE_EPOCH: '1320937200'
TERM: dumb
TZ: UTC
USER: tomjon
USERNAME: tomjon
V: '1'
[--:--:--] START gitlab-tar-file.bst-0: Tracking https://gitlab.com/BuildStream/buildstream/-/archive/1.4.1/buildstream-1.4.1.tar.gz
[00:00:00] FAILURE gitlab-tar-file.bst-0: Tracking https://gitlab.com/BuildStream/buildstream/-/archive/1.4.1/buildstream-1.4.1.tar.gz
[00:00:00] FAILURE gitlab-tar-file.bst: tar source at gitlab-tar-file.bst [line 7 column 2]: Error mirroring https://gitlab.com/BuildStream/buildstream/-/archive/1.4.1/buildstream-1.4.1.tar.gz: HTTP Error 403: Forbidden
======================================================================
Possible fixes
Gitlab appears to be rejecting an arbitrary list of user agents, one of which is the default used by urllib (Python-urllib/3.7). so a good fix here would be to set our own over here: https://gitlab.com/BuildStream/buildstream/-/blob/1.4.2/buildstream/plugins/sources/_downloadablefilesource.p
Other relevant information
We can also reproduce this behaviour using a simple Python program which behaves the same as plugins/sources/_downloadablefilesource.py:
from urllib.request import Request, urlopen
from urllib.error import HTTPError
url = 'https://gitlab.com/BuildStream/buildstream/-/archive/1.4.1/buildstream-1.4.1.tar.gz'
request = Request(url)
request.add_header('Accept', '*/*')
# This program works correctly if we uncomment the following line:
# request.add_header('User-Agent', 'BuildStream (+http://buildstream.build)')
try:
response = urlopen(request)
except HTTPError as err:
print(err.getcode(), err.reason)
print(err.info())
- BuildStream version affected: /milestone %BuildStream_v1.4