Cara yang Benar Menjalankan Typescript di Node.js

·

Dunia pemrograman website tahun 2025 ini sudah banyak developer yang mengadopsi typescript sebagai bahasa pemrograman untuk membuat website atau aplikasi berbasis nodejs.

Kenapa typescript lebih baik dibanding javascript?. Selain memberikan penulisan tipe pada bahasa javacsript, juga memberikan kemudahan programmer untuk mengubah, mengatur dan mengembangkan software karena typescript menjaga setiap data memiliki tipe yang tepat.

Kenapa nodejs? tidak runtime bun atau runtime deno? karena nodejs sudah ada sejak tahun 2009, artinya ketika artikel ini ditulis sudah berusia 16 tahun!. Pengalaman yang panjang ini pastinya memberikan pengalaman yang solid, komunitas yang luas, dan support yang banyak.

Typescript

Bagaimana cara terbaik menjalankan typescript di nodejs?, mari lihat bagaimana typescript bekerja dengan cara install typescript di folder projek.

$ npm init
$ npm install typescript
$ npx tsc --init

Siapkan file typescript seperti ini

src/main.ts
const person: {
  name: string;
  age: number;
} = {
  name: "John Doe",
  age: 30,
}

console.log(`Name: ${person.name}, Age: ${person.age}`);

Kemudian ubah file typescript menjadi javascript menggunakan perintah tsc

Bash
$ ls src
main.ts # hanya 1 file typescript
$ npx tsc
$ ls src 
main.js main.ts # menjadi 2 file

Setelah konversi, maka sekarang kita bisa menjalankan file javascript menggunakan nodejs

Bash
$ node src/main.js
Name: John Doe, Age: 30

Mari kita coba import dari module yang berbeda

TypeScript
// ./src/greet.ts
export const greet = (name: string): string => {
  return `Hello, ${name}!`;
}

// ./src/main.ts
import { greet } from './greet';

const person: {
  name: string;
  age: number;
} = {
  name: "John Doe",
  age: 30,
}

console.log(greet(person.name));

Kode diatas akan menghasilkan kode javascript seperti berikut

TypeScript
// ./src/greet.js
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.greet = void 0;
const greet = (name) => {
    return `Hello, ${name}!`;
};
exports.greet = greet;

// ./src/main.js
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const greet_1 = require("./greet");
const person = {
    name: "John Doe",
    age: 30,
};
console.log((0, greet_1.greet)(person.name));

Ok, nampaknya cukup ribet, tapi kode main.js bisa dijalankan dengan baik.

Bash
$ node src/main.js
Hello, John Doe!

CommonJS vs Module

Sekarang kita coba gunakan library yaitu chalk agar program kita lebih berwarna

Bash
$ npm install chalk

Kemudian update fil greet.ts menjadi seperti ini

TypeScript
import chalk from "chalk";

export const greet = (name: string): string => {
  return `Hello, ${chalk.green(name)}!`;
}

Lalu kita coba jalankan seperti langkah sebelumnya

Bash
$ npx tsc
$ node ./src/main.js
/Users/riochandra/dev/project/typescript/src/greet.js:7
const chalk_1 = __importDefault(require("chalk"));
                                ^

Error [ERR_REQUIRE_ESM]: require() of ES Module /Users/riochandra/dev/project/typescript/node_modules/chalk/source/index.js from /Users/riochandra/dev/project/typescript/src/greet.js not supported.
Instead change the require of index.js in /Users/riochandra/dev/project/typescript/src/greet.js to a dynamic import() which is available in all CommonJS modules.
    at Object.<anonymous> (/Users/riochandra/dev/project/typescript/src/greet.js:7:33) {
  code: 'ERR_REQUIRE_ESM'
}

Node.js v22.3.0

Wow.. error? Kenapa ini?

Error ini mengatakan bahwa “Membutuhkan ESM dari modul chalk”. ESM adalah ECMAScript Modules. Sebelum memcahkan masalah ini lebih baik kita kenali dahulu sejarahnya, Nodejs terdapat 2 tipe kode javascript yaitu

CommonJS

Tipe kode original javascript. Masih menggunakan require untuk memanggil modul lain

TypeScript
const chalk = require('chalk');

console.log(chalk.green("hello"));

ESM (ECMAScript Modules)

Standard Javascript baru untuk memudahakan developer. Contohnya Menggunakan import from untuk memanggil modul lain.

TypeScript
import chalk from 'chalk'

console.log(chalk.green("hello"));

Secara default tsc mengubah typescript menjadi CommonJS. Tetapi module yang diimport didalam kode javascript (contohnya chalk) menggunakan tipe ESM. Perbedaan Tipe ini membuat kode javascript tidak bisa dijalankan.

Hanya ada 2 cara agar kode ini bisa dijalankan yaitu:

  1. Kode projek diubah menjadi ESM
  2. atau bundle seluruh kode (termasuk modul seperti chalk) menjadi CommonJS

Cara 1: Ubah kode projek menjadi ESM

  1. tambah type: module di file package.json
package.json
{
  "name": "typescript",
  "version": "1.0.0",
  "main": "index.js",
  "type": "module",                                                                                            
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "",
  "license": "ISC",
  "description": "",
  "devDependencies": {
    "typescript": "^5.8.3"
  },
  "dependencies": {
    "chalk": "^5.4.1"
  }
}

