CORD-2977 Fix failure to resolve generic foreign keys;
Fix exception reporting in xossh
Change-Id: Ie57bba891c6d0176e7174f6e1964bb2ff5e7dfbc
diff --git a/xos/xos_client/xosapi/fake_stub.py b/xos/xos_client/xosapi/fake_stub.py
index 8cd9c53..0970b39 100644
--- a/xos/xos_client/xosapi/fake_stub.py
+++ b/xos/xos_client/xosapi/fake_stub.py
@@ -275,6 +275,27 @@
def __init__(self, items):
self.items = items
+class FakeElement(object):
+ EQUAL="equal"
+
+ def __init__(self):
+ pass
+
+class FakeElements(object):
+ def __init__(self):
+ self.items = []
+
+ def add(self):
+ el=FakeElement()
+ self.items.append(el)
+ return el
+
+class FakeQuery(object):
+ DEFAULT="default"
+
+ def __init__(self):
+ self.elements = FakeElements()
+
class FakeStub(object):
def __init__(self):
self.id_counter = 1
@@ -285,6 +306,7 @@
setattr(self, "Create%s" % name, functools.partial(self.create, name))
setattr(self, "Delete%s" % name, functools.partial(self.delete, name))
setattr(self, "Update%s" % name, functools.partial(self.update, name))
+ setattr(self, "Filter%s" % name, functools.partial(self.filter, name))
def make_key(self, name, id):
@@ -302,6 +324,22 @@
items.append(v)
return FakeItemList(items)
+ def filter(self, classname, query, metadata=None):
+ items = []
+ for (k,v) in self.objs.items():
+ (this_classname, id) = k.split(":")
+ if this_classname != classname:
+ continue
+ for q in query.elements.items:
+ iValue = getattr(q, "iValue", None)
+ if (iValue is not None) and getattr(v,q.name)!=iValue:
+ continue
+ sValue = getattr(q, "sValue", None)
+ if (sValue is not None) and getattr(v, q.name) != sValue:
+ continue
+ items.append(v)
+ return FakeItemList(items)
+
def create(self, classname, obj, metadata=None):
obj.id = self.id_counter
self.id_counter = self.id_counter + 1
@@ -329,6 +367,7 @@
class FakeCommonProtos(object):
def __init__(self):
self.ID = ID
+ self.Query = FakeQuery
class FakeProtos(object):
def __init__(self):
diff --git a/xos/xos_client/xosapi/orm.py b/xos/xos_client/xosapi/orm.py
index 7845d14..a50b7ee 100644
--- a/xos/xos_client/xosapi/orm.py
+++ b/xos/xos_client/xosapi/orm.py
@@ -35,13 +35,18 @@
u=c.xos_orm.User.objects.get(id=1)
"""
-import functools
import os
import sys
import time
convenience_wrappers = {}
+class ORMGenericContentNotFoundException(Exception):
+ pass
+
+class ORMGenericObjectNotFoundException(Exception):
+ pass
+
class ORMWrapper(object):
""" Wraps a protobuf object to provide ORM features """
@@ -525,8 +530,19 @@
self.reverse_content_type_map[model_name] = ct
def genericForeignKeyResolve(self, content_type_id, id):
+ if content_type_id.endswith("_decl"):
+ content_type_id = content_type_id[:-5]
+
+ if content_type_id not in self.content_type_map:
+ raise ORMGenericContentNotFoundException("Content_type %s not found in self.content_type_map" % content_type_id)
+
model_name = self.content_type_map[content_type_id]
+
model = getattr(self, model_name)
+ objs = model.objects.filter(id=id)
+ if not objs:
+ raise ORMGenericObjectNotFoundException("Object %s of model %s was not found" % (id,model_name))
+
return model.objects.get(id=id)
def add_default_metadata(self, metadata):
diff --git a/xos/xos_client/xosapi/test_orm.py b/xos/xos_client/xosapi/test_orm.py
index 136f71a..93f2155 100644
--- a/xos/xos_client/xosapi/test_orm.py
+++ b/xos/xos_client/xosapi/test_orm.py
@@ -328,6 +328,47 @@
self.assertNotEqual(tag.content_object, None)
self.assertEqual(tag.content_object.id, site.id)
+ def test_generic_foreign_key_get_decl(self):
+ orm = self.make_coreapi()
+ service = orm.Service(name="myservice")
+ service.save()
+ site = orm.Site(name="mysite")
+ site.save()
+ self.assertTrue(site.id > 0)
+ tag = orm.Tag(service=service, name="mytag", value="somevalue", content_type=site.self_content_type_id + "_decl", object_id=site.id)
+ tag.save()
+ self.assertTrue(tag.id > 0)
+ self.assertNotEqual(tag.content_object, None)
+ self.assertEqual(tag.content_object.id, site.id)
+
+ def test_generic_foreign_key_get_bad_contenttype(self):
+ orm = self.make_coreapi()
+ service = orm.Service(name="myservice")
+ service.save()
+ site = orm.Site(name="mysite")
+ site.save()
+ self.assertTrue(site.id > 0)
+ tag = orm.Tag(service=service, name="mytag", value="somevalue", content_type="does_not_exist", object_id=site.id)
+ tag.save()
+ self.assertTrue(tag.id > 0)
+ with self.assertRaises(Exception) as e:
+ obj = tag.content_object
+ self.assertEqual(e.exception.message, "Content_type does_not_exist not found in self.content_type_map")
+
+ def test_generic_foreign_key_get_bad_id(self):
+ orm = self.make_coreapi()
+ service = orm.Service(name="myservice")
+ service.save()
+ site = orm.Site(name="mysite")
+ site.save()
+ self.assertTrue(site.id > 0)
+ tag = orm.Tag(service=service, name="mytag", value="somevalue", content_type=site.self_content_type_id, object_id=4567)
+ tag.save()
+ self.assertTrue(tag.id > 0)
+ with self.assertRaises(Exception) as e:
+ obj = tag.content_object
+ self.assertEqual(e.exception.message, "Object 4567 of model Site was not found")
+
def test_generic_foreign_key_set(self):
orm = self.make_coreapi()
service = orm.Service(name="myservice")
diff --git a/xos/xos_client/xossh b/xos/xos_client/xossh
index 9eda018..02bab8a 100644
--- a/xos/xos_client/xossh
+++ b/xos/xos_client/xossh
@@ -8,7 +8,7 @@
import os, sys
import atexit
import readline
-import rlcompleter
+import traceback
from twisted.internet import reactor
from xosapi.version import __version__
@@ -245,8 +245,8 @@
# Do it
code = compile(command, "<stdin>", "single")
exec code
- except Exception, err:
- print err
+ except Exception:
+ traceback.print_exc()
# check to see if login() was used
if client.session_change: