🎏

MacからSSH接続したUbuntuでClaude Codeに画像をペーストする方法

に公開

はじめに

Claude Codeで画像を入力する方法として,以下の3つが提供されています:

  1. Claude Codeのウィンドウに画像をドラッグ&ドロップする
  2. 画像をコピーして,CLIに Ctrl + V で貼り付ける(※ Cmd + V は不可)
  3. Claudeに画像パスを指定する

これらの中で,2番目の Ctrl + V による貼り付けが最も直感的で実行しやすいため,この方法を実現しようとしました.

しかし,MacでVSCodeを使ってUbuntuサーバーにSSH接続した状態では,Ctrl + V で画像を貼り付けることができません.
これは,ローカル(Mac)とリモート(Ubuntu)のクリップボードが別々に管理されているためです.

本記事ではこの問題を解決する手順を,備忘録としてまとめます.

動作環境

  • ローカル: Mac mini (macOS)
  • リモート: Ubuntu Server
  • 接続方法: VSCodeのRemote-SSH拡張

必要なパッケージ

事前に以下のパッケージをインストールしておく必要があります.

Macでのパッケージ

brew install pngpaste
brew install terminal-notifier

Ubuntuでのパッケージ

sudo apt install inotify-tools
sudo apt install xclip

解決手順

スクリーンショットの画像をClaude Codeに入力する流れは以下のとおりです:

  1. Cmd + Shift + Ctrl + 4 でローカルのクリップボードに画像を保存
  2. Cmd + Shift + Ctrl + 5 で画像をサーバー上の /tmp/clipimg.png に転送
  3. サーバー側でそのパスを監視し,画像をクリップボードに登録(シェルスクリプトを systemd 経由で実行)
  4. Claude CodeのCLIで Ctrl + V により画像を貼り付け

全体の流れの中で設定が必要なのは2番目と3番目のステップです.以下では、この2つの手順を具体的に解説します.

手順1: Macから画像をサーバーに転送するスクリプトの作成

Macで実行するシェルスクリプトを作成します:

TMPFILE="/tmp/clipimg_mac.png"
/opt/homebrew/bin/pngpaste "$TMPFILE"
STATUS=$?

if [ "$STATUS" -ne 0 ]; then
  /opt/homebrew/bin/terminal-notifier -message "クリップボードに画像がありません." -title "転送失敗" -sound Boop
else
  scp "$TMPFILE" ws:/tmp/clipimg.png
  SCP_STATUS=$?
  if [ "$SCP_STATUS" -eq 0 ]; then
    /opt/homebrew/bin/terminal-notifier -message "ws:/tmp/clipimg.png" -title "転送成功" -sound Boop
  else
    /opt/homebrew/bin/terminal-notifier -message "scpコマンドの実行に失敗しました." -title "転送失敗" -sound Boop
  fi
fi

※ ws は .ssh/config に設定したSSHホスト名です.たとえば以下のように設定しておくと便利です:

Host ws
  HostName your.server.ip.address
  User your-username
  IdentityFile ~/.ssh/id_rsa

このスクリプトをAutomatorに登録し,ショートカットキーで起動できるように設定します.

Automatorの設定画面

筆者は Cmd + Shift + Ctrl + 4 でローカルのクリップボードに画像を保存しているため,それに隣接する Cmd + Shift + Ctrl + 5 をこのスクリプト用のショートカットに設定しました:

キーボードショートカットの設定画面

手順2: サーバーでクリップボード監視の設定

次に,サーバー側で画像ファイルを監視してクリップボードにコピーする設定を行います.

まず,/usr/local/bin/watch_clip.sh を作成します:

#!/bin/bash

inotifywait -m /tmp -e create |
  while read path action file; do
    if [[ "$file" == "clipimg.png" ]]; then
      xclip -selection clipboard -t image/png -i /tmp/clipimg.png
      rm /tmp/clipimg.png
    fi
  done

systemdサービスファイル ~/.config/systemd/user/watch_clip.service を作成します:

[Unit]
Description=Watch for clipimg.png and copy to clipboard

[Service]
ExecStart=/usr/local/bin/watch_clip.sh
Restart=on-failure
Environment=DISPLAY=localhost:10.0
Environment=XAUTHORITY=%h/.Xauthority

[Install]
WantedBy=default.target

⚠️ DISPLAY環境変数について
DISPLAY=localhost:10.0 の指定は,X11フォワーディング(ssh -X または -Y)を使ってVSCodeやSSHセッションを開いていることが前提です.
もしうまく動作しない場合は,X11転送が有効になっているか確認してください.

サービスを登録・有効化します:

systemctl --user daemon-reload
systemctl --user enable --now watch_clip.service

Discussion