Skip to content

Commit

Permalink
feat: add ability to pass custom Proxy implementation in clusterapi
Browse files Browse the repository at this point in the history
This is required for Theila to be able pass Kubeconfig without using
temp files.
Unfortunately there is no easier way to pass `rest.Config` into
clusterctl client directly.

Signed-off-by: Artem Chernyshev <[email protected]>
  • Loading branch information
Unix4ever committed Oct 14, 2021
1 parent b2f8f83 commit b018ea2
Show file tree
Hide file tree
Showing 4 changed files with 61 additions and 24 deletions.
2 changes: 1 addition & 1 deletion cmd/capi/cmd/options.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ type Options struct {
// DefaultOptions returns default settings.
func DefaultOptions() Options {
return Options{
CoreProvider: "cluster-api:v0.3.19",
CoreProvider: "cluster-api:v0.4.3",
BootstrapProviders: []string{"talos"},
InfrastructureProviders: []string{"aws"},
ControlPlaneProviders: []string{"talos"},
Expand Down
56 changes: 41 additions & 15 deletions pkg/capi/capi.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ import (
clientcmdapi "k8s.io/client-go/tools/clientcmd/api"
clusterctlv1 "sigs.k8s.io/cluster-api/cmd/clusterctl/api/v1alpha3"
"sigs.k8s.io/cluster-api/cmd/clusterctl/client"
"sigs.k8s.io/cluster-api/cmd/clusterctl/client/cluster"
"sigs.k8s.io/cluster-api/cmd/clusterctl/client/config"
runtimeclient "sigs.k8s.io/controller-runtime/pkg/client"

Expand All @@ -47,6 +48,7 @@ type Manager struct {

// Options for the CAPI installer.
type Options struct {
Proxy cluster.Proxy
Kubeconfig client.Kubeconfig
ClusterctlConfigPath string
CoreProvider string
Expand All @@ -73,30 +75,54 @@ func NewManager(ctx context.Context, options Options) (*Manager, error) {
return nil, err
}

clusterAPI.client, err = client.New(options.ClusterctlConfigPath, client.InjectConfig(configClient))
if err != nil {
return nil, err
opts := []client.Option{
client.InjectConfig(configClient),
}

clusterConfig, err := clusterAPI.GetKubeconfig(ctx)
if options.Proxy != nil {
opts = append(opts, client.InjectClusterClientFactory(func(input client.ClusterClientFactoryInput) (cluster.Client, error) {
return cluster.New(
cluster.Kubeconfig(input.Kubeconfig),
configClient,
cluster.InjectYamlProcessor(input.Processor),
cluster.InjectProxy(options.Proxy),
), nil
}))
}

clusterAPI.client, err = client.New(options.ClusterctlConfigPath, opts...)
if err != nil {
return nil, err
}

clusterAPI.config, err = clientcmd.BuildConfigFromKubeconfigGetter("", func() (*clientcmdapi.Config, error) {
c, e := clientcmd.LoadFromFile(clusterConfig.Path)
if e != nil {
return nil, e
if options.Proxy != nil {
clusterAPI.config, err = options.Proxy.GetConfig()
if err != nil {
return nil, err
}
} else {
var clusterConfig client.Kubeconfig

if clusterAPI.options.ContextName == "" {
clusterAPI.options.ContextName = c.CurrentContext
clusterConfig, err = clusterAPI.GetKubeconfig(ctx)
if err != nil {
return nil, err
}

return c, nil
})
if err != nil {
return nil, err
clusterAPI.config, err = clientcmd.BuildConfigFromKubeconfigGetter("", func() (*clientcmdapi.Config, error) {
c, e := clientcmd.LoadFromFile(clusterConfig.Path)
if e != nil {
return nil, e
}

if clusterAPI.options.ContextName == "" {
clusterAPI.options.ContextName = c.CurrentContext
}

return c, nil
})
if err != nil {
return nil, err
}
}

clusterAPI.clientset, err = kubernetes.NewForConfig(clusterAPI.config)
Expand Down Expand Up @@ -299,7 +325,7 @@ func (clusterAPI *Manager) FetchState(ctx context.Context) error {
})

if err = clusterAPI.runtimeClient.List(ctx, providers); err != nil {
return err
return fmt.Errorf("failed to list providers %w", err)
}

var (
Expand Down
25 changes: 18 additions & 7 deletions pkg/capi/cluster.go
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ import (
type Cluster struct {
manager *Manager
client *talosclient.Client
clientConfig *clientconfig.Config
cluster unstructured.Unstructured
name string
namespace string
Expand Down Expand Up @@ -123,18 +124,15 @@ func (cluster *Cluster) Sync(ctx context.Context) error {
return err
}

var (
clientConfig *clientconfig.Config
talosConfigString string
)
var talosConfigString string

if talosConfigString, found, err = unstructured.NestedString(talosConfig.Object, "status", "talosConfig"); err != nil {
return err
} else if !found {
return fieldNotFound("status", "talosConfig")
}

clientConfig, err = clientconfig.FromString(talosConfigString)
cluster.clientConfig, err = clientconfig.FromString(talosConfigString)

if err != nil {
return err
Expand Down Expand Up @@ -190,11 +188,11 @@ func (cluster *Cluster) Sync(ctx context.Context) error {
return fmt.Errorf("failed to find control plane nodes")
}

clientConfig.Contexts[clientConfig.Context].Endpoints = configEndpoints
cluster.clientConfig.Contexts[cluster.clientConfig.Context].Endpoints = configEndpoints

var talosClient *talosclient.Client

talosClient, err = talosclient.New(ctx, talosclient.WithConfig(clientConfig))
talosClient, err = talosclient.New(ctx, talosclient.WithConfig(cluster.clientConfig))
if err != nil {
return err
}
Expand All @@ -219,6 +217,19 @@ func (cluster *Cluster) TalosClient(ctx context.Context) (*talosclient.Client, e
return cluster.client, nil
}

// TalosConfig returns talosconfig for the cluster.
func (cluster *Cluster) TalosConfig(ctx context.Context) (*clientconfig.Config, error) {
if cluster.clientConfig != nil {
return cluster.clientConfig, nil
}

if err := cluster.Sync(ctx); err != nil {
return nil, err
}

return cluster.clientConfig, nil
}

// Health runs the healthcheck for the cluster.
func (cluster *Cluster) Health(ctx context.Context) error {
return retry.Constant(5*time.Minute, retry.WithUnits(10*time.Second)).RetryWithContext(ctx, func(ctx context.Context) error {
Expand Down
2 changes: 1 addition & 1 deletion pkg/capi/deploy.go
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ func DefaultDeployOptions() *DeployOptions {
ControlPlaneNodes: 1,
WorkerNodes: 1,
ClusterNamespace: "default",
TalosVersion: "v0.11",
TalosVersion: "v0.13",
KubernetesVersion: constants.DefaultKubernetesVersion,
}
}
Expand Down

0 comments on commit b018ea2

Please sign in to comment.