sshfs経由のgit(idmapを含む): '.git/logs/HEAD'に接続できません:権限が拒否されました

sshfs経由のgit(idmapを含む): '.git/logs/HEAD'に接続できません:権限が拒否されました

質問:

sshfsを介してマウントされたgitリポジトリがあり、次のエラーメッセージで変更をコミットすることはできません。

fatal: cannot update the ref 'HEAD': unable to append to '.git/logs/HEAD': Permission denied

可能ですので参考にしてください

cp -a .git/logs/HEAD .git/logs/HEAD.bu
printf foo > .git/logs/HEAD
mv .git/logs/HEAD.bu .git/logs/HEAD

問題ないけど

printf foo >> .git/logs/HEAD

また、「権限が拒否されました」とマークしました。

質問:

自分のローカルコンピュータからリモートストレージにコミットするには、どの設定を変更する必要がありますか?

私が試したこと:

上記の症状を見ると、ファイルの追加に問題があるようです。私が見つけたSSHFSのGitリポジトリ: '.git/logs/HEAD'に接続できません:無効な引数これは以下を指します。https://github.com/libfuse/sshfs/issues/82提案された問題(他のいくつかのエラーメッセージを参照)を使用して解決できますwriteback_cache=no。後者のソースは、man次の警告/解決方法を引用するページを引用します。

CAVEATS / WORKAROUNDS
[...]
   O_APPEND
       When  writeback  caching is enabled, SSHFS cannot reliably support the O_APPEND open
       flag and thus signals an error on open.  To enable support for  unreliable  O_APPEND
       (which  may  overwrite  data if the file changes on the server at a bad time), mount
       the file system with -o unreliable_append.

ただし、このセクションは私のマニュアルページにはありません。

sshfs -V
SSHFS version 3.7.0
FUSE library version 3.9.1
using FUSE kernel interface version 7.31
fusermount3 version: 3.9.1

書き込みストレージキャッシュ機能を無効にしようとしたことがわかりました。実際に削除されました(後で障害のあるそして再度有効 1回以上今後)。だから私の考えではしなければならない大丈夫です。しかし、明らかに(まだ)問題があります。

私が言及するもう1つの問題は、リモートシステムのユーザー名とIDがローカルシステムのユーザー名とIDと一致しないため、その機能を使用する必要があることですidmap

そのfstab項目は次のとおりです。

<remote-user>@<remote-machine>: /mnt/ssh/<remote-machine>  sshfs  _netdev,user,idmap=user,allow_other  0 0

また、私の/etc/fuse.conf内容に

user_allow_other

背景:

答えを避けるには、次のようにしないでください。

  • 私はGitがどのように動作するかを知っています。
  • リポジトリをローカルに複製してコミットし、SSH経由でリモートリポジトリにプッシュできることを知っています。

私はなぜそれをしないか。 - リモートマシンでのみテストできるコードを追跡しているので、コミットする前に必ずテストしてみたいです。したがって、ある程度は避けるべき「単なる」便宜上の問題です。

  1. ローカルコピーでコードを編集します。
  2. ローカルコピーへの変更をコミットします。
  3. リモートレプリカにプッシュします。
  4. SSH(またはスイッチターミナル)を介してリモートコンピュータに接続します。
  5. リモートシステムでコードをテストします。
  6. 別のブランチを確認してください(強制プッシュを許可するには)。
  7. SSHセッションを終了します(またはターミナルに[再]]切り替え)。
  8. コードを編集してください。
  9. ローカルコピーで古いコミットを変更します。
  10. リモートレプリカに強制プッシュします。
  11. SSH(またはスイッチターミナル)を介してリモートコンピュータに接続します。
  12. 強制的に押された分岐を確認してください。
  13. 満足するまでステップ5〜11(ステップ7!)を繰り返します。

代わりに、私は以下が欲しい:

  1. SSH(またはスイッチターミナル)を介してリモートコンピュータに接続します。
  2. リモートコンピュータのリモートコピーでコードを編集します。
  3. リモートシステムでコードをテストします。
  4. リモートコンピュータのリモートコピーでコードを編集します。
  5. 満足するまで手順3~4(2段階!)を繰り返します。
  6. SSHセッションを終了します(またはターミナルに[再]]切り替え)。
  7. ローカルマシンの変更をリモートレプリカにコミットします。

リモートシステムから直接送信しないのはなぜですか? - コミットに署名したいのですが、秘密鍵をリモートコンピュータに委任できないからです。だから私が考えることができる最善の選択は次のとおりです。

  1. SSH(またはスイッチターミナル)を介してリモートコンピュータに接続します。
  2. リモートコンピュータのリモートコピーでコードを編集します。
  3. リモートシステムでコードをテストします。
  4. リモートコンピュータのリモートコピーでコードを編集します。
  5. 満足するまで手順3~4(2段階!)を繰り返します。
  6. リモートシステムのリモートコピーへの変更をコミットします。
  7. 別のブランチを確認してください(強制プッシュを許可するには)。
  8. SSHセッションを終了します(またはターミナルに[再]]切り替え)。
  9. リモートコピーから取得します。
  10. ローカルコピーで古いコミットを変更(署名)します。
  11. リモートレプリカに強制プッシュします。
  12. SSH(またはスイッチターミナル)を介してリモートコンピュータに接続します。
  13. 強制的に押された分岐を確認してください。

