Native Libraries
This is how you give scripts access to your own code. You define a typed interface in Autolang, back it with JavaScript functions, and the VM calls them when scripts invoke those declarations.
If you haven't set up the compiler yet, start with the npm Integration Guide first.
๐ Registering a Native Library
Use registerBuiltInLibrary() to declare a library. You pass it a name, the Autolang source that defines the interface (functions and classes), a LibraryConfig, and the actual JavaScript implementations.
import { ACompiler, AutolangNativeFunc, LibraryConfig } from 'autolang-compiler';
const compiler = await ACompiler.create();
const greet: AutolangNativeFunc = (name) => {
return `Hello, ${name}!`;
};
const add: AutolangNativeFunc = (a, b) => {
return (a as number) + (b as number);
};
const config: LibraryConfig = {
autoImport: true, // available in all files without @import
allowLateinitKeyword: false,
allowNonNullAssertion: false,
};
compiler.registerBuiltInLibrary(
"my/utils",
`
@native("greet")
fun greet(name: String): String
@native("add")
fun add(a: Int, b: Int): Int
`,
config,
{ greet, add }
);
await compiler.compileAndRun("main.atl", `
println(greet("World"))
println(add(10, 32))
`);
console.log(compiler.getOutput());
// Hello, World!
// 42How arguments are passed
thisArg is injected unless the function belongs to a @js_object class instance โ in that case the VM binds the instance to JavaScript's this.For a full listing of LibraryConfig options and all exported types, see the Type Reference.
๐งฉ Wrapping JavaScript Objects with @js_object
When you need to pass a JavaScript object back and forth between the host and scripts (a query builder, a database connection, a stream), annotate the Autolang class with @js_object. This tells the compiler the class is a thin typed wrapper around a native JS object โ the VM preserves the reference and binds it to this when calling methods.
This lets you build clean, fluent APIs in Autolang (like .where().limit().execute()) while keeping the underlying JS object intact on the host side.
Use method shorthand, not arrow functions
@js_object methods rely on JavaScript's this binding, you must use standard function syntax or ES6 method shorthand when implementing them. Arrow functions (() => {}) capture this from the outer scope and will not work correctly.compiler.registerBuiltInLibrary(
"company/database", `
class Product (
val id: Int,
val name: String,
val price: Float
)
@js_object
class Query {
@native("query_where")
fun where(field: String, value: String): Query
@native("query_limit")
fun limit(count: Int): Query
@native("query_exec")
fun execute(): Array<Product>
}
class Database {
@native("create_query")
static fun createQuery(): Query
}
`,
{ autoImport: true },
{
create_query() {
return new JSQueryBuilder();
},
query_where(field, value) {
// "this" is the native JSQueryBuilder instance
return this.where(field, value);
},
query_limit(count) {
return this.limit(count);
},
query_exec() {
return this.execute();
}
}
);
await compiler.compileAndRun("main.atl", `
val products = Database.createQuery()
.where("category", "organic")
.limit(3)
.execute()
products.forEach {|p| println("- ${p.name}: $${p.price}") }
`);See a full working example with this pattern at Examples โ Fluent Query Builder.
๐ Error and Warning Callbacks
Instead of polling for errors after each run, you can subscribe to compiler diagnostics in real time. These callbacks fire during compilation โ not at runtime โ so they're useful for logging or surfacing issues to users immediately.
import { ACompiler } from 'autolang-compiler';
const compiler = await ACompiler.create();
compiler.setOnError((message: string) => {
console.error("[Autolang Error]", message);
});
compiler.setOnWarning((message: string) => {
console.warn("[Autolang Warning]", message);
});
// This will trigger the error callback
compiler.compile("main.atl", `
val x: Int = "not a number"
`);
// Pass null to unsubscribe
compiler.setOnError(null);
compiler.setOnWarning(null);To control what the script can access (HTTP, file system), see Security & Sandboxing.
