def _make_client_document(firestore_api, testcase): from google.cloud.firestore_v1beta1 import Client from google.cloud.firestore_v1beta1.client import DEFAULT_DATABASE import google.auth.credentials _, project, _, database, _, doc_path = testcase.doc_ref_path.split('/', 5) assert database == DEFAULT_DATABASE # Attach the fake GAPIC to a real client. credentials = mock.Mock(spec=google.auth.credentials.Credentials) client = Client(project=project, credentials=credentials) client._firestore_api_internal = firestore_api return client, client.document(doc_path)
def setup(self, firestore_api, proto): from google.cloud.firestore_v1beta1 import Client from google.cloud.firestore_v1beta1.client import DEFAULT_DATABASE import google.auth.credentials _, project, _, database, _, doc_path = proto.doc_ref_path.split('/', 5) self.assertEqual(database, DEFAULT_DATABASE) # Attach the fake GAPIC to a real client. credentials = mock.Mock(spec=google.auth.credentials.Credentials) client = Client(project=project, credentials=credentials) client._firestore_api_internal = firestore_api return client, client.document(doc_path)
def parse_query(testcase): # 'query' testcase contains: # - 'coll_path': collection ref path. # - 'clauses': array of one or more 'Clause' elements # - 'query': the actual google.firestore.v1beta1.StructuredQuery message # to be constructed. # - 'is_error' (as other testcases). # # 'Clause' elements are unions of: # - 'select': [field paths] # - 'where': (field_path, op, json_value) # - 'order_by': (field_path, direction) # - 'offset': int # - 'limit': int # - 'start_at': 'Cursor' # - 'start_after': 'Cursor' # - 'end_at': 'Cursor' # - 'end_before': 'Cursor' # # 'Cursor' contains either: # - 'doc_snapshot': 'DocSnapshot' # - 'json_values': [string] # # 'DocSnapshot' contains: # 'path': str # 'json_data': str from google.auth.credentials import Credentials from google.cloud.firestore_v1beta1 import Client from google.cloud.firestore_v1beta1 import Query _directions = {"asc": Query.ASCENDING, "desc": Query.DESCENDING} credentials = mock.create_autospec(Credentials) client = Client("projectID", credentials) path = parse_path(testcase.coll_path) collection = client.collection(*path) query = collection for clause in testcase.clauses: kind = clause.WhichOneof("clause") if kind == "select": field_paths = [ ".".join(field_path.field) for field_path in clause.select.fields ] query = query.select(field_paths) elif kind == "where": path = ".".join(clause.where.path.field) value = convert_data(json.loads(clause.where.json_value)) query = query.where(path, clause.where.op, value) elif kind == "order_by": path = ".".join(clause.order_by.path.field) direction = clause.order_by.direction direction = _directions.get(direction, direction) query = query.order_by(path, direction=direction) elif kind == "offset": query = query.offset(clause.offset) elif kind == "limit": query = query.limit(clause.limit) elif kind == "start_at": cursor = parse_cursor(clause.start_at, client) query = query.start_at(cursor) elif kind == "start_after": cursor = parse_cursor(clause.start_after, client) query = query.start_after(cursor) elif kind == "end_at": cursor = parse_cursor(clause.end_at, client) query = query.end_at(cursor) elif kind == "end_before": cursor = parse_cursor(clause.end_before, client) query = query.end_before(cursor) else: # pragma: NO COVER raise ValueError("Unknown query clause: {}".format(kind)) return query
def test_listen_testprotos(test_proto): # pragma: NO COVER # test_proto.listen has 'reponses' messages, # 'google.firestore.v1beta1.ListenResponse' # and then an expected list of 'snapshots' (local 'Snapshot'), containing # 'docs' (list of 'google.firestore.v1beta1.Document'), # 'changes' (list lof local 'DocChange', and 'read_time' timestamp. from google.cloud.firestore_v1beta1 import Client from google.cloud.firestore_v1beta1 import DocumentReference from google.cloud.firestore_v1beta1 import DocumentSnapshot from google.cloud.firestore_v1beta1 import Watch import google.auth.credentials testcase = test_proto.listen testname = test_proto.description credentials = mock.Mock(spec=google.auth.credentials.Credentials) client = Client(project="project", credentials=credentials) modulename = "google.cloud.firestore_v1beta1.watch" with mock.patch("%s.Watch.ResumableBidiRpc" % modulename, DummyRpc): with mock.patch("%s.Watch.BackgroundConsumer" % modulename, DummyBackgroundConsumer): with mock.patch( # conformance data sets WATCH_TARGET_ID to 1 "%s.WATCH_TARGET_ID" % modulename, 1): snapshots = [] def callback(keys, applied_changes, read_time): snapshots.append((keys, applied_changes, read_time)) query = DummyQuery(client=client) watch = Watch.for_query(query, callback, DocumentSnapshot, DocumentReference) # conformance data has db string as this db_str = "projects/projectID/databases/(default)" watch._firestore._database_string_internal = db_str if testcase.is_error: try: for proto in testcase.responses: watch.on_snapshot(proto) except RuntimeError: # listen-target-add-wrong-id.textpro # listen-target-remove.textpro pass else: for proto in testcase.responses: watch.on_snapshot(proto) assert len(snapshots) == len(testcase.snapshots) for i, (expected_snapshot, actual_snapshot) in enumerate( zip(testcase.snapshots, snapshots)): expected_changes = expected_snapshot.changes actual_changes = actual_snapshot[1] if len(expected_changes) != len(actual_changes): raise AssertionError( "change length mismatch in %s (snapshot #%s)" % (testname, i)) for y, (expected_change, actual_change) in enumerate( zip(expected_changes, actual_changes)): expected_change_kind = expected_change.kind actual_change_kind = actual_change.type.value if expected_change_kind != actual_change_kind: raise AssertionError( "change type mismatch in %s (snapshot #%s, change #%s')" % (testname, i, y))