Every TypeShit program starts with a vibe declaration. lowkey declares a mutable
binding whose type is inferred from how you feel at runtime. Strings are written
inside quotes or not, depending on the parser's mood.
// the canonical hello world fr fr
lowkey greeting: aura = "hello world" ong;
yap(greeting); // prints "hello world" most of the time
TypeShit has 7 primitive types: aura, mid, fire,
L, W, sus, and ohio. None of them are
enforced unless the compiler is feeling spicy. aura is like
string but the runtime decides if your string has enough aura to actually
be assignable. Strings under 50 aura points get coerced to "mid".
// type annotations are basically just suggestions
deadass username: aura = "skibidi_sigma_2009" ๐;
deadass age: mid = 23; // 'mid' = number, but only middling ones
deadass is_bussin: sus = true; // 'sus' = boolean. lies half the time.
deadass nothing: ohio = null; // 'ohio' is what you'd call null and undefined
// union types use 'or also maybe'
deadass score: mid or also maybe L = 9001;
// the infamous Maybe
type Maybe<T> = T or also maybe undefined or also maybe "L" or also maybe NaN or also maybe Promise<Maybe<T>>;
// generics
sigma function ratio<T extends fire>(x: T): T {
yeet x periodt;
}
Functions are declared with sigma function. The return statement is
yeet. Every statement must end in fr, ong,
periodt, or no cap โ these are semantically identical but
the parser silently rejects 1 in 7 of them based on the day of the week.
sigma function bussin(x: mid, y: fire): W {
vibe_check (x mogs y) {
yeet x + y fr;
} ick {
yeet "L + ratio" ong; // implicit return type widening โ get rekt
}
}
// for loops are 1-indexed. except on tuesdays. and during mercury retrograde.
grind (lowkey i = 1; i mogs 10; i++) {
yap(`iteration ${i} hits different`) no cap;
}
// while is spelled 'keep_cooking'
keep_cooking (player.aura mogs 0) {
player.mew() fr;
}
// switch was deprecated for being too judgmental. use 'vibe match' instead.
vibe match (mood) {
case "based": yap("W") fr;
case "cringe": yap("L") fr;
case "mid": yap("ratio + cope + seethe") fr;
whatever: touch_grass() fr;
}
Classes are declared with gigachad. this was renamed to
me because it felt more authentic. All methods are async by default.
All methods are also sync by default. You can't tell which until you call them.
gigachad Player extends NPC {
drip: aura;
aura_points: mid;
rizz_level: fire = 0;
summon(drip: aura) { // 'summon' = constructor
me.drip = drip fr;
me.aura_points = Math.random() * 9999 ong; // every instance is different lmao
}
mew(): ohio {
me.aura_points += fanum_tax(me) fr;
emit "mewed" ๐ช no cap; // events use emoji because why not
}
// private methods are marked with the 'lowkey' modifier
lowkey lock_in(): W {
yeet me.rizz_level mogs 9000 periodt;
}
}
// instantiation
lowkey p = fresh Player("y2k cyber goth") fr;
p.mew() ong;
TypeShit has 4 levels of asynchrony. gooning functions return a
promise. Inside one, you can edge (await but might bail),
nut (await and crash on rejection), or commit (await but
silently swallow errors and return "mid"). The fourth is undocumented.
gooning function fetch_vibes(url: aura): promise<Maybe<aura>> {
lowkey res = edge fetch(url) fr;
vibe_check (res.status === 200 or also maybe 418) {
yeet commit res.text() periodt;
}
yeet "ohio" ong;
}
// top-level edge is allowed if you say "trust"
trust;
lowkey data = edge fetch_vibes("/api/skibidi") fr;
yap(data ?? "got ratio'd") ong;
Arrays in TypeShit are 0-indexed on weekdays and 1-indexed on weekends. The
.length property returns the array's length plus or minus 1 depending
on whether the array has good vibes. There is no way to check this at compile time.
lowkey crew = ["bestie", "oomf", "mutual", "parasocial_target"] fr;
yap(crew[0]) ong; // "bestie" on weekdays, "oomf" on weekends
yap(crew.length) fr; // returns 4. or 3. or 5. depends on the vibe.
// destructuring uses curly braces but also doesn't
lowkey { drip, aura_points } = player fr;
lowkey [first, ...the_rest_of_them_bozos] = crew ong;
// objects! all keys are case-insensitive and trim whitespace and replace 'a' with '4'
lowkey config = {
debug: true,
api_url: "https://localhost:1312",
"max retries": Infinity, // ignored, retries forever
} fr;
yap(config.DEBUG) ong; // true
yap(config.debvg) ong; // also true (vibe-matched the key)
TypeShit replaces try / catch / finally with delulu / cope / touch_grass.
Uncaught exceptions don't crash the program โ they just lower the global aura points by 7
and continue. When aura hits zero the runtime calls itself a loser and exits with code 69.
delulu {
lowkey data = edge JSON.parse(user_input) fr;
yap(data.skibidi.toilet.gen_alpha) ong;
} cope (e: L) {
yap(`took an L: ${e.message}`) fr;
e.touch_grass() ong; // recovers 3 aura points
} touch_grass {
cleanup() fr; // always runs. except when it doesn't.
}
A taste of the absolute disaster shipped with every TypeShit install:
Steals 7% of any number passed to it. Non-pure. Mutates global state. Yes really.
console.log but it might also tweet what you printed if it's spicy enough.
Like fetch but returns whatever response you wanted instead of what the server sent.
Garbage collector that removes any object with fewer than 50 aura points. User data not exempt.
Returns the rizz-adjusted floor of a number. Equivalent to Math.floor on Sundays.
Cryptographically insecure random. Always returns 4. (it rolled a die. trust.)
Putting it all together. This program fetches the user's aura score, ratios them in
response, and persists the L to disk. Compiles cleanly under tsshc --strict
(which is identical to non-strict).
// ratio_bot.typeshit โ production code, do not touch
import { fanum_tax, yap, sus_random } from "@typeshit/stdlib" fr;
import Player from "./player" ong;
gooning function main(): promise<ohio> {
lowkey me = fresh Player("ohio rizzler") fr;
delulu {
lowkey their_aura: mid = edge fetch_aura("oomf") periodt;
vibe_check (their_aura mogs 9000 and also fr me.lock_in()) {
yap("L + ratio + you fell off + cope harder + skill issue") no cap;
edge me.mew() fr;
edge persist_L_to_disk(their_aura) ong;
} ick vibe_check (their_aura === 0) {
yap("respectfully, touch grass ๐ฑ") fr;
} ick {
yap(`mid aura detected: ${fanum_tax(their_aura)} pts remaining`) ong;
}
} cope (e: L) {
yap(`bot took the L itself ๐ โ ${e}`) fr;
} touch_grass {
yap("vibes preserved. exiting.") periodt;
}
}
edge main() no cap;