diff mbox series

[RFC] Add simple Alpine container

Message ID 20230926090101.7565-1-rpalethorpe@suse.com
State Superseded
Headers show
Series [RFC] Add simple Alpine container | expand

Commit Message

Richard Palethorpe Sept. 26, 2023, 9:01 a.m. UTC
Can be built with `docker/podman build .`. Then run with `podman -it
run sh`. It contains Kirk in /opt/kirk. So `cd /opt/kirk && ./kirk -f
ltp --run-suite syscalls` will run some tests.
---

Hello,

This builds and installs the LTP and Kirk inside an Alpine
container. The idea is to use a standard container workflow to build
and run the LTP from source. This helps with testing LTP itself and
running tests inside a container.

I'd like to add some container files to upstream to help with various
workflows.

The container has a number of problems:

1. If the Git directory has build artifacts in it, these are copied
   into the container (.dockerignore may help)
2. The resulting container is quite large (possibly due to debug symbols)
3. Where should we put container files and how should we name them?
4. Making the slightest change results in a complete container rebuild

Note that SUSE publishes a TW container based on our packaging system:
https://build.opensuse.org/project/show/benchmark:ltp:devel
https://registry.opensuse.org/cgi-bin/cooverview?srch_term=project%3D%5Ebenchmark+container%3D.*

Also, for developing tests, it may be better to build the LTP outside
of a container then copy in the files.

Latest tree is here:
https://github.com/richiejp/ltp/tree/alpine-container

 Containerfile | 35 +++++++++++++++++++++++++++++++++++
 1 file changed, 35 insertions(+)
 create mode 100644 Containerfile

Comments

Marius Kittler Sept. 26, 2023, 10:51 a.m. UTC | #1
Am Dienstag, 26. September 2023, 11:01:01 CEST schrieb Richard Palethorpe via 
ltp:
> Can be built with `docker/podman build .`. Then run with `podman -it
> run sh`. It contains Kirk in /opt/kirk. So `cd /opt/kirk && ./kirk -f
> ltp --run-suite syscalls` will run some tests.
> ---
> 
> Hello,
> 
> This builds and installs the LTP and Kirk inside an Alpine
> container. The idea is to use a standard container workflow to build
> and run the LTP from source. This helps with testing LTP itself and
> running tests inside a container.
> 
> I'd like to add some container files to upstream to help with various
> workflows.
> 
> The container has a number of problems:
> 
> 1. If the Git directory has build artifacts in it, these are copied
>    into the container (.dockerignore may help)

Doing an out-of-source-tree build might also help. Even just printing a 
warning/error in case the repository has already been configured might be good 
enough.

> 3. Where should we put container files and how should we name them?

Maybe just a subdirectory `container` and within that one subdirectory for 
each container.

> Also, for developing tests, it may be better to build the LTP outside
> of a container then copy in the files.

How would you do that? Relevant container-specific dependencies such as musl 
are within the container. One had to expose the container's filesystem tree 
somewhere in the regular filesystem and had to use that as prefix. That doesn't 
seem like an easy way of doing things.

