Last active
June 17, 2021 18:08
-
-
Save sidola/a3397a5580ec5dccdd7299a1552e912d to your computer and use it in GitHub Desktop.
Utility method for dealing with SQLites boolean type in a Typescript codebase
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
type SqliteBool<T extends number | boolean> = T extends number ? boolean : number | |
/** | |
* Converts an sqlite bool (0 or 1) to a real bool, and vice versa. | |
* | |
* @example | |
* sqliteBool(1) // => true | |
* sqliteBool(true) // => 1 | |
*/ | |
export function sqliteBool<T extends number | boolean>(value: T): SqliteBool<T> { | |
// Uses conditional types to flip between the types. | |
// - https://www.typescriptlang.org/docs/handbook/2/conditional-types.html | |
// | |
// Unfortunately the docs conveniently leave out how to implement | |
// a function body using this trick, which is ugly as hell, see | |
// here: | |
// - https://stackoverflow.com/a/67403992 | |
if (typeof value === "number") { | |
if (value === 1) { | |
return true as unknown as SqliteBool<T> | |
} else if (value === 0) { | |
return false as unknown as SqliteBool<T> | |
} else { | |
throw Error(`Expected 0 or 1, got ${value}`) | |
} | |
} | |
if (typeof value === "boolean") { | |
return (value ? 1 : 0) as unknown as SqliteBool<T> | |
} | |
throw Error(`Expected number or bool, was ${typeof value}`) | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment