feat: Show custom resource icons in the UI (#4020)

This commit is contained in:
Bruno Quaresma
2022-09-13 11:32:59 -03:00
committed by GitHub
parent 83c35bb916
commit 214e59452f
60 changed files with 282 additions and 220 deletions

View File

@ -1801,6 +1801,7 @@ func (q *fakeQuerier) InsertWorkspaceResource(_ context.Context, arg database.In
Type: arg.Type, Type: arg.Type,
Name: arg.Name, Name: arg.Name,
Hide: arg.Hide, Hide: arg.Hide,
Icon: arg.Icon,
} }
q.provisionerJobResources = append(q.provisionerJobResources, resource) q.provisionerJobResources = append(q.provisionerJobResources, resource)
return resource, nil return resource, nil

View File

@ -368,7 +368,8 @@ CREATE TABLE workspace_resources (
transition workspace_transition NOT NULL, transition workspace_transition NOT NULL,
type character varying(192) NOT NULL, type character varying(192) NOT NULL,
name character varying(64) NOT NULL, name character varying(64) NOT NULL,
hide boolean DEFAULT false NOT NULL hide boolean DEFAULT false NOT NULL,
icon character varying(256) DEFAULT ''::character varying NOT NULL
); );
CREATE TABLE workspaces ( CREATE TABLE workspaces (

View File

@ -0,0 +1,2 @@
ALTER TABLE workspace_resources
DROP COLUMN icon;

View File

@ -0,0 +1,2 @@
ALTER TABLE workspace_resources
ADD COLUMN icon VARCHAR(256) NOT NULL DEFAULT ''

View File

@ -588,6 +588,7 @@ type WorkspaceResource struct {
Type string `db:"type" json:"type"` Type string `db:"type" json:"type"`
Name string `db:"name" json:"name"` Name string `db:"name" json:"name"`
Hide bool `db:"hide" json:"hide"` Hide bool `db:"hide" json:"hide"`
Icon string `db:"icon" json:"icon"`
} }
type WorkspaceResourceMetadatum struct { type WorkspaceResourceMetadatum struct {

View File

@ -4356,7 +4356,7 @@ func (q *sqlQuerier) UpdateWorkspaceBuildByID(ctx context.Context, arg UpdateWor
const getWorkspaceResourceByID = `-- name: GetWorkspaceResourceByID :one const getWorkspaceResourceByID = `-- name: GetWorkspaceResourceByID :one
SELECT SELECT
id, created_at, job_id, transition, type, name, hide id, created_at, job_id, transition, type, name, hide, icon
FROM FROM
workspace_resources workspace_resources
WHERE WHERE
@ -4374,6 +4374,7 @@ func (q *sqlQuerier) GetWorkspaceResourceByID(ctx context.Context, id uuid.UUID)
&i.Type, &i.Type,
&i.Name, &i.Name,
&i.Hide, &i.Hide,
&i.Icon,
) )
return i, err return i, err
} }
@ -4488,7 +4489,7 @@ func (q *sqlQuerier) GetWorkspaceResourceMetadataCreatedAfter(ctx context.Contex
const getWorkspaceResourcesByJobID = `-- name: GetWorkspaceResourcesByJobID :many const getWorkspaceResourcesByJobID = `-- name: GetWorkspaceResourcesByJobID :many
SELECT SELECT
id, created_at, job_id, transition, type, name, hide id, created_at, job_id, transition, type, name, hide, icon
FROM FROM
workspace_resources workspace_resources
WHERE WHERE
@ -4512,6 +4513,7 @@ func (q *sqlQuerier) GetWorkspaceResourcesByJobID(ctx context.Context, jobID uui
&i.Type, &i.Type,
&i.Name, &i.Name,
&i.Hide, &i.Hide,
&i.Icon,
); err != nil { ); err != nil {
return nil, err return nil, err
} }
@ -4527,7 +4529,7 @@ func (q *sqlQuerier) GetWorkspaceResourcesByJobID(ctx context.Context, jobID uui
} }
const getWorkspaceResourcesCreatedAfter = `-- name: GetWorkspaceResourcesCreatedAfter :many const getWorkspaceResourcesCreatedAfter = `-- name: GetWorkspaceResourcesCreatedAfter :many
SELECT id, created_at, job_id, transition, type, name, hide FROM workspace_resources WHERE created_at > $1 SELECT id, created_at, job_id, transition, type, name, hide, icon FROM workspace_resources WHERE created_at > $1
` `
func (q *sqlQuerier) GetWorkspaceResourcesCreatedAfter(ctx context.Context, createdAt time.Time) ([]WorkspaceResource, error) { func (q *sqlQuerier) GetWorkspaceResourcesCreatedAfter(ctx context.Context, createdAt time.Time) ([]WorkspaceResource, error) {
@ -4547,6 +4549,7 @@ func (q *sqlQuerier) GetWorkspaceResourcesCreatedAfter(ctx context.Context, crea
&i.Type, &i.Type,
&i.Name, &i.Name,
&i.Hide, &i.Hide,
&i.Icon,
); err != nil { ); err != nil {
return nil, err return nil, err
} }
@ -4563,9 +4566,9 @@ func (q *sqlQuerier) GetWorkspaceResourcesCreatedAfter(ctx context.Context, crea
const insertWorkspaceResource = `-- name: InsertWorkspaceResource :one const insertWorkspaceResource = `-- name: InsertWorkspaceResource :one
INSERT INTO INSERT INTO
workspace_resources (id, created_at, job_id, transition, type, name, hide) workspace_resources (id, created_at, job_id, transition, type, name, hide, icon)
VALUES VALUES
($1, $2, $3, $4, $5, $6, $7) RETURNING id, created_at, job_id, transition, type, name, hide ($1, $2, $3, $4, $5, $6, $7, $8) RETURNING id, created_at, job_id, transition, type, name, hide, icon
` `
type InsertWorkspaceResourceParams struct { type InsertWorkspaceResourceParams struct {
@ -4576,6 +4579,7 @@ type InsertWorkspaceResourceParams struct {
Type string `db:"type" json:"type"` Type string `db:"type" json:"type"`
Name string `db:"name" json:"name"` Name string `db:"name" json:"name"`
Hide bool `db:"hide" json:"hide"` Hide bool `db:"hide" json:"hide"`
Icon string `db:"icon" json:"icon"`
} }
func (q *sqlQuerier) InsertWorkspaceResource(ctx context.Context, arg InsertWorkspaceResourceParams) (WorkspaceResource, error) { func (q *sqlQuerier) InsertWorkspaceResource(ctx context.Context, arg InsertWorkspaceResourceParams) (WorkspaceResource, error) {
@ -4587,6 +4591,7 @@ func (q *sqlQuerier) InsertWorkspaceResource(ctx context.Context, arg InsertWork
arg.Type, arg.Type,
arg.Name, arg.Name,
arg.Hide, arg.Hide,
arg.Icon,
) )
var i WorkspaceResource var i WorkspaceResource
err := row.Scan( err := row.Scan(
@ -4597,6 +4602,7 @@ func (q *sqlQuerier) InsertWorkspaceResource(ctx context.Context, arg InsertWork
&i.Type, &i.Type,
&i.Name, &i.Name,
&i.Hide, &i.Hide,
&i.Icon,
) )
return i, err return i, err
} }

View File

@ -19,9 +19,9 @@ SELECT * FROM workspace_resources WHERE created_at > $1;
-- name: InsertWorkspaceResource :one -- name: InsertWorkspaceResource :one
INSERT INTO INSERT INTO
workspace_resources (id, created_at, job_id, transition, type, name, hide) workspace_resources (id, created_at, job_id, transition, type, name, hide, icon)
VALUES VALUES
($1, $2, $3, $4, $5, $6, $7) RETURNING *; ($1, $2, $3, $4, $5, $6, $7, $8) RETURNING *;
-- name: GetWorkspaceResourceMetadataByResourceID :many -- name: GetWorkspaceResourceMetadataByResourceID :many
SELECT SELECT

View File

@ -753,6 +753,7 @@ func insertWorkspaceResource(ctx context.Context, db database.Store, jobID uuid.
Type: protoResource.Type, Type: protoResource.Type,
Name: protoResource.Name, Name: protoResource.Name,
Hide: protoResource.Hide, Hide: protoResource.Hide,
Icon: protoResource.Icon,
}) })
if err != nil { if err != nil {
return xerrors.Errorf("insert provisioner job resource %q: %w", protoResource.Name, err) return xerrors.Errorf("insert provisioner job resource %q: %w", protoResource.Name, err)

View File

@ -707,6 +707,7 @@ func convertWorkspaceResource(resource database.WorkspaceResource, agents []code
Type: resource.Type, Type: resource.Type,
Name: resource.Name, Name: resource.Name,
Hide: resource.Hide, Hide: resource.Hide,
Icon: resource.Icon,
Agents: agents, Agents: agents,
Metadata: convertedMetadata, Metadata: convertedMetadata,
} }

View File

@ -27,6 +27,7 @@ func TestWorkspaceResource(t *testing.T) {
Resources: []*proto.Resource{{ Resources: []*proto.Resource{{
Name: "beta", Name: "beta",
Type: "example", Type: "example",
Icon: "/icon/server.svg",
Agents: []*proto.Agent{{ Agents: []*proto.Agent{{
Id: "something", Id: "something",
Name: "b", Name: "b",
@ -60,9 +61,11 @@ func TestWorkspaceResource(t *testing.T) {
resource, err := client.WorkspaceResource(ctx, resources[1].ID) resource, err := client.WorkspaceResource(ctx, resources[1].ID)
require.NoError(t, err) require.NoError(t, err)
require.Len(t, resource.Agents, 2) require.Len(t, resource.Agents, 2)
// Ensure it's sorted alphabetically! // Ensure agents are sorted alphabetically!
require.Equal(t, "a", resource.Agents[0].Name) require.Equal(t, "a", resource.Agents[0].Name)
require.Equal(t, "b", resource.Agents[1].Name) require.Equal(t, "b", resource.Agents[1].Name)
// Ensure Icon is present
require.Equal(t, "/icon/server.svg", resources[1].Icon)
}) })
t.Run("Apps", func(t *testing.T) { t.Run("Apps", func(t *testing.T) {

View File

@ -26,6 +26,7 @@ type WorkspaceResource struct {
Type string `json:"type"` Type string `json:"type"`
Name string `json:"name"` Name string `json:"name"`
Hide bool `json:"hide"` Hide bool `json:"hide"`
Icon string `json:"icon"`
Agents []WorkspaceAgent `json:"agents,omitempty"` Agents []WorkspaceAgent `json:"agents,omitempty"`
Metadata []WorkspaceResourceMetadata `json:"metadata,omitempty"` Metadata []WorkspaceResourceMetadata `json:"metadata,omitempty"`
} }

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
} }
} }

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
} }
} }

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
azurerm = { azurerm = {
source = "hashicorp/azurerm" source = "hashicorp/azurerm"

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
digitalocean = { digitalocean = {
source = "digitalocean/digitalocean" source = "digitalocean/digitalocean"

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
docker = { docker = {
source = "kreuzwerker/docker" source = "kreuzwerker/docker"

View File

@ -3,7 +3,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
docker = { docker = {
source = "kreuzwerker/docker" source = "kreuzwerker/docker"

View File

@ -9,7 +9,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
docker = { docker = {
source = "kreuzwerker/docker" source = "kreuzwerker/docker"

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
docker = { docker = {
source = "kreuzwerker/docker" source = "kreuzwerker/docker"

View File

@ -6,7 +6,7 @@ terraform {
} }
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "~> 0.4.9" version = "0.4.11"
} }
} }
} }

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
google = { google = {
source = "hashicorp/google" source = "hashicorp/google"

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
google = { google = {
source = "hashicorp/google" source = "hashicorp/google"

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
google = { google = {
source = "hashicorp/google" source = "hashicorp/google"

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.9" version = "0.4.11"
} }
kubernetes = { kubernetes = {
source = "hashicorp/kubernetes" source = "hashicorp/kubernetes"

View File

@ -37,6 +37,7 @@ type agentAppAttributes struct {
type metadataAttributes struct { type metadataAttributes struct {
ResourceID string `mapstructure:"resource_id"` ResourceID string `mapstructure:"resource_id"`
Hide bool `mapstructure:"hide"` Hide bool `mapstructure:"hide"`
Icon string `mapstructure:"icon"`
Items []metadataItem `mapstructure:"item"` Items []metadataItem `mapstructure:"item"`
} }
@ -237,6 +238,7 @@ func ConvertResources(module *tfjson.StateModule, rawGraph string) ([]*proto.Res
// Associate metadata blocks with resources. // Associate metadata blocks with resources.
resourceMetadata := map[string][]*proto.Resource_Metadata{} resourceMetadata := map[string][]*proto.Resource_Metadata{}
resourceHidden := map[string]bool{} resourceHidden := map[string]bool{}
resourceIcon := map[string]string{}
for _, resource := range tfResourceByLabel { for _, resource := range tfResourceByLabel {
if resource.Type != "coder_metadata" { if resource.Type != "coder_metadata" {
continue continue
@ -295,6 +297,7 @@ func ConvertResources(module *tfjson.StateModule, rawGraph string) ([]*proto.Res
} }
resourceHidden[targetLabel] = attrs.Hide resourceHidden[targetLabel] = attrs.Hide
resourceIcon[targetLabel] = attrs.Icon
for _, item := range attrs.Items { for _, item := range attrs.Items {
resourceMetadata[targetLabel] = append(resourceMetadata[targetLabel], resourceMetadata[targetLabel] = append(resourceMetadata[targetLabel],
&proto.Resource_Metadata{ &proto.Resource_Metadata{
@ -325,6 +328,7 @@ func ConvertResources(module *tfjson.StateModule, rawGraph string) ([]*proto.Res
Type: resource.Type, Type: resource.Type,
Agents: agents, Agents: agents,
Hide: resourceHidden[label], Hide: resourceHidden[label],
Icon: resourceIcon[label],
Metadata: resourceMetadata[label], Metadata: resourceMetadata[label],
}) })
} }

View File

@ -121,6 +121,7 @@ func TestConvertResources(t *testing.T) {
Name: "about", Name: "about",
Type: "null_resource", Type: "null_resource",
Hide: true, Hide: true,
Icon: "/icon/server.svg",
Metadata: []*proto.Resource_Metadata{{ Metadata: []*proto.Resource_Metadata{{
Key: "hello", Key: "hello",
Value: "world", Value: "world",

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.10" version = "0.4.11"
} }
} }
} }

View File

@ -147,7 +147,7 @@
"coder": { "coder": {
"name": "coder", "name": "coder",
"full_name": "registry.terraform.io/coder/coder", "full_name": "registry.terraform.io/coder/coder",
"version_constraint": "0.4.10" "version_constraint": "0.4.11"
}, },
"module.module:null": { "module.module:null": {
"name": "null", "name": "null",

View File

@ -16,11 +16,11 @@
"auth": "token", "auth": "token",
"dir": null, "dir": null,
"env": null, "env": null,
"id": "ee0b689a-9785-4d72-923f-e2acf88d709b", "id": "f05ddf9e-106a-4669-bba8-5e2289bd891d",
"init_script": "", "init_script": "",
"os": "linux", "os": "linux",
"startup_script": null, "startup_script": null,
"token": "a295c68a-27af-4dc8-92cd-db154084cf30" "token": "ed4655b9-e917-44af-8706-a1215384a35f"
}, },
"sensitive_values": {} "sensitive_values": {}
} }
@ -44,7 +44,7 @@
"outputs": { "outputs": {
"script": "" "script": ""
}, },
"random": "410687191584620713" "random": "7640853885488752810"
}, },
"sensitive_values": { "sensitive_values": {
"inputs": {}, "inputs": {},
@ -59,7 +59,7 @@
"provider_name": "registry.terraform.io/hashicorp/null", "provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"id": "7780508472225873711", "id": "6481148597794195898",
"triggers": null "triggers": null
}, },
"sensitive_values": {}, "sensitive_values": {},

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.10" version = "0.4.11"
} }
} }
} }

View File

@ -125,7 +125,7 @@
"coder": { "coder": {
"name": "coder", "name": "coder",
"full_name": "registry.terraform.io/coder/coder", "full_name": "registry.terraform.io/coder/coder",
"version_constraint": "0.4.10" "version_constraint": "0.4.11"
}, },
"null": { "null": {
"name": "null", "name": "null",

View File

@ -16,11 +16,11 @@
"auth": "token", "auth": "token",
"dir": null, "dir": null,
"env": null, "env": null,
"id": "97baf22d-c3fc-4570-a025-58dd5235366f", "id": "fcd8018c-7e4a-4e92-855b-e02319ab051e",
"init_script": "", "init_script": "",
"os": "linux", "os": "linux",
"startup_script": null, "startup_script": null,
"token": "ae325f47-8fe4-436c-9787-7295eef26604" "token": "ad906408-0eb0-4844-83f7-0f5070427e1c"
}, },
"sensitive_values": {} "sensitive_values": {}
}, },
@ -32,7 +32,7 @@
"provider_name": "registry.terraform.io/hashicorp/null", "provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"id": "8957171845319631256", "id": "2672857180605476162",
"triggers": null "triggers": null
}, },
"sensitive_values": {}, "sensitive_values": {},
@ -49,7 +49,7 @@
"provider_name": "registry.terraform.io/hashicorp/null", "provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"id": "7521770950111838137", "id": "264584188140644760",
"triggers": null "triggers": null
}, },
"sensitive_values": {}, "sensitive_values": {},

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.10" version = "0.4.11"
} }
} }
} }

