UNPKG

@clawject/di

Version:

<p align="center"> <a href="https://clawject.com/" target="_blank"><img src="https://clawject.com/img/logo.svg" align="center" alt="Clawject Logo" width="120" height="120" /></a> </p>

125 lines (124 loc) 7.63 kB
"use strict"; /** * Code of this file is based on ts-morph/common and ts-morph/bootstrap packages from this repository https://github.com/dsherret/ts-morph * * Unfortunately, typescript package is bundled together with ts-morph, but we want it to be a peer dependency, so we can't use it directly. * */ var _Project_instances, _Project_ts, _Project_sourceFiles, _Project_compilerOptions, _Project_normalizeFileName; Object.defineProperty(exports, "__esModule", { value: true }); exports.Project = void 0; exports.createProject = createProject; const tslib_1 = require("tslib"); const fs = tslib_1.__importStar(require("fs")); const path = tslib_1.__importStar(require("path")); function createProject(ts, options = {}) { const project = new Project({ ...options, ts }); // Load files from tsconfig if provided if (options.tsConfigFilePath && !options.skipAddingFilesFromTsConfig) { project.addSourceFilesFromTsConfig(options.tsConfigFilePath); } return project; } class Project { constructor(options) { _Project_instances.add(this); _Project_ts.set(this, void 0); _Project_sourceFiles.set(this, new Map()); _Project_compilerOptions.set(this, void 0); tslib_1.__classPrivateFieldSet(this, _Project_ts, options.ts, "f"); // Load compiler options from tsconfig if provided if (options.tsConfigFilePath) { const configPath = path.resolve(options.tsConfigFilePath); const configFile = tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").readConfigFile(configPath, tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").sys.readFile); if (configFile.error) { throw new Error(`Error reading tsconfig: ${configFile.error.messageText}`); } const parsedConfig = tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").parseJsonConfigFileContent(configFile.config, tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").sys, path.dirname(configPath)); tslib_1.__classPrivateFieldSet(this, _Project_compilerOptions, { ...parsedConfig.options, ...(options.compilerOptions || {}) }, "f"); } else { tslib_1.__classPrivateFieldSet(this, _Project_compilerOptions, options.compilerOptions || {}, "f"); } } addSourceFilesFromTsConfig(tsConfigFilePath) { const configPath = path.resolve(tsConfigFilePath); const configFile = tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").readConfigFile(configPath, tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").sys.readFile); if (configFile.error) { throw new Error(`Error reading tsconfig: ${configFile.error.messageText}`); } const parsedConfig = tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").parseJsonConfigFileContent(configFile.config, tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").sys, path.dirname(configPath)); // Add all files from tsconfig for (const fileName of parsedConfig.fileNames) { if (fs.existsSync(fileName)) { const sourceText = fs.readFileSync(fileName, 'utf-8'); this.updateSourceFile(fileName, sourceText); } } } getSourceFile(fileName) { return tslib_1.__classPrivateFieldGet(this, _Project_sourceFiles, "f").get(tslib_1.__classPrivateFieldGet(this, _Project_instances, "m", _Project_normalizeFileName).call(this, fileName)); } updateSourceFile(fileNameOrSourceFile, sourceText) { let sourceFile; if (typeof fileNameOrSourceFile === 'string') { const normalizedFileName = tslib_1.__classPrivateFieldGet(this, _Project_instances, "m", _Project_normalizeFileName).call(this, fileNameOrSourceFile); sourceFile = tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").createSourceFile(normalizedFileName, sourceText, tslib_1.__classPrivateFieldGet(this, _Project_compilerOptions, "f").target || tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").ScriptTarget.Latest, true); } else { sourceFile = fileNameOrSourceFile; } const normalizedFileName = tslib_1.__classPrivateFieldGet(this, _Project_instances, "m", _Project_normalizeFileName).call(this, sourceFile.fileName); tslib_1.__classPrivateFieldGet(this, _Project_sourceFiles, "f").set(normalizedFileName, sourceFile); return sourceFile; } createSourceFile(fileName, sourceText = '') { const normalizedFileName = tslib_1.__classPrivateFieldGet(this, _Project_instances, "m", _Project_normalizeFileName).call(this, fileName); if (tslib_1.__classPrivateFieldGet(this, _Project_sourceFiles, "f").has(normalizedFileName)) { throw new Error(`Source file already exists: ${fileName}`); } const sourceFile = tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").createSourceFile(normalizedFileName, sourceText, tslib_1.__classPrivateFieldGet(this, _Project_compilerOptions, "f").target || tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").ScriptTarget.Latest, true); tslib_1.__classPrivateFieldGet(this, _Project_sourceFiles, "f").set(normalizedFileName, sourceFile); return sourceFile; } removeSourceFile(fileNameOrSourceFile) { const fileName = typeof fileNameOrSourceFile === 'string' ? fileNameOrSourceFile : fileNameOrSourceFile.fileName; tslib_1.__classPrivateFieldGet(this, _Project_sourceFiles, "f").delete(tslib_1.__classPrivateFieldGet(this, _Project_instances, "m", _Project_normalizeFileName).call(this, fileName)); } resolveSourceFileDependencies() { // Creating a program will resolve dependencies this.createProgram(); } createProgram(options) { const rootNames = Array.from(tslib_1.__classPrivateFieldGet(this, _Project_sourceFiles, "f").keys()); const compilerHost = tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").createCompilerHost(tslib_1.__classPrivateFieldGet(this, _Project_compilerOptions, "f")); // Override getSourceFile to use our cached source files const originalGetSourceFile = compilerHost.getSourceFile; compilerHost.getSourceFile = (fileName, languageVersionOrOptions, onError, shouldCreateNewSourceFile) => { const normalizedFileName = tslib_1.__classPrivateFieldGet(this, _Project_instances, "m", _Project_normalizeFileName).call(this, fileName); const cachedFile = tslib_1.__classPrivateFieldGet(this, _Project_sourceFiles, "f").get(normalizedFileName); if (cachedFile) { return cachedFile; } return originalGetSourceFile.call(compilerHost, fileName, languageVersionOrOptions, onError, shouldCreateNewSourceFile); }; const program = tslib_1.__classPrivateFieldGet(this, _Project_ts, "f").createProgram({ rootNames, options: tslib_1.__classPrivateFieldGet(this, _Project_compilerOptions, "f"), host: compilerHost, ...options, }); //Necessary to set parent nodes program.getTypeChecker(); return program; } } exports.Project = Project; _Project_ts = new WeakMap(), _Project_sourceFiles = new WeakMap(), _Project_compilerOptions = new WeakMap(), _Project_instances = new WeakSet(), _Project_normalizeFileName = function _Project_normalizeFileName(fileName) { // Normalize path separators and resolve to absolute path return path.resolve(fileName).replace(/\\/g, '/'); };