Val Town Code SearchReturn to Val Town

API Access

You can access search results via JSON API by adding format=json to your query:

https://codesearch.val.run/?q=api&page=20&format=json

For typeahead suggestions, use the /typeahead endpoint:

https://codesearch.val.run/typeahead?q=api

Returns an array of strings in format "username" or "username/projectName"

Found 4213 results for "api"(323ms)

Glancerexample-callout.ts1 match

@bradnoble•Updated 4 days ago
7// Initialize Notion client
8const notion = new Client({
9 auth: Deno.env.get("NOTION_API_KEY"),
10});
11

filterValsmain.tsx1 match

@nbbaier•Updated 4 days ago
3export async function filterVals(id: string, filter: (value: any, index: number, array: any[]) => unknown) {
4 const token = Deno.env.get("valtown");
5 const res = await fetchPaginatedData(`https://api.val.town/v1/users/${id}/vals`, {
6 headers: { Authorization: `Bearer ${token}` },
7 });

filterValsmain.tsx1 match

@dcm31•Updated 4 days ago
3export async function filterVals(id: string, filter: (value: any, index: number, array: any[]) => unknown) {
4 const token = Deno.env.get("valtown");
5 const res = await fetchPaginatedData(`https://api.val.town/v1/users/${id}/vals`, {
6 headers: { Authorization: `Bearer ${token}` },
7 });

blob_adminmain.tsx6 matches

@recklessreticence•Updated 4 days ago
15
16// Public route without authentication
17app.get("/api/public/:id", async (c) => {
18 const key = `__public/${c.req.param("id")}`;
19 const { blob } = await import("https://esm.town/v/std/blob");
133};
134
135app.get("/api/blobs", checkAuth, async (c) => {
136 const prefix = c.req.query("prefix") || "";
137 const limit = parseInt(c.req.query("limit") || "20", 10);
142});
143
144app.get("/api/blob", checkAuth, async (c) => {
145 const key = c.req.query("key");
146 if (!key) return c.text("Missing key parameter", 400);
150});
151
152app.put("/api/blob", checkAuth, async (c) => {
153 const key = c.req.query("key");
154 if (!key) return c.text("Missing key parameter", 400);
159});
160
161app.delete("/api/blob", checkAuth, async (c) => {
162 const key = c.req.query("key");
163 if (!key) return c.text("Missing key parameter", 400);
167});
168
169app.post("/api/blob", checkAuth, async (c) => {
170 const { file, key } = await c.req.parseBody();
171 if (!file || !key) return c.text("Missing file or key", 400);

blob_adminapp.tsx19 matches

@recklessreticence•Updated 4 days ago
70 const menuRef = useRef(null);
71 const isPublic = blob.key.startsWith("__public/");
72 const publicUrl = isPublic ? `${window.location.origin}/api/public/${encodeURIComponent(blob.key.slice(9))}` : null;
73
74 useEffect(() => {
234 setLoading(true);
235 try {
236 const response = await fetch(`/api/blobs?prefix=${encodeKey(searchPrefix)}&limit=${limit}`);
237 const data = await response.json();
238 setBlobs(data);
261 setBlobContentLoading(true);
262 try {
263 const response = await fetch(`/api/blob?key=${encodeKey(clickedBlob.key)}`);
264 const content = await response.text();
265 setSelectedBlob({ ...clickedBlob, key: decodeKey(clickedBlob.key) });
275 const handleSave = async () => {
276 try {
277 await fetch(`/api/blob?key=${encodeKey(selectedBlob.key)}`, {
278 method: "PUT",
279 body: editContent,
287 const handleDelete = async (key) => {
288 try {
289 await fetch(`/api/blob?key=${encodeKey(key)}`, { method: "DELETE" });
290 setBlobs(blobs.filter(b => b.key !== key));
291 if (selectedBlob && selectedBlob.key === key) {
304 const key = `${searchPrefix}${file.name}`;
305 formData.append("key", encodeKey(key));
306 await fetch("/api/blob", { method: "POST", body: formData });
307 const newBlob = { key, size: file.size, lastModified: new Date().toISOString() };
308 setBlobs([newBlob, ...blobs]);
326 try {
327 const fullKey = `${searchPrefix}${key}`;
328 await fetch(`/api/blob?key=${encodeKey(fullKey)}`, {
329 method: "PUT",
330 body: "",
341 const handleDownload = async (key) => {
342 try {
343 const response = await fetch(`/api/blob?key=${encodeKey(key)}`);
344 const blob = await response.blob();
345 const url = window.URL.createObjectURL(blob);
360 if (newKey && newKey !== oldKey) {
361 try {
362 const response = await fetch(`/api/blob?key=${encodeKey(oldKey)}`);
363 const content = await response.blob();
364 await fetch(`/api/blob?key=${encodeKey(newKey)}`, {
365 method: "PUT",
366 body: content,
367 });
368 await fetch(`/api/blob?key=${encodeKey(oldKey)}`, { method: "DELETE" });
369 setBlobs(blobs.map(b => b.key === oldKey ? { ...b, key: newKey } : b));
370 if (selectedBlob && selectedBlob.key === oldKey) {
380 const newKey = `__public/${key}`;
381 try {
382 const response = await fetch(`/api/blob?key=${encodeKey(key)}`);
383 const content = await response.blob();
384 await fetch(`/api/blob?key=${encodeKey(newKey)}`, {
385 method: "PUT",
386 body: content,
387 });
388 await fetch(`/api/blob?key=${encodeKey(key)}`, { method: "DELETE" });
389 setBlobs(blobs.map(b => b.key === key ? { ...b, key: newKey } : b));
390 if (selectedBlob && selectedBlob.key === key) {
399 const newKey = key.slice(9); // Remove "__public/" prefix
400 try {
401 const response = await fetch(`/api/blob?key=${encodeKey(key)}`);
402 const content = await response.blob();
403 await fetch(`/api/blob?key=${encodeKey(newKey)}`, {
404 method: "PUT",
405 body: content,
406 });
407 await fetch(`/api/blob?key=${encodeKey(key)}`, { method: "DELETE" });
408 setBlobs(blobs.map(b => b.key === key ? { ...b, key: newKey } : b));
409 if (selectedBlob && selectedBlob.key === key) {
554 onClick={() =>
555 copyToClipboard(
556 `${window.location.origin}/api/public/${encodeURIComponent(selectedBlob.key.slice(9))}`,
557 )}
558 className="text-blue-400 hover:text-blue-300 text-sm"
577 >
578 <img
579 src={`/api/blob?key=${encodeKey(selectedBlob.key)}`}
580 alt="Blob content"
581 className="max-w-full h-auto"

ValTownBlog2025-04-17-vt-cli.md8 matches

@wolf•Updated 4 days ago
34`vt` is also fast! Operations all happen concurrently whenever possible. Watch 62 files get cloned in 0.17 seconds!
35
36`vt` is still in beta, and we'd love your feedback! Join [the Val Town Discord](https://discord.gg/hd9U4GGB) to leave feedback. Vt is built entirely within Val Town "userspace" (with the public API), and the codebase can be found at <https://github.com/val-town/vt> .
37
38## Try it out!
48![](https://wolf-mermelstein-personal-website.s3.us-east-2.amazonaws.com/b2f61bc1-8402-4192-9a28-6e6458755b80.webp)
49
50Respond yes to the prompt, and ensure you select to create an API key with user read & project read+write permissions.
51
52Then try cloning one of your projects with `vt clone`!
72![Pomdtr's Val Town VScode extension](https://wolf-mermelstein-personal-website.s3.us-east-2.amazonaws.com/pomdtrextension.webp)
73
74One of the very first sight of Val Town "localdev" came with Pomdtr's [Val Town vscode extension](https://marketplace.visualstudio.com/items?itemName=pomdtr.valtown). The extension was pretty straightforward, it hooked into the Val Town API to let you edit your vals locally and then push them to Val Town. It was made pre-project era, so it only supports traditional Vals. VSCode runs on electron, and gives extension developers a lot of power; the extension also offered web previews, and the ability to use Val Town SQL and blobstore.
75
76A bit later, I came along and implemented a fuse file system for Val Town vals, also pre-project era. Fuse is a Linux protocol that lets you implement arbitrary file systems in userspace. By implementing a fuse Val Town file system, all edits locally are instantly reflected on the Val Town website, and vice versa (if you update remotely, then if you try to save locally your editor will say something along the lines of "more recent edits found, are you sure you want to write"). Fuse is very powerful -- writes, reads, and all other file system syscalls can be handled with whatever response you want.
90We decided to rewrite it mostly for compatibility reasons. Linux offers native fuse support, but MacOS and Windows definitely do not. For Mac, there's a project called [MacFuse](https://macfuse.github.io/) that acts as a kernel extension to provide fuse support to Mac. However, it's not totally stable, and [Apple is deprecating kernel extensions](https://developer.apple.com/support/kernel-extensions/) and it may not be the best long term solution. There's a really cool project called [fuse-t](https://www.fuse-t.org/) that takes a different approach, where it implements the fuse protocol by forwarding fuse to NFS (network file system), a protocol that Macs do naively support.
91
92One idea we had to avoid dealing with fuse was to build a generic FTP server, largely inspired by Pomdtr's [Webdav](https://www.val.town/x/pomdtr/webdav/code/webdav.ts) server. His server works totally in userspace and maps the Val Town API to Webdav really nicely. [Webdav](https://en.wikipedia.org/wiki/WebDAV) is a generic "file system" ish (it's quite limited) protocol over HTTP, and making a FTP server would just be implementing on a fancier file transfer protocol that's more capable. What's nice about using protocols like these is that you can then just use `rclone` for mounting or syncing.
93
94In addition to compatibility issues, implementing a fuse backend is just plain complicated. The way `valfs` worked, on [every write syscall](https://github.com/404Wolf/valfs/blob/418eff73b080fe8cdb7fe7f7afd3fe30dbae2720/valfs/vals/valfile.go#L116C1-L153C2), `valfs` would have to parse the file, extract metadata, and do multiple API calls. Even though `vt` is a total rewrite, many design choices for `vt` came from `vtfs`, like considerations on how we handle metadata, the notion that "a val is a file," and more.
95
96At its core, `vt` was built to be a decentralized synchronization tool. Unlike `vtfs`, where the sync is guaranteed and live, syncing happens asynchronously with `vt` (even when "live syncing" with `vt watch`, which is only "psudo-live" since you could create conflicts by updating state on the website while watching). We rebuilt `vt` in typescript with `Deno`, because, well, we (and our community) love typescript and Deno, there's an official [typescript sdk](https://docs.val.town/api/sdk/) for Val Town, and because we have hopes of turning `vt` into a esm library in the future (so you can use `vt` in your own, non-val-town workflows).
97
98We originally wanted to host `vt` itself on Val Town, where we would begin development with git and github, and then eventually transition to using `vt` itself to continue development of `vt` (bootstrapping!).
141One of the most important use cases of `vt` is "watch" functionality. There's a lot of reasons for this. One of the big ones is that, as you (and maybe your favorite LLM) edit your code locally, it is really handy to remove the friction of syncing with Val Town.
142
143From the beginning, my plan for this was to implement "git" behavior first (pushing and pulling), and then just doing file system watching to add live syncing using [Deno.watchFs](https://docs.deno.com/api/deno/~/Deno.watchFs) to handle file system events.
144
145![](https://wolf-mermelstein-personal-website.s3.us-east-2.amazonaws.com/7f2ed32c-8fc4-4f5c-86ed-733402383d14.webp)
222I spent a long time working on setting up a pipe where I would handle consecutive writes, writes that start at index i, end at index i+k, and then a new write that starts at index i+k+1, etc, as a special case. Eventually, I got something working!
223
224For `vtfs` I was using [Openapi Generator](https://github.com/OpenAPITools/openapi-generator), and it turned out that Val Town's OpenAPI specification didn't accept file sizes on the order of my tests -- where the response would include the file size, it was an integer, not a `format: int64` (long).
225
226![Working piped blob uploads](https://wolf-mermelstein-personal-website.s3.us-east-2.amazonaws.com/hashesMatch.webp)

ValTownForNotion1webhookAPI0 matches

@charmaine•Updated 4 days ago
1import { Hono } from "npm:hono@3";
2// import { cors } from "npm:hono@3/cors";
3
4// Import route modules
5import auth from "./routes/auth.ts";

ValTownForNotion1root.ts1 match

@charmaine•Updated 4 days ago
9
10 const content = {
11 headline: "👋 Welcome to the root API endpoint of this Hono app, running on val.town",
12 message: "Find more detail in the README.",
13 url: notionURL,

ValTownForNotion1resets4 matches

@charmaine•Updated 4 days ago
4// Initialize Notion client
5const notion = new Client({
6 auth: Deno.env.get("NOTION_API_KEY"),
7});
8
37 // the block exists, so you can do the reset
38
39 // reset via the API
40 // this way we keep the notion data and the blob data (our cache) in sync
41 // the API resets the blocks on notion pages, and also knows what to do with the blob
42 // (note the x-blob-key header)
43 if (content != "default" && diffInMinutes > .5) {
48 "x-asking-for": "default",
49 "x-blob-key": item.key,
50 "x-api-key": Deno.env.get("X_API_KEY"),
51 },
52 body: JSON.stringify({

ValTownForNotion1README.md1 match

@charmaine•Updated 4 days ago
12## Handling Notion Webhooks
13
14This is done in the webhookAPI file.
15
16## Resetting state

PassphraseAPI2 file matches

@wolf•Updated 19 hours ago

openapi2 file matches

@stevekrouse•Updated 3 days ago
artivilla
founder @outapint.io vibe coding on val.town. dm me to build custom vals: https://artivilla.com
fiberplane
Purveyors of Hono tooling, API Playground enthusiasts, and creators of 🪿 HONC 🪿 (https://honc.dev)