medley

package module
v0.0.2 Latest Latest
Warning

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

Go to latest
Published: Dec 26, 2024 License: Apache-2.0 Imports: 10 Imported by: 0

README

medley

medley provides service location based on hashing.

Build Status codecov.io Go Report Card Quality Gate Status Apache V2 License GitHub Release GoDoc

Summary

Medley is a Service Locator package that finds services based on hashing some arbitrary object. Currently, only consistent hashing is supported.

Table of Contents

Code of Conduct

This project and everyone participating in it are governed by the XMiDT Code Of Conduct. By participating, you agree to this Code.

Install

go get -u github.com/xmidt-org/medley

Contributing

Refer to CONTRIBUTING.md.

Documentation

Overview

Package medley implements distributed hashing aimed at microservices. Currently, only consistent hashing is implemented.

Index

Constants

This section is empty.

Variables

View Source
var (
	// ErrNoServices is returned by a Locator to indicate that the Locator contains
	// no service entries.
	ErrNoServices = errors.New("no services defined")
)

Functions

func DefaultServiceHasher added in v0.0.2

func DefaultServiceHasher[S Service](dst io.Writer, service S) error

DefaultServiceHasher uses fmt.Fprint to write a service object's hash bytes to dst. This function can be used when no ServiceHasher is supplied.

For most concrete Service types, a custom ServiceHasher is preferable as it will be more efficient than the fmt package's reflection.

func FindString added in v0.0.2

func FindString[S Service](l Locator[S], v string) (S, error)

FindString locates a service for a string key.

func HashBasicServiceTo added in v0.0.2

func HashBasicServiceTo(dst io.Writer, s BasicService) error

HashBasicServiceTo is a ServiceHasher for BasicService instances.

func HashStringTo added in v0.0.2

func HashStringTo[SS StringService](dst io.Writer, service SS) error

HashStringTo is a ServiceHasher for services whose underlying type is string. Typically hostnames and URLs fall into this category.

The string is written is such a way as to minimize allocations.

func SetLocator added in v0.0.2

func SetLocator[S Service](u Locator[S], impl Locator[S]) bool

SetLocator sets the implementation for a given locator. This function better tolerates decorators than simply casting to an UpdatableLocator.

If u supplies a 'Set(Locator[S])' method, that is used to set the impl Locator and this function returns true.

Otherwise, this function does nothing and returns false.

Types

type Algorithm

type Algorithm struct {
	// New64 is the constructor for a Hash64 appropriate for this algorithm.
	// This field is required. If this field is unset, methods on this
	// Algorithm may panic.
	New64 func() hash.Hash64

	// Sum64 is this algorithm's simple function to compute a hash over a
	// byte slice. For many algorithms, this function will be more efficient
	// in simple cases.
	//
	// This field is not required. If not supplied, New64 will be used to
	// create a hash of the given bytes.
	Sum64 func([]byte) uint64
}

Algorithm represents a hash algorithm which medley can use to implement service location.

func DefaultAlgorithm

func DefaultAlgorithm() Algorithm

DefaultAlgorithm returns the default hash algorithm for medley. The returned object uses the murmur3 algorithm. The specific implementation is github.com/spaolacci/murmur3.

func (Algorithm) Sum64Bytes added in v0.0.2

func (alg Algorithm) Sum64Bytes(v []byte) uint64

Sumb64Bytes uses Sum64 to compute the hash of the given byte slice. If the Sum64 field isn't set, New64 is used to create a Hash64 and write the given bytes.

func (Algorithm) Sum64String added in v0.0.2

func (alg Algorithm) Sum64String(v string) uint64

Sum64String creates the hash of a string in a way that doesn't create unnecessary allocations.

If Sum64 is set, that function is used to compute the hash. Otherwise, New64 is used to create a Hash64 and write the string's bytes.

type BasicService added in v0.0.2

type BasicService struct {
	// Scheme is the URI scheme for the service, e.g. http.
	Scheme string

	// Host is the domain name or IP address of this service.
	Host string

	// Port is the IP port the service listens on.
	Port int

	// Path is the URI path for this service.
	Path string
}

BasicService is a URI-based service object that represents the typical things an application needs when describing a service. A string can hold the information in this struct, but sometimes an application needs easy access to the individual parts of a URI.

type HashBuilder added in v0.0.2

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

HashBuilder is a Fluent Builder for hash values. Instances of this type may be created via NewHashBuilder. If created directly, then Use must be called before attempting any writes to the builder.

This type is convenient for building hashes of complex types, such as structs. The HashBasicServiceTo function in this package gives an example of this usage.

func NewHashBuilder added in v0.0.2

func NewHashBuilder(dst io.Writer) *HashBuilder

NewHashBuilder creates a HashBuilder that writes to this given destination. Errors from the various WriteXXX methods are accumulated and available via Err(). When an error occurs on the underlying destination, all subsequent writes are ignored.

The given dst io.Writer may be a hash.Hash64. If so, then this builder's Sum64 method may be used to extract the current hash value.

func (*HashBuilder) CanReset added in v0.0.2

func (hb *HashBuilder) CanReset() bool

CanReset tests if Reset will actually do anything, i.e. if the currently wrapped io.Writer supplies a Reset method.

func (*HashBuilder) CanSum64 added in v0.0.2

func (hb *HashBuilder) CanSum64() bool

CanSum64 returns true if the currently wrapped io.Writer can compute the current hash value, i.e. if it supplies a Sum64() uint64 method.

func (*HashBuilder) Err added in v0.0.2

func (hb *HashBuilder) Err() error

Err returns the first error that occurred in any Fluent Chain using this builder. When any error occurs, all subsequent WriteXXX methods do nothing.

func (*HashBuilder) Reset added in v0.0.2

func (hb *HashBuilder) Reset()

Reset resets the underlying io.Writer to its initial state. If the currently wrapped io.Writer does not supply a Reset() method, this method does nothing.

This method allows a HashBuilder and/or its underlying writer to be reused for multiple hashes.

func (*HashBuilder) Sum64 added in v0.0.2

func (hb *HashBuilder) Sum64() (v uint64)

Sum64 returns the current, computed hash value. If the currently wrapped io.Writer does not provide a Sum64() uint64 method, this method returns zero (0).

To determine if this method can compute the current hash value, use CanSum64.

func (*HashBuilder) Use added in v0.0.2

func (hb *HashBuilder) Use(dst io.Writer) *HashBuilder

Use replaces this builder's underlying writer and resets error state. This method may be used to reuse a single builder for different hashes.

If a HashBuilder is created directly, without using NewHashBuilder, this method is required to initialize the builder or writing will cause a panic.

func (*HashBuilder) Write added in v0.0.2

func (hb *HashBuilder) Write(v []byte) *HashBuilder

Write writes the given bytes.

func (*HashBuilder) WriteFloat32 added in v0.0.2

func (hb *HashBuilder) WriteFloat32(v float32) *HashBuilder

WriteFloat32 writes a 32-bit float value in big endian form.

func (*HashBuilder) WriteFloat64 added in v0.0.2

func (hb *HashBuilder) WriteFloat64(v float64) *HashBuilder

WriteFloat64 writes a 64-bit float value in big endian form.

func (*HashBuilder) WriteString added in v0.0.2

func (hb *HashBuilder) WriteString(v string) *HashBuilder

WriteString writes the given string in a manner that does not require additional allocations.

func (*HashBuilder) WriteUint16 added in v0.0.2

func (hb *HashBuilder) WriteUint16(v uint16) *HashBuilder

WriteUint16 writes the given 16-bit integer in big endian form.

func (*HashBuilder) WriteUint32 added in v0.0.2

func (hb *HashBuilder) WriteUint32(v uint32) *HashBuilder

WriteUint32 writes the given 32-bit integer in big endian form.

func (*HashBuilder) WriteUint64 added in v0.0.2

func (hb *HashBuilder) WriteUint64(v uint64) *HashBuilder

WriteUint64 writes the given 64-bit integer in big endian form.

func (*HashBuilder) WriteUint8 added in v0.0.2

func (hb *HashBuilder) WriteUint8(v uint8) *HashBuilder

WriteUint8 writes the given 8-bit unsigned integer.

type Locator added in v0.0.2

type Locator[S Service] interface {
	// Find locates a service for a particular key.
	Find([]byte) (S, error)
}

Locator is a service locator based on hashing input objects.

type Map added in v0.0.2

type Map[S Service, V any] map[S]V

Map is a mapping of services onto arbitrary values. A Map can be used to dedupe services or to provide fast access to some associated value object.

func (Map[S, V]) Len added in v0.0.2

func (m Map[S, V]) Len() int

Len returns the count of services in this map.

func (Map[S, V]) Update added in v0.0.2

func (m Map[S, V]) Update(services ...S) iter.Seq[Update[S, V]]

Update compares an updated slice of services to this Map. One Update is generated for each service object in the update slice, and calling code can iterate over the update to examine its disposition.

This method is primarily useful when determining what to do when a set of services needs to be updated and rehashed.

type MultiLocator added in v0.0.2

type MultiLocator[S Service] struct {
	// contains filtered or unexported fields
}

MultiLocator represents an aggregate set of locators, each of which is consulted for services. Methods on this type are safe for concurrent usage. The zero value for this type is usable, but will return ErrNoServices. To initialize a MultiLocator with some locators, use NewMultiLocator.

A MultiLocator must not be copied after creation.

func NewMultiLocator added in v0.0.2

func NewMultiLocator[S Service](ls ...Locator[S]) *MultiLocator[S]

NewMultiLocator returns a MultiLocator initialized with the give set of Locators.

func (*MultiLocator[S]) Add added in v0.0.2

func (ml *MultiLocator[S]) Add(l Locator[S])

Add adds another locator to this MultiLocator. This method does not protect against adding a Locator more than once.

func (*MultiLocator[S]) Find added in v0.0.2

func (ml *MultiLocator[S]) Find(object []byte) ([]S, error)

Find returns the services from each locator in this aggregate. This method will halt early on error if any Locator returned an error other than ErrNoServices.

This method only returns ErrNoServices if and only if every locator returned no services.

func (*MultiLocator[S]) FindString added in v0.0.2

func (ml *MultiLocator[S]) FindString(object string) ([]S, error)

FindString locates services based on a string key.

func (*MultiLocator[S]) Remove added in v0.0.2

func (ml *MultiLocator[S]) Remove(l Locator[S])

Remove removes a locator from this MultiLocator. If the same Locator was added multiple times, this method only removes the first one.

type Service added in v0.0.2

type Service interface {
	comparable
}

Service represents some sort of endpoint that objects can be hashed to. The only requirement is that a Service satisfy comparable so that in can be used as map keys.

A service's underlying type may be a string, such as a host name or URL. Or a service could be a struct that gives a richer description of an endpoint.

type ServiceHasher added in v0.0.2

type ServiceHasher[S Service] func(io.Writer, S) error

ServiceHasher handles writing a Service's hashable bytes. This closure type is responsible for converting a Service object into a series of bytes to submit to a hashing function.

type StringService added in v0.0.2

type StringService interface {
	Service
	~string
}

StringService is a service whose underlying type is a string. Hostnames, URLs, service locator ids, etc. are usually of this type.

type UpdatableLocator added in v0.0.2

type UpdatableLocator[S Service] struct {
	// contains filtered or unexported fields
}

UpdatableLocator is a Locator whose actual implementation can be swapped out atomically. Useful for dynamic Locators such as would be driven by service discovery or DNS.

The zero value of this type is usable, but will return ErrNoServices. Use NewUpdatableLocator to return an initialized UpdatableLocator.

func NewUpdatableLocator added in v0.0.2

func NewUpdatableLocator[S Service](impl Locator[S]) *UpdatableLocator[S]

NewUpdatableLocator returns an UpdatableLocator initialized with the given implementation.

func (*UpdatableLocator[S]) Find added in v0.0.2

func (ul *UpdatableLocator[S]) Find(object []byte) (svc S, err error)

Find consults the current Locator implementation for the given object. This method returns ErrNoServices is no implementation has been set yet.

func (*UpdatableLocator[S]) Set added in v0.0.2

func (ul *UpdatableLocator[S]) Set(impl Locator[S])

Set atomically changes this locator's implementation. If the implementation is nil, methods of this UpdatableLocator will generally return ErrNoServices. Setting an implementation to nil effectively "turns off" this locator.

type Update added in v0.0.2

type Update[S Service, V any] struct {
	// Service is the service object. One result per service in the update list
	// will be generated.
	Service S

	// Value is the value object associated with Service. If the Service didn't
	// exist in the map, this field will just be the zero value for its type.
	Value V

	// Exists indicates whether the Service field existed in the Map.
	Exists bool
}

Update indicates the disposition of a service object that is (possibly) an update.

Directories

Path Synopsis

Jump to

Keyboard shortcuts

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