@hyper-fetch/firebase-admin 7.5.2 → 7.5.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/__tests__/features/firestore/admin/constraints.admin.spec.ts +23 -0
- package/__tests__/features/firestore/admin/methods.admin.spec.ts +20 -0
- package/__tests__/features/firestore/admin/sockets.base.spec.ts +17 -0
- package/__tests__/features/firestore/shared/constraints.shared.tests.ts +72 -0
- package/__tests__/features/firestore/shared/methods/add-doc.test.suite.ts +29 -0
- package/__tests__/features/firestore/shared/methods/delete-doc.test.suite.ts +52 -0
- package/__tests__/features/firestore/shared/methods/get-doc.test.suite.ts +60 -0
- package/__tests__/features/firestore/shared/methods/get-docs.test.suite.ts +45 -0
- package/__tests__/features/firestore/shared/methods/on-snapshot.test.suite.ts +290 -0
- package/__tests__/features/firestore/shared/methods/set-doc.test.suite.ts +70 -0
- package/__tests__/features/firestore/shared/methods/update-doc.test.suite.ts +40 -0
- package/__tests__/features/firestore/shared/methods.shared.tests.ts +24 -0
- package/__tests__/features/realtime/admin/constraints.admin.spec.ts +15 -0
- package/__tests__/features/realtime/admin/methods.admin.spec.ts +24 -0
- package/__tests__/features/realtime/admin/sockets.base.spec.ts +15 -0
- package/__tests__/features/realtime/shared/constraints.shared.tests.ts +59 -0
- package/__tests__/features/realtime/shared/methods/get.test.suite.ts +64 -0
- package/__tests__/features/realtime/shared/methods/on-value.test.suite.ts +190 -0
- package/__tests__/features/realtime/shared/methods/push.test.suite.ts +48 -0
- package/__tests__/features/realtime/shared/methods/remove.test.suite.ts +46 -0
- package/__tests__/features/realtime/shared/methods/set.test.suite.ts +68 -0
- package/__tests__/features/realtime/shared/methods/update.test.suite.ts +42 -0
- package/__tests__/features/realtime/shared/methods.shared.tests.ts +25 -0
- package/__tests__/global.d.ts +1 -0
- package/__tests__/jest.setup.ts +8 -0
- package/__tests__/shared/request-events.shared.ts +32 -0
- package/__tests__/tsconfig.json +8 -0
- package/__tests__/utils/database.rules.json +11 -0
- package/__tests__/utils/index.ts +3 -0
- package/__tests__/utils/initialize.firestore.admin.ts +16 -0
- package/__tests__/utils/initialize.realtime.admin.ts +19 -0
- package/__tests__/utils/seed/seed.data.ts +21 -0
- package/__tests__/utils/seed.admin.ts +23 -0
- package/jest.config.ts +9 -0
- package/package.json +1 -1
- package/project.json +4 -0
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import { Client } from "@hyper-fetch/core";
|
|
2
|
+
|
|
3
|
+
import { FirebaseAdminAdapter } from "adapter";
|
|
4
|
+
import { Tea } from "../../../../utils";
|
|
5
|
+
import { testLifecycleEvents } from "../../../../shared/request-events.shared";
|
|
6
|
+
|
|
7
|
+
export const updateDocTestSuite = (adapterFunction: () => ReturnType<typeof FirebaseAdminAdapter>) => {
|
|
8
|
+
describe("updateDoc", () => {
|
|
9
|
+
it("should allow for updating data", async () => {
|
|
10
|
+
const newData = { name: "Pou Ran Do Cha", amount: 100, year: 966 } as Tea;
|
|
11
|
+
const client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
12
|
+
const updateReq = client
|
|
13
|
+
.createRequest<{ response: Tea; payload: Tea }>()({
|
|
14
|
+
endpoint: ":teaId",
|
|
15
|
+
method: "updateDoc",
|
|
16
|
+
})
|
|
17
|
+
.setPayload(newData);
|
|
18
|
+
const getReq = client.createRequest<{ response: Tea }>()({
|
|
19
|
+
endpoint: ":teaId",
|
|
20
|
+
method: "getDoc",
|
|
21
|
+
});
|
|
22
|
+
await updateReq.send({ params: { teaId: 1 } });
|
|
23
|
+
const { data } = await getReq.send({ params: { teaId: 1 } });
|
|
24
|
+
expect(data).toStrictEqual({ ...newData, origin: "China", type: "Green", __key: "1" });
|
|
25
|
+
});
|
|
26
|
+
it("should emit lifecycle events", async () => {
|
|
27
|
+
const client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
28
|
+
const newData = { name: "Pou Ran Do Cha", amount: 100, year: 966 } as Tea;
|
|
29
|
+
|
|
30
|
+
const request = client
|
|
31
|
+
.createRequest<{ response: Tea; payload: Tea }>()({
|
|
32
|
+
endpoint: ":teaId",
|
|
33
|
+
method: "updateDoc",
|
|
34
|
+
})
|
|
35
|
+
.setPayload(newData);
|
|
36
|
+
|
|
37
|
+
await testLifecycleEvents(request);
|
|
38
|
+
});
|
|
39
|
+
});
|
|
40
|
+
};
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { FirebaseAdminAdapter, FirebaseAdminAdapterTypes, FirebaseAdminSocketAdapterTypes } from "adapter";
|
|
2
|
+
import { addDocTestSuite } from "./methods/add-doc.test.suite";
|
|
3
|
+
import { deleteDocTestSuite } from "./methods/delete-doc.test.suite";
|
|
4
|
+
import { getDocTestSuite } from "./methods/get-doc.test.suite";
|
|
5
|
+
import { getDocsTestSuite } from "./methods/get-docs.test.suite";
|
|
6
|
+
import { setDocTestSuite } from "./methods/set-doc.test.suite";
|
|
7
|
+
import { updateDocTestSuite } from "./methods/update-doc.test.suite";
|
|
8
|
+
import { onSnapshotTestSuite } from "./methods/on-snapshot.test.suite";
|
|
9
|
+
|
|
10
|
+
export const methodsSharedTestCases = (adapterFunction: () => ReturnType<typeof FirebaseAdminAdapter>) => {
|
|
11
|
+
addDocTestSuite(adapterFunction);
|
|
12
|
+
deleteDocTestSuite(adapterFunction);
|
|
13
|
+
getDocTestSuite(adapterFunction);
|
|
14
|
+
getDocsTestSuite(adapterFunction);
|
|
15
|
+
setDocTestSuite(adapterFunction);
|
|
16
|
+
updateDocTestSuite(adapterFunction);
|
|
17
|
+
};
|
|
18
|
+
|
|
19
|
+
export const socketsMethodsSharedTestCases = (
|
|
20
|
+
adapter: FirebaseAdminSocketAdapterTypes<any>,
|
|
21
|
+
coreAdapter: FirebaseAdminAdapterTypes<any>,
|
|
22
|
+
) => {
|
|
23
|
+
onSnapshotTestSuite(adapter, coreAdapter);
|
|
24
|
+
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { FirebaseAdminAdapter } from "adapter";
|
|
2
|
+
import { seedRealtimeDatabaseAdmin } from "../../../utils/seed.admin";
|
|
3
|
+
import { realtimeDbAdmin } from "../../../utils";
|
|
4
|
+
import { constraintsSharedTestCases } from "../shared/constraints.shared.tests";
|
|
5
|
+
|
|
6
|
+
describe("Realtime Database Admin [Constraints]", () => {
|
|
7
|
+
let db: any;
|
|
8
|
+
beforeEach(async () => {
|
|
9
|
+
db = await realtimeDbAdmin;
|
|
10
|
+
await db.ref("teas").set(null);
|
|
11
|
+
await seedRealtimeDatabaseAdmin(db);
|
|
12
|
+
});
|
|
13
|
+
|
|
14
|
+
constraintsSharedTestCases(() => FirebaseAdminAdapter(db));
|
|
15
|
+
});
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @jest-environment node
|
|
3
|
+
*/
|
|
4
|
+
import { realtimeDbAdmin, seedRealtimeDatabaseAdmin } from "../../../utils";
|
|
5
|
+
import { FirebaseAdminAdapter } from "adapter";
|
|
6
|
+
import { methodsSharedTestCases } from "../shared/methods.shared.tests";
|
|
7
|
+
|
|
8
|
+
describe("Realtime Database Admin [ Methods ]", () => {
|
|
9
|
+
let db: any;
|
|
10
|
+
|
|
11
|
+
beforeAll(async () => {
|
|
12
|
+
db = await realtimeDbAdmin;
|
|
13
|
+
});
|
|
14
|
+
beforeEach(async () => {
|
|
15
|
+
await db.ref("teas").set(null);
|
|
16
|
+
await seedRealtimeDatabaseAdmin(db);
|
|
17
|
+
});
|
|
18
|
+
|
|
19
|
+
afterEach(async () => {
|
|
20
|
+
await db.ref("teas").set(null);
|
|
21
|
+
});
|
|
22
|
+
|
|
23
|
+
methodsSharedTestCases(() => FirebaseAdminAdapter(db));
|
|
24
|
+
});
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @jest-environment node
|
|
3
|
+
*/
|
|
4
|
+
import { realtimeDbAdmin, seedRealtimeDatabaseAdmin } from "../../../utils";
|
|
5
|
+
import { socketsMethodsSharedTestCases } from "../shared/methods.shared.tests";
|
|
6
|
+
import { FirebaseSocketsAdminAdapter, FirebaseAdminAdapter } from "adapter";
|
|
7
|
+
|
|
8
|
+
describe("Realtime Database Admin [Sockets]", () => {
|
|
9
|
+
socketsMethodsSharedTestCases(
|
|
10
|
+
realtimeDbAdmin,
|
|
11
|
+
seedRealtimeDatabaseAdmin,
|
|
12
|
+
FirebaseSocketsAdminAdapter,
|
|
13
|
+
FirebaseAdminAdapter,
|
|
14
|
+
);
|
|
15
|
+
});
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
import { Client } from "@hyper-fetch/core";
|
|
2
|
+
|
|
3
|
+
import { $endAt, $limitToFirst, $orderByChild, $startAt, FirebaseAdminAdapter } from "../../../../src";
|
|
4
|
+
import { Tea } from "../../../utils";
|
|
5
|
+
|
|
6
|
+
export const constraintsSharedTestCases = (adapterFunction: () => ReturnType<typeof FirebaseAdminAdapter>) => {
|
|
7
|
+
describe("Ordering", () => {
|
|
8
|
+
it("Should allow ordering by child", async () => {
|
|
9
|
+
const client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
10
|
+
const req = client.createRequest<{ response: Tea[] }>()({
|
|
11
|
+
endpoint: "",
|
|
12
|
+
method: "getDocs",
|
|
13
|
+
});
|
|
14
|
+
const { data } = await req.send({
|
|
15
|
+
// TODO: Fix this
|
|
16
|
+
queryParams: { constraints: [$orderByChild("origin")] },
|
|
17
|
+
});
|
|
18
|
+
expect(data?.map((el) => el.origin)).toStrictEqual([
|
|
19
|
+
"China",
|
|
20
|
+
"China",
|
|
21
|
+
"China",
|
|
22
|
+
"China",
|
|
23
|
+
"China",
|
|
24
|
+
"China",
|
|
25
|
+
"China",
|
|
26
|
+
"Japan",
|
|
27
|
+
"Taiwan",
|
|
28
|
+
"Taiwan",
|
|
29
|
+
]);
|
|
30
|
+
});
|
|
31
|
+
});
|
|
32
|
+
describe("Filtering and ordering", () => {
|
|
33
|
+
it("Should allow to limit the result and order it", async () => {
|
|
34
|
+
const client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
35
|
+
const req = client.createRequest<{ response: Tea[] }>()({
|
|
36
|
+
endpoint: "",
|
|
37
|
+
method: "getDocs",
|
|
38
|
+
});
|
|
39
|
+
const { data } = await req.send({
|
|
40
|
+
// TODO: Fix this
|
|
41
|
+
queryParams: { constraints: [$orderByChild("origin"), $limitToFirst(5)] },
|
|
42
|
+
});
|
|
43
|
+
expect(data?.map((tea) => tea.origin)).toStrictEqual(["China", "China", "China", "China", "China"]);
|
|
44
|
+
});
|
|
45
|
+
it("Should allow to combine multiple filters", async () => {
|
|
46
|
+
const client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
47
|
+
const req = client.createRequest<{ response: Tea[] }>()({
|
|
48
|
+
endpoint: "",
|
|
49
|
+
method: "getDocs",
|
|
50
|
+
});
|
|
51
|
+
const { data } = await req.send({
|
|
52
|
+
// TODO: Fix this
|
|
53
|
+
queryParams: { constraints: [$orderByChild("year"), $startAt(2021), $endAt(2022)] },
|
|
54
|
+
});
|
|
55
|
+
expect(data).toHaveLength(5);
|
|
56
|
+
expect(data?.map((tea) => tea.year)).toStrictEqual([2021, 2021, 2021, 2022, 2022]);
|
|
57
|
+
});
|
|
58
|
+
});
|
|
59
|
+
};
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import { Client } from "@hyper-fetch/core";
|
|
2
|
+
|
|
3
|
+
import { FirebaseAdminAdapter } from "adapter";
|
|
4
|
+
import { testLifecycleEvents } from "../../../../shared/request-events.shared";
|
|
5
|
+
import { Tea } from "../../../../utils";
|
|
6
|
+
|
|
7
|
+
export const getTestSuite = (adapterFunction: () => ReturnType<typeof FirebaseAdminAdapter>) => {
|
|
8
|
+
describe("get", () => {
|
|
9
|
+
let client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
10
|
+
let clientBees = new Client({ url: "bees/" }).setAdapter(adapterFunction());
|
|
11
|
+
beforeEach(() => {
|
|
12
|
+
clientBees = new Client({ url: "bees/" }).setAdapter(adapterFunction());
|
|
13
|
+
client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
14
|
+
});
|
|
15
|
+
|
|
16
|
+
it("should return data available for endpoint", async () => {
|
|
17
|
+
const req = client.createRequest<{ response: Tea[] }>()({
|
|
18
|
+
endpoint: "",
|
|
19
|
+
method: "get",
|
|
20
|
+
});
|
|
21
|
+
const { data, extra, status, success, error } = await req.send();
|
|
22
|
+
expect(data).toHaveLength(10);
|
|
23
|
+
expect(data[0]).toHaveProperty("__key");
|
|
24
|
+
expect(extra).toHaveProperty("snapshot");
|
|
25
|
+
expect(extra).toHaveProperty("ref");
|
|
26
|
+
expect(status).toBe("success");
|
|
27
|
+
expect(success).toBe(true);
|
|
28
|
+
expect(error).toBe(null);
|
|
29
|
+
});
|
|
30
|
+
it("should return data for dynamic endpoint", async () => {
|
|
31
|
+
const req = client
|
|
32
|
+
.createRequest<{ response: Tea }>()({
|
|
33
|
+
endpoint: ":teaId",
|
|
34
|
+
method: "get",
|
|
35
|
+
})
|
|
36
|
+
.setParams({ teaId: 1 });
|
|
37
|
+
|
|
38
|
+
const { data } = await req.send();
|
|
39
|
+
expect(data).toStrictEqual({ amount: 150, name: "Taiping Hou Kui", origin: "China", type: "Green", year: 2023 });
|
|
40
|
+
});
|
|
41
|
+
it("should return emptyResource status for non existing resource", async () => {
|
|
42
|
+
const req = clientBees
|
|
43
|
+
.createRequest<{ response: Tea }>()({
|
|
44
|
+
endpoint: ":teaId",
|
|
45
|
+
method: "get",
|
|
46
|
+
})
|
|
47
|
+
.setParams({ teaId: 1 });
|
|
48
|
+
|
|
49
|
+
const { data, status } = await req.send();
|
|
50
|
+
expect(data).toStrictEqual(null);
|
|
51
|
+
expect(status).toStrictEqual("emptyResource");
|
|
52
|
+
});
|
|
53
|
+
it("should emit lifecycle events", async () => {
|
|
54
|
+
const req = clientBees
|
|
55
|
+
.createRequest<{ response: Tea }>()({
|
|
56
|
+
endpoint: ":teaId",
|
|
57
|
+
method: "get",
|
|
58
|
+
})
|
|
59
|
+
.setParams({ teaId: 1 });
|
|
60
|
+
|
|
61
|
+
await testLifecycleEvents(req);
|
|
62
|
+
});
|
|
63
|
+
});
|
|
64
|
+
};
|
|
@@ -0,0 +1,190 @@
|
|
|
1
|
+
/* eslint-disable max-params */
|
|
2
|
+
import { Socket } from "@hyper-fetch/sockets";
|
|
3
|
+
import { Client } from "@hyper-fetch/core";
|
|
4
|
+
import waitForExpect from "wait-for-expect";
|
|
5
|
+
|
|
6
|
+
import { FirebaseAdminAdapterTypes, FirebaseAdminSocketAdapterTypes } from "adapter";
|
|
7
|
+
import { Tea } from "../../../../utils";
|
|
8
|
+
|
|
9
|
+
export const onValueTestSuite = (
|
|
10
|
+
db: Promise<any>,
|
|
11
|
+
seedDb: (initializedDb: any) => Promise<void>,
|
|
12
|
+
socketsAdapter: (database: any) => FirebaseAdminSocketAdapterTypes<any>,
|
|
13
|
+
coreAdapter: (database: any) => FirebaseAdminAdapterTypes<any>,
|
|
14
|
+
) => {
|
|
15
|
+
describe("when using onValue method", () => {
|
|
16
|
+
let initializedSocketsAdapter: any;
|
|
17
|
+
let initializedCoreAdapter: any;
|
|
18
|
+
let initializedDb: any;
|
|
19
|
+
let spy = jest.fn();
|
|
20
|
+
const newData = { origin: "Poland", type: "Green", year: 2043, name: "Pou Ran Do Cha", amount: 100 } as Tea;
|
|
21
|
+
|
|
22
|
+
beforeAll(async () => {
|
|
23
|
+
initializedDb = await db;
|
|
24
|
+
initializedSocketsAdapter = socketsAdapter(initializedDb);
|
|
25
|
+
initializedCoreAdapter = coreAdapter(initializedDb);
|
|
26
|
+
});
|
|
27
|
+
|
|
28
|
+
beforeEach(async () => {
|
|
29
|
+
await seedDb(initializedDb);
|
|
30
|
+
});
|
|
31
|
+
|
|
32
|
+
const initialize = async () => {
|
|
33
|
+
const client = new Client({ url: "teas/" }).setAdapter(initializedCoreAdapter);
|
|
34
|
+
const socket = new Socket({ url: "teas/", adapter: initializedSocketsAdapter });
|
|
35
|
+
const pushReq = client
|
|
36
|
+
.createRequest<{ response: Tea; payload: Tea }>()({
|
|
37
|
+
endpoint: "",
|
|
38
|
+
method: "push",
|
|
39
|
+
})
|
|
40
|
+
.setPayload(newData);
|
|
41
|
+
const socketBees = new Socket({ url: "bees/", adapter: initializedSocketsAdapter });
|
|
42
|
+
|
|
43
|
+
return { client, socket, pushReq, socketBees };
|
|
44
|
+
};
|
|
45
|
+
|
|
46
|
+
beforeEach(() => {
|
|
47
|
+
jest.resetAllMocks();
|
|
48
|
+
jest.clearAllMocks();
|
|
49
|
+
spy = jest.fn();
|
|
50
|
+
});
|
|
51
|
+
|
|
52
|
+
it("should return unmount function", async () => {
|
|
53
|
+
const { socket } = await initialize();
|
|
54
|
+
const onValueReq = socket.createListener<Tea[]>()({
|
|
55
|
+
topic: "",
|
|
56
|
+
});
|
|
57
|
+
const unmount = onValueReq.listen(spy);
|
|
58
|
+
expect(unmount).toBeFunction();
|
|
59
|
+
});
|
|
60
|
+
|
|
61
|
+
it("should unmount listeners", async () => {
|
|
62
|
+
const { socket, pushReq } = await initialize();
|
|
63
|
+
const onValueReq = socket.createListener<Tea[]>()({
|
|
64
|
+
topic: "",
|
|
65
|
+
});
|
|
66
|
+
const unmount = onValueReq.listen(spy);
|
|
67
|
+
|
|
68
|
+
await waitForExpect(async () => {
|
|
69
|
+
expect(spy).toHaveBeenCalledTimes(1);
|
|
70
|
+
});
|
|
71
|
+
|
|
72
|
+
unmount();
|
|
73
|
+
|
|
74
|
+
await pushReq.send();
|
|
75
|
+
await pushReq.send();
|
|
76
|
+
|
|
77
|
+
await waitForExpect(async () => {
|
|
78
|
+
expect(spy).toHaveBeenCalledTimes(1);
|
|
79
|
+
}, 1000);
|
|
80
|
+
|
|
81
|
+
expect(socket.adapter.listeners.get(onValueReq.topic)?.size).toBe(0);
|
|
82
|
+
});
|
|
83
|
+
|
|
84
|
+
it("should return emptyResource status", async () => {
|
|
85
|
+
const { socketBees } = await initialize();
|
|
86
|
+
const onValueReq = socketBees.createListener<Tea[]>()({
|
|
87
|
+
topic: "",
|
|
88
|
+
options: { onlyOnce: false },
|
|
89
|
+
});
|
|
90
|
+
|
|
91
|
+
let receivedData: any;
|
|
92
|
+
let receivedExtra: any;
|
|
93
|
+
|
|
94
|
+
const unmount = onValueReq.listen(({ data, extra }) => {
|
|
95
|
+
spy();
|
|
96
|
+
receivedData = data;
|
|
97
|
+
receivedExtra = extra;
|
|
98
|
+
});
|
|
99
|
+
|
|
100
|
+
await waitForExpect(async () => {
|
|
101
|
+
expect(spy).toHaveBeenCalled();
|
|
102
|
+
expect(receivedData).toBeNull();
|
|
103
|
+
expect(receivedExtra.status).toBe("emptyResource");
|
|
104
|
+
});
|
|
105
|
+
|
|
106
|
+
unmount();
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
it("should be called once with onlyOnce option", async () => {
|
|
110
|
+
const { socket, pushReq } = await initialize();
|
|
111
|
+
const onValueReq = socket.createListener<Tea[]>()({
|
|
112
|
+
topic: "",
|
|
113
|
+
options: { onlyOnce: true },
|
|
114
|
+
});
|
|
115
|
+
|
|
116
|
+
const unmount = onValueReq.listen(spy);
|
|
117
|
+
|
|
118
|
+
await pushReq.send();
|
|
119
|
+
|
|
120
|
+
await waitForExpect(async () => {
|
|
121
|
+
expect(spy).toHaveBeenCalledTimes(1);
|
|
122
|
+
});
|
|
123
|
+
|
|
124
|
+
unmount();
|
|
125
|
+
});
|
|
126
|
+
|
|
127
|
+
it("should receive updates", async () => {
|
|
128
|
+
const { socket, pushReq } = await initialize();
|
|
129
|
+
|
|
130
|
+
const onValueReq = socket.createListener<Tea[]>()({
|
|
131
|
+
topic: "",
|
|
132
|
+
options: { onlyOnce: false },
|
|
133
|
+
});
|
|
134
|
+
|
|
135
|
+
let receivedData: any;
|
|
136
|
+
let receivedExtra: any;
|
|
137
|
+
|
|
138
|
+
const unmount = onValueReq.listen(({ data, extra }) => {
|
|
139
|
+
spy();
|
|
140
|
+
receivedData = data;
|
|
141
|
+
receivedExtra = extra;
|
|
142
|
+
});
|
|
143
|
+
|
|
144
|
+
const { data } = await pushReq.send();
|
|
145
|
+
|
|
146
|
+
await waitForExpect(async () => {
|
|
147
|
+
expect(receivedData).toIncludeAllMembers([{ ...newData, __key: data?.__key }]);
|
|
148
|
+
expect(receivedExtra).toHaveProperty("snapshot");
|
|
149
|
+
expect(receivedExtra).toHaveProperty("status");
|
|
150
|
+
expect(receivedExtra).toHaveProperty("ref");
|
|
151
|
+
expect(receivedExtra.status).toBe("success");
|
|
152
|
+
});
|
|
153
|
+
|
|
154
|
+
unmount();
|
|
155
|
+
});
|
|
156
|
+
|
|
157
|
+
it("should return data available for doc", async () => {
|
|
158
|
+
const { socket } = await initialize();
|
|
159
|
+
const onValueReq = socket
|
|
160
|
+
.createListener<Tea[]>()({
|
|
161
|
+
topic: ":teaId",
|
|
162
|
+
})
|
|
163
|
+
.setParams({ teaId: 1 });
|
|
164
|
+
|
|
165
|
+
let receivedData: any;
|
|
166
|
+
let receivedExtra: any;
|
|
167
|
+
const unmount = onValueReq.listen(({ data, extra }) => {
|
|
168
|
+
spy();
|
|
169
|
+
receivedData = data;
|
|
170
|
+
receivedExtra = extra;
|
|
171
|
+
});
|
|
172
|
+
|
|
173
|
+
await waitForExpect(async () => {
|
|
174
|
+
expect(receivedData).toStrictEqual({
|
|
175
|
+
__key: "1",
|
|
176
|
+
amount: 150,
|
|
177
|
+
name: "Taiping Hou Kui",
|
|
178
|
+
origin: "China",
|
|
179
|
+
type: "Green",
|
|
180
|
+
year: 2023,
|
|
181
|
+
});
|
|
182
|
+
expect(receivedExtra).toHaveProperty("snapshot");
|
|
183
|
+
expect(receivedExtra).toHaveProperty("ref");
|
|
184
|
+
expect(receivedExtra.status).toBe("success");
|
|
185
|
+
});
|
|
186
|
+
|
|
187
|
+
unmount();
|
|
188
|
+
});
|
|
189
|
+
});
|
|
190
|
+
};
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
import { Client } from "@hyper-fetch/core";
|
|
2
|
+
|
|
3
|
+
import { FirebaseAdminAdapter } from "adapter";
|
|
4
|
+
import { testLifecycleEvents } from "../../../../shared/request-events.shared";
|
|
5
|
+
import { Tea } from "../../../../utils";
|
|
6
|
+
|
|
7
|
+
export const pushTestSuite = (adapterFunction: () => ReturnType<typeof FirebaseAdminAdapter>) => {
|
|
8
|
+
describe("push", () => {
|
|
9
|
+
let client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
10
|
+
beforeEach(() => {
|
|
11
|
+
client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
12
|
+
});
|
|
13
|
+
|
|
14
|
+
it("should allow for adding data to a list", async () => {
|
|
15
|
+
const newData = { origin: "Poland", type: "Green", year: 2023, name: "Pou Ran Do Cha", amount: 100 } as Tea;
|
|
16
|
+
const getReq = client.createRequest<{ response: Tea[] }>()({
|
|
17
|
+
endpoint: "",
|
|
18
|
+
method: "getDoc",
|
|
19
|
+
});
|
|
20
|
+
const pushReq = client
|
|
21
|
+
.createRequest<{ response: Tea; payload: Tea }>()({
|
|
22
|
+
endpoint: "",
|
|
23
|
+
method: "setDoc",
|
|
24
|
+
options: {},
|
|
25
|
+
})
|
|
26
|
+
.setPayload(newData);
|
|
27
|
+
const { data: pushedData, extra } = await pushReq.send();
|
|
28
|
+
const { data } = await getReq.send();
|
|
29
|
+
|
|
30
|
+
expect(data).toHaveLength(11);
|
|
31
|
+
expect(data).toContainEqual({ ...newData, __key: pushedData?.__key });
|
|
32
|
+
expect(extra).toHaveProperty("key");
|
|
33
|
+
});
|
|
34
|
+
it("should emit lifecycle events", async () => {
|
|
35
|
+
const newData = { origin: "Poland", type: "Green", year: 2043, name: "Pou Ran Do Cha", amount: 100 } as Tea;
|
|
36
|
+
|
|
37
|
+
const pushReq = client
|
|
38
|
+
.createRequest<{ response: Tea; payload: Tea }>()({
|
|
39
|
+
endpoint: "teas/",
|
|
40
|
+
method: "setDoc",
|
|
41
|
+
options: {},
|
|
42
|
+
})
|
|
43
|
+
.setPayload(newData);
|
|
44
|
+
|
|
45
|
+
await testLifecycleEvents(pushReq);
|
|
46
|
+
});
|
|
47
|
+
});
|
|
48
|
+
};
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import { Client } from "@hyper-fetch/core";
|
|
2
|
+
|
|
3
|
+
import { FirebaseAdminAdapter } from "adapter";
|
|
4
|
+
import { testLifecycleEvents } from "../../../../shared/request-events.shared";
|
|
5
|
+
import { Tea } from "../../../../utils";
|
|
6
|
+
|
|
7
|
+
export const removeTestSuite = (adapterFunction: () => ReturnType<typeof FirebaseAdminAdapter>) => {
|
|
8
|
+
let client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
9
|
+
beforeEach(() => {
|
|
10
|
+
client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
11
|
+
});
|
|
12
|
+
describe("remove", () => {
|
|
13
|
+
it("should allow for removing data", async () => {
|
|
14
|
+
const getReq = client
|
|
15
|
+
.createRequest<{ response: Tea }>()({
|
|
16
|
+
endpoint: ":teaId",
|
|
17
|
+
method: "getDoc",
|
|
18
|
+
})
|
|
19
|
+
.setParams({ teaId: 1 });
|
|
20
|
+
|
|
21
|
+
const removeReq = client
|
|
22
|
+
.createRequest<{ response: Tea }>()({
|
|
23
|
+
endpoint: ":teaId",
|
|
24
|
+
method: "deleteDoc",
|
|
25
|
+
})
|
|
26
|
+
.setParams({ teaId: 1 });
|
|
27
|
+
|
|
28
|
+
await removeReq.send();
|
|
29
|
+
const { data, extra } = await getReq.send();
|
|
30
|
+
expect(data).toBe(null);
|
|
31
|
+
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
|
|
32
|
+
// @ts-ignore
|
|
33
|
+
expect(extra?.snapshot?.exists()).toBe(false);
|
|
34
|
+
});
|
|
35
|
+
it("should emit lifecycle events", async () => {
|
|
36
|
+
const removeReq = client
|
|
37
|
+
.createRequest<{ response: Tea }>()({
|
|
38
|
+
endpoint: ":teaId",
|
|
39
|
+
method: "deleteDoc",
|
|
40
|
+
})
|
|
41
|
+
.setParams({ teaId: 1 });
|
|
42
|
+
|
|
43
|
+
await testLifecycleEvents(removeReq);
|
|
44
|
+
});
|
|
45
|
+
});
|
|
46
|
+
};
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { Client } from "@hyper-fetch/core";
|
|
2
|
+
|
|
3
|
+
import { FirebaseAdminAdapter } from "adapter";
|
|
4
|
+
import { testLifecycleEvents } from "../../../../shared/request-events.shared";
|
|
5
|
+
import { Tea } from "../../../../utils";
|
|
6
|
+
|
|
7
|
+
export const setTestSuite = (adapterFunction: () => ReturnType<typeof FirebaseAdminAdapter>) => {
|
|
8
|
+
describe("set", () => {
|
|
9
|
+
let client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
10
|
+
beforeEach(() => {
|
|
11
|
+
client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
12
|
+
});
|
|
13
|
+
it("should set data", async () => {
|
|
14
|
+
const newData = { origin: "Poland", type: "Green", year: 2023, name: "Pou Ran Do Cha", amount: 10 } as Tea;
|
|
15
|
+
|
|
16
|
+
const getReq = client
|
|
17
|
+
.createRequest<{ response: Tea }>()({
|
|
18
|
+
endpoint: ":teaId",
|
|
19
|
+
method: "get",
|
|
20
|
+
})
|
|
21
|
+
.setParams({ teaId: 1 });
|
|
22
|
+
const setReq = client
|
|
23
|
+
.createRequest<{ response: Tea; payload: Tea }>()({
|
|
24
|
+
endpoint: ":teaId",
|
|
25
|
+
method: "set",
|
|
26
|
+
})
|
|
27
|
+
.setParams({ teaId: 1 })
|
|
28
|
+
.setPayload(newData);
|
|
29
|
+
|
|
30
|
+
await setReq.send();
|
|
31
|
+
const { data, extra } = await getReq.send();
|
|
32
|
+
expect(data).toStrictEqual(newData);
|
|
33
|
+
expect(extra.snapshot.exists()).toBe(true);
|
|
34
|
+
});
|
|
35
|
+
it("should allow for removing data via set", async () => {
|
|
36
|
+
const getReq = client
|
|
37
|
+
.createRequest<{ response: Tea }>()({
|
|
38
|
+
endpoint: ":teaId",
|
|
39
|
+
method: "get",
|
|
40
|
+
})
|
|
41
|
+
.setParams({ teaId: 1 });
|
|
42
|
+
|
|
43
|
+
const setReq = client
|
|
44
|
+
.createRequest<Tea, { data: null }>()({
|
|
45
|
+
endpoint: ":teaId",
|
|
46
|
+
method: "set",
|
|
47
|
+
})
|
|
48
|
+
.setParams({ teaId: 1 })
|
|
49
|
+
.setPayload({ data: null });
|
|
50
|
+
|
|
51
|
+
await setReq.send();
|
|
52
|
+
const { data, extra } = await getReq.send();
|
|
53
|
+
expect(data).toBe(null);
|
|
54
|
+
expect(extra.snapshot.exists()).toBe(false);
|
|
55
|
+
});
|
|
56
|
+
it("should emit lifecycle events", async () => {
|
|
57
|
+
const setReq = client
|
|
58
|
+
.createRequest<Tea, { data: null }>()({
|
|
59
|
+
endpoint: ":teaId",
|
|
60
|
+
method: "set",
|
|
61
|
+
})
|
|
62
|
+
.setParams({ teaId: 1 })
|
|
63
|
+
.setPayload({ data: null });
|
|
64
|
+
|
|
65
|
+
await testLifecycleEvents(setReq);
|
|
66
|
+
});
|
|
67
|
+
});
|
|
68
|
+
};
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { Client } from "@hyper-fetch/core";
|
|
2
|
+
|
|
3
|
+
import { FirebaseAdminAdapter } from "adapter";
|
|
4
|
+
import { testLifecycleEvents } from "../../../../shared/request-events.shared";
|
|
5
|
+
import { Tea } from "../../../../utils/seed/seed.data";
|
|
6
|
+
|
|
7
|
+
export const updateTestSuite = (adapterFunction: () => ReturnType<typeof FirebaseAdminAdapter>) => {
|
|
8
|
+
describe("update", () => {
|
|
9
|
+
let client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
10
|
+
beforeEach(() => {
|
|
11
|
+
client = new Client({ url: "teas/" }).setAdapter(adapterFunction());
|
|
12
|
+
});
|
|
13
|
+
|
|
14
|
+
it("should allow for updating data", async () => {
|
|
15
|
+
const newData = { name: "Pou Ran Do Cha", amount: 100, year: 966 } as Tea;
|
|
16
|
+
const updateReq = client
|
|
17
|
+
.createRequest<{ response: Tea; payload: Tea }>()({
|
|
18
|
+
endpoint: ":teaId",
|
|
19
|
+
method: "updateDoc",
|
|
20
|
+
})
|
|
21
|
+
.setPayload(newData);
|
|
22
|
+
const getReq = client.createRequest<{ response: Tea }>()({
|
|
23
|
+
endpoint: ":teaId",
|
|
24
|
+
method: "getDoc",
|
|
25
|
+
});
|
|
26
|
+
await updateReq.send({ params: { teaId: 1 } });
|
|
27
|
+
const { data } = await getReq.send({ params: { teaId: 1 } });
|
|
28
|
+
expect(data).toStrictEqual({ ...newData, origin: "China", type: "Green" });
|
|
29
|
+
});
|
|
30
|
+
it("should emit lifecycle events", async () => {
|
|
31
|
+
const newData = { name: "Pou Ran Do Cha", amount: 100, year: 966 } as Tea;
|
|
32
|
+
|
|
33
|
+
const updateReq = client
|
|
34
|
+
.createRequest<{ response: Tea; payload: Tea }>()({
|
|
35
|
+
endpoint: ":teaId",
|
|
36
|
+
method: "updateDoc",
|
|
37
|
+
})
|
|
38
|
+
.setPayload(newData);
|
|
39
|
+
await testLifecycleEvents(updateReq);
|
|
40
|
+
});
|
|
41
|
+
});
|
|
42
|
+
};
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
/* eslint-disable max-params */
|
|
2
|
+
import { FirebaseAdminAdapter, FirebaseAdminAdapterTypes, FirebaseAdminSocketAdapterTypes } from "adapter";
|
|
3
|
+
import { getTestSuite } from "./methods/get.test.suite";
|
|
4
|
+
import { setTestSuite } from "./methods/set.test.suite";
|
|
5
|
+
import { pushTestSuite } from "./methods/push.test.suite";
|
|
6
|
+
import { updateTestSuite } from "./methods/update.test.suite";
|
|
7
|
+
import { removeTestSuite } from "./methods/remove.test.suite";
|
|
8
|
+
import { onValueTestSuite } from "./methods/on-value.test.suite";
|
|
9
|
+
|
|
10
|
+
export const methodsSharedTestCases = (adapterFunction: () => ReturnType<typeof FirebaseAdminAdapter>) => {
|
|
11
|
+
getTestSuite(adapterFunction);
|
|
12
|
+
setTestSuite(adapterFunction);
|
|
13
|
+
pushTestSuite(adapterFunction);
|
|
14
|
+
updateTestSuite(adapterFunction);
|
|
15
|
+
removeTestSuite(adapterFunction);
|
|
16
|
+
};
|
|
17
|
+
|
|
18
|
+
export const socketsMethodsSharedTestCases = (
|
|
19
|
+
db: any,
|
|
20
|
+
seedDbMethod: (db: any) => Promise<void>,
|
|
21
|
+
socketsAdapter: (database: any) => FirebaseAdminSocketAdapterTypes<any>,
|
|
22
|
+
coreAdapter: (database: any) => FirebaseAdminAdapterTypes<any>,
|
|
23
|
+
) => {
|
|
24
|
+
onValueTestSuite(db, seedDbMethod, socketsAdapter, coreAdapter);
|
|
25
|
+
};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import "jest-extended";
|