auth

package
v0.0.0-...-f17446d Latest Latest
Warning

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

Go to latest
Published: May 14, 2022 License: Apache-2.0 Imports: 8 Imported by: 0

README

Auth - Authentication and Authorization service

Auth service provides authentication features as an API for managing authentication keys as well as administering groups of entities - things and users.

Authentication

User service is using Auth service gRPC API to obtain login token or password reset token. Authentication key consists of the following fields:

  • ID - key ID
  • Type - one of the three types described below
  • IssuerID - an ID of the Mainflux User who issued the key
  • Subject - user email
  • IssuedAt - the timestamp when the key is issued
  • ExpiresAt - the timestamp after which the key is invalid

There are three types of authentication keys:

  • User key - keys issued to the user upon login request
  • API key - keys issued upon the user request
  • Recovery key - password recovery key

Authentication keys are represented and distributed by the corresponding JWT.

User keys are issued when user logs in. Each user request (other than registration and login) contains user key that is used to authenticate the user.

API keys are similar to the User keys. The main difference is that API keys have configurable expiration time. If no time is set, the key will never expire. For that reason, API keys are the only key type that can be revoked. This also means that, despite being used as a JWT, it requires a query to the database to validate the API key. The user with API key can perform all the same actions as the user with login key (can act on behalf of the user for Thing, Channel, or user profile management), except issuing new API keys.

Recovery key is the password recovery key. It's short-lived token used for password recovery process.

For in-depth explanation of the aforementioned scenarios, as well as thorough understanding of Mainflux, please check out the official documentation.

The following actions are supported:

  • create (all key types)
  • verify (all key types)
  • obtain (API keys only)
  • revoke (API keys only)

Groups

User and Things service are using Auth gRPC API to get the list of ids that are part of a group. Groups can be organized as tree structure. Group consists of the following fields:

  • ID - ULID id uniquely representing group
  • Name - name of the group, name of the group is unique at the same level of tree hierarchy for a given tree.
  • ParentID - id of the parent group
  • OwnerID - id of the user that created a group
  • Description - free form text, up to 1024 characters
  • Metadata - Arbitrary, object-encoded group's data
  • Path - tree path consisting of group ids
  • CreatedAt - timestamp at which the group is created
  • UpdatedAt - timestamp at which the group is updated

Configuration

The service is configured using the environment variables presented in the following table. Note that any unset variables will be replaced with their default values.

Variable Description Default
MF_AUTH_LOG_LEVEL Service level (debug, info, warn, error) error
MF_AUTH_DB_HOST Database host address localhost
MF_AUTH_DB_PORT Database host port 5432
MF_AUTH_DB_USER Database user mainflux
MF_AUTH_DB_PASSWORD Database password mainflux
MF_AUTH_DB Name of the database used by the service auth
MF_AUTH_DB_SSL_MODE Database connection SSL mode (disable, require, verify-ca, verify-full) disable
MF_AUTH_DB_SSL_CERT Path to the PEM encoded certificate file
MF_AUTH_DB_SSL_KEY Path to the PEM encoded key file
MF_AUTH_DB_SSL_ROOT_CERT Path to the PEM encoded root certificate file
MF_AUTH_HTTP_PORT Auth service HTTP port 8180
MF_AUTH_GRPC_PORT Auth service gRPC port 8181
MF_AUTH_SERVER_CERT Path to server certificate in pem format
MF_AUTH_SERVER_KEY Path to server key in pem format
MF_AUTH_SECRET String used for signing tokens auth
MF_AUTH_LOGIN_TOKEN_DURATION The login token expiration period 10h
MF_JAEGER_URL Jaeger server URL localhost:6831
MF_KETO_READ_REMOTE_HOST Keto Read Host mainflux-keto
MF_KETO_WRITE_REMOTE_HOST Keto Write Host mainflux-keto
MF_KETO_READ_REMOTE_PORT Keto Read Port 4466
MF_KETO_WRITE_REMOTE_PORT Keto Write Port 4467

Deployment

The service itself is distributed as Docker container. Check the auth service section in docker-compose to see how service is deployed.

To start the service outside of the container, execute the following shell script:

# download the latest version of the service
go get github.com/mainflux/mainflux

cd $GOPATH/src/github.com/mainflux/mainflux

# compile the service
make auth

# copy binary to bin
make install

