(git4)tig(Gitツール)インストール

# ■概略
オープンソースエンジニア歴30年超の筆者が2023年からIBMiを学びだした学習記録です
IBMiでtigをコンパイルした手順です

## <u>◯前提(gitコマンドではなくgitツールが望ましい)</u>
・gitコマンドでbranchを作る時はデフォルトでは現在のbranchから作成される  
・gitコマンドではbranch作成前に現在のbranch確認コマンド入力が必要で一手間多い  
・branch作成時に親branchを強制するI/Fのgitツールがほしい  
・ソースコードをIBMiのIFS上に置くので、IFSで稼働するTUIのgitツールがほしい  
　TUI = TextUserInterface  
  
・TUI gitツールの候補は3つ  
<table border="1" style="border-collapse:collapse;width:800px">
<tr bgcolor=silver><th>TUIツール名</th><th>Googleヒット数</th><th>登場</th><th>開発言語</th></tr>
<tr align=center><td>tig</td><td>394万件</td><td>2016/04から</td><td>C</td></tr>
<tr align=center><td>lazygit</td><td>146万件</td><td>2018/08から</td><td>Go</td></tr>
<tr align=center><td>gitui</td><td>135万件</td><td>2020/04から</td><td>Rust</td></tr>
</table>

どれもIFSのyumパッケージには入っていない  
どれもLinux/Mac/Windowsのバイナリはあるが、IBMiのAIX/PPC64のバイナリはない  
lazygitはGoから、gituiはRustからAIX/PPC64へのクロスコンパイルが必要  
→lazygitはAIX/PPC64へのクロスコンパイルはエラーになる  
　lazygitのコードを調べたが、UNIX,Mac,Windows用のコードはあるが、  
　AIX用のsytem callのコードがない!  
  
よってCで書かれたtigをIBMiのIFSでコンパイルして利用する  

# <u>■インストール</u>
## <u>◯関係パッケージ</u>
```
$ yum install ncurses-devel
$ yum install autoconf libtool automake
$ yum install pkg-config
$ yum install libutil-devel
```

## <u>◯tigのソースコード取得とコンパイル</u>
```
$ cd ~/tig/tig
$ git clone https://github.com/jonas/tig.git

$ cp include/tig/tig.h include/tig/tig.h_org
```
＊以下コメントアウトする(sys.hと重複定義している)
```
$ vim include/tig/tig.h 
143 /*
144 #define MIN(x, y)      ((x) < (y) ? (x) :  (y))
145 #define MAX(x, y)      ((x) > (y) ? (x) :  (y))
146 */
```
＊os400ではC標準関数のiscntrlで漢字が検出されてしまい一部の漢字が表示されない
以下の127,139-143行を追加した
 ```
$ vim src/string.c
 91 // UTF-8 で何バイトで表現されるか取得
 92 // https://jun-networks.hatenablog.com/entry/2020/09/05/020925
 93 int
 94 get_byte(const char *c){
 95     if (!(*c & (1 << 7))) // 1ビット目が0の時は1バイト
 96         return (1);
 97     int bytes = 0;
 98     for (int i = 7; i >= 4; i--)
 99     {
100         if (*c & (1 << i))
101             bytes++;
102         else
103             return (bytes);
104     }
105     return (bytes);
106 }

109 string_expand(char *dst, size_t dstlen, const char *src, int srclen, int tabsize)
110 {

127                 int charlen = get_byte(&src[pos]);

137 //              } else if (isspace((unsigned char)c) || iscntrl((unsigned char)c)) {
139                 } else if (isspace(c)) {
140                         dst[size++] = ' ';
142                 } else if (charlen == 0 ) {
143                         dst[size++] = ' ';
149                 } else {
150                         dst[size++] = src[pos];
151                 }                  
```
```
$ make configure
$ ./configure
$ make
$ make install 
   INSTALL  src/tig -> /usr/local/bin
   INSTALL  tigrc -> /usr/local/etc
$ cp /usr/local/bin/tig /usr/bin
```
# <u>■設定ファイル</u>
## <u>◯/usr/local/etc/tigrcと~/.tigrc</u>
/usr/local/etc/tigrc の共通設定にカスタム設定を追加する  
もし開発者個人が独自設定したいなら、~/.tigrcを作成し各種設定を行う  
tigの使い方は別紙参照  
```
## 各view
set main-view-id = yes

# https://qiita.com/sfus/items/063797a1dd8fdc7d032f
## git外部コマンド
# status画面から確認なしcommit(C)
# refs での C は checkout, main での C は cherry-pick だが上書きする
bind status  C      !git commit
bind refs    C      ?git commit
bind main    C      ?git commit
# status画面からpush(P)
bind status  P      ?git push -u %(remote) %(repo:head)
#bind main P ?git push origin HEAD:$1 "%(prompt Enter push branch => )"
# branch画面(refs)からpull(U)
bind refs    U      ?sh -c "git checkout %(branch) && git pull %(remote) --ff-only && git checkout -"
# branch画面(refs)からbranch作成(B)
bind refs    B      ?git branch "%(prompt New branch name: )" %(branch)
# branch画面(refs)からcheckout(=)
bind refs    =      ?git checkout %(branch)
bind main    <Esc>= ?git checkout %(commit)
# branch画面(refs)からmerge(M)
bind refs    M      ?git merge %(branch)
# branch画面(refs)から親branch確認
bind refs    ^      ?sh -c "git checkout %(branch) && git show-branch|grep -1 `git rev-parse --abbrev-ref HEAD`|head -1|awk -F'[]~^[]' '{print $2}'&& git checkout -"

## 移動系
# g でファイル先頭に移動に変更
bind generic g      move-first-line
# G でファイル末尾に移動
bind generic G      move-last-line
bind main    G      move-last-line
```

## <u>◯~/.bash_profile</u>
ブランチ一覧(refs)や整形ログ画面(main)などで日本語が文字化けする
以下の設定をいれる
```
~/.bash_profile
export LC_ALL=JA_JP.UTF-8
export LESSCHARSET=utf-8
```
## <u>◯コミット時のエディタをvimからnanoに変更する</u>
コミット時のエディタは標準はvim
vimに慣れていない人は以下変更をする
```
git config --global core.editor "nano"
```

または以下を追記  
~/.gitconfig
```
[core]
        editor = nano
```

## <u>◯コミットメッセージテンプレートを変更する</u>
コミット時のメッセージテンプレートを個人ごとに設定できる  
```
$ git config --global commit.template ~/.commit_template
```
　  
または以下を追記
~/.gitconfig  
```
[commit]
        template = /home/{ユーザ名}/.commit_template
```
　  
~/.commit_templates  
```

# ==== Commit Messages(Template) ====
# [prefix] #Issue番号 変更内容
# 例) [fix] #438 コメント追加
# ==== Prefix ====
# [fix] バグ修正
# [hotfix] クリティカルなバグ修正
# [add] 新規機能・新規ファイル追加
# [update] バグではない機能修正
# [revert] 修正取り消し
# [refactor] リファクタリング
# [docs] ドキュメントのみ修正
```

# ■IBMiからgitlabをパスワードなしで使う
### ◯IBMi -> GITLAB
gitlabをパスワードなしで利用するために、
・IBMiで事前に鍵認証を作成し
・gitlabに公開鍵を登録する

#### 1) IBMiで秘密鍵・公開鍵を作成する
　以下複数のssh鍵を使い分ける例
　1つだけならsshkey-gen -t rsaで-fオプションを指定しないと、
　～/.ssh/id_rsa と～/.ssh/id_rsa.pubが作成される
　1つだけなら~/.ssh/configの設定不要
 
　VSCodeインストールでPC(PowerShell)で作成した
　{鍵ファイル名}.key を IBMiの~/.sshにscpし、
　{鍵ファイル名}.pub を gitlabに登録してもよい
```
IBMi $ cd ~/.ssh ※~/.sshがなければ作成する
IBMi /home/{ユーザ}/.ssh$ ssh-keygen -f {鍵ファイル名} -t rsa
→ 秘密鍵の {鍵ファイル名}.key と 公開鍵の {鍵ファイル名}.pub が作成される
```

#### 2) 公開鍵をgitlabに登録する
　https://gitlab.local にログインして、
　左ペインの自分のアイコン → [設定] → [sshキー] → [新しいキーを追加]
　キー の部分に ssh-rsa で始まる 公開鍵({鍵ファイル名}.pub)をコピー&ペーストする
　適当な[タイトル]を入力した[キーを追加]する
　デフォルトは期限が入っているので期限欄を削除して空白にすると無期限になる
 
#### 3) 対象ホストと秘密鍵の対応を設定する
　IBMiの~/.ssh/configに以下を追加する
```
Host gitlab
    HostName gitlab.local
    IdentityFile ~/.ssh/{鍵ファイル名}.key
    User git
    Port 22
    IdentitiesOnly yes
    HostKeyAlgorithms +ssh-rsa
    PubkeyAcceptedKeyTypes +ssh-rsa
```

#### 4) gitの認証鍵確認
　IBMiで以下のようになれば設定完了
　IBMiからgitを利用する際にパスワードが不要になる

```
{ユーザ}@as400dev:~$ ssh gitlab.local
PTY allocation request failed on channel 0
Welcome to GitLab, @{ユーザ}!
Connection to gitlab.local closed.
```