View File

@ -125,7 +125,7 @@
"coder": { "coder": {
"name": "coder", "name": "coder",
"full_name": "registry.terraform.io/coder/coder", "full_name": "registry.terraform.io/coder/coder",
"version_constraint": "0.4.10" "version_constraint": "0.4.11"
}, },
"null": { "null": {
"name": "null", "name": "null",

View File

@ -16,11 +16,11 @@
"auth": "token", "auth": "token",
"dir": null, "dir": null,
"env": null, "env": null,
"id": "75c43b92-2812-4a6b-9a40-16c124c3c2ff", "id": "e3df7d56-17ce-4d8a-9d4e-30ea41cc8a93",
"init_script": "", "init_script": "",
"os": "linux", "os": "linux",
"startup_script": null, "startup_script": null,
"token": "bf14e82d-7e8f-49b5-8e2a-fb84da4b6afa" "token": "1717f79d-2c72-440e-a5c6-e4b8c3fef084"
}, },
"sensitive_values": {} "sensitive_values": {}
}, },
@ -32,7 +32,7 @@
"provider_name": "registry.terraform.io/hashicorp/null", "provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"id": "5082348601033637104", "id": "2957375211969224115",
"triggers": null "triggers": null
}, },
"sensitive_values": {}, "sensitive_values": {},
@ -48,7 +48,7 @@
"provider_name": "registry.terraform.io/hashicorp/null", "provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"id": "135765900644760615", "id": "6924176854496195292",
"triggers": null "triggers": null
}, },
"sensitive_values": {}, "sensitive_values": {},

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.10" version = "0.4.11"
} }
} }
} }

