Skip to content

Commit bcb185f

Browse files
committed
feat: upgrade firestore to firebase v9
1 parent d596b45 commit bcb185f

File tree

5 files changed

+173
-71
lines changed

5 files changed

+173
-71
lines changed

firestore/types.ts

Lines changed: 27 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,44 +1,53 @@
1-
import firebase from 'firebase/app';
1+
import {
2+
DocumentData,
3+
DocumentReference,
4+
DocumentSnapshot,
5+
FirestoreError,
6+
QuerySnapshot,
7+
SnapshotListenOptions,
8+
SnapshotOptions,
9+
} from 'firebase/firestore';
210
import { LoadingHook } from '../util';
311

412
export type IDOptions<T> = {
513
idField?: string;
614
refField?: string;
7-
snapshotOptions?: firebase.firestore.SnapshotOptions;
15+
snapshotOptions?: SnapshotOptions;
816
transform?: (val: any) => T;
917
};
1018
export type Options = {
11-
snapshotListenOptions?: firebase.firestore.SnapshotListenOptions;
19+
snapshotListenOptions?: SnapshotListenOptions;
1220
};
1321
export type DataOptions<T> = Options & IDOptions<T>;
1422
export type OnceOptions = {
15-
getOptions?: firebase.firestore.GetOptions;
23+
getOptions?: GetOptions;
24+
};
25+
export type GetOptions = {
26+
source?: 'default' | 'server' | 'cache';
1627
};
1728
export type OnceDataOptions<T> = OnceOptions & IDOptions<T>;
1829
export type Data<
19-
T = firebase.firestore.DocumentData,
30+
T = DocumentData,
2031
IDField extends string = '',
2132
RefField extends string = ''
22-
> = T &
23-
Record<IDField, string> &
24-
Record<RefField, firebase.firestore.DocumentReference<T>>;
33+
> = T & Record<IDField, string> & Record<RefField, DocumentReference<T>>;
2534

26-
export type CollectionHook<T = firebase.firestore.DocumentData> = LoadingHook<
27-
firebase.firestore.QuerySnapshot<T>,
28-
firebase.FirebaseError
35+
export type CollectionHook<T = DocumentData> = LoadingHook<
36+
QuerySnapshot<T>,
37+
FirestoreError
2938
>;
3039
export type CollectionDataHook<
31-
T = firebase.firestore.DocumentData,
40+
T = DocumentData,
3241
IDField extends string = '',
3342
RefField extends string = ''
34-
> = LoadingHook<Data<T, IDField, RefField>[], firebase.FirebaseError>;
43+
> = LoadingHook<Data<T, IDField, RefField>[], FirestoreError>;
3544

36-
export type DocumentHook<T = firebase.firestore.DocumentData> = LoadingHook<
37-
firebase.firestore.DocumentSnapshot<T>,
38-
firebase.FirebaseError
45+
export type DocumentHook<T = DocumentData> = LoadingHook<
46+
DocumentSnapshot<T>,
47+
FirestoreError
3948
>;
4049
export type DocumentDataHook<
41-
T = firebase.firestore.DocumentData,
50+
T = DocumentData,
4251
IDField extends string = '',
4352
RefField extends string = ''
44-
> = LoadingHook<Data<T, IDField, RefField>, firebase.FirebaseError>;
53+
> = LoadingHook<Data<T, IDField, RefField>, FirestoreError>;

firestore/useCollection.ts

Lines changed: 50 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -1,63 +1,74 @@
1-
import firebase from 'firebase/app';
1+
import {
2+
DocumentData,
3+
FirestoreError,
4+
getDocs,
5+
getDocsFromCache,
6+
getDocsFromServer,
7+
onSnapshot,
8+
Query,
9+
QuerySnapshot,
10+
} from 'firebase/firestore';
211
import { useEffect, useMemo } from 'react';
12+
import { useLoadingValue } from '../util';
313
import { snapshotToData } from './helpers';
414
import {
5-
CollectionHook,
615
CollectionDataHook,
16+
CollectionHook,
717
Data,
818
DataOptions,
9-
OnceOptions,
19+
GetOptions,
1020
OnceDataOptions,
21+
OnceOptions,
1122
Options,
1223
} from './types';
13-
import { useIsEqualRef, useLoadingValue } from '../util';
24+
import { useIsEqualFirestoreQuery } from './util';
1425

