TAURIを触ってみて感じたこと

# はじめに
つい先日,新生デスクトップアプリフレームワーク,Tauriが登場した。ViewをWeb技術を利用して書けるため,フロントエンドエンジニアでも気軽にデスクトップアプリを開発することができる。そんなTauriだが以前から存在している似た志向のElectronと比較して,TauriがElectronの代替となるのか,それともそうはならないのか。そして,個人的にTauriに関して気になったこと等をまとめる。

# 記事を書こうと思ったきっかけ
私は文化祭を前に音楽ゲーム制作をしている。音楽ゲームは,文化祭後一般公開の予定をしており,また気軽に遊べ,クロスプラットフォームを目指した開発をしているため,WebGLを利用することとなった。文化祭では,数台のPCを利用しての展示になり,他の作品も展示されるので,ネットワーク帯域の乱用は避けたく,またゲーム公開後もオプションとしてアプリ版の提供も考えていたためにElectronの利用を考えていた。しかし,Tauriのv1.0の到達により,こちらも選択肢として考え,最終的にどちらにするかを決めようと思ったからである。

# 早速比較してみる
Electronは主にChromiumベースで開発されており,そこにnode.jsのV8を入れた形である。レンダリングエンジンやAPIなど全部入りで提供されている。
一方でTauriはRustで開発され,バックエンドとその他のAPIのみの提供とされている。レンダリングエンジンを積まないことで高速化と軽量化を図ったと言うわけだ。

以下の表はGithubからの一部引用だ。
| 比較 | Tauri | Electron |
|:-:|:-:|:-:|
| インストーラサイズ | 3.1MB | 52.1MB |
| メモリ利用量 | 180MB | 462MB |
| 起動速度 | 0.39秒 | 0.8秒 |
| レンダリング | WRY | Chromium |

見れば分かるように,Tauriが圧倒的なパフォーマンス差をつけている。ところでWRYは何なのだろうか？

## WRY is 何？
WHR,ついついWhy?と間違えそうになるというのはさておき,TauriはOSのWebViewを呼び出すものだ。これを利用することでパフォーマンスの大幅な向上が狙える。また,いくつかのAPIも提供されているため,それらの使用も可能だ。
LinuxではWebKitGTK,WindowsではEdgeのWebView2,MacOSでは恐らくSafariが使われると思われる。OSごとの大幅なレンダリング差異は無さそうだ。また,EdgeのWebView2ではChromiumベースであるため,Windows7以降が必要だ。

# 早速試してみる。
### 準備
どうやらRustとVisual StudioのC++によるデスクトップ開発のインストール必要だ。
[Rust インストール](https://www.rust-lang.org/tools/install)
[Visual Studio インストール](https://visualstudio.microsoft.com/ja/thank-you-downloading-visual-studio/?sku=Community&channel=Release&version=VS2022&source=VSLandingPage&cid=2030&passive=false)

インストールが完了したら,次にTauri CLIをインストールする。CargoとNPMどちらでも利用可能。今回はNPMを利用する。
`cargo install tauri-cli --version "^1.0.0"`
`npm i -D @tauri-apps/cli`

`npx tauri  -h` でヘルプを確認できる。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/999574/cf55be42-d26a-ec2e-4d89-31bd63a3392a.png)

create-tauri-appを利用することで簡単に制作を開始できる。今回は使用しない。
`npm i  create-tauri-app`
`npx create-tauri-app`

`npx tauri init`コマンドでtauriのイニシャライズを行う。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/999574/ca42672d-c6f5-f9ef-bdad-275b12289d17.png)

いくつかの質問にたいして入力し,Enterを叩く。
3番目の質問`Where are your web assets (HTML/CSS/JS) located relative to the "<current dir>/src-tauri/tauri.conf.json" file that will be created?`には/src-tauri/tauri.conf.jsonからHTML等の入ったフォルダを相対パスで指定する。
4番目の質問は基本的に3番目のものと同じでよい。

## HTMLを書く
サクッと一分くらいでHello Worldを書きます。コードは割愛します。

### ビルド
そしたらいよいよビルド。
`npx tauri build` でインストーラをビルド,`npx tauri dev`で開発用ビルドを起動
今回はdevを使用します。コマンドを叩いたらビルドにしばらくかかるのでお茶でも淹れて待ちましょう。

ビルドが終わるとTauriが起動します。いい感じ。F12やCtrl+Shift+iで開発者ツールを開くことができる。今回はWindowsなのでEdgeの開発者ツールと同様のものが起動するはずだ。
ロケーションは`https://tauri.localhost`。
ビルド後にHTML等を弄っても反映されないのでリビルドが必要かも。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/999574/75c1c529-89f8-1eee-f3c8-1a38f349c9bc.png)

## カスタムコマンド
メインプロセスの方で関数を定義し,レンダラーから呼び出す事ができる。
```rust:main.rs
fn main() {
  tauri::Builder::default()
    .invoke_handler(tauri::generate_handler![my_custom_command]) //追加
    .run(tauri::generate_context!())
    .expect("failed to run app");
}

#[tauri::command]  //カスタムコマンド
fn my_custom_command() {
  println!("I was invoked from JS!");
}
```

```js:index.js
//下記のうちどちらかを使用
//npmパッケージからインポート
import { invoke } from '@tauri-apps/api/tauri'
//window.__TAURI__ オブジェクトから
const invoke = window.__TAURI__.invoke

//呼び出し
invoke('my_custom_command')
```

これなら安易にJavascriptを実行してXSSされる危険性も無いだろう。
また,バックエンドがRustという強力な言語で書けることも魅力的である。

## さいごに
今回はTauriがバージョン1.0を迎えたということでお試し感覚で触ってみたが,特に難しいことも無く,シンプルで使いやすそうだという印象を受けた。少しデメリットがあるとすればビルド中に優雅にお茶を嗜めることくらいだろうか。
また,バックエンドがRustで書けるのも非常に良い点であり,余裕が有るならばRustを学んでみるのもアリだろうと感じた。
勿論,Electronは長年あるプロジェクトでパッケージやAPIが豊富にあり,さらにはすべてJavascriptで書け,TypeScriptを利用すればデータの処理等の際に同じ型データを利用できるのでそのような部分には軍配が上がりそうだ。
Tauriが非常に強力なのは間違いないが,Electronのほうが学習コストが低く,また手軽にビルドや実行ができるために一定の需要は残りそうだ。
音楽ゲームのアプリのフレームワークにTauriを利用する可能性は高く,また,Rustに少し興味を持てたような気がする。

いかがだっただろうか。この記事でTauriに少し興味を持ってもらえたら嬉しく思う。勿論やっぱりElectronだと思うならばそれでも良いし,新しいものに挑戦するならばそれでも良い。是非,良いデスクトップアプリ開発ライフを送ってもらえたらと思う。