Skip to content

Commit

Permalink
未开发完,有过期时间的token
Browse files Browse the repository at this point in the history
Signed-off-by: renxiangyu <[email protected]>
  • Loading branch information
renxiangyu committed Dec 20, 2023
1 parent 04938bf commit 5299f53
Show file tree
Hide file tree
Showing 51 changed files with 11,125 additions and 85 deletions.
7 changes: 7 additions & 0 deletions cmd/clustertree/cluster-manager/app/manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -213,6 +213,13 @@ func run(ctx context.Context, opts *options.Options) error {
}
}

podcontrollers.RootPodReconciler{
Client: nil,
RootClient: nil,
DynamicRootClient: nil,
GlobalLeafManager: nil,
Options: nil,
}
// init rootPodController
rootPodReconciler := podcontrollers.RootPodReconciler{
GlobalLeafManager: globalleafManager,
Expand Down
1 change: 1 addition & 0 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -175,6 +175,7 @@ require (
gopkg.in/go-playground/validator.v9 v9.27.0 // indirect
gopkg.in/inf.v0 v0.9.1 // indirect
gopkg.in/natefinch/lumberjack.v2 v2.0.0 // indirect
gopkg.in/square/go-jose.v2 v2.5.1 // indirect
gopkg.in/yaml.v2 v2.4.0 // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect
k8s.io/cloud-provider v0.26.3 // indirect
Expand Down
1 change: 1 addition & 0 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -2212,6 +2212,7 @@ gopkg.in/natefinch/lumberjack.v2 v2.0.0/go.mod h1:l0ndWWf7gzL7RNwBG7wST/UCcT4T24
gopkg.in/resty.v1 v1.12.0/go.mod h1:mDo4pnntr5jdWRML875a/NmxYqAlA73dVijT2AXvQQo=
gopkg.in/square/go-jose.v2 v2.2.2/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI=
gopkg.in/square/go-jose.v2 v2.3.1/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI=
gopkg.in/square/go-jose.v2 v2.5.1 h1:7odma5RETjNHWJnR32wx8t+Io4djHE1PqxCFx3iiZ2w=
gopkg.in/square/go-jose.v2 v2.5.1/go.mod h1:M9dMgbHiYLoDGQrXy7OpJDJWiKiU//h+vD76mk0e1AI=
gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7 h1:uRGJdciOHaEIrze2W8Q3AKkepLTh2hOroT7a+7czfdQ=
gopkg.in/tomb.v1 v1.0.0-20141024135613-dd632973f1e7/go.mod h1:dt/ZhP58zS4L8KSrWDmTeBkI65Dw0HsyUHuEVlX15mw=
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -128,7 +128,7 @@ func (r *SyncResourcesReconciler) SyncResource(ctx context.Context, request reco
_, err := lr.DynamicClient.Resource(r.GroupVersionResource).Namespace(request.Namespace).Get(ctx, request.Name, metav1.GetOptions{})
if err != nil {
if !errors.IsNotFound(err) {
klog.Errorf("Get %s from leaef cluster failed, error: %v", obj.GetKind(), err)
klog.Errorf("Get %s from leaf cluster failed, error: %v", obj.GetKind(), err)
return err
}
return nil
Expand Down
172 changes: 88 additions & 84 deletions pkg/clustertree/cluster-manager/controllers/pod/root_pod_controller.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,14 @@ package pod

import (
"context"
"encoding/base64"
"fmt"
"reflect"
"strconv"
"strings"
"time"

authenticationv1 "k8s.io/api/authentication/v1"
corev1 "k8s.io/api/core/v1"
"k8s.io/apimachinery/pkg/api/errors"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
Expand All @@ -17,6 +20,7 @@ import (
"k8s.io/apimachinery/pkg/util/wait"
"k8s.io/client-go/dynamic"
"k8s.io/klog/v2"
"k8s.io/kubernetes/pkg/serviceaccount"

Check failure on line 23 in pkg/clustertree/cluster-manager/controllers/pod/root_pod_controller.go

View workflow job for this annotation

GitHub Actions / lint

could not import k8s.io/kubernetes/pkg/serviceaccount (-: # k8s.io/kubernetes/pkg/serviceaccount

Check failure on line 23 in pkg/clustertree/cluster-manager/controllers/pod/root_pod_controller.go

View workflow job for this annotation

GitHub Actions / lint

could not import k8s.io/kubernetes/pkg/serviceaccount (-: # k8s.io/kubernetes/pkg/serviceaccount
ctrl "sigs.k8s.io/controller-runtime"
"sigs.k8s.io/controller-runtime/pkg/builder"
"sigs.k8s.io/controller-runtime/pkg/client"
Expand Down Expand Up @@ -365,63 +369,41 @@ func (r *RootPodReconciler) createSAInLeafCluster(ctx context.Context, lr *leafU
return newSA, nil
}

func (r *RootPodReconciler) createSATokenInLeafCluster(ctx context.Context, lr *leafUtils.LeafResource, saName string, ns string) (*corev1.Secret, error) {
satokenKey := types.NamespacedName{
Namespace: ns,
Name: saName,
}
sa := &corev1.ServiceAccount{}
err := r.RootClient.Get(ctx, satokenKey, sa)
func (r *RootPodReconciler) createSATokenInLeafCluster(ctx context.Context, lr *leafUtils.LeafResource, saName string, ns string, ExpirationSeconds *int64, BoundObjectReference *authenticationv1.BoundObjectReference) (*corev1.Secret, error) {
// create token
token, err := utils.CreateToken(lr.Clientset, ns, saName, ExpirationSeconds, BoundObjectReference)
if err != nil {
return nil, fmt.Errorf("could not find sa %s in master cluster: %v", saName, err)
}

var secretName string
if len(sa.Secrets) > 0 {
secretName = sa.Secrets[0].Name
}

csName := fmt.Sprintf("master-%s-token", sa.Name)
csKey := types.NamespacedName{
Namespace: ns,
Name: csName,
}
clientSecret := &corev1.Secret{}
err = lr.Client.Get(ctx, csKey, clientSecret)
if err != nil && !errors.IsNotFound(err) {
return nil, fmt.Errorf("could not check secret %s in member cluster: %v", secretName, err)
}
if err == nil {
return clientSecret, nil
}

secretKey := types.NamespacedName{
Namespace: ns,
Name: secretName,
return nil, err
}

masterSecret := &corev1.Secret{}
err = r.RootClient.Get(ctx, secretKey, masterSecret)
secretName := fmt.Sprintf("satoken-%s", BoundObjectReference.Name)
tokenByte, err := base64.StdEncoding.DecodeString(token.Status.Token)
if err != nil {
return nil, fmt.Errorf("could not find secret %s in master cluster: %v", secretName, err)
return nil, fmt.Errorf("could not decode token to byte: %v", err)
}
tokenData := map[string][]byte{
"token": tokenByte,
}

nData := map[string][]byte{}
nData["token"] = masterSecret.Data["token"]

newSE := &corev1.Secret{
saToken := &corev1.Secret{
ObjectMeta: metav1.ObjectMeta{
Name: csName,
Name: secretName,
Namespace: ns,
Annotations: map[string]string{
"ExpirationTimestamp": token.Status.ExpirationTimestamp.String(),
"BoundObjectReference": BoundObjectReference.String(),
"saName": saName,
"ExpirationSeconds": strconv.FormatInt(*ExpirationSeconds, 10),
},
},
Data: nData,
Data: tokenData,
}
err = lr.Client.Create(ctx, newSE)
err = lr.Client.Create(ctx, saToken)

if err != nil && !errors.IsAlreadyExists(err) {
return nil, fmt.Errorf("could not create sa %s in member cluster: %v", sa, err)
if err != nil {
return nil, fmt.Errorf("could not create Secret-serviceAccountToken %s in member cluster: %v", secretName, err)
}
return newSE, nil
return saToken, nil
}

func (r *RootPodReconciler) createCAInLeafCluster(ctx context.Context, lr *leafUtils.LeafResource, ns string) (*corev1.ConfigMap, error) {
Expand Down Expand Up @@ -496,57 +478,79 @@ func (r *RootPodReconciler) changeToMasterCoreDNS(ctx context.Context, pod *core
}

func (r *RootPodReconciler) convertAuth(ctx context.Context, lr *leafUtils.LeafResource, pod *corev1.Pod) {
// get ExpirationSeconds by AutomountServiceAccountToken
var ExpirationSeconds int64
if pod.Spec.AutomountServiceAccountToken == nil || *pod.Spec.AutomountServiceAccountToken {
falseValue := false
pod.Spec.AutomountServiceAccountToken = &falseValue

sa := pod.Spec.ServiceAccountName
_, err := r.createSAInLeafCluster(ctx, lr, sa, pod.Namespace)
if err != nil {
klog.Errorf("[convertAuth] create sa failed, ns: %s, pod: %s", pod.Namespace, pod.Name)
return
ExpirationSeconds = serviceaccount.WarnOnlyBoundTokenExpirationSeconds
} else {
if pod.Spec.Volumes != nil {
for _, volume := range pod.Spec.Volumes {
if volume.Projected != nil {
for _, projectedVolumeSource := range volume.Projected.Sources {
if projectedVolumeSource.ServiceAccountToken != nil {
ExpirationSeconds = *projectedVolumeSource.ServiceAccountToken.ExpirationSeconds
}
}
}
}
}
}

se, err := r.createSATokenInLeafCluster(ctx, lr, sa, pod.Namespace)
if err != nil {
klog.Errorf("[convertAuth] create sa secret failed, ns: %s, pod: %s", pod.Namespace, pod.Name)
return
}
sa := pod.Spec.ServiceAccountName
_, err := r.createSAInLeafCluster(ctx, lr, sa, pod.Namespace)
if err != nil {
klog.Errorf("[convertAuth] create sa failed, ns: %s, pod: %s", pod.Namespace, pod.Name)
return
}

rootCA, err := r.createCAInLeafCluster(ctx, lr, pod.Namespace)
if err != nil {
klog.Errorf("[convertAuth] create sa secret failed, ns: %s, pod: %s", pod.Namespace, pod.Name)
return
}
// bind the token to the pod parameter
BoundObjectReference := &authenticationv1.BoundObjectReference{
APIVersion: pod.APIVersion,
Kind: pod.Kind,
Name: pod.Name,
UID: pod.UID,
}
se, err := r.createSATokenInLeafCluster(ctx, lr, sa, pod.Namespace, &ExpirationSeconds, BoundObjectReference)
if err != nil {
klog.Errorf("[convertAuth] create secret-saToken failed, ns: %s, pod: %s", pod.Namespace, pod.Name)
return
}

volumes := pod.Spec.Volumes
for _, v := range volumes {
if strings.HasPrefix(v.Name, utils.SATokenPrefix) {
sources := []corev1.VolumeProjection{}
for _, src := range v.Projected.Sources {
if src.ServiceAccountToken != nil {
continue
}
if src.ConfigMap != nil && src.ConfigMap.Name == utils.RooTCAConfigMapName {
src.ConfigMap.Name = rootCA.Name
}
sources = append(sources, src)
rootCA, err := r.createCAInLeafCluster(ctx, lr, pod.Namespace)
if err != nil {
klog.Errorf("[convertAuth] create sa secret failed, ns: %s, pod: %s", pod.Namespace, pod.Name)
return
}

volumes := pod.Spec.Volumes
for _, v := range volumes {
if strings.HasPrefix(v.Name, utils.SATokenPrefix) {
sources := []corev1.VolumeProjection{}
for _, src := range v.Projected.Sources {
if src.ServiceAccountToken != nil {
continue
}
if src.ConfigMap != nil && src.ConfigMap.Name == utils.RooTCAConfigMapName {
src.ConfigMap.Name = rootCA.Name
}
sources = append(sources, src)
}

secretProjection := corev1.VolumeProjection{
Secret: &corev1.SecretProjection{
Items: []corev1.KeyToPath{
{
Key: "token",
Path: "token",
},
secretProjection := corev1.VolumeProjection{
Secret: &corev1.SecretProjection{
Items: []corev1.KeyToPath{
{
Key: "token",
Path: "token",
},
},
}
secretProjection.Secret.Name = se.Name
sources = append(sources, secretProjection)
v.Projected.Sources = sources
},
}
secretProjection.Secret.Name = se.Name
sources = append(sources, secretProjection)
v.Projected.Sources = sources
}
}
}
Expand Down
21 changes: 21 additions & 0 deletions pkg/utils/utils.go
Original file line number Diff line number Diff line change
@@ -1,7 +1,13 @@
package utils

import (
"context"
"fmt"
"strings"

authenticationv1 "k8s.io/api/authentication/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/client-go/kubernetes"
)

func ContainsString(arr []string, s string) bool {
Expand All @@ -25,3 +31,18 @@ func IsIPv6(s string) bool {
}
return false
}

func CreateToken(clientset kubernetes.Interface, namespaceName string, serviceAccountName string, ExpirationSeconds *int64, BoundObjectReference *authenticationv1.BoundObjectReference) (*authenticationv1.TokenRequest, error) {
tokenRequest, err := clientset.CoreV1().ServiceAccounts(namespaceName).CreateToken(context.TODO(), serviceAccountName, &authenticationv1.TokenRequest{
Spec: authenticationv1.TokenRequestSpec{
Audiences: []string{"https://kubernetes.default.svc.cluster.local"},
ExpirationSeconds: ExpirationSeconds,
BoundObjectRef: BoundObjectReference,
},
}, metav1.CreateOptions{})
if err != nil {
return nil, fmt.Errorf("could not create token by serviceAccountName %s in Namespace %s: %v", serviceAccountName, namespaceName, err)
}
return tokenRequest, nil

Check failure on line 47 in pkg/utils/utils.go

View workflow job for this annotation

GitHub Actions / lint

unnecessary trailing newline (whitespace)

Check failure on line 47 in pkg/utils/utils.go

View workflow job for this annotation

GitHub Actions / lint

unnecessary trailing newline (whitespace)
}
71 changes: 71 additions & 0 deletions vendor/golang.org/x/crypto/ed25519/ed25519.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading

0 comments on commit 5299f53

Please sign in to comment.