policies: add unittests for evaluator
This commit is contained in:
parent
b99d23c119
commit
2b5fddb7bf
|
@ -19,7 +19,7 @@ LOGGER = get_logger()
|
||||||
|
|
||||||
|
|
||||||
class Evaluator:
|
class Evaluator:
|
||||||
"""Validate and evaulate jinja2-based expressions"""
|
"""Validate and evaluate jinja2-based expressions"""
|
||||||
|
|
||||||
_env: NativeEnvironment
|
_env: NativeEnvironment
|
||||||
|
|
||||||
|
@ -51,11 +51,12 @@ class Evaluator:
|
||||||
"""Return dictionary with additional global variables passed to expression"""
|
"""Return dictionary with additional global variables passed to expression"""
|
||||||
# update passbook/policies/expression/templates/policy/expression/form.html
|
# update passbook/policies/expression/templates/policy/expression/form.html
|
||||||
# update docs/policies/expression/index.md
|
# update docs/policies/expression/index.md
|
||||||
|
kwargs["pb_is_group_member"] = Evaluator.jinja2_func_is_group_member
|
||||||
|
kwargs["pb_logger"] = get_logger()
|
||||||
|
if request.http_request:
|
||||||
kwargs["pb_is_sso_flow"] = request.http_request.session.get(
|
kwargs["pb_is_sso_flow"] = request.http_request.session.get(
|
||||||
AuthenticationView.SESSION_IS_SSO_LOGIN, False
|
AuthenticationView.SESSION_IS_SSO_LOGIN, False
|
||||||
)
|
)
|
||||||
kwargs["pb_is_group_member"] = Evaluator.jinja2_func_is_group_member
|
|
||||||
kwargs["pb_logger"] = get_logger()
|
|
||||||
kwargs["pb_client_ip"] = (
|
kwargs["pb_client_ip"] = (
|
||||||
get_client_ip(request.http_request) or "255.255.255.255"
|
get_client_ip(request.http_request) or "255.255.255.255"
|
||||||
)
|
)
|
||||||
|
@ -81,7 +82,7 @@ class Evaluator:
|
||||||
req=request,
|
req=request,
|
||||||
)
|
)
|
||||||
return PolicyResult(False)
|
return PolicyResult(False)
|
||||||
if isinstance(result, list) and len(result) == 2:
|
if isinstance(result, (list, tuple)) and len(result) == 2:
|
||||||
return PolicyResult(*result)
|
return PolicyResult(*result)
|
||||||
if result:
|
if result:
|
||||||
return PolicyResult(result)
|
return PolicyResult(result)
|
||||||
|
|
|
@ -0,0 +1,58 @@
|
||||||
|
"""evaluator tests"""
|
||||||
|
from django.core.exceptions import ValidationError
|
||||||
|
from django.test import TestCase
|
||||||
|
from guardian.shortcuts import get_anonymous_user
|
||||||
|
|
||||||
|
from passbook.policies.expression.evaluator import Evaluator
|
||||||
|
from passbook.policies.types import PolicyRequest
|
||||||
|
|
||||||
|
|
||||||
|
class TestEvaluator(TestCase):
|
||||||
|
"""Evaluator tests"""
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
self.request = PolicyRequest(user=get_anonymous_user())
|
||||||
|
|
||||||
|
def test_valid(self):
|
||||||
|
"""test simple value expression"""
|
||||||
|
template = "True"
|
||||||
|
evaluator = Evaluator()
|
||||||
|
self.assertEqual(evaluator.evaluate(template, self.request).passing, True)
|
||||||
|
|
||||||
|
def test_messages(self):
|
||||||
|
"""test expression with message return"""
|
||||||
|
template = "False, 'some message'"
|
||||||
|
evaluator = Evaluator()
|
||||||
|
result = evaluator.evaluate(template, self.request)
|
||||||
|
self.assertEqual(result.passing, False)
|
||||||
|
self.assertEqual(result.messages, ("some message",))
|
||||||
|
|
||||||
|
def test_invalid_syntax(self):
|
||||||
|
"""test invalid syntax"""
|
||||||
|
template = "{%"
|
||||||
|
evaluator = Evaluator()
|
||||||
|
result = evaluator.evaluate(template, self.request)
|
||||||
|
self.assertEqual(result.passing, False)
|
||||||
|
self.assertEqual(result.messages, ("tag name expected",))
|
||||||
|
|
||||||
|
def test_undefined(self):
|
||||||
|
"""test undefined result"""
|
||||||
|
template = "{{ foo.bar }}"
|
||||||
|
evaluator = Evaluator()
|
||||||
|
result = evaluator.evaluate(template, self.request)
|
||||||
|
self.assertEqual(result.passing, False)
|
||||||
|
self.assertEqual(result.messages, ("'foo' is undefined",))
|
||||||
|
|
||||||
|
def test_validate(self):
|
||||||
|
"""test validate"""
|
||||||
|
template = "True"
|
||||||
|
evaluator = Evaluator()
|
||||||
|
result = evaluator.validate(template)
|
||||||
|
self.assertEqual(result, True)
|
||||||
|
|
||||||
|
def test_validate_invalid(self):
|
||||||
|
"""test validate"""
|
||||||
|
template = "{%"
|
||||||
|
evaluator = Evaluator()
|
||||||
|
with self.assertRaises(ValidationError):
|
||||||
|
evaluator.validate(template)
|
|
@ -1,7 +1,7 @@
|
||||||
"""policy structures"""
|
"""policy structures"""
|
||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
from typing import TYPE_CHECKING, Tuple
|
from typing import TYPE_CHECKING, Optional, Tuple
|
||||||
|
|
||||||
from django.db.models import Model
|
from django.db.models import Model
|
||||||
from django.http import HttpRequest
|
from django.http import HttpRequest
|
||||||
|
@ -14,11 +14,13 @@ class PolicyRequest:
|
||||||
"""Data-class to hold policy request data"""
|
"""Data-class to hold policy request data"""
|
||||||
|
|
||||||
user: User
|
user: User
|
||||||
http_request: HttpRequest
|
http_request: Optional[HttpRequest]
|
||||||
obj: Model
|
obj: Optional[Model]
|
||||||
|
|
||||||
def __init__(self, user: User):
|
def __init__(self, user: User):
|
||||||
self.user = user
|
self.user = user
|
||||||
|
self.http_request = None
|
||||||
|
self.obj = None
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
return f"<PolicyRequest user={self.user}>"
|
return f"<PolicyRequest user={self.user}>"
|
||||||
|
|
Reference in New Issue