alt/apps/cli/internal/operator/parser_map.go
toki c0db4b24c1 feat(live-trading): 계좌 동기화와 감사 추적을 추가한다
Live Trading Boundary의 남은 account-sync/audit-trail 작업을 완료해 운영자 headless workflow와 roadmap 완료 후보 상태를 함께 반영한다.
2026-06-08 11:18:41 +09:00

111 lines
5.9 KiB
Go

package operator
import (
"google.golang.org/protobuf/proto"
altv1 "git.toki-labs.com/toki/alt/packages/contracts/gen/go/alt/v1"
protoSocket "git.toki-labs.com/toki/proto-socket/go"
)
// messageFactories lists every ALT protobuf message the CLI API client must
// decode. It mirrors the API/worker parser maps (services/api/internal/contracts
// and services/worker/internal/contracts) because Go's internal boundary keeps
// apps/cli from importing those packages. Keeping a single factory list here, as
// the runtime rails do, ensures a contract message cannot be registered through
// one runner path and missed in another.
func messageFactories() []func() proto.Message {
return []func() proto.Message{
func() proto.Message { return &altv1.HelloRequest{} },
func() proto.Message { return &altv1.HelloResponse{} },
// market read surface: instruments and bars
func() proto.Message { return &altv1.ListInstrumentsRequest{} },
func() proto.Message { return &altv1.ListInstrumentsResponse{} },
func() proto.Message { return &altv1.ListBarsRequest{} },
func() proto.Message { return &altv1.ListBarsResponse{} },
// market import command: daily bars
func() proto.Message { return &altv1.ImportDailyBarsRequest{} },
func() proto.Message { return &altv1.ImportDailyBarsResponse{} },
// backtest surface: start / list / detail / result / compare
func() proto.Message { return &altv1.StartBacktestRequest{} },
func() proto.Message { return &altv1.StartBacktestResponse{} },
func() proto.Message { return &altv1.GetBacktestRunRequest{} },
func() proto.Message { return &altv1.GetBacktestRunResponse{} },
func() proto.Message { return &altv1.GetBacktestResultRequest{} },
func() proto.Message { return &altv1.GetBacktestResultResponse{} },
func() proto.Message { return &altv1.BacktestResult{} },
func() proto.Message { return &altv1.ListBacktestRunsRequest{} },
func() proto.Message { return &altv1.ListBacktestRunsResponse{} },
func() proto.Message { return &altv1.GetBacktestRunDetailRequest{} },
func() proto.Message { return &altv1.GetBacktestRunDetailResponse{} },
func() proto.Message { return &altv1.CompareBacktestRunsRequest{} },
func() proto.Message { return &altv1.CompareBacktestRunsResponse{} },
// paper trading surface: start / state
func() proto.Message { return &altv1.StartPaperTradingRequest{} },
func() proto.Message { return &altv1.StartPaperTradingResponse{} },
func() proto.Message { return &altv1.GetPaperTradingStateRequest{} },
func() proto.Message { return &altv1.GetPaperTradingStateResponse{} },
func() proto.Message { return &altv1.PaperTradingState{} },
// paper order lifecycle surface: submit / cancel / fill
func() proto.Message { return &altv1.SubmitPaperOrderRequest{} },
func() proto.Message { return &altv1.SubmitPaperOrderResponse{} },
func() proto.Message { return &altv1.CancelPaperOrderRequest{} },
func() proto.Message { return &altv1.CancelPaperOrderResponse{} },
func() proto.Message { return &altv1.FillPaperOrderRequest{} },
func() proto.Message { return &altv1.FillPaperOrderResponse{} },
// live trading surface: broker capability probe
func() proto.Message { return &altv1.GetLiveBrokerCapabilitiesRequest{} },
func() proto.Message { return &altv1.GetLiveBrokerCapabilitiesResponse{} },
func() proto.Message { return &altv1.LiveBrokerCapability{} },
// live order lifecycle surface: submit / cancel / get
func() proto.Message { return &altv1.SubmitLiveOrderRequest{} },
func() proto.Message { return &altv1.SubmitLiveOrderResponse{} },
func() proto.Message { return &altv1.CancelLiveOrderRequest{} },
func() proto.Message { return &altv1.CancelLiveOrderResponse{} },
func() proto.Message { return &altv1.GetLiveOrderRequest{} },
func() proto.Message { return &altv1.GetLiveOrderResponse{} },
// live risk/kill switch surface: policy query, kill switch query/set
func() proto.Message { return &altv1.GetLiveRiskPolicyRequest{} },
func() proto.Message { return &altv1.GetLiveRiskPolicyResponse{} },
func() proto.Message { return &altv1.LiveRiskPolicy{} },
func() proto.Message { return &altv1.GetLiveKillSwitchRequest{} },
func() proto.Message { return &altv1.GetLiveKillSwitchResponse{} },
func() proto.Message { return &altv1.SetLiveKillSwitchRequest{} },
func() proto.Message { return &altv1.SetLiveKillSwitchResponse{} },
func() proto.Message { return &altv1.LiveKillSwitchState{} },
// live risk decision: included in SubmitLiveOrderResponse when risk blocked
func() proto.Message { return &altv1.LiveRiskDecision{} },
// live account sync surface: sync from broker / get last snapshot
func() proto.Message { return &altv1.SyncLiveAccountRequest{} },
func() proto.Message { return &altv1.SyncLiveAccountResponse{} },
func() proto.Message { return &altv1.GetLiveAccountSnapshotRequest{} },
func() proto.Message { return &altv1.GetLiveAccountSnapshotResponse{} },
func() proto.Message { return &altv1.LiveAccountSnapshot{} },
func() proto.Message { return &altv1.LiveCashBalance{} },
func() proto.Message { return &altv1.LivePositionSnapshot{} },
// live audit trail surface: list audit events
func() proto.Message { return &altv1.ListLiveAuditEventsRequest{} },
func() proto.Message { return &altv1.ListLiveAuditEventsResponse{} },
func() proto.Message { return &altv1.LiveAuditEvent{} },
}
}
// ParserMap returns a fresh ParserMap populated with all ALT messages the CLI
// runner can send or receive over the proto-socket API rail.
func ParserMap() protoSocket.ParserMap {
factories := messageFactories()
pm := make(protoSocket.ParserMap, len(factories))
for _, factory := range factories {
pm[protoSocket.TypeNameOf(factory())] = parserFor(factory)
}
return pm
}
func parserFor(factory func() proto.Message) func([]byte) (proto.Message, error) {
return func(data []byte) (proto.Message, error) {
msg := factory()
if err := proto.Unmarshal(data, msg); err != nil {
return nil, err
}
return msg, nil
}
}