標準愚痴出力

個人的なIT作業ログです。もしかしたら一般的に参考になることが書いているかもしれません(弱気

「jj diff --color always | (カラー対応ページャ)」が Windows でうまくゆかない

\x1B[…;…m 形式のカラーシーケンスを受け付けるページャ(例えば拙作の nemo )で、Git 互換バージョン管理システム jj のバージョン間差分を見る時、出力が歯抜けになってしまう場合がある(差分が表示されるべき行が空行になったりする)

(例:文字コード変換のためにフィルターを入れようとした)

jj diff --color always | nkf32 -w | nemo

これは Windows のみ発生するケースで、どうやら CR と LF の間にカラーシーケンスが入ってしまうためのようだ。そのせいで、凝ったことをやってるページャはおかしくなる(逆に more.com などはまったく無傷)

この場合、Perl をかませて、単品の CR を削除し、LF を CRLF に変換すればよろしい。

jj diff --color always | nkf32 -w | perl -pe "s/\r//g; s/\n/\r\n/g" | nemo

様々な DB に対応した、サンプルデータベース Chinook Database の Windows 環境でのインストールの仕方

  • 様々な DB に対応したアプリを開発する際に便利
  • 問題が起きる場合は、ほぼ文字コード (スクリプトの UTF-8 が認識されない)

ダウンロード

PostgreSQL でのインストール

C:> set PGCLIENTENCODING=utf-8
C:> psql -h 127.0.0.1 -p 5432 -d postgres -U postgres
SQL> \i Chinook_PostgreSql.sql
SQ>> \q
  • chinook というデータベースが作成され、そこにスキーマが作られる
  • SQL-Bless からアクセスする時は sqlbless postgres://postgres@127.0.0.1:5432/chinook?sslmode=disable

Microsoft SQL Server でのインストール

C:> chcp 65001
C:> sqlcmd -f 65001 -S localhost\SQLExpress -d master -i Chinook_SqlServer.sql
C:> chcp 932
  • chinook というデータベースが作成され、そこにスキーマが作られる
  • SQL-Bless からアクセスする時は sqlbless sqlserver "Server=localhost\SQLEXPRESS;Database=chinook;Trusted_Connection=True;protocol=lpc;"

MySQL でのインストール

C:> mysql --default-character-set=utf8 
C:> source Chinook_MySql.sql 
Query OK, 275 rows affected, 275 warnings (0.079 sec)
Records: 275  Duplicates: 0  Warnings: 275

などと表示されるのが気になるが、データ自体は登録されている模様。
( --default-character-set=utf8 はもしかしたら要らないかもしれないが念のため )

SQL-Bless からのログインは、sqlbless mysql "root:@/mydb" でも、sqlbless mysql "root:@/chinook" でも可能だったが、前者だとデフォルト DB が mydb になってしまい、カーソルによるテーブル名選択が失敗してしまう問題がある(いずれ直さなくては)

SQlite3 でのインストール

C:> sqlite3 (DBファイル名) < Chinook_Sqlite.sql 

のみでよい。SQLite3 は、もともと UTF-8 しかサポートしていないので、cp932 と解釈される心配はない。

Oracle でのインストール

  • 最新版のスクリプトは、複数行INSERTという Oracle 23c 以降でしかサポートされていない SQL を使用している。
  • 23c 以前の環境では v1.4.4 を使う必要がある。 #45
C:> set NLS_LANG=American_America.AL32UTF8
C:> sqlplus /nolog
SQL> connect sys/change_on_install@//localhost:1521/XE as sysdba
SQL> @Chinook_Oracle
  • SQL-Bless でログインする場合は sqlbless oracle://c%%23%%23chinook:chinook@localhost:1521/xe
    • ユーザは、CDB(コンテナDB)用の管理ユーザとして c##chinook が作られているので、接続先は xepdb1 ではなく xe を使う
    • URL的に # は直接書けないので、かわりに %23 を使う(上ではバッチファイル用に % を二つ重ねている)

Pure Go Oracle ドライバー sijms/go-ora v2.9 でタイムゾーン関連の問題が発生した

ターミナル用データベースクライアント SQL-Bless のメンテを再開しています。

今までは、NYAGOS は Windows 7, 8, Server 2008R2 で動作させるため、ビルドは Go 1.20.14 で固定してきました。それとエコシステムが地続きということもあって、他のアプリも 1.20.14 にあわせてきました。1

が、ローカルで完結する NYAGOS はともかく、DB アプリはそろそろまずい気がしてきました。ということで、SQL-Bless は Go 1.20.14 縛りを解除して、最新 Go に切り替えることにします。

が、その前に Go 1.20.14 でビルドする「最後のバージョン」をリリースしておくべきでしょう。ということで、go1.20.14 get でビルドできるライブラリだけでもアップデートです。

> go1.20.14.exe get github.com/sijms/go-ora/v2@latest
go: upgraded github.com/sijms/go-ora/v2 v2.8.22 => v2.9.0

残念ながら go-ora 以外でエラーなくアップデートできたものはなし。そしてテスト:

> cd test

> pwsh test-oracle.ps1
  ; 中略

UPDATE  TESTTBL
   SET  DT = :v1 ,  ST = :v2
 WHERE  TESTNO = :v3  AND  DT = :v4  AND  ST = :v5

(v1) time.Date(2015, time.June, 7, 20, 21, 22, 0, time.Local)
(v2) time.Date(2024, time.August, 9, 10, 11, 12, 787800000, time.Local)
(v3) 10
(v4) time.Date(2024, time.May, 25, 13, 45, 33, 0, time.Location(""))
(v5) time.Date(2024, time.July, 8, 17, 18, 19, 878700000, time.Location(""))

Apply this change? ("y":yes, "n":no, "a":all, "N":none) y
Starts a transaction
0 record(s) updated.
no data found

テーブルを編集して1件更新が走るはずが、スカってしまってテスト失敗。どうも、WHERE 句がマッチしなくなってしまったようです。

SET句で使われているバインド変数 v1 や v2 はユーザが編集した結果なので、SQL-Bless 側で生成した time.Time です。それゆえロケーションが time.Local になっています。一方、WHERE 句で使われている v4, v5 は DB から fetch してきた time.Time そのものです。これのロケーション名が空文字になっています。

そもそも Oracle の DATE 型や TIMESTAMP はタイムゾーン情報がないため、Go言語の time.Time 型へ読み込む場合ドライバー側でロケーション情報を補完する必要がありますが、どうやら、その動作が変わってしまったようです。観測範囲では、v2.8 系では time.Local に近い形で補完されていた一方、v2.9 系では空のロケーション情報となるケースが見られました。

レポジトリにも issue も出ていました。

今後の方針は次のようにしました。

  • とりあえず、動かないと困るので、go-ora は一旦 v2.8 に固定2
    SQL-Bless v0.27.6
  • 恒久対応として、 DATE/TIMESTAMP型を照合する場合、文字列として日時情報を送り、SQL上の TO_DATE 関数, TO_TIMESTAMP関数で DB 内で日時型へ戻すようにする (なるべく ドライバーに time.Time を扱わせない)
    #55, #57

しかし、データベースの日時型というのは、タイムゾーンを持たない「壁時計時刻」(wall-clock time) で扱っているものも多いため、この文字列で扱うという個別対応は、他の DB 対応にも展開した方がよいかもしれません。

なお、自分が go-ora を使っているのはPure Go 製の唯一の Oracle ドライバーパッケージだったためです(ドライバー一覧)。これが CGO 製だとC言語コンパイラが必要になって、他の OS 環境向けのビルド(クロスコンパイル)が面倒になってしまうんですよね。自分の選定はそういう事情があってのものであるため、そういうマルチ OS 対応が特に必要ないという方は他のドライバーパッケージを使うのも選択肢かもしれません。

追記

最新ソース版では次のように文字列ベースになっています

UPDATE  TESTTBL
   SET  DT = TO_DATE(:v1,'YYYY-MM-DD HH24:MI:SS') ,  ST = TO_TIMESTAMP(:v2,'YYYY-MM-DD HH24:MI:SS.FF')
 WHERE  TESTNO = :v3  AND  DT = TO_DATE(:v4,'YYYY-MM-DD HH24:MI:SS')  AND  ST = TO_TIMESTAMP(:v5,'YYYY-MM-DD HH24:MI:SS.FF')

(v1) "2015-06-07 20:21:22"
(v2) "2024-08-09 10:11:12.7878"
(v3) 10
(v4) "2024-05-25 13:45:33"
(v5) "2024-07-08 17:18:19.8787"

Apply this change? ("y":yes, "n":no, "a":all, "N":none) y
Starts a transaction
1 record(s) updated.

  1. go work コマンドでローカルで連携テストをすると、go.mod の書式がかわっていることもあって、Go のバージョンを越えられない場合があるんですよね
  2. 固定を表す英単語として fix だと「修正」とまぎらわしいので、pin の方がいいらしいです

不良債権処理

JSONエディターのサブパッケージを転用して、JSON から指定した JSONPATH の項目を「ありのまま(書式・表現)」の形で抽出して表示するツール書いた(改行だけは添える)。JSON の grep だから jrep

なお、バイナリはまだ用意していない

rclone メモ

設定ファイルの場所

  • ~/.config とか %APPDATA% にあるとか言われがちだが、scoop などでインストールするとまったく違う場所になりがち
  • 正確な場所は、rclone コマンド自体に報告させるのが確実
> rclone config file

Configuration file is stored at:
C:\Users\hymko\scoop\apps\rclone\current\rclone.conf

クラウドストレージのディレクトリごとの使用容量の確認

  • rclone ncdu パス (例: rclone ncdu onedrive:/ )で TUI ツールが起動する
  • ? でヘルプ、q で終了
  • 「使用容量の確認」と「削除」くらいしかできない(でも、それで十分)

進捗表示のデフォルト化

エイリアス

ヘルプを見ると、オプションはサブコマンド名の にしか書けないように見えるが、実際はサブコマンドの にも書ける

> rclone -P copy onedrive:/SoftwareDesign201905.pdf dropbox:/.
Transferred:       47.522 MiB / 47.522 MiB, 100%, 1.232 MiB/s, ETA 0s
Transferred:            1 / 1, 100%
Elapsed time:        42.9s

ゆえにシェルのエイリアスで常につけてもよい。

環境変数 RCLONE_PROGRESS というものもある

-- .nyagos
nyagos.env["RCLONE_PROGRESS"] = "true"

References

GitHub におかれたソフトウェアの「リリース」を逃さずキャッチするには

RSS リーダーなどを使っている場合

GitHub Releases は Atom Feed を出力しているので、通常のリーダーであれば、Releases ページの URL 、もしくは

https://github.com/(アカウント名)/(レポジトリ名)/releases.atom

からフィードを得ることができる。

GitHub のアカウントを持っている場合

該当レポジトリの:Watch ボタン → Custom → Releases にチェックを入れる

GitHub の watch ボタン

Release にチェック

アカウントの通知設定も忘れずに

Setting