aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--pkg/api/handlers/compat/images_build.go10
-rw-r--r--pkg/bindings/images/build.go7
-rw-r--r--test/e2e/build/Containerfile.userns-auto2
-rw-r--r--test/e2e/run_userns_test.go30
4 files changed, 49 insertions, 0 deletions
diff --git a/pkg/api/handlers/compat/images_build.go b/pkg/api/handlers/compat/images_build.go
index 020991cc7..7ba1029a7 100644
--- a/pkg/api/handlers/compat/images_build.go
+++ b/pkg/api/handlers/compat/images_build.go
@@ -101,6 +101,7 @@ func BuildImage(w http.ResponseWriter, r *http.Request) {
ForceRm bool `schema:"forcerm"`
From string `schema:"from"`
HTTPProxy bool `schema:"httpproxy"`
+ IDMappingOptions string `schema:"idmappingoptions"`
IdentityLabel bool `schema:"identitylabel"`
Ignore bool `schema:"ignore"`
Isolation string `schema:"isolation"`
@@ -389,6 +390,14 @@ func BuildImage(w http.ResponseWriter, r *http.Request) {
}
}
+ var idMappingOptions buildahDefine.IDMappingOptions
+ if _, found := r.URL.Query()["idmappingoptions"]; found {
+ if err := json.Unmarshal([]byte(query.IDMappingOptions), &idMappingOptions); err != nil {
+ utils.BadRequest(w, "idmappingoptions", query.IDMappingOptions, err)
+ return
+ }
+ }
+
var cacheFrom reference.Named
if _, found := r.URL.Query()["cachefrom"]; found {
cacheFrom, err = parse.RepoNameToNamedReference(query.CacheFrom)
@@ -644,6 +653,7 @@ func BuildImage(w http.ResponseWriter, r *http.Request) {
Excludes: excludes,
ForceRmIntermediateCtrs: query.ForceRm,
From: fromImage,
+ IDMappingOptions: &idMappingOptions,
IgnoreUnrecognizedInstructions: query.Ignore,
Isolation: isolation,
Jobs: &jobs,
diff --git a/pkg/bindings/images/build.go b/pkg/bindings/images/build.go
index 2615bc516..8348ac54b 100644
--- a/pkg/bindings/images/build.go
+++ b/pkg/bindings/images/build.go
@@ -88,6 +88,13 @@ func Build(ctx context.Context, containerFiles []string, options entities.BuildO
}
params.Set("additionalbuildcontexts", string(additionalBuildContextMap))
}
+ if options.IDMappingOptions != nil {
+ idmappingsOptions, err := jsoniter.Marshal(options.IDMappingOptions)
+ if err != nil {
+ return nil, err
+ }
+ params.Set("idmappingoptions", string(idmappingsOptions))
+ }
if buildArgs := options.Args; len(buildArgs) > 0 {
bArgs, err := jsoniter.MarshalToString(buildArgs)
if err != nil {
diff --git a/test/e2e/build/Containerfile.userns-auto b/test/e2e/build/Containerfile.userns-auto
new file mode 100644
index 000000000..921610982
--- /dev/null
+++ b/test/e2e/build/Containerfile.userns-auto
@@ -0,0 +1,2 @@
+FROM alpine
+RUN cat /proc/self/uid_map
diff --git a/test/e2e/run_userns_test.go b/test/e2e/run_userns_test.go
index f247b2dac..62e512d3a 100644
--- a/test/e2e/run_userns_test.go
+++ b/test/e2e/run_userns_test.go
@@ -8,6 +8,7 @@ import (
"strings"
. "github.com/containers/podman/v4/test/utils"
+ "github.com/containers/storage"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
. "github.com/onsi/gomega/gexec"
@@ -42,6 +43,33 @@ var _ = Describe("Podman UserNS support", func() {
})
+ // Note: Lot of tests for build with --userns=auto are already there in buildah
+ // but they are skipped in podman CI because bud tests are executed in rootfull
+ // environment ( where mappings for the `containers` user is not present in /etc/subuid )
+ // causing them to skip hence this is a redundant test for sanity to make sure
+ // we don't break this feature for podman-remote.
+ It("podman build with --userns=auto", func() {
+ u, err := user.Current()
+ Expect(err).To(BeNil())
+ name := u.Name
+ if name == "root" {
+ name = "containers"
+ }
+ content, err := ioutil.ReadFile("/etc/subuid")
+ if err != nil {
+ Skip("cannot read /etc/subuid")
+ }
+ if !strings.Contains(string(content), name) {
+ Skip("cannot find mappings for the current user")
+ }
+ session := podmanTest.Podman([]string{"build", "-f", "build/Containerfile.userns-auto", "-t", "test", "--userns=auto"})
+ session.WaitWithDefaultTimeout()
+ Expect(session).Should(Exit(0))
+ // `1024` is the default size or length of the range of user IDs
+ // that is mapped between the two user namespaces by --userns=auto.
+ Expect(session.OutputToString()).To(ContainSubstring(fmt.Sprintf("%d", storage.AutoUserNsMinSize)))
+ })
+
It("podman uidmapping and gidmapping", func() {
session := podmanTest.Podman([]string{"run", "--uidmap=0:100:5000", "--gidmap=0:200:5000", "alpine", "echo", "hello"})
session.WaitWithDefaultTimeout()
@@ -157,6 +185,8 @@ var _ = Describe("Podman UserNS support", func() {
session.WaitWithDefaultTimeout()
Expect(session).Should(Exit(0))
l := session.OutputToString()
+ // `1024` is the default size or length of the range of user IDs
+ // that is mapped between the two user namespaces by --userns=auto.
Expect(l).To(ContainSubstring("1024"))
m[l] = l
}