diff --git a/pkg/controller/garbagecollector/operations.go b/pkg/controller/garbagecollector/operations.go index f2ac007cc12..f1cc538e1e4 100644 --- a/pkg/controller/garbagecollector/operations.go +++ b/pkg/controller/garbagecollector/operations.go @@ -48,7 +48,7 @@ func (gc *GarbageCollector) apiResource(apiVersion, kind string) (*metav1.APIRes } glog.V(5).Infof("map kind %s, version %s to resource %s", kind, apiVersion, mapping.Resource) resource := metav1.APIResource{ - Name: mapping.Resource, + Name: mapping.Resource.Resource, Namespaced: mapping.Scope == meta.RESTScopeNamespace, Kind: kind, } diff --git a/pkg/controller/podautoscaler/horizontal.go b/pkg/controller/podautoscaler/horizontal.go index c6593c352a6..2ca40458d62 100644 --- a/pkg/controller/podautoscaler/horizontal.go +++ b/pkg/controller/podautoscaler/horizontal.go @@ -620,7 +620,7 @@ func (a *HorizontalController) shouldScale(hpa *autoscalingv2.HorizontalPodAutos func (a *HorizontalController) scaleForResourceMappings(namespace, name string, mappings []*apimeta.RESTMapping) (*autoscalingv1.Scale, schema.GroupResource, error) { var firstErr error for i, mapping := range mappings { - targetGR := mapping.GroupVersionKind.GroupVersion().WithResource(mapping.Resource).GroupResource() + targetGR := mapping.Resource.GroupResource() scale, err := a.scaleNamespacer.Scales(namespace).Get(targetGR, name) if err == nil { return scale, targetGR, nil diff --git a/pkg/controller/podautoscaler/horizontal_test.go b/pkg/controller/podautoscaler/horizontal_test.go index 95511e79cca..9beca7a446f 100644 --- a/pkg/controller/podautoscaler/horizontal_test.go +++ b/pkg/controller/podautoscaler/horizontal_test.go @@ -523,7 +523,7 @@ func (tc *testCase) prepareTestClient(t *testing.T) (*fake.Clientset, *metricsfa t.Logf("unable to get mapping for %s: %v", gk.String(), err) continue } - groupResource := schema.GroupResource{Group: mapping.GroupVersionKind.Group, Resource: mapping.Resource} + groupResource := mapping.Resource.GroupResource() if getForAction.GetResource().Resource == groupResource.String() { matchedTarget = &tc.metricsTarget[i] diff --git a/pkg/controller/podautoscaler/metrics/rest_metrics_client_test.go b/pkg/controller/podautoscaler/metrics/rest_metrics_client_test.go index 7275a752f0e..81ef554e706 100644 --- a/pkg/controller/podautoscaler/metrics/rest_metrics_client_test.go +++ b/pkg/controller/podautoscaler/metrics/rest_metrics_client_test.go @@ -161,7 +161,7 @@ func (tc *restClientTestCase) prepareTestClient(t *testing.T) (*metricsfake.Clie if err != nil { return true, nil, fmt.Errorf("unable to get mapping for %s: %v", gk.String(), err) } - groupResource := schema.GroupResource{Group: mapping.GroupVersionKind.Group, Resource: mapping.Resource} + groupResource := mapping.Resource.GroupResource() assert.Equal(t, groupResource.String(), getForAction.GetResource().Resource, "should have requested metrics for the resource matching the GroupKind passed in") assert.Equal(t, tc.singleObject.Name, name, "should have requested metrics for the object matching the name passed in") diff --git a/pkg/controller/podautoscaler/replica_calculator_test.go b/pkg/controller/podautoscaler/replica_calculator_test.go index 448d8100b8f..3739c085b41 100644 --- a/pkg/controller/podautoscaler/replica_calculator_test.go +++ b/pkg/controller/podautoscaler/replica_calculator_test.go @@ -230,7 +230,7 @@ func (tc *replicaCalcTestCase) prepareTestClient(t *testing.T) (*fake.Clientset, if err != nil { return true, nil, fmt.Errorf("unable to get mapping for %s: %v", gk.String(), err) } - groupResource := schema.GroupResource{Group: mapping.GroupVersionKind.Group, Resource: mapping.Resource} + groupResource := mapping.Resource.GroupResource() assert.Equal(t, groupResource.String(), getForAction.GetResource().Resource, "should have requested metrics for the resource matching the GroupKind passed in") assert.Equal(t, tc.metric.singleObject.Name, name, "should have requested metrics for the object matching the name passed in") diff --git a/pkg/kubectl/cmd/drain.go b/pkg/kubectl/cmd/drain.go index db4ae94ef64..8ae562744de 100644 --- a/pkg/kubectl/cmd/drain.go +++ b/pkg/kubectl/cmd/drain.go @@ -42,6 +42,7 @@ import ( restclient "k8s.io/client-go/rest" "k8s.io/kubernetes/pkg/kubectl/genericclioptions" + "k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/kubernetes/pkg/api/legacyscheme" "k8s.io/kubernetes/pkg/kubectl" "k8s.io/kubernetes/pkg/kubectl/cmd/templates" @@ -302,7 +303,7 @@ func (o *DrainOptions) Complete(f cmdutil.Factory, cmd *cobra.Command, args []st if err != nil { return err } - if info.Mapping.Resource != "nodes" { + if info.Mapping.Resource.GroupResource() != (schema.GroupResource{Group: "", Resource: "nodes"}) { return fmt.Errorf("error: expected resource of type node, got %q", info.Mapping.Resource) } diff --git a/pkg/kubectl/cmd/rollout/rollout_history.go b/pkg/kubectl/cmd/rollout/rollout_history.go index 6ca6e0855ce..a454acecba1 100644 --- a/pkg/kubectl/cmd/rollout/rollout_history.go +++ b/pkg/kubectl/cmd/rollout/rollout_history.go @@ -109,7 +109,7 @@ func RunHistory(f cmdutil.Factory, cmd *cobra.Command, out io.Writer, args []str return err } - header := fmt.Sprintf("%s %q", mapping.Resource, info.Name) + header := fmt.Sprintf("%s %q", mapping.Resource.Resource, info.Name) if revision > 0 { header = fmt.Sprintf("%s with revision #%d", header, revision) } diff --git a/pkg/kubectl/cmd/rollout/rollout_pause.go b/pkg/kubectl/cmd/rollout/rollout_pause.go index fddf3c8cf47..1640dda4d71 100644 --- a/pkg/kubectl/cmd/rollout/rollout_pause.go +++ b/pkg/kubectl/cmd/rollout/rollout_pause.go @@ -146,7 +146,11 @@ func (o PauseConfig) RunPause() error { for _, patch := range set.CalculatePatches(o.Infos, cmdutil.InternalVersionJSONEncoder(), o.Pauser) { info := patch.Info if patch.Err != nil { - allErrs = append(allErrs, fmt.Errorf("error: %s %q %v", info.Mapping.Resource, info.Name, patch.Err)) + resourceString := info.Mapping.Resource.Resource + if len(info.Mapping.Resource.Group) > 0 { + resourceString = resourceString + "." + info.Mapping.Resource.Group + } + allErrs = append(allErrs, fmt.Errorf("error: %s %q %v", resourceString, info.Name, patch.Err)) continue } diff --git a/pkg/kubectl/cmd/rollout/rollout_resume.go b/pkg/kubectl/cmd/rollout/rollout_resume.go index ac0c19caead..d4b79e023e5 100644 --- a/pkg/kubectl/cmd/rollout/rollout_resume.go +++ b/pkg/kubectl/cmd/rollout/rollout_resume.go @@ -151,7 +151,11 @@ func (o ResumeConfig) RunResume() error { info := patch.Info if patch.Err != nil { - allErrs = append(allErrs, fmt.Errorf("error: %s %q %v", info.Mapping.Resource, info.Name, patch.Err)) + resourceString := info.Mapping.Resource.Resource + if len(info.Mapping.Resource.Group) > 0 { + resourceString = resourceString + "." + info.Mapping.Resource.Group + } + allErrs = append(allErrs, fmt.Errorf("error: %s %q %v", resourceString, info.Name, patch.Err)) continue } diff --git a/pkg/kubectl/cmd/run.go b/pkg/kubectl/cmd/run.go index a56674dd0ce..1285974fb82 100644 --- a/pkg/kubectl/cmd/run.go +++ b/pkg/kubectl/cmd/run.go @@ -461,7 +461,7 @@ func (o *RunOptions) removeCreatedObjects(f cmdutil.Factory, createdObjects []*R Internal(legacyscheme.Scheme). ContinueOnError(). NamespaceParam(namespace).DefaultNamespace(). - ResourceNames(obj.Mapping.Resource, name). + ResourceNames(obj.Mapping.Resource.Resource+"."+obj.Mapping.Resource.Group, name). Flatten(). Do() // Note: we pass in "true" for the "quiet" parameter because diff --git a/pkg/kubectl/cmd/scale.go b/pkg/kubectl/cmd/scale.go index ee14967199d..b1e710cd240 100644 --- a/pkg/kubectl/cmd/scale.go +++ b/pkg/kubectl/cmd/scale.go @@ -24,6 +24,7 @@ import ( "github.com/spf13/cobra" "k8s.io/apimachinery/pkg/api/meta" + "k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/apimachinery/pkg/types" "k8s.io/kubernetes/pkg/client/clientset_generated/internalclientset" batchclient "k8s.io/kubernetes/pkg/client/clientset_generated/internalclientset/typed/batch/internalversion" @@ -225,7 +226,7 @@ func (o *ScaleOptions) RunScale() error { } mapping := info.ResourceMapping() - if mapping.Resource == "jobs" { + if mapping.Resource.GroupResource() == (schema.GroupResource{Group: "batch", Resource: "jobs"}) { // go down the legacy jobs path. This can be removed in 3.14 For now, contain it. fmt.Fprintf(o.ErrOut, "%s scale job is DEPRECATED and will be removed in a future version.\n", o.parent) @@ -234,8 +235,7 @@ func (o *ScaleOptions) RunScale() error { } } else { - gvk := mapping.GroupVersionKind.GroupVersion().WithResource(mapping.Resource) - if err := o.scaler.Scale(info.Namespace, info.Name, uint(o.Replicas), precondition, retry, waitForReplicas, gvk.GroupResource()); err != nil { + if err := o.scaler.Scale(info.Namespace, info.Name, uint(o.Replicas), precondition, retry, waitForReplicas, mapping.Resource.GroupResource()); err != nil { return err } } diff --git a/pkg/kubectl/cmd/util/editor/editoptions.go b/pkg/kubectl/cmd/util/editor/editoptions.go index 324670dda44..93c7f6f031b 100644 --- a/pkg/kubectl/cmd/util/editor/editoptions.go +++ b/pkg/kubectl/cmd/util/editor/editoptions.go @@ -738,11 +738,16 @@ type editResults struct { } func (r *editResults) addError(err error, info *resource.Info) string { + resourceString := info.Mapping.Resource.Resource + if len(info.Mapping.Resource.Group) > 0 { + resourceString = resourceString + "." + info.Mapping.Resource.Group + } + switch { case apierrors.IsInvalid(err): r.edit = append(r.edit, info) reason := editReason{ - head: fmt.Sprintf("%s %q was not valid", info.Mapping.Resource, info.Name), + head: fmt.Sprintf("%s %q was not valid", resourceString, info.Name), } if err, ok := err.(apierrors.APIStatus); ok { if details := err.Status().Details; details != nil { @@ -752,13 +757,13 @@ func (r *editResults) addError(err error, info *resource.Info) string { } } r.header.reasons = append(r.header.reasons, reason) - return fmt.Sprintf("error: %s %q is invalid", info.Mapping.Resource, info.Name) + return fmt.Sprintf("error: %s %q is invalid", resourceString, info.Name) case apierrors.IsNotFound(err): r.notfound++ - return fmt.Sprintf("error: %s %q could not be found on the server", info.Mapping.Resource, info.Name) + return fmt.Sprintf("error: %s %q could not be found on the server", resourceString, info.Name) default: r.retryable++ - return fmt.Sprintf("error: %s %q could not be patched: %v", info.Mapping.Resource, info.Name, err) + return fmt.Sprintf("error: %s %q could not be patched: %v", resourceString, info.Name, err) } } diff --git a/pkg/kubectl/cmd/util/helpers.go b/pkg/kubectl/cmd/util/helpers.go index 6cdec3b3be2..cd8d88d5461 100644 --- a/pkg/kubectl/cmd/util/helpers.go +++ b/pkg/kubectl/cmd/util/helpers.go @@ -576,31 +576,6 @@ func ParsePairs(pairArgs []string, pairType string, supportRemove bool) (newPair return } -// MustPrintWithKinds determines if printer is dealing -// with multiple resource kinds, in which case it will -// return true, indicating resource kind will be -// included as part of printer output -func MustPrintWithKinds(objs []runtime.Object, infos []*resource.Info, sorter *kubectl.RuntimeSort) bool { - var lastMap *meta.RESTMapping - - for ix := range objs { - var mapping *meta.RESTMapping - if sorter != nil { - mapping = infos[sorter.OriginalPosition(ix)].Mapping - } else { - mapping = infos[ix].Mapping - } - - // display "kind" only if we have mixed resources - if lastMap != nil && mapping.Resource != lastMap.Resource { - return true - } - lastMap = mapping - } - - return false -} - // IsSiblingCommandExists receives a pointer to a cobra command and a target string. // Returns true if the target string is found in the list of sibling commands. func IsSiblingCommandExists(cmd *cobra.Command, targetCmdName string) bool { diff --git a/pkg/kubectl/resource/builder.go b/pkg/kubectl/resource/builder.go index 299d9eb199b..bdbbf9fc35d 100644 --- a/pkg/kubectl/resource/builder.go +++ b/pkg/kubectl/resource/builder.go @@ -697,7 +697,7 @@ func (b *Builder) resourceMappings() ([]*meta.RESTMapping, error) { func (b *Builder) resourceTupleMappings() (map[string]*meta.RESTMapping, error) { mappings := make(map[string]*meta.RESTMapping) - canonical := make(map[string]struct{}) + canonical := make(map[schema.GroupVersionResource]struct{}) for _, r := range b.resourceTuples { if _, ok := mappings[r.Resource]; ok { continue @@ -707,7 +707,6 @@ func (b *Builder) resourceTupleMappings() (map[string]*meta.RESTMapping, error) return nil, err } - mappings[mapping.Resource] = mapping mappings[r.Resource] = mapping canonical[mapping.Resource] = struct{}{} } @@ -829,7 +828,7 @@ func (b *Builder) visitByResource() *Result { } clients := make(map[string]RESTClient) for _, mapping := range mappings { - s := fmt.Sprintf("%s/%s", mapping.GroupVersionKind.GroupVersion().String(), mapping.Resource) + s := fmt.Sprintf("%s/%s", mapping.GroupVersionKind.GroupVersion().String(), mapping.Resource.Resource) if _, ok := clients[s]; ok { continue } @@ -848,7 +847,7 @@ func (b *Builder) visitByResource() *Result { if !ok { return result.withError(fmt.Errorf("resource %q is not recognized: %v", tuple.Resource, mappings)) } - s := fmt.Sprintf("%s/%s", mapping.GroupVersionKind.GroupVersion().String(), mapping.Resource) + s := fmt.Sprintf("%s/%s", mapping.GroupVersionKind.GroupVersion().String(), mapping.Resource.Resource) client, ok := clients[s] if !ok { return result.withError(fmt.Errorf("could not find a client for resource %q", tuple.Resource)) diff --git a/pkg/kubectl/resource/builder_test.go b/pkg/kubectl/resource/builder_test.go index c40ae4eebba..3a3e57f1e85 100644 --- a/pkg/kubectl/resource/builder_test.go +++ b/pkg/kubectl/resource/builder_test.go @@ -594,7 +594,7 @@ func TestResourceByName(t *testing.T) { if err != nil { t.Fatalf("unexpected error: %v", err) } - if mapping.Resource != "pods" { + if mapping.Resource != (schema.GroupVersionResource{Group: "", Version: "v1", Resource: "pods"}) { t.Errorf("unexpected resource mapping: %#v", mapping) } } @@ -726,7 +726,7 @@ func TestResourceByNameWithoutRequireObject(t *testing.T) { if err != nil { t.Fatalf("unexpected error: %v", err) } - if mapping.GroupVersionKind.Kind != "Pod" || mapping.Resource != "pods" { + if mapping.GroupVersionKind.Kind != "Pod" || mapping.Resource != (schema.GroupVersionResource{Group: "", Version: "v1", Resource: "pods"}) { t.Errorf("unexpected resource mapping: %#v", mapping) } } @@ -753,7 +753,7 @@ func TestResourceByNameAndEmptySelector(t *testing.T) { if err != nil { t.Fatalf("unexpected error: %v", err) } - if mapping.Resource != "pods" { + if mapping.Resource != (schema.GroupVersionResource{Group: "", Version: "v1", Resource: "pods"}) { t.Errorf("unexpected resource mapping: %#v", mapping) } } @@ -1124,7 +1124,7 @@ func TestListObject(t *testing.T) { if err != nil { t.Fatalf("unexpected error: %v", err) } - if mapping.Resource != "pods" { + if mapping.Resource != (schema.GroupVersionResource{Group: "", Version: "v1", Resource: "pods"}) { t.Errorf("unexpected resource mapping: %#v", mapping) } } diff --git a/pkg/kubectl/resource/helper.go b/pkg/kubectl/resource/helper.go index a7bccc65b94..97f26fa415c 100644 --- a/pkg/kubectl/resource/helper.go +++ b/pkg/kubectl/resource/helper.go @@ -43,7 +43,7 @@ type Helper struct { // NewHelper creates a Helper from a ResourceMapping func NewHelper(client RESTClient, mapping *meta.RESTMapping) *Helper { return &Helper{ - Resource: mapping.Resource, + Resource: mapping.Resource.Resource, RESTClient: client, NamespaceScoped: mapping.Scope.Name() == meta.RESTScopeNameNamespace, } diff --git a/pkg/kubectl/resource/result.go b/pkg/kubectl/resource/result.go index 611471ca7c7..57f66e125d1 100644 --- a/pkg/kubectl/resource/result.go +++ b/pkg/kubectl/resource/result.go @@ -24,6 +24,7 @@ import ( "k8s.io/apimachinery/pkg/api/meta" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" + "k8s.io/apimachinery/pkg/runtime/schema" utilerrors "k8s.io/apimachinery/pkg/util/errors" "k8s.io/apimachinery/pkg/util/sets" "k8s.io/apimachinery/pkg/watch" @@ -196,7 +197,7 @@ func (r *Result) ResourceMapping() (*meta.RESTMapping, error) { if r.err != nil { return nil, r.err } - mappings := map[string]*meta.RESTMapping{} + mappings := map[schema.GroupVersionResource]*meta.RESTMapping{} for i := range r.sources { m, ok := r.sources[i].(ResourceMapping) if !ok { diff --git a/pkg/kubectl/resource/visitor.go b/pkg/kubectl/resource/visitor.go index 95b6bbbe0a6..65e020b2357 100644 --- a/pkg/kubectl/resource/visitor.go +++ b/pkg/kubectl/resource/visitor.go @@ -158,7 +158,7 @@ func (i *Info) Refresh(obj runtime.Object, ignoreError bool) error { func (i *Info) String() string { basicInfo := fmt.Sprintf("Name: %q, Namespace: %q\nObject: %+q", i.Name, i.Namespace, i.Object) if i.Mapping != nil { - mappingInfo := fmt.Sprintf("Resource: %q, GroupVersionKind: %q", i.Mapping.Resource, + mappingInfo := fmt.Sprintf("Resource: %q, GroupVersionKind: %q", i.Mapping.Resource.String(), i.Mapping.GroupVersionKind.String()) return fmt.Sprint(mappingInfo, "\n", basicInfo) } diff --git a/pkg/printers/internalversion/describe.go b/pkg/printers/internalversion/describe.go index 24d33c83cd5..0bc468cc77a 100644 --- a/pkg/printers/internalversion/describe.go +++ b/pkg/printers/internalversion/describe.go @@ -204,7 +204,7 @@ type genericDescriber struct { func (g *genericDescriber) Describe(namespace, name string, describerSettings printers.DescriberSettings) (output string, err error) { apiResource := &metav1.APIResource{ - Name: g.mapping.Resource, + Name: g.mapping.Resource.Resource, Namespaced: g.mapping.Scope.Name() == meta.RESTScopeNameNamespace, Kind: g.mapping.GroupVersionKind.Kind, } diff --git a/plugin/pkg/admission/gc/gc_admission.go b/plugin/pkg/admission/gc/gc_admission.go index ac8af441703..303adc2c180 100644 --- a/plugin/pkg/admission/gc/gc_admission.go +++ b/plugin/pkg/admission/gc/gc_admission.go @@ -186,9 +186,9 @@ func (a *gcPermissionsEnforcement) ownerRefToDeleteAttributeRecords(ref metav1.O Verb: "update", // ownerReference can only refer to an object in the same namespace, so attributes.GetNamespace() equals to the owner's namespace Namespace: attributes.GetNamespace(), - APIGroup: groupVersion.Group, - APIVersion: groupVersion.Version, - Resource: mapping.Resource, + APIGroup: mapping.Resource.Group, + APIVersion: mapping.Resource.Version, + Resource: mapping.Resource.Resource, Subresource: "finalizers", Name: ref.Name, ResourceRequest: true, diff --git a/staging/src/k8s.io/apimachinery/pkg/api/meta/interfaces.go b/staging/src/k8s.io/apimachinery/pkg/api/meta/interfaces.go index 88280a3f4fb..42eac3af001 100644 --- a/staging/src/k8s.io/apimachinery/pkg/api/meta/interfaces.go +++ b/staging/src/k8s.io/apimachinery/pkg/api/meta/interfaces.go @@ -91,9 +91,10 @@ type RESTScope interface { // RESTMapping contains the information needed to deal with objects of a specific // resource and kind in a RESTful manner. type RESTMapping struct { - // Resource is a string representing the name of this resource as a REST client would see it - Resource string + // Resource is the GroupVersionResource (location) for this endpoint + Resource schema.GroupVersionResource + // GroupVersionKind is the GroupVersionKind (data format) to submit to this endpoint GroupVersionKind schema.GroupVersionKind // Scope contains the information needed to deal with REST Resources that are in a resource hierarchy diff --git a/staging/src/k8s.io/apimachinery/pkg/api/meta/restmapper.go b/staging/src/k8s.io/apimachinery/pkg/api/meta/restmapper.go index 027b0f4481a..41b60d7319e 100644 --- a/staging/src/k8s.io/apimachinery/pkg/api/meta/restmapper.go +++ b/staging/src/k8s.io/apimachinery/pkg/api/meta/restmapper.go @@ -505,7 +505,7 @@ func (m *DefaultRESTMapper) RESTMappings(gk schema.GroupKind, versions ...string } mappings = append(mappings, &RESTMapping{ - Resource: res.Resource, + Resource: res, GroupVersionKind: gvk, Scope: scope, }) diff --git a/staging/src/k8s.io/apimachinery/pkg/api/meta/restmapper_test.go b/staging/src/k8s.io/apimachinery/pkg/api/meta/restmapper_test.go index 47276ed6e8f..66ccb317daf 100644 --- a/staging/src/k8s.io/apimachinery/pkg/api/meta/restmapper_test.go +++ b/staging/src/k8s.io/apimachinery/pkg/api/meta/restmapper_test.go @@ -527,7 +527,7 @@ func TestRESTMapperRESTMapping(t *testing.T) { APIGroupVersions []schema.GroupVersion DefaultVersions []schema.GroupVersion - Resource string + Resource schema.GroupVersionResource ExpectedGroupVersion *schema.GroupVersion Err bool }{ @@ -536,14 +536,14 @@ func TestRESTMapperRESTMapping(t *testing.T) { {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "Unknown", Err: true}, - {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "test"}}, Resource: "internalobjects"}, - {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "test"}}, Resource: "internalobjects"}, + {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "test"}}, Resource: testGroupVersion.WithResource("internalobjects")}, + {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "test"}}, Resource: testGroupVersion.WithResource("internalobjects")}, - {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "test"}}, Resource: "internalobjects"}, + {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "test"}}, Resource: testGroupVersion.WithResource("internalobjects")}, - {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{}, Resource: "internalobjects", ExpectedGroupVersion: &schema.GroupVersion{Group: testGroup, Version: "test"}}, + {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{}, Resource: internalGroupVersion.WithResource("internalobjects"), ExpectedGroupVersion: &schema.GroupVersion{Group: testGroup, Version: "test"}}, - {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "test"}}, Resource: "internalobjects"}, + {DefaultVersions: []schema.GroupVersion{testGroupVersion}, Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "test"}}, Resource: testGroupVersion.WithResource("internalobjects")}, // TODO: add test for a resource that exists in one version but not another } @@ -596,7 +596,7 @@ func TestRESTMapperRESTMappingSelectsVersion(t *testing.T) { if err != nil { t.Fatalf("unexpected error: %v", err) } - if mapping.Resource != "otherobjects" || mapping.GroupVersionKind.GroupVersion() != expectedGroupVersion2 { + if mapping.Resource != expectedGroupVersion2.WithResource("otherobjects") || mapping.GroupVersionKind.GroupVersion() != expectedGroupVersion2 { t.Errorf("unexpected mapping: %#v", mapping) } @@ -604,7 +604,7 @@ func TestRESTMapperRESTMappingSelectsVersion(t *testing.T) { if err != nil { t.Fatalf("unexpected error: %v", err) } - if mapping.Resource != "internalobjects" || mapping.GroupVersionKind.GroupVersion() != expectedGroupVersion1 { + if mapping.Resource != expectedGroupVersion1.WithResource("internalobjects") || mapping.GroupVersionKind.GroupVersion() != expectedGroupVersion1 { t.Errorf("unexpected mapping: %#v", mapping) } @@ -634,7 +634,7 @@ func TestRESTMapperRESTMappingSelectsVersion(t *testing.T) { if err != nil { t.Fatalf("unexpected error: %v", err) } - if mapping.Resource != "otherobjects" || mapping.GroupVersionKind.GroupVersion() != expectedGroupVersion2 { + if mapping.Resource != expectedGroupVersion2.WithResource("otherobjects") || mapping.GroupVersionKind.GroupVersion() != expectedGroupVersion2 { t.Errorf("unexpected mapping: %#v", mapping) } } @@ -666,7 +666,7 @@ func TestRESTMapperRESTMappings(t *testing.T) { Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "v2"}}, AddGroupVersionKind: []schema.GroupVersionKind{schema.GroupVersion{Group: testGroup, Version: "v2"}.WithKind("InternalObject")}, - ExpectedRESTMappings: []*RESTMapping{{Resource: "internalobjects", GroupVersionKind: schema.GroupVersionKind{Group: testGroup, Version: "v2", Kind: "InternalObject"}}}, + ExpectedRESTMappings: []*RESTMapping{{Resource: schema.GroupVersionResource{Group: testGroup, Version: "v2", Resource: "internalobjects"}, GroupVersionKind: schema.GroupVersionKind{Group: testGroup, Version: "v2", Kind: "InternalObject"}}}, }, // ask for specific versions - only one available - check ExpectedRESTMappings @@ -675,15 +675,24 @@ func TestRESTMapperRESTMappings(t *testing.T) { Kind: "InternalObject", APIGroupVersions: []schema.GroupVersion{{Group: testGroup, Version: "v3"}, {Group: testGroup, Version: "v2"}}, AddGroupVersionKind: []schema.GroupVersionKind{schema.GroupVersion{Group: testGroup, Version: "v2"}.WithKind("InternalObject")}, - ExpectedRESTMappings: []*RESTMapping{{Resource: "internalobjects", GroupVersionKind: schema.GroupVersionKind{Group: testGroup, Version: "v2", Kind: "InternalObject"}}}, + ExpectedRESTMappings: []*RESTMapping{{Resource: schema.GroupVersionResource{Group: testGroup, Version: "v2", Resource: "internalobjects"}, GroupVersionKind: schema.GroupVersionKind{Group: testGroup, Version: "v2", Kind: "InternalObject"}}}, }, // do not ask for specific version - search through default versions - check ExpectedRESTMappings { - DefaultVersions: []schema.GroupVersion{testGroupVersion, {Group: testGroup, Version: "v2"}}, - Kind: "InternalObject", - AddGroupVersionKind: []schema.GroupVersionKind{schema.GroupVersion{Group: testGroup, Version: "v1"}.WithKind("InternalObject"), schema.GroupVersion{Group: testGroup, Version: "v2"}.WithKind("InternalObject")}, - ExpectedRESTMappings: []*RESTMapping{{Resource: "internalobjects", GroupVersionKind: schema.GroupVersionKind{Group: testGroup, Version: "v1", Kind: "InternalObject"}}, {Resource: "internalobjects", GroupVersionKind: schema.GroupVersionKind{Group: testGroup, Version: "v2", Kind: "InternalObject"}}}, + DefaultVersions: []schema.GroupVersion{testGroupVersion, {Group: testGroup, Version: "v2"}}, + Kind: "InternalObject", + AddGroupVersionKind: []schema.GroupVersionKind{schema.GroupVersion{Group: testGroup, Version: "v1"}.WithKind("InternalObject"), schema.GroupVersion{Group: testGroup, Version: "v2"}.WithKind("InternalObject")}, + ExpectedRESTMappings: []*RESTMapping{ + { + Resource: schema.GroupVersionResource{Group: testGroup, Version: "v1", Resource: "internalobjects"}, + GroupVersionKind: schema.GroupVersionKind{Group: testGroup, Version: "v1", Kind: "InternalObject"}, + }, + { + Resource: schema.GroupVersionResource{Group: testGroup, Version: "v2", Resource: "internalobjects"}, + GroupVersionKind: schema.GroupVersionKind{Group: testGroup, Version: "v2", Kind: "InternalObject"}, + }, + }, }, } diff --git a/staging/src/k8s.io/metrics/pkg/client/custom_metrics/client.go b/staging/src/k8s.io/metrics/pkg/client/custom_metrics/client.go index 1e1763bc8f4..118eeb2bb96 100644 --- a/staging/src/k8s.io/metrics/pkg/client/custom_metrics/client.go +++ b/staging/src/k8s.io/metrics/pkg/client/custom_metrics/client.go @@ -104,11 +104,8 @@ func (c *customMetricsClient) qualResourceForKind(groupKind schema.GroupKind) (s return "", fmt.Errorf("unable to map kind %s to resource: %v", groupKind.String(), err) } - groupResource := schema.GroupResource{ - Group: mapping.GroupVersionKind.Group, - Resource: mapping.Resource, - } - return groupResource.String(), nil + gr := mapping.Resource.GroupResource() + return gr.String(), nil } type rootScopedMetrics struct { diff --git a/test/integration/apiserver/print_test.go b/test/integration/apiserver/print_test.go index 85bfa4c3f4e..511e05a7690 100644 --- a/test/integration/apiserver/print_test.go +++ b/test/integration/apiserver/print_test.go @@ -177,7 +177,7 @@ func TestServerSidePrint(t *testing.T) { if mapping.Scope.Name() == meta.RESTScopeNameNamespace { req = req.Namespace(ns.Name) } - body, err := req.Resource(mapping.Resource).SetHeader("Accept", tableParam).Do().Raw() + body, err := req.Resource(mapping.Resource.Resource).SetHeader("Accept", tableParam).Do().Raw() if err != nil { t.Errorf("unexpected error getting %s: %v", gvk, err) continue diff --git a/test/integration/etcd/etcd_storage_path_test.go b/test/integration/etcd/etcd_storage_path_test.go index 6c8d212aca0..d91cb0bbdfd 100644 --- a/test/integration/etcd/etcd_storage_path_test.go +++ b/test/integration/etcd/etcd_storage_path_test.go @@ -588,10 +588,9 @@ func TestEtcdStoragePath(t *testing.T) { continue } - gvResource := gvk.GroupVersion().WithResource(mapping.Resource) - etcdSeen[gvResource] = empty{} + etcdSeen[mapping.Resource] = empty{} - testData, hasTest := etcdStorageData[gvResource] + testData, hasTest := etcdStorageData[mapping.Resource] if !hasTest { t.Errorf("no test data for %s from %s. Please add a test for your new type to etcdStorageData.", kind, pkgPath) @@ -659,7 +658,7 @@ func TestEtcdStoragePath(t *testing.T) { } addGVKToEtcdBucket(cohabitatingResources, actualGVK, getEtcdBucket(testData.expectedEtcdPath)) - pathSeen[testData.expectedEtcdPath] = append(pathSeen[testData.expectedEtcdPath], gvResource) + pathSeen[testData.expectedEtcdPath] = append(pathSeen[testData.expectedEtcdPath], mapping.Resource) }() } @@ -955,7 +954,7 @@ func (c *allClient) create(stub, ns string, mapping *meta.RESTMapping, all *[]cl return err } namespaced := mapping.Scope.Name() == meta.RESTScopeNameNamespace - output, err := req.NamespaceIfScoped(ns, namespaced).Resource(mapping.Resource).Body(strings.NewReader(stub)).Do().Get() + output, err := req.NamespaceIfScoped(ns, namespaced).Resource(mapping.Resource.Resource).Body(strings.NewReader(stub)).Do().Get() if err != nil { return err } @@ -977,7 +976,7 @@ func (c *allClient) destroy(obj runtime.Object, mapping *meta.RESTMapping) error if err != nil { return err } - return req.NamespaceIfScoped(ns, namespaced).Resource(mapping.Resource).Name(name).Do().Error() + return req.NamespaceIfScoped(ns, namespaced).Resource(mapping.Resource.Resource).Name(name).Do().Error() } func (c *allClient) cleanup(all *[]cleanupData) error {