fgax

package module
v0.0.2 Latest Latest
Warning

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

Go to latest
Published: Jan 31, 2024 License: Apache-2.0 Imports: 17 Imported by: 2

README

Build status

fgax

Go libraries to interact with OpenFGA

Packages

fgax

Wrappers to interact with the OpenFGA go-sdk and client libraries

Installation

You can install fgax by running the following command:

go get github.com/datumforge/fgax@latest
entfga

Ent extension to create relationship tuples using Ent Hooks

Installation

You can install entfga by running the following command:

go get github.com/datumforge/fgax/entfga@latest

In addition to installing entfga, you need to create two files in your ent directory: entc.go and generate.go. The entc.go file should contain the following code:

//go:build ignore

package main

import (
	"log"
	"github.com/datumforge/fgax/entfga"
	"entgo.io/ent/entc"
)

func main() {
	if err := entc.Generate("./schema",
		&gen.Config{},
		entc.Extensions(
            entfga.NewFGAExtension(
                entfga.WithSoftDeletes(),
            ),
		),
	); err != nil {
		log.Fatal("running ent codegen:", err)
	}
}

The generate.go file should contain the following code:

package ent

//go:generate go run -mod=mod entc.go
Usage

When creating the *ent.Client add the following to enable the authz hooks:

	client.WithAuthz()

In the ent schema, provide the following annotation:

// Annotations of the OrgMembership
func (OrgMembership) Annotations() []schema.Annotation {
	return []schema.Annotation{
		entfga.Annotations{
			ObjectType: "organization",
		},
	}
}

The ObjectType must be the same between the ID field name in the schema and the object type in the FGA relationship. In the example above the field in the schema is OrganizationID and the object in FGA is organization.

Soft Deletes

If you are using the soft delete mixin provided by entx, add the following option to the extension:

    entfga.WithSoftDeletes(),

This will allow the hooks to delete tuples correctly after the ent.Op is updated to a UpdateOne from a DeleteOne

Documentation

Overview

Package fgax includes client libraries to interact with openfga authorization credit to https://github.com/canonical/ofga/blob/main/tuples.go

Index

Constants

View Source
const (
	// setup relations for use in creating tuples
	MemberRelation = "member"
	AdminRelation  = "admin"
	OwnerRelation  = "owner"
	ParentRelation = "parent"
	CanView        = "can_view"
	CanEdit        = "can_edit"
	CanDelete      = "can_delete"
)

Variables

View Source
var (
	// ErrFGAMissingHost is returned when a host is not provided
	ErrFGAMissingHost = errors.New("invalid OpenFGA config: missing host")

	// ErrMissingRelation is returned when a relation is empty in a tuple creation
	ErrMissingRelation = errors.New("unable to create tuple, missing relation")

	// ErrMissingObject is returned when a object is empty in a tuple creation
	ErrMissingObject = errors.New("unable to create tuple, missing object")

	// ErrMissingObjectOnDeletion is returned when a object is empty in a tuple deletion
	ErrMissingObjectOnDeletion = errors.New("unable to delete tuple, missing object")

	// ErrFailedToTransformModel is returned when the FGA model cannot be transformed to JSON
	ErrFailedToTransformModel = errors.New("failed to transform fga model")
)

Functions

func Healthcheck

func Healthcheck(client Client) func(ctx context.Context) error

Healthcheck reads the model to check if the connection is working

func ListContains

func ListContains(entityType string, l []string, i string) bool

ListContains checks the results of an fga ListObjects and parses the entities to get the identifier to compare to another identifier based on entity type

Types

type Client

type Client struct {
	// Ofga is the openFGA client
	Ofga ofgaclient.SdkClient
	// Config is the client configuration
	Config ofgaclient.ClientConfiguration
	// Logger is the provided Logger
	Logger *zap.SugaredLogger
}

Client is an event bus client with some configuration

func CreateFGAClientWithStore

func CreateFGAClientWithStore(ctx context.Context, c Config) (*Client, error)

CreateFGAClientWithStore returns a Client with a store and model configured

func NewClient

func NewClient(host string, opts ...Option) (*Client, error)

NewClient returns a wrapped OpenFGA API client ensuring all calls are made to the provided authorization model (id) and returns what is necessary.

func NewMockFGAClient

func NewMockFGAClient(t *testing.T, c *mock_fga.MockSdkClient) *Client

NewMockFGAClient is a mock client based on the mockery testing framework

func (*Client) CheckGroupAccess

func (c *Client) CheckGroupAccess(ctx context.Context, userID, groupID, relation string) (bool, error)

func (*Client) CheckOrgAccess

func (c *Client) CheckOrgAccess(ctx context.Context, userID, orgID, relation string) (bool, error)

func (*Client) CheckTuple

func (c *Client) CheckTuple(ctx context.Context, check ofgaclient.ClientCheckRequest) (bool, error)

CheckTuple checks the openFGA store for provided relationship tuple

func (*Client) CreateModel

func (c *Client) CreateModel(ctx context.Context, fn string, forceCreate bool) (string, error)

CreateModel creates a new fine grained authorization model and returns the model ID

func (*Client) CreateStore

func (c *Client) CreateStore(ctx context.Context, storeName string) (string, error)

