Skip to content

Commit 8f3f57a

Browse files
committed
Make platform configurable instead of only auto-detecting
1 parent 064d91a commit 8f3f57a

File tree

13 files changed

+80
-32
lines changed

13 files changed

+80
-32
lines changed

repo2docker/app.py

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
import sys
1616
import tempfile
1717
import time
18+
import warnings
1819
from urllib.parse import urlparse
1920

2021
import entrypoints
@@ -36,7 +37,7 @@
3637
RBuildPack,
3738
)
3839
from .engine import BuildError, ContainerEngineException, ImageLoadError
39-
from .utils import ByteSpecification, R2dState, chdir
40+
from .utils import ByteSpecification, R2dState, chdir, get_platform
4041

4142

4243
class Repo2Docker(Application):
@@ -250,6 +251,27 @@ def _user_name_default(self):
250251
config=True,
251252
)
252253

254+
platform = Unicode(
255+
config=True,
256+
help="""
257+
Platform to build for, linux/amd64 (recommended) or linux/arm64 (experimental).
258+
""",
259+
)
260+
261+
@default("platform")
262+
def _platform_default(self):
263+
"""
264+
Default platform
265+
"""
266+
p = get_platform()
267+
if p == "linux/arm64":
268+
warnings.warn(
269+
"Building for linux/arm64 is experimental. "
270+
"To use the recommended platform set --Repo2Docker.platform=linux/amd64. "
271+
"To silence this warning set --Repo2Docker.platform=linux/arm64."
272+
)
273+
return p
274+
253275
extra_build_args = Dict(
254276
{},
255277
help="""
@@ -778,6 +800,7 @@ def build(self):
778800
else:
779801
picked_buildpack = self.default_buildpack()
780802

803+
picked_buildpack.platform = self.platform
781804
picked_buildpack.appendix = self.appendix
782805
# Add metadata labels
783806
picked_buildpack.labels["repo2docker.version"] = self.version
@@ -819,6 +842,7 @@ def build(self):
819842
build_args,
820843
self.cache_from,
821844
self.extra_build_kwargs,
845+
platform=self.platform,
822846
):
823847
if docker_client.string_output:
824848
self.log.info(l, extra=dict(phase=R2dState.BUILDING))

repo2docker/buildpacks/_r_base.py

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -4,15 +4,11 @@
44
Keeping this in r.py would lead to cyclic imports.
55
"""
66
from ..semver import parse_version as V
7-
from ..utils import get_platform
87

98

109
def rstudio_base_scripts(r_version):
1110
"""Base steps to install RStudio and shiny-server."""
1211

13-
if get_platform() != "linux-64":
14-
raise RuntimeError("RStudio is only available for linux-64")
15-
1612
# Shiny server (not the package!) seems to be the same version for all R versions
1713
shiny_server_url = "https://download3.rstudio.org/ubuntu-14.04/x86_64/shiny-server-1.5.17.973-amd64.deb"
1814
shiny_proxy_version = "1.1"

repo2docker/buildpacks/base.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,6 @@
1111
import escapism
1212
import jinja2
1313

14-
from ..utils import get_platform
15-
1614
# Only use syntax features supported by Docker 17.09
1715
TEMPLATE = r"""
1816
FROM buildpack-deps:bionic
@@ -231,7 +229,7 @@ def __init__(self):
231229
"Windows environment detected. Note that Windows "
232230
"support is experimental in repo2docker."
233231
)
234-
self.platform = get_platform()
232+
self.platform = ""
235233

236234
def get_packages(self):
237235
"""
@@ -562,6 +560,7 @@ def build(
562560
build_args,
563561
cache_from,
564562
extra_build_kwargs,
563+
platform=None,
565564
):
566565
tarf = io.BytesIO()
567566
tar = tarfile.open(fileobj=tarf, mode="w")
@@ -616,6 +615,7 @@ def _filter_tar(tar):
616615
buildargs=build_args,
617616
container_limits=limits,
618617
cache_from=cache_from,
618+
platform=platform,
619619
)
620620

621621
build_kwargs.update(extra_build_kwargs)

repo2docker/buildpacks/conda/__init__.py

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,14 @@ class CondaBuildPack(BaseImage):
3535
# extra pip requirements.txt for the notebook env
3636
_nb_requirements_file = ""
3737

