Skip to content

Commit 06f5a47

Browse files
committed
Properly handle relative Dockerfile paths and Dockerfile on different drives
Signed-off-by: Joffrey F <[email protected]>
1 parent 2ecc3ad commit 06f5a47

File tree

2 files changed

+52
-9
lines changed

2 files changed

+52
-9
lines changed

docker/api/build.py

Lines changed: 20 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -149,15 +149,7 @@ def build(self, path=None, tag=None, quiet=False, fileobj=None,
149149
lambda x: x != '' and x[0] != '#',
150150
[l.strip() for l in f.read().splitlines()]
151151
))
152-
if dockerfile and os.path.relpath(dockerfile, path).startswith(
153-
'..'):
154-
with open(dockerfile, 'r') as df:
155-
dockerfile = (
156-
'.dockerfile.{0:x}'.format(random.getrandbits(160)),
157-
df.read()
158-
)
159-
else:
160-
dockerfile = (dockerfile, None)
152+
dockerfile = process_dockerfile(dockerfile, path)
161153
context = utils.tar(
162154
path, exclude=exclude, dockerfile=dockerfile, gzip=gzip
163155
)
@@ -312,3 +304,22 @@ def _set_auth_headers(self, headers):
312304
)
313305
else:
314306
log.debug('No auth config found')
307+
308+
309+
def process_dockerfile(dockerfile, path):
310+
if not dockerfile:
311+
return (None, None)
312+
313+
abs_dockerfile = dockerfile
314+
if not os.path.isabs(dockerfile):
315+
abs_dockerfile = os.path.join(path, dockerfile)
316+
317+
if (os.path.splitdrive(path)[0] != os.path.splitdrive(abs_dockerfile)[0] or
318+
os.path.relpath(abs_dockerfile, path).startswith('..')):
319+
with open(abs_dockerfile, 'r') as df:
320+
return (
321+
'.dockerfile.{0:x}'.format(random.getrandbits(160)),
322+
df.read()
323+
)
324+
else:
325+
return (dockerfile, None)

tests/integration/api_build_test.py

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -440,3 +440,35 @@ def test_build_out_of_context_dockerfile(self):
440440
lsdata = self.client.logs(ctnr).strip().split(b'\n')
441441
assert len(lsdata) == 3
442442
assert sorted([b'.', b'..', b'file.txt']) == sorted(lsdata)
443+
444+
def test_build_in_context_dockerfile(self):
445+
base_dir = tempfile.mkdtemp()
446+
self.addCleanup(shutil.rmtree, base_dir)
447+
with open(os.path.join(base_dir, 'file.txt'), 'w') as f:
448+
f.write('hello world')
449+
with open(os.path.join(base_dir, 'custom.dockerfile'), 'w') as df:
450+
df.write('\n'.join([
451+
'FROM busybox',
452+
'COPY . /src',
453+
'WORKDIR /src',
454+
]))
455+
print(os.path.join(base_dir, 'custom.dockerfile'))
456+
img_name = random_name()
457+
self.tmp_imgs.append(img_name)
458+
stream = self.client.build(
459+
path=base_dir, dockerfile='custom.dockerfile', tag=img_name,
460+
decode=True
461+
)
462+
lines = []
463+
for chunk in stream:
464+
lines.append(chunk)
465+
assert 'Successfully tagged' in lines[-1]['stream']
466+
467+
ctnr = self.client.create_container(img_name, 'ls -a')
468+
self.tmp_containers.append(ctnr)
469+
self.client.start(ctnr)
470+
lsdata = self.client.logs(ctnr).strip().split(b'\n')
471+
assert len(lsdata) == 4
472+
assert sorted(
473+
[b'.', b'..', b'file.txt', b'custom.dockerfile']
474+
) == sorted(lsdata)

0 commit comments

Comments
 (0)