mirror of
https://github.com/containers/podman.git
synced 2025-06-23 02:18:13 +08:00
Merge pull request #11180 from baude/buildplaykube
Add ability to build images in play kube
This commit is contained in:
@ -100,6 +100,9 @@ func init() {
|
|||||||
configmapFlagName := "configmap"
|
configmapFlagName := "configmap"
|
||||||
flags.StringSliceVar(&kubeOptions.ConfigMaps, configmapFlagName, []string{}, "`Pathname` of a YAML file containing a kubernetes configmap")
|
flags.StringSliceVar(&kubeOptions.ConfigMaps, configmapFlagName, []string{}, "`Pathname` of a YAML file containing a kubernetes configmap")
|
||||||
_ = kubeCmd.RegisterFlagCompletionFunc(configmapFlagName, completion.AutocompleteDefault)
|
_ = kubeCmd.RegisterFlagCompletionFunc(configmapFlagName, completion.AutocompleteDefault)
|
||||||
|
|
||||||
|
buildFlagName := "build"
|
||||||
|
flags.BoolVar(&kubeOptions.Build, buildFlagName, false, "Build all images in a YAML (given Containerfiles exist)")
|
||||||
}
|
}
|
||||||
_ = flags.MarkHidden("signature-policy")
|
_ = flags.MarkHidden("signature-policy")
|
||||||
}
|
}
|
||||||
|
@ -35,6 +35,36 @@ A Kubernetes PersistentVolumeClaim represents a Podman named volume. Only the Pe
|
|||||||
- volume.podman.io/gid
|
- volume.podman.io/gid
|
||||||
- volume.podman.io/mount-options
|
- volume.podman.io/mount-options
|
||||||
|
|
||||||
|
Play kube is capable of building images on the fly given the correct directory layout and Containerfiles. This
|
||||||
|
option is not available for remote clients yet. Consider the following excerpt from a YAML file:
|
||||||
|
```
|
||||||
|
apiVersion: v1
|
||||||
|
kind: Pod
|
||||||
|
metadata:
|
||||||
|
...
|
||||||
|
spec:
|
||||||
|
containers:
|
||||||
|
- command:
|
||||||
|
- top
|
||||||
|
- name: container
|
||||||
|
value: podman
|
||||||
|
image: foobar
|
||||||
|
...
|
||||||
|
```
|
||||||
|
|
||||||
|
If there is a directory named `foobar` in the current working directory with a file named `Containerfile` or `Dockerfile`,
|
||||||
|
Podman play kube will build that image and name it `foobar`. An example directory structure for this example would look
|
||||||
|
like:
|
||||||
|
```
|
||||||
|
|- mykubefiles
|
||||||
|
|- myplayfile.yaml
|
||||||
|
|- foobar
|
||||||
|
|- Containerfile
|
||||||
|
```
|
||||||
|
|
||||||
|
The build will consider `foobar` to be the context directory for the build. If there is an image in local storage
|
||||||
|
called `foobar`, the image will not be built unless the `--build` flag is used.
|
||||||
|
|
||||||
## OPTIONS
|
## OPTIONS
|
||||||
|
|
||||||
#### **--authfile**=*path*
|
#### **--authfile**=*path*
|
||||||
@ -45,6 +75,10 @@ If the authorization state is not found there, $HOME/.docker/config.json is chec
|
|||||||
Note: You can also override the default path of the authentication file by setting the REGISTRY\_AUTH\_FILE
|
Note: You can also override the default path of the authentication file by setting the REGISTRY\_AUTH\_FILE
|
||||||
environment variable. `export REGISTRY_AUTH_FILE=path`
|
environment variable. `export REGISTRY_AUTH_FILE=path`
|
||||||
|
|
||||||
|
#### **--build**
|
||||||
|
|
||||||
|
Build images even if they are found in the local storage.
|
||||||
|
|
||||||
#### **--cert-dir**=*path*
|
#### **--cert-dir**=*path*
|
||||||
|
|
||||||
Use certificates at *path* (\*.crt, \*.cert, \*.key) to connect to the registry.
|
Use certificates at *path* (\*.crt, \*.cert, \*.key) to connect to the registry.
|
||||||
|
@ -10,6 +10,8 @@ import (
|
|||||||
type PlayKubeOptions struct {
|
type PlayKubeOptions struct {
|
||||||
// Authfile - path to an authentication file.
|
// Authfile - path to an authentication file.
|
||||||
Authfile string
|
Authfile string
|
||||||
|
// Indicator to build all images with Containerfile or Dockerfile
|
||||||
|
Build bool
|
||||||
// CertDir - to a directory containing TLS certifications and keys.
|
// CertDir - to a directory containing TLS certifications and keys.
|
||||||
CertDir string
|
CertDir string
|
||||||
// Username for authenticating against the registry.
|
// Username for authenticating against the registry.
|
||||||
|
@ -7,9 +7,11 @@ import (
|
|||||||
"io"
|
"io"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"os"
|
"os"
|
||||||
|
"path/filepath"
|
||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
|
buildahDefine "github.com/containers/buildah/define"
|
||||||
"github.com/containers/common/libimage"
|
"github.com/containers/common/libimage"
|
||||||
"github.com/containers/common/pkg/config"
|
"github.com/containers/common/pkg/config"
|
||||||
"github.com/containers/image/v5/types"
|
"github.com/containers/image/v5/types"
|
||||||
@ -266,38 +268,68 @@ func (ic *ContainerEngine) playKubePod(ctx context.Context, podName string, podY
|
|||||||
}
|
}
|
||||||
|
|
||||||
containers := make([]*libpod.Container, 0, len(podYAML.Spec.Containers))
|
containers := make([]*libpod.Container, 0, len(podYAML.Spec.Containers))
|
||||||
|
cwd, err := os.Getwd()
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
for _, container := range podYAML.Spec.Containers {
|
for _, container := range podYAML.Spec.Containers {
|
||||||
// Contains all labels obtained from kube
|
// Contains all labels obtained from kube
|
||||||
labels := make(map[string]string)
|
labels := make(map[string]string)
|
||||||
|
var pulledImage *libimage.Image
|
||||||
// NOTE: set the pull policy to "newer". This will cover cases
|
buildFile, err := getBuildFile(container.Image, cwd)
|
||||||
// where the "latest" tag requires a pull and will also
|
if err != nil {
|
||||||
// transparently handle "localhost/" prefixed files which *may*
|
return nil, err
|
||||||
// refer to a locally built image OR an image running a
|
}
|
||||||
// registry on localhost.
|
existsLocally, err := ic.Libpod.LibimageRuntime().Exists(container.Image)
|
||||||
pullPolicy := config.PullPolicyNewer
|
if err != nil {
|
||||||
if len(container.ImagePullPolicy) > 0 {
|
return nil, err
|
||||||
// Make sure to lower the strings since K8s pull policy
|
}
|
||||||
// may be capitalized (see bugzilla.redhat.com/show_bug.cgi?id=1985905).
|
if (len(buildFile) > 0 && !existsLocally) || (len(buildFile) > 0 && options.Build) {
|
||||||
rawPolicy := string(container.ImagePullPolicy)
|
buildOpts := new(buildahDefine.BuildOptions)
|
||||||
pullPolicy, err = config.ParsePullPolicy(strings.ToLower(rawPolicy))
|
commonOpts := new(buildahDefine.CommonBuildOptions)
|
||||||
|
buildOpts.ConfigureNetwork = buildahDefine.NetworkDefault
|
||||||
|
buildOpts.Isolation = buildahDefine.IsolationChroot
|
||||||
|
buildOpts.CommonBuildOpts = commonOpts
|
||||||
|
buildOpts.Output = container.Image
|
||||||
|
if _, _, err := ic.Libpod.Build(ctx, *buildOpts, []string{buildFile}...); err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
i, _, err := ic.Libpod.LibimageRuntime().LookupImage(container.Image, new(libimage.LookupImageOptions))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
}
|
pulledImage = i
|
||||||
// This ensures the image is the image store
|
} else {
|
||||||
pullOptions := &libimage.PullOptions{}
|
// NOTE: set the pull policy to "newer". This will cover cases
|
||||||
pullOptions.AuthFilePath = options.Authfile
|
// where the "latest" tag requires a pull and will also
|
||||||
pullOptions.CertDirPath = options.CertDir
|
// transparently handle "localhost/" prefixed files which *may*
|
||||||
pullOptions.SignaturePolicyPath = options.SignaturePolicy
|
// refer to a locally built image OR an image running a
|
||||||
pullOptions.Writer = writer
|
// registry on localhost.
|
||||||
pullOptions.Username = options.Username
|
pullPolicy := config.PullPolicyNewer
|
||||||
pullOptions.Password = options.Password
|
if len(container.ImagePullPolicy) > 0 {
|
||||||
pullOptions.InsecureSkipTLSVerify = options.SkipTLSVerify
|
// Make sure to lower the strings since K8s pull policy
|
||||||
|
// may be capitalized (see bugzilla.redhat.com/show_bug.cgi?id=1985905).
|
||||||
|
rawPolicy := string(container.ImagePullPolicy)
|
||||||
|
pullPolicy, err = config.ParsePullPolicy(strings.ToLower(rawPolicy))
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// This ensures the image is the image store
|
||||||
|
pullOptions := &libimage.PullOptions{}
|
||||||
|
pullOptions.AuthFilePath = options.Authfile
|
||||||
|
pullOptions.CertDirPath = options.CertDir
|
||||||
|
pullOptions.SignaturePolicyPath = options.SignaturePolicy
|
||||||
|
pullOptions.Writer = writer
|
||||||
|
pullOptions.Username = options.Username
|
||||||
|
pullOptions.Password = options.Password
|
||||||
|
pullOptions.InsecureSkipTLSVerify = options.SkipTLSVerify
|
||||||
|
|
||||||
pulledImages, err := ic.Libpod.LibimageRuntime().Pull(ctx, container.Image, pullPolicy, pullOptions)
|
pulledImages, err := ic.Libpod.LibimageRuntime().Pull(ctx, container.Image, pullPolicy, pullOptions)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
}
|
||||||
|
pulledImage = pulledImages[0]
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handle kube annotations
|
// Handle kube annotations
|
||||||
@ -318,7 +350,7 @@ func (ic *ContainerEngine) playKubePod(ctx context.Context, podName string, podY
|
|||||||
|
|
||||||
specgenOpts := kube.CtrSpecGenOptions{
|
specgenOpts := kube.CtrSpecGenOptions{
|
||||||
Container: container,
|
Container: container,
|
||||||
Image: pulledImages[0],
|
Image: pulledImage,
|
||||||
Volumes: volumes,
|
Volumes: volumes,
|
||||||
PodID: pod.ID(),
|
PodID: pod.ID(),
|
||||||
PodName: podName,
|
PodName: podName,
|
||||||
@ -509,3 +541,48 @@ func sortKubeKinds(documentList [][]byte) ([][]byte, error) {
|
|||||||
|
|
||||||
return sortedDocumentList, nil
|
return sortedDocumentList, nil
|
||||||
}
|
}
|
||||||
|
func imageNamePrefix(imageName string) string {
|
||||||
|
prefix := imageName
|
||||||
|
s := strings.Split(prefix, ":")
|
||||||
|
if len(s) > 0 {
|
||||||
|
prefix = s[0]
|
||||||
|
}
|
||||||
|
s = strings.Split(prefix, "/")
|
||||||
|
if len(s) > 0 {
|
||||||
|
prefix = s[len(s)-1]
|
||||||
|
}
|
||||||
|
s = strings.Split(prefix, "@")
|
||||||
|
if len(s) > 0 {
|
||||||
|
prefix = s[0]
|
||||||
|
}
|
||||||
|
return prefix
|
||||||
|
}
|
||||||
|
|
||||||
|
func getBuildFile(imageName string, cwd string) (string, error) {
|
||||||
|
buildDirName := imageNamePrefix(imageName)
|
||||||
|
containerfilePath := filepath.Join(cwd, buildDirName, "Containerfile")
|
||||||
|
dockerfilePath := filepath.Join(cwd, buildDirName, "Dockerfile")
|
||||||
|
|
||||||
|
_, err := os.Stat(filepath.Join(containerfilePath))
|
||||||
|
if err == nil {
|
||||||
|
logrus.Debugf("building %s with %s", imageName, containerfilePath)
|
||||||
|
return containerfilePath, nil
|
||||||
|
}
|
||||||
|
// If the error is not because the file does not exist, take
|
||||||
|
// a mulligan and try Dockerfile. If that also fails, return that
|
||||||
|
// error
|
||||||
|
if err != nil && !os.IsNotExist(err) {
|
||||||
|
logrus.Errorf("%v: unable to check for %s", err, containerfilePath)
|
||||||
|
}
|
||||||
|
|
||||||
|
_, err = os.Stat(filepath.Join(dockerfilePath))
|
||||||
|
if err == nil {
|
||||||
|
logrus.Debugf("building %s with %s", imageName, dockerfilePath)
|
||||||
|
return dockerfilePath, nil
|
||||||
|
}
|
||||||
|
// Strike two
|
||||||
|
if os.IsNotExist(err) {
|
||||||
|
return "", nil
|
||||||
|
}
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
@ -845,3 +845,18 @@ func (p *PodmanTestIntegration) buildImage(dockerfile, imageName string, layers
|
|||||||
output := session.OutputToStringArray()
|
output := session.OutputToStringArray()
|
||||||
return output[len(output)-1]
|
return output[len(output)-1]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func writeYaml(content string, fileName string) error {
|
||||||
|
f, err := os.Create(fileName)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
defer f.Close()
|
||||||
|
|
||||||
|
_, err = f.WriteString(content)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
243
test/e2e/play_build_test.go
Normal file
243
test/e2e/play_build_test.go
Normal file
@ -0,0 +1,243 @@
|
|||||||
|
// +build !remote
|
||||||
|
|
||||||
|
// build for play kube is not supported on remote yet.
|
||||||
|
|
||||||
|
package integration
|
||||||
|
|
||||||
|
import (
|
||||||
|
"os"
|
||||||
|
"path/filepath"
|
||||||
|
|
||||||
|
. "github.com/containers/podman/v3/test/utils"
|
||||||
|
. "github.com/onsi/ginkgo"
|
||||||
|
. "github.com/onsi/gomega"
|
||||||
|
. "github.com/onsi/gomega/gexec"
|
||||||
|
)
|
||||||
|
|
||||||
|
var _ = Describe("Podman play kube with build", func() {
|
||||||
|
var (
|
||||||
|
tempdir string
|
||||||
|
err error
|
||||||
|
podmanTest *PodmanTestIntegration
|
||||||
|
)
|
||||||
|
|
||||||
|
BeforeEach(func() {
|
||||||
|
tempdir, err = CreateTempDirInTempDir()
|
||||||
|
if err != nil {
|
||||||
|
os.Exit(1)
|
||||||
|
}
|
||||||
|
podmanTest = PodmanTestCreate(tempdir)
|
||||||
|
podmanTest.Setup()
|
||||||
|
podmanTest.SeedImages()
|
||||||
|
})
|
||||||
|
|
||||||
|
AfterEach(func() {
|
||||||
|
podmanTest.Cleanup()
|
||||||
|
f := CurrentGinkgoTestDescription()
|
||||||
|
processTestResult(f)
|
||||||
|
|
||||||
|
})
|
||||||
|
|
||||||
|
var testYAML = `
|
||||||
|
apiVersion: v1
|
||||||
|
kind: Pod
|
||||||
|
metadata:
|
||||||
|
creationTimestamp: "2021-08-05T17:55:51Z"
|
||||||
|
labels:
|
||||||
|
app: foobar
|
||||||
|
name: top_pod
|
||||||
|
spec:
|
||||||
|
containers:
|
||||||
|
- command:
|
||||||
|
- top
|
||||||
|
env:
|
||||||
|
- name: PATH
|
||||||
|
value: /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
|
||||||
|
- name: TERM
|
||||||
|
value: xterm
|
||||||
|
- name: container
|
||||||
|
value: podman
|
||||||
|
image: foobar
|
||||||
|
name: foobar
|
||||||
|
resources: {}
|
||||||
|
securityContext:
|
||||||
|
allowPrivilegeEscalation: true
|
||||||
|
capabilities:
|
||||||
|
drop:
|
||||||
|
- CAP_MKNOD
|
||||||
|
- CAP_NET_RAW
|
||||||
|
- CAP_AUDIT_WRITE
|
||||||
|
privileged: false
|
||||||
|
readOnlyRootFilesystem: false
|
||||||
|
seLinuxOptions: {}
|
||||||
|
tty: true
|
||||||
|
workingDir: /
|
||||||
|
dnsConfig: {}
|
||||||
|
status: {}
|
||||||
|
`
|
||||||
|
|
||||||
|
var playBuildFile = `
|
||||||
|
FROM quay.io/libpod/alpine_nginx:latest
|
||||||
|
RUN apk update && apk add strace
|
||||||
|
LABEL homer=dad
|
||||||
|
`
|
||||||
|
var prebuiltImage = `
|
||||||
|
FROM quay.io/libpod/alpine_nginx:latest
|
||||||
|
RUN apk update && apk add strace
|
||||||
|
LABEL marge=mom
|
||||||
|
`
|
||||||
|
It("Check that image is built using Dockerfile", func() {
|
||||||
|
// Setup
|
||||||
|
yamlDir := filepath.Join(tempdir, RandomString(12))
|
||||||
|
err := os.Mkdir(yamlDir, 0755)
|
||||||
|
err = writeYaml(testYAML, filepath.Join(yamlDir, "top.yaml"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
app1Dir := filepath.Join(yamlDir, "foobar")
|
||||||
|
err = os.Mkdir(app1Dir, 0755)
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
err = writeYaml(playBuildFile, filepath.Join(app1Dir, "Dockerfile"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
|
||||||
|
// Switch to temp dir and restore it afterwards
|
||||||
|
cwd, err := os.Getwd()
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
Expect(os.Chdir(yamlDir)).To(BeNil())
|
||||||
|
defer func() { (Expect(os.Chdir(cwd)).To(BeNil())) }()
|
||||||
|
|
||||||
|
session := podmanTest.Podman([]string{"play", "kube", "top.yaml"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session).Should(Exit(0))
|
||||||
|
|
||||||
|
exists := podmanTest.Podman([]string{"image", "exists", "foobar"})
|
||||||
|
exists.WaitWithDefaultTimeout()
|
||||||
|
Expect(exists).Should(Exit(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"container", "inspect", "top_pod-foobar"})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect).Should(Exit(0))
|
||||||
|
inspectData := inspect.InspectContainerToJSON()
|
||||||
|
Expect(len(inspectData)).To(BeNumerically(">", 0))
|
||||||
|
Expect(inspectData[0].Config.Labels["homer"]).To(Equal("dad"))
|
||||||
|
})
|
||||||
|
|
||||||
|
It("Check that image is built using Containerfile", func() {
|
||||||
|
// Setup
|
||||||
|
yamlDir := filepath.Join(tempdir, RandomString(12))
|
||||||
|
err := os.Mkdir(yamlDir, 0755)
|
||||||
|
err = writeYaml(testYAML, filepath.Join(yamlDir, "top.yaml"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
app1Dir := filepath.Join(yamlDir, "foobar")
|
||||||
|
err = os.Mkdir(app1Dir, 0755)
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
err = writeYaml(playBuildFile, filepath.Join(app1Dir, "Containerfile"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
|
||||||
|
// Switch to temp dir and restore it afterwards
|
||||||
|
cwd, err := os.Getwd()
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
Expect(os.Chdir(yamlDir)).To(BeNil())
|
||||||
|
defer func() { (Expect(os.Chdir(cwd)).To(BeNil())) }()
|
||||||
|
|
||||||
|
session := podmanTest.Podman([]string{"play", "kube", "top.yaml"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session).Should(Exit(0))
|
||||||
|
|
||||||
|
exists := podmanTest.Podman([]string{"image", "exists", "foobar"})
|
||||||
|
exists.WaitWithDefaultTimeout()
|
||||||
|
Expect(exists).Should(Exit(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"container", "inspect", "top_pod-foobar"})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect).Should(Exit(0))
|
||||||
|
inspectData := inspect.InspectContainerToJSON()
|
||||||
|
Expect(len(inspectData)).To(BeNumerically(">", 0))
|
||||||
|
Expect(inspectData[0].Config.Labels["homer"]).To(Equal("dad"))
|
||||||
|
})
|
||||||
|
|
||||||
|
It("Do not build image if already in the local store", func() {
|
||||||
|
// Setup
|
||||||
|
yamlDir := filepath.Join(tempdir, RandomString(12))
|
||||||
|
err := os.Mkdir(yamlDir, 0755)
|
||||||
|
err = writeYaml(testYAML, filepath.Join(yamlDir, "top.yaml"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
|
||||||
|
// build an image called foobar but make sure it doesnt have
|
||||||
|
// the same label as the yaml buildfile, so we can check that
|
||||||
|
// the image is NOT rebuilt.
|
||||||
|
err = writeYaml(prebuiltImage, filepath.Join(yamlDir, "Containerfile"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
|
||||||
|
app1Dir := filepath.Join(yamlDir, "foobar")
|
||||||
|
err = os.Mkdir(app1Dir, 0755)
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
err = writeYaml(playBuildFile, filepath.Join(app1Dir, "Containerfile"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
|
||||||
|
// Switch to temp dir and restore it afterwards
|
||||||
|
cwd, err := os.Getwd()
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
Expect(os.Chdir(yamlDir)).To(BeNil())
|
||||||
|
defer func() { (Expect(os.Chdir(cwd)).To(BeNil())) }()
|
||||||
|
|
||||||
|
// Build the image into the local store
|
||||||
|
build := podmanTest.Podman([]string{"build", "-t", "foobar", "-f", "Containerfile"})
|
||||||
|
build.WaitWithDefaultTimeout()
|
||||||
|
Expect(build).Should(Exit(0))
|
||||||
|
|
||||||
|
session := podmanTest.Podman([]string{"play", "kube", "top.yaml"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session).Should(Exit(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"container", "inspect", "top_pod-foobar"})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect).Should(Exit(0))
|
||||||
|
inspectData := inspect.InspectContainerToJSON()
|
||||||
|
Expect(len(inspectData)).To(BeNumerically(">", 0))
|
||||||
|
Expect(inspectData[0].Config.Labels["homer"]).To(Equal(""))
|
||||||
|
Expect(inspectData[0].Config.Labels["marge"]).To(Equal("mom"))
|
||||||
|
})
|
||||||
|
|
||||||
|
It("--build should override image in store", func() {
|
||||||
|
// Setup
|
||||||
|
yamlDir := filepath.Join(tempdir, RandomString(12))
|
||||||
|
err := os.Mkdir(yamlDir, 0755)
|
||||||
|
err = writeYaml(testYAML, filepath.Join(yamlDir, "top.yaml"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
|
||||||
|
// build an image called foobar but make sure it doesnt have
|
||||||
|
// the same label as the yaml buildfile, so we can check that
|
||||||
|
// the image is NOT rebuilt.
|
||||||
|
err = writeYaml(prebuiltImage, filepath.Join(yamlDir, "Containerfile"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
|
||||||
|
app1Dir := filepath.Join(yamlDir, "foobar")
|
||||||
|
err = os.Mkdir(app1Dir, 0755)
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
err = writeYaml(playBuildFile, filepath.Join(app1Dir, "Containerfile"))
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
|
||||||
|
// Switch to temp dir and restore it afterwards
|
||||||
|
cwd, err := os.Getwd()
|
||||||
|
Expect(err).To(BeNil())
|
||||||
|
Expect(os.Chdir(yamlDir)).To(BeNil())
|
||||||
|
defer func() { (Expect(os.Chdir(cwd)).To(BeNil())) }()
|
||||||
|
|
||||||
|
// Build the image into the local store
|
||||||
|
build := podmanTest.Podman([]string{"build", "-t", "foobar", "-f", "Containerfile"})
|
||||||
|
build.WaitWithDefaultTimeout()
|
||||||
|
Expect(build).Should(Exit(0))
|
||||||
|
|
||||||
|
session := podmanTest.Podman([]string{"play", "kube", "--build", "top.yaml"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session).Should(Exit(0))
|
||||||
|
|
||||||
|
inspect := podmanTest.Podman([]string{"container", "inspect", "top_pod-foobar"})
|
||||||
|
inspect.WaitWithDefaultTimeout()
|
||||||
|
Expect(inspect).Should(Exit(0))
|
||||||
|
inspectData := inspect.InspectContainerToJSON()
|
||||||
|
Expect(len(inspectData)).To(BeNumerically(">", 0))
|
||||||
|
Expect(inspectData[0].Config.Labels["homer"]).To(Equal("dad"))
|
||||||
|
Expect(inspectData[0].Config.Labels["marge"]).To(Equal(""))
|
||||||
|
})
|
||||||
|
|
||||||
|
})
|
@ -512,21 +512,6 @@ var (
|
|||||||
defaultSecret = []byte(`{"FOO":"Zm9v","BAR":"YmFy"}`)
|
defaultSecret = []byte(`{"FOO":"Zm9v","BAR":"YmFy"}`)
|
||||||
)
|
)
|
||||||
|
|
||||||
func writeYaml(content string, fileName string) error {
|
|
||||||
f, err := os.Create(fileName)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
defer f.Close()
|
|
||||||
|
|
||||||
_, err = f.WriteString(content)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// getKubeYaml returns a kubernetes YAML document.
|
// getKubeYaml returns a kubernetes YAML document.
|
||||||
func getKubeYaml(kind string, object interface{}) (string, error) {
|
func getKubeYaml(kind string, object interface{}) (string, error) {
|
||||||
var yamlTemplate string
|
var yamlTemplate string
|
||||||
|
Reference in New Issue
Block a user