javascript - Hur kan webbläsaren använda TypeScript-fil direkt i Vite index.html?
På senaste tiden har jag lekt med Vite. En sak som fascinerar mig är dess förmåga att använda TypeScript-filer direkt i index.html, till exempel.
<script type="module" src="/src/main.ts"></script>
Från dokumentationen förstår jag att Vite kommer att transpile den ursprungliga koden från Typescript till Javascript (jag har kontrollerat att innehållet i main.ts faktiskt omvandlas). Men hur kan webbläsaren köra Javascript-koden inuti en *.ts-fil?
Jag försökte återskapa det genom att skapa en enkel statisk server med en index.html som innehöll skript-taggen som ovan. Ändå kommer webbläsaren att visa ett fel:
Failed to load module script: Expected a JavaScript module script but the server responded with a MIME type of "video/mp2t". Strict MIME type checking is enforced for module scripts per HTML spec.
Så hur är detta möjligt med Vite?
Svar #1
Men hur kan webbläsaren köra Javascript-koden inuti en *.ts-fil?
JavaScript är inte i en *.ts-fil.
Det är en resurs, med en Content-Type: text/javascript responsrubrik, hämtad med en URL. Sökvägen för den URL:en spelar bara roll eftersom den talar om för servern vad den ska leta efter. Webbläsaren bryr sig inte om vilka bokstäver som finns i den.
Svar #2
REDIGERA: Det accepterade svaret är faktiskt korrekt, eftersom OP inte undrade över vad Vite gör under produktions-byggen utan snarare under utvecklings-byggen, vilket är att utveckling serverar de transplierade resultaten från minnet (modifierar Content-Type-huvuden för att servera rätt filtyp, åsidosätter filändelser som antyds vid behov) medan produktion beständigt ändrar URL:er i genererade artefakter.
Mitt svar nedan förklarar vad som händer med Vite-inputs under slutliga transpileringar i produktions-läge, medan det accepterade svaret förklarar hur Vite klarar av att transpile filer i minnet och ändra innehållshuvuden för att leverera de minnes-transpilerade filerna under utvecklings-läge.
Om jag inte missförstår något, tycker jag att svaret som har godkänts inte faktiskt motsvarar vad som frågades. Jag tror att OP undrar hur man kan referera till en "TypeScript"-fil i en Vite-projekts HTML-rotfil (index.html) för att transpila och köra den refererade TypeScript-koden. Ett exempel är:
<script type="module" src="./index.ts"></script>
TL;DR är att webbläsaren aldrig kör TypeScript-kod -- Vite omvandlar URL:en ovan till något som liknar:
<script type="module" src="/index.[content_hash].js"></script>
...hur kan webbläsaren köra Javascript-koden inuti en *.ts-fil?
Det behöver (lyckligtvis) inte. Du svarade delvis på din egen fråga här:
...Vite kommer att transpile den ursprungliga koden från Typescript till Javascript.
Webbläsaren får inte rå TypeScript direkt. Vite transformera inte bara dina tillgångar, det transformera också länkarna i din index.html till andra externa resurser.
Försök att köra npm run build eller vite build, och besök sedan din utmatningskatalog och inspektera den genererade index.html-filen själv.
En "JavaScript-först" modulbuntare (som Webpack) skapar en "beroendegraf" av dina moduler. I princip tillhandahåller du en ingångspunkt, och buntaren går igenom alla importeringar (rekursivt) och gör avancerade saker (dvs. buntning, trädskakning och alla andra transformationer).
Vite, å andra sidan, är vad jag skulle kalla en "HTML-först" bundler. Där Webpack skulle välja att använda JavaScript-filer (och ibland andra filer) som ingångspunkter, tillåter Vite HTML-filer att vara en ingångspunkt. Samma sak händer här, med skillnaden att istället för JavaScript-importer, traverserar Vite istället saker som ett link-tags href-attribut, eller ett img-tags src-attribut.
I båda fallen, när sammanställning och transformation av tillgångar har skett, ser beroendegrafen vanligtvis annorlunda ut -- och filtyperna själva kan ha förändrats. Till exempel skulle flera sammanfogade filer inte längre kräva flera importeringar, och TypeScript-filer kan nu vara JavaScript-filer. Bundlers tar hänsyn till detta genom att dynamiskt ändra import-URL:er och strategi baserat på kontexten.
Hoppas det hjälper!