# set the environment variables and run the service
MF_AUTH_LOG_LEVEL=[Service log level] MF_AUTH_DB_HOST=[Database host address] MF_AUTH_DB_PORT=[Database host port] MF_AUTH_DB_USER=[Database user] MF_AUTH_DB_PASS=[Database password] MF_AUTH_DB=[Name of the database used by the service] MF_AUTH_DB_SSL_MODE=[SSL mode to connect to the database with] MF_AUTH_DB_SSL_CERT=[Path to the PEM encoded certificate file] MF_AUTH_DB_SSL_KEY=[Path to the PEM encoded key file] MF_AUTH_DB_SSL_ROOT_CERT=[Path to the PEM encoded root certificate file] MF_AUTH_HTTP_PORT=[Service HTTP port] MF_AUTH_GRPC_PORT=[Service gRPC port] MF_AUTH_SECRET=[String used for signing tokens] MF_AUTH_SERVER_CERT=[Path to server certificate] MF_AUTH_SERVER_KEY=[Path to server key] MF_JAEGER_URL=[Jaeger server URL] MF_AUTH_LOGIN_TOKEN_DURATION=[The login token expiration period] $GOBIN/mainflux-auth

If MF_EMAIL_TEMPLATE doesn't point to any file service will function but password reset functionality will not work.

Usage

For more information about service capabilities and its usage, please check out the API documentation.

Documentation

Index

Constants

View Source
const (
	// MaxLevel represents the maximum group hierarchy level.
	MaxLevel = uint64(5)
	// MinLevel represents the minimum group hierarchy level.
	MinLevel = uint64(1)
)
View Source
const (
	// LoginKey is temporary User key received on successfull login.
	LoginKey uint32 = iota
	// RecoveryKey represents a key for resseting password.
	RecoveryKey
	// APIKey enables the one to act on behalf of the user.
	APIKey
)

Variables

View Source
var (
	// ErrAssignToGroup indicates failure to assign member to a group.
	ErrAssignToGroup = errors.New("failed to assign member to a group")

	// ErrUnassignFromGroup indicates failure to unassign member from a group.
	ErrUnassignFromGroup = errors.New("failed to unassign member from a group")

	// ErrMissingParent indicates that parent can't be found
	ErrMissingParent = errors.New("failed to retrieve parent")

	// ErrGroupNotEmpty indicates group is not empty, can't be deleted.
	ErrGroupNotEmpty = errors.New("group is not empty")

	// ErrMemberAlreadyAssigned indicates that members is already assigned.
	ErrMemberAlreadyAssigned = errors.New("member is already assigned")
)
View Source
var (
	// ErrInvalidKeyIssuedAt indicates that the Key is being used before it's issued.
	ErrInvalidKeyIssuedAt = errors.New("invalid issue time")

	// ErrKeyExpired indicates that the Key is expired.
	ErrKeyExpired = errors.New("use of expired key")

	// ErrAPIKeyExpired indicates that the Key is expired
	// and that the key type is API key.
	ErrAPIKeyExpired = errors.New("use of expired API key")
)
View Source
var (
	// ErrFailedToRetrieveMembers failed to retrieve group members.
	ErrFailedToRetrieveMembers = errors.New("failed to retrieve group members")

	// ErrFailedToRetrieveMembership failed to retrieve memberships
	ErrFailedToRetrieveMembership = errors.New("failed to retrieve memberships")

	// ErrFailedToRetrieveAll failed to retrieve groups.
	ErrFailedToRetrieveAll = errors.New("failed to retrieve all groups")

	// ErrFailedToRetrieveParents failed to retrieve groups.
	ErrFailedToRetrieveParents = errors.New("failed to retrieve all groups")

	// ErrFailedToRetrieveChildren failed to retrieve groups.
	ErrFailedToRetrieveChildren = errors.New("failed to retrieve all groups")
)

Functions

This section is empty.

Types

type Authn

type Authn interface {
	// Issue issues a new Key, returning its token value alongside.
	Issue(ctx context.Context, token string, key Key) (Key, string, error)

	// Revoke removes the Key with the provided id that is
	// issued by the user identified by the provided key.
	Revoke(ctx context.Context, token, id string) error

	// RetrieveKey retrieves data for the Key identified by the provided
	// ID, that is issued by the user identified by the provided key.
	RetrieveKey(ctx context.Context, token, id string) (Key, error)

	// Identify validates token token. If token is valid, content
	// is returned. If token is invalid, or invocation failed for some
	// other reason, non-nil error value is returned in response.
	Identify(ctx context.Context, token string) (Identity, error)
}

Authn specifies an API that must be fullfiled by the domain service implementation, and all of its decorators (e.g. logging & metrics). Token is a string value of the actual Key and is used to authenticate an Auth service request.

type Authz

