@@ -27,14 +27,17 @@ import (
27
27
"github.com/kcp-dev/logicalcluster/v3"
28
28
29
29
"k8s.io/apimachinery/pkg/labels"
30
+ "k8s.io/apiserver/pkg/authentication/serviceaccount"
30
31
"k8s.io/apiserver/pkg/authorization/authorizer"
31
32
genericapirequest "k8s.io/apiserver/pkg/endpoints/request"
32
33
genericapiserver "k8s.io/apiserver/pkg/server"
34
+ "k8s.io/client-go/rest"
33
35
"k8s.io/client-go/tools/cache"
34
36
"k8s.io/klog/v2"
35
37
36
38
apisv1alpha1 "github.com/kcp-dev/kcp/pkg/apis/apis/v1alpha1"
37
39
"github.com/kcp-dev/kcp/pkg/authorization"
40
+ "github.com/kcp-dev/kcp/pkg/authorization/bootstrap"
38
41
kcpclientset "github.com/kcp-dev/kcp/pkg/client/clientset/versioned/cluster"
39
42
kcpinformers "github.com/kcp-dev/kcp/pkg/client/informers/externalversions"
40
43
virtualapiexportauth "github.com/kcp-dev/kcp/pkg/virtual/apiexport/authorizer"
@@ -53,8 +56,8 @@ const VirtualWorkspaceName string = "apiexport"
53
56
54
57
func BuildVirtualWorkspace (
55
58
rootPathPrefix string ,
59
+ cfg * rest.Config ,
56
60
kubeClusterClient , deepSARClient kcpkubernetesclientset.ClusterInterface ,
57
- dynamicClusterClient kcpdynamic.ClusterInterface ,
58
61
kcpClusterClient kcpclientset.ClusterInterface ,
59
62
cachedKcpInformers kcpinformers.SharedInformerFactory ,
60
63
) ([]rootapiserver.NamedVirtualWorkspace , error ) {
@@ -86,6 +89,37 @@ func BuildVirtualWorkspace(
86
89
}),
87
90
88
91
BootstrapAPISetManagement : func (mainConfig genericapiserver.CompletedConfig ) (apidefinition.APIDefinitionSetGetter , error ) {
92
+ dynamicClient , err := kcpdynamic .NewForConfig (cfg )
93
+ if err != nil {
94
+ return nil , fmt .Errorf ("error creating privileged dynamic kcp client: %w" , err )
95
+ }
96
+
97
+ impersonatedDynamicClientGetter := func (ctx context.Context ) (kcpdynamic.ClusterInterface , error ) {
98
+ cluster , err := genericapirequest .ValidClusterFrom (ctx )
99
+ if err != nil {
100
+ return nil , fmt .Errorf ("error getting valid cluster from context: %w" , err )
101
+ }
102
+
103
+ // Wildcard requests cannot be impersonated against a concrete cluster.
104
+ if cluster .Wildcard {
105
+ return dynamicClient , nil
106
+ }
107
+
108
+ impersonationConfig := rest .CopyConfig (cfg )
109
+ impersonationConfig .Impersonate = rest.ImpersonationConfig {
110
+ UserName : "system:serviceaccount:default:rest" ,
111
+ Groups : []string {bootstrap .SystemKcpAdminGroup },
112
+ Extra : map [string ][]string {
113
+ serviceaccount .ClusterNameKey : {cluster .Name .Path ().String ()},
114
+ },
115
+ }
116
+ impersonatedClient , err := kcpdynamic .NewForConfig (impersonationConfig )
117
+ if err != nil {
118
+ return nil , fmt .Errorf ("error generating dynamic client: %w" , err )
119
+ }
120
+ return impersonatedClient , nil
121
+ }
122
+
89
123
apiReconciler , err := apireconciler .NewAPIReconciler (
90
124
kcpClusterClient ,
91
125
cachedKcpInformers .Apis ().V1alpha1 ().APIResourceSchemas (),
@@ -100,7 +134,7 @@ func BuildVirtualWorkspace(
100
134
})
101
135
}
102
136
103
- storageBuilder := provideDelegatingRestStorage (ctx , dynamicClusterClient , identityHash , wrapper )
137
+ storageBuilder := provideDelegatingRestStorage (ctx , impersonatedDynamicClientGetter , identityHash , wrapper )
104
138
def , err := apiserver .CreateServingInfoFor (mainConfig , apiResourceSchema , version , storageBuilder )
105
139
if err != nil {
106
140
cancelFn ()
@@ -112,7 +146,7 @@ func BuildVirtualWorkspace(
112
146
}, nil
113
147
},
114
148
func (ctx context.Context , clusterName logicalcluster.Name , apiExportName string ) (apidefinition.APIDefinition , error ) {
115
- restProvider , err := provideAPIExportFilteredRestStorage (ctx , dynamicClusterClient , clusterName , apiExportName )
149
+ restProvider , err := provideAPIExportFilteredRestStorage (ctx , impersonatedDynamicClientGetter , clusterName , apiExportName )
116
150
if err != nil {
117
151
return nil , err
118
152
}
0 commit comments