cli

package
v0.4.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 25, 2026 License: MIT Imports: 18 Imported by: 0

Documentation

Overview

Package cli wires the kong grammar, the runtime, and the exit-code mapping. main() does nothing but os.Exit(cli.Run(...)) so every path is testable in-process.

Index

Constants

View Source
const DefaultAssociateTag = "rivr-20"

DefaultAssociateTag is rivr's built-in Amazon Associates tag. When the user neither supplies their own (--associate-tag / RIVR_ASSOCIATE_TAG) nor opts out (--no-associate-tag), product deep links carry this tag.

What it does: if a referred link results in a purchase, Amazon pays the project a small referral fee. The buyer pays nothing extra. It funds rivr's development AND helps the project meet the Amazon Creators API's qualified-sales minimums (which gate official-API access). It is fully disclosed (visible in every URL, in `doctor`, in `schema`, and in the docs), replaceable with your own tag, and disablable.

This is the project's real registered Amazon Associates tag (US store; "-20" suffix).

Variables

This section is empty.

Functions

func Run

func Run(args []string, stdin io.Reader, stdout, stderr io.Writer) int

Run parses args and dispatches, returning the process exit code.

Types

type AgentCmd

type AgentCmd struct{}

func (*AgentCmd) Run

func (c *AgentCmd) Run(rt *Runtime) error

type AuthCmd

type AuthCmd struct {
	Status  AuthStatusCmd  `cmd:"" help:"Test credentials and show auth status for the active provider."`
	Login   AuthLoginCmd   `cmd:"" help:"Store a provider credential (read from stdin)."`
	Logout  AuthLogoutCmd  `cmd:"" help:"Remove LOCAL credentials for a provider."`
	Refresh AuthRefreshCmd `cmd:"" help:"Refresh the official backend's OAuth token."`
}

AuthCmd groups credential management. Secrets are read from STDIN, never argv (contract §7), and stored via internal/auth (env → OS keyring → 0600 file fallback).

type AuthLoginCmd

type AuthLoginCmd struct{}

func (*AuthLoginCmd) Run

func (c *AuthLoginCmd) Run(rt *Runtime) error

type AuthLogoutCmd

type AuthLogoutCmd struct{}

func (*AuthLogoutCmd) Run

func (c *AuthLogoutCmd) Run(rt *Runtime) error

type AuthRefreshCmd

type AuthRefreshCmd struct{}

func (*AuthRefreshCmd) Run

func (c *AuthRefreshCmd) Run(rt *Runtime) error

type AuthStatusCmd

type AuthStatusCmd struct{}

func (*AuthStatusCmd) Run

func (c *AuthStatusCmd) Run(rt *Runtime) error

type BrowseCmd

type BrowseCmd struct {
	NodeID string `arg:"" name:"node-id" help:"Browse-node id."`
}

BrowseCmd implements `rivr browse <node-id>` (read). Browse nodes are an official Creators-API feature; providers that lack it return UNSUPPORTED_BY_PROVIDER.

func (*BrowseCmd) Run

func (c *BrowseCmd) Run(rt *Runtime) error

type CLI

