feat: migrate to typed messages
Some checks failed
CI / Lint (pull_request) Failing after 57s
CI / Test (pull_request) Failing after 1m23s
CI / Release (pull_request) Has been skipped
CI / Docker Build & Push (pull_request) Has been skipped
CI / Notify (pull_request) Successful in 1s

- Switch OnMessage → OnTypedMessage with natsutil.Decode[messages.PipelineTrigger]
- Return *messages.PipelineStatus (not map[string]any)
- Remove strVal/mapVal helpers
- Add .dockerignore, GOAMD64=v3 in Dockerfile
- Update tests for typed structs (14 tests pass)
This commit is contained in:
2026-02-20 07:11:03 -05:00
parent 8f9b2203ca
commit 7cdcbfbff3
5 changed files with 97 additions and 75 deletions

72
main.go
View File

@@ -15,6 +15,8 @@ import (
"git.daviestechlabs.io/daviestechlabs/handler-base/config"
"git.daviestechlabs.io/daviestechlabs/handler-base/handler"
"git.daviestechlabs.io/daviestechlabs/handler-base/messages"
"git.daviestechlabs.io/daviestechlabs/handler-base/natsutil"
)
// Pipeline definitions — maps pipeline name to engine config.
@@ -45,10 +47,21 @@ func main() {
h := handler.New("ai.pipeline.trigger", cfg)
h.OnMessage(func(ctx context.Context, msg *nats.Msg, data map[string]any) (map[string]any, error) {
requestID := strVal(data, "request_id", "unknown")
pipelineName := strVal(data, "pipeline", "")
params := mapVal(data, "parameters")
h.OnTypedMessage(func(ctx context.Context, msg *nats.Msg) (any, error) {
req, err := natsutil.Decode[messages.PipelineTrigger](msg.Data)
if err != nil {
return &messages.PipelineStatus{Status: "error", Error: "Invalid request encoding"}, nil
}
requestID := req.RequestID
if requestID == "" {
requestID = "unknown"
}
pipelineName := req.Pipeline
params := req.Parameters
if params == nil {
params = map[string]any{}
}
slog.Info("triggering pipeline", "pipeline", pipelineName, "request_id", requestID)
@@ -59,16 +72,15 @@ func main() {
for k := range pipelines {
names = append(names, k)
}
return map[string]any{
"request_id": requestID,
"status": "error",
"error": fmt.Sprintf("Unknown pipeline: %s", pipelineName),
"available_pipelines": names,
return &messages.PipelineStatus{
RequestID: requestID,
Status: "error",
Error: fmt.Sprintf("Unknown pipeline: %s", pipelineName),
AvailablePipelines: names,
}, nil
}
var runID string
var err error
if pipeline.Engine == "argo" {
runID, err = submitArgo(ctx, httpClient, argoHost, argoNamespace, pipeline.Template, params, requestID)
@@ -78,20 +90,20 @@ func main() {
if err != nil {
slog.Error("pipeline submit failed", "pipeline", pipelineName, "error", err)
return map[string]any{
"request_id": requestID,
"status": "error",
"error": err.Error(),
return &messages.PipelineStatus{
RequestID: requestID,
Status: "error",
Error: err.Error(),
}, nil
}
result := map[string]any{
"request_id": requestID,
"status": "submitted",
"run_id": runID,
"engine": pipeline.Engine,
"pipeline": pipelineName,
"submitted_at": time.Now().UTC().Format(time.RFC3339),
result := &messages.PipelineStatus{
RequestID: requestID,
Status: "submitted",
RunID: runID,
Engine: pipeline.Engine,
Pipeline: pipelineName,
SubmittedAt: time.Now().UTC().Format(time.RFC3339),
}
// Publish status update
@@ -204,24 +216,6 @@ func submitKubeflow(ctx context.Context, client *http.Client, host, pipelineID s
// Helpers
func strVal(m map[string]any, key, fallback string) string {
if v, ok := m[key]; ok {
if s, ok := v.(string); ok {
return s
}
}
return fallback
}
func mapVal(m map[string]any, key string) map[string]any {
if v, ok := m[key]; ok {
if sub, ok := v.(map[string]any); ok {
return sub
}
}
return map[string]any{}
}
func getEnv(key, fallback string) string {
if v := os.Getenv(key); v != "" {
return v