Skip to content

Commit

Permalink
feat: pass config between KB and external plugin
Browse files Browse the repository at this point in the history
  • Loading branch information
Eileen-Yu committed Nov 15, 2023
1 parent a856875 commit 924daa7
Show file tree
Hide file tree
Showing 13 changed files with 240 additions and 17 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,8 @@ import (
"io"
"os"

"v1/scaffolds"

"sigs.k8s.io/kubebuilder/v3/pkg/plugin/external"
"v1/scaffolds"
)

// Run will run the actual steps of the plugin
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ go 1.20
require (
github.com/spf13/pflag v1.0.5
sigs.k8s.io/kubebuilder/v3 v3.13.0
sigs.k8s.io/yaml v1.3.0
)

require (
Expand All @@ -14,4 +15,7 @@ require (
golang.org/x/sys v0.13.0 // indirect
golang.org/x/text v0.13.0 // indirect
golang.org/x/tools v0.14.0 // indirect
gopkg.in/yaml.v2 v2.4.0 // indirect
)

replace sigs.k8s.io/kubebuilder/v3 => ../../../../../../../
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,8 @@ github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
github.com/onsi/ginkgo/v2 v2.13.0 h1:0jY9lJquiL8fcf3M4LAXN5aMlS/b2BV86HFFPCPMgE4=
github.com/onsi/gomega v1.29.0 h1:KIA/t2t5UBzoirT4H9tsML45GEbo3ouUnBHsCfD2tVg=
github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e h1:fD57ERR4JtEqsWbfPhv4DMiApHyliiK5xCTNVSPiaAs=
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
github.com/pkg/sftp v1.13.1/go.mod h1:3HaPG6Dq1ILlpPZRO0HVMrsydcdLt6HRDccSgb87qRg=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
Expand Down Expand Up @@ -449,8 +451,11 @@ google.golang.org/protobuf v1.24.0/go.mod h1:r/3tXBNzIEhYS9I1OUVjXDlt8tc493IdKGj
google.golang.org/protobuf v1.25.0/go.mod h1:9JNX74DMeImyA3h4bdi1ymwjUzf21/xIlbajtzgsN7c=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f h1:BLraFXnmrev5lT+xlilqcH8XK9/i0At2xKjWk4p6zsU=
gopkg.in/errgo.v2 v2.1.0/go.mod h1:hNsd1EY+bozCKY1Ytp96fpM3vjJbqLJn88ws8XvfDNI=
gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY=
gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
Expand All @@ -467,3 +472,4 @@ rsc.io/sampler v1.3.0/go.mod h1:T1hPZKmBbMNahiBKFy5HrXp6adAjACjK9JXDnKaTXpA=
sigs.k8s.io/kubebuilder/v3 v3.13.0 h1:ft1r2HdI29hEgtbuk3AEjOGX5A0N3jjbSA54oZzXH5I=
sigs.k8s.io/kubebuilder/v3 v3.13.0/go.mod h1:BA3wwWd7P31jNLH9x+l5TzK6Of61SwY469ChO1+G2Cc=
sigs.k8s.io/yaml v1.4.0 h1:Mk1wCc2gy/F0THH0TAp1QYyJNzRm2KCLy3o5ASXVI5E=
sigs.k8s.io/yaml v1.3.0/go.mod h1:GeOyir5tyXNByN85N/dRIT9es5UQNerPYEKK56eTBm8=
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import (
"github.com/spf13/pflag"
"sigs.k8s.io/kubebuilder/v3/pkg/plugin"
"sigs.k8s.io/kubebuilder/v3/pkg/plugin/external"
"sigs.k8s.io/yaml"
)

var ApiFlags = []external.Flag{
Expand Down Expand Up @@ -57,6 +58,40 @@ func ApiCmd(pr *external.PluginRequest) external.PluginResponse {
flags.Parse(pr.Args)
number, _ := flags.GetInt("number")

// Update the project config with GVK
cfg := PluginConfig{}
err := yaml.Unmarshal([]byte(pr.Config), &cfg)
if err != nil {
return external.PluginResponse{
Error: true,
ErrorMsgs: []string{
err.Error(),
},
}
}

// Create and append the new config info
newResource := ResourceData{
Group: "group",
Domain: "my.domain",
Version: "v1",
Kind: "Externalpluginsample",
}
cfg.Resources = append(cfg.Resources, newResource)

updatedConfig, err := yaml.Marshal(cfg)
if err != nil {
return external.PluginResponse{
Error: true,
ErrorMsgs: []string{
err.Error(),
},
}
}

// Update the PluginResponse with the modified config string
pluginResponse.Config = string(updatedConfig)

apiFile := api.NewApiFile(api.WithNumber(number))

// Phase 2 Plugins uses the concept of a "universe" to represent the filesystem for a plugin.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,15 @@ limitations under the License.
package scaffolds

import (
"v1/scaffolds/internal/templates"
"os"
"path/filepath"

"github.com/spf13/pflag"

"sigs.k8s.io/kubebuilder/v3/pkg/plugin"
"sigs.k8s.io/yaml"

"sigs.k8s.io/kubebuilder/v3/pkg/plugin/external"
"v1/scaffolds/internal/templates"
)

var InitFlags = []external.Flag{
Expand Down Expand Up @@ -58,6 +61,46 @@ func InitCmd(pr *external.PluginRequest) external.PluginResponse {
flags.Parse(pr.Args)
domain, _ := flags.GetString("domain")

// Update the project config with ProjectName
cfg := PluginConfig{}
err := yaml.Unmarshal([]byte(pr.Config), &cfg)
if err != nil {
return external.PluginResponse{
Error: true,
ErrorMsgs: []string{
err.Error(),
},
}
}

// Get current directory as the project name
cwd, err := os.Getwd()
if err != nil {
return external.PluginResponse{
Error: true,
ErrorMsgs: []string{
err.Error(),
},
}
}

dirName := filepath.Base(cwd)

cfg.ProjectName = dirName

updatedConfig, err := yaml.Marshal(cfg)
if err != nil {
return external.PluginResponse{
Error: true,
ErrorMsgs: []string{
err.Error(),
},
}
}

// Update the PluginResponse with the modified config string
pluginResponse.Config = string(updatedConfig)

initFile := templates.NewInitFile(templates.WithDomain(domain))

// Phase 2 Plugins uses the concept of a "universe" to represent the filesystem for a plugin.
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
/*
Copyright 2023 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/

package scaffolds

type PluginConfig struct {
ProjectName string `json:"projectname,omitempty"`
Resources []ResourceData `json:"resources,omitempty"`
}

type ResourceData struct {
Group string `json:"group,omitempty"`
Domain string `json:"domain,omitempty"`
Version string `json:"version"`
Kind string `json:"kind"`
}
6 changes: 6 additions & 0 deletions pkg/plugin/external/types.go
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,9 @@ type PluginRequest struct {
// Universe represents the modified file contents that gets updated over a series of plugin runs
// across the plugin chain. Initially, it starts out as empty.
Universe map[string]string `json:"universe"`

// Config stores the project configuration file.
Config string `json:"config"`
}

// PluginResponse is returned to kubebuilder by the plugin and contains all files
Expand Down Expand Up @@ -63,6 +66,9 @@ type PluginResponse struct {
// Flags contains the plugin specific flags that the plugin returns to Kubebuilder when it receives
// a request for a list of supported flags from Kubebuilder
Flags []Flag `json:"flags,omitempty"`

// Config stores the project configuration file.
Config string `json:"config"`
}

// Flag is meant to represent a CLI flag that is used by Kubebuilder to define flags that are parsed
Expand Down
17 changes: 14 additions & 3 deletions pkg/plugins/external/api.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ package external
import (
"github.com/spf13/pflag"

"sigs.k8s.io/kubebuilder/v3/pkg/config"
"sigs.k8s.io/kubebuilder/v3/pkg/machinery"
"sigs.k8s.io/kubebuilder/v3/pkg/model/resource"
"sigs.k8s.io/kubebuilder/v3/pkg/plugin"
Expand All @@ -32,8 +33,9 @@ const (
)

type createAPISubcommand struct {
Path string
Args []string
Path string
Args []string
config config.Config
}

func (p *createAPISubcommand) InjectResource(*resource.Resource) error {
Expand All @@ -56,10 +58,19 @@ func (p *createAPISubcommand) Scaffold(fs machinery.Filesystem) error {
Args: p.Args,
}

err := handlePluginResponse(fs, req, p.Path)
err := handlePluginResponse(fs, req, p.Path, p)
if err != nil {
return err
}

return nil
}

func (p *createAPISubcommand) InjectConfig(c config.Config) error {
p.config = c
return nil
}

func (p *createAPISubcommand) GetConfig() config.Config {
return p.config
}
17 changes: 14 additions & 3 deletions pkg/plugins/external/edit.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ package external
import (
"github.com/spf13/pflag"

"sigs.k8s.io/kubebuilder/v3/pkg/config"
"sigs.k8s.io/kubebuilder/v3/pkg/machinery"
"sigs.k8s.io/kubebuilder/v3/pkg/plugin"
"sigs.k8s.io/kubebuilder/v3/pkg/plugin/external"
Expand All @@ -27,8 +28,9 @@ import (
var _ plugin.EditSubcommand = &editSubcommand{}

type editSubcommand struct {
Path string
Args []string
Path string
Args []string
config config.Config
}

func (p *editSubcommand) UpdateMetadata(_ plugin.CLIMetadata, subcmdMeta *plugin.SubcommandMetadata) {
Expand All @@ -46,10 +48,19 @@ func (p *editSubcommand) Scaffold(fs machinery.Filesystem) error {
Args: p.Args,
}

err := handlePluginResponse(fs, req, p.Path)
err := handlePluginResponse(fs, req, p.Path, p)
if err != nil {
return err
}

return nil
}

func (p *editSubcommand) InjectConfig(c config.Config) error {
p.config = c
return nil
}

func (p *editSubcommand) GetConfig() config.Config {
return p.config
}
27 changes: 26 additions & 1 deletion pkg/plugins/external/helpers.go
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,11 @@ import (

"github.com/spf13/afero"
"github.com/spf13/pflag"
"sigs.k8s.io/kubebuilder/v3/pkg/config"
"sigs.k8s.io/kubebuilder/v3/pkg/machinery"
"sigs.k8s.io/kubebuilder/v3/pkg/plugin"
"sigs.k8s.io/kubebuilder/v3/pkg/plugin/external"
"sigs.k8s.io/yaml"
)

var outputGetter ExecOutputGetter = &execOutputGetter{}
Expand All @@ -51,6 +53,12 @@ type ExecOutputGetter interface {

type execOutputGetter struct{}

// PluginConfigHandler is an interface to update the config modified by external plugin.
type PluginConfigHandler interface {
GetConfig() config.Config
InjectConfig(config.Config) error
}

func (e *execOutputGetter) GetExecOutput(request []byte, path string) ([]byte, error) {
cmd := exec.Command(path) //nolint:gosec
cmd.Stdin = bytes.NewBuffer(request)
Expand Down Expand Up @@ -149,7 +157,8 @@ func getUniverseMap(fs machinery.Filesystem) (map[string]string, error) {
return universe, nil
}

func handlePluginResponse(fs machinery.Filesystem, req external.PluginRequest, path string) error {
// nolint:lll
func handlePluginResponse(fs machinery.Filesystem, req external.PluginRequest, path string, p PluginConfigHandler) error {
var err error

req.Universe, err = getUniverseMap(fs)
Expand All @@ -167,6 +176,22 @@ func handlePluginResponse(fs machinery.Filesystem, req external.PluginRequest, p
return fmt.Errorf("error getting current directory: %v", err)
}

// TODO: for debug only, would delete it
fmt.Println("This is the received config from plugin response!!!!!!!!!!!!!!!!!!!!!!!!!!!!!", res.Config)

// update the config
if res.Config != "" {
updatedConfig := p.GetConfig()

if err := yaml.Unmarshal([]byte(res.Config), updatedConfig); err != nil {
return fmt.Errorf("error unmarshalling the updated config from PluginResponse: %w", err)
}

if err := p.InjectConfig(updatedConfig); err != nil {
return fmt.Errorf("error injecting the updated config from PluginResponse: %w", err)
}
}

for filename, data := range res.Universe {
path := filepath.Join(currentDir, filename)
dir := filepath.Dir(path)
Expand Down
Loading

0 comments on commit 924daa7

Please sign in to comment.