type CLI struct {
	// Output (contract §1, §6)
	Format   string `enum:"json,plain,tsv" default:"plain" help:"Output format: json, plain, or tsv."`
	JSON     bool   `help:"Shorthand for --format=json."`
	NoColor  bool   `help:"Disable colored output."`
	Limit    int    `default:"50" help:"Maximum items to return for list operations."`
	Select   string `help:"Comma-separated dot-path field projection, e.g. asin,title,price."`
	Concise  bool   `help:"Terser output (default)."`
	Detailed bool   `help:"Richer output."`

	// Backend (rivr-specific)
	Provider       string `help:"Backend provider (e.g. serpapi, rainforest, creators). Overrides the configured default." env:"RIVR_PROVIDER"`
	AssociateTag   string `` /* 142-byte string literal not displayed */
	NoAssociateTag bool   `` /* 148-byte string literal not displayed */

	// Prompt-injection hardening (contract §8) — ON by default; --no-wrap-untrusted to disable.
	WrapUntrusted bool `default:"true" negatable:"" help:"Fence attacker-controllable free text (titles, descriptions, reviews) as untrusted."`

	// Safety (contract §2). rivr is read-only: these are present for contract uniformity
	// but inert — no command performs a mutation.
	AllowMutations bool `help:"Permit state-changing operations (no-op: rivr is read-only)."`
	DryRun         bool `help:"Print intended mutations without performing them (no-op: rivr is read-only)."`
	Yes            bool `help:"Assume yes for confirmations (no-op: rivr is read-only)."`
	Force          bool `help:"Bypass safety checks (no-op: rivr is read-only)."`
	NoInput        bool `help:"Never prompt; fail with exit 13 instead."`

	// Commands (all reads)
	Search     SearchCmd     `cmd:"" help:"Search Amazon products by keyword/category."`
	Item       ItemCmd       `cmd:"" help:"Get product detail and offers."`
	Reviews    ReviewsCmd    `cmd:"" help:"Get customer reviews for a product (third-party providers only)."`
	Variations VariationsCmd `cmd:"" help:"List size/color/style variations of a product."`
	Browse     BrowseCmd     `cmd:"" help:"Inspect the browse-node (category) tree."`
	ProviderC  ProviderCmd   `cmd:"" name:"provider" help:"List and inspect configured backends."`
	Auth       AuthCmd       `cmd:"" help:"Manage provider credentials."`
	Doctor     DoctorCmd     `cmd:"" help:"Diagnose setup and report fixes."`
	Schema     SchemaCmd     `cmd:"" help:"Print the machine-readable command schema (JSON)."`
	Agent      AgentCmd      `cmd:"" help:"Print the bundled agent SKILL.md."`
	Version    VersionCmd    `cmd:"" help:"Print the version."`
}

CLI is the kong grammar. Global flags are the universal agent-CLI contract surface plus rivr-specific --provider and --wrap-untrusted; subcommands follow noun-verb grammar.

type DoctorCmd

type DoctorCmd struct{}

func (*DoctorCmd) Run

func (c *DoctorCmd) Run(rt *Runtime) error

type ItemCmd

type ItemCmd struct {
	Get     ItemGetCmd     `cmd:"" help:"Get full product detail for one or more ASINs."`
	Offers  ItemOffersCmd  `cmd:"" help:"Get live offers / buybox / availability for an ASIN."`
	Compare ItemCompareCmd `cmd:"" help:"Compare two or more ASINs side-by-side with a best-of summary."`
}

ItemCmd groups product-detail read subcommands.

type ItemCompareCmd added in v0.2.0

type ItemCompareCmd struct {
	ASIN []string `arg:"" help:"Two or more product ASINs to compare."`
}

ItemCompareCmd implements `rivr item compare <asin...>` (read): fetch each ASIN and return them alongside a "best-of" summary (cheapest / highest-rated / most-reviewed), so an agent doesn't have to hand-assemble a comparison from N separate `item get` calls.

func (*ItemCompareCmd) Run added in v0.2.0

func (c *ItemCompareCmd) Run(rt *Runtime) error

type ItemGetCmd

type ItemGetCmd struct {
	ASIN []string `arg:"" help:"One or more product ASINs."`
}

ItemGetCmd implements `rivr item get <asin...>` (read).

func (*ItemGetCmd) Run

func (c *ItemGetCmd) Run(rt *Runtime) error

type ItemOffersCmd

type ItemOffersCmd struct {
	ASIN string `arg:"" help:"Product ASIN."`
}

ItemOffersCmd implements `rivr item offers <asin>` (read).

func (*ItemOffersCmd) Run

func (c *ItemOffersCmd) Run(rt *Runtime) error

type ProviderCmd

type ProviderCmd struct {
	List ProviderListCmd `cmd:"" help:"List configured backends and their capabilities."`
}

