Skip to content

Commit 3dbc6f5

Browse files
authored
Update blake3 dep, remove dockerfile, simplify build (#1561)
1 parent 21b1022 commit 3dbc6f5

File tree

9 files changed

+154
-91
lines changed

9 files changed

+154
-91
lines changed

context_builder.Dockerfile

Lines changed: 1 addition & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -5,24 +5,14 @@
55
FROM python:3.9-slim AS builder
66

77
RUN apt-get update \
8-
&& apt-get install --yes --no-install-recommends curl build-essential golang-go \
8+
&& apt-get install --yes --no-install-recommends curl \
99
&& apt-get autoremove -y \
1010
&& apt-get clean -y \
1111
&& rm -rf /var/lib/apt/lists/* /tmp/library-scripts/
1212

1313
RUN curl -sSL https://install.python-poetry.org | python -
1414
ENV PATH="/root/.local/bin:${PATH}"
1515

16-
# NB(nikhil): We need to explicitly install Rust and golang-go on arm64 architectures
17-
# for certain truss dependencies (blake3, dockerfile) that don't have prebuilt wheels.
18-
# This is a multi stage image, so the extra tools don't bloat the final image.
19-
RUN curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y
20-
ENV PATH="/root/.cargo/bin:${PATH}"
21-
RUN rustup update stable && rustup default stable
22-
23-
# Will only exist for arm64 builds, but is a no-op otherwise.
24-
ENV PATH="/root/.cargo/bin:${PATH}"
25-
2616
# Chains/train source code is not actually needed (and deps from chains group won't be
2717
# installed when using `--only builder`). But nonetheless poetry fails the install
2818
# if this directory is not present/empty - so we copy it.

poetry.lock

Lines changed: 87 additions & 47 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

pyproject.toml

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[tool.poetry]
22
name = "truss"
3-
version = "0.9.78"
3+
version = "0.9.79rc001"
44
description = "A seamless bridge from model development to model delivery"
55
license = "MIT"
66
readme = "README.md"
@@ -85,7 +85,7 @@ single-source = "^0.3.0"
8585
Jinja2 = { version = "^3.1.2", optional = false }
8686
aiofiles = { version = "^24.1.0", optional = false }
8787
aiohttp = { version = "^3.10.10", optional = false }
88-
blake3 = { version = "^0.3.3", optional = false }
88+
blake3 = { version = "^1.0.4", optional = false }
8989
boto3 = { version = "^1.34.85", optional = false }
9090
click = { version = "^8.0.3", optional = false }
9191
fastapi = { version =">=0.109.1", optional = false }
@@ -159,7 +159,6 @@ types-setuptools = "^69.0.0.0"
159159
[tool.poetry.group.dev-server.dependencies]
160160
# These packages are needed to run local tests of server components. Note that the actual
161161
# server deps for building the docker image are (so far) defined in `requirements.txt`-files.
162-
dockerfile = "^3.2.0"
163162
fastapi =">=0.109.1"
164163
flask = "^2.3.3"
165164
msgpack = ">=1.0.2"

truss/base/constants.py

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,6 @@
1010
HUGGINGFACE_TRANSFORMER = "huggingface_transformer"
1111
LIGHTGBM = "lightgbm"
1212

13-
ARM_PLATFORMS = ("aarch64", "arm64")
14-
1513

1614
_TRUSS_ROOT = pathlib.Path(__file__).parent.parent.resolve()
1715

truss/contexts/image_builder/serving_image_builder.py

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
from __future__ import annotations
22

33
import logging
4-
import platform
54
from abc import ABC, abstractmethod
65
from dataclasses import dataclass
76
from pathlib import Path
@@ -17,7 +16,6 @@
1716

1817
from truss.base import constants
1918
from truss.base.constants import (
20-
ARM_PLATFORMS,
2119
BASE_SERVER_REQUIREMENTS_TXT_FILENAME,
2220
BEI_MAX_CONCURRENCY_TARGET_REQUESTS,
2321
BEI_REQUIRED_MAX_NUM_TOKENS,
@@ -711,8 +709,6 @@ def _render_dockerfile(
711709
MIN_SUPPORTED_PYTHON_VERSION_IN_CUSTOM_BASE_IMAGE.split(".")[0]
712710
)
713711

714-
should_install_arm64_requirements = platform.machine() in ARM_PLATFORMS
715-
716712
hf_access_token = config.secrets.get(constants.HF_ACCESS_TOKEN_KEY)
717713
dockerfile_contents = dockerfile_template.render(
718714
should_install_server_requirements=should_install_server_requirements,
@@ -745,7 +741,6 @@ def _render_dockerfile(
745741
external_data_files=external_data_files,
746742
build_commands=build_commands,
747743
use_local_src=config.use_local_src,
748-
should_install_arm64_requirements=should_install_arm64_requirements,
749744
**FILENAME_CONSTANTS_MAP,
750745
)
751746

truss/contexts/local_loader/docker_build_emulator.py

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,10 @@
22
from pathlib import Path
33
from typing import Dict, List
44

5+
from truss.contexts.local_loader.dockerfile_parser import (
6+
DockerInstruction,
7+
parse_dockerfile,
8+
)
59
from truss.util.path import copy_tree_or_file
610

711

@@ -23,9 +27,7 @@ class DockerBuildEmulator:
2327
"""
2428

2529
def __init__(self, dockerfile_path: Path, context_dir: Path) -> None:
26-
import dockerfile
27-
28-
self._commands = dockerfile.parse_file(str(dockerfile_path))
30+
self._commands = parse_dockerfile(dockerfile_path)
2931
self._context_dir = context_dir
3032

3133
def run(self, fs_root_dir: Path) -> DockerBuildEmulatorResult:
@@ -41,18 +43,20 @@ def _resolve_values(keys: List[str]) -> List[str]:
4143

4244
result = DockerBuildEmulatorResult()
4345
for cmd in self._commands:
44-
if cmd.cmd not in ["ENV", "ENTRYPOINT", "COPY", "WORKDIR"]:
46+
if not cmd.is_supported:
4547
continue
4648
values = _resolve_values(cmd.value)
47-
if cmd.cmd == "ENV":
49+
if cmd.instruction == DockerInstruction.ENV:
50+
if "=" in values[0]:
51+
values = values[0].split("=", 1)
4852
result.env[values[0]] = values[1]
49-
if cmd.cmd == "ENTRYPOINT":
53+
if cmd.instruction == DockerInstruction.ENTRYPOINT:
5054
result.entrypoint = list(values)
51-
if cmd.cmd == "COPY":
55+
if cmd.instruction == DockerInstruction.COPY:
5256
src, dst = values
5357
src = src.replace("./", "", 1)
5458
dst = dst.replace("/", "", 1)
5559
copy_tree_or_file(self._context_dir / src, fs_root_dir / dst)
56-
if cmd.cmd == "WORKDIR":
60+
if cmd.instruction == DockerInstruction.WORKDIR:
5761
result.workdir = result.workdir / values[0]
5862
return result
Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
from dataclasses import dataclass
2+
from enum import Enum
3+
from pathlib import Path
4+
from typing import List
5+
6+
7+
class DockerInstruction(Enum):
8+
COPY = "COPY"
9+
ENV = "ENV"
10+
ENTRYPOINT = "ENTRYPOINT"
11+
WORKDIR = "WORKDIR"
12+
UNKNOWN = "UNKNOWN"
13+
14+
@classmethod
15+
def from_string(cls, instruction: str) -> "DockerInstruction":
16+
try:
17+
return cls(instruction.upper())
18+
except ValueError:
19+
return cls.UNKNOWN
20+
21+
22+
@dataclass
23+
class DockerCommand:
24+
instruction: DockerInstruction
25+
value: List[str]
26+
27+
@property
28+
def is_supported(self) -> bool:
29+
return self.instruction != DockerInstruction.UNKNOWN
30+
31+
32+
def parse_dockerfile(dockerfile_path: Path) -> List[DockerCommand]:
33+
commands = []
34+
with open(dockerfile_path, "r") as f:
35+
content = f.read()
36+
37+
# Join across line continuations.
38+
content = content.replace("\\\n", " ")
39+
for line in content.splitlines():
40+
line = line.strip()
41+
42+
if not line or line.startswith("#"):
43+
continue
44+
45+
parts = line.split(" ", 1)
46+
if len(parts) == 2:
47+
instruction_str, args_str = parts
48+
instruction = DockerInstruction.from_string(instruction_str)
49+
args = args_str.split()
50+
commands.append(DockerCommand(instruction=instruction, value=args))
51+
52+
return commands

truss/templates/base.Dockerfile.jinja

Lines changed: 0 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -25,20 +25,6 @@ RUN pip install mkl
2525
{% block post_base %}
2626
{% endblock %}
2727

28-
# NB(nikhil): We need to install additional toolchains to support installing
29-
# python dependencies (currently blake3 and dockerfile) on arm64 architecture.
30-
# Currently, we only support arm64 in local dev, but we need these for:
31-
# 1) Control server (depends on truss)
32-
# 2) Python DX / Chains (depends on truss)
33-
{% block install_arm64_requirements %}
34-
{%- if should_install_arm64_requirements %}
35-
RUN apt-get update && apt-get install --yes --no-install-recommends golang-go
36-
RUN curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s -- -y
37-
ENV PATH="/root/.cargo/bin:${PATH}"
38-
RUN rustup update stable && rustup default stable
39-
{%- endif %}
40-
{% endblock %}
41-
4228
{% block install_system_requirements %}
4329
{%- if should_install_system_requirements %}
4430
COPY ./{{system_packages_filename}} {{system_packages_filename}}
Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,2 @@
11
torch>=2.0.1
22
blake3>=0.3.3
3-
dockerfile>=3.2.0

0 commit comments

Comments
 (0)