@travetto/transformer
Version:
Functionality for AST transformations, with transformer registration, and general utils
70 lines (57 loc) • 2.16 kB
text/typescript
import ts from 'typescript';
import { ManifestIndex, ManifestModuleUtil } from '@travetto/manifest';
import { NodeTransformer } from './types/visitor.ts';
import { VisitorFactory } from './visitor.ts';
import { TransformerState } from './state.ts';
import { getAllTransformers } from './register.ts';
/**
* Manages the typescript transformers
*/
export class TransformerManager {
/**
* Create transformer manager
* @param transformerFiles
* @param manifest
* @returns
*/
static async create(manifestIndex: ManifestIndex): Promise<TransformerManager> {
const transformerFiles = manifestIndex.find({ folder: f => f === '$transformer' }).map(f => f.sourceFile);
const transformers: NodeTransformer<TransformerState>[] = [];
for (const file of transformerFiles) { // Exclude based on blacklist
const entry = manifestIndex.getEntry(file)!;
transformers.push(...getAllTransformers(await import(ManifestModuleUtil.withOutputExtension(entry.import)), entry.module));
}
for (const x of transformers) {
process.send?.({ type: 'log', payload: { level: 'debug', message: `Loaded Transformer: ${x.key}#${x.type}`, scope: 'transformers' } });
}
// Prepare a new visitor factory with a given type checker
return new TransformerManager(manifestIndex, transformers);
}
#cached: ts.CustomTransformers | undefined;
#transformers: NodeTransformer<TransformerState>[];
#manifestIndex: ManifestIndex;
constructor(manifestIndex: ManifestIndex, transformers: NodeTransformer<TransformerState>[]) {
this.#transformers = transformers;
this.#manifestIndex = manifestIndex;
}
/**
* Initialize with type checker
* @param checker
*/
init(checker: ts.TypeChecker): void {
const visitor = new VisitorFactory(
(ctx, src) => new TransformerState(src, ctx.factory, checker, this.#manifestIndex),
this.#transformers
);
// Define transformers for the compiler
this.#cached = {
before: [visitor.visitor()]
};
}
/**
* Get typescript transformer object
*/
get(): ts.CustomTransformers | undefined {
return this.#cached!;
}
}