apikit

package module
v0.1.0 Latest Latest
Warning

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

Go to latest
Published: Nov 11, 2026 License: MIT Imports: 12 Imported by: 0

README

api-kit

Go Reference Test

api-kit turns a declarative description of a REST API into a command-line tool. A YAML definition names the resources of an API, how they relate, and the calls that change them; api-kit supplies the rest: authentication and token caching, fetching with pagination, joins across resources, multi-step calls with templates and conditions, and the commands, flags and shell completion that expose all of it.

api-kit ships no API of its own. A binary embeds its definition and calls cli.Run.

[!NOTE] api-kit is under construction. Packages land one by one and their APIs change without notice until the first tagged release.

Installation

go get github.com/mittwald/api-kit

api-kit supports Go 1.27 and newer on Linux, macOS and Windows. It builds on cli-kit and cobra.

Packages

Package What it does
apikit JSON values that keep key order and number spelling, and error kinds with the exit codes they map to
expr The small languages of a definition: templates, paths into values, conditions
definition Loads a definition, merges the user's overlays into it and reports every mistake with its key
auth Token sources, stored sessions, validation, renewal and logins, as the definition describes them
engine Requests with caching and retries, listings with pagination, IDs from aliases and searches
output Results as tables, JSON, YAML, CSV, JSONPath selections and plain lines
cli The command tree of a tool, generated from its definition, with shell completion
apitest A scripted fake API for tests, and the definition of an invented pet shop

Example

A definition names the environments of an API and describes its resources:

environments:
  production:
    apis:
      main: https://api.example.test/v1
resources:
  pets:
    columns: [id, name, species]
    filters: ["species="]

A tool embeds it and hands over to cli.Run:

package main

import (
	"context"
	_ "embed"
	"os"

	"github.com/mittwald/cli-kit/buildinfo"

	"github.com/mittwald/api-kit/cli"
	"github.com/mittwald/api-kit/definition"
)

//go:embed definition.yaml
var api []byte

func main() {
	os.Exit(cli.Run(context.Background(), cli.Options{
		Name:       "example",
		Short:      "Query and change the Example API",
		Build:      buildinfo.Get(),
		Definition: definition.Source{Name: "definition.yaml", Data: api},
	}, os.Args[1:]))
}
$ example get pets --filter species=cat
ID        NAME  SPECIES
0a1b2c3e  Tom   cat
$ example get pets 0a1b2c3e -o json

examples/petstore is a complete tool of this kind, with joins, ID aliases, calls that change data and a test that runs it against a fake API.

Versioning

api-kit follows semantic versioning. While it is v0.x, minor releases may change APIs; such changes are listed first in the release notes.

Contributing

Contributions are welcome. See CONTRIBUTING.md for how to build, test and submit changes, and SECURITY.md for reporting vulnerabilities.

License

Copyright (c) 2026 Mittwald CM Service GmbH & Co. KG and contributors

This project is licensed under the MIT License; see the LICENSE file for details.

Documentation

Overview

Package apikit holds what every package of api-kit shares: the kinds of errors the engine reports and the exit codes a command-line tool maps them to.

api-kit turns a declarative description of a REST API into a command-line tool. The packages below this one never print or exit; they return errors that carry a Kind, and package cli decides what to print and which exit code to use.

Index

Constants

View Source
const (
	// ExitOK is the exit code of a successful run.
	ExitOK = 0
	// ExitFailed is the exit code of a failed run.
	ExitFailed = 1
	// ExitUsage is the exit code for a mistake on the command line.
	ExitUsage = 2
	// ExitSkipped is the exit code when nothing was done on purpose.
	ExitSkipped = 3
	// ExitNotFound is the exit code when the resource does not exist.
	ExitNotFound = 4
	// ExitCanceled is the exit code of an interrupted run, 128 plus the
	// number of the interrupt signal.
	ExitCanceled = 130
)

Exit codes a command-line tool ends with.

Variables

This section is empty.

Functions

func Clone

func Clone(v any) any

Clone returns a deep copy of a value of the types Decode produces. Scalars are returned as they are.

func Decode

func Decode(r io.Reader) (any, error)

Decode reads one JSON value from r. Objects become *Object and keep the order of their keys, numbers become json.Number and keep their exact spelling, arrays become []any (never nil). Anything but white space after the value is an error.

func Equal

func Equal(a, b any) bool

Equal reports whether two values of the types Decode produces are the same data: objects have the same keys with equal values, whatever their order; lists have equal elements in the same order; numbers are compared by value, so 1, 1.0 and 1e0 are equal.

func ExitCode

func ExitCode(err error) int

ExitCode returns the exit code for err, ExitOK for nil.

func Falsy

func Falsy(v any) bool

Falsy reports whether a value of the types Decode produces counts as "nothing there": null, false, the empty string, a number equal to zero, an empty list or an empty object.

func Marshal

func Marshal(v any) ([]byte, error)

Marshal returns the compact JSON encoding of v. Unlike json.Marshal it leaves <, > and & as they are: the result is sent to an API or shown in a terminal, not embedded in HTML.

func Normalize

func Normalize(v any) (any, error)

Normalize converts a value built from ordinary Go types into the types Decode produces: every integer and floating-point type becomes a json.Number, map[string]any becomes an *Object with its keys sorted, and slices become []any. Values that already have those types are returned as they are, lists and objects are converted in depth. It returns an error for a value JSON cannot hold, such as a channel or a NaN.

