Start adding unittests for prototypes

This commit is contained in:
Griatch 2018-06-09 23:57:46 +02:00
parent 7f250cdec4
commit e533ceacfe
3 changed files with 48 additions and 4 deletions

View file

@ -416,3 +416,45 @@ def list_prototypes(caller, key=None, tags=None, show_non_use=False, show_non_ed
table.reformat_column(2, width=11, align='c')
table.reformat_column(3, width=16)
return table
def validate_prototype(prototype, protkey=None, protparents=None, _visited=None):
"""
Run validation on a prototype, checking for inifinite regress.
Args:
prototype (dict): Prototype to validate.
protkey (str, optional): The name of the prototype definition. If not given, the prototype
dict needs to have the `prototype_key` field set.
protpartents (dict, optional): The available prototype parent library. If
note given this will be determined from settings/database.
_visited (list, optional): This is an internal work array and should not be set manually.
Raises:
RuntimeError: If prototype has invalid structure.
"""
if not protparents:
protparents = {prototype['prototype_key']: prototype for prototype in search_prototype()}
if _visited is None:
_visited = []
protkey = protkey and protkey.lower() or prototype.get('prototype_key', None)
assert isinstance(prototype, dict)
if id(prototype) in _visited:
raise RuntimeError("%s has infinite nesting of prototypes." % protkey or prototype)
_visited.append(id(prototype))
protstrings = prototype.get("prototype")
if protstrings:
for protstring in make_iter(protstrings):
protstring = protstring.lower()
if protkey is not None and protstring == protkey:
raise RuntimeError("%s tries to prototype itself." % protkey or prototype)
protparent = protparents.get(protstring)
if not protparent:
raise RuntimeError(
"%s's prototype '%s' was not found." % (protkey or prototype, protstring))
validate_prototype(protparent, protstring, protparents, _visited)

View file

@ -426,10 +426,12 @@ def spawn(*prototypes, **kwargs):
"""
# get available protparents
protparents = {prot['prototype_key']: prot for prot in protlib.search_prototype()}
protparents = {prot['prototype_key'].lower(): prot for prot in protlib.search_prototype()}
# overload module's protparents with specifically given protparents
protparents.update(kwargs.get("prototype_parents", {}))
protparents.update(
{key.lower(): value for key, value in kwargs.get("prototype_parents", {}).items()})
for key, prototype in protparents.items():
protlib.validate_prototype(prototype, key.lower(), protparents)

View file

@ -50,10 +50,10 @@ class TestSpawner(EvenniaTest):
def test_spawn(self):
obj1 = spawner.spawn(self.prot1)
# check spawned objects have the right tag
self.assertEqual(list(spawner.search_objects_with_prototype("testprototype")), obj1)
self.assertEqual(list(protlib.search_objects_with_prototype("testprototype")), obj1)
self.assertEqual([o.key for o in spawner.spawn(
_PROTPARENTS["GOBLIN"], _PROTPARENTS["GOBLIN_ARCHWIZARD"],
prototype_parents=_PROTPARENTS)], [])
prototype_parents=_PROTPARENTS)], ['goblin grunt', 'goblin archwizard'])
class TestPrototypeStorage(EvenniaTest):