CreateStore creates a new fine grained authorization store and returns the store ID

func (*Client) DeleteAllObjectRelations

func (c *Client) DeleteAllObjectRelations(ctx context.Context, object string) error

func (*Client) DeleteRelationshipTuple

func (c *Client) DeleteRelationshipTuple(ctx context.Context, tuples []openfga.TupleKeyWithoutCondition) (*ofgaclient.ClientWriteResponse, error)

DeleteRelationshipTuple deletes a relationship tuple in the openFGA store

func (*Client) GetModelID

func (c *Client) GetModelID() string

func (*Client) ListObjectsRequest

func (c *Client) ListObjectsRequest(ctx context.Context, userID, objectType, relation string) (*ofgaclient.ClientListObjectsResponse, error)

ListObjectsRequest creates the ClientListObjectsRequest and queries the FGA store for all objects with the user+relation

func (*Client) WriteTupleKeys

func (c *Client) WriteTupleKeys(ctx context.Context, writes []TupleKey, deletes []TupleKey) (*ofgaclient.ClientWriteResponse, error)

WriteTupleKeys takes a tuples keys, converts them to a client write request, which can contain up to 10 writes and deletes, and executes in a single transaction

type Config

type Config struct {
	// Enabled - checks this first before reading the config
	Enabled bool `yaml:"enabled" split_words:"true" default:"true"`
	// StoreName of the FGA Store
	StoreName string `yaml:"storeName" split_words:"true" default:"datum"`
	// Host of the fga API
	Host string `yaml:"host" split_words:"true" default:"authz.datum.net"`
	// Scheme to connect to the fga API (http or https)
	Scheme string `yaml:"enabled" split_words:"true" default:"https"`
	// StoreID of the authorization store in FGA
	StoreID string `yaml:"enabled" split_words:"true" default:""`
	// ModelID that already exists in authorization store to be used
	ModelID string `yaml:"enabled" split_words:"true" default:""`
	// CreateNewModel force creates a new model, even if one already exists
	CreateNewModel bool `yaml:"enabled" split_words:"true" default:"false"`
	// contains filtered or unexported fields
}

Config configures the openFGA setup

func NewAuthzConfig

func NewAuthzConfig(l *zap.SugaredLogger) (*Config, error)

NewAuthzConfig returns a new authorization configuration

type Entity

type Entity struct {
	Kind       Kind
	Identifier string
	Relation   Relation
}

Entity represents an entity/entity-set in OpenFGA. Example: `user:<user-id>`, `org:<org-id>#member`

func ParseEntity

func ParseEntity(s string) (Entity, error)

ParseEntity will parse a string representation into an Entity. It expects to find entities of the form:

  • <entityType>:<Identifier> eg. organization:datum
  • <entityType>:<Identifier>#<relationship-set> eg. organization:datum#member

func (*Entity) String

func (e *Entity) String() string

String returns a string representation of the entity/entity-set.

type InvalidEntityError

type InvalidEntityError struct {
	EntityRepresentation string
}

InvalidEntityError is returned when an invalid openFGA entity is configured

func (*InvalidEntityError) Error

func (e *InvalidEntityError) Error() string

Error returns the InvalidEntityError in string format

type Kind

type Kind string

Kind represents the type of the entity in OpenFGA.

func (Kind) String

func (k Kind) String() string

String implements the Stringer interface.

type Option

type Option func(c *Client)

Option is a functional configuration option for openFGA client

func WithAuthorizationModelID

func WithAuthorizationModelID(authModelID string) Option

WithAuthorizationModelID sets the authorization model ID

func WithLogger

func WithLogger(l *zap.SugaredLogger) Option

WithLogger sets logger

func WithScheme

func WithScheme(scheme string) Option

WithScheme sets the open fga scheme, defaults to "https"

func WithStoreID

func WithStoreID(storeID string) Option

WithStoreID sets the store IDs, not needed when calling `CreateStore` or `ListStores`

func WithToken

func WithToken(token string) Option

WithToken sets the client credentials

type Relation

type Relation string

Relation represents the type of relation between entities in OpenFGA.

func (Relation) String

func (r Relation) String() string

String implements the Stringer interface.

type TupleKey

type TupleKey struct {
	Subject  Entity
	Object   Entity
	Relation Relation `json:"relation"`
}

func GetTupleKey

func GetTupleKey(subjectID, subjectType, objectID, objectType, relation string) TupleKey

GetTupleKey creates a Tuple key with the provided subject, object, and role

func NewTupleKey

func NewTupleKey() TupleKey

type WritingTuplesError

type WritingTuplesError struct {
	User          string
	Relation      string
	Object        string
	Operation     string
	ErrorResponse error
}

WritingTuplesError is returned when an error is returned writing a relationship tuple

func (*WritingTuplesError) Error

func (e *WritingTuplesError) Error() string

Error returns the InvalidEntityError in string format

Directories

Path Synopsis
Package entfga is an ent extension that creates hooks for OpenFGA relationships
Package entfga is an ent extension that creates hooks for OpenFGA relationships
Package client includes the mock FGA client generated by testify mockery
Package client includes the mock FGA client generated by testify mockery

Jump to

Keyboard shortcuts

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