mirror of
https://github.com/hanzoai/firebase-js-sdk.git
synced 2026-09-24 16:59:10 +00:00
212 lines
6.3 KiB
TypeScript
212 lines
6.3 KiB
TypeScript
/**
|
|
* @license
|
|
* Copyright 2017 Google LLC
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
// Helpers here mock Firestore in order to unit-test API types. Do NOT use
|
|
// these in any integration test, where we expect working Firestore object.
|
|
|
|
import {
|
|
DocumentReference,
|
|
ensureFirestoreConfigured,
|
|
Firestore,
|
|
Query,
|
|
CollectionReference,
|
|
QuerySnapshot,
|
|
DocumentSnapshot,
|
|
SnapshotMetadata
|
|
} from '../../src';
|
|
import {
|
|
EmptyAppCheckTokenProvider,
|
|
EmptyAuthCredentialsProvider
|
|
} from '../../src/api/credentials';
|
|
import { ExpUserDataWriter } from '../../src/api/user_data_writer';
|
|
import { DatabaseId } from '../../src/core/database_info';
|
|
import {
|
|
newQueryForPath,
|
|
newQueryComparator,
|
|
Query as InternalQuery
|
|
} from '../../src/core/query';
|
|
import {
|
|
ChangeType,
|
|
DocumentViewChange,
|
|
ViewSnapshot
|
|
} from '../../src/core/view_snapshot';
|
|
import { documentKeySet, DocumentKeySet } from '../../src/model/collections';
|
|
import { DocumentSet } from '../../src/model/document_set';
|
|
import { JsonObject } from '../../src/model/object_value';
|
|
import { TEST_PROJECT } from '../unit/local/persistence_test_helpers';
|
|
|
|
import { doc, key, path as pathFrom } from './helpers';
|
|
|
|
/**
|
|
* A mock Firestore. Will not work for integration test.
|
|
*/
|
|
export const FIRESTORE = newTestFirestore(TEST_PROJECT);
|
|
|
|
export function firestore(): Firestore {
|
|
return FIRESTORE;
|
|
}
|
|
|
|
export function newTestFirestore(
|
|
projectId = 'new-project',
|
|
databaseId: string | undefined = undefined
|
|
): Firestore {
|
|
return new Firestore(
|
|
new EmptyAuthCredentialsProvider(),
|
|
new EmptyAppCheckTokenProvider(),
|
|
new DatabaseId(databaseId ?? projectId)
|
|
);
|
|
}
|
|
|
|
export function collectionReference(path: string): CollectionReference {
|
|
const db = firestore();
|
|
ensureFirestoreConfigured(db);
|
|
return new CollectionReference(db, /* converter= */ null, pathFrom(path));
|
|
}
|
|
|
|
export function documentReference(path: string): DocumentReference {
|
|
const db = firestore();
|
|
ensureFirestoreConfigured(db);
|
|
return new DocumentReference(db, /* converter= */ null, key(path));
|
|
}
|
|
|
|
export function documentSnapshot(
|
|
path: string,
|
|
data: JsonObject<unknown> | null,
|
|
fromCache: boolean,
|
|
hasPendingWrites?: boolean
|
|
): DocumentSnapshot {
|
|
hasPendingWrites = !!hasPendingWrites;
|
|
const db = firestore();
|
|
const userDataWriter = new ExpUserDataWriter(db);
|
|
if (data) {
|
|
return new DocumentSnapshot(
|
|
db,
|
|
userDataWriter,
|
|
key(path),
|
|
doc(path, 1, data),
|
|
new SnapshotMetadata(hasPendingWrites, fromCache),
|
|
/* converter= */ null
|
|
);
|
|
} else {
|
|
return new DocumentSnapshot(
|
|
db,
|
|
userDataWriter,
|
|
key(path),
|
|
null,
|
|
new SnapshotMetadata(hasPendingWrites, fromCache),
|
|
/* converter= */ null
|
|
);
|
|
}
|
|
}
|
|
|
|
export function query(path: string): Query {
|
|
const db = firestore();
|
|
return new Query(db, /* converter= */ null, newQueryForPath(pathFrom(path)));
|
|
}
|
|
|
|
/**
|
|
* A convenience method for creating a particular query snapshot for tests.
|
|
*
|
|
* @param path - To be used in constructing the query.
|
|
* @param oldDocs - Provides the prior set of documents in the QuerySnapshot.
|
|
* Each entry maps to a document, with the key being the document id, and the
|
|
* value being the document contents.
|
|
* @param docsToAdd - Specifies data to be added into the query snapshot as of
|
|
* now. Each entry maps to a document, with the key being the document id, and
|
|
* the value being the document contents.
|
|
* @param mutatedKeys - The list of document with pending writes.
|
|
* @param fromCache - Whether the query snapshot is cache result.
|
|
* @param syncStateChanged - Whether the sync state has changed.
|
|
* @returns A query snapshot that consists of both sets of documents.
|
|
*/
|
|
export function querySnapshot(
|
|
path: string,
|
|
oldDocs: { [key: string]: JsonObject<unknown> },
|
|
docsToAdd: { [key: string]: JsonObject<unknown> },
|
|
mutatedKeys: DocumentKeySet,
|
|
fromCache: boolean,
|
|
syncStateChanged: boolean,
|
|
hasCachedResults?: boolean
|
|
): QuerySnapshot {
|
|
const query: InternalQuery = newQueryForPath(pathFrom(path));
|
|
let oldDocuments: DocumentSet = new DocumentSet();
|
|
Object.keys(oldDocs).forEach(key => {
|
|
oldDocuments = oldDocuments.add(doc(path + '/' + key, 1, oldDocs[key]));
|
|
});
|
|
let newDocuments: DocumentSet = new DocumentSet();
|
|
const documentChanges: DocumentViewChange[] = [];
|
|
Object.keys(docsToAdd).forEach(key => {
|
|
const docToAdd = doc(path + '/' + key, 1, docsToAdd[key]);
|
|
newDocuments = newDocuments.add(docToAdd);
|
|
documentChanges.push({ type: ChangeType.Added, doc: docToAdd });
|
|
});
|
|
const viewSnapshot: ViewSnapshot = new ViewSnapshot(
|
|
query,
|
|
newDocuments,
|
|
oldDocuments,
|
|
documentChanges,
|
|
mutatedKeys,
|
|
fromCache,
|
|
syncStateChanged,
|
|
false,
|
|
hasCachedResults ?? false
|
|
);
|
|
const db = firestore();
|
|
return new QuerySnapshot(
|
|
db,
|
|
new ExpUserDataWriter(db),
|
|
new Query(db, /* converter= */ null, query),
|
|
viewSnapshot
|
|
);
|
|
}
|
|
|
|
export function querySnapshotWithQuery(
|
|
query: InternalQuery,
|
|
docsToAdd: { [key: string]: JsonObject<unknown> }
|
|
): QuerySnapshot {
|
|
const comparator = newQueryComparator(query);
|
|
let newDocuments: DocumentSet = new DocumentSet(comparator);
|
|
const documentChanges: DocumentViewChange[] = [];
|
|
Object.keys(docsToAdd).forEach(key => {
|
|
const docToAdd = doc(
|
|
query.path.canonicalString() + '/' + key,
|
|
1,
|
|
docsToAdd[key]
|
|
);
|
|
newDocuments = newDocuments.add(docToAdd);
|
|
documentChanges.push({ type: ChangeType.Added, doc: docToAdd });
|
|
});
|
|
const viewSnapshot: ViewSnapshot = new ViewSnapshot(
|
|
query,
|
|
newDocuments,
|
|
new DocumentSet(comparator),
|
|
documentChanges,
|
|
documentKeySet(),
|
|
false,
|
|
true,
|
|
false,
|
|
false
|
|
);
|
|
const db = firestore();
|
|
return new QuerySnapshot(
|
|
db,
|
|
new ExpUserDataWriter(db),
|
|
new Query(db, /* converter= */ null, query),
|
|
viewSnapshot
|
|
);
|
|
}
|