diff --git a/cmd/server/main.go b/cmd/server/main.go index bcb437d0d..80b029f3d 100644 --- a/cmd/server/main.go +++ b/cmd/server/main.go @@ -306,7 +306,7 @@ func main() { var errHomePlugins error homePluginSyncReport, errHomePlugins = homeplugins.SyncWithReport(ctxHomePlugins, parsed, pluginHost) cancelHomePlugins() - errReportPlugins := reportHomePluginStatus(context.Background(), homeClient, homeCfg.NodeID, homePluginSyncReport) + errReportPlugins := home.ReportPluginStatus(context.Background(), homeClient, homeCfg.NodeID, homePluginSyncReport) if errHomePlugins != nil { log.Errorf("failed to fetch plugins from home: %v", errHomePlugins) } @@ -570,7 +570,7 @@ func main() { pluginHost.ApplyConfig(context.Background(), cfg) if configLoadedFromHome { errHomePluginLoad := homeplugins.MarkLoadResults(&homePluginSyncReport, pluginHost) - errReportPlugins := reportHomePluginStatus(context.Background(), homeClient, cfg.Home.NodeID, homePluginSyncReport) + errReportPlugins := home.ReportPluginStatus(context.Background(), homeClient, cfg.Home.NodeID, homePluginSyncReport) if errHomePluginLoad != nil { log.Errorf("failed to load home plugins: %v", errHomePluginLoad) } diff --git a/cmd/server/home_plugin_status.go b/internal/home/plugin_status.go similarity index 56% rename from cmd/server/home_plugin_status.go rename to internal/home/plugin_status.go index 63229685d..71c01a5ca 100644 --- a/cmd/server/home_plugin_status.go +++ b/internal/home/plugin_status.go @@ -1,4 +1,4 @@ -package main +package home import ( "context" @@ -10,13 +10,16 @@ import ( "github.com/router-for-me/CLIProxyAPI/v7/internal/homeplugins" ) -const homePluginStatusReportTimeout = 10 * time.Second +const pluginStatusReportTimeout = 10 * time.Second -type homePluginStatusClient interface { +// PluginStatusClient defines the interface for pushing plugin status reports. +type PluginStatusClient interface { RPushPluginStatus(ctx context.Context, payload []byte) error } -func reportHomePluginStatus(ctx context.Context, client homePluginStatusClient, nodeID string, report homeplugins.SyncReport) error { +// ReportPluginStatus marshals the given report, sets NodeID and UpdatedAt, +// and pushes it to the provided client with a timeout. +func ReportPluginStatus(ctx context.Context, client PluginStatusClient, nodeID string, report homeplugins.SyncReport) error { if client == nil { return fmt.Errorf("home plugin status client is unavailable") } @@ -33,7 +36,7 @@ func reportHomePluginStatus(ctx context.Context, client homePluginStatusClient, if ctx == nil { ctx = context.Background() } - reportCtx, cancel := context.WithTimeout(ctx, homePluginStatusReportTimeout) + reportCtx, cancel := context.WithTimeout(ctx, pluginStatusReportTimeout) defer cancel() return client.RPushPluginStatus(reportCtx, raw) } diff --git a/cmd/server/home_plugin_status_test.go b/internal/home/plugin_status_test.go similarity index 57% rename from cmd/server/home_plugin_status_test.go rename to internal/home/plugin_status_test.go index 3cd860740..a71333fd2 100644 --- a/cmd/server/home_plugin_status_test.go +++ b/internal/home/plugin_status_test.go @@ -1,4 +1,4 @@ -package main +package home import ( "context" @@ -10,18 +10,18 @@ import ( "github.com/router-for-me/CLIProxyAPI/v7/internal/homeplugins" ) -type recordingHomePluginStatusClient struct { +type recordingPluginStatusClient struct { payload []byte err error } -func (c *recordingHomePluginStatusClient) RPushPluginStatus(ctx context.Context, payload []byte) error { +func (c *recordingPluginStatusClient) RPushPluginStatus(ctx context.Context, payload []byte) error { c.payload = append([]byte(nil), payload...) return c.err } -func TestReportHomePluginStatusPushesNodeReport(t *testing.T) { - client := &recordingHomePluginStatusClient{} +func TestReportPluginStatusPushesNodeReport(t *testing.T) { + client := &recordingPluginStatusClient{} report := homeplugins.SyncReport{ Task: "plugin-sync", Status: "success", @@ -29,8 +29,8 @@ func TestReportHomePluginStatusPushesNodeReport(t *testing.T) { Plugins: []homeplugins.PluginInstallStatus{{ID: "sample", InstallStatus: "installed"}}, } - if errReport := reportHomePluginStatus(context.Background(), client, " node-1 ", report); errReport != nil { - t.Fatalf("reportHomePluginStatus() error = %v", errReport) + if errReport := ReportPluginStatus(context.Background(), client, " node-1 ", report); errReport != nil { + t.Fatalf("ReportPluginStatus() error = %v", errReport) } var payload homeplugins.SyncReport if errUnmarshal := json.Unmarshal(client.payload, &payload); errUnmarshal != nil { @@ -44,8 +44,8 @@ func TestReportHomePluginStatusPushesNodeReport(t *testing.T) { } } -func TestReportHomePluginStatusPushesEmptyReport(t *testing.T) { - client := &recordingHomePluginStatusClient{} +func TestReportPluginStatusPushesEmptyReport(t *testing.T) { + client := &recordingPluginStatusClient{} report := homeplugins.SyncReport{ Task: "plugin-sync", Status: "success", @@ -53,8 +53,8 @@ func TestReportHomePluginStatusPushesEmptyReport(t *testing.T) { Plugins: []homeplugins.PluginInstallStatus{}, } - if errReport := reportHomePluginStatus(context.Background(), client, "node-1", report); errReport != nil { - t.Fatalf("reportHomePluginStatus() error = %v", errReport) + if errReport := ReportPluginStatus(context.Background(), client, "node-1", report); errReport != nil { + t.Fatalf("ReportPluginStatus() error = %v", errReport) } var payload homeplugins.SyncReport if errUnmarshal := json.Unmarshal(client.payload, &payload); errUnmarshal != nil { @@ -65,29 +65,29 @@ func TestReportHomePluginStatusPushesEmptyReport(t *testing.T) { } } -func TestReportHomePluginStatusRequiresNodeID(t *testing.T) { - client := &recordingHomePluginStatusClient{} +func TestReportPluginStatusRequiresNodeID(t *testing.T) { + client := &recordingPluginStatusClient{} report := homeplugins.SyncReport{ Plugins: []homeplugins.PluginInstallStatus{{ID: "sample", InstallStatus: "failed"}}, } - errReport := reportHomePluginStatus(context.Background(), client, " ", report) + errReport := ReportPluginStatus(context.Background(), client, " ", report) if errReport == nil || !strings.Contains(errReport.Error(), "node id") { - t.Fatalf("reportHomePluginStatus() error = %v, want node id error", errReport) + t.Fatalf("ReportPluginStatus() error = %v, want node id error", errReport) } if len(client.payload) != 0 { t.Fatalf("client payload = %s, want none", client.payload) } } -func TestReportHomePluginStatusPropagatesPushError(t *testing.T) { - client := &recordingHomePluginStatusClient{err: errors.New("push failed")} +func TestReportPluginStatusPropagatesPushError(t *testing.T) { + client := &recordingPluginStatusClient{err: errors.New("push failed")} report := homeplugins.SyncReport{ Plugins: []homeplugins.PluginInstallStatus{{ID: "sample", InstallStatus: "installed"}}, } - errReport := reportHomePluginStatus(context.Background(), client, "node-1", report) + errReport := ReportPluginStatus(context.Background(), client, "node-1", report) if !errors.Is(errReport, client.err) { - t.Fatalf("reportHomePluginStatus() error = %v, want push failed", errReport) + t.Fatalf("ReportPluginStatus() error = %v, want push failed", errReport) } }