1/** @jsxImportSource https://esm.sh/hono@4.0.8/jsx **/
2
3import { modifyFetchHandler } from "https://esm.town/v/andreterron/codeOnValTown?v=50";
4import view_route from "https://esm.town/v/pomdtr/blob_admin_blob";
5import create_route from "https://esm.town/v/pomdtr/blob_admin_create";
137});
138
139export default modifyFetchHandler(passwordAuth(app.fetch));
1import { email } from "https://esm.town/v/std/email";
2import { fetchJSON } from "https://esm.town/v/stevekrouse/fetchJSON";
3
4export async function dailyDadJoke() {
5 let { setup, punchline } = await fetchJSON("https://official-joke-api.appspot.com/random_joke");
6 return email({
7 text: punchline,
1// This val implements a function to call the Claude API using fetch.
2// It handles the API request and response processing.
3// The Claude API key is expected to be provided in the request headers.
76
77 try {
78 const response = await fetch(url, {
79 method: "POST",
80 headers: headers,
11 }
12
13 const readmeVals: any = await (await fetch("https://janpaul123-readmevals.web.val.run/")).json();
14
15 const API_URL = "https://api.val.town";
69 );
70 });
71 export default app.fetch;`,
72 },
73 {
129 {
130 prompt: "Write a val that accesses environment variables",
131 code: `const res = await fetch("${API_URL}/v1/me", {
132 headers: {
133 Authorization: \`Bearer \${Deno.env.get("valtown")}\`,
141 code: `import process from "node:process";
142
143 const res = await fetch("${API_URL}/v1/me", {
144 headers: {
145 Authorization: \`Bearer \${process.env.valtown}\`,
165 code: `import cheerio from "npm:cheerio";
166
167 const response = await fetch("https://example.com");
168 const body = await response.text();
169 const $ = cheerio.load(body);
453 {
454 role: "user",
455 content: "Write a val that fetches the weather in Brooklyn, NY",
456 },
457 {
458 role: "assistant",
459 content:
460 "```ts\nexport default async function(req: Request): Promise<Response> {\n const apiKey = Deno.env.get(\"METEO_KEY\");\n const apiUrl = `https://api.open-meteo.com/v1/forecast?latitude=40.6782&longitude=-73.9442&hourly=temperature_2m¤t_weather=true&apikey=${apiKey}`;\n\n const response = await fetch(apiUrl);\n const weatherData = await response.json();\n\n return new Response(JSON.stringify(weatherData), { headers: { \"Content-Type\": \"application/json\" } });\n}\n```",
461 },
462 {
467 role: "assistant",
468 content:
469 "```ts\n/** @jsxImportSource npm:hono@3/jsx */\nimport { Hono } from \"npm:hono\";\n\nconst app = new Hono();\napp.get(\"/\", async (c) => {\n return c.html(\n <div>\n <form>\n Your name: <input type=\"text\" name=\"name\" /> <input type=\"submit\" />\n </form>\n Hello {c.req.query(\"name\")}\n </div>,\n );\n});\nexport default app.fetch;\n```",
470 },
471 ...templatePrompts,
128 }
129
130 // Fetch recent requests
131 const requests = await sqlite.execute(`
132 SELECT id, method, url, timestamp
1# Live reload in new tabs
2
3When you're working on an HTML HTTP val in a new tab, it's annoying to have to manually reload the tab on every save. In the Val Town editor, you can hit cmd+enter, but there's nothing like that for a val in a new tab because Val Town doesn't control that new tab (like we control the iframe in the browser preview). However, you control that HTML via the fetch handler you're writing, so you can add a script that polls the Val Town API for the current version number of your val, and reload itself if it detects a new version. This val has a collection of helpers to help you do just that.
4
5## Usage
7```ts
8import { html } from "https://esm.town/v/stevekrouse/html";
9import { reloadOnSaveFetchMiddleware } from "https://esm.town/v/stevekrouse/reloadOnSave";
10
11export default reloadOnSaveFetchMiddleware(async function(req: Request): Promise<Response> {
12 return html(`<h1>Hello!!</h1>`);
13})
37
38/**
39 * @param handler http val's fetch handler
40 * @param vals to watch
41 */
42export function reloadOnSaveFetchMiddleware(
43 handler: (req: Request) => Response | Promise<Response>,
44 vals = [rootValRef()],
24
25 useEffect(() => {
26 fetchVotes();
27 }, []);
28
29 const fetchVotes = async () => {
30 try {
31 const response = await fetch("/votes");
32 const data = await response.json();
33 console.log("Fetched votes:", data);
34 setVotes(data);
35 } catch (error) {
36 console.error("Error fetching votes:", error);
37 }
38 };
41 console.log("Voting for location:", locationId);
42 try {
43 const response = await fetch("/vote", {
44 method: "POST",
45 headers: { "Content-Type": "application/json" },
156 `);
157 const votes = Object.fromEntries(result.rows.map(row => [row.location_id, row.count]));
158 console.log("Fetched votes:", votes);
159 return new Response(JSON.stringify(votes), {
160 headers: { "Content-Type": "application/json" },
161 });
162 } catch (error) {
163 console.error("Error fetching votes:", error);
164 return new Response(JSON.stringify({ error: error.message }), {
165 status: 500,
24
25 useEffect(() => {
26 fetchScrapsAndGenerateSummary(currentWeek);
27 updateUrlState(currentWeek);
28 }, [currentWeek]);
29
30 const fetchScrapsAndGenerateSummary = async (weekStart: Date) => {
31 setLoading(true);
32 setSummary("");
35 try {
36 setDebugInfo(
37 prev => [...prev, `Fetching scraps and generating summary for week of ${weekStart.toDateString()}...`],
38 );
39 const response = await fetch(`/api/summary?week=${weekStart.toISOString()}`);
40 const data = await response.json();
41
46 setDebugInfo(prev => [
47 ...prev,
48 `Fetched ${data.scrapCount} scraps for the week of ${weekStart.toDateString()}`,
49 "Summary generated successfully",
50 ]);
52 setMetadata(data.metadata);
53 } catch (error) {
54 console.error("Error fetching summary:", error);
55 setDebugInfo(prev => [...prev, `Error: ${error.message}`]);
56 setSummary("Error generating summary. Please check the debug information and try again later.");
177
178 if (error) {
179 return new Response(JSON.stringify({ error: "Error fetching scraps: " + error.message }), {
180 status: 500,
181 headers: { "Content-Type": "application/json" },
9export default async function notify() {
10 try {
11 // Fetch and parse the RSS feed
12 const rss = await Parse.parse("https://medium.com/feed/@admiralcloudberg");
13