amino

package
v0.0.0 Latest Latest
Warning

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

Go to latest
Published: Apr 30, 2026 License: Apache-2.0, UNKNOWN, UNKNOWN not legal advice Imports: 0 Imported by: 0

README

Amino

Amino is an encoding/decoding library for structures.

In Amino, all structures are declared in a restricted set of Go. From those declarations, Amino generates Protobuf3-compatible binary bytes.

Amino supports three encoding paths, from slowest to fastest:

  1. Amino reflect — reflection-based encoding/decoding. No code generation required. This is the baseline.

  2. pbbindings (genproto) — generates .proto files via protoc, then generates Go translation code between amino Go structs and protobuf-generated Go structs. Faster than reflect (~3x encode), but requires protoc and produces intermediate proto.Message allocations.

  3. genproto2 — generates MarshalBinary2/UnmarshalBinary2 methods that encode directly to protobuf3 wire format without intermediate structs, proto files, or protoc. Uses backward-writing into a pre-sized buffer for single-allocation marshaling.

Performance (Apple M2)

Encode (ns/op):

Type genproto2 native protobuf amino reflect gp2 vs proto gp2 vs reflect
EmptyStruct 3.3 25.5 68.4 7.8x 20.7x
PrimitivesStruct 247 348 1,434 1.4x 5.8x
ArraysStruct 886 946 5,622 1.07x 6.3x
ArraysArraysStruct 1,350 1,768 12,028 1.3x 8.9x
SlicesSlicesStruct 5,899 7,468 35,967 1.27x 6.1x

Decode (ns/op):

Type genproto2 native protobuf amino reflect gp2 vs proto gp2 vs reflect
EmptyStruct 11.5 49.6 44.6 4.3x 3.9x
PrimitivesStruct 381 386 914 ~1x 2.4x
ArraysStruct 1,548 2,014 4,027 1.3x 2.6x
SlicesSlicesStruct 31,496 15,802 60,615 0.5x 1.9x

genproto2 encode is consistently faster than native protobuf. Decode wins on small/medium types but native protobuf wins on deeply nested slices (fewer allocations in the protobuf runtime). Decode allocation optimization is future work.

Though Amino supports a subset of Protobuf3 and uses it to optimize encoding and decoding, it is NOT intended to be a Protobuf3 library — complete support of Protobuf3 is explicitly not its design goal.

Getting Started

Registering types and packages

Each package should declare in a package-local file (by convention called amino.go) which should look like the following:

package main

import (
	"github.com/gnolang/gno/tm2/pkg/amino"
	"github.com/gnolang/gno/tm2/pkg/amino/genproto/example/submodule"
)

var Package = amino.RegisterPackage(
	amino.NewPackage(
		"main", // The Go package path
		"main", // The (shorter) Proto3 package path (no slashes).
		amino.GetCallersDirname(),
	).WithDependencies(
		submodule.Package,
	).WithTypes(
		StructA{},
		StructB{},
		&StructC{}, // Pointer receiver preferred when decoding to interfaces.
	),
)

You can still override global registrations with local *amino.Codec state. This is used by genproto.P3Context, which may help during migration.

Testing and Fuzzing

See the Makefile for all available targets. Key ones:

make test                  # run all unit tests
make fuzz                  # run all fuzz testers (see below)
make fuzz FUZZTIME=30m     # customize fuzz duration (default: 1h)
Fuzz targets
Target Tool What it tests Codec
make fuzz (3-way comparison) go test -count=999999 Roundtrip equality: amino reflect, pbbindings, and genproto2 produce identical bytes for random valid structs All three
make fuzz (native Go fuzzer) go test -fuzz (Go 1.18+) UnmarshalBinary2 doesn't panic on random bytes (coverage-guided) genproto2
make gofuzz_binary go-fuzz (external tool) amino reflect Unmarshal doesn't panic on random bytes amino reflect
make gofuzz_json go-fuzz (external tool) amino reflect JSONUnmarshal doesn't panic on random JSON amino reflect

The make fuzz target runs the 3-way comparison and native Go fuzzer sequentially. The gofuzz_binary and gofuzz_json targets require the external go-fuzz tool and test the older amino reflect codec only.

Unsupported types

Floating points

Floating point number types are discouraged as they are generally non-deterministic. If you need to use them, use the field tag amino:"unsafe".

Enums

Enum types are not supported in all languages, and they're simple enough to model as integers anyways.

Maps

Maps are not currently supported. There is unstable experimental support for maps in the Amino:JSON codec, but it shouldn't be relied on.

Amino and Proto3

Amino objects are a subset of Proto3.

  • Enums are not supported.
  • Nested message declarations are not supported.

Amino extends Proto3's Any system with a particular concrete type identification format (disfix bytes).

Amino and Go

Amino objects are a subset of Go.

  • Floats are nondeterministic, so aren't supported by default.
  • Chans, funcs, and maps are not supported.
  • Nested pointers are not allowed.
  • Pointers are automatically supported in go-amino but it is an extension of the theoretical Amino spec.

Limitations

  • Pointer types in arrays and slices lose pointer information.
  • Nested pointers are not allowed.
  • Recursive ReprType not allowed.

Documentation

Overview

TODO AMINO DOCS, for now see the main README file, or the code.

