Last active
September 2, 2018 16:25
-
-
Save rchanou/40510496ccf7b46c774a8f14f49bfba7 to your computer and use it in GitHub Desktop.
TypeScript "nameof" Hacks
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
// see issue: https://github.com/Microsoft/TypeScript/issues/1579 | |
function nameOf<T>(obj: T) { | |
let name: string; | |
const makeCopy = (obj: any): any => { | |
const copy = {}; | |
for (const key in obj) { | |
defineProperty(copy, key, { | |
get() { | |
name = key; | |
const value = obj[key]; | |
if (value && typeof value === "object") { | |
return makeCopy(value); | |
} | |
return value; | |
} | |
}); | |
} | |
return copy; | |
}; | |
return (accessor: { (x: T): any }): string => { | |
name = ""; | |
accessor(makeCopy(obj)); | |
return name; | |
}; | |
} | |
function pathOf<T>(obj: T) { | |
let path: string[] = []; | |
const makeCopy = (obj: any): any => { | |
const copy = {}; | |
for (const key in obj) { | |
defineProperty(copy, key, { | |
get() { | |
path.push(key); | |
const value = obj[key]; | |
if (value && typeof value === "object") { | |
return makeCopy(value); | |
} | |
return value; | |
} | |
}); | |
} | |
return copy; | |
}; | |
return (accessor: { (x: T): any }): string[] => { | |
path = []; | |
accessor(makeCopy(obj)); | |
return path; | |
}; | |
} | |
// these were tweaked from the nameof function shared by @rjamesnw here: | |
// https://github.com/Microsoft/TypeScript/issues/1579#issuecomment-394551591 | |
function getKey(selector: (x?: any) => any) { | |
const s = "" + selector; | |
const m = | |
s.match(/return\s+([A-Z$_.]+)/i) || | |
s.match(/.*?(?:=>|function.*?{(?!\s*return))\s*([A-Z$_.]+)/i); | |
const name = (m && m[1]) || ""; | |
const keys = name.split("."); | |
return keys[keys.length - 1]; | |
} | |
function getKeyPath(selector: (x?: any) => any) { | |
const s = "" + selector; | |
const m = | |
s.match(/return\s+([A-Z$_.]+)/i) || | |
s.match(/.*?(?:=>|function.*?{(?!\s*return))\s*([A-Z$_.]+)/i); | |
const name = (m && m[1]) || ""; | |
const keys = name.split("."); | |
return keys.slice(1); | |
} |
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
// just another unrelated higher-order type that I find extremely useful | |
type Omit<T, K extends keyof T> = Pick<T, Diff<keyof T, K>>; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment