Skip to content

Commit

Permalink
Merge pull request #4 from ElrondNetwork/experimental-v3
Browse files Browse the repository at this point in the history
Use regular user within container, adjust volume mounting etc.
  • Loading branch information
andreibancioiu authored Oct 12, 2022
2 parents 4f89a15 + 5b4f6e1 commit 76ee879
Show file tree
Hide file tree
Showing 4 changed files with 26 additions and 44 deletions.
23 changes: 10 additions & 13 deletions Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -5,21 +5,20 @@ ARG VERSION_RUST="nightly-2022-08-23"
ARG VERSION_BINARYEN="105-1"
ARG VERSION_WABT="1.0.27-1"

RUN apt-get update && apt-get install wget -y
RUN apt-get update && apt-get install python3.10 python-is-python3 -y
RUN apt-get update && apt-get install build-essential -y
# Install dependencies (including binaryen and wabt)
RUN apt-get update && apt-get install -y \
wget \
build-essential \
python3.10 python-is-python3 \
binaryen=${VERSION_BINARYEN} \
wabt=${VERSION_WABT}

# Install rust
RUN wget -O rustup.sh https://sh.rustup.rs && \
chmod +x rustup.sh && \
CARGO_HOME=/rust RUSTUP_HOME=/rust ./rustup.sh --verbose --default-toolchain ${VERSION_RUST} --profile minimal --target wasm32-unknown-unknown -y && \
rm rustup.sh

# Install wasm-opt
RUN apt-get update && apt-get install binaryen=${VERSION_BINARYEN}

# Install wabt
RUN apt-get update && apt-get install wabt=${VERSION_WABT}
rm rustup.sh && \
chmod -R 777 /rust

COPY "./build_within_docker.py" "/build.py"

Expand All @@ -28,13 +27,11 @@ ENV CARGO_HOME="/rust"
ENV RUSTUP_HOME="/rust"

# Additional arguments (must be provided at "docker run"):
# --output-owner-id
# --output-group-id
# --no-wasm-opt (optional)
ENTRYPOINT ["python", "./build.py", \
"--project", "/project", \
"--output", "/output", \
"--cargo-target-dir", "/cargo-target-dir"]
"--cargo-target-dir", "/rust/cargo-target-dir"]

LABEL frozen="yes"
LABEL rust=${VERSION_RUST}
Expand Down
8 changes: 2 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# elrond-sdk-images-build-contract-rust