View File

@ -126,7 +126,7 @@
"coder": { "coder": {
"name": "coder", "name": "coder",
"full_name": "registry.terraform.io/coder/coder", "full_name": "registry.terraform.io/coder/coder",
"version_constraint": "0.4.10" "version_constraint": "0.4.11"
}, },
"null": { "null": {
"name": "null", "name": "null",

View File

@ -16,11 +16,11 @@
"auth": "google-instance-identity", "auth": "google-instance-identity",
"dir": null, "dir": null,
"env": null, "env": null,
"id": "9112719f-1e11-41d0-8baf-7f92e94fb510", "id": "9a37096a-7f01-42cd-93d8-9f4572c94489",
"init_script": "", "init_script": "",
"os": "linux", "os": "linux",
"startup_script": null, "startup_script": null,
"token": "8d556c96-9010-4ae9-8993-69c01de97d24" "token": "7784ea1f-7fe5-463f-af8d-255c32d12992"
}, },
"sensitive_values": {} "sensitive_values": {}
}, },
@ -32,8 +32,8 @@
"provider_name": "registry.terraform.io/coder/coder", "provider_name": "registry.terraform.io/coder/coder",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"agent_id": "9112719f-1e11-41d0-8baf-7f92e94fb510", "agent_id": "9a37096a-7f01-42cd-93d8-9f4572c94489",
"id": "35efb5bc-da00-45e8-b38c-df4899417842", "id": "8ed448e2-51d7-4cc7-9e26-a3a77f252b1d",
"instance_id": "example" "instance_id": "example"
}, },
"sensitive_values": {}, "sensitive_values": {},
@ -49,7 +49,7 @@
"provider_name": "registry.terraform.io/hashicorp/null", "provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"id": "6105197068461821872", "id": "771742387122791362",
"triggers": null "triggers": null
}, },
"sensitive_values": {}, "sensitive_values": {},

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.10" version = "0.4.11"
} }
} }
} }

View File

@ -182,7 +182,7 @@
"coder": { "coder": {
"name": "coder", "name": "coder",
"full_name": "registry.terraform.io/coder/coder", "full_name": "registry.terraform.io/coder/coder",
"version_constraint": "0.4.10" "version_constraint": "0.4.11"
}, },
"null": { "null": {
"name": "null", "name": "null",

View File

@ -16,11 +16,11 @@
"auth": "token", "auth": "token",
"dir": null, "dir": null,
"env": null, "env": null,
"id": "0a714220-de27-4721-a6ab-d5c21c8e99b8", "id": "0c3c20d8-8a1d-4fc9-bc73-ed45ddad9a9d",
"init_script": "", "init_script": "",
"os": "linux", "os": "linux",
"startup_script": null, "startup_script": null,
"token": "d241aebd-6d75-4c06-a02e-74b41607345c" "token": "48b3f4c4-4bb9-477c-8d32-d1e14188e5f8"
}, },
"sensitive_values": {} "sensitive_values": {}
}, },
@ -36,11 +36,11 @@
"auth": "token", "auth": "token",
"dir": null, "dir": null,
"env": null, "env": null,
"id": "27567c6b-c52a-4c01-a6ad-368fddb36c9a", "id": "08e8ebc8-4660-47f0-acb5-6ca46747919d",
"init_script": "", "init_script": "",
"os": "darwin", "os": "darwin",
"startup_script": null, "startup_script": null,
"token": "eb5f4e5e-eb57-434c-a444-274b811afa30" "token": "827a1f01-a2d7-4794-ab73-8fd8442010d5"
}, },
"sensitive_values": {} "sensitive_values": {}
}, },
@ -56,11 +56,11 @@
"auth": "token", "auth": "token",
"dir": null, "dir": null,
"env": null, "env": null,
"id": "b689c633-e666-43e1-ac77-9522f187a098", "id": "50f52bd4-a52b-4c73-bf99-fe956913bca4",
"init_script": "", "init_script": "",
"os": "windows", "os": "windows",
"startup_script": null, "startup_script": null,
"token": "90a9c42e-df1f-4656-ac4c-c7f4ab06a269" "token": "159d6407-a913-4e05-8ba7-786d47a7e34b"
}, },
"sensitive_values": {} "sensitive_values": {}
}, },
@ -72,7 +72,7 @@
"provider_name": "registry.terraform.io/hashicorp/null", "provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"id": "7866048965316331550", "id": "2529387636030139440",
"triggers": null "triggers": null
}, },
"sensitive_values": {}, "sensitive_values": {},

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.10" version = "0.4.11"
} }
} }
} }

View File

@ -176,7 +176,7 @@
"coder": { "coder": {
"name": "coder", "name": "coder",
"full_name": "registry.terraform.io/coder/coder", "full_name": "registry.terraform.io/coder/coder",
"version_constraint": "0.4.10" "version_constraint": "0.4.11"
}, },
"null": { "null": {
"name": "null", "name": "null",

View File

@ -16,11 +16,11 @@
"auth": "token", "auth": "token",
"dir": null, "dir": null,
"env": null, "env": null,
"id": "04d74496-49a6-4757-b1b2-47e21840067e", "id": "3d4ee1d5-6413-4dc7-baec-2fa9dbd870ba",
"init_script": "", "init_script": "",
"os": "linux", "os": "linux",
"startup_script": null, "startup_script": null,
"token": "1417b29e-da8c-45fb-998d-fbec32069e8d" "token": "32e082d7-af02-42f1-a5bd-f6adc34220a1"
}, },
"sensitive_values": {} "sensitive_values": {}
}, },
@ -32,10 +32,10 @@
"provider_name": "registry.terraform.io/coder/coder", "provider_name": "registry.terraform.io/coder/coder",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"agent_id": "04d74496-49a6-4757-b1b2-47e21840067e", "agent_id": "3d4ee1d5-6413-4dc7-baec-2fa9dbd870ba",
"command": null, "command": null,
"icon": null, "icon": null,
"id": "0a5869ef-00d9-4a37-9f72-e0b2bf0d266b", "id": "90e045f9-19f1-4d8a-8021-be61c44ee54f",
"name": null, "name": null,
"relative_path": null, "relative_path": null,
"url": null "url": null
@ -53,10 +53,10 @@
"provider_name": "registry.terraform.io/coder/coder", "provider_name": "registry.terraform.io/coder/coder",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"agent_id": "04d74496-49a6-4757-b1b2-47e21840067e", "agent_id": "3d4ee1d5-6413-4dc7-baec-2fa9dbd870ba",
"command": null, "command": null,
"icon": null, "icon": null,
"id": "d525e0c1-b494-4911-8b17-8cfb2d248fbf", "id": "873026f8-3050-4b0b-bebf-41e13e5949bb",
"name": null, "name": null,
"relative_path": null, "relative_path": null,
"url": null "url": null
@ -74,7 +74,7 @@
"provider_name": "registry.terraform.io/hashicorp/null", "provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"id": "5711218402680555438", "id": "4447693752005094678",
"triggers": null "triggers": null
}, },
"sensitive_values": {}, "sensitive_values": {},