Example
package main

import (
	"fmt"
	"reflect"

	amino "github.com/gnolang/gno/tm2/pkg/amino"
)

func main() {
	type Message any

	type bcMessage struct {
		Message string
		Height  int
	}

	type bcResponse struct {
		Status  int
		Message string
	}

	type bcStatus struct {
		Peers int
	}

	// amino.RegisterPackage registers globally.
	amino.RegisterPackage(
		amino.NewPackage(
			reflect.TypeOf(bcMessage{}).PkgPath(),
			"amino_test",
			amino.GetCallersDirname(),
		).
			WithTypes(&bcMessage{}, &bcResponse{}, &bcStatus{}),
	)

	bm := &bcMessage{Message: "ABC", Height: 100}
	msg := bm

	var bz []byte // the marshalled bytes.
	var err error
	bz, err = amino.MarshalAnySized(msg)
	fmt.Printf("Encoded: %X (err: %v)\n", bz, err)

	var msg2 Message
	err = amino.UnmarshalSized(bz, &msg2)
	fmt.Printf("Decoded: %v (err: %v)\n", msg2, err)
	bm2 := msg2.(*bcMessage)
	fmt.Printf("Decoded successfully: %v\n", *bm == *bm2)

}
Output:
Encoded: 210A152F616D696E6F5F746573742E62634D65737361676512080A0341424310C801 (err: <nil>)
Decoded: &{ABC 100} (err: <nil>)
Decoded successfully: true

Index

Examples

Constants

View Source
const (
	// Typ3 types
	Typ3Varint     = Typ3(0)
	Typ38Byte      = Typ3(1)
	Typ3ByteLength = Typ3(2)
	// Typ3_Struct     = Typ3(3)
	// Typ3_StructTerm = Typ3(4)
	Typ34Byte = Typ3(5)
)
View Source
const (
	GasEncodePerByte int64 = 3 // ~2.8 ns/byte amino marshal
	GasDecodePerByte int64 = 3 // ~2.8 ns/byte amino unmarshal (assumed)
)

Gas constants for amino serialization compute cost. Calibrated from Binary2 (genproto2) benchmarks: ~2.8 ns/byte + 427 ns flat (see gnovm/adr/STORAGE_CHARGING_AMINO_HEURISTIC.png). The per-byte slope is used; the flat component is small relative to typical serialized sizes. Same slope assumed for decode pending separate benchmarks. These constants assume amino2 (Binary2).

View Source
const Version = "1.0.0-rc.10"

Version

Variables

View Source
var (

	// ErrNoPointer is thrown when you call a method that expects a pointer, e.g. Unmarshal
	ErrNoPointer = errors.New("expected a pointer")
)

Functions

func AppendBoolReversed

func AppendBoolReversed(buf []byte, b bool) []byte

func AppendByteReversed

func AppendByteReversed(buf []byte, b byte) []byte

func AppendByteSliceReversed

func AppendByteSliceReversed(buf []byte, bz []byte) []byte

func AppendBytesReversed

func AppendBytesReversed(buf []byte, bz []byte) []byte

func AppendDurationReversed

func AppendDurationReversed(buf []byte, d time.Duration) ([]byte, error)

func AppendDurationValueReversed

func AppendDurationValueReversed(buf []byte, s int64, ns int32) ([]byte, error)

func AppendFieldNumberAndTyp3Reversed

func AppendFieldNumberAndTyp3Reversed(buf []byte, num uint32, typ Typ3) []byte

func AppendFloat32Reversed

func AppendFloat32Reversed(buf []byte, f float32) []byte

func AppendFloat64Reversed

func AppendFloat64Reversed(buf []byte, f float64) []byte

func AppendInt32Reversed

func AppendInt32Reversed(buf []byte, i int32) []byte

func AppendInt64Reversed

func AppendInt64Reversed(buf []byte, i int64) []byte

func AppendStringReversed

func AppendStringReversed(buf []byte, s string) []byte

func AppendTimeReversed

func AppendTimeReversed(buf []byte, t time.Time) ([]byte, error)

func AppendTimeValueReversed

func AppendTimeValueReversed(buf []byte, s int64, ns int32) ([]byte, error)

func AppendUint32Reversed

func AppendUint32Reversed(buf []byte, u uint32) []byte

func AppendUint64Reversed

func AppendUint64Reversed(buf []byte, u uint64) []byte

func AppendUvarintReversed

func AppendUvarintReversed(buf []byte, u uint64) []byte

func AppendVarintReversed

func AppendVarintReversed(buf []byte, i int64) []byte

func ByteSliceSize

func ByteSliceSize(bz []byte) int

func DecodeBool

func DecodeBool(bz []byte) (b bool, n int, err error)

func DecodeByte

func DecodeByte(bz []byte) (b byte, n int, err error)

func DecodeByteSlice

func DecodeByteSlice(bz []byte) (bz2 []byte, n int, err error)

func DecodeDuration

func DecodeDuration(bz []byte) (d time.Duration, n int, err error)

func DecodeDurationValue

func DecodeDurationValue(bz []byte) (s int64, ns int32, n int, err error)

func DecodeFloat32

func DecodeFloat32(bz []byte) (f float32, n int, err error)

NOTE: UNSAFE

func DecodeFloat64

func DecodeFloat64(bz []byte) (f float64, n int, err error)

NOTE: UNSAFE

func DecodeInt32

func DecodeInt32(bz []byte) (i int32, n int, err error)

func DecodeInt64

func DecodeInt64(bz []byte) (i int64, n int, err error)

func DecodeJSONDuration

func DecodeJSONDuration(bz []byte, fopts FieldOptions) (d time.Duration, err error)

func DecodeJSONPBDuration

func DecodeJSONPBDuration(bz []byte, fopts FieldOptions) (d durationpb.Duration, err error)

func DecodeJSONPBTimestamp

func DecodeJSONPBTimestamp(bz []byte, fopts FieldOptions) (t timestamppb.Timestamp, err error)

func DecodeJSONTime

func DecodeJSONTime(bz []byte, fopts FieldOptions) (t time.Time, err error)

func DecodeString

func DecodeString(bz []byte) (s string, n int, err error)

func DecodeTime

func DecodeTime(bz []byte) (t time.Time, n int, err error)

func DecodeTimeValue

func DecodeTimeValue(bz []byte) (s int64, ns int32, n int, err error)

DecodeTimeValue decodes seconds (int64) and nanoseconds (int32) since January 1, 1970 UTC, and returns the corresponding time. If nanoseconds is not in the range [0, 999999999], or if seconds is too large, an error is returned.

func DecodeUint32

func DecodeUint32(bz []byte) (u uint32, n int, err error)

func DecodeUint64

func DecodeUint64(bz []byte) (u uint64, n int, err error)

func DecodeUvarint

func DecodeUvarint(bz []byte) (u uint64, n int, err error)

func DecodeUvarint8

func DecodeUvarint8(bz []byte) (u uint8, n int, err error)

func DecodeUvarint16

func DecodeUvarint16(bz []byte) (u uint16, n int, err error)

func DecodeUvarint32

func DecodeUvarint32(bz []byte) (u uint32, n int, err error)

func DecodeVarint

func DecodeVarint(bz []byte) (i int64, n int, err error)

func DecodeVarint8

func DecodeVarint8(bz []byte) (i int8, n int, err error)

func DecodeVarint16

func DecodeVarint16(bz []byte) (i int16, n int, err error)

func DeepCopy

func DeepCopy(o any) (r any)

Deeply copies an object. If anything implements `.DeepCopy() <any>` along the way, the result of that function will be used. Otherwise, if it implements `.MarshalAmino() (<any>, error)` and `.UnmarshalAmino(<any>) error`, the pair will be used to copy. If .MarshalAmino() or .UnmarshalAmino() returns an error, this function will panic.

func DeepCopyToPtr

func DeepCopyToPtr(o any) (ptr any)

Like DeepCopy, but returns a pointer to the copy.

func DeepEqual

func DeepEqual(a, b any) bool

DeepEqual returns true if the types are the same and the binary amino encoding would be the same. TODO: optimize, and support genproto.

func DurationSize

func DurationSize(d time.Duration) int

DurationSize returns the encoded byte size of a time.Duration value (the bare content, without field key or length prefix).

func EncodeBool

func EncodeBool(w io.Writer, b bool) (err error)

func EncodeByte

func EncodeByte(w io.Writer, b byte) (err error)

Unlike EncodeUint8, writes a single byte.

func EncodeByteSlice

func EncodeByteSlice(w io.Writer, bz []byte) (err error)

func EncodeDuration

func EncodeDuration(w io.Writer, d time.Duration) (err error)

func EncodeDurationValue

func EncodeDurationValue(w io.Writer, s int64, ns int32) (err error)

The binary encoding of Duration is the same as Timestamp, but the validation checks are different.

See https://godoc.org/google.golang.org/protobuf/types/known/durationpb#Duration

type Duration struct {

    // Signed seconds of the span of time. Must be from -315,576,000,000
    // to +315,576,000,000 inclusive. Note: these bounds are computed from:
    // 60 sec/min * 60 min/hr * 24 hr/day * 365.25 days/year * 10000 years
    Seconds int64 `protobuf:"varint,1,opt,name=seconds,proto3" json:"seconds,omitempty"`
    // Signed fractions of a second at nanosecond resolution of the span
    // of time. Durations less than one second are represented with a 0
    // `seconds` field and a positive or negative `nanos` field. For durations
    // of one second or more, a non-zero value for the `nanos` field must be
    // of the same sign as the `seconds` field. Must be from -999,999,999
    // to +999,999,999 inclusive.
    Nanos int32 `protobuf:"varint,2,opt,name=nanos,proto3" json:"nanos,omitempty"`
    // contains filtered or unexported fields
}

func EncodeFieldNumberAndTyp3

func EncodeFieldNumberAndTyp3(w io.Writer, num uint32, typ Typ3) error

EncodeFieldNumberAndTyp3 writes a protobuf field key (field number + wire type). This is the exported wrapper around encodeFieldNumberAndTyp3 for use by generated code (genproto2).

func EncodeFloat32

func EncodeFloat32(w io.Writer, f float32) (err error)

NOTE: UNSAFE

func EncodeFloat64

func EncodeFloat64(w io.Writer, f float64) (err error)

