feat: app sharing (now open source!) (#4378)

This commit is contained in:
Dean Sheather
2022-10-15 02:46:38 +10:00
committed by GitHub
parent 19d7281daf
commit d898737d6d
55 changed files with 1069 additions and 412 deletions
+38 -18
View File
@@ -13,13 +13,14 @@ import (
type APIKey struct {
ID string `json:"id" validate:"required"`
// NOTE: do not ever return the HashedSecret
UserID uuid.UUID `json:"user_id" validate:"required"`
LastUsed time.Time `json:"last_used" validate:"required"`
ExpiresAt time.Time `json:"expires_at" validate:"required"`
CreatedAt time.Time `json:"created_at" validate:"required"`
UpdatedAt time.Time `json:"updated_at" validate:"required"`
LoginType LoginType `json:"login_type" validate:"required"`
LifetimeSeconds int64 `json:"lifetime_seconds" validate:"required"`
UserID uuid.UUID `json:"user_id" validate:"required"`
LastUsed time.Time `json:"last_used" validate:"required"`
ExpiresAt time.Time `json:"expires_at" validate:"required"`
CreatedAt time.Time `json:"created_at" validate:"required"`
UpdatedAt time.Time `json:"updated_at" validate:"required"`
LoginType LoginType `json:"login_type" validate:"required"`
Scope APIKeyScope `json:"scope" validate:"required"`
LifetimeSeconds int64 `json:"lifetime_seconds" validate:"required"`
}
type LoginType string
@@ -31,32 +32,51 @@ const (
LoginTypeToken LoginType = "token"
)
type APIKeyScope string
const (
APIKeyScopeAll APIKeyScope = "all"
APIKeyScopeApplicationConnect APIKeyScope = "application_connect"
)
type CreateTokenRequest struct {
Scope APIKeyScope `json:"scope"`
}
// GenerateAPIKeyResponse contains an API key for a user.
type GenerateAPIKeyResponse struct {
Key string `json:"key"`
}
// CreateToken generates an API key that doesn't expire.
func (c *Client) CreateToken(ctx context.Context, userID string) (*GenerateAPIKeyResponse, error) {
res, err := c.Request(ctx, http.MethodPost, fmt.Sprintf("/api/v2/users/%s/keys/tokens", userID), nil)
func (c *Client) CreateToken(ctx context.Context, userID string, req CreateTokenRequest) (GenerateAPIKeyResponse, error) {
res, err := c.Request(ctx, http.MethodPost, fmt.Sprintf("/api/v2/users/%s/keys/tokens", userID), req)
if err != nil {
return nil, err
return GenerateAPIKeyResponse{}, err
}
defer res.Body.Close()
if res.StatusCode > http.StatusCreated {
return nil, readBodyAsError(res)
return GenerateAPIKeyResponse{}, readBodyAsError(res)
}
apiKey := &GenerateAPIKeyResponse{}
return apiKey, json.NewDecoder(res.Body).Decode(apiKey)
var apiKey GenerateAPIKeyResponse
return apiKey, json.NewDecoder(res.Body).Decode(&apiKey)
}
// CreateAPIKey generates an API key for the user ID provided.
func (c *Client) CreateAPIKey(ctx context.Context, user string) (*GenerateAPIKeyResponse, error) {
// DEPRECATED: use CreateToken instead.
func (c *Client) CreateAPIKey(ctx context.Context, user string) (GenerateAPIKeyResponse, error) {
res, err := c.Request(ctx, http.MethodPost, fmt.Sprintf("/api/v2/users/%s/keys", user), nil)
if err != nil {
return nil, err
return GenerateAPIKeyResponse{}, err
}
defer res.Body.Close()
if res.StatusCode > http.StatusCreated {
return nil, readBodyAsError(res)
return GenerateAPIKeyResponse{}, readBodyAsError(res)
}
apiKey := &GenerateAPIKeyResponse{}
return apiKey, json.NewDecoder(res.Body).Decode(apiKey)
var apiKey GenerateAPIKeyResponse
return apiKey, json.NewDecoder(res.Body).Decode(&apiKey)
}
// GetTokens list machine API keys.
-5
View File
@@ -96,11 +96,6 @@ type LoginWithPasswordResponse struct {
SessionToken string `json:"session_token" validate:"required"`
}
// GenerateAPIKeyResponse contains an API key for a user.
type GenerateAPIKeyResponse struct {
Key string `json:"key"`
}
type CreateOrganizationRequest struct {
Name string `json:"name" validate:"required,username"`
}
+10 -1
View File
@@ -13,6 +13,14 @@ const (
WorkspaceAppHealthUnhealthy WorkspaceAppHealth = "unhealthy"
)
type WorkspaceAppSharingLevel string
const (
WorkspaceAppSharingLevelOwner WorkspaceAppSharingLevel = "owner"
WorkspaceAppSharingLevelAuthenticated WorkspaceAppSharingLevel = "authenticated"
WorkspaceAppSharingLevelPublic WorkspaceAppSharingLevel = "public"
)
type WorkspaceApp struct {
ID uuid.UUID `json:"id"`
// Name is a unique identifier attached to an agent.
@@ -25,7 +33,8 @@ type WorkspaceApp struct {
// `coder server` or via a hostname-based dev URL. If this is set to true
// and there is no app wildcard configured on the server, the app will not
// be accessible in the UI.
Subdomain bool `json:"subdomain"`
Subdomain bool `json:"subdomain"`
SharingLevel WorkspaceAppSharingLevel `json:"sharing_level"`
// Healthcheck specifies the configuration for checking app health.
Healthcheck Healthcheck `json:"healthcheck"`
Health WorkspaceAppHealth `json:"health"`