Skip to content

Commit

Permalink
Add pull secrets and re-write image in Pod objects
Browse files Browse the repository at this point in the history
  • Loading branch information
divolgin committed Jul 30, 2020
1 parent 94156f4 commit 405aaef
Show file tree
Hide file tree
Showing 7 changed files with 143 additions and 77 deletions.
4 changes: 2 additions & 2 deletions pkg/base/images.go
Expand Up @@ -23,7 +23,7 @@ type FindPrivateImagesOptions struct {

type FindPrivateImagesResult struct {
Images []kustomizeimage.Image // images to be rewritten
Docs []*k8sdoc.Doc // docs that have rewritten images
Docs []k8sdoc.K8sDoc // docs that have rewritten images
CheckedImages []kotsv1beta1.InstallationImage // all images found in the installation
}

Expand Down Expand Up @@ -66,7 +66,7 @@ type FindObjectsWithImagesOptions struct {
BaseDir string
}

func FindObjectsWithImages(options FindObjectsWithImagesOptions) ([]*k8sdoc.Doc, error) {
func FindObjectsWithImages(options FindObjectsWithImagesOptions) ([]k8sdoc.K8sDoc, error) {
objects, err := image.GetObjectsWithImages(options.BaseDir)
if err != nil {
return nil, errors.Wrap(err, "failed to list upstream images")
Expand Down
38 changes: 11 additions & 27 deletions pkg/image/builder.go
Expand Up @@ -24,7 +24,6 @@ import (
"github.com/replicatedhq/kots/pkg/docker/registry"
"github.com/replicatedhq/kots/pkg/k8sdoc"
"github.com/replicatedhq/kots/pkg/logger"
"gopkg.in/yaml.v2"
kustomizeimage "sigs.k8s.io/kustomize/api/types"
)

Expand Down Expand Up @@ -90,10 +89,10 @@ func CopyImages(srcRegistry, destRegistry registry.RegistryOptions, appSlug stri
return newImages, nil
}

func GetPrivateImages(upstreamDir string, checkedImages map[string]ImageInfo, allPrivate bool) ([]string, []*k8sdoc.Doc, error) {
func GetPrivateImages(upstreamDir string, checkedImages map[string]ImageInfo, allPrivate bool) ([]string, []k8sdoc.K8sDoc, error) {
uniqueImages := make(map[string]bool)

objects := make([]*k8sdoc.Doc, 0) // all objects where images are referenced from
objects := make([]k8sdoc.K8sDoc, 0) // all objects where images are referenced from

err := filepath.Walk(upstreamDir,
func(path string, info os.FileInfo, err error) error {
Expand All @@ -110,7 +109,7 @@ func GetPrivateImages(upstreamDir string, checkedImages map[string]ImageInfo, al
return err
}

return listImagesInFile(contents, func(images []string, doc *k8sdoc.Doc) error {
return listImagesInFile(contents, func(images []string, doc k8sdoc.K8sDoc) error {
numPrivateImages := 0
for _, image := range images {
if allPrivate {
Expand Down Expand Up @@ -164,8 +163,8 @@ func GetPrivateImages(upstreamDir string, checkedImages map[string]ImageInfo, al
return result, objects, nil
}

func GetObjectsWithImages(upstreamDir string) ([]*k8sdoc.Doc, error) {
objects := make([]*k8sdoc.Doc, 0)
func GetObjectsWithImages(upstreamDir string) ([]k8sdoc.K8sDoc, error) {
objects := make([]k8sdoc.K8sDoc, 0)

err := filepath.Walk(upstreamDir,
func(path string, info os.FileInfo, err error) error {
Expand All @@ -182,7 +181,7 @@ func GetObjectsWithImages(upstreamDir string) ([]*k8sdoc.Doc, error) {
return err
}

return listImagesInFile(contents, func(images []string, doc *k8sdoc.Doc) error {
return listImagesInFile(contents, func(images []string, doc k8sdoc.K8sDoc) error {
if len(images) > 0 {
objects = append(objects, doc)
}
Expand Down Expand Up @@ -215,7 +214,7 @@ func copyImagesInFileBetweenRegistries(srcRegistry, destRegistry registry.Regist
savedImages[fmt.Sprintf("%s:%s", image.Name, image.NewTag)] = true
}

err := listImagesInFile(fileData, func(images []string, doc *k8sdoc.Doc) error {
err := listImagesInFile(fileData, func(images []string, doc k8sdoc.K8sDoc) error {
for _, image := range images {
if _, saved := savedImages[image]; saved {
continue
Expand All @@ -242,32 +241,17 @@ func copyImagesInFileBetweenRegistries(srcRegistry, destRegistry registry.Regist
return newImages, err
}

type processImagesFunc func([]string, *k8sdoc.Doc) error
type processImagesFunc func([]string, k8sdoc.K8sDoc) error

func listImagesInFile(contents []byte, handler processImagesFunc) error {
yamlDocs := bytes.Split(contents, []byte("\n---\n"))
for _, yamlDoc := range yamlDocs {
parsed := &k8sdoc.Doc{}
if err := yaml.Unmarshal(yamlDoc, parsed); err != nil {
parsed, err := k8sdoc.ParseYAML(yamlDoc)
if err != nil {
continue
}

images := make([]string, 0)
for _, container := range parsed.Spec.Template.Spec.Containers {
images = append(images, container.Image)
}

for _, container := range parsed.Spec.Template.Spec.InitContainers {
images = append(images, container.Image)
}

for _, container := range parsed.Spec.JobTemplate.Spec.Template.Spec.InitContainers {
images = append(images, container.Image)
}

for _, container := range parsed.Spec.JobTemplate.Spec.Template.Spec.Containers {
images = append(images, container.Image)
}
images := parsed.ListImages()

if err := handler(images, parsed); err != nil {
return err
Expand Down
125 changes: 125 additions & 0 deletions pkg/k8sdoc/types.go
@@ -1,12 +1,30 @@
package k8sdoc

import (
"github.com/pkg/errors"
"gopkg.in/yaml.v2"
corev1 "k8s.io/api/core/v1"
)

type K8sDoc interface {
PatchWithPullSecret(secret *corev1.Secret) K8sDoc
ListImages() []string
}

type Doc struct {
APIVersion string `yaml:"apiVersion"`
Kind string `yaml:"kind"`
Metadata Metadata `yaml:"metadata"`
Spec Spec `yaml:"spec"`
}

type PodDoc struct {
APIVersion string `yaml:"apiVersion"`
Kind string `yaml:"kind"`
Metadata Metadata `yaml:"metadata"`
Spec PodSpec `yaml:"spec"`
}

type Metadata struct {
Name string `yaml:"name"`
Namespace string `yaml:"namespace,omitempty"`
Expand Down Expand Up @@ -41,3 +59,110 @@ type ImagePullSecret map[string]string
type Container struct {
Image string `yaml:"image"`
}

func ParseYAML(yamlDoc []byte) (K8sDoc, error) {
doc := &Doc{}
if err := yaml.Unmarshal(yamlDoc, doc); err != nil {
return nil, errors.Wrap(err, "failed to parse yaml")
}

if doc.Kind != "Pod" {
return doc, nil
}

podDoc := &PodDoc{}
if err := yaml.Unmarshal(yamlDoc, podDoc); err != nil {
return nil, errors.Wrap(err, "failed to parse yaml")
}
return podDoc, nil
}

func (d *Doc) PatchWithPullSecret(secret *corev1.Secret) K8sDoc {
newObj := &Doc{
APIVersion: d.APIVersion,
Kind: d.Kind,
Metadata: Metadata{
Name: d.Metadata.Name,
Namespace: d.Metadata.Namespace,
Labels: d.Metadata.Labels,
},
}
switch d.Kind {
case "CronJob":
newObj.Spec = Spec{
JobTemplate: JobTemplate{
Spec: JobSpec{
Template: Template{
Spec: PodSpec{
ImagePullSecrets: []ImagePullSecret{
{"name": "kotsadm-replicated-registry"},
},
},
},
},
},
}

default:
newObj.Spec = Spec{
Template: Template{
Spec: PodSpec{
ImagePullSecrets: []ImagePullSecret{
{"name": "kotsadm-replicated-registry"},
},
},
},
}
}

return newObj
}

func (d *Doc) ListImages() []string {
images := make([]string, 0)
for _, container := range d.Spec.Template.Spec.Containers {
images = append(images, container.Image)
}

for _, container := range d.Spec.Template.Spec.InitContainers {
images = append(images, container.Image)
}

for _, container := range d.Spec.JobTemplate.Spec.Template.Spec.InitContainers {
images = append(images, container.Image)
}

for _, container := range d.Spec.JobTemplate.Spec.Template.Spec.Containers {
images = append(images, container.Image)
}
return images
}

func (d *PodDoc) PatchWithPullSecret(secret *corev1.Secret) K8sDoc {
return &PodDoc{
APIVersion: d.APIVersion,
Kind: d.Kind,
Metadata: Metadata{
Name: d.Metadata.Name,
Namespace: d.Metadata.Namespace,
Labels: d.Metadata.Labels,
},
Spec: PodSpec{
ImagePullSecrets: []ImagePullSecret{
{"name": "kotsadm-replicated-registry"},
},
},
}
}

func (d *PodDoc) ListImages() []string {
images := make([]string, 0)
for _, container := range d.Spec.Containers {
images = append(images, container.Image)
}

for _, container := range d.Spec.InitContainers {
images = append(images, container.Image)
}
return images
}
4 changes: 2 additions & 2 deletions pkg/midstream/midstream.go
Expand Up @@ -10,11 +10,11 @@ import (
type Midstream struct {
Kustomization *kustomizetypes.Kustomization
Base *base.Base
DocForPatches []*k8sdoc.Doc
DocForPatches []k8sdoc.K8sDoc
PullSecret *corev1.Secret
}

func CreateMidstream(b *base.Base, images []kustomizetypes.Image, objects []*k8sdoc.Doc, pullSecret *corev1.Secret) (*Midstream, error) {
func CreateMidstream(b *base.Base, images []kustomizetypes.Image, objects []k8sdoc.K8sDoc, pullSecret *corev1.Secret) (*Midstream, error) {
kustomization := kustomizetypes.Kustomization{
TypeMeta: kustomizetypes.TypeMeta{
APIVersion: "kustomize.config.k8s.io/v1beta1",
Expand Down
45 changes: 1 addition & 44 deletions pkg/midstream/write.go
Expand Up @@ -7,10 +7,8 @@ import (
"path/filepath"

"github.com/pkg/errors"
"github.com/replicatedhq/kots/pkg/k8sdoc"
"github.com/replicatedhq/kots/pkg/k8sutil"
yaml "gopkg.in/yaml.v2"
corev1 "k8s.io/api/core/v1"
kustomizetypes "sigs.k8s.io/kustomize/api/types"
k8syaml "sigs.k8s.io/yaml"
)
Expand Down Expand Up @@ -161,7 +159,7 @@ func (m *Midstream) writeObjectsWithPullSecret(options WriteOptions) error {
defer f.Close()

for _, o := range m.DocForPatches {
withPullSecret := obejctWithPullSecret(o, m.PullSecret)
withPullSecret := o.PatchWithPullSecret(m.PullSecret)

b, err := yaml.Marshal(withPullSecret)
if err != nil {
Expand Down Expand Up @@ -190,44 +188,3 @@ func removeFromPatches(patches []kustomizetypes.PatchStrategicMerge, filename st
}
return newPatches
}

func obejctWithPullSecret(obj *k8sdoc.Doc, secret *corev1.Secret) *k8sdoc.Doc {
newObj := &k8sdoc.Doc{
APIVersion: obj.APIVersion,
Kind: obj.Kind,
Metadata: k8sdoc.Metadata{
Name: obj.Metadata.Name,
Namespace: obj.Metadata.Namespace,
Labels: obj.Metadata.Labels,
},
}
switch obj.Kind {
case "CronJob":
newObj.Spec = k8sdoc.Spec{
JobTemplate: k8sdoc.JobTemplate{
Spec: k8sdoc.JobSpec{
Template: k8sdoc.Template{
Spec: k8sdoc.PodSpec{
ImagePullSecrets: []k8sdoc.ImagePullSecret{
{"name": "kotsadm-replicated-registry"},
},
},
},
},
},
}

default:
newObj.Spec = k8sdoc.Spec{
Template: k8sdoc.Template{
Spec: k8sdoc.PodSpec{
ImagePullSecrets: []k8sdoc.ImagePullSecret{
{"name": "kotsadm-replicated-registry"},
},
},
},
}
}

return newObj
}
2 changes: 1 addition & 1 deletion pkg/pull/pull.go
Expand Up @@ -282,7 +282,7 @@ func Pull(upstreamURI string, pullOptions PullOptions) (string, error) {

var pullSecret *corev1.Secret
var images []kustomizetypes.Image
var objects []*k8sdoc.Doc
var objects []k8sdoc.K8sDoc
if pullOptions.RewriteImages {

log.ActionWithSpinner("Copying private images")
Expand Down
2 changes: 1 addition & 1 deletion pkg/rewrite/rewrite.go
Expand Up @@ -145,7 +145,7 @@ func Rewrite(rewriteOptions RewriteOptions) error {

var pullSecret *corev1.Secret
var images []kustomizetypes.Image
var objects []*k8sdoc.Doc
var objects []k8sdoc.K8sDoc

if rewriteOptions.CopyImages || rewriteOptions.RegistryEndpoint != "" {
// When CopyImages is set, we copy images, rewrite all images, and use registry
Expand Down

0 comments on commit 405aaef

Please sign in to comment.