Skip to content

Commit f5d2294

Browse files
committedApr 20, 2023
add counter reader
1 parent 69e87c0 commit f5d2294

File tree

7 files changed

+114
-15
lines changed

7 files changed

+114
-15
lines changed
 

‎firestore.rules

+4
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,10 @@ service cloud.firestore {
33
match /databases/{database}/documents {
44
match /{document=**} {
55
allow read, write: if false;
6+
7+
match /counts/{id} {
8+
allow read, write: if true;
9+
}
610
}
711
}
812
}

‎src/App.svelte

+22-10
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
11
<script>
22
import Firebase_Logo_Logomark from "./assets/Firebase_Logo_Logomark.svg";
3+
import ReCaptcha from "./assets/recaptcha_48dp.png";
34
import { initializeApp } from "firebase/app";
4-
import { getFirestore } from "firebase/firestore";
5+
import Counter from "./lib/Counter.svelte";
6+
import CounterReader from "./lib/CounterReader.svelte";
57
68
const firebaseConfig = {
79
apiKey: "AIzaSyAH2JT998LjBxxJO0eX_V5LPAyhhxV2fQQ",
@@ -14,18 +16,31 @@
1416
1517
// Initialize Firebase
1618
const app = initializeApp(firebaseConfig);
17-
const db = getFirestore(app);
1819
</script>
1920

2021
<main>
2122
<div>
2223
<a href="https://firebase.google.com" target="_blank" rel="noreferrer">
23-
<img src={Firebase_Logo_Logomark} class="logo" alt="Firebase Logo" />
24+
<img
25+
src={Firebase_Logo_Logomark}
26+
class="logo firebase"
27+
alt="Firebase Logo"
28+
/>
29+
</a>
30+
<a
31+
href="https://developers.google.com/recaptcha"
32+
target="_blank"
33+
rel="noreferrer"
34+
>
35+
<img src={ReCaptcha} class="logo" alt="Recaptcha Logo" />
2436
</a>
2537
</div>
26-
<h1>Firebase without App Check</h1>
38+
<h1>Firebase with App Check (using reCAPTCHA)</h1>
2739

28-
<div class="card" />
40+
<div class="card">
41+
<Counter {app} />
42+
<CounterReader {app} />
43+
</div>
2944

3045
<p>
3146
Check out <a
@@ -46,10 +61,7 @@
4661
.logo:hover {
4762
filter: drop-shadow(0 0 2em #646cffaa);
4863
}
49-
.logo.svelte:hover {
50-
filter: drop-shadow(0 0 2em #ff3e00aa);
51-
}
52-
.read-the-docs {
53-
color: #888;
64+
.logo.firebase:hover {
65+
filter: drop-shadow(0 0 2em #ffea00fb);
5466
}
5567
</style>

‎src/app.css

+1-1
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,7 @@ button {
5151
border-radius: 8px;
5252
border: 1px solid transparent;
5353
padding: 0.6em 1.2em;
54-
font-size: 1em;
54+
font-size: 3em;
5555
font-weight: 500;
5656
font-family: inherit;
5757
background-color: #1a1a1a;

‎src/assets/no-recaptcha.png

4.34 KB
Loading

‎src/assets/recaptcha_48dp.png

3.09 KB
Loading

‎src/lib/Counter.svelte

+17-4
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,21 @@
11
<script>
2-
let count = 0
3-
const increment = () => {
4-
count += 1
5-
}
2+
export let app;
3+
import { addDoc, collection, getFirestore } from "firebase/firestore";
4+
const db = getFirestore(app);
5+
6+
let count = 0;
7+
const increment = async () => {
8+
count += 1;
9+
try {
10+
const docRef = await addDoc(collection(db, "counts"), {
11+
date: new Date(),
12+
count,
13+
});
14+
console.log("Document written with ID: ", docRef.id);
15+
} catch (e) {
16+
console.error("Error adding document: ", e);
17+
}
18+
};
619
</script>
720

821
<button on:click={increment}>

‎src/lib/CounterReader.svelte

+70
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
<script>
2+
import { onDestroy } from "svelte";
3+
4+
export let app;
5+
import {
6+
collection,
7+
getFirestore,
8+
increment,
9+
onSnapshot,
10+
query,
11+
orderBy,
12+
limit,
13+
Timestamp,
14+
} from "firebase/firestore";
15+
const db = getFirestore(app);
16+
const q = query(collection(db, "counts"), orderBy("date", "desc"), limit(5));
17+
18+
$: counts = [];
19+
20+
const unsubscribe = onSnapshot(q, (querySnapshot) => {
21+
const allCounts = [];
22+
querySnapshot.forEach((doc) => {
23+
allCounts.push({ id: doc.id, ...doc.data() });
24+
});
25+
counts = allCounts;
26+
});
27+
28+
onDestroy(() => {
29+
unsubscribe();
30+
});
31+
</script>
32+
33+
<h2>Last 5</h2>
34+
35+
<section>
36+
{#each counts as count}
37+
<div class="count-container card">
38+
<div><span>ID: </span><span>{count.id}</span></div>
39+
<div>
40+
<span>Time: </span><span
41+
>{count.date.toDate().toLocaleTimeString()}</span
42+
>
43+
</div>
44+
<div><span>Count: </span><span>{count.count}</span></div>
45+
</div>
46+
{/each}
47+
</section>
48+
49+
<style>
50+
section {
51+
display: flex;
52+
justify-content: center;
53+
gap: 0.5rem;
54+
padding: 1rem;
55+
}
56+
.count-container {
57+
display: flex;
58+
flex-direction: column;
59+
align-items: start;
60+
max-width: 300px;
61+
62+
border-radius: 8px;
63+
border: 1px solid transparent;
64+
padding: 0.6em 1.2em;
65+
font-size: 1em;
66+
font-weight: 500;
67+
font-family: inherit;
68+
background-color: #1a1a1a;
69+
}
70+
</style>

0 commit comments

Comments
 (0)
Please sign in to comment.