Skip to content

Commit 1e72219

Browse files
committed
feat(instance): get server-type list info from PCU
1 parent 79c696a commit 1e72219

File tree

3 files changed

+864
-702
lines changed

3 files changed

+864
-702
lines changed

internal/namespaces/instance/v1/custom_server_type.go

Lines changed: 97 additions & 82 deletions
Original file line numberDiff line numberDiff line change
@@ -4,13 +4,13 @@ import (
44
"context"
55
"errors"
66
"fmt"
7-
"sort"
87
"strings"
98

109
"github.com/fatih/color"
1110
"github.com/scaleway/scaleway-cli/v2/core"
1211
"github.com/scaleway/scaleway-cli/v2/core/human"
1312
"github.com/scaleway/scaleway-sdk-go/api/instance/v1"
13+
product_catalog "github.com/scaleway/scaleway-sdk-go/api/product_catalog/v2alpha1"
1414
"github.com/scaleway/scaleway-sdk-go/scw"
1515
)
1616

@@ -35,60 +35,53 @@ var serverTypesAvailabilityMarshalSpecs = human.EnumMarshalSpecs{
3535
//
3636

3737
type customServerType struct {
38-
Name string `json:"name"`
39-
HourlyPrice *scw.Money `json:"hourly_price"`
40-
LocalVolumeMaxSize scw.Size `json:"local_volume_max_size"`
41-
CPU uint32 `json:"cpu"`
42-
GPU *uint64 `json:"gpu"`
43-
RAM scw.Size `json:"ram"`
44-
Arch instance.Arch `json:"arch"`
45-
Availability instance.ServerTypesAvailability `json:"availability"`
46-
MaxFileSystems uint32 `json:"max_file_systems"`
38+
Name string `json:"name"`
39+
HourlyPrice *scw.Money `json:"hourly_price"`
40+
SupportedStorage string
41+
CPU uint32 `json:"cpu"`
42+
GPU uint32 `json:"gpu"`
43+
RAM scw.Size `json:"ram"`
44+
Arch string `json:"arch"`
45+
Bandwidth uint64 `json:"bandwidth"`
46+
Availability instance.ServerTypesAvailability `json:"availability"`
47+
MaxFileSystems uint32 `json:"max_file_systems"`
4748
}
4849

4950
// serverTypeListBuilder transforms the server map into a list to display a
5051
// table of server types instead of a flat key/value list.
5152
// We need it for:
5253
// - [APIGW-1932] hide deprecated instance for scw instance server-type list
5354
func serverTypeListBuilder(c *core.Command) *core.Command {
54-
deprecatedNames := map[string]struct{}{
55-
"START1-L": {},
56-
"START1-M": {},
57-
"START1-S": {},
58-
"START1-XS": {},
59-
"VC1L": {},
60-
"VC1M": {},
61-
"VC1S": {},
62-
"X64-120GB": {},
63-
"X64-15GB": {},
64-
"X64-30GB": {},
65-
"X64-60GB": {},
66-
"C1": {},
67-
"C2M": {},
68-
"C2L": {},
69-
"C2S": {},
70-
"ARM64-2GB": {},
71-
"ARM64-4GB": {},
72-
"ARM64-8GB": {},
73-
"ARM64-16GB": {},
74-
"ARM64-32GB": {},
75-
"ARM64-64GB": {},
76-
"ARM64-128GB": {},
77-
}
78-
7955
c.Run = func(ctx context.Context, argsI any) (any, error) {
80-
api := instance.NewAPI(core.ExtractClient(ctx))
56+
pcuAPI := product_catalog.NewPublicCatalogAPI(core.ExtractClient(ctx))
57+
instanceAPI := instance.NewAPI(core.ExtractClient(ctx))
8158

82-
// Get server types.
59+
// Get server types from Product Catalog API
8360
request := argsI.(*instance.ListServersTypesRequest)
84-
listServersTypesResponse, err := api.ListServersTypes(request, scw.WithAllPages())
61+
instanceProductType := product_catalog.ListPublicCatalogProductsRequestProductTypeInstance
62+
listServersTypesResponse, err := pcuAPI.ListPublicCatalogProducts(
63+
&product_catalog.PublicCatalogAPIListPublicCatalogProductsRequest{
64+
ProductTypes: []product_catalog.ListPublicCatalogProductsRequestProductType{
65+
instanceProductType,
66+
},
67+
Zone: &request.Zone,
68+
Status: nil,
69+
},
70+
scw.WithAllPages(),
71+
scw.WithContext(ctx),
72+
)
73+
if err != nil {
74+
return nil, err
75+
}
76+
77+
// Get server types from Instance API (still needed for the number of file systems)
78+
computeServerTypes, err := instanceAPI.ListServersTypes(request, scw.WithAllPages())
8579
if err != nil {
8680
return nil, err
8781
}
88-
serverTypes := []*customServerType(nil)
8982

9083
// Get server availabilities.
91-
availabilitiesResponse, err := api.GetServerTypesAvailability(
84+
availabilitiesResponse, err := instanceAPI.GetServerTypesAvailability(
9285
&instance.GetServerTypesAvailabilityRequest{
9386
Zone: request.Zone,
9487
},
@@ -98,55 +91,79 @@ func serverTypeListBuilder(c *core.Command) *core.Command {
9891
return nil, err
9992
}
10093

101-
for name, serverType := range listServersTypesResponse.Servers {
102-
_, isDeprecated := deprecatedNames[name]
103-
if isDeprecated {
94+
serverTypes := []*customServerType(nil)
95+
96+
for _, pcuServerType := range listServersTypesResponse.Products {
97+
switch pcuServerType.Status {
98+
case product_catalog.PublicCatalogProductStatusUnknownStatus:
99+
continue
100+
case product_catalog.PublicCatalogProductStatusPublicBeta:
101+
case product_catalog.PublicCatalogProductStatusPreview:
102+
case product_catalog.PublicCatalogProductStatusGeneralAvailability:
103+
case product_catalog.PublicCatalogProductStatusEndOfNewFeatures:
104+
case product_catalog.PublicCatalogProductStatusEndOfGrowth:
105+
continue
106+
case product_catalog.PublicCatalogProductStatusEndOfDeployment:
107+
continue
108+
case product_catalog.PublicCatalogProductStatusEndOfSupport:
109+
continue
110+
case product_catalog.PublicCatalogProductStatusEndOfSale:
111+
continue
112+
case product_catalog.PublicCatalogProductStatusEndOfLife:
113+
continue
114+
case product_catalog.PublicCatalogProductStatusRetired:
104115
continue
105116
}
106117

107-
serverTypeAvailability := instance.ServerTypesAvailability("unknown")
118+
name := pcuServerType.Properties.Instance.OfferID
119+
computeServerType := computeServerTypes.Servers[name]
120+
serverType := &customServerType{
121+
Name: name,
122+
HourlyPrice: pcuServerType.Price.RetailPrice,
123+
MaxFileSystems: computeServerType.Capabilities.MaxFileSystems,
124+
}
108125

109126
if availability, exists := availabilitiesResponse.Servers[name]; exists {
110-
serverTypeAvailability = availability.Availability
127+
serverType.Availability = availability.Availability
111128
}
112129

113-
serverTypes = append(serverTypes, &customServerType{
114-
Name: name,
115-
HourlyPrice: scw.NewMoneyFromFloat(
116-
float64(serverType.HourlyPrice),
117-
"EUR",
118-
3,
119-
),
120-
LocalVolumeMaxSize: serverType.VolumesConstraint.MaxSize,
121-
CPU: serverType.Ncpus,
122-
GPU: serverType.Gpu,
123-
RAM: scw.Size(serverType.RAM),
124-
Arch: serverType.Arch,
125-
Availability: serverTypeAvailability,
126-
MaxFileSystems: serverType.Capabilities.MaxFileSystems,
127-
})
128-
}
130+
if pcuServerType.Properties.Hardware != nil {
131+
if pcuServerType.Properties.Hardware.CPU != nil {
132+
serverType.CPU = pcuServerType.Properties.Hardware.CPU.Virtual.Count
133+
serverType.Arch = pcuServerType.Properties.Hardware.CPU.Arch.String()
134+
}
135+
136+
if pcuServerType.Properties.Hardware.Gpu != nil {
137+
serverType.GPU = pcuServerType.Properties.Hardware.Gpu.Count
138+
}
139+
140+
if pcuServerType.Properties.Hardware.RAM != nil {
141+
serverType.RAM = pcuServerType.Properties.Hardware.RAM.Size
142+
}
143+
144+
if pcuServerType.Properties.Hardware.Storage != nil {
145+
serverType.SupportedStorage = strings.Replace(
146+
pcuServerType.Properties.Hardware.Storage.Description,
147+
"Dynamic local: 1 x SSD",
148+
"Local",
149+
1,
150+
)
151+
}
129152

130-
sort.Slice(serverTypes, func(i, j int) bool {
131-
categoryA := serverTypeCategory(serverTypes[i].Name)
132-
categoryB := serverTypeCategory(serverTypes[j].Name)
133-
if categoryA != categoryB {
134-
return categoryA < categoryB
153+
if pcuServerType.Properties.Hardware.Network != nil {
154+
serverType.Bandwidth = pcuServerType.Properties.Hardware.Network.MaxPublicBandwidth
155+
}
135156
}
136157

137-
return serverTypes[i].HourlyPrice.ToFloat() < serverTypes[j].HourlyPrice.ToFloat()
138-
})
158+
serverTypes = append(serverTypes, serverType)
159+
}
139160

140161
return serverTypes, nil
141162
}
142163

143164
return c
144165
}
145166

146-
func serverTypeCategory(serverTypeName string) (category string) {
147-
return strings.Split(serverTypeName, "-")[0]
148-
}
149-
150167
func getCompatibleTypesBuilder(c *core.Command) *core.Command {
151168
c.Interceptor = func(ctx context.Context, argsI any, runner core.CommandRunner) (any, error) {
152169
rawResp, err := runner(ctx, argsI)
@@ -186,11 +203,10 @@ func getCompatibleTypesBuilder(c *core.Command) *core.Command {
186203
"EUR",
187204
3,
188205
),
189-
LocalVolumeMaxSize: serverType.VolumesConstraint.MaxSize,
190-
CPU: serverType.Ncpus,
191-
GPU: serverType.Gpu,
192-
RAM: scw.Size(serverType.RAM),
193-
Arch: serverType.Arch,
206+
CPU: serverType.Ncpus,
207+
GPU: uint32(*serverType.Gpu),
208+
RAM: scw.Size(serverType.RAM),
209+
Arch: serverType.Arch.String(),
194210
})
195211
}
196212

@@ -220,11 +236,10 @@ func getCompatibleTypesBuilder(c *core.Command) *core.Command {
220236
"EUR",
221237
3,
222238
),
223-
LocalVolumeMaxSize: currentServerType.VolumesConstraint.MaxSize,
224-
CPU: currentServerType.Ncpus,
225-
GPU: currentServerType.Gpu,
226-
RAM: scw.Size(currentServerType.RAM),
227-
Arch: currentServerType.Arch,
239+
CPU: currentServerType.Ncpus,
240+
GPU: uint32(*currentServerType.Gpu),
241+
RAM: scw.Size(currentServerType.RAM),
242+
Arch: currentServerType.Arch.String(),
228243
},
229244
}
230245

internal/namespaces/instance/v1/testdata/test-server-type-list-server-type-list.cassette.yaml

Lines changed: 195 additions & 156 deletions
Large diffs are not rendered by default.

0 commit comments

Comments
 (0)