:hammer: Build minimal docker images without static linking
magicpakenables you to build minimal docker images without any bothersome preparation such as static linking.
# You prepare /bin/your_executable here...ADD https://github.com/coord-e/magicpak/releases/download/v1.2.0/magicpak-x86_64-unknown-linux-musl /usr/bin/magicpak RUN chmod +x /usr/bin/magicpak
RUN /usr/bin/magicpak -v /bin/your_executable /bundle
FROM scratch COPY --from=0 /bundle /.
CMD ["/bin/your_executable"]
That's it! The resulting image shall only contain what your executable requires at runtime. You can find more useful examples of
magicpakunder example/.
magicpakis a command-line utility that analyzes and bundles runtime dependencies of the executable.
magicpakbasically collects all shared object dependencies that are required by a dynamic linker at runtime. Additionally,
magicpak's contributions are summarized as follows:
Dockerfile.
magicpakhandles all
Dockerfile-specific matters to decrease image size.
--dynamicflag enables a dynamic analysis that can discover dependencies other than dynamically linked libraries.
--includeand
--exclude. You can deal with dependencies that cannot be detected automatically.
magicpakis especially useful when you find it difficult to produce a statically linked executable. Also,
magicpakis powerful when building from source is bothering or the source code is not public, because
magicpakonly requires the executable to build a minimal docker image.
You can start with
magicpak path/to/executable path/to/output. This simply analyzes runtime dependencies of your executable statically and put everything your executable needs in runtime to the specified output directory. Once they've bundled, we can simply copy them to the
scratchimage in the second stage as follows.
RUN magicpak path/to/executable /bundleFROM scratch COPY --from=0 /bundle /.
Some executables work well in this way. However, others fail to run properly because
magicpak's static analysis isn't enough to detect all files needed by them at runtime. For this case,
magicpakhas
--includeoption to specify the missing requirements manually. Moreover, you can use
--dynamicto automatically include files that are accessed by the executable during execution.
Despite our careful implementation, our analysis is unreliable in a way because we can't completely determine the runtime behavior before its execution. To ensure that
magicpakcollected all dependencies to perform a specific task,
--testoption is implemented.
--testenables testing of the resulting bundle using chroot(2).
The size of the resulting image is our main concern.
magicpaksupports executable compression using
upx. You can enable it with
--compress.
magicpak [OPTIONS]-r, --install-to <path> Specify the installation path of the executable in the bundle -e, --exclude <glob>... Exclude files/directories from the resulting bundle with glob patterns -i, --include <glob>... Additionally include files/directories with glob patterns --mkdir <path>... Make directories in the resulting bundle -d, --dynamic Enable dynamic analysis --dynamic-arg <arg>... Specify arguments passed to the executable in --dynamic --dynamic-stdin <content> Specify stdin content supplied to the executable in --dynamic -t, --test Enable testing --test-command <command> Specify the test command to use in --test --test-stdin <content> Specify stdin content supplied to the test command in --test --test-stdout <content> Test stdout of the test command -c, --compress Compress the executable with npx --upx-arg <arg>... Specify arguments passed to upx in --compress --upx <path or name> Specify the path or name of upx that would be used in compression --busybox <path or name> Specify the path or name of busybox that would be used in testing --cc <path or name> Specify the path or name of c compiler --log-level <level> Specify the log level -v, --verbose Verbose mode, same as --log-level Info -h, --help Prints help information -V, --version Prints version information
We provide some base images that contain
magicpakand its optional dependencies to get started.
| name | description |
| ------------------------------------------------------------ | ------------------------------------------------------------ |
| magicpak/debian | library/debian with
magicpak| | magicpak/cc
build-essential,
clang, and
magicpak| | magicpak/haskell
magicpak| | magicpak/rust
magicpak|
The following is a dockerfile using
magicpakfor a docker image of
clang-format, a formatter for C/C++/etc. (example/clang-format)
FROM magicpak/debian:buster-magicpak1.2.0RUN apt-get -y update RUN apt-get -y --no-install-recommends install clang-format
RUN magicpak $(which clang-format) /bundle -v
--compress
--upx-arg --best
--test
--test-stdin "int main( ){ }"
--test-stdout "int main() {}"
--install-to /bin/FROM scratch COPY --from=0 /bundle /.
WORKDIR /workdir
CMD ["/bin/clang-format"]
magicpakcomes with absolutely no warranty. There's no guarantee that the processed bundle works properly and identically to the original executable. Although I had no problem using
magicpakfor building various kinds of images, it is recommended to use this with caution and make a careful examination of the resulting bundle.
Licensed under either of
at your option.
Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in the work by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without any additional terms or conditions.