AgentStack
SKILL verified Apache-2.0 Self-run

Finfocus Plugin

skill-rshade-finfocus-finfocus-plugin · by rshade

>

No reviews yet
0 installs
15 views
0.0% view→install

Install

$ agentstack add skill-rshade-finfocus-finfocus-plugin

✓ scanned · ✓ verified — works with Claude Code, Cursor, and more.

Security review

✓ Passed

No issues found. Passed automated security review. · v0.1.0 How review works →

  • Prompt-injection patterns
  • Secret / credential exfiltration
  • Dangerous shell & filesystem operations
  • Untrusted network calls
  • Known-malicious package signatures

What it can access

  • Network access No
  • Filesystem access No
  • Shell / process execution No
  • Environment & secrets No
  • Dynamic code execution No

From automated source analysis of v0.1.0. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.

Are you the author of Finfocus Plugin? Claim this listing to set pricing, connect Stripe payouts, and keep 70% of every sale.
Sign up to claim

About

FinFocus Plugin Development

Plugin Architecture

Plugins communicate with finfocus-core via gRPC using protocol buffers from finfocus-spec. Each plugin is a standalone binary that implements the CostSourceService.

Core CLI -> gRPC -> Plugin Binary
                    (CostSourceService)

Two launcher types:

  • ProcessLauncher (TCP) - Plugin listens on a port
  • StdioLauncher (stdin/stdout) - Plugin communicates over stdio

Quick Start: New Plugin

  1. Create Go module with finfocus-spec dependency
  2. Embed pluginsdk.BasePlugin for common functionality
  3. Implement required gRPC methods
  4. Build binary and install to ~/.finfocus/plugins///
import (
    "github.com/rshade/finfocus-spec/sdk/go/pluginsdk"
    pbc "github.com/rshade/finfocus-spec/sdk/go/proto/finfocus/v1"
)

type MyPlugin struct {
    *pluginsdk.BasePlugin
    logger zerolog.Logger
    mu     sync.Mutex
}

func (p *MyPlugin) Name() string { return "my-plugin" }

Required Methods

Every plugin must implement these CostSourceService methods:

| Method | Purpose | |--------|---------| | GetProjectedCost | Estimate future costs from resource descriptors | | GetActualCost | Return historical costs for a time range | | GetRecommendations | Return cost optimization recommendations | | GetPluginInfo | Return plugin metadata (name, version, providers) | | Shutdown | Clean up resources on termination |

Request Validation

Use pluginsdk validation helpers before processing:

func (p *MyPlugin) GetProjectedCost(ctx context.Context, req *pbc.GetProjectedCostRequest) (*pbc.GetProjectedCostResponse, error) {
    p.mu.Lock()
    defer p.mu.Unlock()

    if err := pluginsdk.ValidateProjectedCostRequest(req); err != nil {
        return nil, status.Errorf(codes.InvalidArgument, "validation: %v", err)
    }
    // Process request...
}

Plugin Installation

Plugins install to ~/.finfocus/plugins///:

# Build and install
make build-recorder
make install-recorder  # -> ~/.finfocus/plugins/recorder/0.1.0/

# Verify
./bin/finfocus plugin list
./bin/finfocus plugin validate

Environment Variables

Plugins receive these from core via pluginsdk constants:

| Constant | Env Var | Purpose | |----------|---------|---------| | pluginsdk.EnvPort | FINFOCUS_PLUGIN_PORT | gRPC port | | pluginsdk.EnvLogLevel | FINFOCUS_LOG_LEVEL | Log verbosity | | pluginsdk.EnvLogFormat | FINFOCUS_LOG_FORMAT | json or text | | pluginsdk.EnvLogFile | FINFOCUS_LOG_FILE | Log file path | | pluginsdk.EnvTraceID | FINFOCUS_TRACE_ID | Distributed trace ID |

Trace ID Propagation

// Server-side: extract trace ID from incoming gRPC metadata
server := grpc.NewServer(
    grpc.UnaryInterceptor(pluginsdk.TracingUnaryServerInterceptor()),
)

// In handlers: get trace ID from context
traceID := pluginsdk.TraceIDFromContext(ctx)

Reference Implementation

The recorder plugin at plugins/recorder/ demonstrates all patterns. See [references/recorder-reference.md](references/recorder-reference.md) for the complete implementation walkthrough.

Plugin Communication Details

See [references/pluginsdk-api.md](references/pluginsdk-api.md) for the full pluginsdk API, proto message types, and gRPC patterns.

Testing Plugins

go test ./plugins/recorder/...                       # Unit tests
go test ./test/integration/recorder_test.go          # Integration
go test -bench=BenchmarkRecorder ./plugins/recorder/... # Perf (<10ms)

Common Pitfalls

  • Always use sync.Mutex for thread safety in gRPC handlers
  • Return status.Errorf(codes.InvalidArgument, ...) for validation errors
  • Call cmd.Wait() after Kill() to prevent zombie processes
  • 10-second timeout with 100ms retry delays for plugin startup
  • Platform-specific binary detection (Unix permissions vs Windows .exe)

Source & license

This open-source skill is cataloged on AgentStack and links to its original source — we do not rehost the code.

  • Author: rshade
  • Source: rshade/finfocus
  • License: Apache-2.0
  • Homepage: https://rshade.github.io/finfocus/

Install and usage instructions live in the source repository linked above.

Reviews

No reviews yet — be the first.

Versions

  • v0.1.0 Imported from the upstream source.