การแปลซอร์สโค้ด คือการแปลงซอร์สโค้ดจากภาษาโปรแกรมหนึ่งไปยังอีกภาษาหนึ่งในระดับนามธรรมเดียวกัน แตกต่างจากการคอมไพล์เป็นโค้ดเครื่อง การแปลซอร์สโค้ดจะแปลโค้ดระหว่างภาษาระดับสูง: TypeScript เป็น JavaScript, Kotlin เป็น Java, Dart เป็น JavaScript ตาม Babel Documentation Babel เป็นตัวแปลซอร์สโค้ดที่ได้รับความนิยมมากที่สุด โดยมีดาวน์โหลดมากกว่า 35 ล้านครั้งต่อสัปดาห์และรองรับปลั๊กอินหลายร้อยตัว
ประเด็นสำคัญ
การแปลซอร์สโค้ด (การคอมไพล์จากซอร์สถึงซอร์ส) คือกระบวนการแปลโปรแกรมจากภาษาโปรแกรมหนึ่งไปยังอีกภาษาหนึ่งในขณะที่รักษาระดับนามธรรมเดียวกัน ตัวแปลซอร์สโค้ดรับซอร์สโค้ดในภาษา A และสร้างโค้ดที่เทียบเท่าในภาษา B ซึ่งสามารถทำงานในสภาพแวดล้อมเป้าหมายได้ ตัวอย่างทั่วไป: TypeScript เป็น JavaScript, SASS เป็น CSS, Haxe เป็นหลายภาษาเป้าหมาย
การแปลซอร์สโค้ดแตกต่างจาก การคอมไพล์ ตรงที่โค้ดเอาต์พุตยังคงอยู่ในระดับสูงและมนุษย์สามารถอ่านได้ (ถึงแม้จะไม่ได้มีวัตถุประสงค์เพื่อการนั้น) คอมไพเลอร์ (GCC, LLVM, javac) แปลโค้ดเป็นโค้ดเครื่องหรือไบต์โค้ด — รูปแบบที่อ่านไม่ได้ ตัวแปลซอร์สโค้ดสร้างโค้ดที่สามารถคอมไพล์หรือย่อขนาดเพิ่มเติมได้
ทำไมต้องมีการแปลซอร์สโค้ด เหตุผลหลักคือความเข้ากันได้ นักพัฒนาต้องการใช้ภาษาสมัยใหม่ (TypeScript พร้อมชนิด, Kotlin พร้อม null safety) แต่แพลตฟอร์มเป้าหมายรองรับเฉพาะ JavaScript หรือ Java การแปลซอร์สโค้ดช่วยให้เขียนด้วยภาษาสมัยใหม่ในขณะที่ปรับใช้โค้ดที่สภาพแวดล้อมเป้าหมายเข้าใจได้
| ตัวแปลซอร์สโค้ด | ซอร์ส → เป้าหมาย | การใช้งาน |
|---|---|---|
| Babel | ES6+/TypeScript → ES5 | การพัฒนาเว็บ, React, Vue |
| tsc (TypeScript Compiler) | TypeScript → JavaScript | แอปพลิเคชัน TypeScript ใดๆ |
| kotlinc-js | Kotlin → JavaScript | Kotlin/JS, React Kotlin Wrappers |
| dart2js | Dart → JavaScript | Flutter Web, AngularDart |
| SWC | TypeScript/JS → ES5 | Next.js, การรวมโค้ดด้วย Rust |
ระดับนามธรรม คือความแตกต่างหลัก ตัวแปลซอร์สโค้ดแปลโค้ดระหว่างภาษาในระดับเดียวกัน (ระดับสูง → ระดับสูง) คอมไพเลอร์แปลจากระดับสูงไปยังระดับต่ำ (โค้ดเครื่อง, ไบต์โค้ด) LLVM IR เป็นการแสดงระดับกลางแต่ยังคงต่ำกว่า C++ หรือ Rust ดั้งเดิม
ความสามารถในการอ่านผลลัพธ์ คือความแตกต่างที่สอง ผลลัพธ์ของการแปลซอร์สโค้ด (JavaScript จาก TypeScript) สามารถอ่านได้และสามารถดีบักในเบราว์เซอร์ได้ ผลลัพธ์ของการคอมไพล์ (โค้ดเครื่องจาก C++) ไม่ได้มีไว้สำหรับการอ่าน — การวิเคราะห์ต้องใช้ดีสแอสเซมเบลอร์ Source maps ช่วยดีบักโค้ดที่แปลแล้วโดยเชื่อมโยงกับซอร์สดั้งเดิม
ใน ไปป์ไลน์ CI/CD การแปลซอร์สโค้ดจะดำเนินการในขั้นตอนการbuild สำหรับโปรเจกต์ TypeScript, tsc หรือ Babel จะทำงานในคอนเทนเนอร์ Docker, สร้าง JavaScript และ source maps จากนั้นจึงย่อขนาดและปรับใช้บนเซิร์ฟเวอร์หรือร้านค้าแอป การกำหนดค่าแคชสำหรับผลลัพธ์การแปลซอร์สโค้ดเป็นสิ่งสำคัญ — tsc --incremental จะบันทึกกราฟการพึ่งพาระหว่างการทำงานแต่ละครั้ง ลดเวลาในการbuild ลง 30–50%
สำหรับโปรเจกต์มือถือ (React Native) การแปลซอร์สโค้ดผ่าน Metro Bundler จะทำงานบนเซิร์ฟเวอร์ CI ทุกครั้งที่เผยแพร่ ไดเรกทอรีแคช (tmp/metro-cache) และการbuild แบบขนานผ่าน --workers ช่วยเร่งกระบวนการ GitHub Actions และ GitLab CI รองรับการแคชไดเรกทอรี node_modules และ .cache ระหว่างการทำงาน ซึ่งสำคัญอย่างยิ่งต่อการลดเวลาไปป์ไลน์
ความเร็วในการทำงาน ก็แตกต่างกัน การคอมไพล์เป็นโค้ดเครื่องให้ประสิทธิภาพสูงสุด การแปลซอร์สโค้ดยังคงค่าใช้จ่ายของระดับนามธรรม: JavaScript จาก TypeScript ทำงานด้วยความเร็วเดียวกับ JavaScript ทั่วไป การปรับให้เหมาะสม (TypeScript —strict) ทำงานในขั้นตอนการวิเคราะห์ ไม่ใช่ในขณะรันไทม์
สถานการณ์ที่ 1: TypeScript → JavaScript — สถานการณ์ที่พบบ่อยที่สุด นักพัฒนาเขียน TypeScript พร้อมชนิด คอมไพเลอร์ tsc หรือ Babel จะลบคําอธิบายประกอบชนิดและสร้าง JavaScript บริสุทธิ์ โปรเจกต์ Angular ทั้งหมดและโปรเจกต์ React ส่วนใหญ่ (2026) ใช้การแปลซอร์สโค้ด TypeScript ตาม State of JS 2025 นักพัฒนา 79% ที่ตอบแบบสำรวจใช้ TypeScript ในโปรเจกต์หลักของตน
สถานการณ์ที่ 2: Kotlin → JavaScript — ใช้ใน Kotlin/JS สำหรับการพัฒนาแบบ full-stack โค้ด Kotlin ถูกคอมไพล์เป็น JavaScript ผ่าน Kotlin Compiler พร้อม IR (Intermediate Representation) Kotlin/JS รองรับการประกาศชนิด TypeScript (.d.ts) สำหรับการรวมกับไลบรารี JS ภายนอก JetBrains ใช้ Kotlin/JS ในผลิตภัณฑ์ของตนสำหรับอินเทอร์เฟซเว็บ
สถานการณ์ที่ 3: SASS/SCSS → CSS — การแปลซอร์สโค้ดของพรีโปรเซสเซอร์ CSS Dart Sass (การใช้งานที่แนะนำ) แปล .scss เป็น .css โดยขยาย mixin, ตัวแปร, กฎที่ซ้อนกัน และฟังก์ชัน นี่ไม่ใช่การคอมไพล์ (CSS ยังคงเป็น CSS) แต่เป็นการแปลซอร์สโค้ดพร้อมส่วนขยายทางไวยากรณ์
| พารามิเตอร์ | การแปลซอร์สโค้ด | การคอมไพล์ | การแปลความหมาย |
|---|---|---|---|
| อินพุต → เอาต์พุต | ระดับสูง → ระดับสูง | ระดับสูง → โค้ดเครื่อง | โค้ด → ทำงานทันที |
| ตัวอย่าง | TypeScript → JavaScript | C++ → ARM/x86 | Python → สภาพรันไทม์ CPython |
| โค้ดเอาต์พุตอ่านได้ | ใช่ | ไม่ | ไม่เกี่ยวข้อง |
| ประสิทธิภาพ | เหมือนภาษาเป้าหมาย | สูงสุด | ต่ำกว่าการคอมไพล์ |
| ต้องใช้รันไทม์ | ไม่ (โค้ดเป้าหมายบริสุทธิ์) | ไม่ | ใช่ |
Babel เป็นตัวแปลซอร์สโค้ด JavaScript ที่ได้รับความนิยมมากที่สุด แปลงโค้ด ES6+/ESNext เป็น JavaScript ที่เข้ากันได้กับ ES5 Babel ทำงานผ่านระบบปลั๊กอินและพรีเซ็ต: ปลั๊กอินแต่ละตัวรับผิดชอบการแปลงหนึ่งอย่าง (arrow functions, async/await, optional chaining) @babel/preset-env จะกำหนดปลั๊กอินที่จำเป็นโดยอัตโนมัติตามเบราว์เซอร์เป้าหมาย (browserslist)
สถาปัตยกรรมของ Babel ประกอบด้วยสามขั้นตอน: การแยกวิเคราะห์ → การแปลง → การสร้าง ตัวแยกวิเคราะห์ (Babylon/@babel/parser) แปลงซอร์สโค้ดเป็น AST (Abstract Syntax Tree) ตัวแปลง (ปลั๊กอิน) ปรับเปลี่ยน AST ตัวสร้าง (@babel/generator) สร้างโค้ดเอาต์พุตจาก AST ที่ถูกปรับเปลี่ยน
// โค้ด ES6+ ดั้งเดิม
const greet = (name = "World") => {
return `Hello, ${name}!`;
};
class User {
constructor(name) {
this.name = name;
}
}
const data = { user: { address: { city: "Moscow" } } };
const city = data?.user?.address?.city;// หลัง Babel (target: > 0.25%, not dead)
"use strict";
var greet = function (name) {
if (name === void 0) { name = "World"; }
return "Hello, " + name + "!";
};
var User = function (name) {
this.name = name;
};
var data = { user: { address: { city: "Moscow" } } };
var city = data != null
? data.user != null
? data.user.address != null
? data.user.address.city
: void 0
: void 0
: void 0;Babel แปลง: ฟังก์ชันลูกศรเป็น function expression, พารามิเตอร์เริ่มต้น (name = “World”) เป็นการตรวจสอบ void 0, สตริงเทมเพลตเป็นการต่อกัน, คลาสเป็นฟังก์ชันคอนสตรัคเตอร์, และ optional chaining (?.) เป็นห่วงโซ่ของตัวดำเนินการ ternary const ถูกแทนที่ด้วย var เพื่อความเข้ากันได้กับ ES5
TypeScript เป็นภาษาที่มีการกำหนดชนิดอย่างเข้มงวดซึ่งถูกแปลซอร์สโค้ดเป็น JavaScript คอมไพเลอร์ tsc (TypeScript Compiler) ทำหน้าที่สองอย่าง: การตรวจสอบชนิดและการแปลซอร์สโค้ด (emit) สิ่งสำคัญที่ต้องเข้าใจ: การตรวจสอบชนิดและการแปลซอร์สโค้ดเป็นขั้นตอนอิสระ คุณสามารถดำเนินการแปลซอร์สโค้ดโดยไม่ต้องตรวจสอบชนิด (--noEmitOnError false) หรือตรวจสอบชนิดโดยไม่สร้างโค้ด (--noEmit true)
การแปลซอร์สโค้ด TypeScript จะลบคําอธิบายประกอบชนิดทั้งหมด, อินเทอร์เฟซ, นามแฝงชนิด และพารามิเตอร์เจเนอริก — สิ่งเหล่านี้ไม่มีใน JavaScript Enum จะถูกแปลงเป็นวัตถุ, ตัวตกแต่งเป็นการเรียกฟังก์ชัน, async/await เป็นเจนเนอเรเตอร์ (ถ้า target ต่ำกว่า ES2017) tsconfig.json ควบคุม target (เวอร์ชัน JavaScript), module (ระบบโมดูล), strict (ความเข้มงวดในการตรวจสอบชนิด) และ outDir (โฟลเดอร์เอาต์พุต)
{
"compilerOptions": {
"target": "es2015",
"module": "esnext",
"lib": ["es2015", "dom"],
"strict": true,
"outDir": "./dist",
"rootDir": "./src",
"esModuleInterop": true,
"sourceMap": true,
"declaration": true
},
"include": ["src/**/*"],
"exclude": ["node_modules"]
}target: “es2015” สั่งให้ tsc สร้าง JavaScript ด้วยไวยากรณ์ ES6 (ฟังก์ชันลูกศร, คลาส, let/const) module: “esnext” รักษาโมดูล ES (import/export) สำหรับ Tree Shaking ใน Webpack ภายหลัง strict: true เปิดใช้งานการตรวจสอบชนิดทั้งหมด (strictNullChecks, noImplicitAny, strictFunctionTypes) declaration: true สร้างไฟล์ .d.ts สำหรับผู้ใช้ TypeScript ของไลบรารี
React Native ใช้ Babel และ Metro เพื่อแปล JavaScript/TypeScript เป็นโค้ดที่ทำงานได้โดย JavaScriptCore (iOS) หรือ Hermes (Android) ปลั๊กอิน Babel เพิ่มการแปลง JSX, คําอธิบายประกอบ Flow/TypeScript และการปรับให้เหมาะสมเฉพาะ React Native Metro Bundler ยังรวมโมดูลและดำเนินการ Hot Module Replacement สำหรับการพัฒนา
Flutter ใช้การแปลซอร์สโค้ด Dart สำหรับ Flutter Web, dart2js แปล Dart เป็น JavaScript ที่ปรับให้เหมาะสม สำหรับ Flutter Mobile, dart2native คอมไพล์ Dart เป็นโค้ด ARM เนทีฟ Flutter ยังรองรับ Dart DevCompiler (dartdevc) สำหรับการพัฒนา — มันแปล Dart เป็น JavaScript ได้เร็วกว่าแต่มีการปรับให้เหมาะสมน้อยกว่า
// babel.config.js — การแปลซอร์สโค้ด React Native
module.exports = {
presets: [
["module:metro-react-native-babel-preset"],
],
plugins: [
["module-resolver", {
root: ["."],
alias: {
"@": "./src",
"@components": "./src/components",
},
}],
"react-native-reanimated/plugin",
],
env: {
production: {
plugins: ["transform-remove-console"],
},
},
};metro-react-native-babel-preset รวมปลั๊กอินที่จำเป็นทั้งหมดสำหรับ React Native: JSX, Flow/TypeScript, ระบบโมดูล Metro, async/await, คุณสมบัติคลาส และตัวตกแต่ง ปลั๊กอิน module-resolver เพิ่มนามแฝงสำหรับการนำเข้าสั้น (@/components/Button แทน ../../components/Button) ในโหมดโปรดักชัน, transform-remove-console จะลบ console.log ทั้งหมดออกจากโค้ด
คำถามที่พบบ่อย
การแปลซอร์สโค้ด แปลโค้ดจากภาษาหนึ่งไปยังอีกภาษาหนึ่งในระดับเดียวกัน (เช่น TypeScript → JavaScript) การคอมไพล์ แปลจากระดับสูงไปยังระดับต่ำ (C++ → โค้ดเครื่อง) ผลลัพธ์ของการแปลซอร์สโค้ดสามารถอ่านได้ ผลลัพธ์ของการคอมไพล์ไม่สามารถอ่านได้
React Native ต้องการการแปลซอร์สโค้ดโดยค่าเริ่มต้น — Metro Bundler ใช้ Babel เพื่อแปลง JSX, TypeScript และ JavaScript สมัยใหม่เป็นโค้ดที่เข้ากันได้กับ JavaScriptCore และ Hermes หากไม่มี Babel, React Native จะไม่สามารถทำงานไวยากรณ์ JSX ของคอมโพเนนต์ได้
ได้: Babel กับ @babel/preset-typescript และ SWC รองรับการแปลซอร์สโค้ด TypeScript ซึ่งเร็วกว่า tsc แต่ Babel ไม่ทำการตรวจสอบชนิด — เพียงลบคําอธิบายประกอบชนิดเท่านั้น สำหรับการตรวจสอบชนิด คุณต้องเรียกใช้ tsc --noEmit แยกต่างหากหรือผ่าน fork-ts-checker-webpack-plugin
Source maps คือไฟล์ที่เชื่อมโยงโค้ดที่แปลแล้วกับซอร์สดั้งเดิม ช่วยให้ดีบัก TypeScript ในเบราว์เซอร์: จุดพักถูกตั้งค่าในไฟล์ .ts, stack traces แสดงบรรทัด .ts แทนที่จะเป็น .js หากไม่มี source maps การดีบักโค้ดที่แปลแล้วแทบจะเป็นไปไม่ได้
การแปลซอร์สโค้ดเอง ไม่ส่งผลต่อประสิทธิภาพของแอปพลิเคชัน — โค้ดเอาต์พุตทำงานด้วยความเร็วเดียวกับโค้ดที่เขียนด้วยภาษาเป้าหมายโดยตรง ค่าใช้จ่ายเพิ่มเติมจะเกิดขึ้นก็ต่อเมื่อตัวแปลซอร์สโค้ดสร้างโค้ดที่ไม่เหมาะสมที่สุด (เช่น Babel อาจสร้าง polyfill ขนาดใหญ่สำหรับเมธอดอาร์เรย์)
สรุป
เราจะพัฒนาแอปพลิเคชันบนมือถือแบบครบวงจร
IT Sectr สร้างแอปพลิเคชัน iOS และ Android สำหรับสตาร์ทอัพและธุรกิจตั้งแต่ปี 2017 เราจะให้คำแนะนำและเสนอวิธีแก้ปัญหาที่ดีที่สุดแก่คุณ
อ่านเพิ่มเติม