17
17
18
18
import * as firestore from '@firebase/firestore-types' ;
19
19
20
+ import * as api from '../protos/firestore_proto_api' ;
21
+
20
22
import { FirebaseApp } from '@firebase/app-types' ;
21
23
import { FirebaseService , _FirebaseApp } from '@firebase/app-types/private' ;
22
24
import { DatabaseId , DatabaseInfo } from '../core/database_info' ;
@@ -38,12 +40,6 @@ import { MemoryPersistenceProvider } from '../local/memory_persistence';
38
40
import { PersistenceProvider } from '../local/persistence' ;
39
41
import { Document , MaybeDocument , NoDocument } from '../model/document' ;
40
42
import { DocumentKey } from '../model/document_key' ;
41
- import {
42
- ArrayValue ,
43
- FieldValue ,
44
- RefValue ,
45
- ServerTimestampValue
46
- } from '../model/field_value' ;
47
43
import { DeleteMutation , Mutation , Precondition } from '../model/mutation' ;
48
44
import { FieldPath , ResourcePath } from '../model/path' ;
49
45
import { PlatformSupport } from '../platform/platform' ;
@@ -101,6 +97,8 @@ import {
101
97
import { UserDataWriter } from './user_data_writer' ;
102
98
import { FirebaseAuthInternalName } from '@firebase/auth-interop-types' ;
103
99
import { Provider } from '@firebase/component' ;
100
+ import { isServerTimestamp } from '../model/server_timestamps' ;
101
+ import { JsonProtoSerializer } from '../remote/serializer' ;
104
102
105
103
// settings() defaults:
106
104
const DEFAULT_HOST = 'firestore.googleapis.com' ;
@@ -555,7 +553,12 @@ export class Firestore implements firestore.FirebaseFirestore, FirebaseService {
555
553
return value ;
556
554
}
557
555
} ;
558
- return new UserDataReader ( preConverter ) ;
556
+ return new UserDataReader (
557
+ new JsonProtoSerializer ( databaseId , {
558
+ useProto3Json : PlatformSupport . getPlatform ( ) . useProto3Json
559
+ } ) ,
560
+ preConverter
561
+ ) ;
559
562
}
560
563
561
564
private static databaseIdFromApp ( app : FirebaseApp ) : DatabaseId {
@@ -1357,14 +1360,20 @@ export interface SnapshotOptions extends firestore.SnapshotOptions {}
1357
1360
1358
1361
export class DocumentSnapshot < T = firestore . DocumentData >
1359
1362
implements firestore . DocumentSnapshot < T > {
1363
+ private readonly _serializer : JsonProtoSerializer ;
1364
+
1360
1365
constructor (
1361
1366
private _firestore : Firestore ,
1362
1367
private _key : DocumentKey ,
1363
1368
public _document : Document | null ,
1364
1369
private _fromCache : boolean ,
1365
1370
private _hasPendingWrites : boolean ,
1366
1371
private readonly _converter ?: firestore . FirestoreDataConverter < T >
1367
- ) { }
1372
+ ) {
1373
+ this . _serializer = new JsonProtoSerializer ( this . _firestore . _databaseId , {
1374
+ useProto3Json : PlatformSupport . getPlatform ( ) . useProto3Json
1375
+ } ) ;
1376
+ }
1368
1377
1369
1378
data ( options ?: firestore . SnapshotOptions ) : T | undefined {
1370
1379
validateBetweenNumberOfArgs ( 'DocumentSnapshot.data' , arguments , 0 , 1 ) ;
@@ -1386,11 +1395,13 @@ export class DocumentSnapshot<T = firestore.DocumentData>
1386
1395
} else {
1387
1396
const userDataWriter = new UserDataWriter (
1388
1397
this . _firestore ,
1398
+ this . _serializer ,
1389
1399
this . _firestore . _areTimestampsInSnapshotsEnabled ( ) ,
1390
1400
options . serverTimestamps ,
1391
1401
/* converter= */ undefined
1392
1402
) ;
1393
- return userDataWriter . convertValue ( this . _document . data ( ) ) as T ;
1403
+ const proto = this . _document . data ( ) . toProto ( ) ;
1404
+ return userDataWriter . convertValue ( proto ) as T ;
1394
1405
}
1395
1406
}
1396
1407
}
@@ -1408,6 +1419,7 @@ export class DocumentSnapshot<T = firestore.DocumentData>
1408
1419
if ( value !== null ) {
1409
1420
const userDataWriter = new UserDataWriter (
1410
1421
this . _firestore ,
1422
+ this . _serializer ,
1411
1423
this . _firestore . _areTimestampsInSnapshotsEnabled ( ) ,
1412
1424
options . serverTimestamps ,
1413
1425
this . _converter
@@ -1495,7 +1507,7 @@ export class Query<T = firestore.DocumentData> implements firestore.Query<T> {
1495
1507
] ;
1496
1508
validateStringEnum ( 'Query.where' , whereFilterOpEnums , 2 , opStr ) ;
1497
1509
1498
- let fieldValue : FieldValue ;
1510
+ let fieldValue : api . Value ;
1499
1511
const fieldPath = fieldPathFromArgument ( 'Query.where' , field ) ;
1500
1512
const operator = Operator . fromString ( opStr ) ;
1501
1513
if ( fieldPath . isKeyField ( ) ) {
@@ -1510,11 +1522,11 @@ export class Query<T = firestore.DocumentData> implements firestore.Query<T> {
1510
1522
) ;
1511
1523
} else if ( operator === Operator . IN ) {
1512
1524
this . validateDisjunctiveFilterElements ( value , operator ) ;
1513
- const referenceList : FieldValue [ ] = [ ] ;
1514
- for ( const arrayValue of value as FieldValue [ ] ) {
1525
+ const referenceList : api . Value [ ] = [ ] ;
1526
+ for ( const arrayValue of value as api . Value [ ] ) {
1515
1527
referenceList . push ( this . parseDocumentIdValue ( arrayValue ) ) ;
1516
1528
}
1517
- fieldValue = new ArrayValue ( referenceList ) ;
1529
+ fieldValue = { arrayValue : { values : referenceList } } ;
1518
1530
} else {
1519
1531
fieldValue = this . parseDocumentIdValue ( value ) ;
1520
1532
}
@@ -1720,7 +1732,7 @@ export class Query<T = firestore.DocumentData> implements firestore.Query<T> {
1720
1732
`${ methodName } ().`
1721
1733
) ;
1722
1734
}
1723
- return this . boundFromDocument ( methodName , snap . _document ! , before ) ;
1735
+ return this . boundFromDocument ( snap . _document ! , before ) ;
1724
1736
} else {
1725
1737
const allFields = [ docOrField ] . concat ( fields ) ;
1726
1738
return this . boundFromFields ( methodName , allFields , before ) ;
@@ -1738,12 +1750,8 @@ export class Query<T = firestore.DocumentData> implements firestore.Query<T> {
1738
1750
* of the query or if any of the fields in the order by are an uncommitted
1739
1751
* server timestamp.
1740
1752
*/
1741
- private boundFromDocument (
1742
- methodName : string ,
1743
- doc : Document ,
1744
- before : boolean
1745
- ) : Bound {
1746
- const components : FieldValue [ ] = [ ] ;
1753
+ private boundFromDocument ( doc : Document , before : boolean ) : Bound {
1754
+ const components : api . Value [ ] = [ ] ;
1747
1755
1748
1756
// Because people expect to continue/end a query at the exact document
1749
1757
// provided, we need to use the implicit sort order rather than the explicit
@@ -1754,10 +1762,12 @@ export class Query<T = firestore.DocumentData> implements firestore.Query<T> {
1754
1762
// results.
1755
1763
for ( const orderBy of this . _query . orderBy ) {
1756
1764
if ( orderBy . field . isKeyField ( ) ) {
1757
- components . push ( new RefValue ( this . firestore . _databaseId , doc . key ) ) ;
1765
+ components . push ( {
1766
+ referenceValue : doc . key . toName ( this . firestore . _databaseId )
1767
+ } ) ;
1758
1768
} else {
1759
1769
const value = doc . field ( orderBy . field ) ;
1760
- if ( value instanceof ServerTimestampValue ) {
1770
+ if ( isServerTimestamp ( value ) ) {
1761
1771
throw new FirestoreError (
1762
1772
Code . INVALID_ARGUMENT ,
1763
1773
'Invalid query. You are trying to start or end a query using a ' +
@@ -1801,7 +1811,7 @@ export class Query<T = firestore.DocumentData> implements firestore.Query<T> {
1801
1811
) ;
1802
1812
}
1803
1813
1804
- const components : FieldValue [ ] = [ ] ;
1814
+ const components : api . Value [ ] = [ ] ;
1805
1815
for ( let i = 0 ; i < values . length ; i ++ ) {
1806
1816
const rawValue = values [ i ] ;
1807
1817
const orderByComponent = orderBy [ i ] ;
@@ -1835,7 +1845,9 @@ export class Query<T = firestore.DocumentData> implements firestore.Query<T> {
1835
1845
) ;
1836
1846
}
1837
1847
const key = new DocumentKey ( path ) ;
1838
- components . push ( new RefValue ( this . firestore . _databaseId , key ) ) ;
1848
+ components . push ( {
1849
+ referenceValue : key . toName ( this . firestore . _databaseId )
1850
+ } ) ;
1839
1851
} else {
1840
1852
const wrapped = this . firestore . _dataReader . parseQueryValue (
1841
1853
methodName ,
@@ -2034,7 +2046,7 @@ export class Query<T = firestore.DocumentData> implements firestore.Query<T> {
2034
2046
* appropriate errors if the value is anything other than a DocumentReference
2035
2047
* or String, or if the string is malformed.
2036
2048
*/
2037
- private parseDocumentIdValue ( documentIdValue : unknown ) : RefValue {
2049
+ private parseDocumentIdValue ( documentIdValue : unknown ) : api . Value {
2038
2050
if ( typeof documentIdValue === 'string' ) {
2039
2051
if ( documentIdValue === '' ) {
2040
2052
throw new FirestoreError (
@@ -2065,10 +2077,12 @@ export class Query<T = firestore.DocumentData> implements firestore.Query<T> {
2065
2077
`but '${ path } ' is not because it has an odd number of segments (${ path . length } ).`
2066
2078
) ;
2067
2079
}
2068
- return new RefValue ( this . firestore . _databaseId , new DocumentKey ( path ) ) ;
2080
+ return {
2081
+ referenceValue : new DocumentKey ( path ) . toName ( this . firestore . _databaseId )
2082
+ } ;
2069
2083
} else if ( documentIdValue instanceof DocumentReference ) {
2070
2084
const ref = documentIdValue as DocumentReference < T > ;
2071
- return new RefValue ( this . firestore . _databaseId , ref . _key ) ;
2085
+ return { referenceValue : ref . _key . toName ( this . firestore . _databaseId ) } ;
2072
2086
} else {
2073
2087
throw new FirestoreError (
2074
2088
Code . INVALID_ARGUMENT ,
0 commit comments