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

Add GET v3/service_offerings/:guid #3579

Merged
merged 8 commits into from
Nov 8, 2024

Conversation

klapkov
Copy link
Contributor

@klapkov klapkov commented Oct 30, 2024

Is there a related GitHub Issue?

#3578

What is this change about?

Here we add GetServiceOffering - GET v3/service_offerings/:guid

Does this PR introduce a breaking change?

no

Acceptance Steps

Tag your pair, your PM, and/or team

Comment on lines 71 to 80
Describe("include broker field", func() {
BeforeEach(func() {
serviceBrokerRepo.ListServiceBrokersReturns([]repositories.ServiceBrokerRecord{{
ServiceBroker: services.ServiceBroker{
Name: "broker-name",
},
CFResource: model.CFResource{
GUID: "broker-guid",
},
}}, nil)
Copy link
Contributor Author

Choose a reason for hiding this comment

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

Not sure if we need this, since we already test the include broker field in the ListServiceOfferings test.

Copy link
Member

Choose a reason for hiding this comment

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

Yeah, looks a bit of a duplication. I would recommend having two whens: When("including broker name" and When("including broker guid that verify that proper broker fields are being returns. Error cases, as you have pointed out, are already covered in other tests.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

Copy link
Member

Choose a reason for hiding this comment

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

After we use the generic include resolver as advised above testing becomes simpler too, for example

Entry("invalid service broker field", "fields[service_broker]=foo", MatchError(ContainSubstring("value must be one of: guid, name"))),
)

It("returns an error if a unsupported param is passed", func() {
Copy link
Member

Choose a reason for hiding this comment

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

That it could be an entry in the invalid query table above. Here is a similar example

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

@@ -54,3 +59,10 @@ func ForServiceOffering(serviceOffering repositories.ServiceOfferingRecord, base
},
}
}

func ForServiceOfferingWithIncluded(serviceOffering repositories.ServiceOfferingRecord, baseURL url.URL, includes ...model.IncludedResource) ServiceOfferingWithIncludedResponse {
Copy link
Member

Choose a reason for hiding this comment

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

I would suggest adding the Included field to the ServiceOfferingResponse type rather than coming up with a new one.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

At first I took this approach, but this would mean that we would have to change the way it is handled in the list endpoint as well - https://github.com/cloudfoundry/korifi/blob/main/api/handlers/service_offering.go#L72. There we handle the "includes" with the ForList presenter and including it in the ForServiceOffering() would change ForList as well. Since only the LIST and GET endpoints for service offerings include fields, it did not seem right - https://v3-apidocs.cloudfoundry.org/version/3.180.0/index.html#fields-parameter. What do you think ?

Copy link
Member

@danail-branekov danail-branekov Nov 1, 2024

Choose a reason for hiding this comment

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

Well, if the field is annotated with omitempty, then I believe it should be not visible in the response. If I am correct, then

  • the get handler would set it on the ServiceOfferingResponse object
  • the list handler would not, it would use the includes as ForList argument. As the Includes would not be set on the ServiceOfferingResponse object, they would be just omited in the response resources. TL;DR I believe that changing the list endpoint would not be necessary.

Or am I overlooking something?


if err = userClient.Get(ctx, client.ObjectKeyFromObject(offering), offering); err != nil {
if k8serrors.IsForbidden(err) {
return ServiceOfferingRecord{}, nil
Copy link
Member

Choose a reason for hiding this comment

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

We should not be ignoring the forbidden error on Get. Instead, we should translate it to korifi forbidden error. You have actually done that below.
Lets just get rid of the forbidden check.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

api/handlers/service_offering.go Show resolved Hide resolved
return nil, apierrors.LogAndReturn(logger, err, "failed to get service offering: %s", serviceOfferingGUID)
}

brokerIncludes, err := h.getBrokerIncludes(r.Context(), authInfo, []repositories.ServiceOfferingRecord{serviceOffering}, payload.IncludeBrokerFields, h.serverURL)
Copy link
Member

Choose a reason for hiding this comment

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

The generic include resolver can be used here, you can see how it works here and here

Copy link
Contributor Author

Choose a reason for hiding this comment

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

In this case should I replace the implementation on the list handler as well ?

Comment on lines 71 to 80
Describe("include broker field", func() {
BeforeEach(func() {
serviceBrokerRepo.ListServiceBrokersReturns([]repositories.ServiceBrokerRecord{{
ServiceBroker: services.ServiceBroker{
Name: "broker-name",
},
CFResource: model.CFResource{
GUID: "broker-guid",
},
}}, nil)
Copy link
Member

Choose a reason for hiding this comment

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

After we use the generic include resolver as advised above testing becomes simpler too, for example

@@ -10,6 +10,25 @@ import (
jellidation "github.com/jellydator/validation"
)

type ServiceOfferingGet struct {
IncludeBrokerFields []string
Copy link
Member

Choose a reason for hiding this comment

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

We should be using the IncludeReourceRule type as we do for plans

@georgethebeatle georgethebeatle enabled auto-merge (squash) November 8, 2024 13:53
@georgethebeatle georgethebeatle linked an issue Nov 8, 2024 that may be closed by this pull request
@georgethebeatle georgethebeatle merged commit 8394199 into cloudfoundry:main Nov 8, 2024
10 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

API GET /v3/service_offerings/:guid is not implemented
3 participants