NOTE: UNSAFE

func EncodeInt32

func EncodeInt32(w io.Writer, i int32) (err error)

func EncodeInt64

func EncodeInt64(w io.Writer, i int64) (err error)

func EncodeJSONDuration

func EncodeJSONDuration(w io.Writer, d time.Duration) (err error)

func EncodeJSONDurationValue

func EncodeJSONDurationValue(w io.Writer, s int64, ns int32) (err error)

func EncodeJSONPBDuration

func EncodeJSONPBDuration(w io.Writer, d *durationpb.Duration) (err error)

func EncodeJSONPBTimestamp

func EncodeJSONPBTimestamp(w io.Writer, t *timestamppb.Timestamp) (err error)

func EncodeJSONTime

func EncodeJSONTime(w io.Writer, t time.Time) (err error)

func EncodeJSONTimeValue

func EncodeJSONTimeValue(w io.Writer, s int64, ns int32) (err error)

func EncodeString

func EncodeString(w io.Writer, s string) (err error)

func EncodeTime

func EncodeTime(w io.Writer, t time.Time) (err error)

func EncodeTimeValue

func EncodeTimeValue(w io.Writer, s int64, ns int32) (err error)

EncodeTimeValue writes the number of seconds (int64) and nanoseconds (int32), with millisecond resolution since January 1, 1970 UTC to the Writer as an UInt64. Milliseconds are used to ease compatibility with Javascript, which does not support finer resolution.

See https://godoc.org/google.golang.org/protobuf/types/known/timestamppb#Timestamp

type Timestamp struct {

    // Represents seconds of UTC time since Unix epoch
    // 1970-01-01T00:00:00Z. Must be from 0001-01-01T00:00:00Z to
    // 9999-12-31T23:59:59Z inclusive.
    Seconds int64 `protobuf:"varint,1,opt,name=seconds,proto3" json:"seconds,omitempty"`
    // Non-negative fractions of a second at nanosecond resolution. Negative
    // second values with fractions must still have non-negative nanos values
    // that count forward in time. Must be from 0 to 999,999,999
    // inclusive.
    Nanos int32 `protobuf:"varint,2,opt,name=nanos,proto3" json:"nanos,omitempty"`
    // contains filtered or unexported fields
}

func EncodeUint32

func EncodeUint32(w io.Writer, u uint32) (err error)

func EncodeUint64

func EncodeUint64(w io.Writer, u uint64) (err error)

func EncodeUvarint

func EncodeUvarint(w io.Writer, u uint64) (err error)

func EncodeUvarint8

func EncodeUvarint8(w io.Writer, i uint8) (err error)

func EncodeUvarint16

func EncodeUvarint16(w io.Writer, i uint16) (err error)

func EncodeUvarint32

func EncodeUvarint32(w io.Writer, i uint32) (err error)

func EncodeVarint

func EncodeVarint(w io.Writer, i int64) (err error)

func EncodeVarint8

func EncodeVarint8(w io.Writer, i int8) (err error)

func EncodeVarint16

func EncodeVarint16(w io.Writer, i int16) (err error)

func EncodeVarint32

func EncodeVarint32(w io.Writer, i int32) (err error)

func GetCallersDirname

func GetCallersDirname() string

Get caller's package directory. Implementation uses `filepath.Dir(runtime.Caller(1))`. NOTE: duplicated in pkg/pkg.go; given what it does and how, both are probably needed.

func GetTypeURL

func GetTypeURL(o any) string

XXX unstable API.

func HasNativeGenproto2

func HasNativeGenproto2(rt reflect.Type) bool

HasNativeGenproto2 returns true if the type has its own genproto2 methods (not just promoted from an embedded struct).

func HasNativePbbindings

func HasNativePbbindings(rt reflect.Type) bool

HasNativePbbindings returns true if the type has its own pbbindings methods (not just promoted from an embedded struct).

func IsASCIIText

func IsASCIIText(s string) bool

Returns true if s is a non-empty printable non-tab ascii character.

func IsEmpty

func IsEmpty(o any) bool

Returns true if it has zero length.

func IsEmptyTime

func IsEmptyTime(t time.Time) bool

func Marshal

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

func MarshalAny

func MarshalAny(o any) ([]byte, error)

func MarshalAnySized

func MarshalAnySized(o any) ([]byte, error)

func MarshalAnySizedWriter

func MarshalAnySizedWriter(w io.Writer, o any) (n int64, err error)

func MarshalJSON

func MarshalJSON(o any) ([]byte, error)

func MarshalJSONAny

func MarshalJSONAny(o any) ([]byte, error)

func MarshalJSONIndent

func MarshalJSONIndent(o any, prefix, indent string) ([]byte, error)

func MarshalSized

func MarshalSized(o any) ([]byte, error)

func MarshalSizedWriter

func MarshalSizedWriter(w io.Writer, o any) (n int64, err error)

func MustMarshal

func MustMarshal(o any) []byte

func MustMarshalAny

func MustMarshalAny(o any) []byte

func MustMarshalAnySized

func MustMarshalAnySized(o any) []byte

func MustMarshalJSON

func MustMarshalJSON(o any) []byte

func MustMarshalJSONAny

