Search

Results include substring matches and semantically similar vals. Learn more
gwoods22 avatar
aws_eventbridge_toggler
@gwoods22
AWS EventBridge Toggler Script that allows you to enable and disable AWS EventBridge rules Setup In AWS go to the IAM and create a new IAM user for Val Town On the Set permissions page, choose the permissions you require. To get this Val up and running you can attach the AmazonEventBridgeFullAccess policy but it's recommended to limit your permissions. The following policy allows for reading and toggling any EventBridge rule: { "Version": "2012-10-17", "Statement": [ { "Sid": "VisualEditor0", "Effect": "Allow", "Action": [ "events:DescribeRule", "events:EnableRule", "events:DisableRule" ], "Resource": "*" } ] } Finally add your AWS region as well as yourAccess Key ID and Secret Access Key from your IAM user to Val Town's environment variables as AWS_REGION , AWS_ACCESS_KEY_ID , and AWS_SECRET_ACCESS_KEY
Script
EnableRuleCommand,
EventBridgeClient,
} from "npm:@aws-sdk/client-eventbridge@3.678.0";
// Allow Deno to pickup AWS_ACCESS_KEY_ID and AWS_SECRET_ACCESS_KEY environment variables
export default async (ruleName: string, enableRule: boolean = true) => {
const eventBridgeClient = new EventBridgeClient({
region: Deno.env.get("AWS_REGION") ?? "",
try {
const toggleResult = await eventBridgeClient.send(toggleCommand);
if (toggleResult.$metadata.httpStatusCode !== 200) {
throw new Error("Failed to toggle rule");
return await eventBridgeClient.send(describeCommand);
} catch (error) {
drew_kuhn avatar
inventiveVioletDinosaur
@drew_kuhn
With our data designed, let’s build the email! Val Town makes this super easy since it provides a robust email package. The package exports a function by the same name (email) which consumes an object. When called with properly formatted parameters, an email will be sent to the address associated with your Val Town account. “Good” emails need some kind of hook to draw the reader’s attention. What better hook than our joke’s setup? Add an email() function call to your Val which sends an email with the setup as its subject and the punchline as its body text. import { email } from "https://esm.town/v/std/email?v=9"; // Fetches a random joke. function fetchRandomJoke() { const SAMPLE_JOKE = { "setup": "What do you call a group of disorganized cats?", "punchline": "A cat-tastrophe.", }; return SAMPLE_JOKE; } const randomJoke = fetchRandomJoke(); const setup = randomJoke.setup; const punchline = randomJoke.punchline; // Sends an email with the joke. export const emailRandomJoke = email({ text: punchline, subject: setup, }); Notice that this data is being passed in as key-value pairs since it is inside of an object. There is only one parameter (that object) passed into the function. Save and evaluate your val by clicking the “Run” button at the top right.
Script
subject: setup,
Notice that this data is being passed in as key-value pairs since it is inside of an object. There is only one parameter (tha
Save and evaluate your val by clicking the “Run” button at the top right.
ktodaz avatar
getGPTResponse
@ktodaz
Get a response from GPT for the player.
Script
"The Hell Let Loose gods have shined upon you today.",
"Don't get too cocky now ;)",
"Time to get outside ;)",
if (playerRank == 2) {
if (Math.random() < 0.6) {
"The Hell Let Loose gods have shined upon you today.",
"Don't get too cocky now ;)",
"Time to get outside ;)",
if (playerRank <= 3)
message += "Congratulations!";
liamdanielduffy avatar
MAXIMUM_VAL_SIZE
@liamdanielduffy
// We ran into a bug where the entirety of React DOM minified would not fit into a val as a string. IS this a max string size? Is it a max val size? Who knows.
Script
export const MAXIMUM_VAL_SIZE = "???";
// We ran into a bug where the entirety of React DOM minified would not fit into a val as a string. IS this a max string size
seflless avatar
parseAmazonOrderEmail
@seflless
// await sqlite.execute(`CREATE TABLE IF NOT EXISTS AmazonOrders3(
Script
return date;
// Database Admin
// https://libsqlstudio.com/client/s/valtown?p=d7880ed3-ad63-4258-a939-5a375f2c3ed8
// Run this to see full table
// select key, description, orderId, orderLink, amount, orderDate from AmazonOrders3
robsimmons avatar
dusa_assertion
@robsimmons
An interactive, runnable TypeScript val by robsimmons
Script
import { Dusa } from "https://unpkg.com/dusa@0.1.6/lib/client.js";
const dusa = new Dusa(`
path X Y :- edge X Y.
pdebie avatar
getLemmyPosts
@pdebie
Fetches the 20 active posts in a community from a specific Lemmy instance.
Script
export async function getLemmyPosts(instance: string, communityName: string) {
const { LemmyHttp } = await import("npm:lemmy-js-client");
let client = new LemmyHttp(`https://${instance}`, {
fetchFunction: fetch,
const { posts } = await client.getPosts({
community_name: communityName,
robsimmons avatar
solutions_enumerate
@robsimmons
An interactive, runnable TypeScript val by robsimmons
Script
import { Dusa } from "https://unpkg.com/dusa@0.1.6/lib/client.js";
const dusa = new Dusa(`name is { "one", "two" }.`);
for (const solution of dusa) {
jxnblk avatar
IndirectionAPI
@jxnblk
// Test without using this?
Script
import { DataRequest } from "https://esm.town/v/jxnblk/ReactStream";
const LENGTH = 128;
const MAX_TOKENS = 512;
stevekrouse avatar
dlock
@stevekrouse
dlock - free distributed lock as a service https://dlock.univalent.net/ Usage API Acquire a lock. The id path segment is the lock ID - choose your own. https://dlock.univalent.net/lock/arbitrary-string/acquire?ttl=60 {"lease":1,"deadline":1655572186} Another attempt to acquire the same lock within its TTL will fail with HTTP status code 409. https://dlock.univalent.net/lock/01899dc0-2742-44f9-9c7b-01830851b299/acquire?ttl=60 {"error":"lock is acquired by another client","deadline":1655572186} The previous lock can be renewed with its lease number, like a heartbeat https://dlock.univalent.net/lock/01899dc0-2742-44f9-9c7b-01830851b299/acquire?ttl=60&lease=1 {"lease":1,"deadline":1655572824} Release a lock https://dlock.univalent.net/lock/01899dc0-2742-44f9-9c7b-01830851b299/release?lease=42
Script
https://dlock.univalent.net/lock/01899dc0-2742-44f9-9c7b-01830851b299/acquire?ttl=60
{"error":"lock is acquired by another client","deadline":1655572186}
### The previous lock can be renewed with its lease number, like a heartbeat
robsimmons avatar
aoc_2023_9
@robsimmons
An interactive, runnable TypeScript val by robsimmons
Script
import { Dusa } from "https://unpkg.com/dusa@0.0.10/lib/client.js";
const INPUT = `
0 3 6 9 12 15
stevekrouse avatar
karma
@stevekrouse
An interactive, runnable TypeScript val by stevekrouse
Script
Of everyone you burned just to get there
It's coming back around
And I keep my side of the street clean
You wouldn't know what I mean
'Cause karma is my boyfriend
Don't you know that cash ain't the only price?
It's coming back around
And I keep my side of the street clean
You wouldn't know what I mean
'Cause karma is my boyfriend
liamdanielduffy avatar
REACT_DOM_MINIFIED_PT3
@liamdanielduffy
// set by liamdanielduffy.buildReactDomMinified at 2023-06-01T12:04:43.666Z
Script
// set by liamdanielduffy.buildReactDomMinified at 2023-06-01T12:04:43.666Z
export let REACT_DOM_MINIFIED_PT3 = "st=d,f.tail=c,f.tailMode=e)}function xi(a,b,c){var d=b.pendingProps,e=d.revealOrder,f=d.
xkonti avatar
cache
@xkonti
Implementation of Redis-like cache - a key-value store with expiring keys. Data is stored in the Val Town SQLite database and shared between all your vals. Setup First you should decide on a name of a SQL table that will be used for storing cache data. It could something like cacheData or kv . Set that value to a new Environment Variable CACHE_TABLE_NAME . Optionally you might add a new CACHE_DEFAULT_TTL Environment Variable. It's value should be set to a number of seconds that will be used when saving new values to the cache without providing the expiration time. By default it's 24h. The setup() function should be ran before using the cache for the first time. You can do that by creating a small temporary Val: import { setup } from "https://esm.town/v/xkonti/cache"; await setup(); Optionally create a scheduled val that will delete expired keys on some interval - 15 minutes can be a good start. import { deleteExpired } from "https://esm.town/v/xkonti/cache"; export default async function cacheCleaner(interval: Interval) { await deleteExpired(); } Usage After setting your cache up you can use it simply by importing functions from https://esm.town/v/xkonti/cache . set(key, value, ttl): Promise Set a value in the cache. key - the key to set the value for value - the value to set - it can be any value that can be serialized to JSON ttl - the time to live in seconds. In other words, after how many seconds the key will expire. If not set, the default TTL is used. returns the number of keys set: 1 if the key was inserted/updated, 0 if the ttl was 0 or invalid // Set a value in the cache with a default TTL await set("luckyNumber", 13); // Set a value that will expire in 5 minutes await set("product:344798", { name: "Audio Interface", price: 209.99}, 5 * 60); setUntil(key, value, expiresAt): Promise Set a value in the cache until a specific date and time. key - the key to set the value for value - the value to set - it can be any value that can be serialized to JSON expiresAt - the expiration time as a UTC date string returns the number of keys set: 1 if the key was inserted/updated, 0 if the `expiresAt`` was in the past // Set a value in the cache until 2024-01-01 16:23:05 UTC await setUntil( "product:155392", { name: "Audio Interface", price: 209.99 }, new Date('2024-01-01T16:23:05Z').toISOString() ); setExpiration(key, ttl): Promise Update the expiration date of a cache entry based on TTL. If the key does not exist or is expired, nothing happens. key - the key of the cache entry to update ttl - the time to live in seconds from now. In other words, after how many seconds the key will expire. If not set, the default TTL is used. returns the number of keys updated: 1 if updated, 0 if not found or ttl was 0 // Set the expiration date in the cache with a default TTL await setExpiration("luckyNumber"); // Set the expiration date in the cache for 5 minutes from now. await setExpiration("luckyNumber", 5 * 60); setExpirationUntil(key, expiresAt): Promise Update the expiration date of a cache entry to a specific UTC date and time. If the key does not exist or is expired, nothing happens. key - the key of the cache entry to update expiresAt - the expiration time as a UTC date string returns the number of keys updated: 1 if updated, 0 if not found or expiresAt was in the past // Set the expiration date in the cache until 2024-01-01 16:23:05 UTC await setExpirationUntil( "product:155392", new Date('2024-01-01T16:23:05Z').toISOString() ); exists(key): Promise Checks if the provided key exists (has value) in the cache. If the key is expired, it's considered non-existent. key - the key to check for existence // Check if the key is present in the cache const hasLuckyNumber: Boolean = await exists("luckyNumber"); get (key): Promise<T | null> Get a value from the cache by key. You can provide a type of the return value or it will default to unknown . If there is no value for the key or the value has expired, null is returned. key - the key to get the value for // Get a value from the cache const luckyNumber: number = await get<number>("luckyNumber"); const luckyNumber: number = await get("luckyNumber") as number; // same as above listKeys(prefix): Promise<string[]> Gets a list of all non-expired keys in the cache that match the prefix. If no prefix is provided, all keys are returned. prefix - the optional prefix to match keys against // Get all keys from the cache const keys: string[] = await listKeys(); // Get all keys from the cache that start with "product:" const keys: string[] = await listKeys("product:"); getMany (prefix, limit): Promise<Array<{ key: string, value: T }>> Get many key-value pairs from the cache that match the given prefix. prefix - the optional prefix to match keys against. If not provided, all keys are considered. limit - the optional maximum number of key-value pairs to return. If 0 , no limit is applied. Defaults to 0 . returns An array of key-value pairs. Each pair is an object with key and value properties. // Get all non-expired keys and their values const everything = await getMany(); // Get all keys and values with a matching prefix const allProducts = await getMany("product:"); // Get 5 keys and values with a matching prefix const discountedProducts = await getMany("discounts:", 5); deleteKey(key): Promise Delete a key from the cache. key - the key to delete returns the number of keys deleted: 1 if the key was deleted, 0 if the key did not exist. // Delete a key from the cache await deleteKey("luckyNumber"); deleteKeys(prefix): Promise Delete all keys from the cache that match the prefix. If no prefix is provided, all keys in the cache are deleted. prefix - the optional prefix to match keys against returns the number of keys deleted // Delete all keys from the cache await deleteKeys(); // Delete all keys from the cache that start with "product:" await deleteKeys("product:"); deleteExpired(): Promise Delete all expired keys from the cache. Perfect for running on a schedule to keep the cache small and fast. returns the number of keys deleted // Delete all expired keys from the cache await deleteExpired();
Script
## exists(key): Promise<Boolean>
Checks if the provided key exists (has value) in the cache. If the key is expired, it's considered non-existent.
- `key` - the key to check for existence
Get many key-value pairs from the cache that match the given prefix.
- `prefix` - the optional prefix to match keys against. If not provided, all keys are considered.
- `limit` - the optional maximum number of key-value pairs to return. If `0`, no limit is applied. Defaults to `0`.
* Check if the provided key exists (has value) in the cache.
* If the key is expired, it's considered non-existent.
* @param key The key to check if exists
* Get many key-value pairs from the cache that match the given prefix.
* @param prefix The prefix to match keys against. If not provided, all keys are considered.
* @param limit The maximum number of key-value pairs to return. If 0, no limit is applied.
janpaul123 avatar
semanticSearchTurso
@janpaul123
Part of Val Town Semantic Search . Uses Turso to search embeddings of all vals, using the sqlite-vss extension. Call OpenAI to generate an embedding for the search query. Query the vss_vals_embeddings table in Turso using vss_search . The vss_vals_embeddings table has been generated by janpaul123/indexValsTurso . It is not run automatically. This table is incomplete due to a bug in Turso .
Script
import { decode as base64Decode, encode as base64Encode } from "https://deno.land/std@0.166.0/encoding/base64.ts";
import { createClient } from "https://esm.sh/@libsql/client@0.6.0/web";
import { sqlToJSON } from "https://esm.town/v/nbbaier/sqliteExportHelpers?v=22";
import { db as allValsDb } from "https://esm.town/v/sqlite/db?v=9";
import OpenAI from "npm:openai";
export default async function semanticSearchPublicVals(query) {
const sqlite = createClient({
url: "libsql://valsembeddings-jpvaltown.turso.io",
authToken: Deno.env.get("TURSO_AUTH_TOKEN_VALSEMBEDDINGS"),