feat(accounts): add explicit route binding workflow

This commit is contained in:
phamnazage-jpg
2026-05-29 19:07:01 +08:00
parent ad94feab72
commit 649eb13f30
8 changed files with 768 additions and 210 deletions

View File

@@ -26,72 +26,74 @@ import (
)
type ActionSet struct {
CreateBatchImportRun func(context.Context, CreateBatchImportRunRequest) (BatchImportRunCreateResponse, error)
ListBatchImportRuns func(context.Context, ListBatchImportRunsRequest) (ListBatchImportRunsResponse, error)
GetBatchImportRun func(context.Context, string) (batch.RunSummaryProjection, error)
ListBatchImportRunItems func(context.Context, ListBatchImportRunItemsRequest) (ListBatchImportRunItemsResponse, error)
GetBatchImportRunItem func(context.Context, GetBatchImportRunItemRequest) (batch.ItemDetailProjection, error)
CreateLogicalGroup func(context.Context, CreateLogicalGroupRequest) (LogicalGroupInfo, error)
ListLogicalGroups func(context.Context) ([]LogicalGroupInfo, error)
GetLogicalGroup func(context.Context, string) (LogicalGroupInfo, error)
UpdateLogicalGroup func(context.Context, UpdateLogicalGroupRequest) (LogicalGroupInfo, error)
DeleteLogicalGroup func(context.Context, string) error
CreateLogicalGroupModel func(context.Context, CreateLogicalGroupModelRequest) (LogicalGroupModelInfo, error)
ListLogicalGroupModels func(context.Context, string) ([]LogicalGroupModelInfo, error)
DeleteLogicalGroupModel func(context.Context, DeleteLogicalGroupModelRequest) error
CreateLogicalGroupRoute func(context.Context, CreateLogicalGroupRouteRequest) (LogicalGroupRouteInfo, error)
ListLogicalGroupRoutes func(context.Context, string) ([]LogicalGroupRouteInfo, error)
UpdateLogicalGroupRoute func(context.Context, UpdateLogicalGroupRouteRequest) (LogicalGroupRouteInfo, error)
DeleteLogicalGroupRoute func(context.Context, DeleteLogicalGroupRouteRequest) error
CreateLogicalGroupRouteModel func(context.Context, CreateLogicalGroupRouteModelRequest) (LogicalGroupRouteModelInfo, error)
ListLogicalGroupRouteModels func(context.Context, ListLogicalGroupRouteModelsRequest) ([]LogicalGroupRouteModelInfo, error)
AppendRouteDecisionLog func(context.Context, AppendRouteDecisionLogRequest) (RouteDecisionLogInfo, error)
ListRouteDecisionLogs func(context.Context, ListRouteDecisionLogsRequest) ([]RouteDecisionLogInfo, error)
AppendRouteFailoverEvent func(context.Context, AppendRouteFailoverEventRequest) (RouteFailoverEventInfo, error)
ListRouteFailoverEvents func(context.Context, ListRouteFailoverEventsRequest) ([]RouteFailoverEventInfo, error)
AppendRouteStickyAudit func(context.Context, AppendRouteStickyAuditRequest) (RouteStickyAuditInfo, error)
ListRouteStickyAudit func(context.Context, ListRouteStickyAuditRequest) ([]RouteStickyAuditInfo, error)
ListRouteHealth func(context.Context, ListRouteHealthRequest) ([]RouteHealthInfo, error)
ResolveRoute func(context.Context, ResolveRouteRequest) (ResolveRouteInfo, error)
RouteChatCompletions func(context.Context, RouteChatCompletionsRequest) (RouteChatCompletionsResult, error)
ProxyRouteChatCompletions func(context.Context, ProxyRouteChatCompletionsRequest) (ProxyRouteChatCompletionsResult, error)
SetStickyBinding func(context.Context, SetStickyBindingRequest) (StickyBindingInfo, error)
GetStickyBinding func(context.Context, GetStickyBindingRequest) (StickyBindingInfo, error)
SetRouteFailure func(context.Context, SetRouteFailureRequest) (RouteFailureInfo, error)
GetRouteFailure func(context.Context, GetRouteFailureRequest) (RouteFailureInfo, error)
SetRouteCooldown func(context.Context, SetRouteCooldownRequest) (RouteCooldownInfo, error)
GetRouteCooldown func(context.Context, GetRouteCooldownRequest) (RouteCooldownInfo, error)
ListProviderAccounts func(context.Context, ListProviderAccountsRequest) ([]ProviderAccountInfo, error)
EnableProviderAccount func(context.Context, UpdateProviderAccountStatusRequest) (ProviderAccountInfo, error)
DisableProviderAccount func(context.Context, UpdateProviderAccountStatusRequest) (ProviderAccountInfo, error)
RetireProviderAccount func(context.Context, UpdateProviderAccountStatusRequest) (ProviderAccountInfo, error)
CreateProviderDraft func(context.Context, CreateProviderDraftRequest) (ProviderDraftInfo, error)
ListProviderDrafts func(context.Context, ListProviderDraftsRequest) ([]ProviderDraftInfo, error)
GetProviderDraft func(context.Context, string) (ProviderDraftInfo, error)
UpdateProviderDraft func(context.Context, UpdateProviderDraftRequest) (ProviderDraftInfo, error)
DeleteProviderDraft func(context.Context, string) error
PublishProviderDraft func(context.Context, PublishProviderDraftRequest) (PublishProviderDraftResult, error)
InstallPack func(context.Context, InstallPackRequest) (provision.PackInstallResult, error)
BatchDetail func(context.Context, BatchDetailRequest) (provision.BatchDetailResult, error)
GetProviderStatus func(context.Context, ProviderQueryRequest) (provision.ProviderSnapshot, error)
GetProviderResources func(context.Context, ProviderQueryRequest) (provision.ProviderSnapshot, error)
GetProviderAccessStatus func(context.Context, ProviderQueryRequest) (provision.ProviderSnapshot, error)
ListProviderImportBatches func(context.Context, ProviderQueryRequest) ([]ImportBatchInfo, error)
PreviewProvider func(context.Context, PreviewProviderRequest) (provision.PreviewReport, error)
ImportProvider func(context.Context, ImportProviderRequest) (provision.RuntimeImportResult, error)
RollbackProvider func(context.Context, RollbackProviderRequest) (provision.RollbackReport, error)
RollbackBatch func(context.Context, RollbackBatchRequest) (provision.RollbackReport, error)
ReconcileProvider func(context.Context, ReconcileProviderRequest) (reconcile.Result, error)
CreateHost func(context.Context, CreateHostRequest) (HostInfo, error)
ProbeHost func(context.Context, ProbeHostRequest) (HostInfo, error)
ListHosts func(context.Context) ([]HostInfo, error)
GetHost func(context.Context, string) (HostInfo, error)
DeleteHost func(context.Context, string) error
ListPacks func(context.Context) ([]PackInfo, error)
GetPack func(context.Context, string) (PackInfo, error)
ListPackProviders func(context.Context, string) ([]PackProviderInfo, error)
AssignAccessSubscriptions func(context.Context, AssignAccessSubscriptionsRequest) (AssignAccessSubscriptionsResult, error)
AccessPreview func(context.Context, AccessPreviewRequest) (AccessPreviewResult, error)
CreateBatchImportRun func(context.Context, CreateBatchImportRunRequest) (BatchImportRunCreateResponse, error)
ListBatchImportRuns func(context.Context, ListBatchImportRunsRequest) (ListBatchImportRunsResponse, error)
GetBatchImportRun func(context.Context, string) (batch.RunSummaryProjection, error)
ListBatchImportRunItems func(context.Context, ListBatchImportRunItemsRequest) (ListBatchImportRunItemsResponse, error)
GetBatchImportRunItem func(context.Context, GetBatchImportRunItemRequest) (batch.ItemDetailProjection, error)
CreateLogicalGroup func(context.Context, CreateLogicalGroupRequest) (LogicalGroupInfo, error)
ListLogicalGroups func(context.Context) ([]LogicalGroupInfo, error)
GetLogicalGroup func(context.Context, string) (LogicalGroupInfo, error)
UpdateLogicalGroup func(context.Context, UpdateLogicalGroupRequest) (LogicalGroupInfo, error)
DeleteLogicalGroup func(context.Context, string) error
CreateLogicalGroupModel func(context.Context, CreateLogicalGroupModelRequest) (LogicalGroupModelInfo, error)
ListLogicalGroupModels func(context.Context, string) ([]LogicalGroupModelInfo, error)
DeleteLogicalGroupModel func(context.Context, DeleteLogicalGroupModelRequest) error
CreateLogicalGroupRoute func(context.Context, CreateLogicalGroupRouteRequest) (LogicalGroupRouteInfo, error)
ListLogicalGroupRoutes func(context.Context, string) ([]LogicalGroupRouteInfo, error)
UpdateLogicalGroupRoute func(context.Context, UpdateLogicalGroupRouteRequest) (LogicalGroupRouteInfo, error)
DeleteLogicalGroupRoute func(context.Context, DeleteLogicalGroupRouteRequest) error
CreateLogicalGroupRouteModel func(context.Context, CreateLogicalGroupRouteModelRequest) (LogicalGroupRouteModelInfo, error)
ListLogicalGroupRouteModels func(context.Context, ListLogicalGroupRouteModelsRequest) ([]LogicalGroupRouteModelInfo, error)
AppendRouteDecisionLog func(context.Context, AppendRouteDecisionLogRequest) (RouteDecisionLogInfo, error)
ListRouteDecisionLogs func(context.Context, ListRouteDecisionLogsRequest) ([]RouteDecisionLogInfo, error)
AppendRouteFailoverEvent func(context.Context, AppendRouteFailoverEventRequest) (RouteFailoverEventInfo, error)
ListRouteFailoverEvents func(context.Context, ListRouteFailoverEventsRequest) ([]RouteFailoverEventInfo, error)
AppendRouteStickyAudit func(context.Context, AppendRouteStickyAuditRequest) (RouteStickyAuditInfo, error)
ListRouteStickyAudit func(context.Context, ListRouteStickyAuditRequest) ([]RouteStickyAuditInfo, error)
ListRouteHealth func(context.Context, ListRouteHealthRequest) ([]RouteHealthInfo, error)
ResolveRoute func(context.Context, ResolveRouteRequest) (ResolveRouteInfo, error)
RouteChatCompletions func(context.Context, RouteChatCompletionsRequest) (RouteChatCompletionsResult, error)
ProxyRouteChatCompletions func(context.Context, ProxyRouteChatCompletionsRequest) (ProxyRouteChatCompletionsResult, error)
SetStickyBinding func(context.Context, SetStickyBindingRequest) (StickyBindingInfo, error)
GetStickyBinding func(context.Context, GetStickyBindingRequest) (StickyBindingInfo, error)
SetRouteFailure func(context.Context, SetRouteFailureRequest) (RouteFailureInfo, error)
GetRouteFailure func(context.Context, GetRouteFailureRequest) (RouteFailureInfo, error)
SetRouteCooldown func(context.Context, SetRouteCooldownRequest) (RouteCooldownInfo, error)
GetRouteCooldown func(context.Context, GetRouteCooldownRequest) (RouteCooldownInfo, error)
ListProviderAccounts func(context.Context, ListProviderAccountsRequest) ([]ProviderAccountInfo, error)
GetProviderAccountBindingCandidates func(context.Context, GetProviderAccountBindingCandidatesRequest) (ProviderAccountBindingCandidatesResult, error)
UpdateProviderAccountBinding func(context.Context, UpdateProviderAccountBindingRequest) (ProviderAccountInfo, error)
EnableProviderAccount func(context.Context, UpdateProviderAccountStatusRequest) (ProviderAccountInfo, error)
DisableProviderAccount func(context.Context, UpdateProviderAccountStatusRequest) (ProviderAccountInfo, error)
RetireProviderAccount func(context.Context, UpdateProviderAccountStatusRequest) (ProviderAccountInfo, error)
CreateProviderDraft func(context.Context, CreateProviderDraftRequest) (ProviderDraftInfo, error)
ListProviderDrafts func(context.Context, ListProviderDraftsRequest) ([]ProviderDraftInfo, error)
GetProviderDraft func(context.Context, string) (ProviderDraftInfo, error)
UpdateProviderDraft func(context.Context, UpdateProviderDraftRequest) (ProviderDraftInfo, error)
DeleteProviderDraft func(context.Context, string) error
PublishProviderDraft func(context.Context, PublishProviderDraftRequest) (PublishProviderDraftResult, error)
InstallPack func(context.Context, InstallPackRequest) (provision.PackInstallResult, error)
BatchDetail func(context.Context, BatchDetailRequest) (provision.BatchDetailResult, error)
GetProviderStatus func(context.Context, ProviderQueryRequest) (provision.ProviderSnapshot, error)
GetProviderResources func(context.Context, ProviderQueryRequest) (provision.ProviderSnapshot, error)
GetProviderAccessStatus func(context.Context, ProviderQueryRequest) (provision.ProviderSnapshot, error)
ListProviderImportBatches func(context.Context, ProviderQueryRequest) ([]ImportBatchInfo, error)
PreviewProvider func(context.Context, PreviewProviderRequest) (provision.PreviewReport, error)
ImportProvider func(context.Context, ImportProviderRequest) (provision.RuntimeImportResult, error)
RollbackProvider func(context.Context, RollbackProviderRequest) (provision.RollbackReport, error)
RollbackBatch func(context.Context, RollbackBatchRequest) (provision.RollbackReport, error)
ReconcileProvider func(context.Context, ReconcileProviderRequest) (reconcile.Result, error)
CreateHost func(context.Context, CreateHostRequest) (HostInfo, error)
ProbeHost func(context.Context, ProbeHostRequest) (HostInfo, error)
ListHosts func(context.Context) ([]HostInfo, error)
GetHost func(context.Context, string) (HostInfo, error)
DeleteHost func(context.Context, string) error
ListPacks func(context.Context) ([]PackInfo, error)
GetPack func(context.Context, string) (PackInfo, error)
ListPackProviders func(context.Context, string) ([]PackProviderInfo, error)
AssignAccessSubscriptions func(context.Context, AssignAccessSubscriptionsRequest) (AssignAccessSubscriptionsResult, error)
AccessPreview func(context.Context, AccessPreviewRequest) (AccessPreviewResult, error)
}
const maxJSONBodyBytes int64 = 1 << 20
@@ -439,6 +441,12 @@ func NewAPIHandlerWithAuth(adminAuth AdminAuthConfig, actions ActionSet) http.Ha
mux.Handle("GET /api/provider-accounts", requireAdminAccess(adminAuth, http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
handleListProviderAccounts(w, r, actions.ListProviderAccounts)
})))
mux.Handle("GET /api/provider-accounts/{accountID}/binding-candidates", requireAdminAccess(adminAuth, http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
handleGetProviderAccountBindingCandidates(w, r, actions.GetProviderAccountBindingCandidates)
})))
mux.Handle("POST /api/provider-accounts/{accountID}/binding", requireAdminAccess(adminAuth, http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
handleUpdateProviderAccountBinding(w, r, actions.UpdateProviderAccountBinding)
})))
mux.Handle("POST /api/provider-accounts/{accountID}/enable", requireAdminAccess(adminAuth, http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
handleEnableProviderAccount(w, r, actions.EnableProviderAccount)
})))
@@ -1261,45 +1269,47 @@ func NewActionSetWithStickyRuntime(sqliteDSN string, stickyRuntime stickyStoreRu
proxyRouteChatCompletions := buildProxyRouteChatCompletionsAction(sqliteDSN, resolveRoute, routeLogWriter)
routeChatCompletions := buildRouteChatCompletionsAction(proxyRouteChatCompletions)
return ActionSet{
CreateBatchImportRun: buildCreateBatchImportRunAction(sqliteDSN),
ListBatchImportRuns: buildListBatchImportRunsAction(sqliteDSN),
GetBatchImportRun: buildGetBatchImportRunAction(sqliteDSN),
ListBatchImportRunItems: buildListBatchImportRunItemsAction(sqliteDSN),
GetBatchImportRunItem: buildGetBatchImportRunItemAction(sqliteDSN),
CreateLogicalGroup: buildCreateLogicalGroupAction(sqliteDSN),
ListLogicalGroups: buildListLogicalGroupsAction(sqliteDSN),
GetLogicalGroup: buildGetLogicalGroupAction(sqliteDSN),
UpdateLogicalGroup: buildUpdateLogicalGroupAction(sqliteDSN),
DeleteLogicalGroup: buildDeleteLogicalGroupAction(sqliteDSN),
CreateLogicalGroupModel: buildCreateLogicalGroupModelAction(sqliteDSN),
ListLogicalGroupModels: buildListLogicalGroupModelsAction(sqliteDSN),
DeleteLogicalGroupModel: buildDeleteLogicalGroupModelAction(sqliteDSN),
CreateLogicalGroupRoute: buildCreateLogicalGroupRouteAction(sqliteDSN),
ListLogicalGroupRoutes: buildListLogicalGroupRoutesAction(sqliteDSN),
UpdateLogicalGroupRoute: buildUpdateLogicalGroupRouteAction(sqliteDSN),
DeleteLogicalGroupRoute: buildDeleteLogicalGroupRouteAction(sqliteDSN),
CreateLogicalGroupRouteModel: buildCreateLogicalGroupRouteModelAction(sqliteDSN),
ListLogicalGroupRouteModels: buildListLogicalGroupRouteModelsAction(sqliteDSN),
AppendRouteDecisionLog: buildAppendRouteDecisionLogAction(routeLogWriter, sqliteDSN),
ListRouteDecisionLogs: buildListRouteDecisionLogsAction(sqliteDSN),
AppendRouteFailoverEvent: buildAppendRouteFailoverEventAction(routeLogWriter, sqliteDSN),
ListRouteFailoverEvents: buildListRouteFailoverEventsAction(sqliteDSN),
AppendRouteStickyAudit: buildAppendRouteStickyAuditAction(routeLogWriter, sqliteDSN),
ListRouteStickyAudit: buildListRouteStickyAuditAction(sqliteDSN),
ListRouteHealth: buildListRouteHealthAction(sqliteDSN, stickyRuntime),
ResolveRoute: resolveRoute,
RouteChatCompletions: routeChatCompletions,
ProxyRouteChatCompletions: proxyRouteChatCompletions,
SetStickyBinding: buildSetStickyBindingAction(stickyRuntime),
GetStickyBinding: buildGetStickyBindingAction(stickyRuntime),
SetRouteFailure: buildSetRouteFailureAction(stickyRuntime),
GetRouteFailure: buildGetRouteFailureAction(stickyRuntime),
SetRouteCooldown: buildSetRouteCooldownAction(stickyRuntime),
GetRouteCooldown: buildGetRouteCooldownAction(stickyRuntime),
ListProviderAccounts: buildListProviderAccountsAction(sqliteDSN),
EnableProviderAccount: buildUpdateProviderAccountStatusAction(sqliteDSN, sqlite.ProviderAccountStatusActive),
DisableProviderAccount: buildUpdateProviderAccountStatusAction(sqliteDSN, sqlite.ProviderAccountStatusDisabled),
RetireProviderAccount: buildUpdateProviderAccountStatusAction(sqliteDSN, sqlite.ProviderAccountStatusDeprecated),
CreateBatchImportRun: buildCreateBatchImportRunAction(sqliteDSN),
ListBatchImportRuns: buildListBatchImportRunsAction(sqliteDSN),
GetBatchImportRun: buildGetBatchImportRunAction(sqliteDSN),
ListBatchImportRunItems: buildListBatchImportRunItemsAction(sqliteDSN),
GetBatchImportRunItem: buildGetBatchImportRunItemAction(sqliteDSN),
CreateLogicalGroup: buildCreateLogicalGroupAction(sqliteDSN),
ListLogicalGroups: buildListLogicalGroupsAction(sqliteDSN),
GetLogicalGroup: buildGetLogicalGroupAction(sqliteDSN),
UpdateLogicalGroup: buildUpdateLogicalGroupAction(sqliteDSN),
DeleteLogicalGroup: buildDeleteLogicalGroupAction(sqliteDSN),
CreateLogicalGroupModel: buildCreateLogicalGroupModelAction(sqliteDSN),
ListLogicalGroupModels: buildListLogicalGroupModelsAction(sqliteDSN),
DeleteLogicalGroupModel: buildDeleteLogicalGroupModelAction(sqliteDSN),
CreateLogicalGroupRoute: buildCreateLogicalGroupRouteAction(sqliteDSN),
ListLogicalGroupRoutes: buildListLogicalGroupRoutesAction(sqliteDSN),
UpdateLogicalGroupRoute: buildUpdateLogicalGroupRouteAction(sqliteDSN),
DeleteLogicalGroupRoute: buildDeleteLogicalGroupRouteAction(sqliteDSN),
CreateLogicalGroupRouteModel: buildCreateLogicalGroupRouteModelAction(sqliteDSN),
ListLogicalGroupRouteModels: buildListLogicalGroupRouteModelsAction(sqliteDSN),
AppendRouteDecisionLog: buildAppendRouteDecisionLogAction(routeLogWriter, sqliteDSN),
ListRouteDecisionLogs: buildListRouteDecisionLogsAction(sqliteDSN),
AppendRouteFailoverEvent: buildAppendRouteFailoverEventAction(routeLogWriter, sqliteDSN),
ListRouteFailoverEvents: buildListRouteFailoverEventsAction(sqliteDSN),
AppendRouteStickyAudit: buildAppendRouteStickyAuditAction(routeLogWriter, sqliteDSN),
ListRouteStickyAudit: buildListRouteStickyAuditAction(sqliteDSN),
ListRouteHealth: buildListRouteHealthAction(sqliteDSN, stickyRuntime),
ResolveRoute: resolveRoute,
RouteChatCompletions: routeChatCompletions,
ProxyRouteChatCompletions: proxyRouteChatCompletions,
SetStickyBinding: buildSetStickyBindingAction(stickyRuntime),
GetStickyBinding: buildGetStickyBindingAction(stickyRuntime),
SetRouteFailure: buildSetRouteFailureAction(stickyRuntime),
GetRouteFailure: buildGetRouteFailureAction(stickyRuntime),
SetRouteCooldown: buildSetRouteCooldownAction(stickyRuntime),
GetRouteCooldown: buildGetRouteCooldownAction(stickyRuntime),
ListProviderAccounts: buildListProviderAccountsAction(sqliteDSN),
GetProviderAccountBindingCandidates: buildGetProviderAccountBindingCandidatesAction(sqliteDSN),
UpdateProviderAccountBinding: buildUpdateProviderAccountBindingAction(sqliteDSN),
EnableProviderAccount: buildUpdateProviderAccountStatusAction(sqliteDSN, sqlite.ProviderAccountStatusActive),
DisableProviderAccount: buildUpdateProviderAccountStatusAction(sqliteDSN, sqlite.ProviderAccountStatusDisabled),
RetireProviderAccount: buildUpdateProviderAccountStatusAction(sqliteDSN, sqlite.ProviderAccountStatusDeprecated),
CreateProviderDraft: func(ctx context.Context, req CreateProviderDraftRequest) (ProviderDraftInfo, error) {
store, err := sqlite.Open(ctx, sqliteDSN)
if err != nil {