そのため、一方では、これらの追加手順を削除したいと思います(機能ブランチを追加すると、状況はより複雑になります。なぜなら、これらのブランチは両方のレプリカで正しく検証され、正しいトレースで構成される必要があるためです)。なぜ「ちょうど動作」しないのか理解したいです(tm)。


修正する:

フォローアップコメント渡す@トゥカン、デバッグ出力でエラーを再現しました。

  1. デバッグ出力を使用してリモコンをインストールします。
 mount -o sshfs_debug MOUNTPOINT
SSHFS version 3.7.0
executing <ssh> <-x> <-a> <-oClearAllForwardings=yes> <-2> <USER@SERVER> <-s> <sftp>
USER@SERVER's password:
Server version: 3
Extension: versions <2,3,4,5,6>
Extension: [email protected] <1>
Extension: [email protected] <1>
Extension: [email protected] <2>
Extension: [email protected] <2>
Extension: [email protected] <1>
remote_uid = 0
  1. 他の端末からマウントされた共有にアクセスします。
cd MOUNTPOINT/DIR_WITH_WRITE_PERMISSIONS
[00002] LSTAT
  [00002]          ATTRS       45bytes (188ms)
  1. 定期的な執筆作業を確認する:
echo foo > foobar
[00003] LSTAT
  [00003]         STATUS       38bytes (46ms)
[00004] LSTAT
  [00004]         STATUS       38bytes (32ms)
[00005] LSTAT
  [00005]          ATTRS       45bytes (242ms)
[00006] OPENDIR
  [00006]         HANDLE       29bytes (31ms)
[00007] READDIR
[00008] READDIR
  [00007]           NAME      668bytes (58ms)
[00009] READDIR
[00010] READDIR
  [00008]           NAME      483bytes (65ms)
[00011] READDIR
[00012] READDIR
  [00009]         STATUS       37bytes (27ms)
  [00010]         STATUS       37bytes (27ms)
[00013] CLOSE
[00014] LSTAT
  [00011]         STATUS       37bytes (27ms)
  [00012]         STATUS       37bytes (27ms)
  [00013]         STATUS       28bytes (26ms)
  [00014]         STATUS       38bytes (31ms)
[00015] OPEN
[00016] LSTAT
  [00015]         HANDLE       29bytes (153ms)
  [00016]          ATTRS       45bytes (158ms)
[00017] FSTAT
  [00017]          ATTRS       45bytes (29ms)
[00018] WRITE
  [00018]         STATUS       28bytes (28ms)
[00019] CLOSE
  [00019]         STATUS       28bytes (28ms)
  1. 接続しようとするとエラーが発生します。
echo bar >> foobar
[00020] LSTAT
  [00020]         STATUS       38bytes (74ms)
[00021] LSTAT
  [00021]         STATUS       38bytes (57ms)
[00022] LSTAT
  [00022]          ATTRS       45bytes (52ms)
[00023] OPENDIR
  [00023]         HANDLE       29bytes (53ms)
[00024] READDIR
[00025] READDIR
  [00024]           NAME      668bytes (68ms)
[00026] READDIR
[00027] READDIR
  [00025]           NAME      597bytes (77ms)
[00028] READDIR
[00029] READDIR
  [00026]         STATUS       37bytes (47ms)
[00030] CLOSE
  [00027]         STATUS       37bytes (47ms)
[00031] OPEN
[00032] LSTAT
  [00028]         STATUS       37bytes (47ms)
  [00029]         STATUS       37bytes (47ms)
  [00030]         STATUS       28bytes (26ms)
  [00031]         STATUS       43bytes (28ms)
  [00032]          ATTRS       45bytes (29ms)
zsh: permission denied: foobar

これが私の問題の根本的な原因を見つけるのに役立つことを願っています。


注:基準回答渡す@devidas(数週間必死に関心を集めて努力した後も解決策が不足しています)そのGitHub問題にクロスポストしました。

答え1

本当に大きくて詳細な質問です。この問題を段階的に解決しましょう。エラーは「権限が拒否されました」です。

Linux error code
EACCES          13      /* Permission denied */

sshfsリポジトリを検索すると、EACCESファイルに2つのインスタンスしかないことがわかりました。[sshfs.c][1]

一つは、ローカルコンテキストのファイル権限に関するものです。あなたが示したもの。

SSH_FX_PERMISSION_DENIED 他のものはSSH権限の拒否によるエラーです。

私が持っているデータに基づいてほぼ確実に話すことができます。ローカルコンピュータに対する権限がある場合

ケース

printf foo >> .git/logs/HEAD

これは代わりに権限が拒否された理由を提供します。

printf foo > .git/logs/HEAD

リモートコンピュータに対する権限がないか、参照されているO_APPENDリモートサーバーがサポートしていません。117号

straceを使用して確認できます。

その理由の一部です。この問題の解決方法は、お客様の回答によって異なります。どんな状況ですか?

より多くのお手伝いをさせていただきますようお知らせください。

同意しない場合は、自由にコメントを残してください。

関連情報