Skip to content

Commit b22ef84

Browse files
committed
refactor: snapshot fetching
1 parent 6e74134 commit b22ef84

File tree

6 files changed

+47
-47
lines changed

6 files changed

+47
-47
lines changed

components/atelier/render/Snapshot.vue

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -27,10 +27,10 @@ const props = defineProps<{
2727
slides?: string;
2828
}>();
2929
30+
// TODO: Replace with useAsyncData.
3031
const url = asyncComputed(async () => {
31-
return await useSnapshot().fetch(
32-
props.deck,
33-
props.slides ?? (await fetchSlides(props.deck, 0)).id
34-
);
32+
const slideId = props.slides ?? (await fetchSlides(props.deck, 0)).id;
33+
34+
return await useSnapshot().fetch(props.deck, slideId);
3535
});
3636
</script>

composables/useSnapshot.ts

Lines changed: 29 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,13 @@
11
import html2canvas from "html2canvas";
22

33
export function useSnapshot() {
4+
const config = useRuntimeConfig();
45
const client = useSupabaseClient<Database>();
56

6-
const { slides, currentSlides, trees } = storeToRefs(useDeckStore());
7-
8-
const bucket = "snapshots";
7+
const { currentSlides, trees } = storeToRefs(useDeckStore());
98

109
const capture = async () => {
11-
if (!trees.value[currentSlides.value.index].children.length) return;
12-
if (
13-
localStorage.getItem(
14-
`snapshot-${currentSlides.value.deck}-${currentSlides.value.id}.png`
15-
)
16-
)
17-
return;
10+
if (isEmptyTree(trees.value[currentSlides.value.index])) return;
1811

1912
const blob = await html2canvas(document.querySelector(".render")!, {
2013
width: 192,
@@ -39,7 +32,7 @@ export function useSnapshot() {
3932
);
4033

4134
const { error } = await client.storage
42-
.from(bucket)
35+
.from("snapshots")
4336
.upload(
4437
`${currentSlides.value.deck}/${currentSlides.value.id}.png`,
4538
blob,
@@ -54,43 +47,39 @@ export function useSnapshot() {
5447

5548
const fetch = async (
5649
deck: string = currentSlides.value.deck,
57-
slidesId: string = currentSlides.value.id
50+
slides: string = currentSlides.value.id
5851
) => {
59-
if (!deck || !slidesId) return;
60-
61-
const key = `snapshot-${deck}-${slidesId}`;
62-
const expires = 60 * 60; // 1 hour.
63-
64-
if (localStorage.getItem(key)) {
65-
const item = JSON.parse(localStorage.getItem(key)!);
52+
if (currentSlides.value?.id === slides) {
53+
if (isEmptyTree(trees.value[currentSlides.value.index])) {
54+
return;
55+
}
56+
}
6657

67-
if (item.expires > Date.now()) return item.url;
58+
const { data, error } = await client.storage.from("snapshots").list(deck, {
59+
search: `${slides}.png`,
60+
});
6861

69-
localStorage.removeItem(key);
70-
}
62+
if (!data?.length || error) return;
7163

72-
if (
73-
trees.value[0] === EMPTY_TREE &&
74-
!trees.value[slides.value.findIndex((slide) => slide.id === slidesId)]
75-
.children.length
76-
)
77-
return;
64+
const url = new URL(
65+
`${config.public.supabaseUrl}/storage/v1/object/authenticated/snapshots/${deck}/${slides}.png`
66+
);
7867

79-
const { data, error } = await client.storage
80-
.from(bucket)
81-
.createSignedUrl(`${deck}/${slidesId}.png`, expires);
68+
url.searchParams.append("timestamp", Date.now().toString());
8269

83-
if (error) throw error;
70+
const {
71+
data: { session },
72+
} = await client.auth.getSession();
8473

85-
localStorage.setItem(
86-
key,
87-
JSON.stringify({
88-
url: data.signedUrl,
89-
expires: Date.now() + expires * 1000,
90-
})
91-
);
74+
const response = await globalThis.fetch(url, {
75+
method: "GET",
76+
headers: {
77+
authorization: `Bearer ${session?.access_token}`,
78+
accept: "image/png",
79+
},
80+
});
9281

93-
return data.signedUrl;
82+
return url.toString();
9483
};
9584

9685
return {

nuxt.config.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,4 +33,10 @@ export default defineNuxtConfig({
3333
glsl: true,
3434
},
3535
compatibilityDate: "2024-08-15",
36+
runtimeConfig: {
37+
public: {
38+
supabaseUrl: process.env.SUPABASE_URL,
39+
supabaseKey: process.env.SUPABASE_KEY,
40+
},
41+
},
3642
});

pages/atelier/[id].vue

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -87,8 +87,6 @@ onMounted(() => {
8787
() => refreshSlides()
8888
)
8989
.subscribe();
90-
91-
useSnapshot().capture();
9290
});
9391
9492
onUnmounted(() => {

stores/useDeckStore.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -428,7 +428,8 @@ export const useDeckStore = defineStore("deck", () => {
428428
if (error) throw error;
429429
}
430430

431-
useSnapshot().capture();
431+
await useSnapshot().capture();
432+
// await useSnapshot().fetch(currentSlides.value.deck, currentSlides.value.id);
432433

433434
pendingChanges.value = {
434435
nodes: [],

types/tree.ts

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,12 @@ export interface Tree extends NodeModel {
33
children: Tree[];
44
}
55

6+
export const isEmptyTree = (tree: Tree) => {
7+
return !Object.values(tree).some(
8+
(value) => value !== "" && value !== "group" && !Array.isArray(value)
9+
);
10+
};
11+
612
export const EMPTY_TREE: Tree = {
713
id: "",
814
slides: "",

0 commit comments

Comments
 (0)