runtime map hash error
This commit is contained in:
parent
1d953a8270
commit
c5baa7c2b3
4 changed files with 39 additions and 5 deletions
|
|
@ -11,7 +11,7 @@ from ytdl_sub.script.types.resolvable import Resolvable
|
||||||
from ytdl_sub.script.types.resolvable import ResolvableToJson
|
from ytdl_sub.script.types.resolvable import ResolvableToJson
|
||||||
from ytdl_sub.script.types.variable import Variable
|
from ytdl_sub.script.types.variable import Variable
|
||||||
from ytdl_sub.script.types.variable_dependency import VariableDependency
|
from ytdl_sub.script.types.variable_dependency import VariableDependency
|
||||||
from ytdl_sub.utils.exceptions import StringFormattingException
|
from ytdl_sub.script.utils.exceptions import KeyNotHashableRuntimeException
|
||||||
|
|
||||||
|
|
||||||
@dataclass(frozen=True)
|
@dataclass(frozen=True)
|
||||||
|
|
@ -42,7 +42,9 @@ class UnresolvedMap(Map, VariableDependency, AnyArgument):
|
||||||
arg=key, resolved_variables=resolved_variables, custom_functions=custom_functions
|
arg=key, resolved_variables=resolved_variables, custom_functions=custom_functions
|
||||||
)
|
)
|
||||||
if not isinstance(resolved_key, Hashable):
|
if not isinstance(resolved_key, Hashable):
|
||||||
raise StringFormattingException("key is not hashable")
|
raise KeyNotHashableRuntimeException(
|
||||||
|
f"Tried to use {resolved_key.type_name()} as a Map key, but it is not hashable."
|
||||||
|
)
|
||||||
|
|
||||||
output[resolved_key] = self._resolve_argument_type(
|
output[resolved_key] = self._resolve_argument_type(
|
||||||
arg=value, resolved_variables=resolved_variables, custom_functions=custom_functions
|
arg=value, resolved_variables=resolved_variables, custom_functions=custom_functions
|
||||||
|
|
|
||||||
|
|
@ -12,7 +12,6 @@ from ytdl_sub.script.types.resolvable import Resolvable
|
||||||
from ytdl_sub.script.types.variable import FunctionArgument
|
from ytdl_sub.script.types.variable import FunctionArgument
|
||||||
from ytdl_sub.script.types.variable import Variable
|
from ytdl_sub.script.types.variable import Variable
|
||||||
from ytdl_sub.script.utils.exceptions import UNREACHABLE
|
from ytdl_sub.script.utils.exceptions import UNREACHABLE
|
||||||
from ytdl_sub.utils.exceptions import StringFormattingException
|
|
||||||
|
|
||||||
|
|
||||||
@dataclass(frozen=True)
|
@dataclass(frozen=True)
|
||||||
|
|
@ -78,7 +77,8 @@ class VariableDependency(ABC):
|
||||||
return arg
|
return arg
|
||||||
if isinstance(arg, Variable):
|
if isinstance(arg, Variable):
|
||||||
if arg not in resolved_variables:
|
if arg not in resolved_variables:
|
||||||
raise StringFormattingException("should never reach@")
|
# All variables should exist and be resolved at this point
|
||||||
|
raise UNREACHABLE
|
||||||
return resolved_variables[arg]
|
return resolved_variables[arg]
|
||||||
if isinstance(arg, VariableDependency):
|
if isinstance(arg, VariableDependency):
|
||||||
return arg.resolve(
|
return arg.resolve(
|
||||||
|
|
|
||||||
|
|
@ -43,10 +43,18 @@ class CycleDetected(UserException):
|
||||||
"""A cycle exists within a user's script"""
|
"""A cycle exists within a user's script"""
|
||||||
|
|
||||||
|
|
||||||
class FunctionRuntimeException(ValueError):
|
class RuntimeException(ValueError, ABC):
|
||||||
|
"""Exception thrown at runtime during resolution"""
|
||||||
|
|
||||||
|
|
||||||
|
class FunctionRuntimeException(RuntimeException):
|
||||||
"""Exception thrown when a ytdl-sub function has an error occur at runtime"""
|
"""Exception thrown when a ytdl-sub function has an error occur at runtime"""
|
||||||
|
|
||||||
|
|
||||||
|
class KeyNotHashableRuntimeException(RuntimeException):
|
||||||
|
"""Map tried to use a non-hashable key at runtime"""
|
||||||
|
|
||||||
|
|
||||||
class UserThrownRuntimeError(ValidationException):
|
class UserThrownRuntimeError(ValidationException):
|
||||||
"""An error explicitly thrown by the user via a function"""
|
"""An error explicitly thrown by the user via a function"""
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -15,6 +15,7 @@ from ytdl_sub.script.types.resolvable import Boolean
|
||||||
from ytdl_sub.script.types.resolvable import Float
|
from ytdl_sub.script.types.resolvable import Float
|
||||||
from ytdl_sub.script.types.resolvable import String
|
from ytdl_sub.script.types.resolvable import String
|
||||||
from ytdl_sub.script.utils.exceptions import InvalidSyntaxException
|
from ytdl_sub.script.utils.exceptions import InvalidSyntaxException
|
||||||
|
from ytdl_sub.script.utils.exceptions import KeyNotHashableRuntimeException
|
||||||
|
|
||||||
|
|
||||||
class TestMap:
|
class TestMap:
|
||||||
|
|
@ -159,3 +160,26 @@ class TestMap:
|
||||||
def test_map_key_not_hashable(self, value: str):
|
def test_map_key_not_hashable(self, value: str):
|
||||||
with pytest.raises(InvalidSyntaxException, match=re.escape(str(MAP_KEY_NOT_HASHABLE))):
|
with pytest.raises(InvalidSyntaxException, match=re.escape(str(MAP_KEY_NOT_HASHABLE))):
|
||||||
Script({"map": value}).resolve()
|
Script({"map": value}).resolve()
|
||||||
|
|
||||||
|
def test_map_key_is_hashable_variable(self):
|
||||||
|
assert Script(
|
||||||
|
{
|
||||||
|
"map": "{{key_variable : 'value' }}",
|
||||||
|
"key_variable": "hashable",
|
||||||
|
}
|
||||||
|
).resolve() == {
|
||||||
|
"key_variable": String("hashable"),
|
||||||
|
"map": ResolvedMap({String("hashable"): String("value")}),
|
||||||
|
}
|
||||||
|
|
||||||
|
def test_map_key_is_non_hashable_variable(self):
|
||||||
|
with pytest.raises(
|
||||||
|
KeyNotHashableRuntimeException,
|
||||||
|
match=re.escape("Tried to use Array as a Map key, but it is not hashable."),
|
||||||
|
):
|
||||||
|
Script(
|
||||||
|
{
|
||||||
|
"map": "{{key_variable : 'value' }}",
|
||||||
|
"key_variable": "{['non-hashable']}",
|
||||||
|
}
|
||||||
|
).resolve()
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue