UNPKG

@neo-one/smart-contract-compiler

Version:

NEO•ONE TypeScript smart contract compiler.

115 lines (113 loc) 5.47 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.createContextForLanguageService = exports.createContextForSnippet = exports.createContextForPath = exports.createContextForDir = exports.COMPILER_OPTIONS = exports.updateContext = void 0; const tslib_1 = require("tslib"); const ts_utils_1 = require("@neo-one/ts-utils"); const typescript_1 = tslib_1.__importDefault(require("typescript")); const Context_1 = require("./Context"); const utils_1 = require("./utils"); function createContext(sourceFiles, program, typeChecker, languageService, host) { return new Context_1.Context(sourceFiles, program, typeChecker, languageService, host); } function updateContext(context, files) { const { program, typeChecker, languageService } = createProgram(Object.keys(files), context.host, { modifyHost: createModifyHostFiles(files), withTestHarness: context.program.__withTestHarness, }); const sourceFiles = utils_1.getAllSourceFiles(Object.keys(files).map((rootName) => ts_utils_1.tsUtils.file.getSourceFileOrThrow(program, rootName)), typeChecker); return context.update(sourceFiles, program, typeChecker, languageService); } exports.updateContext = updateContext; const CREATE_CONTEXT_OPTIONS_DEFAULT = { withTestHarness: false, }; const defaultModifyHost = () => { }; const DEFAULT_MAKE_CONTEXT_OPTIONS = Object.assign(Object.assign({}, CREATE_CONTEXT_OPTIONS_DEFAULT), { modifyHost: defaultModifyHost }); exports.COMPILER_OPTIONS = { target: typescript_1.default.ScriptTarget.ESNext, module: typescript_1.default.ModuleKind.ESNext, moduleResolution: typescript_1.default.ModuleResolutionKind.NodeJs, noLib: true, typeRoots: [], pretty: true, noEmit: true, declaration: false, allowSyntheticDefaultImports: true, resolveJsonModule: false, experimentalDecorators: true, jsx: typescript_1.default.JsxEmit.React, alwaysStrict: true, strict: true, skipLibCheck: true, noUnusedLocals: true, noImplicitReturns: true, allowUnusedLabels: false, noUnusedParameters: false, allowUnreachableCode: false, noFallthroughCasesInSwitch: true, forceConsistentCasingInFileNames: true, }; const makeContext = (rootNames, host, options = DEFAULT_MAKE_CONTEXT_OPTIONS) => { const { program, typeChecker, languageService } = createProgram(rootNames, host, options); const sourceFiles = utils_1.getAllSourceFiles(rootNames.map((rootName) => ts_utils_1.tsUtils.file.getSourceFileOrThrow(program, rootName)), typeChecker); return createContext(sourceFiles, program, typeChecker, languageService, host); }; const createModifyHostFiles = (files) => (host) => { const originalFileExists = host.fileExists === undefined ? undefined : host.fileExists.bind(host); host.fileExists = (file) => { if (files[file] !== undefined) { return true; } return originalFileExists === undefined ? false : originalFileExists(file); }; const originalReadFile = host.readFile === undefined ? undefined : host.readFile.bind(host); host.readFile = (file, ...args) => { const foundFile = files[file]; if (foundFile !== undefined) { return foundFile; } return originalReadFile === undefined ? undefined : originalReadFile(file, ...args); }; }; const createProgram = (rootNames, host, { modifyHost = defaultModifyHost, withTestHarness = false } = DEFAULT_MAKE_CONTEXT_OPTIONS) => { const servicesHost = host.createLanguageServiceHost(rootNames, exports.COMPILER_OPTIONS, withTestHarness); modifyHost(servicesHost); const languageService = typescript_1.default.createLanguageService(servicesHost); const program = languageService.getProgram(); if (program === undefined) { throw new Error('Something went wrong'); } program.__withTestHarness = withTestHarness; return { program, typeChecker: program.getTypeChecker(), languageService, }; }; exports.createContextForDir = async (dir, host, options = CREATE_CONTEXT_OPTIONS_DEFAULT) => { const files = await host.getAllTypescriptFilesInDir(dir); return makeContext(files, host, options); }; exports.createContextForPath = (filePath, host, options = CREATE_CONTEXT_OPTIONS_DEFAULT) => makeContext([filePath], host, options); exports.createContextForSnippet = (code, host, _a = CREATE_CONTEXT_OPTIONS_DEFAULT) => { var { fileName: fileNameIn } = _a, rest = tslib_1.__rest(_a, ["fileName"]); const fileName = host.createSnippetFile(fileNameIn); const context = makeContext([fileName], host, Object.assign(Object.assign({}, rest), { modifyHost: createModifyHostFiles({ [fileName]: code }) })); const sourceFile = ts_utils_1.tsUtils.file.getSourceFileOrThrow(context.program, fileName); return { context, sourceFile, }; }; exports.createContextForLanguageService = (filePath, languageService, host) => { const program = languageService.getProgram(); if (program === undefined) { throw new Error('Something went wrong'); } const sourceFile = ts_utils_1.tsUtils.file.getSourceFileOrThrow(program, filePath); const typeChecker = program.getTypeChecker(); const sourceFiles = utils_1.getAllSourceFiles([sourceFile], typeChecker); return createContext(sourceFiles, program, typeChecker, languageService, host); }; //# sourceMappingURL=createContext.js.map