func Text

func Text(v any) string

Text returns a value of the types Decode produces as a person or a template sees it: nothing for null, true or false for a boolean, a string as it is, a number as it was spelled, and a list or an object as one line of JSON with a space after every comma and colon.

func Unmarshal

func Unmarshal(data []byte) (any, error)

Unmarshal decodes one JSON value from data, as Decode does.

Types

type Error

type Error struct {
	// Kind classifies the error.
	Kind Kind
	// Msg is the message shown to the user.
	Msg string
	// Err is the underlying error, or nil.
	Err error
}

Error is an error with a Kind. Its message is complete as it stands: it carries no "error:" prefix and does not name the program.

func Errorf

func Errorf(kind Kind, format string, args ...any) *Error

Errorf returns an *Error of the given kind. An error among args that is wrapped with %w becomes the underlying error.

func (*Error) Error

func (e *Error) Error() string

Error returns the message.

func (*Error) Unwrap

func (e *Error) Unwrap() error

Unwrap returns the underlying error.

type Kind

type Kind uint8

Kind classifies an error by what a command-line tool does about it.

const (
	// KindFailed is any failure that has no more specific kind: a request
	// the API refused, an unreadable file, an unexpected response.
	KindFailed Kind = iota + 1
	// KindUsage is a mistake on the command line: an unknown option, a
	// missing argument, values that may not be combined.
	KindUsage
	// KindSkipped means nothing was done on purpose: a condition the caller
	// set does not hold, or a result that had to be non-empty is empty.
	KindSkipped
	// KindNotFound means the resource asked for does not exist.
	KindNotFound
	// KindUnauthenticated means no usable credential is available.
	KindUnauthenticated
	// KindDefinition is a mistake in a definition document.
	KindDefinition
	// KindCanceled means the run was interrupted.
	KindCanceled
)

The kinds of errors. The zero Kind means "no error".

func KindOf

func KindOf(err error) Kind

KindOf returns the kind of err: 0 for nil, the kind of the first *Error in its chain, KindCanceled for a canceled context, and KindFailed for anything else.

func (Kind) ExitCode

func (k Kind) ExitCode() int

ExitCode returns the exit code a command-line tool ends with for an error of this kind. The zero Kind maps to ExitOK.

func (Kind) String

func (k Kind) String() string

String returns the kind's name.

type Object

type Object struct {
	// contains filtered or unexported fields
}

Object is a JSON object that keeps its keys in insertion order. API responses, payloads and definition documents are held as Objects, because the order of keys shows up in output and decides which of several rules applies first.

The values of an Object, and of the lists inside it, are of the types Decode produces: nil, bool, string, json.Number, []any and *Object.

An Object is not safe for concurrent use while it is modified.

func NewObject

func NewObject() *Object

NewObject returns an empty object.

func (*Object) All

func (o *Object) All() iter.Seq2[string, any]

All iterates over the keys and values in insertion order. The object must not be modified during the iteration.

func (*Object) Delete

func (o *Object) Delete(key string)

Delete removes key. Deleting a key that is not present does nothing.

func (*Object) Get

func (o *Object) Get(key string) (any, bool)

Get returns the value of key and whether the key is present. It is safe to call on a nil Object, which has no keys.

func (*Object) Has

func (o *Object) Has(key string) bool

Has reports whether key is present.

func (*Object) Keys

func (o *Object) Keys() []string

Keys returns the keys in insertion order. The slice is the caller's.

func (*Object) Len

func (o *Object) Len() int

Len returns the number of keys. A nil Object has none.

func (*Object) MarshalJSON

func (o *Object) MarshalJSON() ([]byte, error)

MarshalJSON encodes the object with its keys in insertion order.

func (*Object) Set

func (o *Object) Set(key string, value any)

Set stores value under key. A new key is appended; an existing key keeps its position.

func (*Object) UnmarshalJSON

func (o *Object) UnmarshalJSON(data []byte) error

UnmarshalJSON decodes a JSON object, keeping the order of its keys. A key that occurs twice keeps its first position and its last value.

Directories

Path Synopsis
Package apitest provides a fake API for tests of code that talks to a REST API through api-kit: of the engine itself, and of the definitions other tools embed.
Package apitest provides a fake API for tests of code that talks to a REST API through api-kit: of the engine itself, and of the definitions other tools embed.
Package auth supplies the token that the requests of a tool carry.
Package auth supplies the token that the requests of a tool carry.
cli
Package cli builds the command tree of a command-line tool and runs it.
Package cli builds the command tree of a command-line tool and runs it.
argv
Package argv rewrites a command line into the form cobra parses, so that spellings cobra does not know keep working:
Package argv rewrites a command line into the form cobra parses, so that spellings cobra does not know keep working:
Package definition reads the declarative description of an API that the rest of api-kit works from.
Package definition reads the declarative description of an API that the rest of api-kit works from.
Package engine talks to the API a definition describes.
Package engine talks to the API a definition describes.
examples
petstore command
Command petstore is a complete command-line tool for an invented API.
Command petstore is a complete command-line tool for an invented API.
Package expr holds the three small languages that API definitions and command lines are written in: templates, paths and conditions.
Package expr holds the three small languages that API definitions and command lines are written in: templates, paths and conditions.
Package output writes the results of a command in the format the user asked for with --output.
Package output writes the results of a command in the format the user asked for with --output.

Jump to

Keyboard shortcuts

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