← Pasty トップへ
v0.9.7-beta

Pasty v0.9.7-beta

2026-06-22 リリース

Pasty v0.9.7-beta — 30 件の P1 + 4 件の Audit Follow-up

v0.9.6-beta の P0 安定化に続き、v0.9.5-beta Stability Audit で洗い出された 30 件の P1 と、Wave-2 audit で追加検出された 4 件の follow-up をまとめて落とします。「ホットパスを軽く、失敗を黙らせず、削除済みは本当に消す。」

⚡ パフォーマンス強化

同一テキスト連続コピー時の SHA256 を省略

クリップボード変化検出のたびに SHA256 を計算していましたが、lastTextString キャッシュを追加し、直前と同一文字列なら既存ハッシュをそのまま再利用します。長文を立て続けにコピーする場面で CPU 使用率が目に見えて下がります

OCR 同時実行を 2 並列に制限

複数の画像を同時にコピーすると Vision OCR が無制限に並走して AIEngine が CPU/メモリを吸い上げる挙動がありました。actor OCRQueue (max=2) で 同時 2 件まで に抑え、3 件目以降はキュー待ちにします。

正規表現の type-load コンパイル

SyntaxHighlighter がプレビュー描画ごとに try! NSRegularExpression(...) を実行していたものを、言語ごとの 静的プロパティに巻き上げ て型ロード時に一度だけコンパイルする方式に変更。コードプレビューが滑らかになります。

Markdown プレビューのメモ化

AttributedString(markdown:) のパース結果を clipID + contentHash をキーに NSCache (容量 256) で記憶します。同じクリップを繰り返し開いてもパースが走らず、長文 Markdown のプレビュー再表示が即座に。

Strip 検索結果の上限明示化

検索結果が大量ヒットした場合に StripPanel が無制限にロードしていた箇所に LIMIT 1000 を明示適用し、上限到達時は「結果が1000件を超えています。検索条件を絞り込んでください」とトーストでガイドします。

🔔 アップデート通知強化

Sparkle 失敗/成功デリゲートの完全実装

これまで Sparkle のダウンロード/インストール失敗はサイレントでした。failedToDownloadUpdate / didFinishUpdateCycleFor / didAbortWithError の 3 デリゲートを実装し、エラーを network / edsa / sandbox / other に分類してそれぞれ専用トーストを出します。インストール成功時も「Pasty を更新しました(バージョン X)」と通知。

起動直後の自動チェックを抑制

launchPad で初回ペーストする前に Sparkle がバックグラウンドチェックに走り、ペースト操作と HTTP リクエストが競合する微細なラグがあった問題を解消。初回ペースト完了起動から 30 秒経過 のいずれか早いほうまで初回チェックを遅延します。

🔐 セキュリティ + TCC

Accessibility 権限の永続アラート

セッション中にユーザーがアクセシビリティ権限を OFF にすると、これまではトーストのみで埋もれがちでした。NSAlert(5 分クールダウン付き)で 「システム設定を開く」 ボタン付きの永続アラートを出し、x-apple.systempreferences:com.apple.preference.security?Privacy_Accessibility に 1 クリックで遷移できるようにしました。

ペースト前の権限チェック順序を修正

PasteAutomator.emitCommandV がこれまで「先にクリップボードへ書き込んでから AX チェック」していたため、権限が剥がれた状態で ユーザーのクリップボードを意図せず上書き していました。チェックを 書き込み前 に移動し、未許可なら一切クリップボードを汚さず処理を中断します。

Blob ディレクトリの権限を 0o700 に固定

~/Library/Application Support/io.pasty.app/blobs/ と画像ステージング dir を毎起動 POSIX 0700 に再適用。他ユーザー / 他プロセスからの覗き見を防ぎます。

IntegrationHubs.undoLast() の AX ガード

Integration Hubs (Linear / Notion / GitHub 等の連携) の 取り消し操作CGEvent.post を AX チェック無しで叩いていた点を修正。AXIsProcessTrusted() で事前ガードし、未許可なら pastyPasteFailed 通知を出して失敗を可視化します。

🔎 削除済みクリップが完全に非表示に

v0.9.6-beta で読み出しパスに WHERE deleted_at IS NULL を入れましたが、Wave-2 audit で 3 つの抜け穴 が見つかりました。

SearchEngine の両パス

空クエリ (recent) と FTS5 MATCH の 両方deleted_at IS NULL を適用。検索で deleted clip が一瞬出るケースを根絶。

Pinboard.items(in:)

ピンボードに登録済みのクリップが ClipStore で soft-delete された場合、Pinboard 側では残骸として表示され続けていた問題を、JOIN に AND clips.deleted_at IS NULL を追加して解消。

InsightsDashboard の全集計

今日 / 週次 / 日次 / カインド別 / アプリ別 / 長期保存などの 全集計クエリdeleted_at IS NULL を入れました。削除済みクリップが統計のグラフを歪めることはなくなります。

FTS5 ソフトデリート同期 (migration v10)

最大の漏れは、deleted_at が NULL→値 に変わっても FTS5 インデックスからは削除されない ことでした。v10 マイグレーションで AFTER UPDATE OF deleted_at トリガーを追加し、soft-delete 時に FTS から除去 / 復元時に再投入する 完全同期 を実現。これで「アプリ再起動するまで MATCH に残骸が出る」が消えます。

🧩 エッジケース

HoverPreview のアニメーション競合

複数のホバープレビューを高速に行き来すると、古いアニメーション完了ハンドラが新しいパネル状態を破壊するレースがありました。animatingPanelID: UUID のトークン照合で 古い完了ハンドラを無視 するようにし、状態の整合性を確保。

Esc キーでドラッグ中断時のクリーンアップ

ドラッグ中に Esc を押すと panel は閉じるのに macOS 側のドラッグ状態が残ったまま で、次のクリックが drop と誤認される問題を解消。Esc 受信時にドラッグが進行中なら leftMouseUp CGEvent を合成してから clearAll() するようにしました。

NSScreen 構成変更への追従

ディスプレイの抜き差し / 解像度変更時に notch hot-zone と strip panel の座標がずれる問題を、NSApplication.didChangeScreenParametersNotification 購読で 再登録 + 再配置 することで解消。

📦 メモリ整理

StackPill の observer 解放

StackPill が NotificationCenter にぶら下げた screenObserver token を deinit で確実に解除。長時間稼働でも漏れません。

PastyApp の Stage-1 observer 解放

起動時に登録される Stage-1 observer 群を stage1Observers: [NSObjectProtocol] に保管し、applicationWillTerminate で一括解除。

DropDelegate の余計な main dispatch を削除

DropDelegate は AppKit / SwiftUI 仕様で main thread 呼び出しが保証されているのに、DispatchQueue.main.async で再ラップしていた箇所を解消。微小ですがレスポンスが軽くなります。

🛠 追加修正

AI エラーのケース別メッセージ化

AIError.modelNotAvailable / .osUnsupported / .aiDisabledBySettings / .other に分類し、4 種のローカライズ済みトースト を出すように。Apple Intelligence 未登録 / OS バージョン不足 / 設定 OFF / その他の区別がユーザー側で明確に。

DragDrop 部分失敗の可視化

複数アイテムのドロップで一部が失敗していた場合に、これまでは成功したものだけ静かに登録されていました。「N 件中 M 件のみ追加されました」 トーストで具体的な数を伝えます。

v5 entity\_uuid バックフィルの冪等化

過去の中断起動などで entity_uuid が NULL のまま残っていた行を救うため、UserDefaults フラグに依存せず毎起動 SELECT COUNT で残存を検査してバックフィルする方式に変更。

🧪 テスト

41 テスト pass — v0.9.6-beta の 36 件に加え、SoftDeleteFilterTests を 5 件追加:


リリース詳細: https://github.com/IvyGain/Pasty/releases/tag/v0.9.7-beta

GitHub Releases で詳細を見る ↗