Skip to content

Commit

Permalink
tests: frontend/dockerfile: add dockerfile lint tests for WCOW
Browse files Browse the repository at this point in the history
A number of integration tests were initially skipped on Windows,
waiting for their platform-specific translations. See #4485.

This commit enables all the dockerfile linter tests that had
been skipped before.

Some of the tests did not need any platform specific change
since the lint warning were being generated before actual
image pull.

Signed-off-by: Anthony Nandaa <[email protected]>
  • Loading branch information
profnandaa committed Aug 20, 2024
1 parent 49f3d8f commit 2e92e16
Show file tree
Hide file tree
Showing 3 changed files with 143 additions and 43 deletions.
181 changes: 140 additions & 41 deletions frontend/dockerfile/dockerfile_lint_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -814,12 +814,28 @@ COPY Dockerfile .
BuildErrLocation: 2,
})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
ARG MY_OS=linux
ARG MY_ARCH=amd64
FROM --platform=linux/${MYARCH} busybox
COPY Dockerfile .
`)
`,
`
ARG MY_OS=windows
ARG MY_ARCH=amd64
FROM --platform=windows/${MYARCH} nanoserver
COPY Dockerfile .
`,
))

osStr := integration.UnixOrWindows("linux", "windows")
streamBuildErr := fmt.Sprintf(
"failed to solve: failed to parse platform %s/${MYARCH}: \"\" is an invalid component of \"%s/\": platform specifier component must match \"^[A-Za-z0-9_-]+$\": invalid argument (did you mean MY_ARCH?)",
osStr, osStr)
unmarshalBuildErr := fmt.Sprintf(
"failed to parse platform %s/${MYARCH}: \"\" is an invalid component of \"%s/\": platform specifier component must match \"^[A-Za-z0-9_-]+$\": invalid argument (did you mean MY_ARCH?)",
osStr, osStr)
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
Warnings: []expectedLintWarning{
Expand All @@ -832,16 +848,23 @@ COPY Dockerfile .
Line: 4,
},
},
StreamBuildErr: "failed to solve: failed to parse platform linux/${MYARCH}: \"\" is an invalid component of \"linux/\": platform specifier component must match \"^[A-Za-z0-9_-]+$\": invalid argument (did you mean MY_ARCH?)",
UnmarshalBuildErr: "failed to parse platform linux/${MYARCH}: \"\" is an invalid component of \"linux/\": platform specifier component must match \"^[A-Za-z0-9_-]+$\": invalid argument (did you mean MY_ARCH?)",
StreamBuildErr: streamBuildErr,
UnmarshalBuildErr: unmarshalBuildErr,
BuildErrLocation: 4,
})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
ARG tag=latest
FROM busybox:${tag}${version} AS b
COPY Dockerfile .
`)
`,
`
ARG tag=latest
FROM nanoserver:${tag}${version} AS b
COPY Dockerfile .
`,
))
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
Warnings: []expectedLintWarning{
Expand Down Expand Up @@ -894,27 +917,50 @@ COPY Dockerfile${foo} .
`)
checkLinterWarnings(t, sb, &lintTestParams{Dockerfile: dockerfile})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
FROM alpine AS base
ARG foo=Dockerfile
FROM base
COPY $foo .
`)
`,
`
FROM nanoserver AS base
ARG foo=Dockerfile
FROM base
COPY $foo .
`,
))
checkLinterWarnings(t, sb, &lintTestParams{Dockerfile: dockerfile})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
FROM alpine
RUN echo $PATH
`)
`,
`
FROM nanoserver
RUN echo $PATH
`,
))
checkLinterWarnings(t, sb, &lintTestParams{Dockerfile: dockerfile})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
FROM alpine
COPY $foo .
ARG foo=bar
RUN echo $foo
`)
`,
`
FROM nanoserver
COPY $foo .
ARG foo=bar
RUN echo $foo
`,
))
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
Warnings: []expectedLintWarning{
Expand All @@ -929,13 +975,22 @@ RUN echo $foo
},
})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
FROM alpine
ARG DIR_BINARIES=binaries/
ARG DIR_ASSETS=assets/
ARG DIR_CONFIG=config/
COPY $DIR_ASSET .
`)
`,
`
FROM nanoserver
ARG DIR_BINARIES=binaries/
ARG DIR_ASSETS=assets/
ARG DIR_CONFIG=config/
COPY $DIR_ASSET .
`,
))
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
Warnings: []expectedLintWarning{
Expand All @@ -950,10 +1005,16 @@ COPY $DIR_ASSET .
},
})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
FROM alpine
ENV PATH=$PAHT:/tmp/bin
`)
`,
`
FROM nanoserver
ENV PATH=$PAHT:/tmp/bin
`,
))
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
Warnings: []expectedLintWarning{
Expand Down Expand Up @@ -1142,10 +1203,16 @@ FROM --platform=${TARGETPLATFORM} scratch
}

func testInvalidDefaultArgInFrom(t *testing.T, sb integration.Sandbox) {
dockerfile := []byte(`
dockerfile := []byte(integration.UnixOrWindows(
`
ARG VERSION
FROM busybox:$VERSION
`)
`,
`
ARG VERSION
FROM nanoserver:$VERSION
`,
))
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
FrontendAttrs: map[string]string{
Expand All @@ -1156,9 +1223,12 @@ FROM busybox:$VERSION
RuleName: "InvalidDefaultArgInFrom",
Description: "Default value for global ARG results in an empty or invalid base image name",
URL: "https://docs.docker.com/go/dockerfile/rule/invalid-default-arg-in-from/",
Detail: "Default value for ARG busybox:$VERSION results in empty or invalid base image name",
Line: 3,
Level: 1,
Detail: fmt.Sprintf(
"Default value for ARG %s:$VERSION results in empty or invalid base image name",
integration.UnixOrWindows("busybox", "nanoserver"),
),
Line: 3,
Level: 1,
},
},
})
Expand All @@ -1170,7 +1240,7 @@ FROM $IMAGE
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
FrontendAttrs: map[string]string{
"build-arg:IMAGE": "busybox:latest",
"build-arg:IMAGE": integration.UnixOrWindows("busybox:latest", "nanoserver:latest"),
},
Warnings: []expectedLintWarning{
{
Expand All @@ -1184,57 +1254,84 @@ FROM $IMAGE
},
})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
ARG SFX="box:"
FROM busy${SFX}
`)
`,
`
ARG SFX="server:"
FROM nano${SFX}
`,
))
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
FrontendAttrs: map[string]string{
"build-arg:SFX": "box:latest",
"build-arg:SFX": integration.UnixOrWindows("box:latest", "server:latest"),
},
Warnings: []expectedLintWarning{
{
RuleName: "InvalidDefaultArgInFrom",
Description: "Default value for global ARG results in an empty or invalid base image name",
URL: "https://docs.docker.com/go/dockerfile/rule/invalid-default-arg-in-from/",
Detail: "Default value for ARG busy${SFX} results in empty or invalid base image name",
Line: 3,
Level: 1,
Detail: fmt.Sprintf(
"Default value for ARG %s${SFX} results in empty or invalid base image name",
integration.UnixOrWindows("busy", "nano"),
),
Line: 3,
Level: 1,
},
},
})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
ARG VERSION="latest"
FROM busybox:${VERSION}
`)
`,
`
ARG VERSION="latest"
FROM nanoserver:${VERSION}
`,
))
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
FrontendAttrs: map[string]string{
"build-arg:VERSION": "latest",
},
})

dockerfile = []byte(`
dockerfile = []byte(integration.UnixOrWindows(
`
ARG BUSYBOX_VARIANT=""
FROM busybox:stable${BUSYBOX_VARIANT}
`)
`,
`
ARG BUSYBOX_VARIANT=""
FROM nanoserver:plus${BUSYBOX_VARIANT}
`,
))
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
FrontendAttrs: map[string]string{
"build-arg:BUSYBOX_VARIANT": "-musl",
"build-arg:BUSYBOX_VARIANT": integration.UnixOrWindows("-musl", "-busybox"),
},
})

dockerfile = []byte(`
ARG BUSYBOX_VARIANT
FROM busybox:stable${BUSYBOX_VARIANT}
`)
dockerfile = []byte(integration.UnixOrWindows(
`
ARG BUSYBOX_VARIANT
FROM busybox:stable${BUSYBOX_VARIANT}
`,
`
ARG BUSYBOX_VARIANT
FROM nanoserver:plus${BUSYBOX_VARIANT}
`,
))
checkLinterWarnings(t, sb, &lintTestParams{
Dockerfile: dockerfile,
FrontendAttrs: map[string]string{
"build-arg:BUSYBOX_VARIANT": "-musl",
"build-arg:BUSYBOX_VARIANT": integration.UnixOrWindows("-musl", "-busybox"),
},
})
}
Expand Down Expand Up @@ -1368,10 +1465,14 @@ func checkProgressStream(t *testing.T, sb integration.Sandbox, lintTest *lintTes

f := getFrontend(t, sb)

platformStr := integration.UnixOrWindows(
"linux/amd64,linux/arm64",
"windows/amd64",
)
attrs := lintTest.FrontendAttrs
if attrs == nil {
attrs = map[string]string{
"platform": "linux/amd64,linux/arm64",
"platform": platformStr,
}
}

Expand Down Expand Up @@ -1420,8 +1521,6 @@ func checkLinterWarnings(t *testing.T, sb integration.Sandbox, lintTest *lintTes
return lintTest.Warnings[i].Line < lintTest.Warnings[j].Line
})

integration.SkipOnPlatform(t, "windows")

if lintTest.TmpDir == nil {
testfiles := []fstest.Applier{
fstest.CreateFile("Dockerfile", lintTest.Dockerfile, 0600),
Expand Down
2 changes: 1 addition & 1 deletion frontend/dockerfile/dockerfile_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -234,7 +234,7 @@ func init() {

images := integration.UnixOrWindows(
[]string{"busybox:latest", "alpine:latest"},
[]string{"nanoserver:latest", "nanoserver:plus"})
[]string{"nanoserver:latest", "nanoserver:plus", "nanoserver:plus-busybox"})
opts = []integration.TestOpt{
integration.WithMirroredImages(integration.OfficialImages(images...)),
integration.WithMatrix("frontend", frontends),
Expand Down
3 changes: 2 additions & 1 deletion util/testutil/integration/util_windows.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,8 @@ var windowsImagesMirrorMap = map[string]string{
// nanoserver with extra binaries, like fc.exe
// TODO(profnandaa): get an approved/compliant repo, placeholder for now
// see dockerfile here - https://github.com/microsoft/windows-container-tools/pull/178
"nanoserver:plus": "docker.io/wintools/nanoserver:ltsc2022",
"nanoserver:plus": "docker.io/wintools/nanoserver:ltsc2022",
"nanoserver:plus-busybox": "docker.io/wintools/nanoserver:ltsc2022",
}

// abstracted function to handle pipe dialing on windows.
Expand Down

0 comments on commit 2e92e16

Please sign in to comment.