RepoPilot

How do their APIs compare?

About fatedier/frp · 2 messages · last activity 9/3/2026

Question

How do their APIs compare?

RepoPilot

These two projects have fundamentally different purposes and shapes of "API," so a direct comparison is really about how each exposes its functionality to Go programs.

frp: configuration-driven, service-oriented API

frp is not really designed as a library-first API — it's primarily a standalone reverse-proxy binary (frpc/frps) that is configured rather than scripted. Its Go-level "API" surface, as seen in the codebase, centers on:

  • Config structs and Complete()/validation methods — e.g., ClientCommonConfig.Complete() [pkg/config/v1/client.go:L85-L101], ServerTransportConfig.Complete() [pkg/config/v1/server.go:L182-L198], and AuthClientConfig.Complete() [pkg/config/v1/client.go:L206-L210]. These fill in defaults and are the main way callers configure a client/server before starting it.
  • Config loading — functions like LoadConfigure (exercised in [pkg/config/load_test.go:L694-L713]) and UnmarshalClientConfFromIni [pkg/config/legacy/client.go:L173-L203] parse YAML/TOML/JSON or legacy INI into these structs. RenderWithTemplate [pkg/config/load.go:L84-L99] supports templated config files.
  • Validation helpersGetClientConfigRequirements [pkg/config/v1/validation/client.go:L73-L98] inspects a completed config to determine runtime requirements (e.g., whether a virtual network stack is needed), and validateIncludeFiles [pkg/config/v1/validation/client.go:L177-L191] checks include-file references.
  • Message dispatch API — internally, pkg/msg provides a Dispatcher with Run() [pkg/msg/handler.go:L127-L131] and AsyncHandler [pkg/msg/handler.go:L102-L108] for handling the frp wire protocol between client and server, plus a registry-style msgCtl for message types [pkg/msg/ctl.go:L27-L33].

So frp's "API" is oriented around struct-based configuration objects with completion/validation lifecycles, then handing them to internal service/dispatcher machinery. It's not designed to be embedded as a general-purpose library for arbitrary programs — it's the internals of the frpc/frps binaries.

mvdan/sh: library-first parsing/interpretation API

mvdan/sh, by contrast, is explicitly designed as a Go library for shell script tooling, and its public API is built around composable, functional-options-style packages:

  • syntax package — provides a parser (syntax.NewParser, referenced conceptually via generated token/parsing code like [syntax/gen_token_parse.go:L117-L134]) to turn shell source into an AST.
  • interp package — provides interp.New/Runner for executing parsed scripts, with pluggable behavior via options like interp.ExecHandlers, exercised extensively in tests such as [interp/handler_test.go:L238-L277] and the built-in help command handling in runHelp [interp/help.go:L142-L215].
  • pattern package — exposes glob/pattern-to-regexp translation (Mode flags like Filenames, EntireString, Shortest, NoGlobCase), as shown extensively in [pattern/pattern_test.go:L1-L120] and implemented in [pattern/pattern.go:L325-L364].
  • fileutil package — small utilities like Shebang() for detecting shell interpreters from a script's shebang line [fileutil/file_test.go:L11-L68].

Key contrast

  • Design intent: frp's API is internal/config-driven — you build and complete config structs, then the binary's service layer consumes them; it's not meant for embedding arbitrary logic. mvdan/sh's API is explicitly a general-purpose library (parser + interpreter + pattern engine) meant to be imported and extended by other Go programs (e.g., shellcheck-like tools, custom shells).
  • Extensibility model: frp extends behavior through config fields and completion defaults (Complete() methods) and message-type registration (msgCtl). mvdan/sh extends behavior through functional options (interp.ExecHandlers(...)) and **bitmask Mode fl

Want to ask your own question?

Open chat for fatedier/frp

Public Q&A. Generated by RepoPilot from the actual source of fatedier/frp. AI answers can be incomplete or stale — verify before relying on them.