By the way, to develop "[PATCH v1] Skip cgroup-related tests if `/sys/fs/
cgroup` readonly" I simply started on a fresh Alpine container, invoked our CI 
script for installing dependencies, followed the build instructions from the 
README, committed the container for later use and then just continued 
developing within the container as usual. (I was still using my editor from 
outside the container. So the clangd integration still assumed glibc headers. 
Maybe one could expose the container's filesystem on the host and change 
include paths via `.clangd` to prefer musl headers from within the container.)
Petr Vorel Sept. 27, 2023, 6:27 a.m. UTC | #2
Hi all,

> Can be built with `docker/podman build .`. Then run with `podman -it
> run sh`. It contains Kirk in /opt/kirk. So `cd /opt/kirk && ./kirk -f
> ltp --run-suite syscalls` will run some tests.
> ---

> Hello,

> This builds and installs the LTP and Kirk inside an Alpine
> container. The idea is to use a standard container workflow to build
> and run the LTP from source. This helps with testing LTP itself and
> running tests inside a container.

> I'd like to add some container files to upstream to help with various
> workflows.

> The container has a number of problems:

> 1. If the Git directory has build artifacts in it, these are copied
>    into the container (.dockerignore may help)
> 2. The resulting container is quite large (possibly due to debug symbols)
> 3. Where should we put container files and how should we name them?
> 4. Making the slightest change results in a complete container rebuild

> Note that SUSE publishes a TW container based on our packaging system:
> https://build.opensuse.org/project/show/benchmark:ltp:devel
> https://registry.opensuse.org/cgi-bin/cooverview?srch_term=project%3D%5Ebenchmark+container%3D.*

> Also, for developing tests, it may be better to build the LTP outside
> of a container then copy in the files.

> +++ b/Containerfile
> @@ -0,0 +1,35 @@
> +FROM alpine:3.18 AS build

Maybe we could use ARG and ENV to allow user to decide which distro to use.
https://stackoverflow.com/questions/76091578/is-it-possible-to-use-an-environment-variable-in-the-from-instruction-of-a-docke
This way we could use various scripts in ci.

> +ARG LTPROOT=/opt/ltp
> +
> +RUN mkdir /build
> +WORKDIR /build
> +COPY . /build
> +RUN ./ci/alpine.sh
> +RUN ./build.sh -p $LTPROOT -i
> +
> +FROM alpine:3.18
Also here.

> +ARG LTPROOT=/opt/ltp
> +ARG KIRKROOT=/opt/kirk
> +
> +RUN apk add \
> +            acl \
> +            keyutils \
> +            libaio \
> +            libacl \
> +            libcap \
> +            libselinux \
> +            libsepol \
> +            libtirpc \
> +            numactl \
> +            openssl \
> +            py3-msgpack
This somehow emulates ./ci/alpine.sh (i.e. ./ci/alpine.sh has keyutils-dev,
which should install also keyutils as a dependency). We could add a mechanism to
ci scripts to install runtime dependencies (e.g. './ci/alpine.sh runtime' would
install all runtime dependencies, './ci/alpine.sh runtime-syscalls' would
install only runtime dependencies for syscalls).

But better would be to move runtime dependencies to kirk. But unfortunately this
part from original Cyril's perl based runltp-ng was not ported to new Andrea's
python based runltp-ng/kirk.

Kind regards,
Petr

> +
> +COPY --from=build $LTPROOT $LTPROOT
> +ENV LTPROOT=$LTPROOT
> +ENV PATH=$LTPROOT/testcases/bin:$LTPROOT/bin:$PATH
> +
> +RUN mkdir -p $KIRKROOT
> +COPY --from=build /build/tools/kirk $KIRKROOT
> +
> +RUN adduser -D -g "Unprivileged LTP user" ltp
> +RUN su ltp
Richard Palethorpe Sept. 27, 2023, 7 a.m. UTC | #3
Hello,

Marius Kittler <mkittler@suse.de> writes:

> Am Dienstag, 26. September 2023, 11:01:01 CEST schrieb Richard Palethorpe via 
> ltp:
>> Can be built with `docker/podman build .`. Then run with `podman -it
>> run sh`. It contains Kirk in /opt/kirk. So `cd /opt/kirk && ./kirk -f
>> ltp --run-suite syscalls` will run some tests.
>> ---
>> 
>> Hello,
>> 
>> This builds and installs the LTP and Kirk inside an Alpine
>> container. The idea is to use a standard container workflow to build
>> and run the LTP from source. This helps with testing LTP itself and
>> running tests inside a container.
>> 
>> I'd like to add some container files to upstream to help with various
>> workflows.
>> 
>> The container has a number of problems:
>> 
>> 1. If the Git directory has build artifacts in it, these are copied
>>    into the container (.dockerignore may help)
>
> Doing an out-of-source-tree build might also help. Even just printing a 
> warning/error in case the repository has already been configured might be good 
> enough.

Good idea, perhaps check with Git that it is a clean
checkout. Especially because one could accidentally copy private files
into the container.

>
>> 3. Where should we put container files and how should we name them?
>
> Maybe just a subdirectory `container` and within that one subdirectory for 
> each container.
>
>> Also, for developing tests, it may be better to build the LTP outside
>> of a container then copy in the files.
>
> How would you do that? Relevant container-specific dependencies such as musl 
> are within the container. One had to expose the container's filesystem tree 
> somewhere in the regular filesystem and had to use that as prefix. That doesn't 
> seem like an easy way of doing things.
>
> By the way, to develop "[PATCH v1] Skip cgroup-related tests if `/sys/fs/
> cgroup` readonly" I simply started on a fresh Alpine container, invoked our CI 
> script for installing dependencies, followed the build instructions from the 
> README, committed the container for later use and then just continued 
> developing within the container as usual. (I was still using my editor from 
> outside the container. So the clangd integration still assumed glibc headers. 
> Maybe one could expose the container's filesystem on the host and change 
> include paths via `.clangd` to prefer musl headers from within the container.)

I'm not sure, you can export the LTP dir as a volume and use 'podman cp'
to copy the headers to somewhere on your host. This does feel hacky
though.

I suppose if clangd can run inside the container then it should be
possible to export its ports and connect to it from outside. However I
just have a checkout of the musl repo and manually search it.
Richard Palethorpe Sept. 27, 2023, 7:29 a.m. UTC | #4
Hello,

Petr Vorel <pvorel@suse.cz> writes:

> Hi all,
>
>> Can be built with `docker/podman build .`. Then run with `podman -it
>> run sh`. It contains Kirk in /opt/kirk. So `cd /opt/kirk && ./kirk -f
>> ltp --run-suite syscalls` will run some tests.
>> ---
>
>> Hello,
>
>> This builds and installs the LTP and Kirk inside an Alpine
>> container. The idea is to use a standard container workflow to build
>> and run the LTP from source. This helps with testing LTP itself and
>> running tests inside a container.
>
>> I'd like to add some container files to upstream to help with various
>> workflows.
>
>> The container has a number of problems:
>
>> 1. If the Git directory has build artifacts in it, these are copied
>>    into the container (.dockerignore may help)
>> 2. The resulting container is quite large (possibly due to debug symbols)
>> 3. Where should we put container files and how should we name them?
>> 4. Making the slightest change results in a complete container rebuild
>
>> Note that SUSE publishes a TW container based on our packaging system:
>> https://build.opensuse.org/project/show/benchmark:ltp:devel
>> https://registry.opensuse.org/cgi-bin/cooverview?srch_term=project%3D%5Ebenchmark+container%3D.*
>
>> Also, for developing tests, it may be better to build the LTP outside
>> of a container then copy in the files.
>
>> +++ b/Containerfile
>> @@ -0,0 +1,35 @@
>> +FROM alpine:3.18 AS build
>
> Maybe we could use ARG and ENV to allow user to decide which distro to use.
> https://stackoverflow.com/questions/76091578/is-it-possible-to-use-an-environment-variable-in-the-from-instruction-of-a-docke
> This way we could use various scripts in ci.

Sounds good assuming it does not make the container file too
complicated. The scripts you made have been really helpful.

>
>> +ARG LTPROOT=/opt/ltp
>> +
>> +RUN mkdir /build
>> +WORKDIR /build
>> +COPY . /build
>> +RUN ./ci/alpine.sh
>> +RUN ./build.sh -p $LTPROOT -i
>> +
>> +FROM alpine:3.18
> Also here.
>
>> +ARG LTPROOT=/opt/ltp
>> +ARG KIRKROOT=/opt/kirk
>> +
>> +RUN apk add \
>> +            acl \
>> +            keyutils \
>> +            libaio \
>> +            libacl \
>> +            libcap \
>> +            libselinux \
>> +            libsepol \
>> +            libtirpc \
>> +            numactl \
>> +            openssl \
>> +            py3-msgpack
> This somehow emulates ./ci/alpine.sh (i.e. ./ci/alpine.sh has keyutils-dev,
> which should install also keyutils as a dependency). We could add a mechanism to
> ci scripts to install runtime dependencies (e.g. './ci/alpine.sh runtime' would
> install all runtime dependencies, './ci/alpine.sh runtime-syscalls' would
> install only runtime dependencies for syscalls).

How about, for now, just an optional 'runtime' flag that only installs
runtime deps?

>
> But better would be to move runtime dependencies to kirk. But unfortunately this
> part from original Cyril's perl based runltp-ng was not ported to new Andrea's
> python based runltp-ng/kirk.

Well we could also make an Alpine, Flatpack, Nix package or any number
of other ways to build LTP and install the deps. Andrea deliberately
chose to decouple that from Kirk. However you could pass the CI scripts
to Kirk during test setup. It's just that those scripts don't live
inside the Kirk repo.

>
> Kind regards,
> Petr
>
>> +
>> +COPY --from=build $LTPROOT $LTPROOT
>> +ENV LTPROOT=$LTPROOT
>> +ENV PATH=$LTPROOT/testcases/bin:$LTPROOT/bin:$PATH
>> +
>> +RUN mkdir -p $KIRKROOT
>> +COPY --from=build /build/tools/kirk $KIRKROOT
>> +
>> +RUN adduser -D -g "Unprivileged LTP user" ltp
>> +RUN su ltp
Petr Vorel Sept. 27, 2023, 9:05 a.m. UTC | #5
Hi all,

...
> >> +++ b/Containerfile
> >> @@ -0,0 +1,35 @@
> >> +FROM alpine:3.18 AS build

> > Maybe we could use ARG and ENV to allow user to decide which distro to use.
> > https://stackoverflow.com/questions/76091578/is-it-possible-to-use-an-environment-variable-in-the-from-instruction-of-a-docke
> > This way we could use various scripts in ci.

> Sounds good assuming it does not make the container file too
> complicated. The scripts you made have been really helpful.

+1. We would need at least some comment. If there are more things to say, it
might be useful to have a wiki page about container based testing (if you have
time and energy to write it).

> >> +ARG LTPROOT=/opt/ltp
> >> +
> >> +RUN mkdir /build
> >> +WORKDIR /build
> >> +COPY . /build
> >> +RUN ./ci/alpine.sh
> >> +RUN ./build.sh -p $LTPROOT -i
> >> +
> >> +FROM alpine:3.18
> > Also here.

> >> +ARG LTPROOT=/opt/ltp
> >> +ARG KIRKROOT=/opt/kirk
> >> +
> >> +RUN apk add \
> >> +            acl \
> >> +            keyutils \
> >> +            libaio \
> >> +            libacl \
> >> +            libcap \
> >> +            libselinux \
> >> +            libsepol \
> >> +            libtirpc \
> >> +            numactl \
> >> +            openssl \
> >> +            py3-msgpack
> > This somehow emulates ./ci/alpine.sh (i.e. ./ci/alpine.sh has keyutils-dev,
> > which should install also keyutils as a dependency). We could add a mechanism to
> > ci scripts to install runtime dependencies (e.g. './ci/alpine.sh runtime' would
> > install all runtime dependencies, './ci/alpine.sh runtime-syscalls' would
> > install only runtime dependencies for syscalls).

> How about, for now, just an optional 'runtime' flag that only installs
> runtime deps?

Sure, no problem. The real work is to identify these runtime dependencies.
I mean not libraries without development headers (headers does not take that
much size, thus I would not bother), but various other tools (e.g. ip,
ping, mkfs.*, useradd, quotacheck, e4crypt, exportfs, modprobe, rmmod, ...) Some
of them are installed on normal distro, but not all; for sure most of them
aren't installed in the default container.

> > But better would be to move runtime dependencies to kirk. But unfortunately this
> > part from original Cyril's perl based runltp-ng was not ported to new Andrea's
> > python based runltp-ng/kirk.

> Well we could also make an Alpine, Flatpack, Nix package or any number
> of other ways to build LTP and install the deps. Andrea deliberately
> chose to decouple that from Kirk. However you could pass the CI scripts
I'm not sure if that was a correct decision. Sure, it might be easier to
maintain scripts like this in the projects kirk runs (e.g. LTP, Kselftest),
but OTOH I see a benefit in having unified interface for all project
(or at least run these upstreamed scripts in kirk in unified way).

> to Kirk during test setup. It's just that those scripts don't live
> inside the Kirk repo.

+1

Kind regards,
Petr
diff mbox series

Patch

diff --git a/Containerfile b/Containerfile
new file mode 100644
index 000000000..7bd50ce52
--- /dev/null
+++ b/Containerfile
@@ -0,0 +1,35 @@ 
+FROM alpine:3.18 AS build
+ARG LTPROOT=/opt/ltp
+
+RUN mkdir /build
+WORKDIR /build
+COPY . /build
+RUN ./ci/alpine.sh
+RUN ./build.sh -p $LTPROOT -i
+
+FROM alpine:3.18
+ARG LTPROOT=/opt/ltp
+ARG KIRKROOT=/opt/kirk
+
+RUN apk add \
+            acl \
+            keyutils \
+            libaio \
+            libacl \
+            libcap \
+            libselinux \
+            libsepol \
+            libtirpc \
+            numactl \
+            openssl \
+            py3-msgpack
+
+COPY --from=build $LTPROOT $LTPROOT
+ENV LTPROOT=$LTPROOT
+ENV PATH=$LTPROOT/testcases/bin:$LTPROOT/bin:$PATH
+
+RUN mkdir -p $KIRKROOT
+COPY --from=build /build/tools/kirk $KIRKROOT
+
+RUN adduser -D -g "Unprivileged LTP user" ltp
+RUN su ltp