Skip to content

Commit

Permalink
feat: support private docker image authentication for custom analyzers
Browse files Browse the repository at this point in the history
Added authentication support for pulling private Docker images when adding custom analyzers, enhancing security and access control.

Signed-off-by: Matthis Holleville <[email protected]>
  • Loading branch information
matthisholleville committed Jul 22, 2024
1 parent cfc4308 commit 1ee5add
Show file tree
Hide file tree
Showing 4 changed files with 45 additions and 5 deletions.
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -514,9 +514,9 @@ _Adding custom analyzer without install_
k8sgpt custom-analyzer add --name my-custom-analyzer --port 8085
```

_Adding custom analyzer from docker image_
_Adding custom analyzer from docker image with auth_
```
k8sgpt custom-analyzer add --install --install-type docker --name my-custom-analyzer --package $MY_DOCKER_IMAGE --port 8085
k8sgpt custom-analyzer add --install --install-type docker --name my-custom-analyzer --package $MY_PRIVATE_DOCKER_IMAGE --port 8085 --username $MY_USERNAME --pasword $MY_PASSWORD
```

_Removing custom analyzer_
Expand Down
6 changes: 5 additions & 1 deletion cmd/customAnalyzer/add.go
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,8 @@ var (
packageUrl string
name string
url string
username string
password string
port int
)

Expand Down Expand Up @@ -67,7 +69,7 @@ var addCmd = &cobra.Command{
}

// create a pod in-cluster with custom analyzer
err = install.Deploy(packageUrl, name, url, port)
err = install.Deploy(packageUrl, name, url, username, password, port)
if err != nil {
color.Red("Error installing custom analyzer: %s", err.Error())
os.Exit(1)
Expand Down Expand Up @@ -97,6 +99,8 @@ func init() {
addCmd.Flags().StringVarP(&installType, "install-type", "t", "docker", "Specify the installation type (e.g., docker, kubernetes).")
addCmd.Flags().BoolVarP(&install, "install", "i", false, "Flag to indicate whether to install the custom analyzer after adding.")
addCmd.Flags().StringVarP(&packageUrl, "package", "p", "", "URL of the custom analyzer package.")
addCmd.Flags().StringVarP(&username, "username", "s", "", "Username used for pulling package.")
addCmd.Flags().StringVarP(&password, "password", "w", "", "Password used for pulling package.")
addCmd.Flags().StringVarP(&name, "name", "n", "my-custom-analyzer", "Name of the custom analyzer.")
addCmd.Flags().StringVarP(&url, "url", "u", "localhost", "URL for the custom analyzer connection.")
addCmd.Flags().IntVarP(&port, "port", "r", 8085, "Port for the custom analyzer connection.")
Expand Down
2 changes: 1 addition & 1 deletion pkg/customAnalyzer/customAnalyzer.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ type Connection struct {
}

type ICustomAnalyzer interface {
Deploy(packageUrl, name, url string, port int) error
Deploy(packageUrl, name, url, username, password string, port int) error
UnDeploy(name string) error
}

Expand Down
38 changes: 37 additions & 1 deletion pkg/customAnalyzer/docker/docker.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,17 @@ package docker

import (
"context"
"encoding/base64"
"encoding/json"
"fmt"
"io"
"os"
"strconv"

"github.com/docker/docker/api/types/container"
"github.com/docker/docker/api/types/filters"
"github.com/docker/docker/api/types/image"
"github.com/docker/docker/api/types/registry"
"github.com/docker/docker/client"
"github.com/docker/go-connections/nat"
)
Expand All @@ -28,7 +34,32 @@ func NewDocker() *Docker {
}
}

func (d *Docker) Deploy(packageUrl, name, url string, port int) error {
func (d *Docker) pullImage(imageRef, username, password string) error {
authConfig := registry.AuthConfig{
Username: username,
Password: password,
}
encodedJSON, err := json.Marshal(authConfig)
if err != nil {
panic(err)
}
authStr := base64.URLEncoding.EncodeToString(encodedJSON)

_, _, err = d.client.ImageInspectWithRaw(d.ctx, imageRef)
if err != nil {
out, err := d.client.ImagePull(d.ctx, imageRef, image.PullOptions{RegistryAuth: authStr})
if err != nil {
return err
}
defer out.Close()
io.Copy(os.Stdout, out)

Check failure on line 55 in pkg/customAnalyzer/docker/docker.go

View workflow job for this annotation

GitHub Actions / golangci-lint

[golangci] reported by reviewdog 🐶 Error return value of `io.Copy` is not checked (errcheck) Raw Output: pkg/customAnalyzer/docker/docker.go:55:10: Error return value of `io.Copy` is not checked (errcheck) io.Copy(os.Stdout, out) ^
}

return nil

}

func (d *Docker) Deploy(packageUrl, name, url, username, password string, port int) error {
portStr := strconv.Itoa(port)
containerPort := fmt.Sprintf("%s/tcp", portStr)

Expand All @@ -50,6 +81,11 @@ func (d *Docker) Deploy(packageUrl, name, url string, port int) error {
},
}

err := d.pullImage(packageUrl, username, password)
if err != nil {
return err
}

resp, err := d.client.ContainerCreate(d.ctx, config, hostConfig, nil, nil, name)
if err != nil {
return err
Expand Down

0 comments on commit 1ee5add

Please sign in to comment.