Documentation
¶
Overview ¶
Package scriptgrant decides who other than a script's owner may ask for a run of it, and binds the parameters a script takes from the caller rather than from the request (#1846).
A grant names a persona, a role or an API key. It lets that principal run the script over HTTP and read the runs it started, which carry the outputs; it never opens the source, the version history, the state or any edit. The run still executes as the script principal with its author's roles, so a grant decides who may ask, never what the run may reach.
A parameter declared with bind "caller.<claim>" takes the caller's claim, which for an API key is one of its attributes. That is what lets one script serve every tenant of an embedding application without any caller being able to name another tenant in a request body.
Index ¶
- Constants
- Variables
- func BindCaller(defs []script.Param, values, claims map[string]any) (map[string]any, error)
- type Caller
- type Grant
- type PostgresStore
- func (s *PostgresStore) Add(ctx context.Context, g Grant) error
- func (s *PostgresStore) Allows(ctx context.Context, scriptID string, c Caller) (bool, error)
- func (s *PostgresStore) GrantedScriptIDs(ctx context.Context, c Caller) ([]string, error)
- func (s *PostgresStore) List(ctx context.Context, scriptID string) ([]Grant, error)
- func (s *PostgresStore) Remove(ctx context.Context, g Grant) (bool, error)
- type Store
Constants ¶
const ( KindPersona = "persona" KindRole = "role" KindAPIKey = "api_key" )
Principal kinds a grant names.
Variables ¶
var ErrBoundInRequest = errors.New("this parameter's value is the caller's")
ErrBoundInRequest refuses a request that sends a value for a caller-bound parameter. It is refused rather than overridden, so a client that believes it chose the value learns that it did not.
var ErrClaimMissing = errors.New("the caller does not carry the claim this script is bound to")
ErrClaimMissing refuses a caller who does not carry a claim a parameter is bound to: without it there is no value the script may be run with.
Functions ¶
func BindCaller ¶
BindCaller binds a run's parameters, taking each caller-bound parameter from claims and every other one from values, through script.BindParams. The bound set is what the run records, the caller's values included.
Types ¶
type Grant ¶
type Grant struct {
ScriptID string `json:"script_id" example:"3f2b6c1e-8d4a-4b8e-9f1a-2c3d4e5f6a7b"`
Kind string `json:"principal_kind" example:"api_key"`
Principal string `json:"principal" example:"reporting-app"`
GrantedBy string `json:"granted_by" example:"jane@example.com"`
CreatedAt time.Time `json:"created_at"`
}
Grant lets one principal run one script.
type PostgresStore ¶
type PostgresStore struct {
// contains filtered or unexported fields
}
PostgresStore keeps grants in script_grants.
func (*PostgresStore) Add ¶
func (s *PostgresStore) Add(ctx context.Context, g Grant) error
Add records a grant; granting what is already granted keeps the first.
func (*PostgresStore) GrantedScriptIDs ¶
GrantedScriptIDs lists the scripts granted to anything the caller is.
type Store ¶
type Store interface {
// List returns a script's grants, oldest first.
List(ctx context.Context, scriptID string) ([]Grant, error)
// Add records a grant; granting what is already granted changes nothing.
Add(ctx context.Context, g Grant) error
// Remove withdraws a grant, reporting whether there was one.
Remove(ctx context.Context, g Grant) (bool, error)
// Allows reports whether any grant on the script names the caller.
Allows(ctx context.Context, scriptID string, c Caller) (bool, error)
// GrantedScriptIDs lists the scripts granted to anything the caller is.
GrantedScriptIDs(ctx context.Context, c Caller) ([]string, error)
}
Store keeps the grants.