func MustMarshalJSONAny(o any) []byte

func MustMarshalSized

func MustMarshalSized(o any) []byte

func MustUnmarshal

func MustUnmarshal(bz []byte, ptr any)

func MustUnmarshalAny

func MustUnmarshalAny(bz []byte, ptr any)

func MustUnmarshalJSON

func MustUnmarshalJSON(bz []byte, ptr any)

func MustUnmarshalSized

func MustUnmarshalSized(bz []byte, ptr any)

func PrependBool

func PrependBool(buf []byte, offset int, b bool) int

func PrependByte

func PrependByte(buf []byte, offset int, b byte) int

func PrependByteSlice

func PrependByteSlice(buf []byte, offset int, bz []byte) int

func PrependBytes

func PrependBytes(buf []byte, offset int, bz []byte) int

func PrependDuration

func PrependDuration(buf []byte, offset int, d time.Duration) (int, error)

func PrependDurationValue

func PrependDurationValue(buf []byte, offset int, s int64, ns int32) (int, error)

func PrependFieldNumberAndTyp3

func PrependFieldNumberAndTyp3(buf []byte, offset int, num uint32, typ Typ3) int

func PrependFloat32

func PrependFloat32(buf []byte, offset int, f float32) int

func PrependFloat64

func PrependFloat64(buf []byte, offset int, f float64) int

func PrependInt32

func PrependInt32(buf []byte, offset int, i int32) int

func PrependInt64

func PrependInt64(buf []byte, offset int, i int64) int

func PrependString

func PrependString(buf []byte, offset int, s string) int

func PrependTime

func PrependTime(buf []byte, offset int, t time.Time) (int, error)

func PrependTimeValue

func PrependTimeValue(buf []byte, offset int, s int64, ns int32) (int, error)

PrependTimeValue writes Timestamp proto fields backward into buf.

func PrependUint32

func PrependUint32(buf []byte, offset int, u uint32) int

func PrependUint64

func PrependUint64(buf []byte, offset int, u uint64) int

func PrependUvarint

func PrependUvarint(buf []byte, offset int, u uint64) int

func PrependVarint

func PrependVarint(buf []byte, offset int, i int64) int

func RegisterGenproto2Type

func RegisterGenproto2Type(rt reflect.Type)

RegisterGenproto2Type records that a type has native genproto2 methods. Called from init() in generated pb3_gen.go files. Logs a warning if the type was already registered — duplicate init() calls typically indicate a regenerated file pulled in twice, or two generated files claiming the same type.

func RegisterPbbindingsType

func RegisterPbbindingsType(rt reflect.Type)

RegisterPbbindingsType records that a type has native pbbindings methods. Called from init() in generated pbbindings.go files. Logs a warning if the type was already registered — see RegisterGenproto2Type for typical causes.

func SkipField

func SkipField(bz []byte, typ Typ3) (n int, err error)

SkipField skips over a field value given its wire type. Used by generated unmarshal code to skip unknown fields.

func TimeSize

func TimeSize(t time.Time) int

TimeSize returns the encoded byte size of a time.Time value (the bare content, without field key or length prefix).

func Unmarshal

func Unmarshal(bz []byte, ptr any) error

func UnmarshalAny

func UnmarshalAny(bz []byte, ptr any) error

func UnmarshalAny2

func UnmarshalAny2(typeURL string, value []byte, ptr any) error

func UnmarshalAnySized

func UnmarshalAnySized(bz []byte, ptr any) error

func UnmarshalJSON

func UnmarshalJSON(bz []byte, ptr any) error

func UnmarshalSized

func UnmarshalSized(bz []byte, ptr any) error

func UnmarshalSizedReader

func UnmarshalSizedReader(r io.Reader, ptr any, maxSize int64) (n int64, err error)

func UvarintSize

func UvarintSize(u uint64) int

func VarintSize

func VarintSize(i int64) int

Types

type Codec

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

func NewCodec

func NewCodec() *Codec

func (*Codec) Autoseal

func (cdc *Codec) Autoseal() *Codec

func (*Codec) GetPackages

func (cdc *Codec) GetPackages() pkg.PackageSet

XXX TODO: make this safe so modifications don't affect runtime codec, and ensure that it stays safe. NOTE: do not modify the returned Packages.

func (*Codec) GetStats

func (cdc *Codec) GetStats() *codecStats

GetStats returns a pointer to the codec's decode-path counters for testing and observability.

func (*Codec) GetTypeInfo

func (cdc *Codec) GetTypeInfo(rt reflect.Type) (info *TypeInfo, err error)

This is used primarily for gengo. XXX TODO: make this safe so modifications don't affect runtime codec, and ensure that it stays safe. NOTE: do not modify the returned TypeInfo.

func (*Codec) GetTypeURL

func (cdc *Codec) GetTypeURL(o any) string

TODO: this does need the cdc receiver, as it should also work for non-pbbindings-optimized types. Returns the default type url for the given concrete type. NOTE: It must be fast, as it is used in pbbindings. XXX Unstable API.

func (*Codec) JSONMarshal

func (cdc *Codec) JSONMarshal(o any) ([]byte, error)

func (*Codec) JSONUnmarshal

func (cdc *Codec) JSONUnmarshal(bz []byte, ptr any) error

