Skip to content

Commit

Permalink
dataclients/kubernetes: add token file flag
Browse files Browse the repository at this point in the history
Add flag to supply token file when running outside of cluster.

Signed-off-by: Alexander Yastrebov <alexander.yastrebov@zalando.de>
  • Loading branch information
AlexanderYastrebov committed Sep 13, 2023
1 parent 3419310 commit b11ea9b
Show file tree
Hide file tree
Showing 4 changed files with 30 additions and 12 deletions.
7 changes: 5 additions & 2 deletions config/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -151,6 +151,7 @@ type Config struct {
KubernetesIngress bool `yaml:"kubernetes"`
KubernetesInCluster bool `yaml:"kubernetes-in-cluster"`
KubernetesURL string `yaml:"kubernetes-url"`
KubernetesTokenFile string `yaml:"kubernetes-token-file"`
KubernetesHealthcheck bool `yaml:"kubernetes-healthcheck"`
KubernetesHTTPSRedirect bool `yaml:"kubernetes-https-redirect"`
KubernetesHTTPSRedirectCode int `yaml:"kubernetes-https-redirect-code"`
Expand Down Expand Up @@ -436,8 +437,9 @@ func NewConfig() *Config {

// Kubernetes:
flag.BoolVar(&cfg.KubernetesIngress, "kubernetes", false, "enables skipper to generate routes for ingress resources in kubernetes cluster. Enables -normalize-host")
flag.BoolVar(&cfg.KubernetesInCluster, "kubernetes-in-cluster", false, "specify if skipper is running inside kubernetes cluster")
flag.StringVar(&cfg.KubernetesURL, "kubernetes-url", "", "kubernetes API base URL for the ingress data client; requires kubectl proxy running; omit if kubernetes-in-cluster is set to true")
flag.BoolVar(&cfg.KubernetesInCluster, "kubernetes-in-cluster", false, "specify if skipper is running inside kubernetes cluster. It will automatically discover API server URL and service account token")
flag.StringVar(&cfg.KubernetesURL, "kubernetes-url", "", "kubernetes API server URL, ignored if kubernetes-in-cluster is set to true")
flag.StringVar(&cfg.KubernetesTokenFile, "kubernetes-token-file", "", "kubernetes token file path, ignored if kubernetes-in-cluster is set to true")
flag.BoolVar(&cfg.KubernetesHealthcheck, "kubernetes-healthcheck", true, "automatic healthcheck route for internal IPs with path /kube-system/healthz; valid only with kubernetes")
flag.BoolVar(&cfg.KubernetesHTTPSRedirect, "kubernetes-https-redirect", true, "automatic HTTP->HTTPS redirect route; valid only with kubernetes")
flag.IntVar(&cfg.KubernetesHTTPSRedirectCode, "kubernetes-https-redirect-code", 308, "overrides the default redirect code (308) when used together with -kubernetes-https-redirect")
Expand Down Expand Up @@ -779,6 +781,7 @@ func (c *Config) ToOptions() skipper.Options {
Kubernetes: c.KubernetesIngress,
KubernetesInCluster: c.KubernetesInCluster,
KubernetesURL: c.KubernetesURL,
KubernetesTokenFile: c.KubernetesTokenFile,
KubernetesHealthcheck: c.KubernetesHealthcheck,
KubernetesHTTPSRedirect: c.KubernetesHTTPSRedirect,
KubernetesHTTPSRedirectCode: c.KubernetesHTTPSRedirectCode,
Expand Down
26 changes: 16 additions & 10 deletions dataclients/kubernetes/clusterclient.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ type clusterClient struct {
endpointsURI string
secretsURI string
tokenProvider secrets.SecretsProvider
tokenFile string
apiURL string
certificateRegistry *certregistry.CertRegistry

Expand Down Expand Up @@ -168,17 +169,22 @@ func newClusterClient(o Options, apiURL, ingCls, rgCls string, quit <-chan struc

if o.KubernetesInCluster {
c.tokenProvider = secrets.NewSecretPaths(time.Minute)
err := c.tokenProvider.Add(serviceAccountDir + serviceAccountTokenKey)
if err != nil {
log.Errorf("Failed to Add secret %s: %v", serviceAccountDir+serviceAccountTokenKey, err)
return nil, err
c.tokenFile = serviceAccountDir + serviceAccountTokenKey
} else if o.TokenFile != "" {
c.tokenProvider = secrets.NewSecretPaths(time.Minute)
c.tokenFile = o.TokenFile
}

if c.tokenProvider != nil {
if err := c.tokenProvider.Add(c.tokenFile); err != nil {
return nil, fmt.Errorf("failed to add secret %s: %v", c.tokenFile, err)
}

b, ok := c.tokenProvider.GetSecret(serviceAccountDir + serviceAccountTokenKey)
if !ok {
return nil, fmt.Errorf("failed to GetSecret: %s", serviceAccountDir+serviceAccountTokenKey)
if b, ok := c.tokenProvider.GetSecret(c.tokenFile); ok {
log.Debugf("Got secret %d bytes from %s", len(b), c.tokenFile)
} else {
return nil, fmt.Errorf("failed to get secret %s", c.tokenFile)
}
log.Debugf("Got secret %d bytes", len(b))
}

if o.KubernetesNamespace != "" {
Expand Down Expand Up @@ -227,9 +233,9 @@ func (c *clusterClient) createRequest(uri string, body io.Reader) (*http.Request
}

if c.tokenProvider != nil {
token, ok := c.tokenProvider.GetSecret(serviceAccountDir + serviceAccountTokenKey)
token, ok := c.tokenProvider.GetSecret(c.tokenFile)
if !ok {
return nil, fmt.Errorf("secret not found: %v", serviceAccountDir+serviceAccountTokenKey)
return nil, fmt.Errorf("secret not found: %v", c.tokenFile)
}
req.Header.Set("Authorization", "Bearer "+string(token))
}
Expand Down
4 changes: 4 additions & 0 deletions dataclients/kubernetes/kube.go
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,10 @@ type Options struct {
// environment variables.)
KubernetesURL string

// TokenFile configures path to the token file.
// Defaults to /var/run/secrets/kubernetes.io/serviceaccount/token when running in-cluster.
TokenFile string

// KubernetesNamespace is used to switch between finding ingresses in the cluster-scope or limit
// the ingresses to only those in the specified namespace. Defaults to "" which means monitor ingresses
// in the cluster-scope.
Expand Down
5 changes: 5 additions & 0 deletions skipper.go
Original file line number Diff line number Diff line change
Expand Up @@ -166,6 +166,10 @@ type Options struct {
// skipper is not running in-cluster, the default API URL will be used.
KubernetesURL string

// KubernetesTokenFile configures path to the token file.
// Defaults to /var/run/secrets/kubernetes.io/serviceaccount/token when running in-cluster.
KubernetesTokenFile string

// KubernetesHealthcheck, when Kubernetes ingress is set, indicates
// whether an automatic healthcheck route should be generated. The
// generated route will report healthyness when the Kubernetes API
Expand Down Expand Up @@ -913,6 +917,7 @@ func (o *Options) KubernetesDataClientOptions() kubernetes.Options {
DefaultFiltersDir: o.DefaultFiltersDir,
KubernetesInCluster: o.KubernetesInCluster,
KubernetesURL: o.KubernetesURL,
TokenFile: o.KubernetesTokenFile,
KubernetesNamespace: o.KubernetesNamespace,
KubernetesEnableEastWest: o.KubernetesEnableEastWest,
KubernetesEastWestDomain: o.KubernetesEastWestDomain,
Expand Down

0 comments on commit b11ea9b

Please sign in to comment.