2. ubah module di tsconfig.json

tsconfig.json
    "module": "NodeNext", /* Specify what module code is generated. */

3. tambah .js pada file yang di-impor

TypeScript
import { greet } from './greet.js';

const person: {
  name: string;
  age: number;
} = {
  name: "John Doe",
  age: 30,
}

console.log(greet(person.name));

Selesai.

Sekarang kita bisa jalankan kode typescript tanpa masalah

Bash
$ npx tsc && node src/main.js
Hello, John Doe!

Metode ini bisa berjalan normal di lingkungan nodejs saja, sedangkan dilingkungan browser hanya browser terbaru sejak 2016.

Cara 2: Ubah seluruh projek menjadi CommonJS

Mengubah seluruh projek kode termasuk modul terinstall menjadi commonjs adalah salah satu cara yang sering digunakan, selain support pada browser dan teknologi lama juga memiliki kemungkinan digunakan oleh banyak lingkungan.

Typescript tidak bisa mengubah kode didalam node_modules, bundling datang jadi solusi untuk mengubah dan menggabungkan seluruh script menjadi satu file javascript (atau beberapa file). Konsep ini lebih mirip seperti mengubah kode c++ menjadi Executable Binary.

Library yang sering digunakan untuk bundling adalah seperti webpack, esbuild, dan parcel. Kali ini kita akan gunakan esbuild karena kecepatannya dan support typescript. Sehingga kita tidak memerlukan tsc kecuali untuk pengecekan tipe saja.

Mari kembalikan module di tsconfig.json jadi CommonJS

tsconfig.json
- "module": "ESNext", /* Specify what module code is generated. */
+ "module": "CommonJS", /* Specify what module code is generated. */

Pada file main.ts import file tanpa .js, sehingga seluruh file main.ts seperti ini

main.ts
-import { greet } from './greet.js';
+import { greet } from './greet';

const person: {
  name: string;
  age: number;
} = {
  name: "John Doe",
  age: 30,
}

console.log(greet(person.name));

Install package esbuild

Bash
npm install --save-exact --save-dev esbuild

Buatlah script tambahan di file package.json.

package.json
{
  "name": "typescript",
  "version": "1.0.0",
  "main": "index.js",
  "type": "commonjs",
  "scripts": {
    "build": "esbuild src/main.ts --bundle --platform=node --target=node18 --outdir=dist"
  },
  "author": "",
  "license": "ISC",
  "description": "",
  "devDependencies": {
    "esbuild": "0.25.2",
    "typescript": "^5.8.3"
  },
  "dependencies": {
    "chalk": "^5.4.1"
  }
}

Script esbuild memiliki beberapa konfigurasi yaitu:

  • src/main.ts, file permulaan yang dibaca pertama kali
  • --bundle: Menggabungkan semua file js menjadi 1
  • --platform=node: compile untuk nodejs, bukan browser
  • --target=node18: karena untuk nodejs, maka targetkan minimal versi nodejs
  • --outdir=dist: output folder yaitu folder dist

Jalankan perintah npm run build

Bash
$ npm run build

> typescript@1.0.0 build
> esbuild src/main.ts --bundle --platform=node --target=node18 --outdir=dist

  dist/main.js  15.8kb

 Done in 11ms

Periksa apakah file js bisa dijalankan

Bash
$ node dist/main.js
Hello, John Doe!

Ok, it works perfectly.

Sebagai tambahan, esbuild tidak memeriksa tipe data typescript, maka perlu konfigurasi tambahan

jika bentuk kode seperti ini, ini harusnya error karena other tidak tersedia, tetapi esbuild tidak akan memeriksa itu.

TypeScript
import { greet } from './greet';

const person: {
  name: string;
  age: number;
} = {
  name: "John Doe",
  age: 30,
}

// harusnya error
console.log(greet(person.other));

Maka, untuk memeriksa error harus jalankan perintah tsc --noEmit untuk memeriksa data

Hanya menggunakan esbuild, tidak error

Bash
$ npm run build                                                               

> typescript@1.0.0 build
> esbuild src/main.ts --bundle --platform=node --target=node18 --outdir=dist


  dist/main.js  15.8kb

 Done in 25ms

Tambahkan npx tsc --noEmit SEBELUM menjalankan build untuk memeriksa tipe

Bash
$ npx tsc --noEmit && npm run build
src/main.ts:11:26 - error TS2339: Property 'other' does not exist on type '{ name: string; age: number; }'.

11 console.log(greet(person.other));
                            ~~~~~


Found 1 error in src/main.ts:11

Dengan cara mengubah kode ESM menjadi CommonJS akan menjadikan kode projek bisa dijalankan SELURUH runtime javascript termasuk browser.

Kesimpulan

Menjalankan typescript di nodejs memerlukan beberapa library seperti typescript dan bundling untuk mengubah kode typescript menjadi javascript. Pemilihan esbuild sebagai library bundling sangat bagus karena sudah support typescript secara default dan memiliki fitur bundling. Terima kasih sudah membaca semoga bermanfaat.

    Comments

    Leave a Reply

    Your email address will not be published. Required fields are marked *