while / for、enum、List、const、+= など、実用寄りの機能がどんどん追加されたlibrary! マクロで登録がかなり書きやすくなったhashmaps、ユーザー定義 state、generic functions、formatter、LSP などが課題Rotoは、Rustアプリの中で動かすためのスクリプト言語です。
ただの「スクリプト」ではなく、型が静的に決まる(実行前に型がチェックされやすい)うえに、JIT-compilation(実行しながら高速化する仕組み)を使うのが大きな特徴です。
ここが面白いところで、普通のスクリプト言語は「手軽だけど遅い」か「速いけど扱いが重い」のどちらかになりがちです。Rotoはその中間を狙っている感じで、Rustアプリに安全に、しかもそこそこ速く、外部から動きを差し替えられるのが強みだと思います。
NLnet Labs はこれを自分たちの Rotonda というプロジェクトのために育てていますが、記事を見る限り、かなり汎用的な形にもなってきています。
記事では、公開からの1年を振り返って、こんな変化があったとまとめています。
こうして見ると、単なる「試作」ではなく、かなりちゃんとした道具に育ってきたのがわかります。
個人的には、ロゴができたという話が地味に重要だと思います。技術プロジェクトって、ロゴがあると急に“内輪の実験”から“外に出すプロダクト”っぽくなるんですよね。あれ、意外と効きます。
Rotoはこの1年で、言語としてずいぶん充実しました。
追加された主な機能はこんな感じです。
while と for ループ% などの演算子追加enum+= のような compound assignmentglobal const bindings中でも大きかったのは List型 だそうです。
Rotoのあらゆる型のリストを作れて、連結したり、反復処理したりできます。しかも、RustとRotoの間でそのリストをやり取りするのが難所だったのに、今ではちゃんとサポートされ、コストも比較的低いとのこと。
ここはかなり重要です。スクリプト言語って「おもちゃ」は作れても、Rust本体とデータをやり取りするところで急にしんどくなることが多いんです。そこを通したのは、実用性の大きな前進だと思います。
Rotoは文法も少し変わって、Rustに似せてきました。
function ではなく fn# コメントではなく //これは地味だけど、かなり良い変更ではないかと思います。
Rustを書いている人にとっては学習コストが下がるし、見た目の違和感も減ります。もちろんRotoはRustの完全なサブセットにはならないそうですが、それでいいんだと思います。全部Rustに寄せすぎると、今度は「Rustでよくない?」になりがちなので。
記事にはこんな例も載っています。雰囲気をつかむにはちょうどいいです。
const DUTCH_CITIES: List[String] = [
"Amsterdam",
"Rotterdam",
"Utrecht",
"Delft",
];
fn is_dutch_location(x: String) -> String {
// Note: you can also use the contains method on a list, but this
// shows off more new language features.
for city in DUTCH_CITIES {
if x == city {
return f"The beautiful Dutch city of {x}!";
}
}
f"{x} is not in the Netherlands..."
}
Rotoの価値は、言語単体よりもRustアプリにどう組み込めるかで決まります。
記事ではここが大きく改善されたと強調されています。
昔は、Rustの型や関数を登録するのに、こんな感じで少し面倒でした。
runtime を渡す正直、こういうのは「動くけど、あまり気持ちよくない」パターンです。
新しいやり方では、library! マクロを使って、Rustらしくまとめて書けます。
impl ブロックや docstring、self も使えるようになっていて、かなり自然です。
要するに、Rustの普通のコードを書く感覚に近づいたということです。
これは地味ですが、とても大きい改善です。埋め込み言語は、最終的に「書くのが面倒だと誰も使わない」ので、APIの気持ちよさはかなり大事だと思います。
Rotoには、Richard de Ruijter さんがデザインした正式なロゴができました。
記事では「fun and playful」という方向性が強調されています。
技術系のコンポーネントって、性能や機能ばかり語られがちですが、こういう視覚的なアイデンティティも意外と効きます。
「これはちゃんと育てるつもりのプロジェクトなんだな」と伝わるからです。
今後は manual、slides、sticker など、いろいろな場所で使われる予定とのことです。
この1年で、Rotoは EuroRust 2025 と FOSDEM 2026 で紹介されました。
こういう発表があると、プロジェクトの理解しやすさが一気に上がります。
特に、実装の裏側まで話してくれるのは良いですね。使う側だけでなく、「どう設計しているのか」が見えると信頼感が増します。

記事でもっとも嬉しそうなのが、この話かもしれません。
Rotoは NLnet Labs の外でも使われ始めていて、最初の採用例は Iocaine です。
Iocaine は、WebサーバーをAI crawlerから守って、わざと“ゴミ”を返すような scriptable proxy とのこと。
この Iocaine では、Roto / Lua / Fennel を使えるそうですが、同梱されるデフォルトスクリプトは Roto で書かれているそうです。
理由は、作者によれば 3つの言語の中でRotoが最も性能が良かったから。
これはかなり重要な実績です。
「速いと言っていたけど、本当にそうなの?」という疑問に、少なくとも実運用の場で答えが出始めているわけです。
もちろん、1件の採用で全部が証明されるわけではありません。でも、実際に外部で使われ、バグ報告や機能要望が集まるのは、プロジェクトとしてかなり良い流れだと思います。
記事では、Iocaine の作者 Algernon さんへの感謝も述べられています。
こういう相互作用で、言語やツールは一気に育つんですよね。
Rotoはかなり成熟してきたものの、まだ終わりではありません。
今後ほしいものとして、記事では次のようなものが挙げられています。
hashmaps個人的には、formatter と LSP がかなり重要だと思います。
言語機能が増えるのも大事ですが、毎日使うなら「コードを整える」「補完が効く」「エラーがわかりやすい」が効いてきます。
つまり、言語の完成度は“文法の豊富さ”だけでは決まらないんです。使うときの気持ちよさが本丸です。
この1年のRotoは、単に機能が増えただけではなく、
という意味で、プロジェクトとしての地盤が一気に固まった1年だったと言えそうです。
Rustアプリに「安全に動く、でも表現力のあるスクリプト」を埋め込みたい人には、かなり面白い選択肢ではないでしょうか。
まだ未完成な部分はあるものの、記事を読む限り、かなり筋の良い方向に進んでいると思います。
参考: One year of Roto, a compiled scripting language for Rust