外部バイナリの埋め込み
アプリケーションに機能を追加したり、ユーザーが追加の依存関係(Node.jsやPythonなど)をインストールできないようにしたりするために、外部バイナリを埋め込む必要があるかもしれません。このようなバイナリを「サイドカー sidecar
」と呼びます。
バイナリは、任意のプログラミング言語で記述された実行ファイルです。一般的な使用例としては、pyinstaller
を使用してバンドルされた Python CLI アプリケーションや API サーバーなどが挙げられます。
お望みのバイナリをバンドルするには、tauri.conf.json
の tauri > bundle
オブジェクトに externalBin
プロパティを追加します。
externalBin
の設定では、絶対パスまたは相対パスのいずれかを使用して対象のバイナリを指定する「文字列のリスト」が必要です。
以下は、「サイドカー」の設定を説明するための「Tauri の設定」の抜粋(スニペット)です:
{ "bundle": { "externalBin": [ "/absolute/path/to/sidecar", "../relative/path/to/binary", "binaries/my-sidecar" ] }}
サポートされているどのアーキテクチャでも外部バイナリが動作するようにするには、指定されたパスに「同じ名前」と「接尾辞 -$TARGET_TRIPLE
」(ターゲット・トリプル)を持つバイナリが存在していなければなりません。
たとえば、"externalBin": ["binaries/my-sidecar"]
の場合、Linux では実行可能ファイル「src-tauri/binaries/my-sidecar-x86_64-unknown-linux-gnu
」が、Apple Silicon を搭載した Mac OS では実行可能ファイル「src-tauri/binaries/my-sidecar-aarch64-apple-darwin
」が必要となります。
《訳注》 ターゲット・トリプル 原文は target triple。Rust でクロスコンパイルを行なう場合のアーキテクチャの指定方式で、コンパイル対象(target)を三つ(triple)の項目「CPU ファミリー名」「メーカー名」「OS 名」で指定します。上記の説明例では
aarch64-apple-darwin
などのようにハイフンで結ばれた表記になっています。
次のコマンドで表示される「host:
」プロパティを見ることで、現在の プラットフォームの「接尾辞 -$TARGET_TRIPLE
」が判ります:
rustc -Vv
ほとんどの Unix システムに搭載されている grep
コマンドと cut
コマンドが使用できる場合は、次のコマンドでターゲット・トリプルを直接抽出できます:
rustc -Vv | grep host | cut -f2 -d' '
Windows では shell の代わりに PowerShell を使用します:
rustc -Vv | Select-String "host:" | ForEach-Object {$_.Line.split(" ")[1]}
次の例は、ターゲット・トリプルをバイナリに追加する Node.js スクリプトです。
import { execSync } from 'child_process';import fs from 'fs';
const extension = process.platform === 'win32' ? '.exe' : '';
const rustInfo = execSync('rustc -vV');const targetTriple = /host: (\S+)/g.exec(rustInfo)[1];if (!targetTriple) { console.error('Failed to determine platform target triple');}fs.renameSync( `src-tauri/binaries/sidecar${extension}`, `src-tauri/binaries/sidecar-${targetTriple}${extension}`);
このスクリプトは、それが実行されているアーキテクチャとは異なるアーキテクチャ向けにコンパイルした場合は機能しないので、自分用ビルド・スクリプトを作成するための出発点として使用してください。
Rust 側では、tauri_plugin_shell::ShellExt
トレイトをインポートし、AppHandle で shell().sidecar()
関数を呼び出します:
《訳注》 トレイト 原文は trait(性格の「特徴」「特質」、遺伝的な「形質」を表す語)。『Rust 日本語版』では、異なる型に対して共通の振る舞いを定義する、というような説明が行なわれています。「型の形質」=「型質?」
use tauri_plugin_shell::ShellExt;use tauri_plugin_shell::process::CommandEvent;
let sidecar_command = app.shell().sidecar("my-sidecar").unwrap();let (mut rx, mut _child) = sidecar_command .spawn() .expect("Failed to spawn sidecar");
tauri::async_runtime::spawn(async move { // stdout(標準出力)などのイベントを読み取ります while let Some(event) = rx.recv().await { if let CommandEvent::Stdout(line_bytes) = event { let line = String::from_utf8_lossy(&line_bytes); window .emit("message", Some(format!("'{}'", line))) .expect("failed to emit event"); // stdin(標準入力)に書き込みます child.write("message from Rust\n".as_bytes()).unwrap(); } }});
このコードを Tauri コマンド内に配置すれば、AppHandle を簡単に渡すことができ、ビルダー・スクリプト内に AppHandle への参照を保存すれば、アプリケーション内のどこからでも AppHandle へアクセス可能になります。
「サイドカー」を実行する場合、Tauri では、子プロセスで execute
または spawn
メソッドを実行する権限を「サイドカー」に付与する必要があります。この権限を付与するには、ファイル <PROJECT ROOT>/src-tauri/capabilities/default.json
に移動し、以下のセクションを権限配列に追加します。前述の「Note」欄で説明した「相対パスの記述方法」に従って「サイドカー」を記述することを忘れないでください。
{ "permissions": [ "core:default", { "identifier": "shell:allow-execute", "allow": [ { "name": "binaries/app", "sidecar": true } ] } ]}
JavaScript コード内では、@tauri-apps/plugin-shell
モジュールから Command
クラスをインポートし、sidecar
静的メソッドを使用します。
import { Command } from '@tauri-apps/plugin-shell';const command = Command.sidecar('binaries/my-sidecar');const output = await command.execute();
通常の コマンド を実行する場合と同じように、Sidecar のコマンドに引数を渡すことができます。
引数は 静的 static(たとえば -o
または serve
)または 動的 dynamic(たとえば <file_path>
または localhost:<PORT>
)のいずれかになります。引数は、呼び出す順番通りに定義します。「静的引数」はそのまま定義されますが、「動的引数」は正規表現を使用して定義します。
まず、src-tauri/capabilities/default.json
に、サイドカー・コマンドに渡す必要がある引数を定義します:
{ "$schema": "../gen/schemas/desktop-schema.json", "identifier": "default", "description": "Capability for the main window", "windows": ["main"], "permissions": [ "core:default", { "identifier": "shell:allow-execute", "allow": [ { "args": [ "arg1", "-a", "--arg2", { "validator": "\\S+" } ], "name": "binaries/my-sidecar", "sidecar": true } ] } ]}
あとは、サイドカー・コマンドを呼び出すには、すべての引数を配列として渡すだけです。
Rust では:
use tauri_plugin_shell::ShellExt;#[tauri::command]async fn call_my_sidecar(app: tauri::AppHandle) { let sidecar_command = app .shell() .sidecar("my-sidecar") .unwrap() .args(["arg1", "-a", "--arg2", "any-string-that-matches-the-validator"]); let (mut _rx, mut _child) = sidecar_command.spawn().unwrap();}
JavaScript では:
import { Command } from '@tauri-apps/plugin-shell';// 引数配列は `capabilities/default.json` で指定されたものと完全に一致することに注意してください。const command = Command.sidecar('binaries/my-sidecar', [ 'arg1', '-a', '--arg2', 'any-string-that-matches-the-validator',]);const output = await command.execute();
【※ この日本語版は、「Jan 06, 2025 英語版」に基づいています】
© 2025 Tauri Contributors. CC-BY / MIT