type Authz interface {
	// Authorize checks authorization of the given `subject`. Basically,
	// Authorize verifies that Is `subject` allowed to `relation` on
	// `object`. Authorize returns a non-nil error if the subject has
	// no relation on the object (which simply means the operation is
	// denied).
	Authorize(ctx context.Context, pr PolicyReq) error

	// AddPolicy creates a policy for the given subject, so that, after
	// AddPolicy, `subject` has a `relation` on `object`. Returns a non-nil
	// error in case of failures.
	AddPolicy(ctx context.Context, pr PolicyReq) error

	// AddPolicies adds new policies for given subjects. This method is
	// only allowed to use as an admin.
	AddPolicies(ctx context.Context, token, object string, subjectIDs, relations []string) error

	// DeletePolicy removes a policy.
	DeletePolicy(ctx context.Context, pr PolicyReq) error

	// DeletePolicies deletes policies for given subjects. This method is
	// only allowed to use as an admin.
	DeletePolicies(ctx context.Context, token, object string, subjectIDs, relations []string) error

	// ListPolicies lists policies based on the given PolicyReq structure.
	ListPolicies(ctx context.Context, pr PolicyReq) (PolicyPage, error)
}

Authz represents a authorization service. It exposes functionalities through `auth` to perform authorization.

type Group

type Group struct {
	ID          string
	OwnerID     string
	ParentID    string
	Name        string
	Description string
	Metadata    GroupMetadata
	// Indicates a level in tree hierarchy.
	// Root node is level 1.
	Level int
	// Path in a tree consisting of group ids
	// parentID1.parentID2.childID1
	// e.g. 01EXPM5Z8HRGFAEWTETR1X1441.01EXPKW2TVK74S5NWQ979VJ4PJ.01EXPKW2TVK74S5NWQ979VJ4PJ
	Path      string
	Children  []*Group
	CreatedAt time.Time
	UpdatedAt time.Time
}

Group represents the group information.

type GroupMetadata

type GroupMetadata map[string]interface{}

GroupMetadata defines the Metadata type.

type GroupPage

type GroupPage struct {
	PageMetadata
	Groups []Group
}

GroupPage contains page related metadata as well as list of groups that belong to this page.

type GroupRepository

type GroupRepository interface {
	// Save group
	Save(ctx context.Context, g Group) (Group, error)

	// Update a group
	Update(ctx context.Context, g Group) (Group, error)

	// Delete a group
	Delete(ctx context.Context, id string) error

	// RetrieveByID retrieves group by its id
	RetrieveByID(ctx context.Context, id string) (Group, error)

	// RetrieveAll retrieves all groups.
	RetrieveAll(ctx context.Context, pm PageMetadata) (GroupPage, error)

	// RetrieveAllParents retrieves all groups that are ancestors to the group with given groupID.
	RetrieveAllParents(ctx context.Context, groupID string, pm PageMetadata) (GroupPage, error)

	// RetrieveAllChildren retrieves all children from group with given groupID up to the hierarchy level.
	RetrieveAllChildren(ctx context.Context, groupID string, pm PageMetadata) (GroupPage, error)

	//  Retrieves list of groups that member belongs to
	Memberships(ctx context.Context, memberID string, pm PageMetadata) (GroupPage, error)

	// Members retrieves everything that is assigned to a group identified by groupID.
	Members(ctx context.Context, groupID, groupType string, pm PageMetadata) (MemberPage, error)

	// Assign adds a member to group.
	Assign(ctx context.Context, groupID, groupType string, memberIDs ...string) error

	// Unassign removes a member from a group
	Unassign(ctx context.Context, groupID string, memberIDs ...string) error
}

GroupRepository specifies a group persistence API.

type GroupService

type GroupService interface {
	// CreateGroup creates new  group.
	CreateGroup(ctx context.Context, token string, g Group) (Group, error)

	// UpdateGroup updates the group identified by the provided ID.
	UpdateGroup(ctx context.Context, token string, g Group) (Group, error)

	// ViewGroup retrieves data about the group identified by ID.
	ViewGroup(ctx context.Context, token, id string) (Group, error)

	// ListGroups retrieves groups.
	ListGroups(ctx context.Context, token string, pm PageMetadata) (GroupPage, error)

	// ListChildren retrieves groups that are children to group identified by parentID
	ListChildren(ctx context.Context, token, parentID string, pm PageMetadata) (GroupPage, error)

	// ListParents retrieves groups that are parent to group identified by childID.
	ListParents(ctx context.Context, token, childID string, pm PageMetadata) (GroupPage, error)

	// ListMembers retrieves everything that is assigned to a group identified by groupID.
	ListMembers(ctx context.Context, token, groupID, groupType string, pm PageMetadata) (MemberPage, error)

	// ListMemberships retrieves all groups for member that is identified with memberID belongs to.
	ListMemberships(ctx context.Context, token, memberID string, pm PageMetadata) (GroupPage, error)

	// RemoveGroup removes the group identified with the provided ID.
	RemoveGroup(ctx context.Context, token, id string) error

	// Assign adds a member with memberID into the group identified by groupID.
	Assign(ctx context.Context, token, groupID, groupType string, memberIDs ...string) error

	// Unassign removes member with memberID from group identified by groupID.
	Unassign(ctx context.Context, token, groupID string, memberIDs ...string) error

	// AssignGroupAccessRights adds access rights on thing groups to user group.
	AssignGroupAccessRights(ctx context.Context, token, thingGroupID, userGroupID string) error
}

