🏃

gistリポジトリに一発で移動したい

2021/07/10に公開

Linuxコマンドの勉強の一貫としてシェルコマンドを考えてみた。
もっとスマートなやり方などがあれば教えていただきたいです🙇🏻‍♂️


gistをメモとして利用するにあたってリポジトリをghq経由で落としてきたが、編集のたびにいちいちディレクトリを移動するのが面倒...

gistのリポジトリ名にはgithubとは違いハッシュ値が振られてしまうので、ぱっと見でどのgistなのかわかりにくい...

ということで、"一発で"は誇張しすぎたかもしれないが、簡単にghq配下のgistリポジトリへ移動するシェルコマンドを考えた。

先に結論

このコマンドを実行することで、ghq配下のgistリポジトリにfuzzy検索を用いて移動することができる。

$ cd "$(ghq list -p | grep $(gh gist list | awk '{print $1, $2}' | fzf | awk '{print $1}'))"

やっていることとしては単純で、ghq list -pで出力されるghq配下のローカルリポジトリのフルパスを、あいまい検索で特定されたgistリポジトリのハッシュ値でgrepしている。
gistリポジトリへ移動するために大枠をcdで囲んでおり、個々のコマンドの出力には無駄な情報が含まれているので、awkコマンドで必要な情報だけに絞っている。

必要なもの

実際に使用するには以下ツールが必要。

  • ghq
    ローカルでのリポジトリをまとめて管理できるようになる
  • github cli
    issue、PRなどの操作をcli上で行える
  • fzf
    cliでディレクトリやファイルなどのあいまい検索を提供する

ちなみにMacとzsh上で動作しているが、Linuxでもおそらく動くはず。

注意点

どのgistリポジトリにするのかという部分は、gistの説明文をfzfで曖昧に検索しているため、説明文が設定されていないと移動したい対象をハッシュ値で特定することになる。
また、gh gist listはリモートリポジトリ上の全てのgistが出力される。
そのためハッシュを特定したとしてもローカルリポジトリ(ディレクトリ)が存在しなければ移動できない。

本当はローカルに存在するgistだけを表示したいが、更にコマンドが複雑化しそうだったのと、必要であればローカルにghq経由でダウンロードできるので、一旦これでよしとしたい🥲

導入方法

コマンドを**.zshrc**などの設定ファイルに記載する。
注意点にも書いたがローカルに存在しないgistリポジトリを選んでしまった場合のためにifで回避し、エイリアスでfunctionを呼び出している。

.zshrc
# ghq配下のリポジトリに移動する
function cd_ghq_on_fzf {
  local dir="$(ghq list -p | grep $(gh gist list | awk '{print $1, $2}' | fzf | awk '{print $1}'))"
  if [ -n "$dir" ]; then
    cd "$dir"
  else
    echo "no such ghq directory"
  fi
}

alias sd='cd_ghq_on_fzf'

あとはターミナル上でsdと叩けばおk

github上のリポジトリも検索対象にする

以下のコマンドを使用する。
上記のコマンドの結果にghq list -pでローカルにあるgistではなくgithub側のリポジトリの一覧を足しています。

$ cd "$(ghq list -p | grep $((gh gist list | awk '{print $1, $2}' ; ghq list -p | grep -v gist) | fzf | awk '{print $1}'))"

同じように設定ファイルに記載する。

.zshrc
# ghq配下のリポジトリに移動する
function cd_ghq_on_fzf {
  local dir="$(ghq list -p | grep $((gh gist list | awk '{print $1, $2}' ; ghq list -p | grep -v gist) | fzf | awk '{print $1}'))"
  if [ -n "$dir" ]; then
    cd "$dir"
  else
    echo "no such ghq directory"
  fi
}

alias sd='cd_ghq_on_fzf'

実際につかってみよう

まずghqで管理しているリポジトリの一覧を確認してみます。

ふむふむ、github.comとgist.github.comというサービス名でディレクトリが別れていて、その下にユーザー名のディレクトリがありますね。
更にその下に各リポジトリを配置していますが、gistリポジトリは53be64ff4a82e9770c744146724a07cbというハッシュ値がディレクトリ(リポジトリ)名になってますね。
これでは、このリポジトリが指しているgistがどれなのかわからない...

そこで今回作ったsdを実行してみましょう。
最初はdotfilesというディレクトリにいます、覚えておいてください。

実行するとfzfが立ち上がり、github.comとgist.github.comの全てのリポジトリが表示されました!
でもまだ3件しかないのでいいけど、もし1000件あったらどうしよう...

安心してください!fzfはあいまい検索を提供してくれるのでぱっと思い浮かんだワードをターミナルに入力すれば、リポジトリを絞ってくれます!

あとはEnterを押すだけ。
dotfilesから対象のレポジトリに移動していることがわかりますね!
パット見ではどのgistなのかわからなかったこのディレクトリに、gistの説明文からハッシュ値を特定して移動してくることができました!

最後に

pecoを使ってghq配下のリポジトリへ移動する記事をいくつか見かけたが、fzfでかつgistを対象にしたものはなかったので作ってみた。
これでターミナル上でgistをメモツールとして使えるようになったので、積極的に活用したい。

作ってる最中に、gistをgithubリポジトリとして集約する方法を見つけて「あれ、こっちのやり方でやればgistリポジトリのハッシュ値も回避できて管理が楽じゃね」と思ったのは内緒の話。
Github Gist を1個のレポジトリでまとめて管理する ( git submodule を利用 )

あと都度更新するメモとしてはzennのスクラップでも可能なため、cli対応されたら100%乗り換えると思う🤣

Discussion