Documentation
¶
Overview ¶
Package storage contains storage interfaces and implementations.
Index ¶
- Constants
- Variables
- func ContextWithRelationshipTupleReader(parent context.Context, reader RelationshipTupleReader) context.Context
- func ExceededMaxTypeDefinitionsLimitError(limit int) error
- func InvalidWriteInputError(tk tuple.TupleWithoutCondition, operation openfgav1.TupleOperation) error
- type AssertionsBackend
- type AuthorizationModelBackend
- type AuthorizationModelReadBackend
- type ChangelogBackend
- type Deletes
- type Iterator
- type OpenFGADatastore
- type PaginationOptions
- type ReadStartingWithUserFilter
- type ReadUsersetTuplesFilter
- type ReadinessStatus
- type RelationshipTupleReader
- type RelationshipTupleWriter
- type StoresBackend
- type TupleBackend
- type TupleIterator
- type TupleKeyFilterFunc
- type TupleKeyIterator
- type TupleRecord
- type TypeDefinitionWriteBackend
- type Writes
Examples ¶
Constants ¶
const ( // DefaultMaxTuplesPerWrite specifies the default maximum number of tuples that can be written // in a single write operation. This constant is used to limit the batch size in write operations // to maintain performance and avoid overloading the system. The value is set to 100 tuples, // which is a balance between efficiency and resource usage. DefaultMaxTuplesPerWrite = 100 // DefaultMaxTypesPerAuthorizationModel defines the default upper limit on the number of distinct // types that can be included in a single authorization model. This constraint helps in managing // the complexity and ensuring the maintainability of the authorization models. The limit is // set to 100 types, providing ample flexibility while keeping the model manageable. DefaultMaxTypesPerAuthorizationModel = 100 // DefaultPageSize sets the default number of items to be returned in a single page when paginating // through a set of results. This constant is used to standardize the pagination size across various // parts of the system, ensuring a consistent and manageable volume of data per page. The default // value is set to 50, balancing detail per page with the overall number of pages. DefaultPageSize = 50 )
Variables ¶
var ( // ErrCollision is returned when an item already exists within the store. ErrCollision = errors.New("item already exists") // ErrInvalidContinuationToken is returned when the continuation token is invalid. ErrInvalidContinuationToken = errors.New("invalid continuation token") // ErrMismatchObjectType is returned when there is a type discrepancy between the requested // object in the ReadChanges API and the type indicated by the continuation token. ErrMismatchObjectType = errors.New("mismatched types in request and continuation token") // ErrInvalidWriteInput is returned when the tuple to be written // already existed or the tuple to be deleted did not exist. ErrInvalidWriteInput = errors.New("invalid write input") // ErrTransactionalWriteFailed is returned when two writes attempt to write the same tuple at the same time. ErrTransactionalWriteFailed = errors.New("transactional write failed due to conflict") // ErrExceededWriteBatchLimit is returned when MaxTuplesPerWrite is exceeded. ErrExceededWriteBatchLimit = errors.New("number of operations exceeded write batch limit") // ErrCancelled is returned when the request has been cancelled. ErrCancelled = errors.New("request has been cancelled") // ErrDeadlineExceeded is returned when the request's deadline is exceeded. ErrDeadlineExceeded = errors.New("request deadline exceeded") // ErrNotFound is returned when the object does not exist. ErrNotFound = errors.New("not found") )
var ErrIteratorDone = errors.New("iterator done")
ErrIteratorDone is returned when the iterator has finished iterating through all the items.
Functions ¶
func ContextWithRelationshipTupleReader ¶ added in v1.5.0
func ContextWithRelationshipTupleReader( parent context.Context, reader RelationshipTupleReader, ) context.Context
ContextWithRelationshipTupleReader sets the provided [RelationshipTupleReader] in the context. The context returned is a new context derived from the parent context provided.
func ExceededMaxTypeDefinitionsLimitError ¶
ExceededMaxTypeDefinitionsLimitError constructs an error indicating that the maximum allowed limit for type definitions has been exceeded.
func InvalidWriteInputError ¶
func InvalidWriteInputError(tk tuple.TupleWithoutCondition, operation openfgav1.TupleOperation) error
InvalidWriteInputError generates an error for invalid operations in a tuple store. This function is invoked when an attempt is made to write or delete a tuple with invalid conditions. Specifically, it addresses two scenarios: 1. Attempting to delete a non-existent tuple. 2. Attempting to write a tuple that already exists.
Types ¶
type AssertionsBackend ¶
type AssertionsBackend interface {
// WriteAssertions overwrites the assertions for a store and modelID.
WriteAssertions(ctx context.Context, store, modelID string, assertions []*openfgav1.Assertion) error
// ReadAssertions returns the assertions for a store and modelID.
// If no assertions were ever written, it must return an empty list.
ReadAssertions(ctx context.Context, store, modelID string) ([]*openfgav1.Assertion, error)
}
AssertionsBackend is an interface that defines the set of methods for reading and writing assertions.
type AuthorizationModelBackend ¶
type AuthorizationModelBackend interface {
AuthorizationModelReadBackend
TypeDefinitionWriteBackend
}
AuthorizationModelBackend provides an read/write interface for managing models and their type definitions.
type AuthorizationModelReadBackend ¶
type AuthorizationModelReadBackend interface {
// ReadAuthorizationModel reads the model corresponding to store and model ID.
// If it's not found, it must return ErrNotFound.
ReadAuthorizationModel(ctx context.Context, store string, id string) (*openfgav1.AuthorizationModel, error)
// ReadAuthorizationModels reads all models for the supplied store and returns them in descending order of ULID (from newest to oldest).
ReadAuthorizationModels(ctx context.Context, store string, options PaginationOptions) ([]*openfgav1.AuthorizationModel, []byte, error)
// FindLatestAuthorizationModel returns the last model for the store.
// If none were ever written, it must return ErrNotFound.
FindLatestAuthorizationModel(ctx context.Context, store string) (*openfgav1.AuthorizationModel, error)
}
AuthorizationModelReadBackend provides a read interface for managing type definitions.
type ChangelogBackend ¶
type ChangelogBackend interface {
// ReadChanges returns the writes and deletes that have occurred for tuples within a store,
// in the order that they occurred.
// You can optionally provide a filter to filter out changes for objects of a specific type.
// The horizonOffset should be specified using a unit no more granular than a millisecond
// and should be interpreted as a millisecond duration.
ReadChanges(
ctx context.Context,
store,
objectType string,
paginationOptions PaginationOptions,
horizonOffset time.Duration,
) ([]*openfgav1.TupleChange, []byte, error)
}
ChangelogBackend is an interface for interacting with and managing changelogs.
type Deletes ¶
type Deletes = []*openfgav1.TupleKeyWithoutCondition
Deletes is a typesafe alias for Delete arguments.
type Iterator ¶
type Iterator[T any] interface { // Next will return the next available // item or ErrIteratorDone if no more // items are available. Next(ctx context.Context) (T, error) // Stop terminates iteration over // the underlying iterator. Stop() }
Iterator is a generic interface defining methods for iterating over a collection of items of type T.
func NewCombinedIterator ¶
NewCombinedIterator takes generic iterators of a given type T and combines them into a single iterator that yields all the values from all iterators. Duplicates can be returned.
type OpenFGADatastore ¶
type OpenFGADatastore interface {
TupleBackend
AuthorizationModelBackend
StoresBackend
AssertionsBackend
ChangelogBackend
// IsReady reports whether the datastore is ready to accept traffic.
IsReady(ctx context.Context) (ReadinessStatus, error)
// Close closes the datastore and cleans up any residual resources.
Close()
}
OpenFGADatastore is an interface that defines a set of methods for interacting with and managing data in an OpenFGA (Fine-Grained Authorization) system.
type PaginationOptions ¶
PaginationOptions holds the settings for pagination in data retrieval operations. It defines the number of items to be included on each page (PageSize) and a marker from where to start the page (From).
func NewPaginationOptions ¶
func NewPaginationOptions(ps int32, contToken string) PaginationOptions
NewPaginationOptions creates a new PaginationOptions instance with a specified page size and continuation token. If the input page size is empty, it uses DefaultPageSize
type ReadStartingWithUserFilter ¶
type ReadStartingWithUserFilter struct {
ObjectType string
Relation string
UserFilter []*openfgav1.ObjectRelation
}
ReadStartingWithUserFilter specifies the filter options that will be used to constrain the [RelationshipTupleReader.ReadStartingWithUser] query.
type ReadUsersetTuplesFilter ¶ added in v0.4.0
type ReadUsersetTuplesFilter struct {
Object string // Required.
Relation string // Required.
AllowedUserTypeRestrictions []*openfgav1.RelationReference // Optional.
}
ReadUsersetTuplesFilter specifies the filter options that will be used to constrain the ReadUsersetTuples query.
type ReadinessStatus ¶ added in v1.3.8
type ReadinessStatus struct {
// Message is a human-friendly status message for the current datastore status.
Message string
IsReady bool
}
ReadinessStatus represents the readiness status of the datastore.
type RelationshipTupleReader ¶
type RelationshipTupleReader interface {
// Read the set of tuples associated with `store` and `tupleKey`, which may be nil or partially filled. If nil,
// Read will return an iterator over all the tuples in the given `store`. If the `tupleKey` is partially filled,
// it will return an iterator over those tuples which match the `tupleKey`. Note that at least one of `Object`
// or `User` (or both), must be specified in this case.
//
// The caller must be careful to close the [TupleIterator], either by consuming the entire iterator or by closing it.
// There is NO guarantee on the order returned on the iterator.
Read(ctx context.Context, store string, tupleKey *openfgav1.TupleKey) (TupleIterator, error)
// ReadPage functions similarly to Read but includes support for pagination. It takes
// mandatory pagination options (pageSize can be zero :/)
// and returns a slice of tuples along with a continuation token. This token can be used for retrieving subsequent pages of data.
ReadPage(
ctx context.Context,
store string,
tupleKey *openfgav1.TupleKey,
paginationOptions PaginationOptions,
) ([]*openfgav1.Tuple, []byte, error)
// ReadUserTuple tries to return one tuple that matches the provided key exactly.
// If none is found, it must return [ErrNotFound].
ReadUserTuple(
ctx context.Context,
store string,
tupleKey *openfgav1.TupleKey,
) (*openfgav1.Tuple, error)
// ReadUsersetTuples returns all userset tuples for a specified object and relation.
// For example, given the following relationship tuples:
// document:doc1, viewer, user:*
// document:doc1, viewer, group:eng#member
// and the filter
// object=document:1, relation=viewer, allowedTypesForUser=[group#member]
// this method would return the tuple (document:doc1, viewer, group:eng#member)
// If allowedTypesForUser is empty, both tuples would be returned.
// There is NO guarantee on the order returned on the iterator.
ReadUsersetTuples(
ctx context.Context,
store string,
filter ReadUsersetTuplesFilter,
) (TupleIterator, error)
// ReadStartingWithUser performs a reverse read of relationship tuples starting at one or
// more user(s) or userset(s) and filtered by object type and relation.
//
// For example, given the following relationship tuples:
// document:doc1, viewer, user:jon
// document:doc2, viewer, group:eng#member
// document:doc3, editor, user:jon
//
// ReverseReadTuples for ['user:jon', 'group:eng#member'] filtered by 'document#viewer' would
// return ['document:doc1#viewer@user:jon', 'document:doc2#viewer@group:eng#member'].
// There is NO guarantee on the order returned on the iterator.
ReadStartingWithUser(
ctx context.Context,
store string,
filter ReadStartingWithUserFilter,
) (TupleIterator, error)
}
RelationshipTupleReader is an interface that defines the set of methods required to read relationship tuples from a data store.
func RelationshipTupleReaderFromContext ¶ added in v1.5.0
func RelationshipTupleReaderFromContext(ctx context.Context) (RelationshipTupleReader, bool)
RelationshipTupleReaderFromContext extracts a [RelationshipTupleReader] from the provided context (if any). If no such value is in the context a boolean false is returned, otherwise the RelationshipTupleReader is returned.
type RelationshipTupleWriter ¶
type RelationshipTupleWriter interface {
// Write updates data in the tuple backend, performing all delete operations in
// `deletes` before adding new values in `writes`, returning the time of the transaction, or an error.
// If there are more than MaxTuplesPerWrite, it must return ErrExceededWriteBatchLimit.
// If two requests attempt to write the same tuple at the same time, it must return ErrTransactionalWriteFailed.
// If the tuple to be written already existed or the tuple to be deleted didn't exist, it must return ErrInvalidWriteInput.
Write(ctx context.Context, store string, d Deletes, w Writes) error
// MaxTuplesPerWrite returns the maximum number of items (writes and deletes combined)
// allowed in a single write transaction.
MaxTuplesPerWrite() int
}
RelationshipTupleWriter is an interface that defines the set of methods required for writing relationship tuples in a data store.
type StoresBackend ¶
type StoresBackend interface {
CreateStore(ctx context.Context, store *openfgav1.Store) (*openfgav1.Store, error)
DeleteStore(ctx context.Context, id string) error
GetStore(ctx context.Context, id string) (*openfgav1.Store, error)
ListStores(ctx context.Context, paginationOptions PaginationOptions) ([]*openfgav1.Store, []byte, error)
}
StoresBackend is an interface that defines the set of methods required for interacting with and managing different types of storage backends.
type TupleBackend ¶
type TupleBackend interface {
RelationshipTupleReader
RelationshipTupleWriter
}
A TupleBackend provides a read/write interface for managing tuples.
type TupleIterator ¶
TupleIterator is an iterator for *openfgav1.Tuple(s). It is closed by explicitly calling [Iterator.Stop] or by calling [Iterator.Next] until it returns an ErrIteratorDone error.
func NewStaticTupleIterator ¶
func NewStaticTupleIterator(tuples []*openfgav1.Tuple) TupleIterator
NewStaticTupleIterator returns a TupleIterator that iterates over the provided slice.
type TupleKeyFilterFunc ¶
TupleKeyFilterFunc is a filter function that is used to filter out tuples from a TupleKeyIterator that don't meet certain criteria. Implementations should return true if the tuple should be returned and false if it should be filtered out.
type TupleKeyIterator ¶
TupleKeyIterator is an iterator for *openfgav1.TupleKey(s). It is closed by explicitly calling [Iterator.Stop] or by calling [Iterator.Next] until it returns an ErrIteratorDone error.
func NewFilteredTupleKeyIterator ¶
func NewFilteredTupleKeyIterator(iter TupleKeyIterator, filter TupleKeyFilterFunc) TupleKeyIterator
NewFilteredTupleKeyIterator returns a TupleKeyIterator that filters out all *openfgav1.Tuple(s) that don't meet the conditions of the provided TupleKeyFilterFunc.
Example ¶
tuples := []*openfgav1.TupleKey{
tuple.NewTupleKey("document:doc1", "viewer", "user:jon"),
tuple.NewTupleKey("document:doc1", "editor", "user:elbuo"),
}
iter := NewFilteredTupleKeyIterator(
NewStaticTupleKeyIterator(tuples),
func(tk *openfgav1.TupleKey) bool {
return tk.GetRelation() == "editor"
},
)
defer iter.Stop()
var filtered []string
for {
tuple, err := iter.Next(context.Background())
if err != nil {
if err == ErrIteratorDone {
break
}
// Handle the error in some way.
panic(err)
}
filtered = append(filtered, fmt.Sprintf("%s#%s@%s", tuple.GetObject(), tuple.GetRelation(), tuple.GetUser()))
}
fmt.Println(filtered)
Output: [document:doc1#editor@user:elbuo]
func NewStaticTupleKeyIterator ¶
func NewStaticTupleKeyIterator(tupleKeys []*openfgav1.TupleKey) TupleKeyIterator
NewStaticTupleKeyIterator returns a TupleKeyIterator that iterates over the provided slice.
func NewTupleKeyIteratorFromTupleIterator ¶
func NewTupleKeyIteratorFromTupleIterator(iter TupleIterator) TupleKeyIterator
NewTupleKeyIteratorFromTupleIterator takes a TupleIterator and yields all the *openfgav1.TupleKey(s) from it as a TupleKeyIterator.
type TupleRecord ¶ added in v1.3.8
type TupleRecord struct {
Store string
ObjectType string
ObjectID string
Relation string
User string
ConditionName string
ConditionContext *structpb.Struct
Ulid string
InsertedAt time.Time
}
TupleRecord represents a record structure used to store information about a specific tuple.
func (*TupleRecord) AsTuple ¶ added in v1.3.8
func (t *TupleRecord) AsTuple() *openfgav1.Tuple
AsTuple converts a TupleRecord into a *openfgav1.Tuple.
type TypeDefinitionWriteBackend ¶
type TypeDefinitionWriteBackend interface {
// MaxTypesPerAuthorizationModel returns the maximum number of type definition rows/items per model.
MaxTypesPerAuthorizationModel() int
// WriteAuthorizationModel writes an authorization model for the given store.
WriteAuthorizationModel(ctx context.Context, store string, model *openfgav1.AuthorizationModel) error
}
TypeDefinitionWriteBackend provides a write interface for managing typed definition.
Directories
¶
| Path | Synopsis |
|---|---|
|
Package memory contains an implementation of the storage interface that lives in memory.
|
Package memory contains an implementation of the storage interface that lives in memory. |
|
Package mysql contains an implementation of the storage interface that works with MySQL.
|
Package mysql contains an implementation of the storage interface that works with MySQL. |
|
Package postgres contains an implementation of the storage interface that works with Postgres.
|
Package postgres contains an implementation of the storage interface that works with Postgres. |
|
Package sqlcommon contains utility functions shared among all SQL data stores.
|
Package sqlcommon contains utility functions shared among all SQL data stores. |
|
Package storagewrappers contains decorators for storage implementations.
|
Package storagewrappers contains decorators for storage implementations. |