func (*Codec) Marshal

func (cdc *Codec) Marshal(o any) ([]byte, error)

Marshal encodes the object o according to the Amino spec. Marshal doesn't prefix the byte-length of the encoding, so the caller must handle framing. Type information as in google.protobuf.Any isn't included, so manually wrap before calling if you need to decode into an interface. NOTE: nil-struct-pointers have no encoding. In the context of a struct, the absence of a field does denote a nil-struct-pointer, but in general this is not the case, so unlike MarshalJSON.

func (*Codec) MarshalAny

func (cdc *Codec) MarshalAny(o any) ([]byte, error)

MarshalAny encodes the registered object wrapped with google.protobuf.Any.

func (*Codec) MarshalAnyBinary2

func (cdc *Codec) MarshalAnyBinary2(o any, buf []byte, offset int) (int, error)

MarshalAnyBinary2 writes a google.protobuf.Any envelope backward into buf at offset, using the same Prepend* backward encoding as generated code. For use within generated MarshalBinary2 methods.

func (*Codec) MarshalAnySized

func (cdc *Codec) MarshalAnySized(o any) ([]byte, error)

func (*Codec) MarshalAnySizedWriter

func (cdc *Codec) MarshalAnySizedWriter(w io.Writer, o any) (n int64, err error)

func (*Codec) MarshalBinary2

func (cdc *Codec) MarshalBinary2(pbm2 PBMarshaler2) ([]byte, error)

Use genproto2 direct encoding.

func (*Codec) MarshalJSONAny

func (cdc *Codec) MarshalJSONAny(o any) ([]byte, error)

func (*Codec) MarshalJSONIndent

func (cdc *Codec) MarshalJSONIndent(o any, prefix, indent string) ([]byte, error)

MarshalJSONIndent calls json.Indent on the output of cdc.MarshalJSON using the given prefix and indent string.

func (*Codec) MarshalPBBindings

func (cdc *Codec) MarshalPBBindings(pbm PBMessager) ([]byte, error)

Use pbbindings.

func (*Codec) MarshalReflect

func (cdc *Codec) MarshalReflect(o any) ([]byte, error)

Use reflection.

func (*Codec) MarshalSized

func (cdc *Codec) MarshalSized(o any) ([]byte, error)

MarshalSized encodes the object o according to the Amino spec, but prefixed by a uvarint encoding of the object to encode. Use Marshal if you don't want byte-length prefixing.

For consistency, MarshalSized will first dereference pointers before encoding. MarshalSized will panic if o is a nil-pointer, or if o is invalid.

func (*Codec) MarshalSizedWriter

func (cdc *Codec) MarshalSizedWriter(w io.Writer, o any) (n int64, err error)

MarshalSizedWriter writes the bytes as would be returned from MarshalSized to the writer w.

func (*Codec) MustMarshal

func (cdc *Codec) MustMarshal(o any) []byte

Panics if error.

func (*Codec) MustMarshalAny

func (cdc *Codec) MustMarshalAny(o any) []byte

Panics if error.

func (*Codec) MustMarshalAnySized

func (cdc *Codec) MustMarshalAnySized(o any) []byte

func (*Codec) MustMarshalJSON

func (cdc *Codec) MustMarshalJSON(o any) []byte

MustMarshalJSON panics if an error occurs. Besides that behaves exactly like MarshalJSON.

func (*Codec) MustMarshalJSONAny

func (cdc *Codec) MustMarshalJSONAny(o any) []byte

MustMarshalJSONAny panics if an error occurs. Besides that behaves exactly like MarshalJSONAny.

func (*Codec) MustMarshalSized

func (cdc *Codec) MustMarshalSized(o any) []byte

Panics if error.

func (*Codec) MustUnmarshal

func (cdc *Codec) MustUnmarshal(bz []byte, ptr any)

Panics if error.

func (*Codec) MustUnmarshalAny

func (cdc *Codec) MustUnmarshalAny(bz []byte, ptr any)

func (*Codec) MustUnmarshalJSON

func (cdc *Codec) MustUnmarshalJSON(bz []byte, ptr any)

MustUnmarshalJSON panics if an error occurs. Besides that behaves exactly like UnmarshalJSON.

func (*Codec) MustUnmarshalSized

func (cdc *Codec) MustUnmarshalSized(bz []byte, ptr any)

Panics if error.

func (*Codec) PrintTypes

func (cdc *Codec) PrintTypes(out io.Writer) error

PrintTypes writes all registered types in a markdown-style table. The table's header is:

| Type | TypeURL | Notes |

Where Type is the golang type name and TypeURL is the type_url the type was registered with.

func (*Codec) RegisterPackage

func (cdc *Codec) RegisterPackage(pkg *Package)

The package isn't (yet) necessary besides to get the full name of concrete types. Registers all dependencies of pkg recursively. This operation is idempotent -- pkgs already registered may be registered again.

func (*Codec) RegisterTypeFrom

func (cdc *Codec) RegisterTypeFrom(rt reflect.Type, pkg *Package)

This function should be used to register concrete types that will appear in interface fields/elements to be encoded/decoded by go-amino. You may want to use RegisterPackage() instead which registers everything in a package. Usage: `amino.RegisterTypeFrom(MyStruct1{}, "/tm.cryp.MyStruct1")`

