Lists methods without TypeScript typings.
Usage:
mistypes <js> --- <dts>
# http://editorconfig.org/ | |
root = true | |
[*] | |
indent_style = tab | |
insert_final_newline = true | |
trim_trailing_whitespace = true | |
[*.md] | |
indent_size = 3 |
node_modules/ |
#!/usr/bin/env ts-node-script -T | |
import * as ts from "typescript"; | |
import { tsIds } from "./ts-ids"; | |
const files = process.argv.slice(2); | |
interface InOut { | |
minuend: string[]; | |
subtrahend: string[]; | |
} | |
function inOut(files: readonly string[]): InOut { | |
let idx = files.findIndex((s) => s === "---"); | |
if (idx === -1) { | |
idx = Infinity; | |
} | |
return { minuend: files.slice(0, idx), subtrahend: files.slice(idx + 1) }; | |
} | |
function* difference(minuend: Iterable<string>, subtrahend: Iterable<string>) { | |
const set = new Set(subtrahend); | |
for (const item of minuend) { | |
if (!set.has(item)) { | |
yield item; | |
} | |
} | |
} | |
function filesIds(files: readonly string[]) { | |
const program = ts.createProgram(files, { allowJs: true }); | |
return program.getSourceFiles().flatMap(tsIds); | |
} | |
const { minuend, subtrahend } = inOut(files); | |
// It breaks without Array.from | |
for (const entry of Array.from( | |
difference(filesIds(minuend), filesIds(subtrahend)) | |
)) { | |
console.log(entry); | |
} |
{ | |
"name": "mistypes", | |
"version": "0.0.0", | |
"description": "Lists methods without TypeScript typings", | |
"bin": "mistypes.ts", | |
"dependencies": { | |
"ts-node": "^8.8.2", | |
"typescript": "^3.8.3" | |
}, | |
"devDependencies": { | |
"@types/node": "^13.11.1", | |
"prettier": "2.0.4" | |
}, | |
"repository": { | |
"type": "git", | |
"url": "https://gist.github.com/885dbe80be82e706e9e84c967269e17b.git" | |
}, | |
"keywords": [ | |
"typescript" | |
], | |
"author": "Wojciech Pawlik <woj.pawlik@gmail.com>", | |
"license": "ISC" | |
} |
import * as ts from "typescript"; | |
const isStatic = ({ kind }: ts.Modifier) => kind === 120; | |
export function tsIds(file: ts.SourceFile): string[] { | |
const ids: string[] = []; | |
ts.forEachChild(file, (node) => { | |
if (ts.isClassDeclaration(node)) { | |
node.forEachChild((member) => { | |
if (ts.isMethodDeclaration(member)) { | |
const sep = member.modifiers?.some(isStatic) ? "." : "::"; | |
ids.push( | |
node.name?.escapedText + sep + member.name.getText(file) + "()" | |
); | |
} | |
}); | |
} | |
}); | |
return ids; | |
} |
{ | |
"compilerOptions": { | |
"module": "CommonJS", | |
"noEmit": true, | |
"strict": true, | |
"target": "ES2019" | |
} | |
} |
Related: tsdjs/tsd#63 (comment)