15-
export const useCollection = <T = firebase.firestore.DocumentData>(
16-
query?: firebase.firestore.Query | null,
26+
export const useCollection = <T = DocumentData>(
27+
query?: Query<T> | null,
1728
options?: Options
1829
): CollectionHook<T> => {
1930
return useCollectionInternal<T>(true, query, options);
2031
};
2132

22-
export const useCollectionOnce = <T = firebase.firestore.DocumentData>(
23-
query?: firebase.firestore.Query<T> | null,
33+
export const useCollectionOnce = <T = DocumentData>(
34+
query?: Query<T> | null,
2435
options?: OnceOptions
2536
): CollectionHook<T> => {
2637
return useCollectionInternal<T>(false, query, options);
2738
};
2839

2940
export const useCollectionData = <
30-
T = firebase.firestore.DocumentData,
41+
T = DocumentData,
3142
IDField extends string = '',
3243
RefField extends string = ''
3344
>(
34-
query?: firebase.firestore.Query | null,
45+
query?: Query<T> | null,
3546
options?: DataOptions<T>
3647
): CollectionDataHook<T, IDField, RefField> => {
3748
return useCollectionDataInternal<T, IDField, RefField>(true, query, options);
3849
};
3950

4051
export const useCollectionDataOnce = <
41-
T = firebase.firestore.DocumentData,
52+
T = DocumentData,
4253
IDField extends string = '',
4354
RefField extends string = ''
4455
>(
45-
query?: firebase.firestore.Query | null,
56+
query?: Query<T> | null,
4657
options?: OnceDataOptions<T>
4758
): CollectionDataHook<T, IDField, RefField> => {
4859
return useCollectionDataInternal<T, IDField, RefField>(false, query, options);
4960
};
5061

51-
const useCollectionInternal = <T = firebase.firestore.DocumentData>(
62+
const useCollectionInternal = <T = DocumentData>(
5263
listen: boolean,
53-
query?: firebase.firestore.Query | null,
64+
query?: Query<T> | null,
5465
options?: Options & OnceOptions
5566
) => {
5667
const { error, loading, reset, setError, setValue, value } = useLoadingValue<
57-
firebase.firestore.QuerySnapshot,
58-
firebase.FirebaseError
68+
QuerySnapshot,
69+
FirestoreError
5970
>();
60-
const ref = useIsEqualRef(query, reset);
71+
const ref = useIsEqualFirestoreQuery<Query<T>>(query, reset);
6172

6273
useEffect(() => {
6374
if (!ref.current) {
@@ -67,39 +78,38 @@ const useCollectionInternal = <T = firebase.firestore.DocumentData>(
6778
if (listen) {
6879
const listener =
6980
options && options.snapshotListenOptions
70-
? ref.current.onSnapshot(
81+
? onSnapshot(
82+
ref.current,
7183
options.snapshotListenOptions,
7284
setValue,
7385
setError
7486
)
75-
: ref.current.onSnapshot(setValue, setError);
87+
: onSnapshot(ref.current, setValue, setError);
7688

7789
return () => {
7890
listener();
7991
};
8092
} else {
81-
ref.current
82-
.get(options ? options.getOptions : undefined)
83-
.then(setValue)
84-
.catch(setError);
93+
const get = getDocsFnFromGetOptions(options?.getOptions);
94+
get(ref.current).then(setValue).catch(setError);
8595
}
8696
}, [ref.current]);
8797

8898
const resArray: CollectionHook<T> = [
89-
value as firebase.firestore.QuerySnapshot<T>,
99+
value as QuerySnapshot<T>,
90100
loading,
91101
error,
92102
];
93103
return useMemo(() => resArray, resArray);
94104
};
95105

96106
const useCollectionDataInternal = <
97-
T = firebase.firestore.DocumentData,
107+
T = DocumentData,
98108
IDField extends string = '',
99109
RefField extends string = ''
100110
>(
101111
listen: boolean,
102-
query?: firebase.firestore.Query | null,
112+
query?: Query<T> | null,
103113
options?: DataOptions<T> & OnceDataOptions<T>
104114
): CollectionDataHook<T, IDField, RefField> => {
105115
const idField = options ? options.idField : undefined;
@@ -134,3 +144,17 @@ const useCollectionDataInternal = <
134144
];
135145
return useMemo(() => resArray, resArray);
136146
};
147+
148+
function getDocsFnFromGetOptions(
149+
{ source }: GetOptions = { source: 'default' }
150+
) {
151+
switch (source) {
152+
default:
153+
case 'default':
154+
return getDocs;
155+
case 'cache':
156+
return getDocsFromCache;
157+
case 'server':
158+
return getDocsFromServer;
159+
}
160+
}

firestore/useDocument.ts

Lines changed: 51 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -1,63 +1,74 @@
1-
import firebase from 'firebase/app';
1+
import {
2+
DocumentData,
3+
DocumentReference,
4+
DocumentSnapshot,
5+
FirestoreError,
6+
getDoc,
7+
getDocFromCache,
8+
getDocFromServer,
9+
onSnapshot,
10+
} from 'firebase/firestore';
211
import { useEffect, useMemo } from 'react';
12+
import { useLoadingValue } from '../util';
313
import { snapshotToData } from './helpers';
414
import {
515
Data,
616
DataOptions,
7-
DocumentHook,
817
DocumentDataHook,
9-
OnceOptions,
18+
DocumentHook,
19+
GetOptions,
1020
OnceDataOptions,
21+
OnceOptions,
1122
Options,
1223
} from './types';
13-
import { useIsEqualRef, useLoadingValue } from '../util';
24+
import { useIsEqualFirestoreRef } from './util';
1425

15-
export const useDocument = <T = firebase.firestore.DocumentData>(
16-
docRef?: firebase.firestore.DocumentReference | null,
26+
export const useDocument = <T = DocumentData>(
27+
docRef?: DocumentReference<T> | null,
1728
options?: Options
1829
): DocumentHook<T> => {
1930
return useDocumentInternal<T>(true, docRef, options);
2031
};
2132

22-
export const useDocumentOnce = <T = firebase.firestore.DocumentData>(
23-
docRef?: firebase.firestore.DocumentReference | null,
33+
export const useDocumentOnce = <T = DocumentData>(
34+
docRef?: DocumentReference<T> | null,
2435
options?: OnceOptions
2536
): DocumentHook<T> => {
2637
return useDocumentInternal<T>(false, docRef, options);
2738
};
2839

2940
export const useDocumentData = <
30-
T = firebase.firestore.DocumentData,
41+
T = DocumentData,
3142
IDField extends string = '',
3243
RefField extends string = ''
3344
>(
34-
docRef?: firebase.firestore.DocumentReference | null,
45+
docRef?: DocumentReference<T> | null,
3546
options?: DataOptions<T>
3647
): DocumentDataHook<T, IDField, RefField> => {
3748
return useDocumentDataInternal<T, IDField, RefField>(true, docRef, options);
3849
};
3950

4051
export const useDocumentDataOnce = <
41-
T = firebase.firestore.DocumentData,
52+
T = DocumentData,
4253
IDField extends string = '',
4354
RefField extends string = ''
4455
>(
45-
docRef?: firebase.firestore.DocumentReference | null,
56+
docRef?: DocumentReference<T> | null,
4657
options?: OnceDataOptions<T>
4758
): DocumentDataHook<T, IDField, RefField> => {
4859
return useDocumentDataInternal<T, IDField, RefField>(false, docRef, options);
4960
};
5061

51-
const useDocumentInternal = <T = firebase.firestore.DocumentData>(
62+
const useDocumentInternal = <T = DocumentData>(
5263
listen: boolean,
53-
docRef?: firebase.firestore.DocumentReference | null,
64+
docRef?: DocumentReference<T> | null,
5465
options?: Options & OnceOptions
5566
): DocumentHook<T> => {
5667
const { error, loading, reset, setError, setValue, value } = useLoadingValue<
57-
firebase.firestore.DocumentSnapshot,
58-
firebase.FirebaseError
68+
DocumentSnapshot<T>,
69+
FirestoreError
5970
>();
60-
const ref = useIsEqualRef(docRef, reset);
71+
const ref = useIsEqualFirestoreRef<DocumentReference<T>>(docRef, reset);
6172

6273
useEffect(() => {
6374
if (!ref.current) {
@@ -67,39 +78,39 @@ const useDocumentInternal = <T = firebase.firestore.DocumentData>(
6778
if (listen) {
6879
const listener =
6980
options && options.snapshotListenOptions
70-
? ref.current.onSnapshot(
81+
? onSnapshot(
82+
ref.current,
7183
options.snapshotListenOptions,
7284
setValue,
7385
setError
7486
)
75-
: ref.current.onSnapshot(setValue, setError);
87+
: onSnapshot(ref.current, setValue, setError);
7688

7789
return () => {
7890
listener();
7991
};
8092
} else {
81-
ref.current
82-
.get(options ? options.getOptions : undefined)
83-
.then(setValue)
84-
.catch(setError);
93+
const get = getDocFnFromGetOptions(options?.getOptions);
94+
95+
get(ref.current).then(setValue).catch(setError);
8596
}
8697
}, [ref.current]);
8798

8899
const resArray: DocumentHook<T> = [
89-
value as firebase.firestore.DocumentSnapshot<T>,
100+
value as DocumentSnapshot<T>,
90101
loading,
91102
error,
92103
];
93104
return useMemo(() => resArray, resArray);
94105
};
95106

96107
const useDocumentDataInternal = <
97-
T = firebase.firestore.DocumentData,
108+
T = DocumentData,
98109
IDField extends string = '',
99110
RefField extends string = ''
100111
>(
101112
listen: boolean,
102-
docRef?: firebase.firestore.DocumentReference | null,
113+
docRef?: DocumentReference<T> | null,
103114
options?: DataOptions<T>
104115
): DocumentDataHook<T, IDField, RefField> => {
105116
const idField = options ? options.idField : undefined;
@@ -132,3 +143,17 @@ const useDocumentDataInternal = <
132143
];
133144
return useMemo(() => resArray, resArray);
134145
};
146+
147+
function getDocFnFromGetOptions(
148+
{ source }: GetOptions = { source: 'default' }
149+
) {
150+
switch (source) {
151+
default:
152+
case 'default':
153+
return getDoc;
154+
case 'cache':
155+
return getDocFromCache;
156+
case 'server':
157+
return getDocFromServer;
158+
}
159+
}

0 commit comments

Comments
 (0)