go2ts.go

  1// A command line tool for generating typescript type declarations from go
  2// struct types.
  3//
  4// Example:
  5//
  6//	go run ./cmd/go2ts -o ui/src/generated-types.ts
  7package main
  8
  9import (
 10	"flag"
 11	"fmt"
 12	"os"
 13	"time"
 14
 15	"go.skia.org/infra/go/go2ts"
 16	"shelley.exe.dev/db"
 17	"shelley.exe.dev/db/generated"
 18	"shelley.exe.dev/llm"
 19)
 20
 21func main() {
 22	outputPath := flag.String("o", "", "Path to the output TypeScript file.")
 23	flag.Parse()
 24
 25	if *outputPath == "" {
 26		fmt.Println("Usage: go run ./cmd/go2ts -o <output-file>")
 27		os.Exit(1)
 28	}
 29
 30	generator := TS()
 31
 32	w, err := os.Create(*outputPath)
 33	if err != nil {
 34		fmt.Printf("error: %v\n", err)
 35		os.Exit(1)
 36	}
 37	defer w.Close()
 38
 39	fmt.Fprintf(w, "// Auto-generated by shelley.exe.dev/cmd/go2ts.go\n")
 40	fmt.Fprintf(w, "// Do not edit manually - regenerate with: go run ./cmd/go2ts -o ui/src/generated-types.ts\n\n")
 41	generator.Render(w)
 42}
 43
 44// TS returns a Go2TS generator for go types we want to use in TypeScript.
 45func TS() *go2ts.Go2TS {
 46	generator := go2ts.New()
 47
 48	// Database message types enum
 49	generator.AddMultipleUnion(
 50		[]db.MessageType{
 51			db.MessageTypeUser,
 52			db.MessageTypeAgent,
 53			db.MessageTypeTool,
 54			db.MessageTypeError,
 55			db.MessageTypeSystem,
 56			db.MessageTypeGitInfo,
 57		},
 58	)
 59
 60	// Database struct types
 61	generator.AddMultiple(
 62		generated.Conversation{},
 63		llm.Usage{},
 64	)
 65
 66	generator.AddMultiple(
 67		apiMessageForTS{},
 68		streamResponseForTS{},
 69		conversationWithStateForTS{},
 70	)
 71
 72	// Generate clean nominal types
 73	generator.GenerateNominalTypes = true
 74
 75	return generator
 76}
 77
 78type apiMessageForTS struct {
 79	MessageID      string    `json:"message_id"`
 80	ConversationID string    `json:"conversation_id"`
 81	SequenceID     int64     `json:"sequence_id"`
 82	Type           string    `json:"type"`
 83	LlmData        *string   `json:"llm_data,omitempty"`
 84	UserData       *string   `json:"user_data,omitempty"`
 85	UsageData      *string   `json:"usage_data,omitempty"`
 86	CreatedAt      time.Time `json:"created_at"`
 87	DisplayData    *string   `json:"display_data,omitempty"`
 88	EndOfTurn      *bool     `json:"end_of_turn,omitempty"`
 89}
 90
 91type conversationStateForTS struct {
 92	ConversationID string `json:"conversation_id"`
 93	Working        bool   `json:"working"`
 94	Model          string `json:"model,omitempty"`
 95}
 96
 97type conversationWithStateForTS struct {
 98	ConversationID       string  `json:"conversation_id"`
 99	Slug                 *string `json:"slug"`
100	UserInitiated        bool    `json:"user_initiated"`
101	CreatedAt            string  `json:"created_at"`
102	UpdatedAt            string  `json:"updated_at"`
103	Cwd                  *string `json:"cwd"`
104	Archived             bool    `json:"archived"`
105	ParentConversationID *string `json:"parent_conversation_id"`
106	Model                *string `json:"model"`
107	Working              bool    `json:"working"`
108}
109
110type streamResponseForTS struct {
111	Messages          []apiMessageForTS       `json:"messages"`
112	Conversation      generated.Conversation  `json:"conversation"`
113	ConversationState *conversationStateForTS `json:"conversation_state,omitempty"`
114	Heartbeat         bool                    `json:"heartbeat,omitempty"`
115}