GroupService specifies an API that must be fullfiled by the domain service implementation, and all of its decorators (e.g. logging & metrics).

type Identity

type Identity struct {
	ID    string
	Email string
}

Identity contains ID and Email.

type Key

type Key struct {
	ID        string
	Type      uint32
	IssuerID  string
	Subject   string
	IssuedAt  time.Time
	ExpiresAt time.Time
}

Key represents API key.

func (Key) Expired

func (k Key) Expired() bool

Expired verifies if the key is expired.

type KeyRepository

type KeyRepository interface {
	// Save persists the Key. A non-nil error is returned to indicate
	// operation failure
	Save(context.Context, Key) (string, error)

	// Retrieve retrieves Key by its unique identifier.
	Retrieve(context.Context, string, string) (Key, error)

	// Remove removes Key with provided ID.
	Remove(context.Context, string, string) error
}

KeyRepository specifies Key persistence API.

type Member

type Member struct {
	ID   string
	Type string
}

Member represents the member information.

type MemberPage

type MemberPage struct {
	PageMetadata
	Members []Member
}

MemberPage contains page related metadata as well as list of members that belong to this page.

type PageMetadata

type PageMetadata struct {
	Total    uint64
	Offset   uint64
	Limit    uint64
	Size     uint64
	Level    uint64
	Name     string
	Type     string
	Metadata GroupMetadata
}

PageMetadata contains page metadata that helps navigation.

type PolicyAgent

type PolicyAgent interface {
	// CheckPolicy checks if the subject has a relation on the object.
	// It returns a non-nil error if the subject has no relation on
	// the object (which simply means the operation is denied).
	CheckPolicy(ctx context.Context, pr PolicyReq) error

	// AddPolicy creates a policy for the given subject, so that, after
	// AddPolicy, `subject` has a `relation` on `object`. Returns a non-nil
	// error in case of failures.
	AddPolicy(ctx context.Context, pr PolicyReq) error

	// DeletePolicy removes a policy.
	DeletePolicy(ctx context.Context, pr PolicyReq) error

	RetrievePolicies(ctx context.Context, pr PolicyReq) ([]*acl.RelationTuple, error)
}

PolicyAgent facilitates the communication to authorization services and implements Authz functionalities for certain authorization services (e.g. ORY Keto).

type PolicyPage

type PolicyPage struct {
	Policies []string
}

type PolicyReq

type PolicyReq struct {
	Subject  string
	Object   string
	Relation string
}

PolicyReq represents an argument struct for making a policy related function calls.

type Service

type Service interface {
	Authn
	Authz

	// GroupService implements groups API, creating groups, assigning members
	GroupService
}

Service specifies an API that must be fulfilled by the domain service implementation, and all of its decorators (e.g. logging & metrics). Token is a string value of the actual Key and is used to authenticate an Auth service request.

func New

func New(keys KeyRepository, groups GroupRepository, idp mainflux.IDProvider, tokenizer Tokenizer, policyAgent PolicyAgent, duration time.Duration) Service

New instantiates the auth service implementation.

type Tokenizer

type Tokenizer interface {
	// Issue converts API Key to its string representation.
	Issue(Key) (string, error)

	// Parse extracts API Key data from string token.
	Parse(string) (Key, error)
}

Tokenizer specifies API for encoding and decoding between string and Key.

Directories

Path Synopsis
api
Package api contains implementation of Auth service HTTP API.
Package api contains implementation of Auth service HTTP API.
grpc
Package grpc contains implementation of Auth service gRPC API.
Package grpc contains implementation of Auth service gRPC API.
Package keto contains PolicyAgent implementation using Keto.
Package keto contains PolicyAgent implementation using Keto.
Package postgres contains Key repository implementations using PostgreSQL as the underlying database.
Package postgres contains Key repository implementations using PostgreSQL as the underlying database.
Package tracing contains middlewares that will add spans to existing traces.
Package tracing contains middlewares that will add spans to existing traces.

Jump to

Keyboard shortcuts

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