1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
import { blob } from "https://esm.town/v/std/blob";
export default async function(req: Request): Promise<Response> {
let img_title = "cover";
let button_state = "START";
if (req.method === "POST") {
const body = await req.json();
const fid = body.untrustedData.fid;
const key = `powerscards2-${fid}`;
const buttonIdx = body.untrustedData.buttonIndex;
const fidData = await blob.getJSON(key);
if (!fidData) {
// start new game
img_title = "00-q";
button_state = "ASK";
await blob.setJSON(key, {
last_seen: img_title,
cards: ["00", "01", "02", "03", "04", "05", "06", "07", "08", "09", "10", "11", "12"],
});
} else { // seen this gamer before
if (!fidData.cards.length) {
button_state = "DONE";
img_title = "wowow";
} else {
// check if its checking answers or ready to show next one
const [card_number, card_state] = fidData.last_seen.split("-");
if (card_state === "q") {
img_title = `${card_number}-a`;
button_state = "SHOW_ANSWER";
await blob.setJSON(key, { last_seen: img_title, cards: fidData.cards });
// if card state is answer
} else if (buttonIdx === 2 && card_number) { // right!
let remaining = fidData.cards.filter(el => el !== card_number);
if (!remaining.length) {
button_state = "DONE";
img_title = "wowow";
} else {
button_state = "ASK";
img_title = `${remaining[Math.floor(Math.random() * remaining.length)]}-q`;
}
await blob.setJSON(key, { last_seen: img_title, cards: remaining });
} else if (buttonIdx === 1 && card_number) { // wrong
button_state = "ASK";
img_title = `${fidData.cards[Math.floor(Math.random() * fidData.cards.length)]}-q`;
await blob.setJSON(key, { last_seen: img_title, cards: fidData.cards });
}
}
}
}
const url = `https://whatrocks.github.io/powers-of-2-frame/${img_title}.jpg`;
let button = `<meta property="fc:frame:button:1" content="Start Learning" />`;
if (button_state === "ASK") {
button = `<meta property="fc:frame:button:1" content="Reveal" />`;
}
if (button_state === "SHOW_ANSWER") {
button =
`<meta property="fc:frame:button:1" content="I got it wrong!" /><meta property="fc:frame:button:2" content="Got it right!" />`;
}
if (button_state === "DONE") {
button = ``;
}
const htmlContent = `
<!DOCTYPE html>
<html>
<head>
<meta property="og:title" content="Powers of 2 Frame" />
<meta property="og:image" content=${url} />
<meta property="fc:frame" content="vNext" />
<meta property="fc:frame:image" content="${url}" />
${button}
</head>
<body>
<h1>Learn the powers of 2, in a frame!</h1>
</body>
</html>
`;
return new Response(htmlContent, {
status: 200,
headers: {
"Content-Type": "text/html; charset=utf-8",
},
});
}
👆 This is a val. Vals are TypeScript snippets of code, written in the browser and run on our servers. Create scheduled functions, email yourself, and persist small pieces of data — all from the browser.