func (*Codec) Seal

func (cdc *Codec) Seal() *Codec

func (*Codec) SizeAnyBinary2

func (cdc *Codec) SizeAnyBinary2(o any) (int, error)

SizeAnyBinary2 computes the encoded size of a google.protobuf.Any envelope arithmetically, without marshaling. For use in generated SizeBinary2 methods.

func (*Codec) Unmarshal

func (cdc *Codec) Unmarshal(bz []byte, ptr any) error

Unmarshal will panic if ptr is a nil-pointer.

func (*Codec) UnmarshalAny

func (cdc *Codec) UnmarshalAny(bz []byte, ptr any) (err error)

UnmarshalAny decodes the registered object from an Any.

func (*Codec) UnmarshalAny2

func (cdc *Codec) UnmarshalAny2(typeURL string, value []byte, ptr any) (err error)

like UnmarshalAny() but with typeURL and value destructured.

func (*Codec) UnmarshalAnyBinary2

func (cdc *Codec) UnmarshalAnyBinary2(bz []byte, ptr any, anyDepth int) error

UnmarshalAnyBinary2 decodes a google.protobuf.Any-wrapped value using genproto2. For use within generated UnmarshalBinary2 methods. Unlike unmarshalAnyBinary2, this errors (not falls through) if the concrete type does not implement PBMessager2. UnmarshalAnyBinary2 decodes a google.protobuf.Any-wrapped value. anyDepth is incremented by 1 (the sole increment point for depth tracking); exceeding maxAnyDepth returns an error.

func (*Codec) UnmarshalAnySized

func (cdc *Codec) UnmarshalAnySized(bz []byte, ptr any) error

Like UnmarshalAny, but will first decode the byte-length prefix.

func (*Codec) UnmarshalReflect

func (cdc *Codec) UnmarshalReflect(bz []byte, ptr any) error

Use reflection.

func (*Codec) UnmarshalSized

func (cdc *Codec) UnmarshalSized(bz []byte, ptr any) error

Like Unmarshal, but will first decode the byte-length prefix. UnmarshalSized will panic if ptr is a nil-pointer. Returns an error if not all of bz is consumed.

func (*Codec) UnmarshalSizedReader

func (cdc *Codec) UnmarshalSizedReader(r io.Reader, ptr any,
	maxSize int64,
) (n int64, err error)

Like Unmarshal, but will first read the byte-length prefix. UnmarshalSizedReader will panic if ptr is a nil-pointer. If maxSize is 0, there is no limit (not recommended).

func (*Codec) WithPBBindings

func (cdc *Codec) WithPBBindings() *Codec

Returns a new codec that is optimized w/ pbbindings. The returned codec is sealed, but may be affected by modifications to the underlying codec.

type ConcreteInfo

type ConcreteInfo struct {
	Registered            bool      // Registered with Register*().
	Name                  string    // Registered name which may override default reflection name.
	PointerPreferred      bool      // Deserialize to pointer type if possible.
	TypeURL               string    // <domain and path>/<p3 package no slashes>.<Name>
	IsAminoMarshaler      bool      // Implements MarshalAmino() (<ReprObject>, error) and UnmarshalAmino(<ReprObject>) (error).
	ReprType              *TypeInfo // <ReprType> if IsAminoMarshaler, that, or by default the identity Type.
	IsJSONValueType       bool      // If true, the Any representation uses the "value" field (instead of embedding @type).
	IsBinaryWellKnownType bool      // If true, use built-in functions to encode/decode.
	IsJSONWellKnownType   bool      // If true, use built-in functions to encode/decode.
	IsJSONAnyValueType    bool      // If true, the interface/Any representation uses the "value" field.
	Elem                  *TypeInfo // Set if Type.Kind() is Slice or Array.
	ElemIsPtr             bool      // Set true iff Type.Elem().Kind() is Pointer.
}

type FieldInfo

type FieldInfo struct {
	Type         reflect.Type  // Struct field reflect.Type.
	TypeInfo     *TypeInfo     // Dereferenced struct field TypeInfo
	Name         string        // Struct field name
	Index        int           // Struct field index
	ZeroValue    reflect.Value // Could be nil pointer unlike TypeInfo.ZeroValue.
	UnpackedList bool          // True iff this field should be encoded as an unpacked list.
	FieldOptions               // Encoding options
}

func (*FieldInfo) IsPtr

func (finfo *FieldInfo) IsPtr() bool

func (*FieldInfo) ValidateBasic

func (finfo *FieldInfo) ValidateBasic()

type FieldOptions

type FieldOptions struct {
	JSONName      string // (JSON) field name
	JSONOmitEmpty bool   // (JSON) omitempty
	BinFixed64    bool   // (Binary) Encode as fixed64
	BinFixed32    bool   // (Binary) Encode as fixed32
	BinFieldNum   uint32 // (Binary) max 1<<29-1

	Unsafe         bool // e.g. if this field is a float.
	WriteEmpty     bool // write empty structs and lists (default false except for pointers)
	NilElements    bool // Empty list elements are decoded as nil iff set, otherwise are never nil.
	UseGoogleTypes bool // If true, decodes Any timestamp and duration to google types.
}

