Write Roblox Games with TypeScript.

Try it online

import { CollectionService } from "@rbxts/services";

for (const obj of CollectionService.GetTagged("Lava")) {
  if (obj.IsA("BasePart")) {
    obj.Touched.Connect(part => {
      const character = part.Parent;
      if (character) {
        const humanoid = character.FindFirstChild("Humanoid");
        if (humanoid && humanoid.IsA("Humanoid")) {

Enter Type Safety

protected name?: string

With static types, you'll never have an error caused by a typo, indexing a nil value, or passing the wrong object to a function ever again.

Static types also guide your development with intelligent autocompletion for parameter types and structures from your own code, not just the Roblox API.

Working together, these features help you work faster and write better code at the same time.

Modern Syntax & Features

x.filter(i => i > 5).map(i => i * 2)

Lua is simple. That's great for beginners, but not for experienced developers who want to get stuff done. TypeScript rocks an elegant and modern feature set that blows Lua out of the water.

Arrow functions, object destructuring, functional data manipulation, and proper OOP structures is just a handful of what TypeScript has to offer.

Unparalleled Tooling

let unused = { name

Instantly have access to the development tools that millions of professionals use every day. Insightful static analysis, cohesive workflow with VS Code, intelligent linting from TSLint, and backed by a real package manager with versioned dependencies.

Welcome to the present.

Lua Interoperability

Lua Interoperability

Have an existing Lua code base? Don't worry. roblox-ts makes it easy to interop with existing Lua code by means of declaration files—just pair your Lua files with a special file that denotes what types it expects, and you're in action.

On the flip side, calling into TypeScript code from Lua is completely transparent and requires no extra effort or configuration.

interface BasePart extends PVInstance {
  Anchored: boolean;
  BrickColor: BrickColor;
  CFrame: CFrame;
  CanCollide: boolean;
  readonly CenterOfMass: Vector3;
  CollisionGroupId: number;
  Color: Color3;
  CustomPhysicalProperties: PhysicalProperties;
  Massless: boolean;
  Material: Enum.Material;
  Position: Vector3;

Typed Roblox API with Automatic Updates

roblox-ts offers TypeScript typings for the entire Roblox API, a hybrid of machine-generated types and hand-crafted overrides, enabling smart IntelliSense docs as you type. And whenever Roblox updates, a new version of @rbxts/types is automatically built and deployed, so you'll never have to wait for a human to start using new features.


Fostering an ecosystem of Roblox TypeScript packages

roblox-ts is backed by NPM, a trusted package manager with versioned dependencies. Your projects can rely on community-driven resources.

A centralized package manager ensures that every roblox-ts developer is on the same page.

Take a look at a list of user-created packages.

function returnsAPromise() {
  return new Promise((resolve, reject, onCancel) => {
    Promise.spawn(() => {
      let cancelled = false;

      onCancel(() => cancelled = true);

      while (!cancelled) {
        print("An async, cancellable operation!");

const promise = returnsAPromise();

Native Promises

Yielding sucks. With Promises baked in to the language, roblox-ts puts a modern async primitive at your fingertips. Promises give us a way to model any asynchronous operation without blocking, and make for easy handling when things fail.

Our Promises boast modern features like Promise inspection, finally, and cancellation with optional abort semantics.

async function getPage() {
  return HttpService.GetAsync("")

async function example() {
  const html = await getPage();
  return html.gsub("rep", "lace");

const promise = example()
promise.then(html => html.gsub("lace", "rep"))
  .then(html => print(html))


Async functions are special functions that implicitly create and return a Promise when you call them. Need to yield when calling a Roblox API or a library that doesn't use Promises? No problem—you can do so safely inside of an async function. Upon calling an async function, you get a Promise back instantly which resolves when the async function returns.

When working with a lot of Promises, the .then's can really add up. await is an operator that will yield until a Promise resolves. Since await only works inside of async functions, you'll never unintentionally block the thread.


Pairs with Popular Syncing Tools

The roblox-ts compiler pairs with the popular syncing tool Rojo in order to intelligently compile imports. If you change where your code will end up in your sync configuration, roblox-ts will automatically adapt on the next compile.

More Features