Current section
Files
Jump to
Current section
Files
lib/policy.ex
defmodule Carny.Policy do
@moduledoc """
Policies are lists of statements that you can validate an identifier against.
"""
alias Carny.Statement
defstruct statements: []
@doc ~S"""
Adds a statement to a given policy
## Examples
iex> Carny.Policy.add_statement(%Carny.Policy{statements: [%Carny.Statement{effect: :deny}]}, %Carny.Statement{})
%Carny.Policy{statements: [%Carny.Statement{}, %Carny.Statement{effect: :deny}]}
"""
def add_statement(policy, statement) do
Map.update!(policy, :statements, fn statements ->
[statement | statements]
end)
end
@doc """
Does the id pass a specific policy? The use case here is we have
already looked up a policy for our given resource and want to make
sure that it has access to some other resource (id).
## Examples
iex> Carny.Policy.authorized?("start", %Carny.Identifier{}, %Carny.Policy{statements: [%Carny.Statement{privileges: ["start"], resources: [%Carny.Identifier{}]}]})
true
"""
def authorized?(privilege, id, policy) do
# As soon as we reach a "true" value then halt
# because we know it should have access
Enum.reduce_while(policy.statements, false, fn
statement, false ->
{:cont, Statement.passes?(privilege, id, statement)}
_statement, true ->
{:halt, true}
end)
end
end