Leveraging User-Defined Type Guards and Type Predicates in TypeScript