Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix OpenAPI aggregation cleanup #120108

Merged
merged 1 commit into from
Aug 31, 2023
Merged

Conversation

tnqn
Copy link
Member

@tnqn tnqn commented Aug 22, 2023

What type of PR is this?

/kind bug

What this PR does / why we need it:

There were four issues in OpenAPI aggregation cleanup:

  1. When removing an APIService, openAPIAggregationController was called twice while openAPIV3AggregationController was never called, leading to OpenAPI v3 for the APIService not cleaned up.
  2. When removing a local APIService, v2 specAggregator should not return ErrAPIServiceNotFound when it doesn't find the APIService because local APIServices were never added to its cache, otherwise confusing error logs would be generated. Besides, the method's comment indicates that the desired behavior is that no error is returned if the APIService does not exist.
  3. When removing an APIService, v3 specProxier should update openapiv2converter's cache, like when updating an APIService, otherwise the API would not be removed from "/openapi/v3".
  4. When v3 AggregationController reconciles an APIService, it should stop requeueing it if it fails with ErrAPIServiceNotFound as the APIService has been removed, like what v2 AggregationController does, otherwise it would keep reconciling the APIService forever.

Which issue(s) this PR fixes:

Fixes #120107

Special notes for your reviewer:

Does this PR introduce a user-facing change?

Fix OpenAPI v3 not being cleaned up after deleting APIServices

Additional documentation e.g., KEPs (Kubernetes Enhancement Proposals), usage docs, etc.:


@k8s-ci-robot k8s-ci-robot added release-note Denotes a PR that will be considered when it comes time to generate release notes. size/M Denotes a PR that changes 30-99 lines, ignoring generated files. kind/bug Categorizes issue or PR as related to a bug. cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. do-not-merge/needs-sig Indicates an issue or PR lacks a `sig/foo` label and requires one. needs-triage Indicates an issue or PR lacks a `triage/foo` label and requires one. needs-priority Indicates a PR lacks a `priority/foo` label and requires one. area/test sig/api-machinery Categorizes an issue or PR as relevant to SIG API Machinery. sig/testing Categorizes an issue or PR as relevant to SIG Testing. and removed do-not-merge/needs-sig Indicates an issue or PR lacks a `sig/foo` label and requires one. labels Aug 22, 2023
Copy link
Member

@Jefftree Jefftree left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for reporting and fixing this! A couple small nits