ProviderCmd groups backend-management read subcommands.

type ProviderListCmd

type ProviderListCmd struct{}

ProviderListCmd implements `rivr provider list` (read).

func (*ProviderListCmd) Run

func (c *ProviderListCmd) Run(rt *Runtime) error

type ReviewsCmd

type ReviewsCmd struct {
	ASIN   string `arg:"" help:"Product ASIN."`
	Cursor string `help:"Opaque pagination cursor from a previous nextCursor."`
}

ReviewsCmd implements `rivr reviews <asin>` (read). Review text is the sharpest prompt-injection vector — bodies/titles are always fenced. Not all backends serve it (the official Creators API returns no review text → UNSUPPORTED_BY_PROVIDER).

func (*ReviewsCmd) Run

func (c *ReviewsCmd) Run(rt *Runtime) error

type Runtime

type Runtime struct {
	Cfg   *CLI
	Out   *output.Writer
	Stdin io.Reader
	Ctx   context.Context
	// contains filtered or unexported fields
}

Runtime is the per-invocation context bound into every command's Run method.

func (*Runtime) Fence

func (rt *Runtime) Fence(s string) string

Fence wraps a free-text value as untrusted when --wrap-untrusted is on (contract §8).

func (*Runtime) FenceAll

func (rt *Runtime) FenceAll(ss []string) []string

FenceAll fences a slice of free-text values.

func (*Runtime) Guard

func (rt *Runtime) Guard(op string) error

Guard enforces the read-only-by-default mutation gate (contract §2). rivr has no mutating commands, so this is never reached at runtime — kept for contract uniformity.

func (rt *Runtime) Link(u string) string

Link decorates a product deep link with the active Associates tag. The CLI is read-only; the deep link is its terminal hand-off to amazon.com (purchase happens in the user's browser session). By default the built-in project tag is used (see affiliate.go); a user tag replaces it, and --no-associate-tag disables it (with a one-time stderr notice). Non-product URLs (e.g. images) are not passed through here.

func (*Runtime) PartnerTag

func (rt *Runtime) PartnerTag() string

PartnerTag returns the tag to send to the official Creators API, which REQUIRES a partnerTag on every request. Unlike deep-link decoration, this can't be empty: a user tag wins, otherwise the built-in default (even when link-decoration is opted out).

func (*Runtime) Provider

func (rt *Runtime) Provider() (provider.Provider, error)

Provider resolves the active backend (flag > RIVR_PROVIDER > default), erroring with a structured config/auth error when unknown or unconfigured.

type SchemaCmd

type SchemaCmd struct{}

func (*SchemaCmd) Run

func (c *SchemaCmd) Run(rt *Runtime) error

type SearchCmd

type SearchCmd struct {
	Query     string  `arg:"" help:"Search keywords."`
	Category  string  `help:"Restrict to a category / browse node."`
	MinRating float64 `name:"min-rating" help:"Minimum average star rating (0-5)."`
	Prime     bool    `help:"Only Prime-eligible offers."`
	MinPrice  float64 `name:"min-price" help:"Minimum price."`
	MaxPrice  float64 `name:"max-price" help:"Maximum price."`
	Sort      string  `help:"Sort order (provider-defined, e.g. relevance, price-asc, rating)."`
	Cursor    string  `help:"Opaque pagination cursor from a previous nextCursor."`
}

SearchCmd implements `rivr search <query>` (read).

func (*SearchCmd) Run

func (c *SearchCmd) Run(rt *Runtime) error

type VariationsCmd

type VariationsCmd struct {
	ASIN string `arg:"" help:"Parent product ASIN."`
}

VariationsCmd implements `rivr variations <asin>` (read).

func (*VariationsCmd) Run

func (c *VariationsCmd) Run(rt *Runtime) error

type VersionCmd

type VersionCmd struct {
	Check bool `help:"Check GitHub for a newer release (network)."`
}

func (*VersionCmd) Run

func (c *VersionCmd) Run(rt *Runtime) error

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL