.motion2dproj 保存形式判断メモ
作成日: 2026-05-13
現行実装
現行の .motion2dproj は単一JSONファイルで、正規化済みPNGを data:image/png;base64,... のData URLとして内包する。
保存対象:
schemaVersion: 1app: "yurari"- 正規化PNG Data URL
- パーツ
- メッシュ
- リグ値とキーフレーム
- マウス入力設定
cameraTracking: "not_adopted"
保存しないもの:
- カメラ映像
- 音声
- 顔特徴量
- 外部モデル
- 絶対パス、OSユーザー名、デバイスID、ログ
初期仕様との差分
初期仕様では .motion2dproj はZIPコンテナで、manifest.json、assets/source.png、parts/*.json、meshes/*.json、rig/*.json、settings.json、licenses/THIRD_PARTY_NOTICES.md を含む想定だった。
現行実装は軽量MVPとして、ZIPコンテナではなく単一JSONに集約している。これにより実装と読み書きは単純だが、大きい画像ではJSONが肥大化しやすく、将来の差分保存やアセット分離には向かない。
今回の判断
今回はZIP化せず、スキーマ検証強化を先に実装する。
理由:
- 既存
.motion2dprojとの後方互換を維持しながら、破損・過大・想定外データを先に安全に拒否できる。 - ZIP化にはZip Slip、ZIP爆弾、総展開サイズ、ファイル数、圧縮率、パス正規化、ライセンス同梱のテストが必要で、今回の優先タスクより変更範囲が大きい。
- 新規ZIP依存を追加する場合はライセンス、保守状況、CSP影響、バンドルサイズのレビューが必要になる。
- Rust側でZIP処理を行う場合はTauri権限とファイルIO境界の設計が必要になる。
実装した検証
src/lib/projectValidation.ts に .motion2dproj 読み込み時の検証を追加した。
検証対象:
- JSONサイズ上限 75 MB
schemaVersionapp- 画像サイズ、総ピクセル数、PNG Data URL形式、Data URL上限
- パーツID、種別、ラベル、点数、座標範囲、重複ID
- メッシュ数、頂点数、三角形数、頂点ID、三角形インデックス、パーツ参照整合性
- リグ値のパラメータ範囲、キーフレーム、頂点差分参照整合性
- 入力設定の範囲
- 禁止データを示すキーの拒否
後方互換:
- 既存の
app: "single-image-motion-mvp"は読み込み時にyurariとして正規化する。 - 既存プロジェクトに新しい入力設定がない場合は既定値を補う。
- JSON + PNG Data URL形式の読み込みは維持する。
ZIP化する場合の設計メモ
v0.2以降でZIP化する場合は、以下を満たすまで実装しない。
- 旧JSON形式の読み込み互換を維持する。
- 新形式は
manifest.jsonを先に検証してから個別ファイルを読む。 - ZIP内パスに絶対パス、
..、制御文字、予約デバイス名を許可しない。 - 総展開サイズ、個別ファイルサイズ、ファイル数、圧縮率の上限を設ける。
- 画像は
assets/source.pngとして保存し、JSONへData URLを入れない。 - ZIP処理は可能ならRust側に寄せ、Tauri権限を必要最小限にする。
- ZIP化後もカメラ映像、音声、外部モデル、個人情報ログを含めない。
- ZIP依存を追加する場合は
docs/dependency_review.mdにライセンスと採用理由を追記する。