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

[Metal] default Metal Gateway responses do not match the API spec #64

Open
ctreatma opened this issue Jun 28, 2024 · 3 comments
Open

[Metal] default Metal Gateway responses do not match the API spec #64

ctreatma opened this issue Jun 28, 2024 · 3 comments

Comments

@ctreatma
Copy link
Contributor

ctreatma commented Jun 28, 2024

This is a finding from investigation on equinix-labs/metal-go#137.
This also relates to equinix-labs/metal-go#128.

The Metal Gateway API endpoints are all specified as returning the following schema:

oneOf:
- $ref: ./MetalGateway.yaml
- $ref: ./VrfMetalGateway.yaml

In OpenAPI 3, a oneOf has to match exactly one of the nested schemas, but by default, the Metal API response from Metal Gateway endpoints does not include enough information to differentiate between gateways (anything that matches the VrfMetalGateway schema will also match the MetalGateway schema).

This could be addressed with API changes, or possibly with spec changes that do not require an API change, but in the meantime the best workaround we have found is to add the following to all Metal Gateway API requests made with this SDK:

.Includes([]string{"ip_reservation"})

This workaround instructs the API to include IP reservation details in the API response. IPReservation and VrfIpReservation can be distinguished by the SDK, which enables the SDK to determine the gateway type (because MetalGateway has an IPReservation and VrfMetalGateway has a VrfIpReservation.

NOTE: because the Metal Gateway deletes are async, you also need to include the IP reservation in delete requests to avoid a response validation error.

You can see an example of the .Include() call here: https://github.com/equinix/terraform-provider-equinix/blob/611e78a32a865aa374d2e4896cd0978252b983c4/internal/resources/metal/gateway/resource.go#L173

@ctreatma ctreatma changed the title [Metal] default Metal Gateway responses are not valid [Metal] default Metal Gateway responses do not match the API spec Jun 28, 2024
@bjenkins-metal
Copy link

Hey gang! Just adding a +1 that this is impacting me with a project I am working on now. I had to use the httpResp return and not the err or the actual response. No way to get an ID reliably right now without touching the http responses. At least nothing I could find.

@displague
Copy link
Member

displague commented Aug 13, 2024

Hey @bjenkins-metal

In https://github.com/equinix/metal-cli/pull/481/files there is an example of getting either the MetalGateway or the VrfMetalGateway from a FindMetalGatewayById call. This example is obtuse because it attempts to handle MetalGateways and VrfGateways in a compatible way for output using a gatewayIsh interface and wrappers to abstract the common functions (GetId, GetIpReservation, ...).

The main take-away is that you'll need to specify the includes, specifically ip_reservation, and to use either of the two Gateway fields, whichever is not nil. (The code that was replaced in the PR was more direct about this).

@bjenkins-metal
Copy link

Thank you. Include did in fact fix the schema return problem I was having. Hope this example helps someone else.
resp, _, err := apiClient.MetalGatewaysApi.CreateMetalGateway(context.Background(), projectId).CreateMetalGatewayRequest(*metalGatewayInput).Include([]string{"ip_reservation"}).Execute()

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

No branches or pull requests

3 participants