TypeScript compiler wrapper for static analysis and code manipulation.
npx @tessl/cli install tessl/npm-ts-morph@26.0.0ts-morph is a TypeScript compiler wrapper that provides an easier and more intuitive way to programmatically navigate, analyze, and manipulate TypeScript and JavaScript Abstract Syntax Trees (AST). It abstracts the complexities of the native TypeScript compiler API, offering a fluent, chainable interface for code analysis, transformation, and generation tasks.
npm install ts-morphimport { Project, SourceFile, ClassDeclaration, Node } from "ts-morph";For CommonJS:
const { Project, SourceFile, ClassDeclaration, Node } = require("ts-morph");import { Project } from "ts-morph";
// Create a new project
const project = new Project({
tsConfigFilePath: "tsconfig.json",
});
// Add a source file
const sourceFile = project.createSourceFile("example.ts", `
class Example {
private name: string;
constructor(name: string) {
this.name = name;
}
greet() {
return \`Hello, \${this.name}!\`;
}
}
`);
// Navigate and manipulate the AST
const classDeclaration = sourceFile.getClassOrThrow("Example");
const greetMethod = classDeclaration.getMethodOrThrow("greet");
// Add a parameter to the greet method
greetMethod.addParameter({
name: "suffix",
type: "string",
hasQuestionToken: true,
});
// Get the modified code
console.log(sourceFile.getFullText());
// Save the changes
project.saveSync();ts-morph is built around several key components:
Project class manages TypeScript projects, source files, and compilationCore project functionality for managing TypeScript projects, source files, and compilation settings. Essential for setting up analysis and manipulation workflows.
class Project {
constructor(options?: ProjectOptions);
addSourceFileAtPath(filePath: string): SourceFile;
createSourceFile(filePath: string, text?: string, options?: SourceFileCreateOptions): SourceFile;
getSourceFile(fileNameOrPath: string): SourceFile | undefined;
getSourceFiles(): SourceFile[];
save(): Promise<void>;
saveSync(): void;
emit(): Promise<EmitResult>;
emitSync(): EmitResult;
getProgram(): Program;
getTypeChecker(): TypeChecker;
}
interface ProjectOptions {
tsConfigFilePath?: string;
compilerOptions?: CompilerOptions;
fileSystem?: FileSystemHost;
manipulationSettings?: Partial<ManipulationSettings>;
useInMemoryFileSystem?: boolean;
}Complete set of AST node classes providing navigation, analysis, and manipulation capabilities for all TypeScript language constructs.
abstract class Node<T = ts.Node> {
getKind(): SyntaxKind;
getKindName(): string;
getText(): string;
getFullText(): string;
getStart(): number;
getEnd(): number;
getParent(): Node | undefined;
getChildren(): Node[];
getFirstChild(): Node | undefined;
getLastChild(): Node | undefined;
getPreviousSibling(): Node | undefined;
getNextSibling(): Node | undefined;
remove(): void;
replaceWithText(text: string): Node;
}Structure-based API for creating new TypeScript code elements with full type safety and intelligent formatting.
interface ClassDeclarationStructure {
kind: StructureKind.Class;
name: string;
extends?: string;
implements?: string[];
isAbstract?: boolean;
isExported?: boolean;
decorators?: DecoratorStructure[];
docs?: JSDocStructure[];
methods?: MethodDeclarationStructure[];
properties?: PropertyDeclarationStructure[];
constructors?: ConstructorDeclarationStructure[];
}
class SourceFile {
addClass(structure: ClassDeclarationStructure): ClassDeclaration;
addFunction(structure: FunctionDeclarationStructure): FunctionDeclaration;
addInterface(structure: InterfaceDeclarationStructure): InterfaceDeclaration;
addEnum(structure: EnumDeclarationStructure): EnumDeclaration;
addImportDeclaration(structure: ImportDeclarationStructure): ImportDeclaration;
}Direct access to TypeScript's type checker and type information for advanced static analysis and type-aware transformations.
class TypeChecker {
getTypeAtLocation(node: Node): Type;
getSymbolAtLocation(node: Node): Symbol | undefined;
getTypeOfSymbolAtLocation(symbol: Symbol, node: Node): Type;
getSignatureFromDeclaration(node: SignatureDeclaration): Signature | undefined;
}
class Type {
getText(): string;
getSymbol(): Symbol | undefined;
getApparentType(): Type;
isArray(): boolean;
isBoolean(): boolean;
isString(): boolean;
isNumber(): boolean;
isObject(): boolean;
isUnion(): boolean;
isIntersection(): boolean;
}Comprehensive file system operations and directory management capabilities integrated with the project structure.
class Directory {
getName(): string;
getPath(): string;
getBaseName(): string;
getParent(): Directory | undefined;
getDirectories(): Directory[];
getSourceFiles(): SourceFile[];
createDirectory(name: string): Directory;
createSourceFile(fileName: string, text?: string): SourceFile;
addSourceFileAtPath(filePath: string): SourceFile;
copy(dirPath: string, options?: DirectoryCopyOptions): Directory;
move(dirPath: string, options?: DirectoryMoveOptions): Directory;
delete(): void;
}ts-morph provides a comprehensive set of error classes for different error conditions:
class BaseError extends Error {}
class ArgumentError extends BaseError {}
class FileNotFoundError extends BaseError {}
class DirectoryNotFoundError extends BaseError {}
class InvalidOperationError extends BaseError {}
class ManipulationError extends BaseError {}type Constructor<T = {}> = new (...args: any[]) => T;
type WriterFunction = (writer: CodeBlockWriter) => void;
enum SyntaxKind {
// Extensive enumeration of all TypeScript syntax kinds
// Re-exported from TypeScript compiler API
}
enum StructureKind {
Class,
Method,
Property,
Function,
Interface,
// ... all structure types
}