mirror of
https://github.com/freeCodeCamp/freeCodeCamp.git
synced 2026-05-28 18:26:54 +00:00
feat(client): tsx compilation (#62236)
Co-authored-by: Oliver Eyton-Williams <ojeytonwilliams@gmail.com>
This commit is contained in:
File diff suppressed because one or more lines are too long
@@ -1,5 +1,6 @@
|
||||
import { type VirtualTypeScriptEnvironment } from '@typescript/vfs';
|
||||
import type { CompilerOptions, CompilerHost } from 'typescript';
|
||||
import reactTypes from './react-types.json';
|
||||
|
||||
// Most of the ts types are only a guideline. This is because we're not bundling
|
||||
// TS in this worker. The specific TS version is going to be determined by the
|
||||
@@ -40,7 +41,7 @@ interface CancelEvent extends MessageEvent {
|
||||
}
|
||||
|
||||
// Pin at the latest TS version available as cdnjs doesn't support version range.
|
||||
const TS_VERSION = '5.7.3';
|
||||
const TS_VERSION = '5.9.2';
|
||||
|
||||
let tsEnv: VirtualTypeScriptEnvironment | null = null;
|
||||
let compilerHost: CompilerHost | null = null;
|
||||
@@ -54,7 +55,12 @@ importScripts(
|
||||
function importTS(version: string) {
|
||||
if (cachedVersion == version) return;
|
||||
importScripts(
|
||||
`https://cdnjs.cloudflare.com/ajax/libs/typescript/${version}/typescript.min.js`
|
||||
/* typescript.min.js fails with
|
||||
|
||||
typescript.min.js:320 Uncaught TypeError: Class constructors cannot be invoked without 'new'
|
||||
|
||||
so we're using the non-minified version for now. */
|
||||
`https://cdnjs.cloudflare.com/ajax/libs/typescript/${version}/typescript.js`
|
||||
);
|
||||
cachedVersion = version;
|
||||
}
|
||||
@@ -63,10 +69,13 @@ async function setupTypeScript() {
|
||||
importTS(TS_VERSION);
|
||||
const compilerOptions: CompilerOptions = {
|
||||
target: ts.ScriptTarget.ES2015,
|
||||
skipLibCheck: true // TODO: look into why this is needed. Are we doing something wrong? Could it be that it's not "synced" with this TS version?
|
||||
module: ts.ModuleKind.Preserve, // Babel is handling module transformation, so TS should leave them alone.
|
||||
skipLibCheck: true, // TODO: look into why this is needed. Are we doing something wrong? Could it be that it's not "synced" with this TS version?
|
||||
// from the docs: "Note: it's possible for this list to get out of
|
||||
// sync with TypeScript over time. It was last synced with TypeScript
|
||||
// 3.8.0-rc."
|
||||
jsx: ts.JsxEmit.Preserve, // Babel will handle JSX,
|
||||
allowUmdGlobalAccess: true // Necessary because React is loaded via a UMD script.
|
||||
};
|
||||
const fsMap = await createDefaultMapFromCDN(
|
||||
compilerOptions,
|
||||
@@ -75,6 +84,12 @@ async function setupTypeScript() {
|
||||
ts
|
||||
);
|
||||
|
||||
// This can be any path, but doing this means import React from 'react' works, if we ever need it.
|
||||
const reactTypesPath = `/node_modules/@types/react/index.d.ts`;
|
||||
|
||||
// It may be necessary to get all the types (global.d.ts etc)
|
||||
fsMap.set(reactTypesPath, reactTypes['react-18'] || '');
|
||||
|
||||
const system = tsvfs.createSystem(fsMap);
|
||||
// TODO: if passed an invalid compiler options object (e.g. { module:
|
||||
// ts.ModuleKind.CommonJS, moduleResolution: ts.ModuleResolutionKind.NodeNext
|
||||
@@ -82,10 +97,11 @@ async function setupTypeScript() {
|
||||
// show them the diagnostics from this function.
|
||||
const env = tsvfs.createVirtualTypeScriptEnvironment(
|
||||
system,
|
||||
[],
|
||||
[reactTypesPath],
|
||||
ts,
|
||||
compilerOptions
|
||||
);
|
||||
|
||||
compilerHost = createVirtualCompilerHost(
|
||||
system,
|
||||
compilerOptions,
|
||||
@@ -133,11 +149,12 @@ function handleCompileRequest(data: TSCompileEvent['data'], port: MessagePort) {
|
||||
|
||||
// TODO: If creating the file fresh each time is too slow, we can try checking
|
||||
// if the file exists and updating it if it does.
|
||||
tsEnv?.createFile('index.ts', code);
|
||||
// TODO: make sure the .tsx extension doesn't cause issues with vanilla TS.
|
||||
tsEnv?.createFile('/index.tsx', code);
|
||||
|
||||
const program = tsEnv!.languageService.getProgram()!;
|
||||
|
||||
const emitOutput = tsEnv!.languageService.getEmitOutput('index.ts');
|
||||
const emitOutput = tsEnv!.languageService.getEmitOutput('index.tsx');
|
||||
const compiled = emitOutput.outputFiles[0].text;
|
||||
|
||||
const message: TSCompiledMessage = {
|
||||
|
||||
Reference in New Issue
Block a user