10import { NotebookView } from "./NotebookView.tsx";
11
12const API_BASE = "/api/memories";
13const MEMORIES_PER_PAGE = 20; // Increased from 7 to 20 memories per page
14
90
91 // Fetch avatar image
92 fetch("/api/images/stevens.jpg")
93 .then((response) => {
94 if (response.ok) return response.blob();
104
105 // Fetch wood background
106 fetch("/api/images/wood.jpg")
107 .then((response) => {
108 if (response.ok) return response.blob();
133 setError(null);
134 try {
135 const response = await fetch(API_BASE);
136 if (!response.ok) {
137 throw new Error(`HTTP error! status: ${response.status}`);
176
177 try {
178 const response = await fetch(API_BASE, {
179 method: "POST",
180 headers: { "Content-Type": "application/json" },
199
200 try {
201 const response = await fetch(`${API_BASE}/${id}`, {
202 method: "DELETE",
203 });
231
232 try {
233 const response = await fetch(`${API_BASE}/${editingMemory.id}`, {
234 method: "PUT",
235 headers: { "Content-Type": "application/json" },
606 <div className="font-pixel text-[#f8f1e0]">
607 <style jsx>{`
608 @import url("https://fonts.googleapis.com/css2?family=Pixelify+Sans&display=swap");
609
610 @tailwind base;
8import { type Memory } from "../../shared/types.ts";
9
10const API_BASE = "/api/memories";
11const MEMORIES_PER_PAGE = 20;
12
71 setError(null);
72 try {
73 const response = await fetch(API_BASE);
74 if (!response.ok) {
75 throw new Error(`HTTP error! status: ${response.status}`);
100
101 try {
102 const response = await fetch(API_BASE, {
103 method: "POST",
104 headers: { "Content-Type": "application/json" },
123
124 try {
125 const response = await fetch(`${API_BASE}/${id}`, {
126 method: "DELETE",
127 });
155
156 try {
157 const response = await fetch(`${API_BASE}/${editingMemory.id}`, {
158 method: "PUT",
159 headers: { "Content-Type": "application/json" },
53You'll need to set up some environment variables to make it run.
54
55- `ANTHROPIC_API_KEY` for LLM calls
56- You'll need to follow [these instructions](https://docs.val.town/integrations/telegram/) to make a telegram bot, and set `TELEGRAM_TOKEN`. You'll also need to get a `TELEGRAM_CHAT_ID` in order to have the bot remember chat contents.
57- For the Google Calendar integration you'll need `GOOGLE_CALENDAR_ACCOUNT_ID` and `GOOGLE_CALENDAR_CALENDAR_ID`. See [these instuctions](https://www.val.town/v/stevekrouse/pipedream) for details.
1const baseUrl = "https://api.neynar.com/v2/farcaster/";
2
3export async function fetchNeynarGet(path: string) {
7 "Content-Type": "application/json",
8 "x-neynar-experimental": "true",
9 "x-api-key": "NEYNAR_API_DOCS",
10 },
11 });
19 }));
20
21app.get("/api/counter/get", async c => c.json(await db.get("counter")));
22app.get("/api/counter/increment", async c => c.json(await db.set("counter", (await db.get("counter") || 0) + 1)));
23
24app.get("/frontend/**/*", c => serveFile(c.req.path, import.meta.url));
84
85const loadEmoji = (code) => {
86 // const api = `https://cdnjs.cloudflare.com/ajax/libs/twemoji/14.0.2/svg/${code.toLowerCase()}.svg`
87 const api = `https://cdn.jsdelivr.net/gh/shuding/fluentui-emoji-unicode/assets/${code.toLowerCase()}_color.svg`;
88 return fetch(api).then((r) => r.text());
89};
90
53 <div className="">✷ Farcaster mini app manifest + webhook + embed metadata</div>
54 <div className="">✷ Farcaster notifications (storing tokens, sending recurring notifications, ...)</div>
55 <div className="">✷ Neynar API integration for Farcaster data</div>
56 <div className="">✷ Hosted on Val Town (instant deployments on save)</div>
57 <div className="">
67
68function Database() {
69 const queryFn = () => fetch("/api/counter/get").then((r) => r.json());
70 const { data, refetch } = useQuery({ queryKey: ["counter"], queryFn });
71 return (
73 {/* <h2 className="font-semibold">Database Example</h2> */}
74 <div className="">Counter value: {data}</div>
75 <Button variant="outline" onClick={() => fetch("/api/counter/increment").then(refetch)}>
76 Increment
77 </Button>
2import { serveFile, readFile } from "https://esm.town/v/std/utils@85-main/index.ts";
3import { setupDatabase } from "./database/migrations";
4import apiRoutes from "./routes/api";
5
6// Initialize the Hono app
33});
34
35// Mount API routes
36app.route("/api", apiRoutes);
37
38// Serve static files
46
47 // Get initial data for the frontend
48 const response = await apiRoutes.fetch(
49 new Request("http://localhost/api/tools", { method: "GET" }),
50 c.env
51 );
1import { useState, useEffect } from "react";
2
3const USER_ENDPOINT = "/api/user";
4
5export function useUser() {
20 SUM(num_images) as total_images
21 FROM ${USAGE_TABLE}
22 WHERE our_api_token = 1
23 GROUP BY user_id, username
24 ORDER BY total_price DESC