test/e2e/apimachinery/openapiv3.go Show resolved Hide resolved
@@ -236,7 +236,7 @@ func (s *specAggregator) RemoveAPIService(apiServiceName string) error {
defer s.mutex.Unlock()

if _, exists := s.specsByAPIServiceName[apiServiceName]; !exists {
return ErrAPIServiceNotFound
return nil
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This function cannot return an error anymore right? Would it make sense to to change the function signature so it's more clear?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure, changed the signature.

@alexzielenski
Copy link
Contributor

/triage accepted
/assign @Jefftree

@k8s-ci-robot k8s-ci-robot added triage/accepted Indicates an issue or PR is ready to be actively worked on. and removed needs-triage Indicates an issue or PR lacks a `triage/foo` label and requires one. labels Aug 22, 2023
Copy link
Member Author

@tnqn tnqn left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@Jefftree thanks for your review and comments.

@@ -236,7 +236,7 @@ func (s *specAggregator) RemoveAPIService(apiServiceName string) error {
defer s.mutex.Unlock()

if _, exists := s.specsByAPIServiceName[apiServiceName]; !exists {
return ErrAPIServiceNotFound
return nil
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure, changed the signature.

test/e2e/apimachinery/openapiv3.go Show resolved Hide resolved
@k8s-ci-robot k8s-ci-robot added size/L Denotes a PR that changes 100-499 lines, ignoring generated files. and removed size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Aug 23, 2023
@Jefftree
Copy link
Member

/lgtm
/assign @jpbetz
/cc @apelisse

I think we should backport this at least to 1.27

@k8s-ci-robot k8s-ci-robot added the lgtm "Looks good to me", indicates that a PR is ready to be merged. label Aug 23, 2023
@k8s-ci-robot
Copy link
Contributor

LGTM label has been added.

Git tree hash: a3860487bb874ef97b06556bedf588beefd8ed23

@@ -45,7 +45,7 @@ var ErrAPIServiceNotFound = errors.New("resource not found")
type SpecAggregator interface {
AddUpdateAPIService(apiService *v1.APIService, handler http.Handler) error
UpdateAPIServiceSpec(apiServiceName string) error
RemoveAPIService(apiServiceName string) error
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

you introduced a special error. This is becoming part of the interface and needs documentation. Or better: get rid of the error and use found bool, err error

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

updated

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

just a note that adding a return parameter will probably make backporting slightly more involved

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

made a compromise here: documented the specific error ErrAPIServiceNotFound to avoid affecting v2 code and facilitate backporting.

@tnqn
Copy link
Member Author

tnqn commented Aug 30, 2023

Thanks @sttts for your review. The code was mainly to be consistent with OpenAPI v2, please let me know if we should change them together or focus on bugfix in the PR.

@k8s-ci-robot k8s-ci-robot removed the lgtm "Looks good to me", indicates that a PR is ready to be merged. label Aug 30, 2023
RemoveAPIService(apiServiceName string) error
// UpdateAPIServiceSpec updates the APIService. It returns a bool which indicates whether the APIService exists and
// the actual error.
UpdateAPIServiceSpec(apiServiceName string) (bool, error)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is not what I meant. If you make "not found" explicit, it is not an error anymore. So we would return false, nil.

@tnqn tnqn force-pushed the fix-appgregator branch 2 times, most recently from f0862ed to 1a753b9 Compare August 30, 2023 15:26
@k8s-ci-robot k8s-ci-robot added size/M Denotes a PR that changes 30-99 lines, ignoring generated files. and removed size/L Denotes a PR that changes 100-499 lines, ignoring generated files. labels Aug 30, 2023
There were four issues in OpenAPI aggregation cleanup:
1. When removing an APIService, openAPIAggregationController was called
   twice while openAPIV3AggregationController was never called, leading
   to OpenAPI v3 for the APIService not cleaned up.
2. When removing a local APIService, v2 specAggregator should not return
   ErrAPIServiceNotFound when it doesn't find the APIService because
   local APIServices were never added to its cache, otherwise confusing
   error logs would be generated. Besides, the method's comment
   indicates that the desired behavior is that no error is returned if
   the APIService does not exist.
3. When removing an APIService, v3 specProxier should update
   openapiv2converter's cache, like when updating an APIService,
   otherwise the API would not be removed from "/openapi/v3".
4. When v3 AggregationController reconciles an APIService, it should
   stop requeueing it if it fails with ErrAPIServiceNotFound as the
   APIService has been removed, like what v2 AggregationController does,
   otherwise it would keep reconciling the APIService forever.

Signed-off-by: Quan Tian <[email protected]>
@sttts
Copy link
Contributor

sttts commented Aug 31, 2023

/approve

Leaving final lgtm to @Jefftree

@k8s-ci-robot k8s-ci-robot added the approved Indicates a PR has been approved by an approver from all required OWNERS files. label Aug 31, 2023
@Jefftree
Copy link
Member

/approve
/lgtm

@k8s-ci-robot k8s-ci-robot added the lgtm "Looks good to me", indicates that a PR is ready to be merged. label Aug 31, 2023
@k8s-ci-robot
Copy link
Contributor

LGTM label has been added.

Git tree hash: a371c959f6684053431a451213d161f6b11213f2

@k8s-ci-robot
Copy link
Contributor

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: Jefftree, sttts, tnqn

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@tnqn
Copy link
Member Author

tnqn commented Aug 31, 2023

/retest

@k8s-ci-robot k8s-ci-robot merged commit dd0c2d4 into kubernetes:master Aug 31, 2023
15 checks passed
@k8s-ci-robot k8s-ci-robot added this to the v1.29 milestone Aug 31, 2023
@tnqn tnqn deleted the fix-appgregator branch September 1, 2023 02:25
@tnqn
Copy link
Member Author

tnqn commented Sep 1, 2023

I think we should backport this at least to 1.27

@Jefftree I found there are some conflicts when backporting it to 1.27 due to the change: #118212, just want to check with you if it's still worth to backport in this situation. If yes, I would need to add ErrAPIServiceNotFound to 1.27.

There is no conflict with 1.28.

@Jefftree
Copy link
Member

Jefftree commented Sep 1, 2023

@tnqn: OpenAPIV3 went GA in 1.27 so I think it'd be worth it. Let me know if you need help with it.

@tnqn
Copy link
Member Author

tnqn commented Sep 1, 2023

@tnqn: OpenAPIV3 went GA in 1.27 so I think it'd be worth it. Let me know if you need help with it.

Got it, created #120362 for 1.27, removed the changes in v2 as the interface can return error in that release.

k8s-ci-robot added a commit that referenced this pull request Sep 7, 2023
…-upstream-release-1.27

Automated cherry pick of #120108: Fix OpenAPI aggregation cleanup
k8s-ci-robot added a commit that referenced this pull request Sep 7, 2023
…-upstream-release-1.28

Automated cherry pick of #120108: Fix OpenAPI aggregation cleanup
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
approved Indicates a PR has been approved by an approver from all required OWNERS files. area/test cncf-cla: yes Indicates the PR's author has signed the CNCF CLA. kind/bug Categorizes issue or PR as related to a bug. lgtm "Looks good to me", indicates that a PR is ready to be merged. needs-priority Indicates a PR lacks a `priority/foo` label and requires one. release-note Denotes a PR that will be considered when it comes time to generate release notes. sig/api-machinery Categorizes an issue or PR as relevant to SIG API Machinery. sig/testing Categorizes an issue or PR as relevant to SIG Testing. size/M Denotes a PR that changes 30-99 lines, ignoring generated files. triage/accepted Indicates an issue or PR is ready to be actively worked on.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

kube-apiserver doesn't clean up OpenAPI properly after deleting an APIService/CRD
6 participants