Docker image (and wrappers) for reproducible contract builds (Rust).
Docker image (and wrappers) for reproducible contract builds (Rust). See [docs.elrond.com](https://docs.elrond.com/developers/reproducible-contract-builds/).

## Build the Docker image

Expand Down Expand Up @@ -35,8 +35,6 @@ This is useful for useful for testing, debugging and reviewing the script.
export PROJECT=${HOME}/contracts/reproducible-contract-build-example
export OUTPUT=${HOME}/contracts/output
export CARGO_TARGET_DIR=${HOME}/cargo-target-dir
export OWNER_ID=$(id -u)
export GROUP_ID=$(id -g)
export PATH=${HOME}/elrondsdk/vendor-rust/bin:${HOME}/elrondsdk/wabt/latest/bin:${PATH}
export RUSTUP_HOME=${HOME}/elrondsdk/vendor-rust
export CARGO_HOME=${HOME}/elrondsdk/vendor-rust
Expand All @@ -46,7 +44,5 @@ Build a project:

```
python3 ./build_within_docker.py --project=${PROJECT} --output=${OUTPUT} \
--cargo-target-dir=${CARGO_TARGET_DIR} \
--output-owner-id=${OWNER_ID} \
--output-group-id=${GROUP_ID}
--cargo-target-dir=${CARGO_TARGET_DIR}
```
12 changes: 5 additions & 7 deletions build_with_docker.py
Original file line number Diff line number Diff line change
Expand Up @@ -42,12 +42,12 @@ def main(cli_args: List[str]):

def run_docker(image: str, docker_interactive: bool, docker_tty: bool, project_path: Path, output_path: Path, cargo_target_dir: Union[Path, None], no_wasm_opt: bool):
docker_mount_args = [
"--mount", f"type=bind,source={project_path},destination=/project",
"--mount", f"type=bind,source={output_path},destination=/output"
"--volume", f"{project_path}:/project",
"--volume", f"{output_path}:/output"
]

if cargo_target_dir:
docker_mount_args += ["--mount", f"type=bind,source={cargo_target_dir},destination=/cargo-target-dir"]
docker_mount_args += ["--volume", f"{cargo_target_dir}:/cargo-target-dir"]

docker_args = ["docker", "run"]

Expand All @@ -57,12 +57,10 @@ def run_docker(image: str, docker_interactive: bool, docker_tty: bool, project_p
docker_args += ["--tty"]

docker_args += docker_mount_args
docker_args += ["--user", f"{str(os.getuid())}:{str(os.getgid())}"]
docker_args += ["--rm", image]

entrypoint_args = [
"--output-owner-id", str(os.getuid()),
"--output-group-id", str(os.getgid())
]
entrypoint_args: List[str] = []

if no_wasm_opt:
entrypoint_args.append("--no-wasm-opt")
Expand Down
27 changes: 9 additions & 18 deletions build_within_docker.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
import shutil
import subprocess
import sys
import time
from argparse import ArgumentParser
from hashlib import blake2b
from pathlib import Path
Expand Down Expand Up @@ -55,21 +56,19 @@ def dump_to_file(self, file: Path):
def main(cli_args: List[str]):
logging.basicConfig(level=logging.DEBUG)

start_time = time.time()

artifacts_accumulator = BuildArtifactsAccumulator()

parser = ArgumentParser()
parser.add_argument("--project", type=str, required=True, help="source code directory")
parser.add_argument("--output", type=str, required=True)
parser.add_argument("--no-wasm-opt", action="store_true", default=False, help="do not optimize wasm files after the build (default: %(default)s)")
parser.add_argument("--cargo-target-dir", type=str, required=True, help="Cargo's target-dir")
parser.add_argument("--output-owner-id", type=int, required=True, help="set owner of output folder")
parser.add_argument("--output-group-id", type=int, required=True, help="set group of output folder")

parsed_args = parser.parse_args(cli_args)
project_path = Path(parsed_args.project).expanduser()
parent_output_directory = Path(parsed_args.output)
owner_id = parsed_args.output_owner_id
group_id = parsed_args.output_group_id

contracts_directories = get_contracts_directories(project_path)

Expand All @@ -96,15 +95,18 @@ def main(cli_args: List[str]):
# The archive will also include the "output" folder (useful for debugging)
clean(build_directory, clean_output=False)

promote_cargo_lock_to_contract_directory(build_directory, contract_directory, owner_id, group_id)
promote_cargo_lock_to_contract_directory(build_directory, contract_directory)

# The archive is created after build, so that Cargo.lock files are included, as well (useful for debugging)
archive_source_code(contract_name, contract_version, build_directory, output_subdirectory)

artifacts_accumulator.gather_artifacts(contract_name, output_subdirectory)

artifacts_accumulator.dump_to_file(parent_output_directory / "artifacts.json")
adjust_output_ownership(parent_output_directory, owner_id, group_id)

end_time = time.time()
time_elapsed = end_time - start_time
logger.info(f"Built in {time_elapsed} seconds, as user = {os.getuid()}, group = {os.getgid()}")


def get_contracts_directories(project_path: Path) -> List[Path]:
Expand Down Expand Up @@ -168,11 +170,10 @@ def build(context: BuildContext):
shutil.copytree(cargo_output_directory, context.output_directory, dirs_exist_ok=True)


def promote_cargo_lock_to_contract_directory(build_directory: Path, contract_directory: Path, owner_id: int, group_id: int):
def promote_cargo_lock_to_contract_directory(build_directory: Path, contract_directory: Path):
from_path = build_directory / "wasm" / "Cargo.lock"
to_path = contract_directory / "wasm" / "Cargo.lock"
shutil.copy(from_path, to_path)
os.chown(to_path, owner_id, group_id)


def generate_wabt_artifacts(wasm_file: Path):
Expand Down Expand Up @@ -233,15 +234,5 @@ def archive_source_code(contract_name: str, contract_version: str, input_directo
logger.info(f"Created archive: {archive_file}")


def adjust_output_ownership(output_directory: Path, owner_id: int, group_id: int):
logger.info(f"Adjust ownership of output directory: directory = {output_directory}, owner = {owner_id}, group = {group_id}")

for root, dirs, files in os.walk(output_directory):
for item in dirs:
os.chown(Path(root) / item, owner_id, group_id)
for item in files:
os.chown(Path(root) / item, owner_id, group_id)


if __name__ == "__main__":
main(sys.argv[1:])

0 comments on commit 76ee879

Please sign in to comment.