Merge pull request #471 from vmware-tanzu/change-credentialissuer-strategies-api
Deprecate status.kubeConfigInfo field in CredentialIssuer and move this data into strategies field.
This commit is contained in:
commit
30f5f66090
@ -8,6 +8,9 @@ import metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
|||||||
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
||||||
type StrategyType string
|
type StrategyType string
|
||||||
|
|
||||||
|
// +kubebuilder:validation:Enum=TokenCredentialRequestAPI
|
||||||
|
type FrontendType string
|
||||||
|
|
||||||
// +kubebuilder:validation:Enum=Success;Error
|
// +kubebuilder:validation:Enum=Success;Error
|
||||||
type StrategyStatus string
|
type StrategyStatus string
|
||||||
|
|
||||||
@ -17,11 +20,14 @@ type StrategyReason string
|
|||||||
const (
|
const (
|
||||||
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
||||||
|
|
||||||
|
TokenCredentialRequestAPIFrontendType = FrontendType("TokenCredentialRequestAPI")
|
||||||
|
|
||||||
SuccessStrategyStatus = StrategyStatus("Success")
|
SuccessStrategyStatus = StrategyStatus("Success")
|
||||||
ErrorStrategyStatus = StrategyStatus("Error")
|
ErrorStrategyStatus = StrategyStatus("Error")
|
||||||
|
|
||||||
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
||||||
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
CouldNotGetClusterInfoStrategyReason = StrategyReason("CouldNotGetClusterInfo")
|
||||||
|
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
||||||
)
|
)
|
||||||
|
|
||||||
// Status of a credential issuer.
|
// Status of a credential issuer.
|
||||||
@ -30,6 +36,7 @@ type CredentialIssuerStatus struct {
|
|||||||
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
||||||
|
|
||||||
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
||||||
|
// This field is deprecated and will be removed in a future version.
|
||||||
// +optional
|
// +optional
|
||||||
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
||||||
}
|
}
|
||||||
@ -63,6 +70,30 @@ type CredentialIssuerStrategy struct {
|
|||||||
|
|
||||||
// When the status was last checked.
|
// When the status was last checked.
|
||||||
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
||||||
|
|
||||||
|
// Frontend describes how clients can connect using this strategy.
|
||||||
|
Frontend *CredentialIssuerFrontend `json:"frontend,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type CredentialIssuerFrontend struct {
|
||||||
|
// Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
Type FrontendType `json:"type"`
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
// This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
TokenCredentialRequestAPIInfo *TokenCredentialRequestAPIInfo `json:"tokenCredentialRequestInfo,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
type TokenCredentialRequestAPIInfo struct {
|
||||||
|
// Server is the Kubernetes API server URL.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
// +kubebuilder:validation:Pattern=`^https://|^http://`
|
||||||
|
Server string `json:"server"`
|
||||||
|
|
||||||
|
// CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
CertificateAuthorityData string `json:"certificateAuthorityData"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Describes the configuration status of a Pinniped credential issuer.
|
// Describes the configuration status of a Pinniped credential issuer.
|
||||||
|
@ -40,7 +40,8 @@ spec:
|
|||||||
properties:
|
properties:
|
||||||
kubeConfigInfo:
|
kubeConfigInfo:
|
||||||
description: Information needed to form a valid Pinniped-based kubeconfig
|
description: Information needed to form a valid Pinniped-based kubeconfig
|
||||||
using this credential issuer.
|
using this credential issuer. This field is deprecated and will
|
||||||
|
be removed in a future version.
|
||||||
properties:
|
properties:
|
||||||
certificateAuthorityData:
|
certificateAuthorityData:
|
||||||
description: The K8s API server CA bundle.
|
description: The K8s API server CA bundle.
|
||||||
@ -62,6 +63,38 @@ spec:
|
|||||||
description: Status of an integration strategy that was attempted
|
description: Status of an integration strategy that was attempted
|
||||||
by Pinniped.
|
by Pinniped.
|
||||||
properties:
|
properties:
|
||||||
|
frontend:
|
||||||
|
description: Frontend describes how clients can connect using
|
||||||
|
this strategy.
|
||||||
|
properties:
|
||||||
|
tokenCredentialRequestInfo:
|
||||||
|
description: TokenCredentialRequestAPIInfo describes the
|
||||||
|
parameters for the TokenCredentialRequest API on this
|
||||||
|
Concierge. This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
properties:
|
||||||
|
certificateAuthorityData:
|
||||||
|
description: CertificateAuthorityData is the Kubernetes
|
||||||
|
API server CA bundle.
|
||||||
|
minLength: 1
|
||||||
|
type: string
|
||||||
|
server:
|
||||||
|
description: Server is the Kubernetes API server URL.
|
||||||
|
minLength: 1
|
||||||
|
pattern: ^https://|^http://
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- certificateAuthorityData
|
||||||
|
- server
|
||||||
|
type: object
|
||||||
|
type:
|
||||||
|
description: Type describes which frontend mechanism clients
|
||||||
|
can use with a strategy.
|
||||||
|
enum:
|
||||||
|
- TokenCredentialRequestAPI
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- type
|
||||||
|
type: object
|
||||||
lastUpdateTime:
|
lastUpdateTime:
|
||||||
description: When the status was last checked.
|
description: When the status was last checked.
|
||||||
format: date-time
|
format: date-time
|
||||||
|
39
generated/1.17/README.adoc
generated
39
generated/1.17/README.adoc
generated
@ -236,6 +236,24 @@ Describes the configuration status of a Pinniped credential issuer.
|
|||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerfrontend"]
|
||||||
|
==== CredentialIssuerFrontend
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.Appears In:
|
||||||
|
****
|
||||||
|
- xref:{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$]
|
||||||
|
****
|
||||||
|
|
||||||
|
[cols="25a,75a", options="header"]
|
||||||
|
|===
|
||||||
|
| Field | Description
|
||||||
|
| *`type`* __FrontendType__ | Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
| *`tokenCredentialRequestInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-tokencredentialrequestapiinfo[$$TokenCredentialRequestAPIInfo$$]__ | TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge. This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
|===
|
||||||
|
|
||||||
|
|
||||||
[id="{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo"]
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo"]
|
||||||
==== CredentialIssuerKubeConfigInfo
|
==== CredentialIssuerKubeConfigInfo
|
||||||
|
|
||||||
@ -270,7 +288,7 @@ Status of a credential issuer.
|
|||||||
|===
|
|===
|
||||||
| Field | Description
|
| Field | Description
|
||||||
| *`strategies`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$] array__ | List of integration strategies that were attempted by Pinniped.
|
| *`strategies`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$] array__ | List of integration strategies that were attempted by Pinniped.
|
||||||
| *`kubeConfigInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo[$$CredentialIssuerKubeConfigInfo$$]__ | Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
| *`kubeConfigInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo[$$CredentialIssuerKubeConfigInfo$$]__ | Information needed to form a valid Pinniped-based kubeconfig using this credential issuer. This field is deprecated and will be removed in a future version.
|
||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
@ -292,6 +310,25 @@ Status of a credential issuer.
|
|||||||
| *`reason`* __StrategyReason__ | Reason for the current status.
|
| *`reason`* __StrategyReason__ | Reason for the current status.
|
||||||
| *`message`* __string__ | Human-readable description of the current status.
|
| *`message`* __string__ | Human-readable description of the current status.
|
||||||
| *`lastUpdateTime`* __link:https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.17/#time-v1-meta[$$Time$$]__ | When the status was last checked.
|
| *`lastUpdateTime`* __link:https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.17/#time-v1-meta[$$Time$$]__ | When the status was last checked.
|
||||||
|
| *`frontend`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerfrontend[$$CredentialIssuerFrontend$$]__ | Frontend describes how clients can connect using this strategy.
|
||||||
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-tokencredentialrequestapiinfo"]
|
||||||
|
==== TokenCredentialRequestAPIInfo
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.Appears In:
|
||||||
|
****
|
||||||
|
- xref:{anchor_prefix}-go-pinniped-dev-generated-1-17-apis-concierge-config-v1alpha1-credentialissuerfrontend[$$CredentialIssuerFrontend$$]
|
||||||
|
****
|
||||||
|
|
||||||
|
[cols="25a,75a", options="header"]
|
||||||
|
|===
|
||||||
|
| Field | Description
|
||||||
|
| *`server`* __string__ | Server is the Kubernetes API server URL.
|
||||||
|
| *`certificateAuthorityData`* __string__ | CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
@ -8,6 +8,9 @@ import metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
|||||||
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
||||||
type StrategyType string
|
type StrategyType string
|
||||||
|
|
||||||
|
// +kubebuilder:validation:Enum=TokenCredentialRequestAPI
|
||||||
|
type FrontendType string
|
||||||
|
|
||||||
// +kubebuilder:validation:Enum=Success;Error
|
// +kubebuilder:validation:Enum=Success;Error
|
||||||
type StrategyStatus string
|
type StrategyStatus string
|
||||||
|
|
||||||
@ -17,11 +20,14 @@ type StrategyReason string
|
|||||||
const (
|
const (
|
||||||
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
||||||
|
|
||||||
|
TokenCredentialRequestAPIFrontendType = FrontendType("TokenCredentialRequestAPI")
|
||||||
|
|
||||||
SuccessStrategyStatus = StrategyStatus("Success")
|
SuccessStrategyStatus = StrategyStatus("Success")
|
||||||
ErrorStrategyStatus = StrategyStatus("Error")
|
ErrorStrategyStatus = StrategyStatus("Error")
|
||||||
|
|
||||||
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
||||||
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
CouldNotGetClusterInfoStrategyReason = StrategyReason("CouldNotGetClusterInfo")
|
||||||
|
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
||||||
)
|
)
|
||||||
|
|
||||||
// Status of a credential issuer.
|
// Status of a credential issuer.
|
||||||
@ -30,6 +36,7 @@ type CredentialIssuerStatus struct {
|
|||||||
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
||||||
|
|
||||||
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
||||||
|
// This field is deprecated and will be removed in a future version.
|
||||||
// +optional
|
// +optional
|
||||||
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
||||||
}
|
}
|
||||||
@ -63,6 +70,30 @@ type CredentialIssuerStrategy struct {
|
|||||||
|
|
||||||
// When the status was last checked.
|
// When the status was last checked.
|
||||||
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
||||||
|
|
||||||
|
// Frontend describes how clients can connect using this strategy.
|
||||||
|
Frontend *CredentialIssuerFrontend `json:"frontend,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type CredentialIssuerFrontend struct {
|
||||||
|
// Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
Type FrontendType `json:"type"`
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
// This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
TokenCredentialRequestAPIInfo *TokenCredentialRequestAPIInfo `json:"tokenCredentialRequestInfo,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
type TokenCredentialRequestAPIInfo struct {
|
||||||
|
// Server is the Kubernetes API server URL.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
// +kubebuilder:validation:Pattern=`^https://|^http://`
|
||||||
|
Server string `json:"server"`
|
||||||
|
|
||||||
|
// CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
CertificateAuthorityData string `json:"certificateAuthorityData"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Describes the configuration status of a Pinniped credential issuer.
|
// Describes the configuration status of a Pinniped credential issuer.
|
||||||
|
@ -38,6 +38,27 @@ func (in *CredentialIssuer) DeepCopyObject() runtime.Object {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopyInto(out *CredentialIssuerFrontend) {
|
||||||
|
*out = *in
|
||||||
|
if in.TokenCredentialRequestAPIInfo != nil {
|
||||||
|
in, out := &in.TokenCredentialRequestAPIInfo, &out.TokenCredentialRequestAPIInfo
|
||||||
|
*out = new(TokenCredentialRequestAPIInfo)
|
||||||
|
**out = **in
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CredentialIssuerFrontend.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopy() *CredentialIssuerFrontend {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(CredentialIssuerFrontend)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
||||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
||||||
*out = *in
|
*out = *in
|
||||||
@ -119,6 +140,11 @@ func (in *CredentialIssuerStatus) DeepCopy() *CredentialIssuerStatus {
|
|||||||
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
||||||
*out = *in
|
*out = *in
|
||||||
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
||||||
|
if in.Frontend != nil {
|
||||||
|
in, out := &in.Frontend, &out.Frontend
|
||||||
|
*out = new(CredentialIssuerFrontend)
|
||||||
|
(*in).DeepCopyInto(*out)
|
||||||
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -131,3 +157,19 @@ func (in *CredentialIssuerStrategy) DeepCopy() *CredentialIssuerStrategy {
|
|||||||
in.DeepCopyInto(out)
|
in.DeepCopyInto(out)
|
||||||
return out
|
return out
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopyInto(out *TokenCredentialRequestAPIInfo) {
|
||||||
|
*out = *in
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new TokenCredentialRequestAPIInfo.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopy() *TokenCredentialRequestAPIInfo {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(TokenCredentialRequestAPIInfo)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
@ -40,7 +40,8 @@ spec:
|
|||||||
properties:
|
properties:
|
||||||
kubeConfigInfo:
|
kubeConfigInfo:
|
||||||
description: Information needed to form a valid Pinniped-based kubeconfig
|
description: Information needed to form a valid Pinniped-based kubeconfig
|
||||||
using this credential issuer.
|
using this credential issuer. This field is deprecated and will
|
||||||
|
be removed in a future version.
|
||||||
properties:
|
properties:
|
||||||
certificateAuthorityData:
|
certificateAuthorityData:
|
||||||
description: The K8s API server CA bundle.
|
description: The K8s API server CA bundle.
|
||||||
@ -62,6 +63,38 @@ spec:
|
|||||||
description: Status of an integration strategy that was attempted
|
description: Status of an integration strategy that was attempted
|
||||||
by Pinniped.
|
by Pinniped.
|
||||||
properties:
|
properties:
|
||||||
|
frontend:
|
||||||
|
description: Frontend describes how clients can connect using
|
||||||
|
this strategy.
|
||||||
|
properties:
|
||||||
|
tokenCredentialRequestInfo:
|
||||||
|
description: TokenCredentialRequestAPIInfo describes the
|
||||||
|
parameters for the TokenCredentialRequest API on this
|
||||||
|
Concierge. This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
properties:
|
||||||
|
certificateAuthorityData:
|
||||||
|
description: CertificateAuthorityData is the Kubernetes
|
||||||
|
API server CA bundle.
|
||||||
|
minLength: 1
|
||||||
|
type: string
|
||||||
|
server:
|
||||||
|
description: Server is the Kubernetes API server URL.
|
||||||
|
minLength: 1
|
||||||
|
pattern: ^https://|^http://
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- certificateAuthorityData
|
||||||
|
- server
|
||||||
|
type: object
|
||||||
|
type:
|
||||||
|
description: Type describes which frontend mechanism clients
|
||||||
|
can use with a strategy.
|
||||||
|
enum:
|
||||||
|
- TokenCredentialRequestAPI
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- type
|
||||||
|
type: object
|
||||||
lastUpdateTime:
|
lastUpdateTime:
|
||||||
description: When the status was last checked.
|
description: When the status was last checked.
|
||||||
format: date-time
|
format: date-time
|
||||||
|
39
generated/1.18/README.adoc
generated
39
generated/1.18/README.adoc
generated
@ -236,6 +236,24 @@ Describes the configuration status of a Pinniped credential issuer.
|
|||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerfrontend"]
|
||||||
|
==== CredentialIssuerFrontend
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.Appears In:
|
||||||
|
****
|
||||||
|
- xref:{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$]
|
||||||
|
****
|
||||||
|
|
||||||
|
[cols="25a,75a", options="header"]
|
||||||
|
|===
|
||||||
|
| Field | Description
|
||||||
|
| *`type`* __FrontendType__ | Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
| *`tokenCredentialRequestInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-tokencredentialrequestapiinfo[$$TokenCredentialRequestAPIInfo$$]__ | TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge. This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
|===
|
||||||
|
|
||||||
|
|
||||||
[id="{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo"]
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo"]
|
||||||
==== CredentialIssuerKubeConfigInfo
|
==== CredentialIssuerKubeConfigInfo
|
||||||
|
|
||||||
@ -270,7 +288,7 @@ Status of a credential issuer.
|
|||||||
|===
|
|===
|
||||||
| Field | Description
|
| Field | Description
|
||||||
| *`strategies`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$] array__ | List of integration strategies that were attempted by Pinniped.
|
| *`strategies`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$] array__ | List of integration strategies that were attempted by Pinniped.
|
||||||
| *`kubeConfigInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo[$$CredentialIssuerKubeConfigInfo$$]__ | Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
| *`kubeConfigInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo[$$CredentialIssuerKubeConfigInfo$$]__ | Information needed to form a valid Pinniped-based kubeconfig using this credential issuer. This field is deprecated and will be removed in a future version.
|
||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
@ -292,6 +310,25 @@ Status of a credential issuer.
|
|||||||
| *`reason`* __StrategyReason__ | Reason for the current status.
|
| *`reason`* __StrategyReason__ | Reason for the current status.
|
||||||
| *`message`* __string__ | Human-readable description of the current status.
|
| *`message`* __string__ | Human-readable description of the current status.
|
||||||
| *`lastUpdateTime`* __link:https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.18/#time-v1-meta[$$Time$$]__ | When the status was last checked.
|
| *`lastUpdateTime`* __link:https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.18/#time-v1-meta[$$Time$$]__ | When the status was last checked.
|
||||||
|
| *`frontend`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerfrontend[$$CredentialIssuerFrontend$$]__ | Frontend describes how clients can connect using this strategy.
|
||||||
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-tokencredentialrequestapiinfo"]
|
||||||
|
==== TokenCredentialRequestAPIInfo
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.Appears In:
|
||||||
|
****
|
||||||
|
- xref:{anchor_prefix}-go-pinniped-dev-generated-1-18-apis-concierge-config-v1alpha1-credentialissuerfrontend[$$CredentialIssuerFrontend$$]
|
||||||
|
****
|
||||||
|
|
||||||
|
[cols="25a,75a", options="header"]
|
||||||
|
|===
|
||||||
|
| Field | Description
|
||||||
|
| *`server`* __string__ | Server is the Kubernetes API server URL.
|
||||||
|
| *`certificateAuthorityData`* __string__ | CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
@ -8,6 +8,9 @@ import metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
|||||||
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
||||||
type StrategyType string
|
type StrategyType string
|
||||||
|
|
||||||
|
// +kubebuilder:validation:Enum=TokenCredentialRequestAPI
|
||||||
|
type FrontendType string
|
||||||
|
|
||||||
// +kubebuilder:validation:Enum=Success;Error
|
// +kubebuilder:validation:Enum=Success;Error
|
||||||
type StrategyStatus string
|
type StrategyStatus string
|
||||||
|
|
||||||
@ -17,11 +20,14 @@ type StrategyReason string
|
|||||||
const (
|
const (
|
||||||
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
||||||
|
|
||||||
|
TokenCredentialRequestAPIFrontendType = FrontendType("TokenCredentialRequestAPI")
|
||||||
|
|
||||||
SuccessStrategyStatus = StrategyStatus("Success")
|
SuccessStrategyStatus = StrategyStatus("Success")
|
||||||
ErrorStrategyStatus = StrategyStatus("Error")
|
ErrorStrategyStatus = StrategyStatus("Error")
|
||||||
|
|
||||||
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
||||||
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
CouldNotGetClusterInfoStrategyReason = StrategyReason("CouldNotGetClusterInfo")
|
||||||
|
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
||||||
)
|
)
|
||||||
|
|
||||||
// Status of a credential issuer.
|
// Status of a credential issuer.
|
||||||
@ -30,6 +36,7 @@ type CredentialIssuerStatus struct {
|
|||||||
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
||||||
|
|
||||||
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
||||||
|
// This field is deprecated and will be removed in a future version.
|
||||||
// +optional
|
// +optional
|
||||||
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
||||||
}
|
}
|
||||||
@ -63,6 +70,30 @@ type CredentialIssuerStrategy struct {
|
|||||||
|
|
||||||
// When the status was last checked.
|
// When the status was last checked.
|
||||||
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
||||||
|
|
||||||
|
// Frontend describes how clients can connect using this strategy.
|
||||||
|
Frontend *CredentialIssuerFrontend `json:"frontend,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type CredentialIssuerFrontend struct {
|
||||||
|
// Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
Type FrontendType `json:"type"`
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
// This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
TokenCredentialRequestAPIInfo *TokenCredentialRequestAPIInfo `json:"tokenCredentialRequestInfo,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
type TokenCredentialRequestAPIInfo struct {
|
||||||
|
// Server is the Kubernetes API server URL.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
// +kubebuilder:validation:Pattern=`^https://|^http://`
|
||||||
|
Server string `json:"server"`
|
||||||
|
|
||||||
|
// CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
CertificateAuthorityData string `json:"certificateAuthorityData"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Describes the configuration status of a Pinniped credential issuer.
|
// Describes the configuration status of a Pinniped credential issuer.
|
||||||
|
@ -38,6 +38,27 @@ func (in *CredentialIssuer) DeepCopyObject() runtime.Object {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopyInto(out *CredentialIssuerFrontend) {
|
||||||
|
*out = *in
|
||||||
|
if in.TokenCredentialRequestAPIInfo != nil {
|
||||||
|
in, out := &in.TokenCredentialRequestAPIInfo, &out.TokenCredentialRequestAPIInfo
|
||||||
|
*out = new(TokenCredentialRequestAPIInfo)
|
||||||
|
**out = **in
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CredentialIssuerFrontend.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopy() *CredentialIssuerFrontend {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(CredentialIssuerFrontend)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
||||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
||||||
*out = *in
|
*out = *in
|
||||||
@ -119,6 +140,11 @@ func (in *CredentialIssuerStatus) DeepCopy() *CredentialIssuerStatus {
|
|||||||
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
||||||
*out = *in
|
*out = *in
|
||||||
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
||||||
|
if in.Frontend != nil {
|
||||||
|
in, out := &in.Frontend, &out.Frontend
|
||||||
|
*out = new(CredentialIssuerFrontend)
|
||||||
|
(*in).DeepCopyInto(*out)
|
||||||
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -131,3 +157,19 @@ func (in *CredentialIssuerStrategy) DeepCopy() *CredentialIssuerStrategy {
|
|||||||
in.DeepCopyInto(out)
|
in.DeepCopyInto(out)
|
||||||
return out
|
return out
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopyInto(out *TokenCredentialRequestAPIInfo) {
|
||||||
|
*out = *in
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new TokenCredentialRequestAPIInfo.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopy() *TokenCredentialRequestAPIInfo {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(TokenCredentialRequestAPIInfo)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
@ -40,7 +40,8 @@ spec:
|
|||||||
properties:
|
properties:
|
||||||
kubeConfigInfo:
|
kubeConfigInfo:
|
||||||
description: Information needed to form a valid Pinniped-based kubeconfig
|
description: Information needed to form a valid Pinniped-based kubeconfig
|
||||||
using this credential issuer.
|
using this credential issuer. This field is deprecated and will
|
||||||
|
be removed in a future version.
|
||||||
properties:
|
properties:
|
||||||
certificateAuthorityData:
|
certificateAuthorityData:
|
||||||
description: The K8s API server CA bundle.
|
description: The K8s API server CA bundle.
|
||||||
@ -62,6 +63,38 @@ spec:
|
|||||||
description: Status of an integration strategy that was attempted
|
description: Status of an integration strategy that was attempted
|
||||||
by Pinniped.
|
by Pinniped.
|
||||||
properties:
|
properties:
|
||||||
|
frontend:
|
||||||
|
description: Frontend describes how clients can connect using
|
||||||
|
this strategy.
|
||||||
|
properties:
|
||||||
|
tokenCredentialRequestInfo:
|
||||||
|
description: TokenCredentialRequestAPIInfo describes the
|
||||||
|
parameters for the TokenCredentialRequest API on this
|
||||||
|
Concierge. This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
properties:
|
||||||
|
certificateAuthorityData:
|
||||||
|
description: CertificateAuthorityData is the Kubernetes
|
||||||
|
API server CA bundle.
|
||||||
|
minLength: 1
|
||||||
|
type: string
|
||||||
|
server:
|
||||||
|
description: Server is the Kubernetes API server URL.
|
||||||
|
minLength: 1
|
||||||
|
pattern: ^https://|^http://
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- certificateAuthorityData
|
||||||
|
- server
|
||||||
|
type: object
|
||||||
|
type:
|
||||||
|
description: Type describes which frontend mechanism clients
|
||||||
|
can use with a strategy.
|
||||||
|
enum:
|
||||||
|
- TokenCredentialRequestAPI
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- type
|
||||||
|
type: object
|
||||||
lastUpdateTime:
|
lastUpdateTime:
|
||||||
description: When the status was last checked.
|
description: When the status was last checked.
|
||||||
format: date-time
|
format: date-time
|
||||||
|
39
generated/1.19/README.adoc
generated
39
generated/1.19/README.adoc
generated
@ -236,6 +236,24 @@ Describes the configuration status of a Pinniped credential issuer.
|
|||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerfrontend"]
|
||||||
|
==== CredentialIssuerFrontend
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.Appears In:
|
||||||
|
****
|
||||||
|
- xref:{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$]
|
||||||
|
****
|
||||||
|
|
||||||
|
[cols="25a,75a", options="header"]
|
||||||
|
|===
|
||||||
|
| Field | Description
|
||||||
|
| *`type`* __FrontendType__ | Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
| *`tokenCredentialRequestInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-tokencredentialrequestapiinfo[$$TokenCredentialRequestAPIInfo$$]__ | TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge. This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
|===
|
||||||
|
|
||||||
|
|
||||||
[id="{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo"]
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo"]
|
||||||
==== CredentialIssuerKubeConfigInfo
|
==== CredentialIssuerKubeConfigInfo
|
||||||
|
|
||||||
@ -270,7 +288,7 @@ Status of a credential issuer.
|
|||||||
|===
|
|===
|
||||||
| Field | Description
|
| Field | Description
|
||||||
| *`strategies`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$] array__ | List of integration strategies that were attempted by Pinniped.
|
| *`strategies`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$] array__ | List of integration strategies that were attempted by Pinniped.
|
||||||
| *`kubeConfigInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo[$$CredentialIssuerKubeConfigInfo$$]__ | Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
| *`kubeConfigInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo[$$CredentialIssuerKubeConfigInfo$$]__ | Information needed to form a valid Pinniped-based kubeconfig using this credential issuer. This field is deprecated and will be removed in a future version.
|
||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
@ -292,6 +310,25 @@ Status of a credential issuer.
|
|||||||
| *`reason`* __StrategyReason__ | Reason for the current status.
|
| *`reason`* __StrategyReason__ | Reason for the current status.
|
||||||
| *`message`* __string__ | Human-readable description of the current status.
|
| *`message`* __string__ | Human-readable description of the current status.
|
||||||
| *`lastUpdateTime`* __link:https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.19/#time-v1-meta[$$Time$$]__ | When the status was last checked.
|
| *`lastUpdateTime`* __link:https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.19/#time-v1-meta[$$Time$$]__ | When the status was last checked.
|
||||||
|
| *`frontend`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerfrontend[$$CredentialIssuerFrontend$$]__ | Frontend describes how clients can connect using this strategy.
|
||||||
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-tokencredentialrequestapiinfo"]
|
||||||
|
==== TokenCredentialRequestAPIInfo
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.Appears In:
|
||||||
|
****
|
||||||
|
- xref:{anchor_prefix}-go-pinniped-dev-generated-1-19-apis-concierge-config-v1alpha1-credentialissuerfrontend[$$CredentialIssuerFrontend$$]
|
||||||
|
****
|
||||||
|
|
||||||
|
[cols="25a,75a", options="header"]
|
||||||
|
|===
|
||||||
|
| Field | Description
|
||||||
|
| *`server`* __string__ | Server is the Kubernetes API server URL.
|
||||||
|
| *`certificateAuthorityData`* __string__ | CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
@ -8,6 +8,9 @@ import metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
|||||||
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
||||||
type StrategyType string
|
type StrategyType string
|
||||||
|
|
||||||
|
// +kubebuilder:validation:Enum=TokenCredentialRequestAPI
|
||||||
|
type FrontendType string
|
||||||
|
|
||||||
// +kubebuilder:validation:Enum=Success;Error
|
// +kubebuilder:validation:Enum=Success;Error
|
||||||
type StrategyStatus string
|
type StrategyStatus string
|
||||||
|
|
||||||
@ -17,11 +20,14 @@ type StrategyReason string
|
|||||||
const (
|
const (
|
||||||
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
||||||
|
|
||||||
|
TokenCredentialRequestAPIFrontendType = FrontendType("TokenCredentialRequestAPI")
|
||||||
|
|
||||||
SuccessStrategyStatus = StrategyStatus("Success")
|
SuccessStrategyStatus = StrategyStatus("Success")
|
||||||
ErrorStrategyStatus = StrategyStatus("Error")
|
ErrorStrategyStatus = StrategyStatus("Error")
|
||||||
|
|
||||||
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
||||||
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
CouldNotGetClusterInfoStrategyReason = StrategyReason("CouldNotGetClusterInfo")
|
||||||
|
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
||||||
)
|
)
|
||||||
|
|
||||||
// Status of a credential issuer.
|
// Status of a credential issuer.
|
||||||
@ -30,6 +36,7 @@ type CredentialIssuerStatus struct {
|
|||||||
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
||||||
|
|
||||||
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
||||||
|
// This field is deprecated and will be removed in a future version.
|
||||||
// +optional
|
// +optional
|
||||||
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
||||||
}
|
}
|
||||||
@ -63,6 +70,30 @@ type CredentialIssuerStrategy struct {
|
|||||||
|
|
||||||
// When the status was last checked.
|
// When the status was last checked.
|
||||||
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
||||||
|
|
||||||
|
// Frontend describes how clients can connect using this strategy.
|
||||||
|
Frontend *CredentialIssuerFrontend `json:"frontend,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type CredentialIssuerFrontend struct {
|
||||||
|
// Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
Type FrontendType `json:"type"`
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
// This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
TokenCredentialRequestAPIInfo *TokenCredentialRequestAPIInfo `json:"tokenCredentialRequestInfo,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
type TokenCredentialRequestAPIInfo struct {
|
||||||
|
// Server is the Kubernetes API server URL.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
// +kubebuilder:validation:Pattern=`^https://|^http://`
|
||||||
|
Server string `json:"server"`
|
||||||
|
|
||||||
|
// CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
CertificateAuthorityData string `json:"certificateAuthorityData"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Describes the configuration status of a Pinniped credential issuer.
|
// Describes the configuration status of a Pinniped credential issuer.
|
||||||
|
@ -38,6 +38,27 @@ func (in *CredentialIssuer) DeepCopyObject() runtime.Object {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopyInto(out *CredentialIssuerFrontend) {
|
||||||
|
*out = *in
|
||||||
|
if in.TokenCredentialRequestAPIInfo != nil {
|
||||||
|
in, out := &in.TokenCredentialRequestAPIInfo, &out.TokenCredentialRequestAPIInfo
|
||||||
|
*out = new(TokenCredentialRequestAPIInfo)
|
||||||
|
**out = **in
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CredentialIssuerFrontend.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopy() *CredentialIssuerFrontend {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(CredentialIssuerFrontend)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
||||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
||||||
*out = *in
|
*out = *in
|
||||||
@ -119,6 +140,11 @@ func (in *CredentialIssuerStatus) DeepCopy() *CredentialIssuerStatus {
|
|||||||
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
||||||
*out = *in
|
*out = *in
|
||||||
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
||||||
|
if in.Frontend != nil {
|
||||||
|
in, out := &in.Frontend, &out.Frontend
|
||||||
|
*out = new(CredentialIssuerFrontend)
|
||||||
|
(*in).DeepCopyInto(*out)
|
||||||
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -131,3 +157,19 @@ func (in *CredentialIssuerStrategy) DeepCopy() *CredentialIssuerStrategy {
|
|||||||
in.DeepCopyInto(out)
|
in.DeepCopyInto(out)
|
||||||
return out
|
return out
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopyInto(out *TokenCredentialRequestAPIInfo) {
|
||||||
|
*out = *in
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new TokenCredentialRequestAPIInfo.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopy() *TokenCredentialRequestAPIInfo {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(TokenCredentialRequestAPIInfo)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
@ -40,7 +40,8 @@ spec:
|
|||||||
properties:
|
properties:
|
||||||
kubeConfigInfo:
|
kubeConfigInfo:
|
||||||
description: Information needed to form a valid Pinniped-based kubeconfig
|
description: Information needed to form a valid Pinniped-based kubeconfig
|
||||||
using this credential issuer.
|
using this credential issuer. This field is deprecated and will
|
||||||
|
be removed in a future version.
|
||||||
properties:
|
properties:
|
||||||
certificateAuthorityData:
|
certificateAuthorityData:
|
||||||
description: The K8s API server CA bundle.
|
description: The K8s API server CA bundle.
|
||||||
@ -62,6 +63,38 @@ spec:
|
|||||||
description: Status of an integration strategy that was attempted
|
description: Status of an integration strategy that was attempted
|
||||||
by Pinniped.
|
by Pinniped.
|
||||||
properties:
|
properties:
|
||||||
|
frontend:
|
||||||
|
description: Frontend describes how clients can connect using
|
||||||
|
this strategy.
|
||||||
|
properties:
|
||||||
|
tokenCredentialRequestInfo:
|
||||||
|
description: TokenCredentialRequestAPIInfo describes the
|
||||||
|
parameters for the TokenCredentialRequest API on this
|
||||||
|
Concierge. This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
properties:
|
||||||
|
certificateAuthorityData:
|
||||||
|
description: CertificateAuthorityData is the Kubernetes
|
||||||
|
API server CA bundle.
|
||||||
|
minLength: 1
|
||||||
|
type: string
|
||||||
|
server:
|
||||||
|
description: Server is the Kubernetes API server URL.
|
||||||
|
minLength: 1
|
||||||
|
pattern: ^https://|^http://
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- certificateAuthorityData
|
||||||
|
- server
|
||||||
|
type: object
|
||||||
|
type:
|
||||||
|
description: Type describes which frontend mechanism clients
|
||||||
|
can use with a strategy.
|
||||||
|
enum:
|
||||||
|
- TokenCredentialRequestAPI
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- type
|
||||||
|
type: object
|
||||||
lastUpdateTime:
|
lastUpdateTime:
|
||||||
description: When the status was last checked.
|
description: When the status was last checked.
|
||||||
format: date-time
|
format: date-time
|
||||||
|
39
generated/1.20/README.adoc
generated
39
generated/1.20/README.adoc
generated
@ -236,6 +236,24 @@ Describes the configuration status of a Pinniped credential issuer.
|
|||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerfrontend"]
|
||||||
|
==== CredentialIssuerFrontend
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.Appears In:
|
||||||
|
****
|
||||||
|
- xref:{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$]
|
||||||
|
****
|
||||||
|
|
||||||
|
[cols="25a,75a", options="header"]
|
||||||
|
|===
|
||||||
|
| Field | Description
|
||||||
|
| *`type`* __FrontendType__ | Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
| *`tokenCredentialRequestInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-tokencredentialrequestapiinfo[$$TokenCredentialRequestAPIInfo$$]__ | TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge. This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
|===
|
||||||
|
|
||||||
|
|
||||||
[id="{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo"]
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo"]
|
||||||
==== CredentialIssuerKubeConfigInfo
|
==== CredentialIssuerKubeConfigInfo
|
||||||
|
|
||||||
@ -270,7 +288,7 @@ Status of a credential issuer.
|
|||||||
|===
|
|===
|
||||||
| Field | Description
|
| Field | Description
|
||||||
| *`strategies`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$] array__ | List of integration strategies that were attempted by Pinniped.
|
| *`strategies`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerstrategy[$$CredentialIssuerStrategy$$] array__ | List of integration strategies that were attempted by Pinniped.
|
||||||
| *`kubeConfigInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo[$$CredentialIssuerKubeConfigInfo$$]__ | Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
| *`kubeConfigInfo`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerkubeconfiginfo[$$CredentialIssuerKubeConfigInfo$$]__ | Information needed to form a valid Pinniped-based kubeconfig using this credential issuer. This field is deprecated and will be removed in a future version.
|
||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
@ -292,6 +310,25 @@ Status of a credential issuer.
|
|||||||
| *`reason`* __StrategyReason__ | Reason for the current status.
|
| *`reason`* __StrategyReason__ | Reason for the current status.
|
||||||
| *`message`* __string__ | Human-readable description of the current status.
|
| *`message`* __string__ | Human-readable description of the current status.
|
||||||
| *`lastUpdateTime`* __link:https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.2/#time-v1-meta[$$Time$$]__ | When the status was last checked.
|
| *`lastUpdateTime`* __link:https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.2/#time-v1-meta[$$Time$$]__ | When the status was last checked.
|
||||||
|
| *`frontend`* __xref:{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerfrontend[$$CredentialIssuerFrontend$$]__ | Frontend describes how clients can connect using this strategy.
|
||||||
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
[id="{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-tokencredentialrequestapiinfo"]
|
||||||
|
==== TokenCredentialRequestAPIInfo
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
.Appears In:
|
||||||
|
****
|
||||||
|
- xref:{anchor_prefix}-go-pinniped-dev-generated-1-20-apis-concierge-config-v1alpha1-credentialissuerfrontend[$$CredentialIssuerFrontend$$]
|
||||||
|
****
|
||||||
|
|
||||||
|
[cols="25a,75a", options="header"]
|
||||||
|
|===
|
||||||
|
| Field | Description
|
||||||
|
| *`server`* __string__ | Server is the Kubernetes API server URL.
|
||||||
|
| *`certificateAuthorityData`* __string__ | CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|===
|
|===
|
||||||
|
|
||||||
|
|
||||||
|
@ -8,6 +8,9 @@ import metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
|||||||
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
||||||
type StrategyType string
|
type StrategyType string
|
||||||
|
|
||||||
|
// +kubebuilder:validation:Enum=TokenCredentialRequestAPI
|
||||||
|
type FrontendType string
|
||||||
|
|
||||||
// +kubebuilder:validation:Enum=Success;Error
|
// +kubebuilder:validation:Enum=Success;Error
|
||||||
type StrategyStatus string
|
type StrategyStatus string
|
||||||
|
|
||||||
@ -17,11 +20,14 @@ type StrategyReason string
|
|||||||
const (
|
const (
|
||||||
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
||||||
|
|
||||||
|
TokenCredentialRequestAPIFrontendType = FrontendType("TokenCredentialRequestAPI")
|
||||||
|
|
||||||
SuccessStrategyStatus = StrategyStatus("Success")
|
SuccessStrategyStatus = StrategyStatus("Success")
|
||||||
ErrorStrategyStatus = StrategyStatus("Error")
|
ErrorStrategyStatus = StrategyStatus("Error")
|
||||||
|
|
||||||
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
||||||
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
CouldNotGetClusterInfoStrategyReason = StrategyReason("CouldNotGetClusterInfo")
|
||||||
|
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
||||||
)
|
)
|
||||||
|
|
||||||
// Status of a credential issuer.
|
// Status of a credential issuer.
|
||||||
@ -30,6 +36,7 @@ type CredentialIssuerStatus struct {
|
|||||||
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
||||||
|
|
||||||
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
||||||
|
// This field is deprecated and will be removed in a future version.
|
||||||
// +optional
|
// +optional
|
||||||
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
||||||
}
|
}
|
||||||
@ -63,6 +70,30 @@ type CredentialIssuerStrategy struct {
|
|||||||
|
|
||||||
// When the status was last checked.
|
// When the status was last checked.
|
||||||
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
||||||
|
|
||||||
|
// Frontend describes how clients can connect using this strategy.
|
||||||
|
Frontend *CredentialIssuerFrontend `json:"frontend,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type CredentialIssuerFrontend struct {
|
||||||
|
// Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
Type FrontendType `json:"type"`
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
// This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
TokenCredentialRequestAPIInfo *TokenCredentialRequestAPIInfo `json:"tokenCredentialRequestInfo,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
type TokenCredentialRequestAPIInfo struct {
|
||||||
|
// Server is the Kubernetes API server URL.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
// +kubebuilder:validation:Pattern=`^https://|^http://`
|
||||||
|
Server string `json:"server"`
|
||||||
|
|
||||||
|
// CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
CertificateAuthorityData string `json:"certificateAuthorityData"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Describes the configuration status of a Pinniped credential issuer.
|
// Describes the configuration status of a Pinniped credential issuer.
|
||||||
|
@ -38,6 +38,27 @@ func (in *CredentialIssuer) DeepCopyObject() runtime.Object {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopyInto(out *CredentialIssuerFrontend) {
|
||||||
|
*out = *in
|
||||||
|
if in.TokenCredentialRequestAPIInfo != nil {
|
||||||
|
in, out := &in.TokenCredentialRequestAPIInfo, &out.TokenCredentialRequestAPIInfo
|
||||||
|
*out = new(TokenCredentialRequestAPIInfo)
|
||||||
|
**out = **in
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CredentialIssuerFrontend.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopy() *CredentialIssuerFrontend {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(CredentialIssuerFrontend)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
||||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
||||||
*out = *in
|
*out = *in
|
||||||
@ -119,6 +140,11 @@ func (in *CredentialIssuerStatus) DeepCopy() *CredentialIssuerStatus {
|
|||||||
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
||||||
*out = *in
|
*out = *in
|
||||||
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
||||||
|
if in.Frontend != nil {
|
||||||
|
in, out := &in.Frontend, &out.Frontend
|
||||||
|
*out = new(CredentialIssuerFrontend)
|
||||||
|
(*in).DeepCopyInto(*out)
|
||||||
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -131,3 +157,19 @@ func (in *CredentialIssuerStrategy) DeepCopy() *CredentialIssuerStrategy {
|
|||||||
in.DeepCopyInto(out)
|
in.DeepCopyInto(out)
|
||||||
return out
|
return out
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopyInto(out *TokenCredentialRequestAPIInfo) {
|
||||||
|
*out = *in
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new TokenCredentialRequestAPIInfo.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopy() *TokenCredentialRequestAPIInfo {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(TokenCredentialRequestAPIInfo)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
@ -40,7 +40,8 @@ spec:
|
|||||||
properties:
|
properties:
|
||||||
kubeConfigInfo:
|
kubeConfigInfo:
|
||||||
description: Information needed to form a valid Pinniped-based kubeconfig
|
description: Information needed to form a valid Pinniped-based kubeconfig
|
||||||
using this credential issuer.
|
using this credential issuer. This field is deprecated and will
|
||||||
|
be removed in a future version.
|
||||||
properties:
|
properties:
|
||||||
certificateAuthorityData:
|
certificateAuthorityData:
|
||||||
description: The K8s API server CA bundle.
|
description: The K8s API server CA bundle.
|
||||||
@ -62,6 +63,38 @@ spec:
|
|||||||
description: Status of an integration strategy that was attempted
|
description: Status of an integration strategy that was attempted
|
||||||
by Pinniped.
|
by Pinniped.
|
||||||
properties:
|
properties:
|
||||||
|
frontend:
|
||||||
|
description: Frontend describes how clients can connect using
|
||||||
|
this strategy.
|
||||||
|
properties:
|
||||||
|
tokenCredentialRequestInfo:
|
||||||
|
description: TokenCredentialRequestAPIInfo describes the
|
||||||
|
parameters for the TokenCredentialRequest API on this
|
||||||
|
Concierge. This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
properties:
|
||||||
|
certificateAuthorityData:
|
||||||
|
description: CertificateAuthorityData is the Kubernetes
|
||||||
|
API server CA bundle.
|
||||||
|
minLength: 1
|
||||||
|
type: string
|
||||||
|
server:
|
||||||
|
description: Server is the Kubernetes API server URL.
|
||||||
|
minLength: 1
|
||||||
|
pattern: ^https://|^http://
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- certificateAuthorityData
|
||||||
|
- server
|
||||||
|
type: object
|
||||||
|
type:
|
||||||
|
description: Type describes which frontend mechanism clients
|
||||||
|
can use with a strategy.
|
||||||
|
enum:
|
||||||
|
- TokenCredentialRequestAPI
|
||||||
|
type: string
|
||||||
|
required:
|
||||||
|
- type
|
||||||
|
type: object
|
||||||
lastUpdateTime:
|
lastUpdateTime:
|
||||||
description: When the status was last checked.
|
description: When the status was last checked.
|
||||||
format: date-time
|
format: date-time
|
||||||
|
@ -8,6 +8,9 @@ import metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
|||||||
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
// +kubebuilder:validation:Enum=KubeClusterSigningCertificate
|
||||||
type StrategyType string
|
type StrategyType string
|
||||||
|
|
||||||
|
// +kubebuilder:validation:Enum=TokenCredentialRequestAPI
|
||||||
|
type FrontendType string
|
||||||
|
|
||||||
// +kubebuilder:validation:Enum=Success;Error
|
// +kubebuilder:validation:Enum=Success;Error
|
||||||
type StrategyStatus string
|
type StrategyStatus string
|
||||||
|
|
||||||
@ -17,11 +20,14 @@ type StrategyReason string
|
|||||||
const (
|
const (
|
||||||
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
KubeClusterSigningCertificateStrategyType = StrategyType("KubeClusterSigningCertificate")
|
||||||
|
|
||||||
|
TokenCredentialRequestAPIFrontendType = FrontendType("TokenCredentialRequestAPI")
|
||||||
|
|
||||||
SuccessStrategyStatus = StrategyStatus("Success")
|
SuccessStrategyStatus = StrategyStatus("Success")
|
||||||
ErrorStrategyStatus = StrategyStatus("Error")
|
ErrorStrategyStatus = StrategyStatus("Error")
|
||||||
|
|
||||||
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
CouldNotFetchKeyStrategyReason = StrategyReason("CouldNotFetchKey")
|
||||||
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
CouldNotGetClusterInfoStrategyReason = StrategyReason("CouldNotGetClusterInfo")
|
||||||
|
FetchedKeyStrategyReason = StrategyReason("FetchedKey")
|
||||||
)
|
)
|
||||||
|
|
||||||
// Status of a credential issuer.
|
// Status of a credential issuer.
|
||||||
@ -30,6 +36,7 @@ type CredentialIssuerStatus struct {
|
|||||||
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
Strategies []CredentialIssuerStrategy `json:"strategies"`
|
||||||
|
|
||||||
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
// Information needed to form a valid Pinniped-based kubeconfig using this credential issuer.
|
||||||
|
// This field is deprecated and will be removed in a future version.
|
||||||
// +optional
|
// +optional
|
||||||
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
KubeConfigInfo *CredentialIssuerKubeConfigInfo `json:"kubeConfigInfo,omitempty"`
|
||||||
}
|
}
|
||||||
@ -63,6 +70,30 @@ type CredentialIssuerStrategy struct {
|
|||||||
|
|
||||||
// When the status was last checked.
|
// When the status was last checked.
|
||||||
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
LastUpdateTime metav1.Time `json:"lastUpdateTime"`
|
||||||
|
|
||||||
|
// Frontend describes how clients can connect using this strategy.
|
||||||
|
Frontend *CredentialIssuerFrontend `json:"frontend,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
type CredentialIssuerFrontend struct {
|
||||||
|
// Type describes which frontend mechanism clients can use with a strategy.
|
||||||
|
Type FrontendType `json:"type"`
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
// This field is only set when Type is "TokenCredentialRequestAPI".
|
||||||
|
TokenCredentialRequestAPIInfo *TokenCredentialRequestAPIInfo `json:"tokenCredentialRequestInfo,omitempty"`
|
||||||
|
}
|
||||||
|
|
||||||
|
// TokenCredentialRequestAPIInfo describes the parameters for the TokenCredentialRequest API on this Concierge.
|
||||||
|
type TokenCredentialRequestAPIInfo struct {
|
||||||
|
// Server is the Kubernetes API server URL.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
// +kubebuilder:validation:Pattern=`^https://|^http://`
|
||||||
|
Server string `json:"server"`
|
||||||
|
|
||||||
|
// CertificateAuthorityData is the Kubernetes API server CA bundle.
|
||||||
|
// +kubebuilder:validation:MinLength=1
|
||||||
|
CertificateAuthorityData string `json:"certificateAuthorityData"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Describes the configuration status of a Pinniped credential issuer.
|
// Describes the configuration status of a Pinniped credential issuer.
|
||||||
|
@ -38,6 +38,27 @@ func (in *CredentialIssuer) DeepCopyObject() runtime.Object {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopyInto(out *CredentialIssuerFrontend) {
|
||||||
|
*out = *in
|
||||||
|
if in.TokenCredentialRequestAPIInfo != nil {
|
||||||
|
in, out := &in.TokenCredentialRequestAPIInfo, &out.TokenCredentialRequestAPIInfo
|
||||||
|
*out = new(TokenCredentialRequestAPIInfo)
|
||||||
|
**out = **in
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CredentialIssuerFrontend.
|
||||||
|
func (in *CredentialIssuerFrontend) DeepCopy() *CredentialIssuerFrontend {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(CredentialIssuerFrontend)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
|
||||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
func (in *CredentialIssuerKubeConfigInfo) DeepCopyInto(out *CredentialIssuerKubeConfigInfo) {
|
||||||
*out = *in
|
*out = *in
|
||||||
@ -119,6 +140,11 @@ func (in *CredentialIssuerStatus) DeepCopy() *CredentialIssuerStatus {
|
|||||||
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
func (in *CredentialIssuerStrategy) DeepCopyInto(out *CredentialIssuerStrategy) {
|
||||||
*out = *in
|
*out = *in
|
||||||
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
in.LastUpdateTime.DeepCopyInto(&out.LastUpdateTime)
|
||||||
|
if in.Frontend != nil {
|
||||||
|
in, out := &in.Frontend, &out.Frontend
|
||||||
|
*out = new(CredentialIssuerFrontend)
|
||||||
|
(*in).DeepCopyInto(*out)
|
||||||
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -131,3 +157,19 @@ func (in *CredentialIssuerStrategy) DeepCopy() *CredentialIssuerStrategy {
|
|||||||
in.DeepCopyInto(out)
|
in.DeepCopyInto(out)
|
||||||
return out
|
return out
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopyInto(out *TokenCredentialRequestAPIInfo) {
|
||||||
|
*out = *in
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new TokenCredentialRequestAPIInfo.
|
||||||
|
func (in *TokenCredentialRequestAPIInfo) DeepCopy() *TokenCredentialRequestAPIInfo {
|
||||||
|
if in == nil {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
out := new(TokenCredentialRequestAPIInfo)
|
||||||
|
in.DeepCopyInto(out)
|
||||||
|
return out
|
||||||
|
}
|
||||||
|
7
go.sum
7
go.sum
@ -214,7 +214,6 @@ github.com/go-logr/logr v0.4.0/go.mod h1:z6/tIYblkpsD+a4lm/fGIIU9mZ+XfAiaFtq7xTg
|
|||||||
github.com/go-logr/stdr v0.4.0 h1:ijk9G/xzDRZdMU1QRhLYdHuWvNZWqte+NZMOGsiKWbc=
|
github.com/go-logr/stdr v0.4.0 h1:ijk9G/xzDRZdMU1QRhLYdHuWvNZWqte+NZMOGsiKWbc=
|
||||||
github.com/go-logr/stdr v0.4.0/go.mod h1:NO1vneyJDqKVgJYnxhwXWWmQPOvNM391IG3H8ql3jiA=
|
github.com/go-logr/stdr v0.4.0/go.mod h1:NO1vneyJDqKVgJYnxhwXWWmQPOvNM391IG3H8ql3jiA=
|
||||||
github.com/go-openapi/jsonpointer v0.19.2/go.mod h1:3akKfEdA7DF1sugOqz1dVQHBcuDBPKZGEoHC/NkiQRg=
|
github.com/go-openapi/jsonpointer v0.19.2/go.mod h1:3akKfEdA7DF1sugOqz1dVQHBcuDBPKZGEoHC/NkiQRg=
|
||||||
github.com/go-openapi/jsonpointer v0.19.3 h1:gihV7YNZK1iK6Tgwwsxo2rJbD1GTbdm72325Bq8FI3w=
|
|
||||||
github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
|
github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
|
||||||
github.com/go-openapi/jsonpointer v0.19.5 h1:gZr+CIYByUqjcgeLXnQu2gHYQC9o73G2XUeOFYEICuY=
|
github.com/go-openapi/jsonpointer v0.19.5 h1:gZr+CIYByUqjcgeLXnQu2gHYQC9o73G2XUeOFYEICuY=
|
||||||
github.com/go-openapi/jsonpointer v0.19.5/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
|
github.com/go-openapi/jsonpointer v0.19.5/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg=
|
||||||
@ -226,7 +225,6 @@ github.com/go-openapi/spec v0.19.3/go.mod h1:FpwSN1ksY1eteniUU7X0N/BgJ7a4WvBFVA8
|
|||||||
github.com/go-openapi/spec v0.20.3 h1:uH9RQ6vdyPSs2pSy9fL8QPspDF2AMIMPtmK5coSSjtQ=
|
github.com/go-openapi/spec v0.20.3 h1:uH9RQ6vdyPSs2pSy9fL8QPspDF2AMIMPtmK5coSSjtQ=
|
||||||
github.com/go-openapi/spec v0.20.3/go.mod h1:gG4F8wdEDN+YPBMVnzE85Rbhf+Th2DTvA9nFPQ5AYEg=
|
github.com/go-openapi/spec v0.20.3/go.mod h1:gG4F8wdEDN+YPBMVnzE85Rbhf+Th2DTvA9nFPQ5AYEg=
|
||||||
github.com/go-openapi/swag v0.19.2/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk=
|
github.com/go-openapi/swag v0.19.2/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk=
|
||||||
github.com/go-openapi/swag v0.19.5 h1:lTz6Ys4CmqqCQmZPBlbQENR1/GucA2bzYTE12Pw4tFY=
|
|
||||||
github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk=
|
github.com/go-openapi/swag v0.19.5/go.mod h1:POnQmlKehdgb5mhVOsnJFsivZCEZ/vjK9gh66Z9tfKk=
|
||||||
github.com/go-openapi/swag v0.19.14 h1:gm3vOOXfiuw5i9p5N9xJvfjvuofpyvLA9Wr6QfK5Fng=
|
github.com/go-openapi/swag v0.19.14 h1:gm3vOOXfiuw5i9p5N9xJvfjvuofpyvLA9Wr6QfK5Fng=
|
||||||
github.com/go-openapi/swag v0.19.14/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ=
|
github.com/go-openapi/swag v0.19.14/go.mod h1:QYRuS/SOXUCsnplDa677K7+DxSOj6IPNl/eQntq43wQ=
|
||||||
@ -693,7 +691,6 @@ github.com/magiconair/properties v1.8.1 h1:ZC2Vc7/ZFkGmsVC9KvOjumD+G5lXy2RtTKyzR
|
|||||||
github.com/magiconair/properties v1.8.1/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ=
|
github.com/magiconair/properties v1.8.1/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ=
|
||||||
github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
|
github.com/mailru/easyjson v0.0.0-20190614124828-94de47d64c63/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
|
||||||
github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
|
github.com/mailru/easyjson v0.0.0-20190626092158-b2ccc519800e/go.mod h1:C1wdFJiN94OJF2b5HbByQZoLdCWB1Yqtg26g4irojpc=
|
||||||
github.com/mailru/easyjson v0.7.0 h1:aizVhC/NAAcKWb+5QsU1iNOZb4Yws5UO2I+aIprQITM=
|
|
||||||
github.com/mailru/easyjson v0.7.0/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs=
|
github.com/mailru/easyjson v0.7.0/go.mod h1:KAzv3t3aY1NaHWoQz1+4F1ccyAH66Jk7yos7ldAVICs=
|
||||||
github.com/mailru/easyjson v0.7.6 h1:8yTIVnZgCoiM1TgqoeTl+LfU5Jg6/xL3QhGQnimLYnA=
|
github.com/mailru/easyjson v0.7.6 h1:8yTIVnZgCoiM1TgqoeTl+LfU5Jg6/xL3QhGQnimLYnA=
|
||||||
github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc=
|
github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc=
|
||||||
@ -1178,7 +1175,6 @@ golang.org/x/net v0.0.0-20200506145744-7e3656a0809f/go.mod h1:qpuaurCH72eLCgpAm/
|
|||||||
golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A=
|
golang.org/x/net v0.0.0-20200520004742-59133d7f0dd7/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A=
|
||||||
golang.org/x/net v0.0.0-20200520182314-0ba52f642ac2/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A=
|
golang.org/x/net v0.0.0-20200520182314-0ba52f642ac2/go.mod h1:qpuaurCH72eLCgpAm/N6yyVIVM9cpaDIP3A8BGJEC5A=
|
||||||
golang.org/x/net v0.0.0-20200625001655-4c5254603344/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA=
|
golang.org/x/net v0.0.0-20200625001655-4c5254603344/go.mod h1:/O7V0waA8r7cgGh81Ro3o1hOxt32SMVPicZroKQ2sZA=
|
||||||
golang.org/x/net v0.0.0-20201110031124-69a78807bb2b h1:uwuIcX0g4Yl1NC5XAz37xsr2lTtcqevgzYNVt49waME=
|
|
||||||
golang.org/x/net v0.0.0-20201110031124-69a78807bb2b/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
|
golang.org/x/net v0.0.0-20201110031124-69a78807bb2b/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU=
|
||||||
golang.org/x/net v0.0.0-20210119194325-5f4716e94777 h1:003p0dJM77cxMSyCPFphvZf/Y5/NXf5fzg6ufd1/Oew=
|
golang.org/x/net v0.0.0-20210119194325-5f4716e94777 h1:003p0dJM77cxMSyCPFphvZf/Y5/NXf5fzg6ufd1/Oew=
|
||||||
golang.org/x/net v0.0.0-20210119194325-5f4716e94777/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
golang.org/x/net v0.0.0-20210119194325-5f4716e94777/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
|
||||||
@ -1266,11 +1262,9 @@ golang.org/x/sys v0.0.0-20200602225109-6fdc65e7d980/go.mod h1:h1NjWce9XRLGQEsW7w
|
|||||||
golang.org/x/sys v0.0.0-20200615200032-f1bc736245b1/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20200615200032-f1bc736245b1/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20200720211630-cb9d2d5c5666/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20200720211630-cb9d2d5c5666/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20201112073958-5cba982894dd h1:5CtCZbICpIOFdgO940moixOPjc0178IU44m4EjOO5IY=
|
|
||||||
golang.org/x/sys v0.0.0-20201112073958-5cba982894dd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20201112073958-5cba982894dd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68 h1:nxC68pudNYkKU6jWhgrqdreuFiOQWj1Fs7T3VrH4Pjw=
|
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68 h1:nxC68pudNYkKU6jWhgrqdreuFiOQWj1Fs7T3VrH4Pjw=
|
||||||
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
|
||||||
golang.org/x/term v0.0.0-20201117132131-f5c789dd3221 h1:/ZHdbVpdR/jk3g30/d4yUL0JU9kksj8+F/bnQUVLGDM=
|
|
||||||
golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw=
|
golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw=
|
||||||
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1 h1:v+OssWQX+hTHEmOBgwxdZxK4zHq3yOs8F9J7mk0PY8E=
|
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1 h1:v+OssWQX+hTHEmOBgwxdZxK4zHq3yOs8F9J7mk0PY8E=
|
||||||
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
|
||||||
@ -1279,7 +1273,6 @@ golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
|||||||
golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
|
||||||
golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
|
golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk=
|
||||||
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||||
golang.org/x/text v0.3.4 h1:0YWbFKbhXG/wIiuHDSKpS0Iy7FSA+u45VtBMfQcFTTc=
|
|
||||||
golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||||
golang.org/x/text v0.3.5 h1:i6eZZ+zk0SOf0xgBpEpPD18qWcJda6q1sxt3S0kzyUQ=
|
golang.org/x/text v0.3.5 h1:i6eZZ+zk0SOf0xgBpEpPD18qWcJda6q1sxt3S0kzyUQ=
|
||||||
golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
|
||||||
|
@ -1,121 +0,0 @@
|
|||||||
// Copyright 2020-2021 the Pinniped contributors. All Rights Reserved.
|
|
||||||
// SPDX-License-Identifier: Apache-2.0
|
|
||||||
|
|
||||||
package issuerconfig
|
|
||||||
|
|
||||||
import (
|
|
||||||
"encoding/base64"
|
|
||||||
"fmt"
|
|
||||||
|
|
||||||
k8serrors "k8s.io/apimachinery/pkg/api/errors"
|
|
||||||
corev1informers "k8s.io/client-go/informers/core/v1"
|
|
||||||
"k8s.io/client-go/tools/clientcmd"
|
|
||||||
"k8s.io/klog/v2"
|
|
||||||
|
|
||||||
configv1alpha1 "go.pinniped.dev/generated/latest/apis/concierge/config/v1alpha1"
|
|
||||||
pinnipedclientset "go.pinniped.dev/generated/latest/client/concierge/clientset/versioned"
|
|
||||||
pinnipedcontroller "go.pinniped.dev/internal/controller"
|
|
||||||
"go.pinniped.dev/internal/controllerlib"
|
|
||||||
"go.pinniped.dev/internal/plog"
|
|
||||||
)
|
|
||||||
|
|
||||||
const (
|
|
||||||
ClusterInfoNamespace = "kube-public"
|
|
||||||
clusterInfoName = "cluster-info"
|
|
||||||
clusterInfoConfigMapKey = "kubeconfig"
|
|
||||||
)
|
|
||||||
|
|
||||||
type kubeConigInfoPublisherController struct {
|
|
||||||
credentialIssuerResourceName string
|
|
||||||
credentialIssuerLabels map[string]string
|
|
||||||
serverOverride *string
|
|
||||||
pinnipedClient pinnipedclientset.Interface
|
|
||||||
configMapInformer corev1informers.ConfigMapInformer
|
|
||||||
}
|
|
||||||
|
|
||||||
// NewKubeConfigInfoPublisherController returns a controller that syncs the
|
|
||||||
// configv1alpha1.CredentialIssuer.Status.KubeConfigInfo field with the cluster-info ConfigMap
|
|
||||||
// in the kube-public namespace.
|
|
||||||
func NewKubeConfigInfoPublisherController(
|
|
||||||
credentialIssuerResourceName string,
|
|
||||||
credentialIssuerLabels map[string]string,
|
|
||||||
serverOverride *string,
|
|
||||||
pinnipedClient pinnipedclientset.Interface,
|
|
||||||
configMapInformer corev1informers.ConfigMapInformer,
|
|
||||||
withInformer pinnipedcontroller.WithInformerOptionFunc,
|
|
||||||
) controllerlib.Controller {
|
|
||||||
return controllerlib.New(
|
|
||||||
controllerlib.Config{
|
|
||||||
Name: "publisher-controller",
|
|
||||||
Syncer: &kubeConigInfoPublisherController{
|
|
||||||
credentialIssuerResourceName: credentialIssuerResourceName,
|
|
||||||
credentialIssuerLabels: credentialIssuerLabels,
|
|
||||||
serverOverride: serverOverride,
|
|
||||||
pinnipedClient: pinnipedClient,
|
|
||||||
configMapInformer: configMapInformer,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
withInformer(
|
|
||||||
configMapInformer,
|
|
||||||
pinnipedcontroller.NameAndNamespaceExactMatchFilterFactory(clusterInfoName, ClusterInfoNamespace),
|
|
||||||
controllerlib.InformerOption{},
|
|
||||||
),
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
|
||||||
func (c *kubeConigInfoPublisherController) Sync(ctx controllerlib.Context) error {
|
|
||||||
configMap, err := c.configMapInformer.
|
|
||||||
Lister().
|
|
||||||
ConfigMaps(ClusterInfoNamespace).
|
|
||||||
Get(clusterInfoName)
|
|
||||||
notFound := k8serrors.IsNotFound(err)
|
|
||||||
if err != nil && !notFound {
|
|
||||||
return fmt.Errorf("failed to get %s configmap: %w", clusterInfoName, err)
|
|
||||||
}
|
|
||||||
if notFound {
|
|
||||||
plog.Debug(
|
|
||||||
"could not find config map",
|
|
||||||
"configmap",
|
|
||||||
klog.KRef(ClusterInfoNamespace, clusterInfoName),
|
|
||||||
)
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
kubeConfig, kubeConfigPresent := configMap.Data[clusterInfoConfigMapKey]
|
|
||||||
if !kubeConfigPresent {
|
|
||||||
plog.Debug("could not find kubeconfig configmap key")
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
config, err := clientcmd.Load([]byte(kubeConfig))
|
|
||||||
if err != nil {
|
|
||||||
plog.Debug("could not load kubeconfig configmap key")
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
var certificateAuthorityData, server string
|
|
||||||
for _, v := range config.Clusters {
|
|
||||||
certificateAuthorityData = base64.StdEncoding.EncodeToString(v.CertificateAuthorityData)
|
|
||||||
server = v.Server
|
|
||||||
break
|
|
||||||
}
|
|
||||||
|
|
||||||
if c.serverOverride != nil {
|
|
||||||
server = *c.serverOverride
|
|
||||||
}
|
|
||||||
|
|
||||||
updateServerAndCAFunc := func(c *configv1alpha1.CredentialIssuerStatus) {
|
|
||||||
c.KubeConfigInfo = &configv1alpha1.CredentialIssuerKubeConfigInfo{
|
|
||||||
Server: server,
|
|
||||||
CertificateAuthorityData: certificateAuthorityData,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return CreateOrUpdateCredentialIssuerStatus(
|
|
||||||
ctx.Context,
|
|
||||||
c.credentialIssuerResourceName,
|
|
||||||
c.credentialIssuerLabels,
|
|
||||||
c.pinnipedClient,
|
|
||||||
updateServerAndCAFunc,
|
|
||||||
)
|
|
||||||
}
|
|
@ -1,444 +0,0 @@
|
|||||||
// Copyright 2020-2021 the Pinniped contributors. All Rights Reserved.
|
|
||||||
// SPDX-License-Identifier: Apache-2.0
|
|
||||||
|
|
||||||
package issuerconfig
|
|
||||||
|
|
||||||
import (
|
|
||||||
"context"
|
|
||||||
"errors"
|
|
||||||
"testing"
|
|
||||||
"time"
|
|
||||||
|
|
||||||
"github.com/sclevine/spec"
|
|
||||||
"github.com/sclevine/spec/report"
|
|
||||||
"github.com/stretchr/testify/require"
|
|
||||||
corev1 "k8s.io/api/core/v1"
|
|
||||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
|
||||||
"k8s.io/apimachinery/pkg/runtime"
|
|
||||||
"k8s.io/apimachinery/pkg/runtime/schema"
|
|
||||||
kubeinformers "k8s.io/client-go/informers"
|
|
||||||
kubernetesfake "k8s.io/client-go/kubernetes/fake"
|
|
||||||
coretesting "k8s.io/client-go/testing"
|
|
||||||
|
|
||||||
configv1alpha1 "go.pinniped.dev/generated/latest/apis/concierge/config/v1alpha1"
|
|
||||||
pinnipedfake "go.pinniped.dev/generated/latest/client/concierge/clientset/versioned/fake"
|
|
||||||
"go.pinniped.dev/internal/controllerlib"
|
|
||||||
"go.pinniped.dev/internal/here"
|
|
||||||
"go.pinniped.dev/internal/testutil"
|
|
||||||
)
|
|
||||||
|
|
||||||
func TestInformerFilters(t *testing.T) {
|
|
||||||
spec.Run(t, "informer filters", func(t *testing.T, when spec.G, it spec.S) {
|
|
||||||
const credentialIssuerResourceName = "some-resource-name"
|
|
||||||
|
|
||||||
var r *require.Assertions
|
|
||||||
var observableWithInformerOption *testutil.ObservableWithInformerOption
|
|
||||||
var configMapInformerFilter controllerlib.Filter
|
|
||||||
|
|
||||||
it.Before(func() {
|
|
||||||
r = require.New(t)
|
|
||||||
observableWithInformerOption = testutil.NewObservableWithInformerOption()
|
|
||||||
configMapInformer := kubeinformers.NewSharedInformerFactory(nil, 0).Core().V1().ConfigMaps()
|
|
||||||
_ = NewKubeConfigInfoPublisherController(
|
|
||||||
credentialIssuerResourceName,
|
|
||||||
map[string]string{},
|
|
||||||
nil,
|
|
||||||
nil,
|
|
||||||
configMapInformer,
|
|
||||||
observableWithInformerOption.WithInformer, // make it possible to observe the behavior of the Filters
|
|
||||||
)
|
|
||||||
configMapInformerFilter = observableWithInformerOption.GetFilterForInformer(configMapInformer)
|
|
||||||
})
|
|
||||||
|
|
||||||
when("watching ConfigMap objects", func() {
|
|
||||||
var subject controllerlib.Filter
|
|
||||||
var target, wrongNamespace, wrongName, unrelated *corev1.ConfigMap
|
|
||||||
|
|
||||||
it.Before(func() {
|
|
||||||
subject = configMapInformerFilter
|
|
||||||
target = &corev1.ConfigMap{ObjectMeta: metav1.ObjectMeta{Name: "cluster-info", Namespace: "kube-public"}}
|
|
||||||
wrongNamespace = &corev1.ConfigMap{ObjectMeta: metav1.ObjectMeta{Name: "cluster-info", Namespace: "wrong-namespace"}}
|
|
||||||
wrongName = &corev1.ConfigMap{ObjectMeta: metav1.ObjectMeta{Name: "wrong-name", Namespace: "kube-public"}}
|
|
||||||
unrelated = &corev1.ConfigMap{ObjectMeta: metav1.ObjectMeta{Name: "wrong-name", Namespace: "wrong-namespace"}}
|
|
||||||
})
|
|
||||||
|
|
||||||
when("the target ConfigMap changes", func() {
|
|
||||||
it("returns true to trigger the sync method", func() {
|
|
||||||
r.True(subject.Add(target))
|
|
||||||
r.True(subject.Update(target, unrelated))
|
|
||||||
r.True(subject.Update(unrelated, target))
|
|
||||||
r.True(subject.Delete(target))
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("a ConfigMap from another namespace changes", func() {
|
|
||||||
it("returns false to avoid triggering the sync method", func() {
|
|
||||||
r.False(subject.Add(wrongNamespace))
|
|
||||||
r.False(subject.Update(wrongNamespace, unrelated))
|
|
||||||
r.False(subject.Update(unrelated, wrongNamespace))
|
|
||||||
r.False(subject.Delete(wrongNamespace))
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("a ConfigMap with a different name changes", func() {
|
|
||||||
it("returns false to avoid triggering the sync method", func() {
|
|
||||||
r.False(subject.Add(wrongName))
|
|
||||||
r.False(subject.Update(wrongName, unrelated))
|
|
||||||
r.False(subject.Update(unrelated, wrongName))
|
|
||||||
r.False(subject.Delete(wrongName))
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("a ConfigMap with a different name and a different namespace changes", func() {
|
|
||||||
it("returns false to avoid triggering the sync method", func() {
|
|
||||||
r.False(subject.Add(unrelated))
|
|
||||||
r.False(subject.Update(unrelated, unrelated))
|
|
||||||
r.False(subject.Delete(unrelated))
|
|
||||||
})
|
|
||||||
})
|
|
||||||
})
|
|
||||||
}, spec.Parallel(), spec.Report(report.Terminal{}))
|
|
||||||
}
|
|
||||||
|
|
||||||
func TestSync(t *testing.T) {
|
|
||||||
spec.Run(t, "Sync", func(t *testing.T, when spec.G, it spec.S) {
|
|
||||||
const credentialIssuerResourceName = "some-resource-name"
|
|
||||||
|
|
||||||
var r *require.Assertions
|
|
||||||
|
|
||||||
var subject controllerlib.Controller
|
|
||||||
var serverOverride *string
|
|
||||||
var kubeInformerClient *kubernetesfake.Clientset
|
|
||||||
var kubeInformers kubeinformers.SharedInformerFactory
|
|
||||||
var pinnipedAPIClient *pinnipedfake.Clientset
|
|
||||||
var timeoutContext context.Context
|
|
||||||
var timeoutContextCancel context.CancelFunc
|
|
||||||
var syncContext *controllerlib.Context
|
|
||||||
|
|
||||||
var expectedCredentialIssuer = func(expectedServerURL, expectedCAData string) (schema.GroupVersionResource, *configv1alpha1.CredentialIssuer, *configv1alpha1.CredentialIssuer) {
|
|
||||||
expectedCredentialIssuerGVR := schema.GroupVersionResource{
|
|
||||||
Group: configv1alpha1.GroupName,
|
|
||||||
Version: "v1alpha1",
|
|
||||||
Resource: "credentialissuers",
|
|
||||||
}
|
|
||||||
|
|
||||||
expectedCreateCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
|
||||||
ObjectMeta: metav1.ObjectMeta{
|
|
||||||
Name: credentialIssuerResourceName,
|
|
||||||
Labels: map[string]string{
|
|
||||||
"myLabelKey1": "myLabelValue1",
|
|
||||||
"myLabelKey2": "myLabelValue2",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
expectedCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
|
||||||
ObjectMeta: metav1.ObjectMeta{
|
|
||||||
Name: credentialIssuerResourceName,
|
|
||||||
Labels: map[string]string{
|
|
||||||
"myLabelKey1": "myLabelValue1",
|
|
||||||
"myLabelKey2": "myLabelValue2",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
Status: configv1alpha1.CredentialIssuerStatus{
|
|
||||||
KubeConfigInfo: &configv1alpha1.CredentialIssuerKubeConfigInfo{
|
|
||||||
Server: expectedServerURL,
|
|
||||||
CertificateAuthorityData: expectedCAData,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
return expectedCredentialIssuerGVR, expectedCreateCredentialIssuer, expectedCredentialIssuer
|
|
||||||
}
|
|
||||||
|
|
||||||
// Defer starting the informers until the last possible moment so that the
|
|
||||||
// nested Before's can keep adding things to the informer caches.
|
|
||||||
var startInformersAndController = func() {
|
|
||||||
// Set this at the last second to allow for injection of server override.
|
|
||||||
subject = NewKubeConfigInfoPublisherController(
|
|
||||||
credentialIssuerResourceName,
|
|
||||||
map[string]string{
|
|
||||||
"myLabelKey1": "myLabelValue1",
|
|
||||||
"myLabelKey2": "myLabelValue2",
|
|
||||||
},
|
|
||||||
serverOverride,
|
|
||||||
pinnipedAPIClient,
|
|
||||||
kubeInformers.Core().V1().ConfigMaps(),
|
|
||||||
controllerlib.WithInformer,
|
|
||||||
)
|
|
||||||
|
|
||||||
// Set this at the last second to support calling subject.Name().
|
|
||||||
syncContext = &controllerlib.Context{
|
|
||||||
Context: timeoutContext,
|
|
||||||
Name: subject.Name(),
|
|
||||||
Key: controllerlib.Key{
|
|
||||||
Namespace: "kube-public",
|
|
||||||
Name: "cluster-info",
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
// Must start informers before calling TestRunSynchronously()
|
|
||||||
kubeInformers.Start(timeoutContext.Done())
|
|
||||||
controllerlib.TestRunSynchronously(t, subject)
|
|
||||||
}
|
|
||||||
|
|
||||||
it.Before(func() {
|
|
||||||
r = require.New(t)
|
|
||||||
|
|
||||||
timeoutContext, timeoutContextCancel = context.WithTimeout(context.Background(), time.Second*3)
|
|
||||||
|
|
||||||
kubeInformerClient = kubernetesfake.NewSimpleClientset()
|
|
||||||
kubeInformers = kubeinformers.NewSharedInformerFactory(kubeInformerClient, 0)
|
|
||||||
pinnipedAPIClient = pinnipedfake.NewSimpleClientset()
|
|
||||||
})
|
|
||||||
|
|
||||||
it.After(func() {
|
|
||||||
timeoutContextCancel()
|
|
||||||
})
|
|
||||||
|
|
||||||
when("there is a cluster-info ConfigMap in the kube-public namespace", func() {
|
|
||||||
const caData = "c29tZS1jZXJ0aWZpY2F0ZS1hdXRob3JpdHktZGF0YQo=" // "some-certificate-authority-data" base64 encoded
|
|
||||||
const kubeServerURL = "https://some-server"
|
|
||||||
|
|
||||||
when("the ConfigMap has the expected `kubeconfig` top-level data key", func() {
|
|
||||||
it.Before(func() {
|
|
||||||
clusterInfoConfigMap := &corev1.ConfigMap{
|
|
||||||
ObjectMeta: metav1.ObjectMeta{Name: "cluster-info", Namespace: "kube-public"},
|
|
||||||
// Note that go fmt puts tabs in our file, which we must remove from our configmap yaml below.
|
|
||||||
Data: map[string]string{
|
|
||||||
"kubeconfig": here.Docf(`
|
|
||||||
kind: Config
|
|
||||||
apiVersion: v1
|
|
||||||
clusters:
|
|
||||||
- name: ""
|
|
||||||
cluster:
|
|
||||||
certificate-authority-data: "%s"
|
|
||||||
server: "%s"`,
|
|
||||||
caData, kubeServerURL),
|
|
||||||
"uninteresting-key": "uninteresting-value",
|
|
||||||
},
|
|
||||||
}
|
|
||||||
err := kubeInformerClient.Tracker().Add(clusterInfoConfigMap)
|
|
||||||
r.NoError(err)
|
|
||||||
})
|
|
||||||
|
|
||||||
when("the CredentialIssuer does not already exist", func() {
|
|
||||||
it("creates a CredentialIssuer", func() {
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.NoError(err)
|
|
||||||
|
|
||||||
expectedCredentialIssuerGVR, expectedCreateCredentialIssuer, expectedCredentialIssuer := expectedCredentialIssuer(
|
|
||||||
kubeServerURL,
|
|
||||||
caData,
|
|
||||||
)
|
|
||||||
|
|
||||||
r.Equal(
|
|
||||||
[]coretesting.Action{
|
|
||||||
coretesting.NewRootGetAction(expectedCredentialIssuerGVR, expectedCreateCredentialIssuer.Name),
|
|
||||||
coretesting.NewRootCreateAction(
|
|
||||||
expectedCredentialIssuerGVR,
|
|
||||||
expectedCreateCredentialIssuer,
|
|
||||||
),
|
|
||||||
coretesting.NewRootUpdateSubresourceAction(
|
|
||||||
expectedCredentialIssuerGVR,
|
|
||||||
"status",
|
|
||||||
expectedCredentialIssuer,
|
|
||||||
),
|
|
||||||
},
|
|
||||||
pinnipedAPIClient.Actions(),
|
|
||||||
)
|
|
||||||
})
|
|
||||||
|
|
||||||
when("creating the CredentialIssuer fails", func() {
|
|
||||||
it.Before(func() {
|
|
||||||
pinnipedAPIClient.PrependReactor(
|
|
||||||
"create",
|
|
||||||
"credentialissuers",
|
|
||||||
func(_ coretesting.Action) (bool, runtime.Object, error) {
|
|
||||||
return true, nil, errors.New("create failed")
|
|
||||||
},
|
|
||||||
)
|
|
||||||
})
|
|
||||||
|
|
||||||
it("returns the create error", func() {
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.EqualError(err, "could not create or update credentialissuer: create failed: create failed")
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("a server override is passed to the controller", func() {
|
|
||||||
it("uses the server override field", func() {
|
|
||||||
serverOverride = new(string)
|
|
||||||
*serverOverride = "https://some-server-override"
|
|
||||||
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.NoError(err)
|
|
||||||
|
|
||||||
expectedCredentialIssuerGVR, expectedCreateCredentialIssuer, expectedCredentialIssuer := expectedCredentialIssuer(
|
|
||||||
kubeServerURL,
|
|
||||||
caData,
|
|
||||||
)
|
|
||||||
expectedCredentialIssuer.Status.KubeConfigInfo.Server = "https://some-server-override"
|
|
||||||
|
|
||||||
r.Equal(
|
|
||||||
[]coretesting.Action{
|
|
||||||
coretesting.NewRootGetAction(expectedCredentialIssuerGVR, expectedCreateCredentialIssuer.Name),
|
|
||||||
coretesting.NewRootCreateAction(
|
|
||||||
expectedCredentialIssuerGVR,
|
|
||||||
expectedCreateCredentialIssuer,
|
|
||||||
),
|
|
||||||
coretesting.NewRootUpdateSubresourceAction(
|
|
||||||
expectedCredentialIssuerGVR,
|
|
||||||
"status",
|
|
||||||
expectedCredentialIssuer,
|
|
||||||
),
|
|
||||||
},
|
|
||||||
pinnipedAPIClient.Actions(),
|
|
||||||
)
|
|
||||||
})
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("the CredentialIssuer already exists", func() {
|
|
||||||
when("the CredentialIssuer is already up to date according to the data in the ConfigMap", func() {
|
|
||||||
var credentialIssuerGVR schema.GroupVersionResource
|
|
||||||
var credentialIssuer *configv1alpha1.CredentialIssuer
|
|
||||||
|
|
||||||
it.Before(func() {
|
|
||||||
credentialIssuerGVR, _, credentialIssuer = expectedCredentialIssuer(
|
|
||||||
kubeServerURL,
|
|
||||||
caData,
|
|
||||||
)
|
|
||||||
err := pinnipedAPIClient.Tracker().Add(credentialIssuer)
|
|
||||||
r.NoError(err)
|
|
||||||
})
|
|
||||||
|
|
||||||
it("does not update the CredentialIssuer to avoid unnecessary etcd writes/api calls", func() {
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.NoError(err)
|
|
||||||
|
|
||||||
r.Equal(
|
|
||||||
[]coretesting.Action{
|
|
||||||
coretesting.NewRootGetAction(credentialIssuerGVR, credentialIssuer.Name),
|
|
||||||
},
|
|
||||||
pinnipedAPIClient.Actions(),
|
|
||||||
)
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("the CredentialIssuer is stale compared to the data in the ConfigMap", func() {
|
|
||||||
it.Before(func() {
|
|
||||||
_, _, expectedCredentialIssuer := expectedCredentialIssuer(
|
|
||||||
kubeServerURL,
|
|
||||||
caData,
|
|
||||||
)
|
|
||||||
expectedCredentialIssuer.Status.KubeConfigInfo.Server = "https://some-other-server"
|
|
||||||
r.NoError(pinnipedAPIClient.Tracker().Add(expectedCredentialIssuer))
|
|
||||||
})
|
|
||||||
|
|
||||||
it("updates the existing CredentialIssuer", func() {
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.NoError(err)
|
|
||||||
|
|
||||||
expectedCredentialIssuerGVR, _, expectedCredentialIssuer := expectedCredentialIssuer(
|
|
||||||
kubeServerURL,
|
|
||||||
caData,
|
|
||||||
)
|
|
||||||
expectedActions := []coretesting.Action{
|
|
||||||
coretesting.NewRootGetAction(expectedCredentialIssuerGVR, expectedCredentialIssuer.Name),
|
|
||||||
coretesting.NewRootUpdateSubresourceAction(
|
|
||||||
expectedCredentialIssuerGVR,
|
|
||||||
"status",
|
|
||||||
expectedCredentialIssuer,
|
|
||||||
),
|
|
||||||
}
|
|
||||||
r.Equal(expectedActions, pinnipedAPIClient.Actions())
|
|
||||||
})
|
|
||||||
|
|
||||||
when("updating the CredentialIssuer fails", func() {
|
|
||||||
it.Before(func() {
|
|
||||||
pinnipedAPIClient.PrependReactor(
|
|
||||||
"update",
|
|
||||||
"credentialissuers",
|
|
||||||
func(_ coretesting.Action) (bool, runtime.Object, error) {
|
|
||||||
return true, nil, errors.New("update failed")
|
|
||||||
},
|
|
||||||
)
|
|
||||||
})
|
|
||||||
|
|
||||||
it("returns the update error", func() {
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.EqualError(err, "could not create or update credentialissuer: update failed")
|
|
||||||
})
|
|
||||||
})
|
|
||||||
})
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("the ConfigMap is missing the expected `kubeconfig` top-level data key", func() {
|
|
||||||
it.Before(func() {
|
|
||||||
clusterInfoConfigMap := &corev1.ConfigMap{
|
|
||||||
ObjectMeta: metav1.ObjectMeta{Name: "cluster-info", Namespace: "kube-public"},
|
|
||||||
Data: map[string]string{
|
|
||||||
"these are not the droids you're looking for": "uninteresting-value",
|
|
||||||
},
|
|
||||||
}
|
|
||||||
err := kubeInformerClient.Tracker().Add(clusterInfoConfigMap)
|
|
||||||
r.NoError(err)
|
|
||||||
})
|
|
||||||
|
|
||||||
it("keeps waiting for it to exist", func() {
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.NoError(err)
|
|
||||||
r.Empty(pinnipedAPIClient.Actions())
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("the ConfigMap does not have a valid kubeconfig", func() {
|
|
||||||
it.Before(func() {
|
|
||||||
clusterInfoConfigMap := &corev1.ConfigMap{
|
|
||||||
ObjectMeta: metav1.ObjectMeta{Name: "cluster-info", Namespace: "kube-public"},
|
|
||||||
Data: map[string]string{
|
|
||||||
"kubeconfig": "this is an invalid kubeconfig",
|
|
||||||
},
|
|
||||||
}
|
|
||||||
err := kubeInformerClient.Tracker().Add(clusterInfoConfigMap)
|
|
||||||
r.NoError(err)
|
|
||||||
})
|
|
||||||
|
|
||||||
it("keeps waiting for it to be properly formatted", func() {
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.NoError(err)
|
|
||||||
r.Empty(pinnipedAPIClient.Actions())
|
|
||||||
})
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("there is not a cluster-info ConfigMap in the kube-public namespace", func() {
|
|
||||||
it.Before(func() {
|
|
||||||
unrelatedConfigMap := &corev1.ConfigMap{
|
|
||||||
ObjectMeta: metav1.ObjectMeta{
|
|
||||||
Name: "oops this is not the cluster-info ConfigMap",
|
|
||||||
Namespace: "kube-public",
|
|
||||||
},
|
|
||||||
}
|
|
||||||
err := kubeInformerClient.Tracker().Add(unrelatedConfigMap)
|
|
||||||
r.NoError(err)
|
|
||||||
})
|
|
||||||
|
|
||||||
it("keeps waiting for one", func() {
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.NoError(err)
|
|
||||||
r.Empty(pinnipedAPIClient.Actions())
|
|
||||||
})
|
|
||||||
})
|
|
||||||
}, spec.Parallel(), spec.Report(report.Terminal{}))
|
|
||||||
}
|
|
@ -42,6 +42,14 @@ func mergeStrategy(configToUpdate *v1alpha1.CredentialIssuerStatus, strategy v1a
|
|||||||
configToUpdate.Strategies = append(configToUpdate.Strategies, strategy)
|
configToUpdate.Strategies = append(configToUpdate.Strategies, strategy)
|
||||||
}
|
}
|
||||||
sort.Stable(sortableStrategies(configToUpdate.Strategies))
|
sort.Stable(sortableStrategies(configToUpdate.Strategies))
|
||||||
|
|
||||||
|
// Special case: the "TokenCredentialRequestAPI" data is mirrored into the deprecated status.kubeConfigInfo field.
|
||||||
|
if strategy.Frontend != nil && strategy.Frontend.Type == v1alpha1.TokenCredentialRequestAPIFrontendType {
|
||||||
|
configToUpdate.KubeConfigInfo = &v1alpha1.CredentialIssuerKubeConfigInfo{
|
||||||
|
Server: strategy.Frontend.TokenCredentialRequestAPIInfo.Server,
|
||||||
|
CertificateAuthorityData: strategy.Frontend.TokenCredentialRequestAPIInfo.CertificateAuthorityData,
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: sort strategies by server preference rather than alphanumerically by type.
|
// TODO: sort strategies by server preference rather than alphanumerically by type.
|
||||||
|
@ -47,6 +47,48 @@ func TestMergeStrategy(t *testing.T) {
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "new entry updating deprecated kubeConfigInfo",
|
||||||
|
configToUpdate: v1alpha1.CredentialIssuerStatus{
|
||||||
|
Strategies: nil,
|
||||||
|
},
|
||||||
|
strategy: v1alpha1.CredentialIssuerStrategy{
|
||||||
|
Type: "Type1",
|
||||||
|
Status: v1alpha1.SuccessStrategyStatus,
|
||||||
|
Reason: "some reason",
|
||||||
|
Message: "some message",
|
||||||
|
LastUpdateTime: t1,
|
||||||
|
Frontend: &v1alpha1.CredentialIssuerFrontend{
|
||||||
|
Type: "TokenCredentialRequestAPI",
|
||||||
|
TokenCredentialRequestAPIInfo: &v1alpha1.TokenCredentialRequestAPIInfo{
|
||||||
|
Server: "https://test-server",
|
||||||
|
CertificateAuthorityData: "test-ca-bundle",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
expected: v1alpha1.CredentialIssuerStatus{
|
||||||
|
Strategies: []v1alpha1.CredentialIssuerStrategy{
|
||||||
|
{
|
||||||
|
Type: "Type1",
|
||||||
|
Status: v1alpha1.SuccessStrategyStatus,
|
||||||
|
Reason: "some reason",
|
||||||
|
Message: "some message",
|
||||||
|
LastUpdateTime: t1,
|
||||||
|
Frontend: &v1alpha1.CredentialIssuerFrontend{
|
||||||
|
Type: "TokenCredentialRequestAPI",
|
||||||
|
TokenCredentialRequestAPIInfo: &v1alpha1.TokenCredentialRequestAPIInfo{
|
||||||
|
Server: "https://test-server",
|
||||||
|
CertificateAuthorityData: "test-ca-bundle",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
KubeConfigInfo: &v1alpha1.CredentialIssuerKubeConfigInfo{
|
||||||
|
Server: "https://test-server",
|
||||||
|
CertificateAuthorityData: "test-ca-bundle",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "existing entry to update",
|
name: "existing entry to update",
|
||||||
configToUpdate: v1alpha1.CredentialIssuerStatus{
|
configToUpdate: v1alpha1.CredentialIssuerStatus{
|
||||||
|
@ -33,6 +33,7 @@ const (
|
|||||||
type annotaterController struct {
|
type annotaterController struct {
|
||||||
agentPodConfig *AgentPodConfig
|
agentPodConfig *AgentPodConfig
|
||||||
credentialIssuerLocationConfig *CredentialIssuerLocationConfig
|
credentialIssuerLocationConfig *CredentialIssuerLocationConfig
|
||||||
|
credentialIssuerLabels map[string]string
|
||||||
clock clock.Clock
|
clock clock.Clock
|
||||||
k8sClient kubernetes.Interface
|
k8sClient kubernetes.Interface
|
||||||
pinnipedAPIClient pinnipedclientset.Interface
|
pinnipedAPIClient pinnipedclientset.Interface
|
||||||
@ -51,6 +52,7 @@ type annotaterController struct {
|
|||||||
func NewAnnotaterController(
|
func NewAnnotaterController(
|
||||||
agentPodConfig *AgentPodConfig,
|
agentPodConfig *AgentPodConfig,
|
||||||
credentialIssuerLocationConfig *CredentialIssuerLocationConfig,
|
credentialIssuerLocationConfig *CredentialIssuerLocationConfig,
|
||||||
|
credentialIssuerLabels map[string]string,
|
||||||
clock clock.Clock,
|
clock clock.Clock,
|
||||||
k8sClient kubernetes.Interface,
|
k8sClient kubernetes.Interface,
|
||||||
pinnipedAPIClient pinnipedclientset.Interface,
|
pinnipedAPIClient pinnipedclientset.Interface,
|
||||||
@ -64,6 +66,7 @@ func NewAnnotaterController(
|
|||||||
Syncer: &annotaterController{
|
Syncer: &annotaterController{
|
||||||
agentPodConfig: agentPodConfig,
|
agentPodConfig: agentPodConfig,
|
||||||
credentialIssuerLocationConfig: credentialIssuerLocationConfig,
|
credentialIssuerLocationConfig: credentialIssuerLocationConfig,
|
||||||
|
credentialIssuerLabels: credentialIssuerLabels,
|
||||||
clock: clock,
|
clock: clock,
|
||||||
k8sClient: k8sClient,
|
k8sClient: k8sClient,
|
||||||
pinnipedAPIClient: pinnipedAPIClient,
|
pinnipedAPIClient: pinnipedAPIClient,
|
||||||
@ -125,7 +128,7 @@ func (c *annotaterController) Sync(ctx controllerlib.Context) error {
|
|||||||
strategyResultUpdateErr := issuerconfig.UpdateStrategy(
|
strategyResultUpdateErr := issuerconfig.UpdateStrategy(
|
||||||
ctx.Context,
|
ctx.Context,
|
||||||
c.credentialIssuerLocationConfig.Name,
|
c.credentialIssuerLocationConfig.Name,
|
||||||
nil,
|
c.credentialIssuerLabels,
|
||||||
c.pinnipedAPIClient,
|
c.pinnipedAPIClient,
|
||||||
strategyError(c.clock, err),
|
strategyError(c.clock, err),
|
||||||
)
|
)
|
||||||
|
@ -41,6 +41,7 @@ func TestAnnotaterControllerFilter(t *testing.T) {
|
|||||||
) {
|
) {
|
||||||
_ = NewAnnotaterController(
|
_ = NewAnnotaterController(
|
||||||
agentPodConfig,
|
agentPodConfig,
|
||||||
|
nil, // credentialIssuerLabels, shouldn't matter
|
||||||
nil, // credentialIssuerLocationConfig, shouldn't matter
|
nil, // credentialIssuerLocationConfig, shouldn't matter
|
||||||
nil, // clock, shouldn't matter
|
nil, // clock, shouldn't matter
|
||||||
nil, // k8sClient, shouldn't matter
|
nil, // k8sClient, shouldn't matter
|
||||||
@ -85,6 +86,7 @@ func TestAnnotaterControllerSync(t *testing.T) {
|
|||||||
var podsGVR schema.GroupVersionResource
|
var podsGVR schema.GroupVersionResource
|
||||||
var credentialIssuerGVR schema.GroupVersionResource
|
var credentialIssuerGVR schema.GroupVersionResource
|
||||||
var frozenNow time.Time
|
var frozenNow time.Time
|
||||||
|
var credentialIssuerLabels map[string]string
|
||||||
|
|
||||||
// Defer starting the informers until the last possible moment so that the
|
// Defer starting the informers until the last possible moment so that the
|
||||||
// nested Before's can keep adding things to the informer caches.
|
// nested Before's can keep adding things to the informer caches.
|
||||||
@ -103,6 +105,7 @@ func TestAnnotaterControllerSync(t *testing.T) {
|
|||||||
&CredentialIssuerLocationConfig{
|
&CredentialIssuerLocationConfig{
|
||||||
Name: credentialIssuerResourceName,
|
Name: credentialIssuerResourceName,
|
||||||
},
|
},
|
||||||
|
credentialIssuerLabels,
|
||||||
clock.NewFakeClock(frozenNow),
|
clock.NewFakeClock(frozenNow),
|
||||||
kubeAPIClient,
|
kubeAPIClient,
|
||||||
pinnipedAPIClient,
|
pinnipedAPIClient,
|
||||||
@ -238,10 +241,6 @@ func TestAnnotaterControllerSync(t *testing.T) {
|
|||||||
},
|
},
|
||||||
Status: configv1alpha1.CredentialIssuerStatus{
|
Status: configv1alpha1.CredentialIssuerStatus{
|
||||||
Strategies: []configv1alpha1.CredentialIssuerStrategy{},
|
Strategies: []configv1alpha1.CredentialIssuerStrategy{},
|
||||||
KubeConfigInfo: &configv1alpha1.CredentialIssuerKubeConfigInfo{
|
|
||||||
Server: "some-server",
|
|
||||||
CertificateAuthorityData: "some-ca-value",
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
r.NoError(pinnipedAPIClient.Tracker().Add(initialCredentialIssuer))
|
r.NoError(pinnipedAPIClient.Tracker().Add(initialCredentialIssuer))
|
||||||
@ -301,6 +300,10 @@ func TestAnnotaterControllerSync(t *testing.T) {
|
|||||||
})
|
})
|
||||||
|
|
||||||
when("there is not already a CredentialIssuer", func() {
|
when("there is not already a CredentialIssuer", func() {
|
||||||
|
it.Before(func() {
|
||||||
|
credentialIssuerLabels = map[string]string{"foo": "bar"}
|
||||||
|
})
|
||||||
|
|
||||||
it("creates the CredentialIssuer status with the error", func() {
|
it("creates the CredentialIssuer status with the error", func() {
|
||||||
startInformersAndController()
|
startInformersAndController()
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
err := controllerlib.TestSync(t, subject, *syncContext)
|
||||||
@ -308,14 +311,16 @@ func TestAnnotaterControllerSync(t *testing.T) {
|
|||||||
expectedCreateCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
expectedCreateCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
||||||
TypeMeta: metav1.TypeMeta{},
|
TypeMeta: metav1.TypeMeta{},
|
||||||
ObjectMeta: metav1.ObjectMeta{
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
Name: credentialIssuerResourceName,
|
Name: credentialIssuerResourceName,
|
||||||
|
Labels: map[string]string{"foo": "bar"},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
expectedCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
expectedCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
||||||
TypeMeta: metav1.TypeMeta{},
|
TypeMeta: metav1.TypeMeta{},
|
||||||
ObjectMeta: metav1.ObjectMeta{
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
Name: credentialIssuerResourceName,
|
Name: credentialIssuerResourceName,
|
||||||
|
Labels: map[string]string{"foo": "bar"},
|
||||||
},
|
},
|
||||||
Status: configv1alpha1.CredentialIssuerStatus{
|
Status: configv1alpha1.CredentialIssuerStatus{
|
||||||
Strategies: []configv1alpha1.CredentialIssuerStrategy{
|
Strategies: []configv1alpha1.CredentialIssuerStrategy{
|
||||||
|
@ -309,10 +309,6 @@ func TestCreaterControllerSync(t *testing.T) {
|
|||||||
},
|
},
|
||||||
Status: configv1alpha1.CredentialIssuerStatus{
|
Status: configv1alpha1.CredentialIssuerStatus{
|
||||||
Strategies: []configv1alpha1.CredentialIssuerStrategy{},
|
Strategies: []configv1alpha1.CredentialIssuerStrategy{},
|
||||||
KubeConfigInfo: &configv1alpha1.CredentialIssuerKubeConfigInfo{
|
|
||||||
Server: "some-server",
|
|
||||||
CertificateAuthorityData: "some-ca-value",
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
r.NoError(pinnipedAPIClient.Tracker().Add(initialCredentialIssuer))
|
r.NoError(pinnipedAPIClient.Tracker().Add(initialCredentialIssuer))
|
||||||
@ -449,10 +445,6 @@ func TestCreaterControllerSync(t *testing.T) {
|
|||||||
},
|
},
|
||||||
Status: configv1alpha1.CredentialIssuerStatus{
|
Status: configv1alpha1.CredentialIssuerStatus{
|
||||||
Strategies: []configv1alpha1.CredentialIssuerStrategy{},
|
Strategies: []configv1alpha1.CredentialIssuerStrategy{},
|
||||||
KubeConfigInfo: &configv1alpha1.CredentialIssuerKubeConfigInfo{
|
|
||||||
Server: "some-server",
|
|
||||||
CertificateAuthorityData: "some-ca-value",
|
|
||||||
},
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
r.NoError(pinnipedAPIClient.Tracker().Add(initialCredentialIssuer))
|
r.NoError(pinnipedAPIClient.Tracker().Add(initialCredentialIssuer))
|
||||||
|
@ -4,14 +4,18 @@
|
|||||||
package kubecertagent
|
package kubecertagent
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"encoding/base64"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
|
||||||
v1 "k8s.io/api/core/v1"
|
v1 "k8s.io/api/core/v1"
|
||||||
k8serrors "k8s.io/apimachinery/pkg/api/errors"
|
k8serrors "k8s.io/apimachinery/pkg/api/errors"
|
||||||
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||||
"k8s.io/apimachinery/pkg/util/clock"
|
"k8s.io/apimachinery/pkg/util/clock"
|
||||||
corev1informers "k8s.io/client-go/informers/core/v1"
|
corev1informers "k8s.io/client-go/informers/core/v1"
|
||||||
|
"k8s.io/client-go/tools/clientcmd"
|
||||||
"k8s.io/klog/v2"
|
"k8s.io/klog/v2"
|
||||||
|
|
||||||
|
configv1alpha1 "go.pinniped.dev/generated/latest/apis/concierge/config/v1alpha1"
|
||||||
pinnipedclientset "go.pinniped.dev/generated/latest/client/concierge/clientset/versioned"
|
pinnipedclientset "go.pinniped.dev/generated/latest/client/concierge/clientset/versioned"
|
||||||
pinnipedcontroller "go.pinniped.dev/internal/controller"
|
pinnipedcontroller "go.pinniped.dev/internal/controller"
|
||||||
"go.pinniped.dev/internal/controller/issuerconfig"
|
"go.pinniped.dev/internal/controller/issuerconfig"
|
||||||
@ -19,13 +23,22 @@ import (
|
|||||||
"go.pinniped.dev/internal/dynamiccert"
|
"go.pinniped.dev/internal/dynamiccert"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
const (
|
||||||
|
ClusterInfoNamespace = "kube-public"
|
||||||
|
clusterInfoName = "cluster-info"
|
||||||
|
clusterInfoConfigMapKey = "kubeconfig"
|
||||||
|
)
|
||||||
|
|
||||||
type execerController struct {
|
type execerController struct {
|
||||||
credentialIssuerLocationConfig *CredentialIssuerLocationConfig
|
credentialIssuerLocationConfig *CredentialIssuerLocationConfig
|
||||||
|
credentialIssuerLabels map[string]string
|
||||||
|
discoveryURLOverride *string
|
||||||
dynamicCertProvider dynamiccert.Provider
|
dynamicCertProvider dynamiccert.Provider
|
||||||
podCommandExecutor PodCommandExecutor
|
podCommandExecutor PodCommandExecutor
|
||||||
clock clock.Clock
|
clock clock.Clock
|
||||||
pinnipedAPIClient pinnipedclientset.Interface
|
pinnipedAPIClient pinnipedclientset.Interface
|
||||||
agentPodInformer corev1informers.PodInformer
|
agentPodInformer corev1informers.PodInformer
|
||||||
|
configMapInformer corev1informers.ConfigMapInformer
|
||||||
}
|
}
|
||||||
|
|
||||||
// NewExecerController returns a controllerlib.Controller that listens for agent pods with proper
|
// NewExecerController returns a controllerlib.Controller that listens for agent pods with proper
|
||||||
@ -36,11 +49,14 @@ type execerController struct {
|
|||||||
// credentialIssuerLocationConfig, with any errors that it encounters.
|
// credentialIssuerLocationConfig, with any errors that it encounters.
|
||||||
func NewExecerController(
|
func NewExecerController(
|
||||||
credentialIssuerLocationConfig *CredentialIssuerLocationConfig,
|
credentialIssuerLocationConfig *CredentialIssuerLocationConfig,
|
||||||
|
credentialIssuerLabels map[string]string,
|
||||||
|
discoveryURLOverride *string,
|
||||||
dynamicCertProvider dynamiccert.Provider,
|
dynamicCertProvider dynamiccert.Provider,
|
||||||
podCommandExecutor PodCommandExecutor,
|
podCommandExecutor PodCommandExecutor,
|
||||||
pinnipedAPIClient pinnipedclientset.Interface,
|
pinnipedAPIClient pinnipedclientset.Interface,
|
||||||
clock clock.Clock,
|
clock clock.Clock,
|
||||||
agentPodInformer corev1informers.PodInformer,
|
agentPodInformer corev1informers.PodInformer,
|
||||||
|
configMapInformer corev1informers.ConfigMapInformer,
|
||||||
withInformer pinnipedcontroller.WithInformerOptionFunc,
|
withInformer pinnipedcontroller.WithInformerOptionFunc,
|
||||||
) controllerlib.Controller {
|
) controllerlib.Controller {
|
||||||
return controllerlib.New(
|
return controllerlib.New(
|
||||||
@ -48,11 +64,14 @@ func NewExecerController(
|
|||||||
Name: "kube-cert-agent-execer-controller",
|
Name: "kube-cert-agent-execer-controller",
|
||||||
Syncer: &execerController{
|
Syncer: &execerController{
|
||||||
credentialIssuerLocationConfig: credentialIssuerLocationConfig,
|
credentialIssuerLocationConfig: credentialIssuerLocationConfig,
|
||||||
|
credentialIssuerLabels: credentialIssuerLabels,
|
||||||
|
discoveryURLOverride: discoveryURLOverride,
|
||||||
dynamicCertProvider: dynamicCertProvider,
|
dynamicCertProvider: dynamicCertProvider,
|
||||||
podCommandExecutor: podCommandExecutor,
|
podCommandExecutor: podCommandExecutor,
|
||||||
pinnipedAPIClient: pinnipedAPIClient,
|
pinnipedAPIClient: pinnipedAPIClient,
|
||||||
clock: clock,
|
clock: clock,
|
||||||
agentPodInformer: agentPodInformer,
|
agentPodInformer: agentPodInformer,
|
||||||
|
configMapInformer: configMapInformer,
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
withInformer(
|
withInformer(
|
||||||
@ -60,6 +79,11 @@ func NewExecerController(
|
|||||||
pinnipedcontroller.SimpleFilter(isAgentPod, nil), // nil parent func is fine because each event is distinct
|
pinnipedcontroller.SimpleFilter(isAgentPod, nil), // nil parent func is fine because each event is distinct
|
||||||
controllerlib.InformerOption{},
|
controllerlib.InformerOption{},
|
||||||
),
|
),
|
||||||
|
withInformer(
|
||||||
|
configMapInformer,
|
||||||
|
pinnipedcontroller.NameAndNamespaceExactMatchFilterFactory(clusterInfoName, ClusterInfoNamespace),
|
||||||
|
controllerlib.InformerOption{},
|
||||||
|
),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -91,7 +115,7 @@ func (c *execerController) Sync(ctx controllerlib.Context) error {
|
|||||||
strategyResultUpdateErr := issuerconfig.UpdateStrategy(
|
strategyResultUpdateErr := issuerconfig.UpdateStrategy(
|
||||||
ctx.Context,
|
ctx.Context,
|
||||||
c.credentialIssuerLocationConfig.Name,
|
c.credentialIssuerLocationConfig.Name,
|
||||||
nil,
|
c.credentialIssuerLabels,
|
||||||
c.pinnipedAPIClient,
|
c.pinnipedAPIClient,
|
||||||
strategyError(c.clock, err),
|
strategyError(c.clock, err),
|
||||||
)
|
)
|
||||||
@ -104,7 +128,7 @@ func (c *execerController) Sync(ctx controllerlib.Context) error {
|
|||||||
strategyResultUpdateErr := issuerconfig.UpdateStrategy(
|
strategyResultUpdateErr := issuerconfig.UpdateStrategy(
|
||||||
ctx.Context,
|
ctx.Context,
|
||||||
c.credentialIssuerLocationConfig.Name,
|
c.credentialIssuerLocationConfig.Name,
|
||||||
nil,
|
c.credentialIssuerLabels,
|
||||||
c.pinnipedAPIClient,
|
c.pinnipedAPIClient,
|
||||||
strategyError(c.clock, err),
|
strategyError(c.clock, err),
|
||||||
)
|
)
|
||||||
@ -114,18 +138,74 @@ func (c *execerController) Sync(ctx controllerlib.Context) error {
|
|||||||
|
|
||||||
c.dynamicCertProvider.Set([]byte(certPEM), []byte(keyPEM))
|
c.dynamicCertProvider.Set([]byte(certPEM), []byte(keyPEM))
|
||||||
|
|
||||||
err = issuerconfig.UpdateStrategy(
|
apiInfo, err := c.getTokenCredentialRequestAPIInfo()
|
||||||
ctx.Context,
|
|
||||||
c.credentialIssuerLocationConfig.Name,
|
|
||||||
nil,
|
|
||||||
c.pinnipedAPIClient,
|
|
||||||
strategySuccess(c.clock),
|
|
||||||
)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
strategyResultUpdateErr := issuerconfig.UpdateStrategy(
|
||||||
|
ctx.Context,
|
||||||
|
c.credentialIssuerLocationConfig.Name,
|
||||||
|
c.credentialIssuerLabels,
|
||||||
|
c.pinnipedAPIClient,
|
||||||
|
configv1alpha1.CredentialIssuerStrategy{
|
||||||
|
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
||||||
|
Status: configv1alpha1.ErrorStrategyStatus,
|
||||||
|
Reason: configv1alpha1.CouldNotGetClusterInfoStrategyReason,
|
||||||
|
Message: err.Error(),
|
||||||
|
LastUpdateTime: metav1.NewTime(c.clock.Now()),
|
||||||
|
},
|
||||||
|
)
|
||||||
|
klog.ErrorS(strategyResultUpdateErr, "could not create or update CredentialIssuer with strategy success")
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
return nil
|
return issuerconfig.UpdateStrategy(
|
||||||
|
ctx.Context,
|
||||||
|
c.credentialIssuerLocationConfig.Name,
|
||||||
|
c.credentialIssuerLabels,
|
||||||
|
c.pinnipedAPIClient,
|
||||||
|
configv1alpha1.CredentialIssuerStrategy{
|
||||||
|
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
||||||
|
Status: configv1alpha1.SuccessStrategyStatus,
|
||||||
|
Reason: configv1alpha1.FetchedKeyStrategyReason,
|
||||||
|
Message: "Key was fetched successfully",
|
||||||
|
LastUpdateTime: metav1.NewTime(c.clock.Now()),
|
||||||
|
Frontend: &configv1alpha1.CredentialIssuerFrontend{
|
||||||
|
Type: configv1alpha1.TokenCredentialRequestAPIFrontendType,
|
||||||
|
TokenCredentialRequestAPIInfo: apiInfo,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (c *execerController) getTokenCredentialRequestAPIInfo() (*configv1alpha1.TokenCredentialRequestAPIInfo, error) {
|
||||||
|
configMap, err := c.configMapInformer.
|
||||||
|
Lister().
|
||||||
|
ConfigMaps(ClusterInfoNamespace).
|
||||||
|
Get(clusterInfoName)
|
||||||
|
if err != nil {
|
||||||
|
return nil, fmt.Errorf("failed to get %s configmap: %w", clusterInfoName, err)
|
||||||
|
}
|
||||||
|
|
||||||
|
kubeConfigYAML, kubeConfigPresent := configMap.Data[clusterInfoConfigMapKey]
|
||||||
|
if !kubeConfigPresent {
|
||||||
|
return nil, fmt.Errorf("failed to get %s key from %s configmap", clusterInfoConfigMapKey, clusterInfoName)
|
||||||
|
}
|
||||||
|
|
||||||
|
kubeconfig, err := clientcmd.Load([]byte(kubeConfigYAML))
|
||||||
|
if err != nil {
|
||||||
|
return nil, fmt.Errorf("failed to load data from %s key in %s configmap", clusterInfoConfigMapKey, clusterInfoName)
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, v := range kubeconfig.Clusters {
|
||||||
|
result := &configv1alpha1.TokenCredentialRequestAPIInfo{
|
||||||
|
Server: v.Server,
|
||||||
|
CertificateAuthorityData: base64.StdEncoding.EncodeToString(v.CertificateAuthorityData),
|
||||||
|
}
|
||||||
|
if c.discoveryURLOverride != nil {
|
||||||
|
result.Server = *c.discoveryURLOverride
|
||||||
|
}
|
||||||
|
return result, nil
|
||||||
|
}
|
||||||
|
return nil, fmt.Errorf("kubeconfig in %s key in %s configmap did not contain any clusters", clusterInfoConfigMapKey, clusterInfoName)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *execerController) getKeypairFilePaths(pod *v1.Pod) (string, string) {
|
func (c *execerController) getKeypairFilePaths(pod *v1.Pod) (string, string) {
|
||||||
|
@ -27,6 +27,7 @@ import (
|
|||||||
pinnipedfake "go.pinniped.dev/generated/latest/client/concierge/clientset/versioned/fake"
|
pinnipedfake "go.pinniped.dev/generated/latest/client/concierge/clientset/versioned/fake"
|
||||||
"go.pinniped.dev/internal/controllerlib"
|
"go.pinniped.dev/internal/controllerlib"
|
||||||
"go.pinniped.dev/internal/dynamiccert"
|
"go.pinniped.dev/internal/dynamiccert"
|
||||||
|
"go.pinniped.dev/internal/here"
|
||||||
"go.pinniped.dev/internal/testutil"
|
"go.pinniped.dev/internal/testutil"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -41,16 +42,21 @@ func TestExecerControllerOptions(t *testing.T) {
|
|||||||
it.Before(func() {
|
it.Before(func() {
|
||||||
r = require.New(t)
|
r = require.New(t)
|
||||||
observableWithInformerOption = testutil.NewObservableWithInformerOption()
|
observableWithInformerOption = testutil.NewObservableWithInformerOption()
|
||||||
agentPodsInformer := kubeinformers.NewSharedInformerFactory(nil, 0).Core().V1().Pods()
|
informerFactory := kubeinformers.NewSharedInformerFactory(nil, 0)
|
||||||
|
agentPodsInformer := informerFactory.Core().V1().Pods()
|
||||||
|
configMapsInformer := informerFactory.Core().V1().ConfigMaps()
|
||||||
_ = NewExecerController(
|
_ = NewExecerController(
|
||||||
&CredentialIssuerLocationConfig{
|
&CredentialIssuerLocationConfig{
|
||||||
Name: "ignored by this test",
|
Name: "ignored by this test",
|
||||||
},
|
},
|
||||||
|
nil, // credentialIssuerLabels, not needed for this test
|
||||||
|
nil, // discoveryURLOverride, not needed for this test
|
||||||
nil, // dynamicCertProvider, not needed for this test
|
nil, // dynamicCertProvider, not needed for this test
|
||||||
nil, // podCommandExecutor, not needed for this test
|
nil, // podCommandExecutor, not needed for this test
|
||||||
nil, // pinnipedAPIClient, not needed for this test
|
nil, // pinnipedAPIClient, not needed for this test
|
||||||
nil, // clock, not needed for this test
|
nil, // clock, not needed for this test
|
||||||
agentPodsInformer,
|
agentPodsInformer,
|
||||||
|
configMapsInformer,
|
||||||
observableWithInformerOption.WithInformer,
|
observableWithInformerOption.WithInformer,
|
||||||
)
|
)
|
||||||
agentPodInformerFilter = observableWithInformerOption.GetFilterForInformer(agentPodsInformer)
|
agentPodInformerFilter = observableWithInformerOption.GetFilterForInformer(agentPodsInformer)
|
||||||
@ -144,9 +150,11 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
var timeoutContextCancel context.CancelFunc
|
var timeoutContextCancel context.CancelFunc
|
||||||
var syncContext *controllerlib.Context
|
var syncContext *controllerlib.Context
|
||||||
var pinnipedAPIClient *pinnipedfake.Clientset
|
var pinnipedAPIClient *pinnipedfake.Clientset
|
||||||
var agentPodInformer kubeinformers.SharedInformerFactory
|
var kubeInformerFactory kubeinformers.SharedInformerFactory
|
||||||
var agentPodInformerClient *kubernetesfake.Clientset
|
var kubeClientset *kubernetesfake.Clientset
|
||||||
var fakeExecutor *fakePodExecutor
|
var fakeExecutor *fakePodExecutor
|
||||||
|
var credentialIssuerLabels map[string]string
|
||||||
|
var discoveryURLOverride *string
|
||||||
var dynamicCertProvider dynamiccert.Provider
|
var dynamicCertProvider dynamiccert.Provider
|
||||||
var fakeCertPEM, fakeKeyPEM string
|
var fakeCertPEM, fakeKeyPEM string
|
||||||
var credentialIssuerGVR schema.GroupVersionResource
|
var credentialIssuerGVR schema.GroupVersionResource
|
||||||
@ -160,11 +168,14 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
&CredentialIssuerLocationConfig{
|
&CredentialIssuerLocationConfig{
|
||||||
Name: credentialIssuerResourceName,
|
Name: credentialIssuerResourceName,
|
||||||
},
|
},
|
||||||
|
credentialIssuerLabels,
|
||||||
|
discoveryURLOverride,
|
||||||
dynamicCertProvider,
|
dynamicCertProvider,
|
||||||
fakeExecutor,
|
fakeExecutor,
|
||||||
pinnipedAPIClient,
|
pinnipedAPIClient,
|
||||||
clock.NewFakeClock(frozenNow),
|
clock.NewFakeClock(frozenNow),
|
||||||
agentPodInformer.Core().V1().Pods(),
|
kubeInformerFactory.Core().V1().Pods(),
|
||||||
|
kubeInformerFactory.Core().V1().ConfigMaps(),
|
||||||
controllerlib.WithInformer,
|
controllerlib.WithInformer,
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -179,7 +190,7 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Must start informers before calling TestRunSynchronously()
|
// Must start informers before calling TestRunSynchronously()
|
||||||
agentPodInformer.Start(timeoutContext.Done())
|
kubeInformerFactory.Start(timeoutContext.Done())
|
||||||
controllerlib.TestRunSynchronously(t, subject)
|
controllerlib.TestRunSynchronously(t, subject)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -219,8 +230,8 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
|
|
||||||
timeoutContext, timeoutContextCancel = context.WithTimeout(context.Background(), time.Second*3)
|
timeoutContext, timeoutContextCancel = context.WithTimeout(context.Background(), time.Second*3)
|
||||||
pinnipedAPIClient = pinnipedfake.NewSimpleClientset()
|
pinnipedAPIClient = pinnipedfake.NewSimpleClientset()
|
||||||
agentPodInformerClient = kubernetesfake.NewSimpleClientset()
|
kubeClientset = kubernetesfake.NewSimpleClientset()
|
||||||
agentPodInformer = kubeinformers.NewSharedInformerFactory(agentPodInformerClient, 0)
|
kubeInformerFactory = kubeinformers.NewSharedInformerFactory(kubeClientset, 0)
|
||||||
fakeExecutor = &fakePodExecutor{r: r}
|
fakeExecutor = &fakePodExecutor{r: r}
|
||||||
frozenNow = time.Date(2020, time.September, 23, 7, 42, 0, 0, time.Local)
|
frozenNow = time.Date(2020, time.September, 23, 7, 42, 0, 0, time.Local)
|
||||||
dynamicCertProvider = dynamiccert.New()
|
dynamicCertProvider = dynamiccert.New()
|
||||||
@ -253,7 +264,7 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
Namespace: agentPodNamespace,
|
Namespace: agentPodNamespace,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
r.NoError(agentPodInformerClient.Tracker().Add(unrelatedPod))
|
r.NoError(kubeClientset.Tracker().Add(unrelatedPod))
|
||||||
startInformersAndController()
|
startInformersAndController()
|
||||||
})
|
})
|
||||||
|
|
||||||
@ -266,7 +277,7 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
when("there is an agent pod, as determined by its labels matching the agent pod template labels, which is not yet annotated by the annotater controller", func() {
|
when("there is an agent pod, as determined by its labels matching the agent pod template labels, which is not yet annotated by the annotater controller", func() {
|
||||||
it.Before(func() {
|
it.Before(func() {
|
||||||
agentPod := newAgentPod(agentPodName, false)
|
agentPod := newAgentPod(agentPodName, false)
|
||||||
r.NoError(agentPodInformerClient.Tracker().Add(agentPod))
|
r.NoError(kubeClientset.Tracker().Add(agentPod))
|
||||||
startInformersAndController()
|
startInformersAndController()
|
||||||
})
|
})
|
||||||
|
|
||||||
@ -280,7 +291,7 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
it.Before(func() {
|
it.Before(func() {
|
||||||
agentPod := newAgentPod(agentPodName, true)
|
agentPod := newAgentPod(agentPodName, true)
|
||||||
agentPod.Status.Phase = corev1.PodPending // not Running
|
agentPod.Status.Phase = corev1.PodPending // not Running
|
||||||
r.NoError(agentPodInformerClient.Tracker().Add(agentPod))
|
r.NoError(kubeClientset.Tracker().Add(agentPod))
|
||||||
startInformersAndController()
|
startInformersAndController()
|
||||||
})
|
})
|
||||||
|
|
||||||
@ -295,8 +306,8 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
targetAgentPod := newAgentPod(agentPodName, true)
|
targetAgentPod := newAgentPod(agentPodName, true)
|
||||||
targetAgentPod.Status.Phase = corev1.PodRunning
|
targetAgentPod.Status.Phase = corev1.PodRunning
|
||||||
anotherAgentPod := newAgentPod("some-other-agent-pod-which-is-not-the-context-of-this-sync", true)
|
anotherAgentPod := newAgentPod("some-other-agent-pod-which-is-not-the-context-of-this-sync", true)
|
||||||
r.NoError(agentPodInformerClient.Tracker().Add(targetAgentPod))
|
r.NoError(kubeClientset.Tracker().Add(targetAgentPod))
|
||||||
r.NoError(agentPodInformerClient.Tracker().Add(anotherAgentPod))
|
r.NoError(kubeClientset.Tracker().Add(anotherAgentPod))
|
||||||
})
|
})
|
||||||
|
|
||||||
when("the resulting pod execs will succeed", func() {
|
when("the resulting pod execs will succeed", func() {
|
||||||
@ -304,90 +315,10 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
fakeExecutor.resultsToReturn = []string{fakeCertPEM, fakeKeyPEM}
|
fakeExecutor.resultsToReturn = []string{fakeCertPEM, fakeKeyPEM}
|
||||||
})
|
})
|
||||||
|
|
||||||
it("execs to the agent pod to get the keys and updates the dynamic certificates provider with the new certs", func() {
|
when("the cluster-info ConfigMap is not found", func() {
|
||||||
startInformersAndController()
|
it("returns an error and updates the strategy with an error", func() {
|
||||||
r.NoError(controllerlib.TestSync(t, subject, *syncContext))
|
|
||||||
|
|
||||||
r.Equal(2, fakeExecutor.callCount)
|
|
||||||
|
|
||||||
r.Equal(agentPodNamespace, fakeExecutor.calledWithPodNamespace[0])
|
|
||||||
r.Equal(agentPodName, fakeExecutor.calledWithPodName[0])
|
|
||||||
r.Equal([]string{"cat", fakeCertPath}, fakeExecutor.calledWithCommandAndArgs[0])
|
|
||||||
|
|
||||||
r.Equal(agentPodNamespace, fakeExecutor.calledWithPodNamespace[1])
|
|
||||||
r.Equal(agentPodName, fakeExecutor.calledWithPodName[1])
|
|
||||||
r.Equal([]string{"cat", fakeKeyPath}, fakeExecutor.calledWithCommandAndArgs[1])
|
|
||||||
|
|
||||||
actualCertPEM, actualKeyPEM := dynamicCertProvider.CurrentCertKeyContent()
|
|
||||||
r.Equal(fakeCertPEM, string(actualCertPEM))
|
|
||||||
r.Equal(fakeKeyPEM, string(actualKeyPEM))
|
|
||||||
})
|
|
||||||
|
|
||||||
when("there is already a CredentialIssuer", func() {
|
|
||||||
var initialCredentialIssuer *configv1alpha1.CredentialIssuer
|
|
||||||
|
|
||||||
it.Before(func() {
|
|
||||||
initialCredentialIssuer = &configv1alpha1.CredentialIssuer{
|
|
||||||
TypeMeta: metav1.TypeMeta{},
|
|
||||||
ObjectMeta: metav1.ObjectMeta{
|
|
||||||
Name: credentialIssuerResourceName,
|
|
||||||
},
|
|
||||||
Status: configv1alpha1.CredentialIssuerStatus{
|
|
||||||
Strategies: []configv1alpha1.CredentialIssuerStrategy{},
|
|
||||||
KubeConfigInfo: &configv1alpha1.CredentialIssuerKubeConfigInfo{
|
|
||||||
Server: "some-server",
|
|
||||||
CertificateAuthorityData: "some-ca-value",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
r.NoError(pinnipedAPIClient.Tracker().Add(initialCredentialIssuer))
|
|
||||||
})
|
|
||||||
|
|
||||||
it("also updates the the existing CredentialIssuer status field", func() {
|
|
||||||
startInformersAndController()
|
startInformersAndController()
|
||||||
r.NoError(controllerlib.TestSync(t, subject, *syncContext))
|
r.EqualError(controllerlib.TestSync(t, subject, *syncContext), `failed to get cluster-info configmap: configmap "cluster-info" not found`)
|
||||||
|
|
||||||
expectedCredentialIssuer := initialCredentialIssuer.DeepCopy()
|
|
||||||
expectedCredentialIssuer.Status.Strategies = []configv1alpha1.CredentialIssuerStrategy{
|
|
||||||
{
|
|
||||||
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
|
||||||
Status: configv1alpha1.SuccessStrategyStatus,
|
|
||||||
Reason: configv1alpha1.FetchedKeyStrategyReason,
|
|
||||||
Message: "Key was fetched successfully",
|
|
||||||
LastUpdateTime: metav1.NewTime(frozenNow),
|
|
||||||
},
|
|
||||||
}
|
|
||||||
expectedGetAction := coretesting.NewRootGetAction(credentialIssuerGVR, credentialIssuerResourceName)
|
|
||||||
expectedCreateAction := coretesting.NewRootUpdateSubresourceAction(credentialIssuerGVR, "status", expectedCredentialIssuer)
|
|
||||||
r.Equal([]coretesting.Action{expectedGetAction, expectedCreateAction}, pinnipedAPIClient.Actions())
|
|
||||||
})
|
|
||||||
|
|
||||||
when("updating the CredentialIssuer fails", func() {
|
|
||||||
it.Before(func() {
|
|
||||||
pinnipedAPIClient.PrependReactor(
|
|
||||||
"update",
|
|
||||||
"credentialissuers",
|
|
||||||
func(_ coretesting.Action) (bool, runtime.Object, error) {
|
|
||||||
return true, nil, errors.New("some update error")
|
|
||||||
},
|
|
||||||
)
|
|
||||||
})
|
|
||||||
|
|
||||||
it("returns an error", func() {
|
|
||||||
startInformersAndController()
|
|
||||||
err := controllerlib.TestSync(t, subject, *syncContext)
|
|
||||||
r.EqualError(err, "could not create or update credentialissuer: some update error")
|
|
||||||
})
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
when("there is not already a CredentialIssuer", func() {
|
|
||||||
it.Before(func() {
|
|
||||||
startInformersAndController()
|
|
||||||
})
|
|
||||||
|
|
||||||
it("also creates the the CredentialIssuer with the appropriate status field", func() {
|
|
||||||
r.NoError(controllerlib.TestSync(t, subject, *syncContext))
|
|
||||||
|
|
||||||
expectedCreateCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
expectedCreateCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
||||||
TypeMeta: metav1.TypeMeta{},
|
TypeMeta: metav1.TypeMeta{},
|
||||||
@ -405,9 +336,9 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
Strategies: []configv1alpha1.CredentialIssuerStrategy{
|
Strategies: []configv1alpha1.CredentialIssuerStrategy{
|
||||||
{
|
{
|
||||||
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
||||||
Status: configv1alpha1.SuccessStrategyStatus,
|
Status: configv1alpha1.ErrorStrategyStatus,
|
||||||
Reason: configv1alpha1.FetchedKeyStrategyReason,
|
Reason: configv1alpha1.CouldNotGetClusterInfoStrategyReason,
|
||||||
Message: "Key was fetched successfully",
|
Message: `failed to get cluster-info configmap: configmap "cluster-info" not found`,
|
||||||
LastUpdateTime: metav1.NewTime(frozenNow),
|
LastUpdateTime: metav1.NewTime(frozenNow),
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@ -419,6 +350,226 @@ func TestManagerControllerSync(t *testing.T) {
|
|||||||
r.Equal([]coretesting.Action{expectedGetAction, expectedCreateAction, expectedUpdateAction}, pinnipedAPIClient.Actions())
|
r.Equal([]coretesting.Action{expectedGetAction, expectedCreateAction, expectedUpdateAction}, pinnipedAPIClient.Actions())
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
when("the cluster-info ConfigMap is missing a key", func() {
|
||||||
|
it.Before(func() {
|
||||||
|
r.NoError(kubeClientset.Tracker().Add(&corev1.ConfigMap{
|
||||||
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
|
Namespace: ClusterInfoNamespace,
|
||||||
|
Name: clusterInfoName,
|
||||||
|
},
|
||||||
|
Data: map[string]string{"uninteresting-key": "uninteresting-value"},
|
||||||
|
}))
|
||||||
|
})
|
||||||
|
it("returns an error", func() {
|
||||||
|
startInformersAndController()
|
||||||
|
r.EqualError(controllerlib.TestSync(t, subject, *syncContext), `failed to get kubeconfig key from cluster-info configmap`)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
when("the cluster-info ConfigMap is contains invalid YAML", func() {
|
||||||
|
it.Before(func() {
|
||||||
|
r.NoError(kubeClientset.Tracker().Add(&corev1.ConfigMap{
|
||||||
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
|
Namespace: ClusterInfoNamespace,
|
||||||
|
Name: clusterInfoName,
|
||||||
|
},
|
||||||
|
Data: map[string]string{"kubeconfig": "invalid-yaml"},
|
||||||
|
}))
|
||||||
|
})
|
||||||
|
it("returns an error", func() {
|
||||||
|
startInformersAndController()
|
||||||
|
r.EqualError(controllerlib.TestSync(t, subject, *syncContext), `failed to load data from kubeconfig key in cluster-info configmap`)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
when("the cluster-info ConfigMap is contains an empty list of clusters", func() {
|
||||||
|
it.Before(func() {
|
||||||
|
r.NoError(kubeClientset.Tracker().Add(&corev1.ConfigMap{
|
||||||
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
|
Namespace: ClusterInfoNamespace,
|
||||||
|
Name: clusterInfoName,
|
||||||
|
},
|
||||||
|
Data: map[string]string{
|
||||||
|
"kubeconfig": here.Doc(`
|
||||||
|
kind: Config
|
||||||
|
apiVersion: v1
|
||||||
|
clusters: []
|
||||||
|
`),
|
||||||
|
"uninteresting-key": "uninteresting-value",
|
||||||
|
},
|
||||||
|
}))
|
||||||
|
})
|
||||||
|
it("returns an error", func() {
|
||||||
|
startInformersAndController()
|
||||||
|
r.EqualError(controllerlib.TestSync(t, subject, *syncContext), `kubeconfig in kubeconfig key in cluster-info configmap did not contain any clusters`)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
when("the cluster-info ConfigMap is valid", func() {
|
||||||
|
it.Before(func() {
|
||||||
|
const caData = "c29tZS1jZXJ0aWZpY2F0ZS1hdXRob3JpdHktZGF0YQo=" // "some-certificate-authority-data" base64 encoded
|
||||||
|
const kubeServerURL = "https://some-server"
|
||||||
|
r.NoError(kubeClientset.Tracker().Add(&corev1.ConfigMap{
|
||||||
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
|
Namespace: ClusterInfoNamespace,
|
||||||
|
Name: clusterInfoName,
|
||||||
|
},
|
||||||
|
Data: map[string]string{
|
||||||
|
"kubeconfig": here.Docf(`
|
||||||
|
kind: Config
|
||||||
|
apiVersion: v1
|
||||||
|
clusters:
|
||||||
|
- name: ""
|
||||||
|
cluster:
|
||||||
|
certificate-authority-data: "%s"
|
||||||
|
server: "%s"`,
|
||||||
|
caData, kubeServerURL),
|
||||||
|
"uninteresting-key": "uninteresting-value",
|
||||||
|
},
|
||||||
|
}))
|
||||||
|
})
|
||||||
|
|
||||||
|
it("execs to the agent pod to get the keys and updates the dynamic certificates provider with the new certs", func() {
|
||||||
|
startInformersAndController()
|
||||||
|
r.NoError(controllerlib.TestSync(t, subject, *syncContext))
|
||||||
|
|
||||||
|
r.Equal(2, fakeExecutor.callCount)
|
||||||
|
|
||||||
|
r.Equal(agentPodNamespace, fakeExecutor.calledWithPodNamespace[0])
|
||||||
|
r.Equal(agentPodName, fakeExecutor.calledWithPodName[0])
|
||||||
|
r.Equal([]string{"cat", fakeCertPath}, fakeExecutor.calledWithCommandAndArgs[0])
|
||||||
|
|
||||||
|
r.Equal(agentPodNamespace, fakeExecutor.calledWithPodNamespace[1])
|
||||||
|
r.Equal(agentPodName, fakeExecutor.calledWithPodName[1])
|
||||||
|
r.Equal([]string{"cat", fakeKeyPath}, fakeExecutor.calledWithCommandAndArgs[1])
|
||||||
|
|
||||||
|
actualCertPEM, actualKeyPEM := dynamicCertProvider.CurrentCertKeyContent()
|
||||||
|
r.Equal(fakeCertPEM, string(actualCertPEM))
|
||||||
|
r.Equal(fakeKeyPEM, string(actualKeyPEM))
|
||||||
|
})
|
||||||
|
|
||||||
|
when("there is already a CredentialIssuer", func() {
|
||||||
|
var initialCredentialIssuer *configv1alpha1.CredentialIssuer
|
||||||
|
|
||||||
|
it.Before(func() {
|
||||||
|
initialCredentialIssuer = &configv1alpha1.CredentialIssuer{
|
||||||
|
TypeMeta: metav1.TypeMeta{},
|
||||||
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
|
Name: credentialIssuerResourceName,
|
||||||
|
},
|
||||||
|
Status: configv1alpha1.CredentialIssuerStatus{
|
||||||
|
Strategies: []configv1alpha1.CredentialIssuerStrategy{},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
r.NoError(pinnipedAPIClient.Tracker().Add(initialCredentialIssuer))
|
||||||
|
})
|
||||||
|
|
||||||
|
it("also updates the the existing CredentialIssuer status field", func() {
|
||||||
|
startInformersAndController()
|
||||||
|
r.NoError(controllerlib.TestSync(t, subject, *syncContext))
|
||||||
|
|
||||||
|
// The first update to the CredentialIssuer will set the strategy entry
|
||||||
|
expectedCredentialIssuer := initialCredentialIssuer.DeepCopy()
|
||||||
|
expectedCredentialIssuer.Status.Strategies = []configv1alpha1.CredentialIssuerStrategy{
|
||||||
|
{
|
||||||
|
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
||||||
|
Status: configv1alpha1.SuccessStrategyStatus,
|
||||||
|
Reason: configv1alpha1.FetchedKeyStrategyReason,
|
||||||
|
Message: "Key was fetched successfully",
|
||||||
|
LastUpdateTime: metav1.NewTime(frozenNow),
|
||||||
|
Frontend: &configv1alpha1.CredentialIssuerFrontend{
|
||||||
|
Type: configv1alpha1.TokenCredentialRequestAPIFrontendType,
|
||||||
|
TokenCredentialRequestAPIInfo: &configv1alpha1.TokenCredentialRequestAPIInfo{
|
||||||
|
Server: "https://some-server",
|
||||||
|
CertificateAuthorityData: "c29tZS1jZXJ0aWZpY2F0ZS1hdXRob3JpdHktZGF0YQo=",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
expectedCredentialIssuer.Status.KubeConfigInfo = &configv1alpha1.CredentialIssuerKubeConfigInfo{
|
||||||
|
Server: "https://some-server",
|
||||||
|
CertificateAuthorityData: "c29tZS1jZXJ0aWZpY2F0ZS1hdXRob3JpdHktZGF0YQo=",
|
||||||
|
}
|
||||||
|
expectedGetAction := coretesting.NewRootGetAction(credentialIssuerGVR, credentialIssuerResourceName)
|
||||||
|
expectedCreateAction := coretesting.NewRootUpdateSubresourceAction(credentialIssuerGVR, "status", expectedCredentialIssuer)
|
||||||
|
r.Equal([]coretesting.Action{expectedGetAction, expectedCreateAction}, pinnipedAPIClient.Actions())
|
||||||
|
})
|
||||||
|
|
||||||
|
when("updating the CredentialIssuer fails", func() {
|
||||||
|
it.Before(func() {
|
||||||
|
pinnipedAPIClient.PrependReactor(
|
||||||
|
"update",
|
||||||
|
"credentialissuers",
|
||||||
|
func(_ coretesting.Action) (bool, runtime.Object, error) {
|
||||||
|
return true, nil, errors.New("some update error")
|
||||||
|
},
|
||||||
|
)
|
||||||
|
})
|
||||||
|
|
||||||
|
it("returns an error", func() {
|
||||||
|
startInformersAndController()
|
||||||
|
err := controllerlib.TestSync(t, subject, *syncContext)
|
||||||
|
r.EqualError(err, "could not create or update credentialissuer: some update error")
|
||||||
|
})
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
when("there is not already a CredentialIssuer", func() {
|
||||||
|
it.Before(func() {
|
||||||
|
server := "https://overridden-server-url.example.com"
|
||||||
|
discoveryURLOverride = &server
|
||||||
|
credentialIssuerLabels = map[string]string{"foo": "bar"}
|
||||||
|
startInformersAndController()
|
||||||
|
})
|
||||||
|
|
||||||
|
it("also creates the the CredentialIssuer with the appropriate status field and labels", func() {
|
||||||
|
r.NoError(controllerlib.TestSync(t, subject, *syncContext))
|
||||||
|
|
||||||
|
expectedCreateCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
||||||
|
TypeMeta: metav1.TypeMeta{},
|
||||||
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
|
Name: credentialIssuerResourceName,
|
||||||
|
Labels: map[string]string{"foo": "bar"},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
expectedCredentialIssuer := &configv1alpha1.CredentialIssuer{
|
||||||
|
TypeMeta: metav1.TypeMeta{},
|
||||||
|
ObjectMeta: metav1.ObjectMeta{
|
||||||
|
Name: credentialIssuerResourceName,
|
||||||
|
Labels: map[string]string{"foo": "bar"},
|
||||||
|
},
|
||||||
|
Status: configv1alpha1.CredentialIssuerStatus{
|
||||||
|
Strategies: []configv1alpha1.CredentialIssuerStrategy{
|
||||||
|
{
|
||||||
|
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
||||||
|
Status: configv1alpha1.SuccessStrategyStatus,
|
||||||
|
Reason: configv1alpha1.FetchedKeyStrategyReason,
|
||||||
|
Message: "Key was fetched successfully",
|
||||||
|
LastUpdateTime: metav1.NewTime(frozenNow),
|
||||||
|
Frontend: &configv1alpha1.CredentialIssuerFrontend{
|
||||||
|
Type: configv1alpha1.TokenCredentialRequestAPIFrontendType,
|
||||||
|
TokenCredentialRequestAPIInfo: &configv1alpha1.TokenCredentialRequestAPIInfo{
|
||||||
|
Server: "https://overridden-server-url.example.com",
|
||||||
|
CertificateAuthorityData: "c29tZS1jZXJ0aWZpY2F0ZS1hdXRob3JpdHktZGF0YQo=",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
KubeConfigInfo: &configv1alpha1.CredentialIssuerKubeConfigInfo{
|
||||||
|
Server: "https://overridden-server-url.example.com",
|
||||||
|
CertificateAuthorityData: "c29tZS1jZXJ0aWZpY2F0ZS1hdXRob3JpdHktZGF0YQo=",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
expectedGetAction := coretesting.NewRootGetAction(credentialIssuerGVR, credentialIssuerResourceName)
|
||||||
|
expectedCreateAction := coretesting.NewRootCreateAction(credentialIssuerGVR, expectedCreateCredentialIssuer)
|
||||||
|
expectedUpdateAction := coretesting.NewRootUpdateSubresourceAction(credentialIssuerGVR, "status", expectedCredentialIssuer)
|
||||||
|
r.Equal([]coretesting.Action{expectedGetAction, expectedCreateAction, expectedUpdateAction}, pinnipedAPIClient.Actions())
|
||||||
|
})
|
||||||
|
})
|
||||||
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
when("the first resulting pod exec will fail", func() {
|
when("the first resulting pod exec will fail", func() {
|
||||||
|
@ -277,16 +277,6 @@ func findControllerManagerPodForSpecificAgentPod(
|
|||||||
return maybeControllerManagerPod, nil
|
return maybeControllerManagerPod, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func strategySuccess(clock clock.Clock) configv1alpha1.CredentialIssuerStrategy {
|
|
||||||
return configv1alpha1.CredentialIssuerStrategy{
|
|
||||||
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
|
||||||
Status: configv1alpha1.SuccessStrategyStatus,
|
|
||||||
Reason: configv1alpha1.FetchedKeyStrategyReason,
|
|
||||||
Message: "Key was fetched successfully",
|
|
||||||
LastUpdateTime: metav1.NewTime(clock.Now()),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func strategyError(clock clock.Clock, err error) configv1alpha1.CredentialIssuerStrategy {
|
func strategyError(clock clock.Clock, err error) configv1alpha1.CredentialIssuerStrategy {
|
||||||
return configv1alpha1.CredentialIssuerStrategy{
|
return configv1alpha1.CredentialIssuerStrategy{
|
||||||
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
Type: configv1alpha1.KubeClusterSigningCertificateStrategyType,
|
||||||
|
@ -24,7 +24,6 @@ import (
|
|||||||
"go.pinniped.dev/internal/controller/authenticator/cachecleaner"
|
"go.pinniped.dev/internal/controller/authenticator/cachecleaner"
|
||||||
"go.pinniped.dev/internal/controller/authenticator/jwtcachefiller"
|
"go.pinniped.dev/internal/controller/authenticator/jwtcachefiller"
|
||||||
"go.pinniped.dev/internal/controller/authenticator/webhookcachefiller"
|
"go.pinniped.dev/internal/controller/authenticator/webhookcachefiller"
|
||||||
"go.pinniped.dev/internal/controller/issuerconfig"
|
|
||||||
"go.pinniped.dev/internal/controller/kubecertagent"
|
"go.pinniped.dev/internal/controller/kubecertagent"
|
||||||
"go.pinniped.dev/internal/controllerlib"
|
"go.pinniped.dev/internal/controllerlib"
|
||||||
"go.pinniped.dev/internal/deploymentref"
|
"go.pinniped.dev/internal/deploymentref"
|
||||||
@ -124,20 +123,6 @@ func PrepareControllers(c *Config) (func(ctx context.Context), error) {
|
|||||||
controllerManager := controllerlib.
|
controllerManager := controllerlib.
|
||||||
NewManager().
|
NewManager().
|
||||||
|
|
||||||
// KubeConfig info publishing controller is responsible for writing the KubeConfig information to the
|
|
||||||
// CredentialIssuer resource and keeping that information up to date.
|
|
||||||
WithController(
|
|
||||||
issuerconfig.NewKubeConfigInfoPublisherController(
|
|
||||||
c.NamesConfig.CredentialIssuer,
|
|
||||||
c.Labels,
|
|
||||||
c.DiscoveryURLOverride,
|
|
||||||
client.PinnipedConcierge,
|
|
||||||
informers.kubePublicNamespaceK8s.Core().V1().ConfigMaps(),
|
|
||||||
controllerlib.WithInformer,
|
|
||||||
),
|
|
||||||
singletonWorker,
|
|
||||||
).
|
|
||||||
|
|
||||||
// API certs controllers are responsible for managing the TLS certificates used to serve Pinniped's API.
|
// API certs controllers are responsible for managing the TLS certificates used to serve Pinniped's API.
|
||||||
WithController(
|
WithController(
|
||||||
apicerts.NewCertsManagerController(
|
apicerts.NewCertsManagerController(
|
||||||
@ -219,6 +204,7 @@ func PrepareControllers(c *Config) (func(ctx context.Context), error) {
|
|||||||
kubecertagent.NewAnnotaterController(
|
kubecertagent.NewAnnotaterController(
|
||||||
agentPodConfig,
|
agentPodConfig,
|
||||||
credentialIssuerLocationConfig,
|
credentialIssuerLocationConfig,
|
||||||
|
c.Labels,
|
||||||
clock.RealClock{},
|
clock.RealClock{},
|
||||||
client.Kubernetes,
|
client.Kubernetes,
|
||||||
client.PinnipedConcierge,
|
client.PinnipedConcierge,
|
||||||
@ -231,11 +217,14 @@ func PrepareControllers(c *Config) (func(ctx context.Context), error) {
|
|||||||
WithController(
|
WithController(
|
||||||
kubecertagent.NewExecerController(
|
kubecertagent.NewExecerController(
|
||||||
credentialIssuerLocationConfig,
|
credentialIssuerLocationConfig,
|
||||||
|
c.Labels,
|
||||||
|
c.DiscoveryURLOverride,
|
||||||
c.DynamicSigningCertProvider,
|
c.DynamicSigningCertProvider,
|
||||||
kubecertagent.NewPodCommandExecutor(client.JSONConfig, client.Kubernetes),
|
kubecertagent.NewPodCommandExecutor(client.JSONConfig, client.Kubernetes),
|
||||||
client.PinnipedConcierge,
|
client.PinnipedConcierge,
|
||||||
clock.RealClock{},
|
clock.RealClock{},
|
||||||
informers.installationNamespaceK8s.Core().V1().Pods(),
|
informers.installationNamespaceK8s.Core().V1().Pods(),
|
||||||
|
informers.kubePublicNamespaceK8s.Core().V1().ConfigMaps(),
|
||||||
controllerlib.WithInformer,
|
controllerlib.WithInformer,
|
||||||
),
|
),
|
||||||
singletonWorker,
|
singletonWorker,
|
||||||
@ -303,7 +292,7 @@ func createInformers(
|
|||||||
kubePublicNamespaceK8s: k8sinformers.NewSharedInformerFactoryWithOptions(
|
kubePublicNamespaceK8s: k8sinformers.NewSharedInformerFactoryWithOptions(
|
||||||
k8sClient,
|
k8sClient,
|
||||||
defaultResyncInterval,
|
defaultResyncInterval,
|
||||||
k8sinformers.WithNamespace(issuerconfig.ClusterInfoNamespace),
|
k8sinformers.WithNamespace(kubecertagent.ClusterInfoNamespace),
|
||||||
),
|
),
|
||||||
kubeSystemNamespaceK8s: k8sinformers.NewSharedInformerFactoryWithOptions(
|
kubeSystemNamespaceK8s: k8sinformers.NewSharedInformerFactoryWithOptions(
|
||||||
k8sClient,
|
k8sClient,
|
||||||
|
@ -72,12 +72,20 @@ func TestCredentialIssuer(t *testing.T) {
|
|||||||
require.Equal(t, configv1alpha1.SuccessStrategyStatus, actualStatusStrategy.Status)
|
require.Equal(t, configv1alpha1.SuccessStrategyStatus, actualStatusStrategy.Status)
|
||||||
require.Equal(t, configv1alpha1.FetchedKeyStrategyReason, actualStatusStrategy.Reason)
|
require.Equal(t, configv1alpha1.FetchedKeyStrategyReason, actualStatusStrategy.Reason)
|
||||||
require.Equal(t, "Key was fetched successfully", actualStatusStrategy.Message)
|
require.Equal(t, "Key was fetched successfully", actualStatusStrategy.Message)
|
||||||
|
require.NotNil(t, actualStatusStrategy.Frontend)
|
||||||
|
require.Equal(t, configv1alpha1.TokenCredentialRequestAPIFrontendType, actualStatusStrategy.Frontend.Type)
|
||||||
|
expectedTokenRequestAPIInfo := configv1alpha1.TokenCredentialRequestAPIInfo{
|
||||||
|
Server: config.Host,
|
||||||
|
CertificateAuthorityData: base64.StdEncoding.EncodeToString(config.TLSClientConfig.CAData),
|
||||||
|
}
|
||||||
|
require.Equal(t, &expectedTokenRequestAPIInfo, actualStatusStrategy.Frontend.TokenCredentialRequestAPIInfo)
|
||||||
|
|
||||||
// Verify the published kube config info.
|
// Verify the published kube config info.
|
||||||
require.Equal(
|
require.Equal(
|
||||||
t,
|
t,
|
||||||
&configv1alpha1.CredentialIssuerKubeConfigInfo{
|
&configv1alpha1.CredentialIssuerKubeConfigInfo{
|
||||||
Server: config.Host,
|
Server: expectedTokenRequestAPIInfo.Server,
|
||||||
CertificateAuthorityData: base64.StdEncoding.EncodeToString(config.TLSClientConfig.CAData),
|
CertificateAuthorityData: expectedTokenRequestAPIInfo.CertificateAuthorityData,
|
||||||
},
|
},
|
||||||
actualStatusKubeConfigInfo,
|
actualStatusKubeConfigInfo,
|
||||||
)
|
)
|
Loading…
Reference in New Issue
Block a user