View File

@ -2,7 +2,7 @@ terraform {
required_providers { required_providers {
coder = { coder = {
source = "coder/coder" source = "coder/coder"
version = "0.4.10" version = "0.4.11"
} }
} }
} }
@ -17,6 +17,7 @@ resource "null_resource" "about" {}
resource "coder_metadata" "about_info" { resource "coder_metadata" "about_info" {
resource_id = null_resource.about.id resource_id = null_resource.about.id
hide = true hide = true
icon = "/icon/server.svg"
item { item {
key = "hello" key = "hello"
value = "world" value = "world"

View File

@ -30,6 +30,7 @@
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"hide": true, "hide": true,
"icon": "/icon/server.svg",
"item": [ "item": [
{ {
"key": "hello", "key": "hello",
@ -119,6 +120,7 @@
"before": null, "before": null,
"after": { "after": {
"hide": true, "hide": true,
"icon": "/icon/server.svg",
"item": [ "item": [
{ {
"key": "hello", "key": "hello",
@ -198,7 +200,7 @@
"coder": { "coder": {
"name": "coder", "name": "coder",
"full_name": "registry.terraform.io/coder/coder", "full_name": "registry.terraform.io/coder/coder",
"version_constraint": "0.4.10" "version_constraint": "0.4.11"
}, },
"null": { "null": {
"name": "null", "name": "null",
@ -233,6 +235,9 @@
"hide": { "hide": {
"constant_value": true "constant_value": true
}, },
"icon": {
"constant_value": "/icon/server.svg"
},
"item": [ "item": [
{ {
"key": { "key": {

View File

@ -16,11 +16,11 @@
"auth": "token", "auth": "token",
"dir": null, "dir": null,
"env": null, "env": null,
"id": "bf761056-4c83-4f36-98e9-fb15c4f3818f", "id": "09aac2a4-9d8e-43ef-83cb-34657db199f4",
"init_script": "", "init_script": "",
"os": "linux", "os": "linux",
"startup_script": null, "startup_script": null,
"token": "fcc945d1-ad27-47e5-9c31-aeb4ffd2dd67" "token": "a0f6b8af-8edc-447f-b6d2-67a60ecd2a77"
}, },
"sensitive_values": {} "sensitive_values": {}
}, },
@ -33,7 +33,8 @@
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"hide": true, "hide": true,
"id": "6f981e35-73a3-4478-8227-fed4643afd71", "icon": "/icon/server.svg",
"id": "a7f9cf03-de78-4d17-bcbb-21dc34c2d86a",
"item": [ "item": [
{ {
"is_null": false, "is_null": false,
@ -60,7 +61,7 @@
"value": "squirrel" "value": "squirrel"
} }
], ],
"resource_id": "3184975245680216434" "resource_id": "6209384655473556868"
}, },
"sensitive_values": { "sensitive_values": {
"item": [ "item": [
@ -82,7 +83,7 @@
"provider_name": "registry.terraform.io/hashicorp/null", "provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0, "schema_version": 0,
"values": { "values": {
"id": "3184975245680216434", "id": "6209384655473556868",
"triggers": null "triggers": null
}, },
"sensitive_values": {} "sensitive_values": {}

View File

@ -935,6 +935,7 @@ type Resource struct {
Agents []*Agent `protobuf:"bytes,3,rep,name=agents,proto3" json:"agents,omitempty"` Agents []*Agent `protobuf:"bytes,3,rep,name=agents,proto3" json:"agents,omitempty"`
Metadata []*Resource_Metadata `protobuf:"bytes,4,rep,name=metadata,proto3" json:"metadata,omitempty"` Metadata []*Resource_Metadata `protobuf:"bytes,4,rep,name=metadata,proto3" json:"metadata,omitempty"`
Hide bool `protobuf:"varint,5,opt,name=hide,proto3" json:"hide,omitempty"` Hide bool `protobuf:"varint,5,opt,name=hide,proto3" json:"hide,omitempty"`
Icon string `protobuf:"bytes,6,opt,name=icon,proto3" json:"icon,omitempty"`
} }
func (x *Resource) Reset() { func (x *Resource) Reset() {
@ -1004,6 +1005,13 @@ func (x *Resource) GetHide() bool {
return false return false
} }
func (x *Resource) GetIcon() string {
if x != nil {
return x.Icon
}
return ""
}
// Parse consumes source-code from a directory to produce inputs. // Parse consumes source-code from a directory to produce inputs.
type Parse struct { type Parse struct {
state protoimpl.MessageState state protoimpl.MessageState
@ -1880,7 +1888,7 @@ var file_provisionersdk_proto_provisioner_proto_rawDesc = []byte{
0x52, 0x03, 0x75, 0x72, 0x6c, 0x12, 0x12, 0x0a, 0x04, 0x69, 0x63, 0x6f, 0x6e, 0x18, 0x04, 0x20, 0x52, 0x03, 0x75, 0x72, 0x6c, 0x12, 0x12, 0x0a, 0x04, 0x69, 0x63, 0x6f, 0x6e, 0x18, 0x04, 0x20,
0x01, 0x28, 0x09, 0x52, 0x04, 0x69, 0x63, 0x6f, 0x6e, 0x12, 0x23, 0x0a, 0x0d, 0x72, 0x65, 0x6c, 0x01, 0x28, 0x09, 0x52, 0x04, 0x69, 0x63, 0x6f, 0x6e, 0x12, 0x23, 0x0a, 0x0d, 0x72, 0x65, 0x6c,
0x61, 0x74, 0x69, 0x76, 0x65, 0x5f, 0x70, 0x61, 0x74, 0x68, 0x18, 0x05, 0x20, 0x01, 0x28, 0x08, 0x61, 0x74, 0x69, 0x76, 0x65, 0x5f, 0x70, 0x61, 0x74, 0x68, 0x18, 0x05, 0x20, 0x01, 0x28, 0x08,
0x52, 0x0c, 0x72, 0x65, 0x6c, 0x61, 0x74, 0x69, 0x76, 0x65, 0x50, 0x61, 0x74, 0x68, 0x22, 0x99, 0x52, 0x0c, 0x72, 0x65, 0x6c, 0x61, 0x74, 0x69, 0x76, 0x65, 0x50, 0x61, 0x74, 0x68, 0x22, 0xad,
0x02, 0x0a, 0x08, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x6e, 0x02, 0x0a, 0x08, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x12, 0x12, 0x0a, 0x04, 0x6e,
0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12, 0x61, 0x6d, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x6e, 0x61, 0x6d, 0x65, 0x12,
0x12, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74, 0x12, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x74,
@ -1891,111 +1899,112 @@ var file_provisionersdk_proto_provisioner_proto_rawDesc = []byte{
0x0b, 0x32, 0x1e, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x0b, 0x32, 0x1e, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e,
0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x2e, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74,
0x61, 0x52, 0x08, 0x6d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x12, 0x12, 0x0a, 0x04, 0x68, 0x61, 0x52, 0x08, 0x6d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x12, 0x12, 0x0a, 0x04, 0x68,
0x69, 0x64, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x08, 0x52, 0x04, 0x68, 0x69, 0x64, 0x65, 0x1a, 0x69, 0x64, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x08, 0x52, 0x04, 0x68, 0x69, 0x64, 0x65, 0x12,
0x69, 0x0a, 0x08, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x12, 0x10, 0x0a, 0x03, 0x6b, 0x12, 0x0a, 0x04, 0x69, 0x63, 0x6f, 0x6e, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x04, 0x69,
0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x63, 0x6f, 0x6e, 0x1a, 0x69, 0x0a, 0x08, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x12,
0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x76, 0x61, 0x10, 0x0a, 0x03, 0x6b, 0x65, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x6b, 0x65,
0x6c, 0x75, 0x65, 0x12, 0x1c, 0x0a, 0x09, 0x73, 0x65, 0x6e, 0x73, 0x69, 0x74, 0x69, 0x76, 0x65, 0x79, 0x12, 0x14, 0x0a, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09,
0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x09, 0x73, 0x65, 0x6e, 0x73, 0x69, 0x74, 0x69, 0x76, 0x52, 0x05, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x1c, 0x0a, 0x09, 0x73, 0x65, 0x6e, 0x73, 0x69,
0x65, 0x12, 0x17, 0x0a, 0x07, 0x69, 0x73, 0x5f, 0x6e, 0x75, 0x6c, 0x6c, 0x18, 0x04, 0x20, 0x01, 0x74, 0x69, 0x76, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x08, 0x52, 0x09, 0x73, 0x65, 0x6e, 0x73,
0x28, 0x08, 0x52, 0x06, 0x69, 0x73, 0x4e, 0x75, 0x6c, 0x6c, 0x22, 0xfc, 0x01, 0x0a, 0x05, 0x50, 0x69, 0x74, 0x69, 0x76, 0x65, 0x12, 0x17, 0x0a, 0x07, 0x69, 0x73, 0x5f, 0x6e, 0x75, 0x6c, 0x6c,
0x61, 0x72, 0x73, 0x65, 0x1a, 0x27, 0x0a, 0x07, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x18, 0x04, 0x20, 0x01, 0x28, 0x08, 0x52, 0x06, 0x69, 0x73, 0x4e, 0x75, 0x6c, 0x6c, 0x22, 0xfc,
0x1c, 0x0a, 0x09, 0x64, 0x69, 0x72, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x79, 0x18, 0x01, 0x20, 0x01, 0x01, 0x0a, 0x05, 0x50, 0x61, 0x72, 0x73, 0x65, 0x1a, 0x27, 0x0a, 0x07, 0x52, 0x65, 0x71, 0x75,
0x28, 0x09, 0x52, 0x09, 0x64, 0x69, 0x72, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x79, 0x1a, 0x55, 0x0a, 0x65, 0x73, 0x74, 0x12, 0x1c, 0x0a, 0x09, 0x64, 0x69, 0x72, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x79,
0x08, 0x43, 0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x12, 0x49, 0x0a, 0x11, 0x70, 0x61, 0x72, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x64, 0x69, 0x72, 0x65, 0x63, 0x74, 0x6f, 0x72,
0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x5f, 0x73, 0x63, 0x68, 0x65, 0x6d, 0x61, 0x73, 0x18, 0x02, 0x79, 0x1a, 0x55, 0x0a, 0x08, 0x43, 0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x12, 0x49, 0x0a,
0x20, 0x03, 0x28, 0x0b, 0x32, 0x1c, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x11, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x5f, 0x73, 0x63, 0x68, 0x65, 0x6d,
0x65, 0x72, 0x2e, 0x50, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x53, 0x63, 0x68, 0x65, 0x61, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1c, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69,
0x6d, 0x61, 0x52, 0x10, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x53, 0x63, 0x68, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72,
0x65, 0x6d, 0x61, 0x73, 0x1a, 0x73, 0x0a, 0x08, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x53, 0x63, 0x68, 0x65, 0x6d, 0x61, 0x52, 0x10, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65,
0x12, 0x24, 0x0a, 0x03, 0x6c, 0x6f, 0x67, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x10, 0x2e, 0x72, 0x53, 0x63, 0x68, 0x65, 0x6d, 0x61, 0x73, 0x1a, 0x73, 0x0a, 0x08, 0x52, 0x65, 0x73, 0x70,
0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x4c, 0x6f, 0x67, 0x48, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x24, 0x0a, 0x03, 0x6c, 0x6f, 0x67, 0x18, 0x01, 0x20, 0x01, 0x28,
0x00, 0x52, 0x03, 0x6c, 0x6f, 0x67, 0x12, 0x39, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x0b, 0x32, 0x10, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e,
0x74, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1b, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x4c, 0x6f, 0x67, 0x48, 0x00, 0x52, 0x03, 0x6c, 0x6f, 0x67, 0x12, 0x39, 0x0a, 0x08, 0x63, 0x6f,
0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x61, 0x72, 0x73, 0x65, 0x2e, 0x43, 0x6f, 0x6d, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1b, 0x2e, 0x70,
0x70, 0x6c, 0x65, 0x74, 0x65, 0x48, 0x00, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x61, 0x72, 0x73, 0x65,
0x65, 0x42, 0x06, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x22, 0xae, 0x07, 0x0a, 0x09, 0x50, 0x72, 0x2e, 0x43, 0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x48, 0x00, 0x52, 0x08, 0x63, 0x6f, 0x6d,
0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x1a, 0xd1, 0x02, 0x0a, 0x08, 0x4d, 0x65, 0x74, 0x61, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x42, 0x06, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x22, 0xae, 0x07,
0x64, 0x61, 0x74, 0x61, 0x12, 0x1b, 0x0a, 0x09, 0x63, 0x6f, 0x64, 0x65, 0x72, 0x5f, 0x75, 0x72, 0x0a, 0x09, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x1a, 0xd1, 0x02, 0x0a, 0x08,
0x6c, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x63, 0x6f, 0x64, 0x65, 0x72, 0x55, 0x72, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x12, 0x1b, 0x0a, 0x09, 0x63, 0x6f, 0x64, 0x65,
0x6c, 0x12, 0x53, 0x0a, 0x14, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x5f, 0x74, 0x72, 0x5f, 0x75, 0x72, 0x6c, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x63, 0x6f, 0x64,
0x72, 0x61, 0x6e, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x65, 0x72, 0x55, 0x72, 0x6c, 0x12, 0x53, 0x0a, 0x14, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61,
0x20, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x57, 0x6f, 0x63, 0x65, 0x5f, 0x74, 0x72, 0x61, 0x6e, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x02, 0x20,
0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x01, 0x28, 0x0e, 0x32, 0x20, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65,
0x6e, 0x52, 0x13, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x54, 0x72, 0x61, 0x6e, 0x72, 0x2e, 0x57, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x54, 0x72, 0x61, 0x6e, 0x73,
0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x25, 0x0a, 0x0e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x13, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65,
0x61, 0x63, 0x65, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0d, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x25, 0x0a, 0x0e, 0x77, 0x6f,
0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x27, 0x0a, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x03, 0x20, 0x01,
0x0f, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x5f, 0x6f, 0x77, 0x6e, 0x65, 0x72, 0x28, 0x09, 0x52, 0x0d, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x4e, 0x61, 0x6d,
0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0e, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x12, 0x27, 0x0a, 0x0f, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x5f, 0x6f,
0x65, 0x4f, 0x77, 0x6e, 0x65, 0x72, 0x12, 0x21, 0x0a, 0x0c, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x77, 0x6e, 0x65, 0x72, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0e, 0x77, 0x6f, 0x72, 0x6b,
0x61, 0x63, 0x65, 0x5f, 0x69, 0x64, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x77, 0x6f, 0x73, 0x70, 0x61, 0x63, 0x65, 0x4f, 0x77, 0x6e, 0x65, 0x72, 0x12, 0x21, 0x0a, 0x0c, 0x77, 0x6f,
0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x49, 0x64, 0x12, 0x2c, 0x0a, 0x12, 0x77, 0x6f, 0x72, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x5f, 0x69, 0x64, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09,
0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x5f, 0x6f, 0x77, 0x6e, 0x65, 0x72, 0x5f, 0x69, 0x64, 0x18, 0x52, 0x0b, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x49, 0x64, 0x12, 0x2c, 0x0a,
0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x10, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x12, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x5f, 0x6f, 0x77, 0x6e, 0x65, 0x72,
0x4f, 0x77, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x12, 0x32, 0x0a, 0x15, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x5f, 0x69, 0x64, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x10, 0x77, 0x6f, 0x72, 0x6b, 0x73,
0x70, 0x61, 0x63, 0x65, 0x5f, 0x6f, 0x77, 0x6e, 0x65, 0x72, 0x5f, 0x65, 0x6d, 0x61, 0x69, 0x6c, 0x70, 0x61, 0x63, 0x65, 0x4f, 0x77, 0x6e, 0x65, 0x72, 0x49, 0x64, 0x12, 0x32, 0x0a, 0x15, 0x77,
0x18, 0x07, 0x20, 0x01, 0x28, 0x09, 0x52, 0x13, 0x77, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x5f, 0x6f, 0x77, 0x6e, 0x65, 0x72, 0x5f, 0x65,
0x65, 0x4f, 0x77, 0x6e, 0x65, 0x72, 0x45, 0x6d, 0x61, 0x69, 0x6c, 0x1a, 0xd9, 0x01, 0x0a, 0x05, 0x6d, 0x61, 0x69, 0x6c, 0x18, 0x07, 0x20, 0x01, 0x28, 0x09, 0x52, 0x13, 0x77, 0x6f, 0x72, 0x6b,
0x53, 0x74, 0x61, 0x72, 0x74, 0x12, 0x1c, 0x0a, 0x09, 0x64, 0x69, 0x72, 0x65, 0x63, 0x74, 0x6f, 0x73, 0x70, 0x61, 0x63, 0x65, 0x4f, 0x77, 0x6e, 0x65, 0x72, 0x45, 0x6d, 0x61, 0x69, 0x6c, 0x1a,
0x72, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x64, 0x69, 0x72, 0x65, 0x63, 0x74, 0xd9, 0x01, 0x0a, 0x05, 0x53, 0x74, 0x61, 0x72, 0x74, 0x12, 0x1c, 0x0a, 0x09, 0x64, 0x69, 0x72,
0x6f, 0x72, 0x79, 0x12, 0x46, 0x0a, 0x10, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x79, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x64, 0x69,
0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1b, 0x2e, 0x72, 0x65, 0x63, 0x74, 0x6f, 0x72, 0x79, 0x12, 0x46, 0x0a, 0x10, 0x70, 0x61, 0x72, 0x61, 0x6d,
0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x61, 0x72, 0x61, 0x65, 0x74, 0x65, 0x72, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x18, 0x02, 0x20, 0x03, 0x28,
0x6d, 0x65, 0x74, 0x65, 0x72, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x52, 0x0f, 0x70, 0x61, 0x72, 0x61, 0x0b, 0x32, 0x1b, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e,
0x6d, 0x65, 0x74, 0x65, 0x72, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x12, 0x3b, 0x0a, 0x08, 0x6d, 0x50, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x52, 0x0f,
0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x18, 0x03, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1f, 0x2e, 0x70, 0x61, 0x72, 0x61, 0x6d, 0x65, 0x74, 0x65, 0x72, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x73, 0x12,
0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x3b, 0x0a, 0x08, 0x6d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x18, 0x03, 0x20, 0x01, 0x28,
0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x52, 0x08, 0x0b, 0x32, 0x1f, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e,
0x6d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x12, 0x14, 0x0a, 0x05, 0x73, 0x74, 0x61, 0x74, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x4d, 0x65, 0x74, 0x61, 0x64, 0x61,
0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x12, 0x17, 0x74, 0x61, 0x52, 0x08, 0x6d, 0x65, 0x74, 0x61, 0x64, 0x61, 0x74, 0x61, 0x12, 0x14, 0x0a, 0x05,
0x0a, 0x07, 0x64, 0x72, 0x79, 0x5f, 0x72, 0x75, 0x6e, 0x18, 0x05, 0x20, 0x01, 0x28, 0x08, 0x52, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x05, 0x73, 0x74, 0x61,
0x06, 0x64, 0x72, 0x79, 0x52, 0x75, 0x6e, 0x1a, 0x08, 0x0a, 0x06, 0x43, 0x61, 0x6e, 0x63, 0x65, 0x74, 0x65, 0x12, 0x17, 0x0a, 0x07, 0x64, 0x72, 0x79, 0x5f, 0x72, 0x75, 0x6e, 0x18, 0x05, 0x20,
0x6c, 0x1a, 0x80, 0x01, 0x0a, 0x07, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x34, 0x0a, 0x01, 0x28, 0x08, 0x52, 0x06, 0x64, 0x72, 0x79, 0x52, 0x75, 0x6e, 0x1a, 0x08, 0x0a, 0x06, 0x43,
0x05, 0x73, 0x74, 0x61, 0x72, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1c, 0x2e, 0x70, 0x61, 0x6e, 0x63, 0x65, 0x6c, 0x1a, 0x80, 0x01, 0x0a, 0x07, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73,
0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x74, 0x12, 0x34, 0x0a, 0x05, 0x73, 0x74, 0x61, 0x72, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b,
0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x53, 0x74, 0x61, 0x72, 0x74, 0x48, 0x00, 0x52, 0x05, 0x73, 0x74, 0x32, 0x1c, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50,
0x61, 0x72, 0x74, 0x12, 0x37, 0x0a, 0x06, 0x63, 0x61, 0x6e, 0x63, 0x65, 0x6c, 0x18, 0x02, 0x20, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x53, 0x74, 0x61, 0x72, 0x74, 0x48, 0x00,
0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x52, 0x05, 0x73, 0x74, 0x61, 0x72, 0x74, 0x12, 0x37, 0x0a, 0x06, 0x63, 0x61, 0x6e, 0x63, 0x65,
0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x43, 0x61, 0x6e, 0x63, 0x6c, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1d, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73,
0x65, 0x6c, 0x48, 0x00, 0x52, 0x06, 0x63, 0x61, 0x6e, 0x63, 0x65, 0x6c, 0x42, 0x06, 0x0a, 0x04, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e,
0x74, 0x79, 0x70, 0x65, 0x1a, 0x6b, 0x0a, 0x08, 0x43, 0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x43, 0x61, 0x6e, 0x63, 0x65, 0x6c, 0x48, 0x00, 0x52, 0x06, 0x63, 0x61, 0x6e, 0x63, 0x65, 0x6c,
0x12, 0x14, 0x0a, 0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0c, 0x52, 0x42, 0x06, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x1a, 0x6b, 0x0a, 0x08, 0x43, 0x6f, 0x6d, 0x70,
0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x12, 0x14, 0x0a, 0x05, 0x65, 0x72, 0x72, 0x6f, 0x72, 0x18, 0x6c, 0x65, 0x74, 0x65, 0x12, 0x14, 0x0a, 0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x18, 0x01, 0x20,
0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x65, 0x72, 0x72, 0x6f, 0x72, 0x12, 0x33, 0x0a, 0x09, 0x01, 0x28, 0x0c, 0x52, 0x05, 0x73, 0x74, 0x61, 0x74, 0x65, 0x12, 0x14, 0x0a, 0x05, 0x65, 0x72,
0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x72, 0x6f, 0x72, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x65, 0x72, 0x72, 0x6f, 0x72,
0x15, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x52, 0x65, 0x12, 0x33, 0x0a, 0x09, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x73, 0x18, 0x03, 0x20,
0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x52, 0x09, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x03, 0x28, 0x0b, 0x32, 0x15, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65,
0x73, 0x1a, 0x77, 0x0a, 0x08, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x24, 0x0a, 0x72, 0x2e, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x52, 0x09, 0x72, 0x65, 0x73, 0x6f,
0x03, 0x6c, 0x6f, 0x67, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x10, 0x2e, 0x70, 0x72, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x73, 0x1a, 0x77, 0x0a, 0x08, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73,
0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x4c, 0x6f, 0x67, 0x48, 0x00, 0x52, 0x03, 0x65, 0x12, 0x24, 0x0a, 0x03, 0x6c, 0x6f, 0x67, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x10,
0x6c, 0x6f, 0x67, 0x12, 0x3d, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x18, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x4c, 0x6f, 0x67,
0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1f, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x48, 0x00, 0x52, 0x03, 0x6c, 0x6f, 0x67, 0x12, 0x3d, 0x0a, 0x08, 0x63, 0x6f, 0x6d, 0x70, 0x6c,
0x6e, 0x65, 0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x43, 0x6f, 0x65, 0x74, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1f, 0x2e, 0x70, 0x72, 0x6f, 0x76,
0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x48, 0x00, 0x52, 0x08, 0x63, 0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f,
0x74, 0x65, 0x42, 0x06, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x2a, 0x3f, 0x0a, 0x08, 0x4c, 0x6f, 0x6e, 0x2e, 0x43, 0x6f, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x48, 0x00, 0x52, 0x08, 0x63, 0x6f,
0x67, 0x4c, 0x65, 0x76, 0x65, 0x6c, 0x12, 0x09, 0x0a, 0x05, 0x54, 0x52, 0x41, 0x43, 0x45, 0x10, 0x6d, 0x70, 0x6c, 0x65, 0x74, 0x65, 0x42, 0x06, 0x0a, 0x04, 0x74, 0x79, 0x70, 0x65, 0x2a, 0x3f,
0x00, 0x12, 0x09, 0x0a, 0x05, 0x44, 0x45, 0x42, 0x55, 0x47, 0x10, 0x01, 0x12, 0x08, 0x0a, 0x04, 0x0a, 0x08, 0x4c, 0x6f, 0x67, 0x4c, 0x65, 0x76, 0x65, 0x6c, 0x12, 0x09, 0x0a, 0x05, 0x54, 0x52,
0x49, 0x4e, 0x46, 0x4f, 0x10, 0x02, 0x12, 0x08, 0x0a, 0x04, 0x57, 0x41, 0x52, 0x4e, 0x10, 0x03, 0x41, 0x43, 0x45, 0x10, 0x00, 0x12, 0x09, 0x0a, 0x05, 0x44, 0x45, 0x42, 0x55, 0x47, 0x10, 0x01,
0x12, 0x09, 0x0a, 0x05, 0x45, 0x52, 0x52, 0x4f, 0x52, 0x10, 0x04, 0x2a, 0x37, 0x0a, 0x13, 0x57, 0x12, 0x08, 0x0a, 0x04, 0x49, 0x4e, 0x46, 0x4f, 0x10, 0x02, 0x12, 0x08, 0x0a, 0x04, 0x57, 0x41,
0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x54, 0x72, 0x61, 0x6e, 0x73, 0x69, 0x74, 0x69, 0x52, 0x4e, 0x10, 0x03, 0x12, 0x09, 0x0a, 0x05, 0x45, 0x52, 0x52, 0x4f, 0x52, 0x10, 0x04, 0x2a,
0x6f, 0x6e, 0x12, 0x09, 0x0a, 0x05, 0x53, 0x54, 0x41, 0x52, 0x54, 0x10, 0x00, 0x12, 0x08, 0x0a, 0x37, 0x0a, 0x13, 0x57, 0x6f, 0x72, 0x6b, 0x73, 0x70, 0x61, 0x63, 0x65, 0x54, 0x72, 0x61, 0x6e,
0x04, 0x53, 0x54, 0x4f, 0x50, 0x10, 0x01, 0x12, 0x0b, 0x0a, 0x07, 0x44, 0x45, 0x53, 0x54, 0x52, 0x73, 0x69, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x09, 0x0a, 0x05, 0x53, 0x54, 0x41, 0x52, 0x54, 0x10,
0x4f, 0x59, 0x10, 0x02, 0x32, 0xa3, 0x01, 0x0a, 0x0b, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x00, 0x12, 0x08, 0x0a, 0x04, 0x53, 0x54, 0x4f, 0x50, 0x10, 0x01, 0x12, 0x0b, 0x0a, 0x07, 0x44,
0x6f, 0x6e, 0x65, 0x72, 0x12, 0x42, 0x0a, 0x05, 0x50, 0x61, 0x72, 0x73, 0x65, 0x12, 0x1a, 0x2e, 0x45, 0x53, 0x54, 0x52, 0x4f, 0x59, 0x10, 0x02, 0x32, 0xa3, 0x01, 0x0a, 0x0b, 0x50, 0x72, 0x6f,
0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x12, 0x42, 0x0a, 0x05, 0x50, 0x61, 0x72, 0x73,
0x65, 0x12, 0x1a, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e,
0x50, 0x61, 0x72, 0x73, 0x65, 0x2e, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1b, 0x2e,
0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x61, 0x72, 0x73, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x61, 0x72, 0x73,
0x65, 0x2e, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1b, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x65, 0x2e, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x30, 0x01, 0x12, 0x50, 0x0a, 0x09,
0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x61, 0x72, 0x73, 0x65, 0x2e, 0x52, 0x65, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x1e, 0x2e, 0x70, 0x72, 0x6f, 0x76,
0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x30, 0x01, 0x12, 0x50, 0x0a, 0x09, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f,
0x69, 0x73, 0x69, 0x6f, 0x6e, 0x12, 0x1e, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1f, 0x2e, 0x70, 0x72, 0x6f, 0x76,
0x6e, 0x65, 0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x52, 0x65, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f,
0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1f, 0x2e, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x28, 0x01, 0x30, 0x01, 0x42, 0x2d,
0x6e, 0x65, 0x72, 0x2e, 0x50, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x2e, 0x52, 0x65, 0x5a, 0x2b, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x63, 0x6f, 0x64,
0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x28, 0x01, 0x30, 0x01, 0x42, 0x2d, 0x5a, 0x2b, 0x67, 0x69, 0x65, 0x72, 0x2f, 0x63, 0x6f, 0x64, 0x65, 0x72, 0x2f, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69,
0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x63, 0x6f, 0x64, 0x65, 0x72, 0x2f, 0x63, 0x6f, 0x6e, 0x65, 0x72, 0x73, 0x64, 0x6b, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x06, 0x70,
0x6f, 0x64, 0x65, 0x72, 0x2f, 0x70, 0x72, 0x6f, 0x76, 0x69, 0x73, 0x69, 0x6f, 0x6e, 0x65, 0x72, 0x72, 0x6f, 0x74, 0x6f, 0x33,
0x73, 0x64, 0x6b, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f,
0x33,
} }
var ( var (

View File

@ -110,6 +110,7 @@ message Resource {
} }
repeated Metadata metadata = 4; repeated Metadata metadata = 4;
bool hide = 5; bool hide = 5;
string icon = 6;
} }
// Parse consumes source-code from a directory to produce inputs. // Parse consumes source-code from a directory to produce inputs.

View File

@ -637,6 +637,7 @@ export interface WorkspaceResource {
readonly type: string readonly type: string
readonly name: string readonly name: string
readonly hide: boolean readonly hide: boolean
readonly icon: string
readonly agents?: WorkspaceAgent[] readonly agents?: WorkspaceAgent[]
readonly metadata?: WorkspaceResourceMetadata[] readonly metadata?: WorkspaceResourceMetadata[]
} }

View File

@ -1,4 +1,5 @@
import { Story } from "@storybook/react" import { Story } from "@storybook/react"
import { MockWorkspaceResource } from "testHelpers/entities"
import { ResourceAvatar, ResourceAvatarProps } from "./ResourceAvatar" import { ResourceAvatar, ResourceAvatarProps } from "./ResourceAvatar"
export default { export default {
@ -10,25 +11,40 @@ const Template: Story<ResourceAvatarProps> = (args) => <ResourceAvatar {...args}
export const VolumeResource = Template.bind({}) export const VolumeResource = Template.bind({})
VolumeResource.args = { VolumeResource.args = {
resource: {
...MockWorkspaceResource,
type: "docker_volume", type: "docker_volume",
},
} }
export const ComputeResource = Template.bind({}) export const ComputeResource = Template.bind({})
ComputeResource.args = { ComputeResource.args = {
resource: {
...MockWorkspaceResource,
type: "docker_container", type: "docker_container",
},
} }
export const ImageResource = Template.bind({}) export const ImageResource = Template.bind({})
ImageResource.args = { ImageResource.args = {
resource: {
...MockWorkspaceResource,
type: "docker_image", type: "docker_image",
},
} }
export const NullResource = Template.bind({}) export const NullResource = Template.bind({})
NullResource.args = { NullResource.args = {
resource: {
...MockWorkspaceResource,
type: "null_resource", type: "null_resource",
},
} }
export const UnknownResource = Template.bind({}) export const UnknownResource = Template.bind({})
UnknownResource.args = { UnknownResource.args = {
resource: {
...MockWorkspaceResource,
type: "noexistentvalue", type: "noexistentvalue",
},
} }

View File

@ -1,51 +1,47 @@
import Avatar from "@material-ui/core/Avatar" import Avatar from "@material-ui/core/Avatar"
import { makeStyles } from "@material-ui/core/styles" import { makeStyles } from "@material-ui/core/styles"
import FolderIcon from "@material-ui/icons/FolderOutlined"
import ImageIcon from "@material-ui/icons/ImageOutlined"
import MemoryIcon from "@material-ui/icons/MemoryOutlined"
import WidgetsIcon from "@material-ui/icons/WidgetsOutlined"
import React from "react" import React from "react"
import { WorkspaceResource } from "../../api/typesGenerated" import { WorkspaceResource } from "../../api/typesGenerated"
// For this special case, we need to apply a different style because how this
// particular icon has been designed
const AdjustedMemoryIcon: typeof MemoryIcon = ({ style, ...props }) => {
return <MemoryIcon style={{ ...style, fontSize: 24 }} {...props} />
}
// NOTE @jsjoeio, @BrunoQuaresma // NOTE @jsjoeio, @BrunoQuaresma
// These resources (i.e. docker_image, kubernetes_deployment) map to Terraform // These resources (i.e. docker_image, kubernetes_deployment) map to Terraform
// resource types. These are the most used ones and are based on user usage. // resource types. These are the most used ones and are based on user usage.
// We may want to update from time-to-time. // We may want to update from time-to-time.
const iconByResource: Record<WorkspaceResource["type"], typeof MemoryIcon | undefined> = { const iconPathByResource: Record<WorkspaceResource["type"], string> = {
docker_volume: FolderIcon, docker_volume: "/icon/folder.svg",
docker_container: AdjustedMemoryIcon, docker_container: "/icon/memory.svg",
docker_image: ImageIcon, docker_image: "/icon/image.svg",
kubernetes_persistent_volume_claim: FolderIcon, kubernetes_persistent_volume_claim: "/icon/folder.svg",
kubernetes_pod: AdjustedMemoryIcon, kubernetes_pod: "/icon/memory.svg",
google_compute_disk: FolderIcon, google_compute_disk: "/icon/folder.svg",
google_compute_instance: AdjustedMemoryIcon, google_compute_instance: "/icon/memory.svg",
aws_instance: AdjustedMemoryIcon, aws_instance: "/icon/memory.svg",
kubernetes_deployment: AdjustedMemoryIcon, kubernetes_deployment: "/icon/memory.svg",
null_resource: WidgetsIcon, null_resource: "/icon/widgets.svg",
} }
export type ResourceAvatarProps = { type: WorkspaceResource["type"] } export type ResourceAvatarProps = { resource: WorkspaceResource }
export const ResourceAvatar: React.FC<ResourceAvatarProps> = ({ type }) => { export const ResourceAvatar: React.FC<ResourceAvatarProps> = ({ resource }) => {
const IconComponent = iconByResource[type] ?? WidgetsIcon const hasIcon = resource.icon && resource.icon !== ""
const avatarSrc = hasIcon
? resource.icon
: // resource.type is dynamic so iconPathByResource[resource.type] can be null
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
iconPathByResource[resource.type] ?? iconPathByResource["null_resource"]
const styles = useStyles() const styles = useStyles()
return ( return <Avatar className={styles.resourceAvatar} src={avatarSrc} />
<Avatar className={styles.resourceAvatar}>
<IconComponent style={{ fontSize: 20 }} />
</Avatar>
)
} }
const useStyles = makeStyles((theme) => ({ const useStyles = makeStyles((theme) => ({
resourceAvatar: { resourceAvatar: {
color: theme.palette.info.contrastText, color: theme.palette.info.contrastText,
backgroundColor: theme.palette.info.main, backgroundColor: theme.palette.info.main,
"& img": {
width: 20,
height: 20,
},
}, },
})) }))

View File

@ -49,7 +49,7 @@ export const ResourceAvatarData: FC<ResourceAvatarDataProps> = ({ resource }) =>
return ( return (
<div className={styles.root}> <div className={styles.root}>
<div className={styles.avatarWrapper}> <div className={styles.avatarWrapper}>
<ResourceAvatar type={resource.type} /> <ResourceAvatar resource={resource} />
</div> </div>
<TableCellData> <TableCellData>

View File

@ -61,7 +61,7 @@ export const TemplateResourcesTable: FC<React.PropsWithChildren<TemplateResource
title={resource.name} title={resource.name}
subtitle={resource.type} subtitle={resource.type}
highlightTitle highlightTitle
avatar={<ResourceAvatar type={resource.type} />} avatar={<ResourceAvatar resource={resource} />}
/> />
</TableCell> </TableCell>
<TableCell colSpan={3}></TableCell> <TableCell colSpan={3}></TableCell>
@ -79,7 +79,7 @@ export const TemplateResourcesTable: FC<React.PropsWithChildren<TemplateResource
title={resource.name} title={resource.name}
subtitle={resource.type} subtitle={resource.type}
highlightTitle highlightTitle
avatar={<ResourceAvatar type={resource.type} />} avatar={<ResourceAvatar resource={resource} />}
/> />
</TableCell> </TableCell>
)} )}

View File

@ -394,6 +394,7 @@ export const MockWorkspaceResource: TypesGen.WorkspaceResource = {
type: "google_compute_disk", type: "google_compute_disk",
workspace_transition: "start", workspace_transition: "start",
hide: false, hide: false,
icon: "",
metadata: [ metadata: [
{ key: "type", value: "a-workspace-resource", sensitive: false }, { key: "type", value: "a-workspace-resource", sensitive: false },
{ key: "api_key", value: "12345678", sensitive: true }, { key: "api_key", value: "12345678", sensitive: true },
@ -409,6 +410,7 @@ export const MockWorkspaceResource2: TypesGen.WorkspaceResource = {
type: "google_compute_disk", type: "google_compute_disk",
workspace_transition: "start", workspace_transition: "start",
hide: false, hide: false,
icon: "",
metadata: [ metadata: [
{ key: "type", value: "google_compute_disk", sensitive: false }, { key: "type", value: "google_compute_disk", sensitive: false },
{ key: "size", value: "32GB", sensitive: false }, { key: "size", value: "32GB", sensitive: false },
@ -424,6 +426,7 @@ export const MockWorkspaceResource3: TypesGen.WorkspaceResource = {
type: "google_compute_disk", type: "google_compute_disk",
workspace_transition: "start", workspace_transition: "start",
hide: true, hide: true,
icon: "",
metadata: [ metadata: [
{ key: "type", value: "google_compute_disk", sensitive: false }, { key: "type", value: "google_compute_disk", sensitive: false },
{ key: "size", value: "32GB", sensitive: false }, { key: "size", value: "32GB", sensitive: false },

View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" height="48" width="48" fill="#FFF"><path d="M24 22q-8.05 0-13.025-2.45T6 14q0-3.15 4.975-5.575Q15.95 6 24 6t13.025 2.425Q42 10.85 42 14q0 3.1-4.975 5.55Q32.05 22 24 22Zm0 10q-7.3 0-12.65-2.2Q6 27.6 6 24.5v-5q0 1.95 1.875 3.375t4.65 2.35q2.775.925 5.9 1.35Q21.55 27 24 27q2.5 0 5.6-.425 3.1-.425 5.875-1.325 2.775-.9 4.65-2.325Q42 21.5 42 19.5v5q0 3.1-5.35 5.3Q31.3 32 24 32Zm0 10q-7.3 0-12.65-2.2Q6 37.6 6 34.5v-5q0 1.95 1.875 3.375t4.65 2.35q2.775.925 5.9 1.35Q21.55 37 24 37q2.5 0 5.6-.425 3.1-.425 5.875-1.325 2.775-.9 4.65-2.325Q42 31.5 42 29.5v5q0 3.1-5.35 5.3Q31.3 42 24 42Z"/></svg>

After

Width:  |  Height:  |  Size: 630 B

View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" height="48" width="48" fill="#FFF"><path d="M7.05 40q-1.2 0-2.1-.925-.9-.925-.9-2.075V11q0-1.15.9-2.075Q5.85 8 7.05 8h14l3 3h17q1.15 0 2.075.925.925.925.925 2.075v23q0 1.15-.925 2.075Q42.2 40 41.05 40Zm0-29v26h34V14H22.8l-3-3H7.05Zm0 0v26Z"/></svg>

After

Width:  |  Height:  |  Size: 289 B

View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" height="48" width="48" fill="#FFF"><path d="M9 42q-1.2 0-2.1-.9Q6 40.2 6 39V9q0-1.2.9-2.1Q7.8 6 9 6h30q1.2 0 2.1.9.9.9.9 2.1v30q0 1.2-.9 2.1-.9.9-2.1.9Zm0-3h30V9H9v30Zm2.8-4.85h24.45l-7.35-9.8-6.6 8.55-4.65-6.35ZM9 39V9v30Z"/></svg>

After

Width:  |  Height:  |  Size: 273 B

View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" height="48" width="48" fill="#FFF"><path d="M18.85 29.15V18.9H29.1v10.25Zm3-3h4.25V21.9h-4.25ZM18 42v-4h-5q-1.2 0-2.1-.9-.9-.9-.9-2.1v-5H6v-3h4v-6.2H6v-3h4v-5q0-1.2.9-2.1.9-.9 2.1-.9h5V6h3v3.8h6.2V6h3v3.8h5q1.2 0 2.1.9.9.9.9 2.1v5H42v3h-3.8V27H42v3h-3.8v5q0 1.2-.9 2.1-.9.9-2.1.9h-5v4h-3v-4H21v4Zm17.2-7V12.8H13V35ZM24 24Z"/></svg>

After

Width:  |  Height:  |  Size: 372 B

View File

@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" height="48" width="48" fill="#FFF"><path d="M33.95 24.7 23.3 14.05 33.95 3.4 44.6 14.05ZM6 21.1V6.05h15.05V21.1ZM26.9 42V26.95h15.05V42ZM6 42V26.95h15.05V42Zm3-23.9h9.05V9.05H9Zm25.1 2.55 6.45-6.45-6.45-6.45-6.45 6.45ZM29.9 39h9.05v-9.05H29.9ZM9 39h9.05v-9.05H9Zm9.05-20.9Zm9.6-3.9Zm-9.6 15.75Zm11.85 0Z"/></svg>

After

Width:  |  Height:  |  Size: 353 B