def testQueryForWholeStructure(self): class Employee(model.Model): name = model.StringProperty() rank = model.IntegerProperty() class Manager(Employee): report = model.StructuredProperty(Employee, repeated=True) reports_a = [] for i in range(3): e = Employee(name=str(i), rank=i) e.put() reports_a.append(e) reports_b = [] for i in range(3, 6): e = Employee(name=str(i), rank=0) e.put() reports_b.append(e) mgr_a = Manager(name='a', report=reports_a) mgr_a.put() mgr_b = Manager(name='b', report=reports_b) mgr_b.put() mgr_c = Manager(name='c', report=reports_a + reports_b) mgr_c.put() res = list(Manager.query(Manager.report == Employee(name='1', rank=1))) self.assertEqual(res, [mgr_a, mgr_c]) res = list(Manager.query(Manager.report == Employee(rank=0))) self.assertEqual(res, [mgr_a, mgr_b, mgr_c]) res = list(Manager.query(Manager.report == Employee(rank=0, name='3'))) self.assertEqual(res, [mgr_b, mgr_c]) res = list(Manager.query(Manager.report == Employee(rank=0, name='1'))) self.assertEqual(res, []) res = list( Manager.query(Manager.report == Employee(rank=0, name='0'), Manager.report == Employee(rank=1, name='1'))) self.assertEqual(res, [mgr_a, mgr_c]) q = Manager.query(Manager.report == Employee(rank=2, name='2')) res = list(q) self.assertEqual(res, [mgr_a, mgr_c]) res = list(q.iter(options=query.QueryOptions(offset=1))) self.assertEqual(res, [mgr_c]) res = list(q.iter(options=query.QueryOptions(limit=1))) self.assertEqual(res, [mgr_a])
def testContext_MapQuery_Cursors(self): qo = query.QueryOptions(produce_cursors=True) @tasklets.tasklet def callback(batch, i, ent): return ent.key.pairs()[-1] @tasklets.tasklet def foo(): yield self.create_entities() qry = query.Query(kind='Foo') res = yield self.ctx.map_query(qry, callback, options=qo) raise tasklets.Return(res) res = foo().get_result() self.assertEqual(set(res), set([('Foo', 1), ('Foo', 2), ('Foo', 3)]))
def testContext_MapQuery_KeysOnly(self): qo = query.QueryOptions(keys_only=True) @tasklets.tasklet def callback(key): return key.pairs()[-1] @tasklets.tasklet def foo(): yield self.create_entities() qry = query.Query(kind='Foo') res = yield self.ctx.map_query(qry, callback, options=qo) raise tasklets.Return(res) res = foo().get_result() self.assertEqual(set(res), set([('Foo', 1), ('Foo', 2), ('Foo', 3)]))
def testCursorsKeysOnly(self): qo = query.QueryOptions(produce_cursors=True, keys_only=True) q = query.Query(kind='Foo') it = q.iter(options=qo) expected = [self.joe.key, self.jill.key, self.moe.key] self.assertRaises(datastore_errors.BadArgumentError, it.cursor_before) self.assertRaises(datastore_errors.BadArgumentError, it.cursor_after) before = [] after = [] for i, ent in enumerate(it): self.assertEqual(ent, expected[i]) before.append(it.cursor_before()) after.append(it.cursor_after()) before.append(it.cursor_before()) after.append(it.cursor_after()) self.assertEqual(before[1], after[0]) self.assertEqual(before[2], after[1]) self.assertEqual(before[3], after[2]) self.assertEqual(before[3], after[3]) # !!!
def testCursorsEfficientPaging(self): # We want to read a 'page' of data, get the cursor just past the # page, and know whether there is another page, all with a single # RPC. To do this, set limit=pagesize+1, batch_size=pagesize. q = query.Query(kind='Foo') cursors = {} mores = {} for pagesize in [1, 2, 3, 4]: qo = query.QueryOptions(produce_cursors=True, limit=pagesize + 1, batch_size=pagesize) it = q.iter(options=qo) todo = pagesize for ent in it: todo -= 1 if todo <= 0: break cursors[pagesize] = it.cursor_after() mores[pagesize] = it.probably_has_next() self.assertEqual(mores, {1: True, 2: True, 3: False, 4: False}) self.assertEqual(cursors[3], cursors[4])
def testGetKeysOnly(self): qo = query.QueryOptions(keys_only=True) q = query.Query(kind='Foo').filter(Foo.tags == 'jill').order(Foo.name) self.assertEqual(q.get(options=qo), self.jill.key)
def testFetchKeysOnly(self): qo = query.QueryOptions(keys_only=True) q = query.Query(kind='Foo').filter(Foo.tags == 'jill').order(Foo.name) self.assertEqual(q.fetch(10, options=qo), [self.jill.key, self.joe.key])