feat(core): plugin display_name + description; CLI prompts; SDK fields
This commit is contained in:
parent
dae3aa918a
commit
041a7c2e3f
@ -76,6 +76,23 @@ func newPluginInitCmd() *cobra.Command {
|
|||||||
return fmt.Errorf("plugin name is required")
|
return fmt.Errorf("plugin name is required")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
rawName := name
|
||||||
|
name = strings.ToLower(name)
|
||||||
|
|
||||||
|
fmt.Printf("Display name [%s]: ", rawName)
|
||||||
|
displayName := ""
|
||||||
|
if scanner.Scan() {
|
||||||
|
displayName = strings.TrimSpace(scanner.Text())
|
||||||
|
}
|
||||||
|
if displayName == "" {
|
||||||
|
displayName = rawName
|
||||||
|
}
|
||||||
|
|
||||||
|
fmt.Print("Description (one-line summary, optional): ")
|
||||||
|
description := ""
|
||||||
|
if scanner.Scan() {
|
||||||
|
description = strings.TrimSpace(scanner.Text())
|
||||||
|
}
|
||||||
|
|
||||||
kind, err := promptKind(scanner)
|
kind, err := promptKind(scanner)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -92,7 +109,8 @@ func newPluginInitCmd() *cobra.Command {
|
|||||||
if _, err := cli.Reg.CreatePlugin(ctx, connect.NewRequest(&v1.CreatePluginRequest{
|
if _, err := cli.Reg.CreatePlugin(ctx, connect.NewRequest(&v1.CreatePluginRequest{
|
||||||
ScopeSlug: scopeAPISlug(scope),
|
ScopeSlug: scopeAPISlug(scope),
|
||||||
Name: name,
|
Name: name,
|
||||||
Description: "",
|
DisplayName: displayName,
|
||||||
|
Description: description,
|
||||||
Kind: kind,
|
Kind: kind,
|
||||||
Categories: cats,
|
Categories: cats,
|
||||||
})); err != nil {
|
})); err != nil {
|
||||||
@ -100,7 +118,7 @@ func newPluginInitCmd() *cobra.Command {
|
|||||||
}
|
}
|
||||||
fmt.Printf("\nCreated %s/%s\n", scope, name)
|
fmt.Printf("\nCreated %s/%s\n", scope, name)
|
||||||
|
|
||||||
if err := upsertPluginMod(scope, name, kind, cats); err != nil {
|
if err := upsertPluginMod(scope, name, displayName, description, kind, cats); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
fmt.Println("plugin.mod updated")
|
fmt.Println("plugin.mod updated")
|
||||||
@ -576,7 +594,7 @@ func submodulePaths(repoDir string) []string {
|
|||||||
return paths
|
return paths
|
||||||
}
|
}
|
||||||
|
|
||||||
func upsertPluginMod(scope, name, kind string, categories []string) error {
|
func upsertPluginMod(scope, name, displayName, description, kind string, categories []string) error {
|
||||||
const file = "plugin.mod"
|
const file = "plugin.mod"
|
||||||
existing, _ := os.ReadFile(file)
|
existing, _ := os.ReadFile(file)
|
||||||
mod, _ := core.ParseModFull(existing)
|
mod, _ := core.ParseModFull(existing)
|
||||||
@ -588,6 +606,8 @@ func upsertPluginMod(scope, name, kind string, categories []string) error {
|
|||||||
}
|
}
|
||||||
mod.Plugin.Scope = scope
|
mod.Plugin.Scope = scope
|
||||||
mod.Plugin.Name = name
|
mod.Plugin.Name = name
|
||||||
|
mod.Plugin.DisplayName = displayName
|
||||||
|
mod.Plugin.Description = description
|
||||||
mod.Plugin.Kind = kind
|
mod.Plugin.Kind = kind
|
||||||
mod.Plugin.Categories = categories
|
mod.Plugin.Categories = categories
|
||||||
return writeMod(file, mod)
|
return writeMod(file, mod)
|
||||||
@ -597,8 +617,14 @@ func writeMod(path string, m *core.ModFile) error {
|
|||||||
var b strings.Builder
|
var b strings.Builder
|
||||||
b.WriteString("[plugin]\n")
|
b.WriteString("[plugin]\n")
|
||||||
b.WriteString(fmt.Sprintf("name = %q\n", m.Plugin.Name))
|
b.WriteString(fmt.Sprintf("name = %q\n", m.Plugin.Name))
|
||||||
|
if m.Plugin.DisplayName != "" {
|
||||||
|
b.WriteString(fmt.Sprintf("display_name = %q\n", m.Plugin.DisplayName))
|
||||||
|
}
|
||||||
b.WriteString(fmt.Sprintf("scope = %q\n", m.Plugin.Scope))
|
b.WriteString(fmt.Sprintf("scope = %q\n", m.Plugin.Scope))
|
||||||
b.WriteString(fmt.Sprintf("version = %q\n", m.Plugin.Version))
|
b.WriteString(fmt.Sprintf("version = %q\n", m.Plugin.Version))
|
||||||
|
if m.Plugin.Description != "" {
|
||||||
|
b.WriteString(fmt.Sprintf("description = %q\n", m.Plugin.Description))
|
||||||
|
}
|
||||||
if m.Plugin.Kind != "" {
|
if m.Plugin.Kind != "" {
|
||||||
b.WriteString(fmt.Sprintf("kind = %q\n", m.Plugin.Kind))
|
b.WriteString(fmt.Sprintf("kind = %q\n", m.Plugin.Kind))
|
||||||
}
|
}
|
||||||
|
|||||||
@ -102,6 +102,7 @@ type Plugin struct {
|
|||||||
Categories []string `protobuf:"bytes,8,rep,name=categories,proto3" json:"categories,omitempty"`
|
Categories []string `protobuf:"bytes,8,rep,name=categories,proto3" json:"categories,omitempty"`
|
||||||
UpdatedAt *timestamppb.Timestamp `protobuf:"bytes,9,opt,name=updated_at,json=updatedAt,proto3" json:"updated_at,omitempty"`
|
UpdatedAt *timestamppb.Timestamp `protobuf:"bytes,9,opt,name=updated_at,json=updatedAt,proto3" json:"updated_at,omitempty"`
|
||||||
Kind string `protobuf:"bytes,10,opt,name=kind,proto3" json:"kind,omitempty"`
|
Kind string `protobuf:"bytes,10,opt,name=kind,proto3" json:"kind,omitempty"`
|
||||||
|
DisplayName string `protobuf:"bytes,11,opt,name=display_name,json=displayName,proto3" json:"display_name,omitempty"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
}
|
}
|
||||||
@ -206,6 +207,13 @@ func (x *Plugin) GetKind() string {
|
|||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (x *Plugin) GetDisplayName() string {
|
||||||
|
if x != nil {
|
||||||
|
return x.DisplayName
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
type Category struct {
|
type Category struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
Slug string `protobuf:"bytes,1,opt,name=slug,proto3" json:"slug,omitempty"`
|
Slug string `protobuf:"bytes,1,opt,name=slug,proto3" json:"slug,omitempty"`
|
||||||
@ -713,6 +721,7 @@ type CreatePluginRequest struct {
|
|||||||
Description string `protobuf:"bytes,3,opt,name=description,proto3" json:"description,omitempty"`
|
Description string `protobuf:"bytes,3,opt,name=description,proto3" json:"description,omitempty"`
|
||||||
Kind string `protobuf:"bytes,4,opt,name=kind,proto3" json:"kind,omitempty"`
|
Kind string `protobuf:"bytes,4,opt,name=kind,proto3" json:"kind,omitempty"`
|
||||||
Categories []string `protobuf:"bytes,5,rep,name=categories,proto3" json:"categories,omitempty"`
|
Categories []string `protobuf:"bytes,5,rep,name=categories,proto3" json:"categories,omitempty"`
|
||||||
|
DisplayName string `protobuf:"bytes,6,opt,name=display_name,json=displayName,proto3" json:"display_name,omitempty"`
|
||||||
unknownFields protoimpl.UnknownFields
|
unknownFields protoimpl.UnknownFields
|
||||||
sizeCache protoimpl.SizeCache
|
sizeCache protoimpl.SizeCache
|
||||||
}
|
}
|
||||||
@ -782,6 +791,13 @@ func (x *CreatePluginRequest) GetCategories() []string {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (x *CreatePluginRequest) GetDisplayName() string {
|
||||||
|
if x != nil {
|
||||||
|
return x.DisplayName
|
||||||
|
}
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
type CreatePluginResponse struct {
|
type CreatePluginResponse struct {
|
||||||
state protoimpl.MessageState `protogen:"open.v1"`
|
state protoimpl.MessageState `protogen:"open.v1"`
|
||||||
Plugin *Plugin `protobuf:"bytes,1,opt,name=plugin,proto3" json:"plugin,omitempty"`
|
Plugin *Plugin `protobuf:"bytes,1,opt,name=plugin,proto3" json:"plugin,omitempty"`
|
||||||
@ -2188,7 +2204,7 @@ const file_orchestrator_v1_plugin_registry_proto_rawDesc = "" +
|
|||||||
"\x04slug\x18\x02 \x01(\tR\x04slug\x12!\n" +
|
"\x04slug\x18\x02 \x01(\tR\x04slug\x12!\n" +
|
||||||
"\fdisplay_name\x18\x03 \x01(\tR\vdisplayName\x129\n" +
|
"\fdisplay_name\x18\x03 \x01(\tR\vdisplayName\x129\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
"created_at\x18\x04 \x01(\v2\x1a.google.protobuf.TimestampR\tcreatedAt\"\xb9\x02\n" +
|
"created_at\x18\x04 \x01(\v2\x1a.google.protobuf.TimestampR\tcreatedAt\"\xdc\x02\n" +
|
||||||
"\x06Plugin\x12\x0e\n" +
|
"\x06Plugin\x12\x0e\n" +
|
||||||
"\x02id\x18\x01 \x01(\tR\x02id\x12\x1d\n" +
|
"\x02id\x18\x01 \x01(\tR\x02id\x12\x1d\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
@ -2206,7 +2222,8 @@ const file_orchestrator_v1_plugin_registry_proto_rawDesc = "" +
|
|||||||
"\n" +
|
"\n" +
|
||||||
"updated_at\x18\t \x01(\v2\x1a.google.protobuf.TimestampR\tupdatedAt\x12\x12\n" +
|
"updated_at\x18\t \x01(\v2\x1a.google.protobuf.TimestampR\tupdatedAt\x12\x12\n" +
|
||||||
"\x04kind\x18\n" +
|
"\x04kind\x18\n" +
|
||||||
" \x01(\tR\x04kind\"\x82\x01\n" +
|
" \x01(\tR\x04kind\x12!\n" +
|
||||||
|
"\fdisplay_name\x18\v \x01(\tR\vdisplayName\"\x82\x01\n" +
|
||||||
"\bCategory\x12\x12\n" +
|
"\bCategory\x12\x12\n" +
|
||||||
"\x04slug\x18\x01 \x01(\tR\x04slug\x12!\n" +
|
"\x04slug\x18\x01 \x01(\tR\x04slug\x12!\n" +
|
||||||
"\fdisplay_name\x18\x02 \x01(\tR\vdisplayName\x12 \n" +
|
"\fdisplay_name\x18\x02 \x01(\tR\vdisplayName\x12 \n" +
|
||||||
@ -2240,7 +2257,7 @@ const file_orchestrator_v1_plugin_registry_proto_rawDesc = "" +
|
|||||||
"\x04slug\x18\x01 \x01(\tR\x04slug\"s\n" +
|
"\x04slug\x18\x01 \x01(\tR\x04slug\"s\n" +
|
||||||
"\x10GetScopeResponse\x12,\n" +
|
"\x10GetScopeResponse\x12,\n" +
|
||||||
"\x05scope\x18\x01 \x01(\v2\x16.orchestrator.v1.ScopeR\x05scope\x121\n" +
|
"\x05scope\x18\x01 \x01(\v2\x16.orchestrator.v1.ScopeR\x05scope\x121\n" +
|
||||||
"\aplugins\x18\x02 \x03(\v2\x17.orchestrator.v1.PluginR\aplugins\"\x9e\x01\n" +
|
"\aplugins\x18\x02 \x03(\v2\x17.orchestrator.v1.PluginR\aplugins\"\xc1\x01\n" +
|
||||||
"\x13CreatePluginRequest\x12\x1d\n" +
|
"\x13CreatePluginRequest\x12\x1d\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
"scope_slug\x18\x01 \x01(\tR\tscopeSlug\x12\x12\n" +
|
"scope_slug\x18\x01 \x01(\tR\tscopeSlug\x12\x12\n" +
|
||||||
@ -2249,7 +2266,8 @@ const file_orchestrator_v1_plugin_registry_proto_rawDesc = "" +
|
|||||||
"\x04kind\x18\x04 \x01(\tR\x04kind\x12\x1e\n" +
|
"\x04kind\x18\x04 \x01(\tR\x04kind\x12\x1e\n" +
|
||||||
"\n" +
|
"\n" +
|
||||||
"categories\x18\x05 \x03(\tR\n" +
|
"categories\x18\x05 \x03(\tR\n" +
|
||||||
"categories\"G\n" +
|
"categories\x12!\n" +
|
||||||
|
"\fdisplay_name\x18\x06 \x01(\tR\vdisplayName\"G\n" +
|
||||||
"\x14CreatePluginResponse\x12/\n" +
|
"\x14CreatePluginResponse\x12/\n" +
|
||||||
"\x06plugin\x18\x01 \x01(\v2\x17.orchestrator.v1.PluginR\x06plugin\"E\n" +
|
"\x06plugin\x18\x01 \x01(\v2\x17.orchestrator.v1.PluginR\x06plugin\"E\n" +
|
||||||
"\x10GetPluginRequest\x12\x1d\n" +
|
"\x10GetPluginRequest\x12\x1d\n" +
|
||||||
|
|||||||
@ -13,7 +13,15 @@ type ModFile struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type ModPlugin struct {
|
type ModPlugin struct {
|
||||||
|
// Name is the lowercase identifier used for the plugin slug in URLs and DB
|
||||||
|
// lookups. The CLI normalises this on write; the registry normalises on
|
||||||
|
// create. Use DisplayName for human-readable presentation.
|
||||||
Name string `toml:"name"`
|
Name string `toml:"name"`
|
||||||
|
// DisplayName is the human-readable form (any case). Optional; if empty
|
||||||
|
// the registry falls back to the input name with its original case.
|
||||||
|
DisplayName string `toml:"display_name,omitempty"`
|
||||||
|
// Description is the short summary surfaced in the registry. Optional.
|
||||||
|
Description string `toml:"description,omitempty"`
|
||||||
// Scope is the plugin owner namespace as it appears in plugin.mod. It may
|
// Scope is the plugin owner namespace as it appears in plugin.mod. It may
|
||||||
// include the leading "@" (e.g. "@themes") or omit it (e.g. "themes") —
|
// include the leading "@" (e.g. "@themes") or omit it (e.g. "themes") —
|
||||||
// both forms are accepted. Consumers comparing scopes should trim the "@"
|
// both forms are accepted. Consumers comparing scopes should trim the "@"
|
||||||
|
|||||||
@ -58,6 +58,7 @@ message Plugin {
|
|||||||
repeated string categories = 8;
|
repeated string categories = 8;
|
||||||
google.protobuf.Timestamp updated_at = 9;
|
google.protobuf.Timestamp updated_at = 9;
|
||||||
string kind = 10;
|
string kind = 10;
|
||||||
|
string display_name = 11;
|
||||||
}
|
}
|
||||||
|
|
||||||
message Category {
|
message Category {
|
||||||
@ -101,6 +102,7 @@ message CreatePluginRequest {
|
|||||||
string description = 3;
|
string description = 3;
|
||||||
string kind = 4;
|
string kind = 4;
|
||||||
repeated string categories = 5;
|
repeated string categories = 5;
|
||||||
|
string display_name = 6;
|
||||||
}
|
}
|
||||||
message CreatePluginResponse {
|
message CreatePluginResponse {
|
||||||
Plugin plugin = 1;
|
Plugin plugin = 1;
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user