Skip to content
This repository was archived by the owner on Aug 30, 2024. It is now read-only.

Commit 258f3e1

Browse files
authored
Add registry operations to coder-sdk (#178)
1 parent 6df7494 commit 258f3e1

File tree

3 files changed

+114
-1
lines changed

3 files changed

+114
-1
lines changed

ci/integration/envs_test.go

+60
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import (
55
"fmt"
66
"math"
77
"net/url"
8+
"os"
89
"regexp"
910
"testing"
1011
"time"
@@ -36,6 +37,61 @@ func cleanupEnv(t *testing.T, client *coder.Client, envID string) func() {
3637
}
3738
}
3839

40+
// this is a stopgap until we have support for a `coder images` subcommand
41+
// until then, we want can use the *coder.Client to ensure our integration tests
42+
// work on fresh deployments.
43+
func ensureImageImported(ctx context.Context, t *testing.T, client *coder.Client, img string) {
44+
orgs, err := client.Organizations(ctx)
45+
assert.Success(t, "get orgs", err)
46+
47+
var org *coder.Organization
48+
search:
49+
for _, o := range orgs {
50+
for _, m := range o.Members {
51+
if m.Email == os.Getenv("CODER_EMAIL") {
52+
o := o
53+
org = &o
54+
break search
55+
}
56+
}
57+
}
58+
if org == nil {
59+
slogtest.Fatal(t, "failed to find org of current user")
60+
return // help the linter out a bit
61+
}
62+
63+
registries, err := client.Registries(ctx, org.ID)
64+
assert.Success(t, "get registries", err)
65+
66+
var dockerhubID string
67+
for _, r := range registries {
68+
if r.Registry == "index.docker.io" {
69+
dockerhubID = r.ID
70+
}
71+
}
72+
assert.True(t, "docker hub registry found", dockerhubID != "")
73+
74+
imgs, err := client.OrganizationImages(ctx, org.ID)
75+
assert.Success(t, "get org images", err)
76+
found := false
77+
for _, i := range imgs {
78+
if i.Repository == img {
79+
found = true
80+
}
81+
}
82+
if !found {
83+
// ignore this error for now as it causes a race with other parallel tests
84+
_, _ = client.ImportImage(ctx, org.ID, coder.ImportImageReq{
85+
RegistryID: &dockerhubID,
86+
Repository: img,
87+
Tag: "latest",
88+
DefaultCPUCores: 2.5,
89+
DefaultDiskGB: 22,
90+
DefaultMemoryGB: 3,
91+
})
92+
}
93+
}
94+
3995
func TestEnvsCLI(t *testing.T) {
4096
t.Parallel()
4197

@@ -68,6 +124,8 @@ func TestEnvsCLI(t *testing.T) {
68124
tcli.Error(),
69125
)
70126

127+
ensureImageImported(ctx, t, client, "ubuntu")
128+
71129
name := randString(10)
72130
cpu := 2.3
73131
c.Run(ctx, fmt.Sprintf("coder envs create %s --image ubuntu --cpu %f", name, cpu)).Assert(t,
@@ -103,6 +161,8 @@ func TestEnvsCLI(t *testing.T) {
103161
headlessLogin(ctx, t, c)
104162
client := cleanupClient(ctx, t)
105163

164+
ensureImageImported(ctx, t, client, "ubuntu")
165+
106166
name := randString(10)
107167
c.Run(ctx, fmt.Sprintf("coder envs create %s --image ubuntu --follow", name)).Assert(t,
108168
tcli.Success(),

coder-sdk/registries.go

+53
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
package coder
2+
3+
import (
4+
"context"
5+
"net/http"
6+
"time"
7+
)
8+
9+
// Registry defines an image registry configuration.
10+
type Registry struct {
11+
ID string `json:"id"`
12+
OrganizationID string `json:"organization_id"`
13+
FriendlyName string `json:"friendly_name"`
14+
Registry string `json:"registry"`
15+
CreatedAt time.Time `json:"created_at"`
16+
UpdatedAt time.Time `json:"updated_at"`
17+
}
18+
19+
// Registries fetches all registries in an organization.
20+
func (c Client) Registries(ctx context.Context, orgID string) ([]Registry, error) {
21+
var r []Registry
22+
if err := c.requestBody(ctx, http.MethodGet, "/api/orgs/"+orgID+"/registries", nil, &r); err != nil {
23+
return nil, err
24+
}
25+
return r, nil
26+
}
27+
28+
// RegistryByID fetches a registry resource by its ID.
29+
func (c Client) RegistryByID(ctx context.Context, orgID, registryID string) (*Registry, error) {
30+
var r Registry
31+
if err := c.requestBody(ctx, http.MethodGet, "/api/orgs/"+orgID+"/registries/"+registryID, nil, &r); err != nil {
32+
return nil, err
33+
}
34+
return &r, nil
35+
}
36+
37+
// UpdateRegistryReq defines the requests parameters for a partial update of a registry resource.
38+
type UpdateRegistryReq struct {
39+
Registry *string `json:"registry"`
40+
FriendlyName *string `json:"friendly_name"`
41+
Username *string `json:"username"`
42+
Password *string `json:"password"`
43+
}
44+
45+
// UpdateRegistry applies a partial update to a registry resource.
46+
func (c Client) UpdateRegistry(ctx context.Context, orgID, registryID string, req UpdateRegistryReq) error {
47+
return c.requestBody(ctx, http.MethodPatch, "/api/orgs/"+orgID+"/registries/"+registryID, req, nil)
48+
}
49+
50+
// DeleteRegistry deletes a registry resource by its ID.
51+
func (c Client) DeleteRegistry(ctx context.Context, orgID, registryID string) error {
52+
return c.requestBody(ctx, http.MethodDelete, "/api/orgs/"+orgID+"/registries/"+registryID, nil, nil)
53+
}

internal/cmd/envs.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -62,7 +62,7 @@ func lsEnvsCommand(user *string) *cobra.Command {
6262
}
6363
if len(envs) < 1 {
6464
clog.LogInfo("no environments found")
65-
return nil
65+
envs = []coder.Environment{} // ensures that json output still marshals
6666
}
6767

6868
switch outputFmt {

0 commit comments

Comments
 (0)