type InterfaceInfo

type InterfaceInfo struct{}

type InvalidDurationError

type InvalidDurationError string

func (InvalidDurationError) Error

func (e InvalidDurationError) Error() string

type InvalidTimeError

type InvalidTimeError string

func (InvalidTimeError) Error

func (e InvalidTimeError) Error() string

type Object

type Object interface {
	GetTypeURL() string
}

All concrete types must implement the Object interface for genproto bindings. They are generated automatically by genproto/bindings.go

type PBMarshaler2

type PBMarshaler2 interface {
	MarshalBinary2(cdc *Codec, buf []byte, offset int) (int, error)
	SizeBinary2(cdc *Codec) (int, error)
}

PBMessager2 is implemented by types that can directly marshal/unmarshal protobuf3 wire bytes without intermediate protobuf structs. Generated by genproto2. PBMarshaler2 is the encode-only subset of PBMessager2. Both methods have value receivers, so T (not just *T) satisfies this. Used by SizeAnyBinary2/MarshalAnyBinary2 for interface field encoding.

type PBMessager

type PBMessager interface {
	ToPBMessage(*Codec) (proto.Message, error)
	EmptyPBMessage(*Codec) proto.Message
	FromPBMessage(*Codec, proto.Message) error
}

Methods generated by genproto/bindings.go for faster encoding.

type PBMessager2

type PBMessager2 interface {
	PBMarshaler2
	UnmarshalBinary2(cdc *Codec, bz []byte, anyDepth int) error
}

type Package

type Package = pkg.Package

Package "pkg" exists So dependencies can create Packages. We export it here so this amino package can use it natively.

func NewPackage

func NewPackage(gopkg string, p3pkg string, dirname string) *Package

Create an unregistered amino package with args: - (gopkg string) The Go package path, e.g. "github.com/gnolang/gno/tm2/pkg/std" - (p3pkg string) The (shorter) Proto3 package path (no slashes), e.g. "std" - (dirname string) Package directory this is called from. Typical is to use `amino.GetCallersDirname()`

func RegisterPackage

func RegisterPackage(pi *pkg.Package) *Package

Given amino package `pi`, register it with the global codec. NOTE: do not modify the result.

type StructInfo

type StructInfo struct {
	Fields []FieldInfo // If a struct.
}

type Typ3

type Typ3 uint8

func DecodeFieldNumberAndTyp3

func DecodeFieldNumberAndTyp3(bz []byte) (num uint32, typ Typ3, n int, err error)

DecodeFieldNumberAndTyp3 reads a protobuf field key (field number + wire type). This is the exported wrapper around decodeFieldNumberAndTyp3 for use by generated code (genproto2).

func (Typ3) String

func (typ Typ3) String() string

type Type

type Type = pkg.Type

Package "pkg" exists So dependencies can create Packages. We export it here so this amino package can use it natively.

type TypeInfo

type TypeInfo struct {
	Type      reflect.Type // never a pointer kind.
	Package   *Package     // package associated with Type.
	PtrToType reflect.Type
	ZeroValue reflect.Value
	InterfaceInfo
	ConcreteInfo
	StructInfo
}

func GetTypeInfo

func GetTypeInfo(rt reflect.Type) (info *TypeInfo, err error)

Returns a new TypeInfo instance. NOTE: it uses a new codec for security's sake. (*TypeInfo of gcdc should not be exposed) Therefore it may be inefficient. If you need efficiency, implement with a new method that takes as argument a non-global codec instance.

func (*TypeInfo) GetTyp3

func (info *TypeInfo) GetTyp3(fopts FieldOptions) Typ3

func (*TypeInfo) GetUltimateElem

func (info *TypeInfo) GetUltimateElem() *TypeInfo

If this is a slice or array, get .Elem.ReprType until no longer slice or array.

func (*TypeInfo) IsStructOrUnpacked

func (info *TypeInfo) IsStructOrUnpacked(fopt FieldOptions) bool

Used to determine whether to create an implicit struct or not. Notice that the binary encoding of a list to be unpacked is indistinguishable from a struct that contains that list. NOTE: we expect info.Elem to be prepopulated, constructed within the scope of a Codec.

func (*TypeInfo) IsStructOrUnpackedTopLevel

func (info *TypeInfo) IsStructOrUnpackedTopLevel() bool

IsStructOrUnpackedTopLevel is the top-level (non-struct-field) variant of IsStructOrUnpacked. Top-level contexts (e.g. MarshalReflect / MarshalBinary2 entry points, writeReprMarshal / writeReprUnmarshal) have no field-level BinFixed tag, so fopts is zero. Calling this helper instead of passing a literal FieldOptions{} makes the invariant explicit and greppable.

NOTE: a future top-level list type whose element's typ3 depends on BinFixed (e.g. `type Fixed64s []int64` used directly as a top-level message) would need the caller to thread a real fopts; today no such type exists and typ3 for non-BinFixed Int64 is Varint anyway, so this helper's behavior is identical to IsStructOrUnpacked(FieldOptions{}). Callers must ensure they are genuinely in a top-level context before using this helper.

func (*TypeInfo) String

func (info *TypeInfo) String() string

Jump to

Keyboard shortcuts

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