38+
def _conda_platform(self):
39+
"""Return the conda platform name for the current platform"""
40+
if self.platform == "linux/amd64":
41+
return "linux-64"
42+
if self.platform == "linux/arm64":
43+
return "linux-aarch64"
44+
raise ValueError(f"Unknown platform {self.platform}")
45+
3846
def get_build_env(self):
3947
"""Return environment variables to be set.
4048
@@ -59,7 +67,7 @@ def get_build_env(self):
5967
# this exe should be used for installs after bootstrap with micromamba
6068
# switch this to /usr/local/bin/micromamba to use it for all installs
6169
("MAMBA_EXE", "${CONDA_DIR}/bin/mamba"),
62-
("CONDA_PLATFORM", self.platform),
70+
("CONDA_PLATFORM", self._conda_platform()),
6371
]
6472
if self._nb_requirements_file:
6573
env.append(("NB_REQUIREMENTS_FILE", self._nb_requirements_file))
@@ -161,7 +169,7 @@ def get_build_script_files(self):
161169
# major Python versions during upgrade.
162170
# If no version is specified or no matching X.Y version is found,
163171
# the default base environment is used.
164-
frozen_name = f"environment-{self.platform}.lock"
172+
frozen_name = f"environment-{self._conda_platform()}.lock"
165173
pip_frozen_name = "requirements.txt"
166174
if py_version:
167175
if self.python_version == "2.7":
@@ -177,13 +185,15 @@ def get_build_script_files(self):
177185
self._kernel_requirements_file
178186
) = "/tmp/env/kernel-requirements.txt"
179187
else:
180-
py_frozen_name = f"environment.py-{py_version}-{self.platform}.lock"
188+
py_frozen_name = (
189+
f"environment.py-{py_version}-{self._conda_platform()}.lock"
190+
)
181191
if os.path.exists(os.path.join(HERE, py_frozen_name)):
182192
frozen_name = py_frozen_name
183193
pip_frozen_name = f"requirements.py-{py_version}.pip"
184194
else:
185195
raise ValueError(
186-
f"Python version {py_version} {self.platform} is not supported!"
196+
f"Python version {py_version} {self._conda_platform()} is not supported!"
187197
)
188198
files[
189199
"conda/" + frozen_name
@@ -369,6 +379,10 @@ def get_env_scripts(self):
369379
""",
370380
)
371381
)
382+
if self.platform != "linux/amd64":
383+
raise RuntimeError(
384+
f"RStudio is only available for linux/amd64 ({self.platform})"
385+
)
372386
scripts += rstudio_base_scripts(self.r_version)
373387
scripts += [
374388
(

repo2docker/buildpacks/docker.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ def build(
3030
build_args,
3131
cache_from,
3232
extra_build_kwargs,
33+
platform=None,
3334
):
3435
"""Build a Docker image based on the Dockerfile in the source repo."""
3536
# If you work on this bit of code check the corresponding code in
@@ -55,6 +56,7 @@ def build(
5556
container_limits=limits,
5657
cache_from=cache_from,
5758
labels=self.get_labels(),
59+
platform=platform,
5860
)
5961

6062
build_kwargs.update(extra_build_kwargs)

repo2docker/buildpacks/julia/julia_project.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -87,7 +87,7 @@ def get_build_env(self):
8787
For example, a tuple may be `('JULIA_VERSION', '0.6.0')`.
8888
8989
"""
90-
if self.platform == "linux-aarch64":
90+
if self.platform == "linux/arm64":
9191
julia_arch = julia_arch_short = "aarch64"
9292
else:
9393
julia_arch = "x86_64"

repo2docker/buildpacks/julia/julia_require.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,7 @@ def get_build_env(self):
7777
For example, a tuple may be `('JULIA_VERSION', '0.6.0')`.
7878
7979
"""
80-
if self.platform == "linux-aarch64":
80+
if self.platform == "linux/arm64":
8181
julia_arch = julia_arch_short = "aarch64"
8282
else:
8383
julia_arch = "x86_64"

repo2docker/buildpacks/nix/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ def get_build_scripts(self):
3131
- install nix package manager for user
3232
3333
"""
34-
if self.platform == "linux-aarch64":
34+
if self.platform == "linux/arm64":
3535
nix_arch = "aarch64"
3636
else:
3737
nix_arch = "x86_64"

repo2docker/buildpacks/r.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@
55
import requests
66

77
from ..semver import parse_version as V
8-
from ..utils import get_platform
98
from ._r_base import rstudio_base_scripts
109
from .python import PythonBuildPack
1110

@@ -278,8 +277,10 @@ def get_build_scripts(self):
278277

279278
cran_mirror_url = self.get_cran_mirror_url(self.checkpoint_date)
280279

281-
if get_platform() != "linux-64":
282-
raise RuntimeError("RStudio is only available for linux-64")
280+
if self.platform != "linux/amd64":
281+
raise RuntimeError(
282+
f"RStudio is only available for linux/amd64 ({self.platform})"
283+
)
283284
scripts = [
284285
(
285286
"root",

repo2docker/docker.py

Lines changed: 2 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,6 @@
88
import docker
99

1010
from .engine import Container, ContainerEngine, ContainerEngineException, Image
11-
from .utils import get_platform
1211

1312

1413
class DockerContainer(Container):
@@ -92,14 +91,9 @@ def build(
9291
fileobj=None,
9392
path="",
9493
labels=None,
94+
platform=None,
9595
**kwargs,
9696
):
97-
platform = get_platform()
98-
if platform == "linux-aarch64":
99-
docker_platform = "linux/arm64"
100-
else:
101-
docker_platform = "linux/amd64"
102-
10397
return self._apiclient.build(
10498
buildargs=buildargs,
10599
cache_from=cache_from,
@@ -113,7 +107,7 @@ def build(
113107
fileobj=fileobj,
114108
path=path,
115109
labels=labels,
116-
platform=docker_platform,
110+
platform=platform,
117111
**kwargs,
118112
)
119113

0 commit comments

Comments
 (0)