Skip to content

Commit 082fc9a

Browse files
committed
feat(fs): types for collection, audit log, state, and snapshot changes
1 parent 7d2fd53 commit 082fc9a

File tree

7 files changed

+45
-67
lines changed

7 files changed

+45
-67
lines changed

src/firestore/collection/changes.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -10,24 +10,24 @@ import { DocumentChangeAction, Action } from '../interfaces';
1010
* order of occurence.
1111
* @param query
1212
*/
13-
export function docChanges(query: Query): Observable<DocumentChangeAction[]> {
13+
export function docChanges<T>(query: Query): Observable<DocumentChangeAction<T>[]> {
1414
return fromCollectionRef(query)
1515
.pipe(
1616
map(action =>
1717
action.payload.docChanges()
18-
.map(change => ({ type: change.type, payload: change }))));
18+
.map(change => ({ type: change.type, payload: change } as DocumentChangeAction<T>))));
1919
}
2020

2121
/**
2222
* Return a stream of document changes on a query. These results are in sort order.
2323
* @param query
2424
*/
25-
export function sortedChanges(query: Query, events: DocumentChangeType[]): Observable<DocumentChangeAction[]> {
25+
export function sortedChanges<T>(query: Query, events: DocumentChangeType[]): Observable<DocumentChangeAction<T>[]> {
2626
return fromCollectionRef(query)
2727
.pipe(
2828
map(changes => changes.payload.docChanges()),
2929
scan((current, changes) => combineChanges(current, changes, events), []),
30-
map(changes => changes.map(c => ({ type: c.type, payload: c }))));
30+
map(changes => changes.map(c => ({ type: c.type, payload: c } as DocumentChangeAction<T>))));
3131
}
3232

