mirror of
https://github.com/edgelesssys/constellation.git
synced 2024-12-24 23:19:39 -05:00
ci: add cli k8s compatibility table artifact upload to ci (#1218)
* add cli k8s compatibility api to ci * extend versionsapi package * rework cli info upload via ci * join errors natively * fix semver * upload from hack file * fix ci checks * add distributionid * setup go before running hack file * setup go after repo checkout * use logger instead of panic, invalidate cache * use provided ctx Co-authored-by: Paul Meyer <49727155+katexochen@users.noreply.github.com> --------- Co-authored-by: Paul Meyer <49727155+katexochen@users.noreply.github.com>
This commit is contained in:
parent
ed2e6fe233
commit
a274ac8a7c
27
.github/workflows/build-os-image.yml
vendored
27
.github/workflows/build-os-image.yml
vendored
@ -122,6 +122,7 @@ jobs:
|
||||
imageName: ${{ steps.image-version.outputs.imageName }}
|
||||
imageNameShort: ${{ steps.image-version.outputs.imageNameShort }}
|
||||
imageApiBasePath: ${{ steps.image-version.outputs.imageApiBasePath }}
|
||||
cliApiBasePath: ${{ steps.image-version.outputs.cliApiBasePath }}
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@ac593985615ec2ede58e132d2e21d2b1cbd6127c # v3.3.0
|
||||
@ -193,6 +194,7 @@ jobs:
|
||||
echo "imageVersion=${IMAGE_VERSION}"
|
||||
echo "imageName=ref/${REF}/stream/${STREAM}/${IMAGE_VERSION}"
|
||||
echo "imageApiBasePath=constellation/v1/ref/${REF}/stream/${STREAM}/${IMAGE_VERSION}/image"
|
||||
echo "cliApiBasePath=constellation/v1/ref/${REF}/stream/${STREAM}/${IMAGE_VERSION}/cli"
|
||||
} >> "$GITHUB_OUTPUT"
|
||||
|
||||
if [[ "${REF}" = "-" ]] && [[ "${STREAM}" = "stable" ]]; then
|
||||
@ -863,8 +865,8 @@ jobs:
|
||||
--no-progress
|
||||
done
|
||||
|
||||
upload-image-lookup-table:
|
||||
name: "Upload image lookup table"
|
||||
upload-artifacts:
|
||||
name: "Upload image lookup table and CLI compatibility info"
|
||||
runs-on: ubuntu-22.04
|
||||
needs: [build-settings, upload-os-image]
|
||||
permissions:
|
||||
@ -918,8 +920,27 @@ jobs:
|
||||
echo -e "\`\`\`"
|
||||
} >> "$GITHUB_STEP_SUMMARY"
|
||||
|
||||
- name: Checkout
|
||||
uses: actions/checkout@ac593985615ec2ede58e132d2e21d2b1cbd6127c # v3.3.0
|
||||
with:
|
||||
ref: ${{ inputs.ref || github.head_ref }}
|
||||
|
||||
- name: Setup Go environment
|
||||
uses: actions/setup-go@6edd4406fa81c3da01a34fa6f6343087c207a568 # v3.5.0
|
||||
with:
|
||||
go-version: "1.20.1"
|
||||
cache: true
|
||||
|
||||
- name: Create CLI compatibility information artifact
|
||||
shell: bash
|
||||
run: |
|
||||
go run ./hack/cli-k8s-compatibility/main.go \
|
||||
--ref=${{ needs.build-settings.outputs.ref }} \
|
||||
--stream=${{ needs.build-settings.outputs.stream }} \
|
||||
--version=${{ needs.build-settings.outputs.imageVersion }} \
|
||||
|
||||
add-version-to-versionsapi:
|
||||
needs: [upload-image-lookup-table, build-settings]
|
||||
needs: [upload-artifacts, build-settings]
|
||||
name: "Add version to versionsapi"
|
||||
if: needs.build-settings.outputs.ref != '-'
|
||||
permissions:
|
||||
|
66
hack/cli-k8s-compatibility/main.go
Normal file
66
hack/cli-k8s-compatibility/main.go
Normal file
@ -0,0 +1,66 @@
|
||||
/*
|
||||
Copyright (c) Edgeless Systems GmbH
|
||||
|
||||
SPDX-License-Identifier: AGPL-3.0-only
|
||||
*/
|
||||
|
||||
// cli-k8s-compatibility generates JSON output for a CLI version and its supported Kubernetes versions.
|
||||
package main
|
||||
|
||||
import (
|
||||
"context"
|
||||
"flag"
|
||||
|
||||
"github.com/edgelesssys/constellation/v2/internal/logger"
|
||||
"github.com/edgelesssys/constellation/v2/internal/versions"
|
||||
"github.com/edgelesssys/constellation/v2/internal/versionsapi"
|
||||
"github.com/edgelesssys/constellation/v2/internal/versionsapi/client"
|
||||
"go.uber.org/zap/zapcore"
|
||||
)
|
||||
|
||||
var (
|
||||
refFlag = flag.String("ref", "", "the reference name of the image")
|
||||
streamFlag = flag.String("stream", "", "the stream name of the image")
|
||||
versionFlag = flag.String("version", "", "the version of the image")
|
||||
)
|
||||
|
||||
func main() {
|
||||
log := logger.New(logger.PlainLog, zapcore.DebugLevel)
|
||||
ctx := context.Background()
|
||||
|
||||
flag.Parse()
|
||||
if *refFlag == "" {
|
||||
log.Fatalf("ref must be set")
|
||||
}
|
||||
if *streamFlag == "" {
|
||||
log.Fatalf("stream must be set")
|
||||
}
|
||||
if *versionFlag == "" {
|
||||
log.Fatalf("version must be set")
|
||||
}
|
||||
|
||||
cliInfo := versionsapi.CLIInfo{
|
||||
Ref: *refFlag,
|
||||
Stream: *streamFlag,
|
||||
Version: *versionFlag,
|
||||
Kubernetes: []string{},
|
||||
}
|
||||
|
||||
for _, v := range versions.VersionConfigs {
|
||||
cliInfo.Kubernetes = append(cliInfo.Kubernetes, v.ClusterVersion)
|
||||
}
|
||||
|
||||
c, err := client.NewClient(ctx, "eu-central-1", "cdn-constellation-backend", "E1H77EZTHC3NE4", false, log)
|
||||
if err != nil {
|
||||
log.Fatalf("creating s3 client: %w", err)
|
||||
}
|
||||
defer func() {
|
||||
if err := c.InvalidateCache(ctx); err != nil {
|
||||
log.Fatalf("invalidating cache: %w", err)
|
||||
}
|
||||
}()
|
||||
|
||||
if err := c.UpdateCLIInfo(ctx, cliInfo); err != nil {
|
||||
log.Fatalf("updating cli info: %w", err)
|
||||
}
|
||||
}
|
@ -91,10 +91,12 @@ require (
|
||||
github.com/aws/aws-sdk-go-v2/config v1.18.10 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/credentials v1.13.10 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.12.21 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/feature/s3/manager v1.11.49 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.27 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.4.21 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/internal/ini v1.3.28 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/internal/v4a v1.0.18 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/service/cloudfront v1.24.0 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/service/ec2 v1.83.0 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.9.11 // indirect
|
||||
github.com/aws/aws-sdk-go-v2/service/internal/checksum v1.1.22 // indirect
|
||||
|
@ -227,6 +227,8 @@ github.com/aws/aws-sdk-go-v2/credentials v1.13.10 h1:T4Y39IhelTLg1f3xiKJssThnFxs
|
||||
github.com/aws/aws-sdk-go-v2/credentials v1.13.10/go.mod h1:tqAm4JmQaShel+Qi38hmd1QglSnnxaYt50k/9yGQzzc=
|
||||
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.12.21 h1:j9wi1kQ8b+e0FBVHxCqCGo4kxDU175hoDHcWAi0sauU=
|
||||
github.com/aws/aws-sdk-go-v2/feature/ec2/imds v1.12.21/go.mod h1:ugwW57Z5Z48bpvUyZuaPy4Kv+vEfJWnIrky7RmkBvJg=
|
||||
github.com/aws/aws-sdk-go-v2/feature/s3/manager v1.11.49 h1:zPFhadkmXbXu3RVXTPU4HVW+g2DStMY+01cJaj//+Cw=
|
||||
github.com/aws/aws-sdk-go-v2/feature/s3/manager v1.11.49/go.mod h1:N9gSChQkKpdAj7vRpfKma4ND88zoZM+v6W2lJgWrDh4=
|
||||
github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.27 h1:I3cakv2Uy1vNmmhRQmFptYDxOvBnwCdNwyw63N0RaRU=
|
||||
github.com/aws/aws-sdk-go-v2/internal/configsources v1.1.27/go.mod h1:a1/UpzeyBBerajpnP5nGZa9mGzsBn5cOKxm6NWQsvoI=
|
||||
github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 v2.4.21 h1:5NbbMrIzmUn/TXFqAle6mgrH5m9cOvMLRGL7pnG8tRE=
|
||||
@ -235,6 +237,8 @@ github.com/aws/aws-sdk-go-v2/internal/ini v1.3.28 h1:KeTxcGdNnQudb46oOl4d90f2I33
|
||||
github.com/aws/aws-sdk-go-v2/internal/ini v1.3.28/go.mod h1:yRZVr/iT0AqyHeep00SZ4YfBAKojXz08w3XMBscdi0c=
|
||||
github.com/aws/aws-sdk-go-v2/internal/v4a v1.0.18 h1:H/mF2LNWwX00lD6FlYfKpLLZgUW7oIzCBkig78x4Xok=
|
||||
github.com/aws/aws-sdk-go-v2/internal/v4a v1.0.18/go.mod h1:T2Ku+STrYQ1zIkL1wMvj8P3wWQaaCMKNdz70MT2FLfE=
|
||||
github.com/aws/aws-sdk-go-v2/service/cloudfront v1.24.0 h1:k1RJsiyqnUm5u+jrYOls9MoP9xgqsVUOrfsYy9mxCro=
|
||||
github.com/aws/aws-sdk-go-v2/service/cloudfront v1.24.0/go.mod h1:xUOmvPrMKmH94stXswKsGSkL02vMpNU+rTG+eIzFfNQ=
|
||||
github.com/aws/aws-sdk-go-v2/service/ec2 v1.83.0 h1:6eTsq8mUG4VCrqbebRYVtgkKguP9J2veJHuhdISMM+Y=
|
||||
github.com/aws/aws-sdk-go-v2/service/ec2 v1.83.0/go.mod h1:mV0E7631M1eXdB+tlGFIw6JxfsC7Pz7+7Aw15oLVhZw=
|
||||
github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding v1.9.11 h1:y2+VQzC6Zh2ojtV2LoC0MNwHWc6qXv/j2vrQtlftkdA=
|
||||
|
@ -140,6 +140,16 @@ func (c *Client) UpdateImageInfo(ctx context.Context, imageInfo versionsapi.Imag
|
||||
return update(ctx, c, imageInfo)
|
||||
}
|
||||
|
||||
// FetchCLIInfo fetches the given CLI info from the versions API.
|
||||
func (c *Client) FetchCLIInfo(ctx context.Context, cliInfo versionsapi.CLIInfo) (versionsapi.CLIInfo, error) {
|
||||
return fetch(ctx, c, cliInfo)
|
||||
}
|
||||
|
||||
// UpdateCLIInfo updates the given CLI info in the versions API.
|
||||
func (c *Client) UpdateCLIInfo(ctx context.Context, cliInfo versionsapi.CLIInfo) error {
|
||||
return update(ctx, c, cliInfo)
|
||||
}
|
||||
|
||||
// DeleteRef deletes the given ref from the versions API.
|
||||
func (c *Client) DeleteRef(ctx context.Context, ref string) error {
|
||||
if err := versionsapi.ValidateRef(ref); err != nil {
|
||||
|
95
internal/versionsapi/cliinfo.go
Normal file
95
internal/versionsapi/cliinfo.go
Normal file
@ -0,0 +1,95 @@
|
||||
/*
|
||||
Copyright (c) Edgeless Systems GmbH
|
||||
|
||||
SPDX-License-Identifier: AGPL-3.0-only
|
||||
*/
|
||||
|
||||
package versionsapi
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"net/url"
|
||||
"path"
|
||||
|
||||
"github.com/edgelesssys/constellation/v2/internal/constants"
|
||||
"golang.org/x/mod/semver"
|
||||
)
|
||||
|
||||
// CLIInfo contains information about a specific CLI version (i.e. it's compatibility with Kubernetes versions).
|
||||
type CLIInfo struct {
|
||||
// Ref is the reference name of the image.
|
||||
Ref string `json:"ref,omitempty"`
|
||||
// Stream is the stream name of the image.
|
||||
Stream string `json:"stream,omitempty"`
|
||||
// Version is the version of the image.
|
||||
Version string `json:"version,omitempty"`
|
||||
// Kubernetes contains all compatible Kubernetes versions.
|
||||
Kubernetes []string `json:"kubernetes,omitempty"`
|
||||
}
|
||||
|
||||
// JSONPath returns the S3 JSON path for this object.
|
||||
func (c CLIInfo) JSONPath() string {
|
||||
return path.Join(
|
||||
constants.CDNAPIPrefix,
|
||||
"ref", c.Ref,
|
||||
"stream", c.Stream,
|
||||
c.Version,
|
||||
"cli",
|
||||
"info.json",
|
||||
)
|
||||
}
|
||||
|
||||
// URL returns the URL to the JSON file for this object.
|
||||
func (c CLIInfo) URL() (string, error) {
|
||||
url, err := url.Parse(constants.CDNRepositoryURL)
|
||||
if err != nil {
|
||||
return "", fmt.Errorf("parsing CDN URL: %w", err)
|
||||
}
|
||||
url.Path = c.JSONPath()
|
||||
return url.String(), nil
|
||||
}
|
||||
|
||||
// ValidateRequest validates the request parameters of the list.
|
||||
// The Kubernetes slice must be empty.
|
||||
func (c CLIInfo) ValidateRequest() error {
|
||||
var retErr error
|
||||
if err := ValidateRef(c.Ref); err != nil {
|
||||
retErr = errors.Join(retErr, err)
|
||||
}
|
||||
if err := ValidateStream(c.Ref, c.Stream); err != nil {
|
||||
retErr = errors.Join(retErr, err)
|
||||
}
|
||||
if !semver.IsValid(c.Version) {
|
||||
retErr = errors.Join(retErr, fmt.Errorf("version %q is not a valid semver", c.Version))
|
||||
}
|
||||
if len(c.Kubernetes) != 0 {
|
||||
retErr = errors.Join(retErr, errors.New("Kubernetes slice must be empty for request"))
|
||||
}
|
||||
|
||||
return retErr
|
||||
}
|
||||
|
||||
// Validate checks if the CLI info is valid.
|
||||
func (c CLIInfo) Validate() error {
|
||||
var retErr error
|
||||
if err := ValidateRef(c.Ref); err != nil {
|
||||
retErr = errors.Join(retErr, err)
|
||||
}
|
||||
if err := ValidateStream(c.Ref, c.Stream); err != nil {
|
||||
retErr = errors.Join(retErr, err)
|
||||
}
|
||||
if !semver.IsValid(c.Version) {
|
||||
retErr = errors.Join(retErr, fmt.Errorf("version %q is not a valid semver", c.Version))
|
||||
}
|
||||
if len(c.Kubernetes) == 0 {
|
||||
retErr = errors.Join(retErr, errors.New("Kubernetes slice must not be empty"))
|
||||
}
|
||||
for _, k := range c.Kubernetes {
|
||||
if !semver.IsValid(k) {
|
||||
retErr = errors.Join(retErr, fmt.Errorf("Kubernetes version %q is not a valid semver", k))
|
||||
}
|
||||
}
|
||||
|
||||
return retErr
|
||||
}
|
221
internal/versionsapi/cliinfo_test.go
Normal file
221
internal/versionsapi/cliinfo_test.go
Normal file
@ -0,0 +1,221 @@
|
||||
/*
|
||||
Copyright (c) Edgeless Systems GmbH
|
||||
|
||||
SPDX-License-Identifier: AGPL-3.0-only
|
||||
*/
|
||||
|
||||
package versionsapi
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
||||
"github.com/edgelesssys/constellation/v2/internal/constants"
|
||||
"github.com/stretchr/testify/assert"
|
||||
)
|
||||
|
||||
func TestCLIInfoJSONPath(t *testing.T) {
|
||||
testCases := map[string]struct {
|
||||
info CLIInfo
|
||||
wantPath string
|
||||
}{
|
||||
"cli info": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "nightly",
|
||||
Version: "v1.0.0",
|
||||
},
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/test-ref/stream/nightly/v1.0.0/cli/info.json",
|
||||
},
|
||||
"cli info release": {
|
||||
info: CLIInfo{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
Version: "v1.0.0",
|
||||
},
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/-/stream/stable/v1.0.0/cli/info.json",
|
||||
},
|
||||
}
|
||||
|
||||
for name, tc := range testCases {
|
||||
t.Run(name, func(t *testing.T) {
|
||||
assert.Equal(t, tc.wantPath, tc.info.JSONPath())
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestCLIInfoURL(t *testing.T) {
|
||||
testCases := map[string]struct {
|
||||
info CLIInfo
|
||||
wantURL string
|
||||
wantPath string
|
||||
}{
|
||||
"cli info": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "nightly",
|
||||
Version: "v1.0.0",
|
||||
},
|
||||
wantURL: constants.CDNRepositoryURL + "/" + constants.CDNAPIPrefix + "/ref/test-ref/stream/nightly/v1.0.0/cli/info.json",
|
||||
},
|
||||
"cli info release": {
|
||||
info: CLIInfo{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
Version: "v1.0.0",
|
||||
},
|
||||
wantURL: constants.CDNRepositoryURL + "/" + constants.CDNAPIPrefix + "/ref/-/stream/stable/v1.0.0/cli/info.json",
|
||||
},
|
||||
}
|
||||
|
||||
for name, tc := range testCases {
|
||||
t.Run(name, func(t *testing.T) {
|
||||
assert := assert.New(t)
|
||||
url, err := tc.info.URL()
|
||||
assert.NoError(err)
|
||||
assert.Equal(tc.wantURL, url)
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestCLIInfoValidate(t *testing.T) {
|
||||
testCases := map[string]struct {
|
||||
info CLIInfo
|
||||
wantErr bool
|
||||
}{
|
||||
"valid cli info": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "nightly",
|
||||
Version: "v1.0.0",
|
||||
Kubernetes: []string{"v1.26.1", "v1.3.3", "v1.32"},
|
||||
},
|
||||
},
|
||||
"invalid ref": {
|
||||
info: CLIInfo{
|
||||
Ref: "",
|
||||
Stream: "nightly",
|
||||
Version: "v1.0.0",
|
||||
Kubernetes: []string{"v1.26.1", "v1.3.3", "v1.32"},
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid stream": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "",
|
||||
Version: "v1.0.0",
|
||||
Kubernetes: []string{"v1.26.1", "v1.3.3", "v1.32"},
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid version": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "nightly",
|
||||
Version: "",
|
||||
Kubernetes: []string{"v1.26.1", "v1.3.3", "v1.32"},
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid k8s versions": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "nightly",
|
||||
Version: "v1.0.0",
|
||||
Kubernetes: []string{"1", "", "1.32"},
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"multiple errors": {
|
||||
info: CLIInfo{
|
||||
Ref: "",
|
||||
Stream: "",
|
||||
Version: "",
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
}
|
||||
|
||||
for name, tc := range testCases {
|
||||
t.Run(name, func(t *testing.T) {
|
||||
assert := assert.New(t)
|
||||
err := tc.info.Validate()
|
||||
|
||||
if tc.wantErr {
|
||||
assert.Error(err)
|
||||
} else {
|
||||
assert.NoError(err)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
func TestCLIInfoValidateRequest(t *testing.T) {
|
||||
testCases := map[string]struct {
|
||||
info CLIInfo
|
||||
wantErr bool
|
||||
}{
|
||||
"valid cli info": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "nightly",
|
||||
Version: "v1.0.0",
|
||||
},
|
||||
},
|
||||
"invalid ref": {
|
||||
info: CLIInfo{
|
||||
Ref: "",
|
||||
Stream: "nightly",
|
||||
Version: "v1.0.0",
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid stream": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "",
|
||||
Version: "v1.0.0",
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid version": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "nightly",
|
||||
Version: "",
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid k8s versions": {
|
||||
info: CLIInfo{
|
||||
Ref: "test-ref",
|
||||
Stream: "nightly",
|
||||
Version: "v1.0.0",
|
||||
Kubernetes: []string{"v1.26.1", "v1.3.3", "v1.32"},
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"multiple errors": {
|
||||
info: CLIInfo{
|
||||
Ref: "",
|
||||
Stream: "",
|
||||
Version: "",
|
||||
Kubernetes: []string{"v1.26.1", "v1.3.3", "v1.32"},
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
}
|
||||
|
||||
for name, tc := range testCases {
|
||||
t.Run(name, func(t *testing.T) {
|
||||
assert := assert.New(t)
|
||||
err := tc.info.ValidateRequest()
|
||||
|
||||
if tc.wantErr {
|
||||
assert.Error(err)
|
||||
} else {
|
||||
assert.NoError(err)
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
@ -49,6 +49,11 @@ func (f *Fetcher) FetchImageInfo(ctx context.Context, imageInfo versionsapi.Imag
|
||||
return fetch(ctx, f.httpc, imageInfo)
|
||||
}
|
||||
|
||||
// FetchCLIInfo fetches the given cli info from the versions API.
|
||||
func (f *Fetcher) FetchCLIInfo(ctx context.Context, cliInfo versionsapi.CLIInfo) (versionsapi.CLIInfo, error) {
|
||||
return fetch(ctx, f.httpc, cliInfo)
|
||||
}
|
||||
|
||||
type apiObject interface {
|
||||
ValidateRequest() error
|
||||
Validate() error
|
||||
|
@ -167,6 +167,8 @@ const (
|
||||
VersionKindUnknown VersionKind = iota
|
||||
// VersionKindImage is the kind for image versions.
|
||||
VersionKindImage
|
||||
// VersionKindCLI is the kind for CLI versions.
|
||||
VersionKindCLI
|
||||
)
|
||||
|
||||
// MarshalJSON marshals the VersionKind to JSON.
|
||||
@ -189,6 +191,8 @@ func (k VersionKind) String() string {
|
||||
switch k {
|
||||
case VersionKindImage:
|
||||
return "image"
|
||||
case VersionKindCLI:
|
||||
return "cli"
|
||||
default:
|
||||
return "unknown"
|
||||
}
|
||||
@ -199,6 +203,8 @@ func VersionKindFromString(s string) VersionKind {
|
||||
switch strings.ToLower(s) {
|
||||
case "image":
|
||||
return VersionKindImage
|
||||
case "cli":
|
||||
return VersionKindCLI
|
||||
default:
|
||||
return VersionKindUnknown
|
||||
}
|
||||
|
@ -41,16 +41,41 @@ func TestNewVersionFromShortPath(t *testing.T) {
|
||||
Kind: VersionKindImage,
|
||||
},
|
||||
},
|
||||
"stable release cli": {
|
||||
path: "v9.9.9",
|
||||
kind: VersionKindCLI,
|
||||
wantVer: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
},
|
||||
"release debug cli": {
|
||||
path: "stream/debug/v9.9.9",
|
||||
kind: VersionKindCLI,
|
||||
wantVer: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "debug",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
},
|
||||
"unknown kind": {
|
||||
path: "v9.9.9",
|
||||
kind: VersionKindUnknown,
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid path": {
|
||||
"invalid path image": {
|
||||
path: "va.b.c",
|
||||
kind: VersionKindImage,
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid path cli": {
|
||||
path: "va.b.c",
|
||||
kind: VersionKindCLI,
|
||||
wantErr: true,
|
||||
},
|
||||
}
|
||||
|
||||
for name, tc := range testCases {
|
||||
@ -100,6 +125,33 @@ func TestVersionShortPath(t *testing.T) {
|
||||
},
|
||||
want: "ref/foo/stream/debug/v9.9.9",
|
||||
},
|
||||
"stable release cli": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
want: "v9.9.9",
|
||||
},
|
||||
"release debug cli": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "debug",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
want: "stream/debug/v9.9.9",
|
||||
},
|
||||
"branch cli": {
|
||||
ver: Version{
|
||||
Ref: "foo",
|
||||
Stream: "debug",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
want: "ref/foo/stream/debug/v9.9.9",
|
||||
},
|
||||
}
|
||||
|
||||
for name, tc := range testCases {
|
||||
@ -117,7 +169,7 @@ func TestVersionValidate(t *testing.T) {
|
||||
ver Version
|
||||
wantErr bool
|
||||
}{
|
||||
"valid": {
|
||||
"valid image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
@ -125,7 +177,7 @@ func TestVersionValidate(t *testing.T) {
|
||||
Kind: VersionKindImage,
|
||||
},
|
||||
},
|
||||
"invalid ref": {
|
||||
"invalid ref image": {
|
||||
ver: Version{
|
||||
Ref: "foo/bar",
|
||||
Stream: "stable",
|
||||
@ -134,7 +186,7 @@ func TestVersionValidate(t *testing.T) {
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid stream": {
|
||||
"invalid stream image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "foo/bar",
|
||||
@ -143,7 +195,7 @@ func TestVersionValidate(t *testing.T) {
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid version": {
|
||||
"invalid version image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
@ -152,12 +204,38 @@ func TestVersionValidate(t *testing.T) {
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid kind": {
|
||||
"valid cli": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindUnknown,
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
},
|
||||
"invalid ref cli": {
|
||||
ver: Version{
|
||||
Ref: "foo/bar",
|
||||
Stream: "stable",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid stream cli": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "foo/bar",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
"invalid version cli": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
Version: "v9.9.9/foo",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
wantErr: true,
|
||||
},
|
||||
@ -266,7 +344,7 @@ func TestVersionListPathURL(t *testing.T) {
|
||||
wantPath string
|
||||
wantURL string
|
||||
}{
|
||||
"release": {
|
||||
"release image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
@ -277,7 +355,7 @@ func TestVersionListPathURL(t *testing.T) {
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/stable/versions/major/v9/image.json",
|
||||
wantURL: constants.CDNRepositoryURL + "/" + constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/stable/versions/major/v9/image.json",
|
||||
},
|
||||
"release with minor": {
|
||||
"release with minor image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
@ -288,7 +366,7 @@ func TestVersionListPathURL(t *testing.T) {
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/stable/versions/minor/v9.9/image.json",
|
||||
wantURL: constants.CDNRepositoryURL + "/" + constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/stable/versions/minor/v9.9/image.json",
|
||||
},
|
||||
"release with patch": {
|
||||
"release with patch image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
@ -299,7 +377,7 @@ func TestVersionListPathURL(t *testing.T) {
|
||||
wantPath: "",
|
||||
wantURL: "",
|
||||
},
|
||||
"release with unknown": {
|
||||
"release with unknown image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
@ -310,7 +388,7 @@ func TestVersionListPathURL(t *testing.T) {
|
||||
wantPath: "",
|
||||
wantURL: "",
|
||||
},
|
||||
"release debug stream": {
|
||||
"release debug stream image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "debug",
|
||||
@ -321,7 +399,7 @@ func TestVersionListPathURL(t *testing.T) {
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/debug/versions/major/v9/image.json",
|
||||
wantURL: constants.CDNRepositoryURL + "/" + constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/debug/versions/major/v9/image.json",
|
||||
},
|
||||
"release debug stream with minor": {
|
||||
"release debug stream with minor image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "debug",
|
||||
@ -332,7 +410,7 @@ func TestVersionListPathURL(t *testing.T) {
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/debug/versions/minor/v9.9/image.json",
|
||||
wantURL: constants.CDNRepositoryURL + "/" + constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/debug/versions/minor/v9.9/image.json",
|
||||
},
|
||||
"branch ref": {
|
||||
"branch ref image": {
|
||||
ver: Version{
|
||||
Ref: "foo",
|
||||
Stream: "debug",
|
||||
@ -343,7 +421,7 @@ func TestVersionListPathURL(t *testing.T) {
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/foo/stream/debug/versions/major/v9/image.json",
|
||||
wantURL: constants.CDNRepositoryURL + "/" + constants.CDNAPIPrefix + "/ref/foo/stream/debug/versions/major/v9/image.json",
|
||||
},
|
||||
"branch ref with minor": {
|
||||
"branch ref with minor image": {
|
||||
ver: Version{
|
||||
Ref: "foo",
|
||||
Stream: "debug",
|
||||
@ -378,7 +456,7 @@ func TestVersionArtifactPathURL(t *testing.T) {
|
||||
ver Version
|
||||
wantPath string
|
||||
}{
|
||||
"release": {
|
||||
"release image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
@ -387,7 +465,7 @@ func TestVersionArtifactPathURL(t *testing.T) {
|
||||
},
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/stable/v9.9.9",
|
||||
},
|
||||
"release debug stream": {
|
||||
"release debug stream image": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "debug",
|
||||
@ -396,7 +474,7 @@ func TestVersionArtifactPathURL(t *testing.T) {
|
||||
},
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/debug/v9.9.9",
|
||||
},
|
||||
"branch ref": {
|
||||
"branch ref image": {
|
||||
ver: Version{
|
||||
Ref: "foo",
|
||||
Stream: "debug",
|
||||
@ -405,6 +483,33 @@ func TestVersionArtifactPathURL(t *testing.T) {
|
||||
},
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/foo/stream/debug/v9.9.9",
|
||||
},
|
||||
"release cli": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "stable",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/stable/v9.9.9",
|
||||
},
|
||||
"release debug stream cli": {
|
||||
ver: Version{
|
||||
Ref: ReleaseRef,
|
||||
Stream: "debug",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/" + ReleaseRef + "/stream/debug/v9.9.9",
|
||||
},
|
||||
"branch ref cli": {
|
||||
ver: Version{
|
||||
Ref: "foo",
|
||||
Stream: "debug",
|
||||
Version: "v9.9.9",
|
||||
Kind: VersionKindCLI,
|
||||
},
|
||||
wantPath: constants.CDNAPIPrefix + "/ref/foo/stream/debug/v9.9.9",
|
||||
},
|
||||
}
|
||||
|
||||
for name, tc := range testCases {
|
||||
@ -422,6 +527,7 @@ func TestVersionArtifactPathURL(t *testing.T) {
|
||||
func TestVersionKindUnMarshalJson(t *testing.T) {
|
||||
testCases := map[string]VersionKind{
|
||||
`"image"`: VersionKindImage,
|
||||
`"cli"`: VersionKindCLI,
|
||||
`"unknown"`: VersionKindUnknown,
|
||||
}
|
||||
|
||||
@ -444,6 +550,7 @@ func TestVersionKindUnMarshalJson(t *testing.T) {
|
||||
func TestVersionKindFromString(t *testing.T) {
|
||||
testCases := map[string]VersionKind{
|
||||
"image": VersionKindImage,
|
||||
"cli": VersionKindCLI,
|
||||
"unknown": VersionKindUnknown,
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user