I noticed I have gotten used to write some pieces of code in certain way for reason or another. Sometimes the focus is in the specific pattern, sometimes it's in the formatting and cosmetics. This collection of templates aims to work as a memory-refreshener paste-board. Also, I think it's fun to have a way to document what I actually think is the canonical way to do it (in my opinion).
Usage: Copy snippets, find and replace TODO
s.
// TODO: Add disclaimer and general remarks, if applicable | |
// Imports here | |
// TODO: Add interfaces and types here | |
/** | |
* [ClassName] - Represents [what the class models or does]. | |
* | |
* This class is used for [explain purpose/use case]. It provides [mention key functionality]. | |
* Use this class when [describe when it's useful]. | |
* | |
* TODO: Rename class | |
* TODO: Rewrite description | |
* TODO: Remove sections that does not have content | |
*/ | |
export class MyCustomClass { | |
// ─────────────────────────────────────── | |
// Public properties | |
// ─────────────────────────────────────── | |
// ─────────────────────────────────────── | |
// Private properties | |
// ─────────────────────────────────────── | |
// ─────────────────────────────────────── | |
// Constructor | |
// ─────────────────────────────────────── | |
constructor() { | |
// TODO: Rename class | |
} | |
// ─────────────────────────────────────── | |
// Public methods | |
// ─────────────────────────────────────── | |
// ─────────────────────────────────────── | |
// Private methods | |
// ─────────────────────────────────────── | |
} | |
// --> TODO: Add additional helpers here |
/** | |
* TODO: Add disclaimer and general remarks, if applicable | |
*/ | |
// --> TODO: Add imports here | |
// --> TODO: Add interfaces and types here | |
/** | |
* [ClassName] - Represents [what the class models or does]. | |
* | |
* This class is used for [explain purpose/use case]. It provides [mention key functionality]. | |
* Use this class when [describe when it's useful]. | |
* | |
* TODO: Rename class | |
* TODO: Rewrite description | |
* TODO: Remove sections that does not have content | |
*/ | |
export class MyCustomSingleton { | |
// ─────────────────────────────────────── | |
// Private static properties | |
// ─────────────────────────────────────── | |
private static _instance: MyCustomSingleton; | |
// ─────────────────────────────────────── | |
// Public properties | |
// ─────────────────────────────────────── | |
// ─────────────────────────────────────── | |
// Private properties | |
// ─────────────────────────────────────── | |
// ─────────────────────────────────────── | |
// Constructor | |
// ─────────────────────────────────────── | |
private constructor() { | |
// TODO: Rename class | |
} | |
// ================================ | |
// Singleton accessor | |
// ================================ | |
/** | |
* Returns the singleton instance of MyCustomSingleton. | |
* If the instance doesn't exist, it creates one. | |
* TODO: add instantiation parameters if needed | |
*/ | |
public static getInstance(): MyCustomSingleton { | |
if (!MyCustomSingleton._instance) { | |
MyCustomSingleton._instance = new MyCustomSingleton(); | |
} | |
return MyCustomSingleton._instance; | |
} | |
// ================================ | |
// Public methods | |
// ================================ | |
// ================================ | |
// Private methods | |
// ================================ | |
} | |
// TODO: Add helper functions here |
// TODO: Add disclaimer and general remarks, if applicable | |
// TODO: Add imports here | |
// TODO: Add interfaces and types here | |
// MyCustomExplicitSingleton is a clean, maintainable TypeScript class following the singleton pattern. | |
// TODO: Rewrite description | |
// TODO: Rename class | |
export class MyCustomExplicitSingleton { | |
// ================================ | |
// Private Static Properties | |
// ================================ | |
private static _instance: MyCustomExplicitSingleton; | |
// ================================ | |
// Public Properties | |
// ================================ | |
// ================================ | |
// Private Properties | |
// ================================ | |
// ================================ | |
// Constructor | |
// ================================ | |
private constructor() { | |
// TODO: Rename class | |
} | |
// ================================ | |
// Singleton Accessors | |
// ================================ | |
// Returns the singleton instance of MyCustomExplicitSingleton. | |
public static getInstance(): MyCustomExplicitSingleton { | |
if (!MyCustomExplicitSingleton._instance) { | |
throw new Error( | |
"Instance has not been created yet and constructor parameters are missing." | |
); | |
} | |
return MyCustomExplicitSingleton._instance; | |
} | |
// Creates the singleton instance of MyCustomExplicitSingleton. | |
// Makes it more explicit from user point of view where the instance is created. | |
public static createInstance(): MyCustomExplicitSingleton { | |
if (MyCustomExplicitSingleton._instance) { | |
return MyCustomExplicitSingleton._instance; | |
} | |
MyCustomExplicitSingleton._instance = new MyCustomExplicitSingleton(); | |
return MyCustomExplicitSingleton._instance; | |
} | |
// ================================ | |
// Public Methods | |
// ================================ | |
// ================================ | |
// Private Methods | |
// ================================ | |
} | |
// TODO: Add helper functions here |
// ================================ | |
// Event Bus with Typed ACK Support | |
// ================================ | |
type Listener<Data, Ack> = (data: Data) => Ack | Promise<Ack>; | |
type EventMap = Record<string, { data: unknown; ack: unknown }>; | |
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
// TODO (for whoever uses this): Define Events with ACK Types | |
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | |
interface Events extends EventMap { | |
userJoined: { data: { userId: string; name: string }; ack: string }; // ACK is a string | |
messageReceived: { | |
data: { message: string; sender: string }; | |
ack: boolean; | |
}; // ACK is a boolean | |
} | |
const listeners: { | |
[K in keyof Events]?: Listener<Events[K]["data"], Events[K]["ack"]>[]; | |
} = {}; | |
function on<K extends keyof Events>( | |
event: K, | |
callback: Listener<Events[K]["data"], Events[K]["ack"]> | |
): void { | |
if (!listeners[event]) { | |
listeners[event] = []; | |
} | |
listeners[event]!.push(callback); | |
} | |
async function emit<K extends keyof Events>( | |
event: K, | |
data: Events[K]["data"] | |
): Promise<Events[K]["ack"][]> { | |
if (!listeners[event]) return []; | |
const responses = listeners[event]!.map((cb) => cb(data)); | |
return await Promise.all(responses); | |
} | |
export { on, emit }; |
let count: number | null = null; | |
function init(): void { | |
count = 0; | |
} | |
function increment(): void { | |
if (count) { | |
count++; | |
} | |
} | |
function decrement(): void { | |
if (count) { | |
count--; | |
} | |
} | |
function getCount(): number { | |
if (!count) { | |
throw new Error("Count has not been defined!"); | |
} | |
return count; | |
} | |
export { init, increment, decrement, getCount }; |
function createUser(name: string, age: number) { | |
let score = 0; | |
return { | |
name, | |
age, | |
incrementScore(): void { | |
score++; | |
}, | |
getScore(): number { | |
return score; | |
}, | |
}; | |
} | |
// Usage | |
const user = createUser("Alice", 25); | |
user.incrementScore(); | |
log(`User Score: ${user.getScore()}`); // 1 |
function createSecureUser<T extends { username: string; password: string }>( | |
user: T | |
): Omit<T, "password"> & { password: string } { | |
return new Proxy(user, { | |
get(target, prop: keyof T) { | |
if (prop === "password") return "***"; | |
return target[prop]; | |
}, | |
}); | |
} | |
// Usage | |
const secureUser = createSecureUser({ username: "admin", password: "secret" }); | |
log(`Username: ${secureUser.username}`); // "admin" | |
log(`Password: ${secureUser.password}`); // "\*\*\*" |