diff --git a/.gitignore b/.gitignore index 9c8de6681..d5a2ef909 100644 --- a/.gitignore +++ b/.gitignore @@ -22,3 +22,4 @@ htmlcov .tox .cache .npm-debug.log +Dockerfile-e diff --git a/buildman/component/buildcomponent.py b/buildman/component/buildcomponent.py index e7730cd81..eeb6d0dba 100644 --- a/buildman/component/buildcomponent.py +++ b/buildman/component/buildcomponent.py @@ -1,4 +1,5 @@ import datetime +import os import time import logging import json @@ -122,9 +123,13 @@ class BuildComponent(BaseComponent): # base_image: The image name and credentials to use to conduct the base image pull. # username: The username for pulling the base image (if any). # password: The password for pulling the base image (if any). + + subdir, dockerfile_name = os.path.split(build_config.get('build_subdir', '/Dockerfile')) + build_arguments = { 'build_package': build_job.get_build_package_url(self.user_files), - 'sub_directory': build_config.get('build_subdir', ''), + 'sub_directory': subdir, + 'dockerfile_name': dockerfile_name, 'repository': repository_name, 'registry': self.registry_hostname, 'pull_token': build_job.repo_build.access_token.code, diff --git a/buildman/manager/executor.py b/buildman/manager/executor.py index 202cf0921..585267c05 100644 --- a/buildman/manager/executor.py +++ b/buildman/manager/executor.py @@ -276,6 +276,7 @@ class PopenExecutor(BuilderExecutor): 'DOCKER_TLS_VERIFY': os.environ.get('DOCKER_TLS_VERIFY', ''), 'DOCKER_CERT_PATH': os.environ.get('DOCKER_CERT_PATH', ''), 'DOCKER_HOST': os.environ.get('DOCKER_HOST', ''), + 'PATH': "/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin" } logpipe = LogPipe(logging.INFO) diff --git a/buildtrigger/basehandler.py b/buildtrigger/basehandler.py index f8ed97563..a991c3be9 100644 --- a/buildtrigger/basehandler.py +++ b/buildtrigger/basehandler.py @@ -258,6 +258,11 @@ class BuildTriggerHandler(object): can be called in a loop, so it should be as fast as possible. """ pass + @classmethod + def path_is_dockerfile(cls, file_name): + """ Returns whether the file is named Dockerfile or follows the convention .Dockerfile""" + return file_name.endswith(".Dockerfile") or u"Dockerfile" == file_name + @classmethod def service_name(cls): """ @@ -285,14 +290,7 @@ class BuildTriggerHandler(object): def get_dockerfile_path(self): """ Returns the normalized path to the Dockerfile found in the subdirectory in the config. """ - subdirectory = self.config.get('subdir', '') - if subdirectory == '/': - subdirectory = '' - else: - if not subdirectory.endswith('/'): - subdirectory = subdirectory + '/' - - return subdirectory + 'Dockerfile' + return self.config.get('subdir', '') def prepare_build(self, metadata, is_manual=False): # Ensure that the metadata meets the scheme. diff --git a/buildtrigger/bitbuckethandler.py b/buildtrigger/bitbuckethandler.py index 02e6b228f..68290cde4 100644 --- a/buildtrigger/bitbuckethandler.py +++ b/buildtrigger/bitbuckethandler.py @@ -1,23 +1,21 @@ import logging +import os import re - from calendar import timegm import dateutil.parser - +from bitbucket import BitBucket from jsonschema import validate + +from app import app, get_app_url +from buildtrigger.basehandler import BuildTriggerHandler from buildtrigger.triggerutil import (RepositoryReadException, TriggerActivationException, TriggerDeactivationException, TriggerStartException, InvalidPayloadException, TriggerProviderException, determine_build_ref, raise_if_skipped_build, find_matching_branches) - -from buildtrigger.basehandler import BuildTriggerHandler - -from app import app, get_app_url -from bitbucket import BitBucket -from util.security.ssh import generate_ssh_keypair from util.dict_wrappers import JSONPathDict, SafeDictSetter +from util.security.ssh import generate_ssh_keypair logger = logging.getLogger(__name__) @@ -455,10 +453,7 @@ class BitbucketBuildTrigger(BuildTriggerHandler): raise RepositoryReadException(err_msg) files = set([f['path'] for f in data['files']]) - if 'Dockerfile' in files: - return [''] - - return [] + return ["/" + file_path for file_path in files if self.path_is_dockerfile(os.path.basename(file_path))] def load_dockerfile_contents(self): repository = self._get_repository_client() diff --git a/buildtrigger/githubhandler.py b/buildtrigger/githubhandler.py index a6df8a979..80dd5e2aa 100644 --- a/buildtrigger/githubhandler.py +++ b/buildtrigger/githubhandler.py @@ -1,6 +1,7 @@ import logging import os.path import base64 +import re from calendar import timegm from functools import wraps @@ -348,9 +349,8 @@ class GithubBuildTrigger(BuildTriggerHandler): default_commit = repo.get_branch(branches[0]).commit commit_tree = repo.get_git_tree(default_commit.sha, recursive=True) - return [os.path.dirname(elem.path) for elem in commit_tree.tree - if (elem.type == u'blob' and - os.path.basename(elem.path) == u'Dockerfile')] + return [elem.path for elem in commit_tree.tree + if (elem.type == u'blob' and self.path_is_dockerfile(os.path.basename(elem.path)))] except GithubException as ghe: message = ghe.data.get('message', 'Unable to list contents of repository: %s' % source) if message == 'Branch not found': diff --git a/buildtrigger/gitlabhandler.py b/buildtrigger/gitlabhandler.py index 5d221874b..0bd47c910 100644 --- a/buildtrigger/gitlabhandler.py +++ b/buildtrigger/gitlabhandler.py @@ -1,4 +1,5 @@ import logging +import os from calendar import timegm from functools import wraps @@ -341,11 +342,7 @@ class GitLabBuildTrigger(BuildTriggerHandler): msg = 'Unable to find GitLab repository tree for source: %s' % new_build_source raise RepositoryReadException(msg) - for node in repo_tree: - if node['name'] == 'Dockerfile': - return [''] - - return [] + return ["/"+node['name'] for node in repo_tree if self.path_is_dockerfile(node['name'])] @_catch_timeouts def load_dockerfile_contents(self): diff --git a/buildtrigger/test/test_basehandler.py b/buildtrigger/test/test_basehandler.py new file mode 100644 index 000000000..d8955740a --- /dev/null +++ b/buildtrigger/test/test_basehandler.py @@ -0,0 +1,15 @@ +import pytest + +from buildtrigger.basehandler import BuildTriggerHandler + + +@pytest.mark.parametrize('input,output', [ + ("Dockerfile", True), + ("server.Dockerfile", True), + (u"Dockerfile", True), + (u"server.Dockerfile", True), + ("bad file name", False), + (u"bad file name", False), +]) +def test_path_is_dockerfile(input, output): + assert BuildTriggerHandler.path_is_dockerfile(input) == output diff --git a/buildtrigger/test/test_bitbuckethandler.py b/buildtrigger/test/test_bitbuckethandler.py index 12c653db5..320a18906 100644 --- a/buildtrigger/test/test_bitbuckethandler.py +++ b/buildtrigger/test/test_bitbuckethandler.py @@ -13,12 +13,12 @@ def bitbucket_trigger(): def test_list_build_subdirs(bitbucket_trigger): - assert bitbucket_trigger.list_build_subdirs() == [''] + assert bitbucket_trigger.list_build_subdirs() == ["/Dockerfile"] @pytest.mark.parametrize('subdir, contents', [ - ('', 'hello world'), - ('somesubdir', 'hi universe'), + ('/Dockerfile', 'hello world'), + ('somesubdir/Dockerfile', 'hi universe'), ('unknownpath', None), ]) def test_load_dockerfile_contents(subdir, contents): diff --git a/buildtrigger/test/test_githubhandler.py b/buildtrigger/test/test_githubhandler.py index 5f9a1d786..4ca91ece4 100644 --- a/buildtrigger/test/test_githubhandler.py +++ b/buildtrigger/test/test_githubhandler.py @@ -68,8 +68,8 @@ def test_handle_trigger_request(github_trigger, payload, expected_error, expecte @pytest.mark.parametrize('subdir, contents', [ - ('', 'hello world'), - ('somesubdir', 'hi universe'), + ('/Dockerfile', 'hello world'), + ('somesubdir/Dockerfile', 'hi universe'), ('unknownpath', None), ]) def test_load_dockerfile_contents(subdir, contents): @@ -86,4 +86,4 @@ def test_lookup_user(username, expected_response, github_trigger): def test_list_build_subdirs(github_trigger): - assert github_trigger.list_build_subdirs() == ['', 'somesubdir'] + assert github_trigger.list_build_subdirs() == ['Dockerfile', 'somesubdir/Dockerfile'] diff --git a/buildtrigger/test/test_gitlabhandler.py b/buildtrigger/test/test_gitlabhandler.py index c88c591d6..d20a690be 100644 --- a/buildtrigger/test/test_gitlabhandler.py +++ b/buildtrigger/test/test_gitlabhandler.py @@ -13,12 +13,12 @@ def gitlab_trigger(): def test_list_build_subdirs(gitlab_trigger): - assert gitlab_trigger.list_build_subdirs() == [''] + assert gitlab_trigger.list_build_subdirs() == ['/Dockerfile'] @pytest.mark.parametrize('subdir, contents', [ - ('', 'hello world'), - ('somesubdir', 'hi universe'), + ('/Dockerfile', 'hello world'), + ('somesubdir/Dockerfile', 'hi universe'), ('unknownpath', None), ]) def test_load_dockerfile_contents(subdir, contents): diff --git a/static/js/services/trigger-service.js b/static/js/services/trigger-service.js index 6406fec10..3d8c3d143 100644 --- a/static/js/services/trigger-service.js +++ b/static/js/services/trigger-service.js @@ -208,10 +208,6 @@ angular.module('quay').factory('TriggerService', ['UtilService', '$sanitize', 'K return '//Dockerfile'; } - if (subdirectory[subdirectory.length - 1] != '/') { - subdirectory = subdirectory + '/'; - } - return '//' + subdirectory.replace(new RegExp('(^\/+|\/+$)'), '') + 'Dockerfile'; };