3333
/**

src/firestore/collection/collection.ts

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ import { map, filter } from 'rxjs/operators';
55

66
import { Injectable } from '@angular/core';
77

8-
import { QueryFn, AssociatedReference, DocumentChangeAction } from '../interfaces';
8+
import { QueryFn, AssociatedReference, DocumentChangeAction, DocumentChange } from '../interfaces';
99
import { docChanges, sortedChanges } from './changes';
1010
import { AngularFirestoreDocument } from '../document/document';
1111
import { AngularFirestore } from '../firestore';
@@ -62,17 +62,17 @@ export class AngularFirestoreCollection<T> {
6262
* your own data structure.
6363
* @param events
6464
*/
65-
stateChanges(events?: DocumentChangeType[]): Observable<DocumentChangeAction[]> {
65+
stateChanges(events?: DocumentChangeType[]): Observable<DocumentChangeAction<T>[]> {
6666
if(!events || events.length === 0) {
6767
return this.afs.scheduler.keepUnstableUntilFirst(
6868
this.afs.scheduler.runOutsideAngular(
69-
docChanges(this.query)
69+
docChanges<T>(this.query)
7070
)
7171
);
7272
}
7373
return this.afs.scheduler.keepUnstableUntilFirst(
7474
this.afs.scheduler.runOutsideAngular(
75-
docChanges(this.query)
75+
docChanges<T>(this.query)
7676
)
7777
)
7878
.pipe(
@@ -86,7 +86,7 @@ export class AngularFirestoreCollection<T> {
8686
* but it collects each event in an array over time.
8787
* @param events
8888
*/
89-
auditTrail(events?: DocumentChangeType[]): Observable<DocumentChangeAction[]> {
89+
auditTrail(events?: DocumentChangeType[]): Observable<DocumentChangeAction<T>[]> {
9090
return this.stateChanges(events).scan((current, action) => [...current, ...action], []);
9191
}
9292

@@ -95,9 +95,9 @@ export class AngularFirestoreCollection<T> {
9595
* query order.
9696
* @param events
9797
*/
98-
snapshotChanges(events?: DocumentChangeType[]): Observable<DocumentChangeAction[]> {
98+
snapshotChanges(events?: DocumentChangeType[]): Observable<DocumentChangeAction<T>[]> {
9999
const validatedEvents = validateEventsArray(events);
100-
const sortedChanges$ = sortedChanges(this.query, validatedEvents);
100+
const sortedChanges$ = sortedChanges<T>(this.query, validatedEvents);
101101
const scheduledSortedChanges$ = this.afs.scheduler.runOutsideAngular(sortedChanges$);
102102
return this.afs.scheduler.keepUnstableUntilFirst(scheduledSortedChanges$);
103103
}

src/firestore/document/document.spec.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@ describe('AngularFirestoreDocument', () => {
5757
const stock = new AngularFirestoreDocument<Stock>(ref, afs);
5858
await stock.set(FAKE_STOCK_DATA);
5959
const obs$ = stock.valueChanges();
60-
obs$.pipe(take(1)).subscribe(async (data: Stock) => {
60+
obs$.pipe(take(1)).subscribe(async data => {
6161
expect(JSON.stringify(data)).toBe(JSON.stringify(FAKE_STOCK_DATA));
6262
stock.delete().then(done).catch(done.fail);
6363
});

src/firestore/document/document.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
1-
import { DocumentReference, SetOptions, DocumentSnapshot } from '@firebase/firestore-types';
1+
import { DocumentReference, SetOptions } from '@firebase/firestore-types';
22
import { Observable, Subscriber } from 'rxjs';
3-
import { QueryFn, AssociatedReference, Action } from '../interfaces';
3+
import { QueryFn, AssociatedReference, Action, DocumentSnapshot } from '../interfaces';
44
import { fromDocRef } from '../observable/fromRef';
55
import { map } from 'rxjs/operators';
66

@@ -70,17 +70,17 @@ export class AngularFirestoreDocument<T> {
7070
* @param path
7171
* @param queryFn
7272
*/
73-
collection<T>(path: string, queryFn?: QueryFn): AngularFirestoreCollection<T> {
73+
collection<R>(path: string, queryFn?: QueryFn): AngularFirestoreCollection<R> {
7474
const collectionRef = this.ref.collection(path);
7575
const { ref, query } = associateQuery(collectionRef, queryFn);
76-
return new AngularFirestoreCollection<T>(ref, query, this.afs);
76+
return new AngularFirestoreCollection<R>(ref, query, this.afs);
7777
}
7878

7979
/**
8080
* Listen to snapshot updates from the document.
8181
*/
82-
snapshotChanges(): Observable<Action<DocumentSnapshot>> {
83-
const fromDocRef$ = fromDocRef(this.ref);
82+
snapshotChanges(): Observable<Action<DocumentSnapshot<T>>> {
83+
const fromDocRef$ = fromDocRef<T>(this.ref);
8484
const scheduledFromDocRef$ = this.afs.scheduler.runOutsideAngular(fromDocRef$);
8585
return this.afs.scheduler.keepUnstableUntilFirst(scheduledFromDocRef$);
8686
}

src/firestore/interfaces.ts

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,21 @@
11
import { Subscriber } from 'rxjs';
2-
import { DocumentChangeType, DocumentChange, CollectionReference, Query } from '@firebase/firestore-types';
2+
import { DocumentChangeType, DocumentSnapshot as _DocumentSnapshot, SnapshotOptions, QueryDocumentSnapshot as _QueryDocumentSnapshot, DocumentChange as _DocumentChange, CollectionReference, Query } from '@firebase/firestore-types';
33

4-
export interface DocumentChangeAction {
4+
export interface DocumentSnapshot<T> extends _DocumentSnapshot {
5+
data(options?: SnapshotOptions): T | undefined;
6+
}
7+
8+
export interface QueryDocumentSnapshot<T> extends _QueryDocumentSnapshot {
9+
data(options?: SnapshotOptions): T;
10+
}
11+
12+
export interface DocumentChange<T> extends _DocumentChange {
13+
readonly doc: QueryDocumentSnapshot<T>;
14+
}
15+
16+
export interface DocumentChangeAction<T> {
517
type: DocumentChangeType;
6-
payload: DocumentChange;
18+
payload: DocumentChange<T>;
719
}
820

921
export interface Action<T> {

src/firestore/observable/fromRef.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
1-
import { DocumentReference, Query, QuerySnapshot, DocumentSnapshot } from '@firebase/firestore-types';
1+
import { DocumentReference, Query, QuerySnapshot } from '@firebase/firestore-types';
22
import { Observable, Subscriber } from 'rxjs';
3-
import { Action, Reference } from '../interfaces';
3+
import { Action, Reference, DocumentSnapshot } from '../interfaces';
44
import { map, share } from 'rxjs/operators';
55

66
function _fromRef<T, R>(ref: Reference<T>): Observable<R> {
@@ -14,8 +14,8 @@ export function fromRef<R>(ref: DocumentReference | Query) {
1414
return _fromRef<typeof ref, R>(ref).pipe(share());
1515
}
1616

17-
export function fromDocRef(ref: DocumentReference): Observable<Action<DocumentSnapshot>>{
18-
return fromRef<DocumentSnapshot>(ref)
17+
export function fromDocRef<T>(ref: DocumentReference): Observable<Action<DocumentSnapshot<T>>>{
18+
return fromRef<DocumentSnapshot<T>>(ref)
1919
.pipe(
2020
map(payload => ({ payload, type: 'value' }))
2121
);

yarn.lock

Lines changed: 8 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@
6262
dom-storage "2.1.0"
6363
tslib "1.9.0"
6464
xmlhttprequest "1.8.0"
65+
6566
"@firebase/[email protected]", "@firebase/auth-types@^0.3.2":
6667
version "0.3.2"
6768
resolved "https://registry.yarnpkg.com/@firebase/auth-types/-/auth-types-0.3.2.tgz#fc636084eb82cb098e4e76efc5fffd315e22abdd"
@@ -72,34 +73,21 @@
7273
dependencies:
7374
"@firebase/auth-types" "0.3.2"
7475

75-
"@firebase/database-types@0.3.1", "@firebase/database-types@^0.3.1":
76+
"@firebase/database-types@^0.3.1":
7677
version "0.3.1"
7778
resolved "https://registry.yarnpkg.com/@firebase/database-types/-/database-types-0.3.1.tgz#4a15423f3b2cb3bed111f5a353c5c1bb2e2787ba"
7879

7980
"@firebase/[email protected]", "@firebase/database@^0.3.1":
8081
version "0.3.1"
8182
resolved "https://registry.yarnpkg.com/@firebase/database/-/database-0.3.1.tgz#1ca0797b8e9a243d383d31b1873373b84a2048b9"
82-
83-
"@firebase/[email protected]", "@firebase/auth-types@^0.2.1":
84-
version "0.2.1"
85-
resolved "https://registry.yarnpkg.com/@firebase/auth-types/-/auth-types-0.2.1.tgz#83a03939358ce8a59de85404b9ed7ca13a51548f"
86-
87-
"@firebase/[email protected]", "@firebase/auth@^0.4.2":
88-
version "0.4.2"
89-
resolved "https://registry.yarnpkg.com/@firebase/auth/-/auth-0.4.2.tgz#63044e6ca6fb98ddc2de5a442f56f9d612ed1903"
9083
dependencies:
91-
"@firebase/auth-types" "0.2.1"
92-
93-
"@firebase/[email protected]", "@firebase/database-types@^0.2.1":
94-
version "0.2.1"
95-
resolved "https://registry.yarnpkg.com/@firebase/database-types/-/database-types-0.2.1.tgz#f83a6d03af5f8c93276ceb89e1f31e4664c9df1b"
96-
97-
"@firebase/[email protected]", "@firebase/database@^0.2.2":
98-
version "0.2.2"
99-
resolved "https://registry.yarnpkg.com/@firebase/database/-/database-0.2.2.tgz#a8a0709644d7f281b400e983c71c8c65fba90c70"
84+
"@firebase/database-types" "0.3.1"
85+
"@firebase/logger" "0.1.1"
86+
"@firebase/util" "0.2.0"
87+
faye-websocket "0.11.1"
88+
tslib "1.9.0"
10089

10190
"@firebase/[email protected]", "@firebase/firestore-types@^0.4.1":
102-
10391
version "0.4.1"
10492
resolved "https://registry.yarnpkg.com/@firebase/firestore-types/-/firestore-types-0.4.1.tgz#9a96dff26f0537b13ff119b5e7ab4bddad2068d1"
10593

@@ -112,7 +100,7 @@
112100
"@firebase/webchannel-wrapper" "0.2.8"
113101
grpc "1.10.1"
114102
tslib "1.9.0"
115-
103+
116104
"@firebase/[email protected]":
117105
version "0.1.2"
118106
resolved "https://registry.yarnpkg.com/@firebase/functions-types/-/functions-types-0.1.2.tgz#f291b2945218a97d9ab0e20f2fdec2cef6f90f94"
@@ -1837,12 +1825,6 @@ fast-levenshtein@~2.0.4:
18371825
version "2.0.6"
18381826
resolved "https://registry.yarnpkg.com/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz#3d8a5c66883a16a30ca8643e851f19baa7797917"
18391827

1840-
1841-
version "0.11.1"
1842-
resolved "https://registry.yarnpkg.com/faye-websocket/-/faye-websocket-0.11.1.tgz#f0efe18c4f56e4f40afc7e06c719fd5ee6188f38"
1843-
dependencies:
1844-
websocket-driver ">=0.5.1"
1845-
18461828
file-uri-to-path@1:
18471829
version "1.0.0"
18481830
resolved "https://registry.yarnpkg.com/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz#553a7b8446ff6f684359c445f1e37a05dacc33dd"
@@ -1918,7 +1900,6 @@ fined@^1.0.1:
19181900
object.pick "^1.2.0"
19191901
parse-filepath "^1.0.1"
19201902

1921-
19221903
firebase@^5.0.2:
19231904
version "5.0.2"
19241905
resolved "https://registry.yarnpkg.com/firebase/-/firebase-5.0.2.tgz#5c0d647acc10552d15169e5f8482413aff1264cb"
@@ -2607,10 +2588,6 @@ http-errors@~1.6.2:
26072588
setprototypeof "1.1.0"
26082589
statuses ">= 1.4.0 < 2"
26092590

2610-
http-parser-js@>=0.4.0:
2611-
version "0.4.12"
2612-
resolved "https://registry.yarnpkg.com/http-parser-js/-/http-parser-js-0.4.12.tgz#b9cfbf4a2cf26f0fc34b10ca1489a27771e3474f"
2613-
26142591
http-proxy-agent@1:
26152592
version "1.0.0"
26162593
resolved "https://registry.yarnpkg.com/http-proxy-agent/-/http-proxy-agent-1.0.0.tgz#cc1ce38e453bf984a0f7702d2dd59c73d081284a"
@@ -5791,17 +5768,6 @@ void-elements@^2.0.0:
57915768
version "2.0.1"
57925769
resolved "https://registry.yarnpkg.com/void-elements/-/void-elements-2.0.1.tgz#c066afb582bb1cb4128d60ea92392e94d5e9dbec"
57935770

5794-
websocket-driver@>=0.5.1:
5795-
version "0.7.0"
5796-
resolved "https://registry.yarnpkg.com/websocket-driver/-/websocket-driver-0.7.0.tgz#0caf9d2d755d93aee049d4bdd0d3fe2cca2a24eb"
5797-
dependencies:
5798-
http-parser-js ">=0.4.0"
5799-
websocket-extensions ">=0.1.1"
5800-
5801-
websocket-extensions@>=0.1.1:
5802-
version "0.1.3"
5803-
resolved "https://registry.yarnpkg.com/websocket-extensions/-/websocket-extensions-0.1.3.tgz#5d2ff22977003ec687a4b87073dfbbac146ccf29"
5804-
58055771
[email protected], whatwg-fetch@>=0.10.0:
58065772
version "2.0.4"
58075773
resolved "https://registry.yarnpkg.com/whatwg-fetch/-/whatwg-fetch-2.0.4.tgz#dde6a5df315f9d39991aa17621853d720b85566f"

0 commit comments

Comments
 (0)