一人情シスのつぶやき

名古屋の中小企業で一人情シスをしている作者が、日々の業務で思うことをつぶやきます。

今日のクソVBAコード

stDocName = ChrW(xx) & ChrW(yy) & ChrW(zz) & ChrW(abc) & ChrW(def) & ChrW(ghi) & ChrW(jkl) & ChrW(mno) & ChrW(pqr) & ChrW(stu)
DoCmd.OpenReport stDocName, acPreview

ChrWの引数は実際にはコードが入る。 式の右辺をイミディエイトウィンドウに入力すると、日本語のレポート名が表示される...

暗号化?なんのために? あとで見る人への嫌がらせか? ちょっと意味がわからない

CIの導入について検討

一人で開発していても、テストやデプロイにミスが出る可能性はある。 CIの導入を検討した。

結論としては、CI用途のサーバーを別途導入することはしない。現在主に開発しているC#プロジェクトでは、CIにもWindowsが必要となる。ライセンス費用が必要だし、Dockerでお手軽に再構築できる環境としたいため。

やりたいことは以下の通り

  • リポジトリのPRコードのビルド
  • テスト、結果通知、OKならmerge
  • DBの構成情報に関して、リポジトリと実環境で差異がないかチェック

1,2点目はWindowsを避ける以上、不可能。開発時に自端末でテストを行い、PRのコメントに記載する運用で対応。 3点目は、毎日定時に実行する普通のバッチでなんとかなるレベル。

テストに関して、DBに関連するところは一切やっていない。面倒なので。 一方で内製アプリの殆どはDBのデータを持ってきてそのまま表示し、加工して更新する程度のものがほとんどのため、結果ほとんどテストがない状態。 本番環境に接続する際には専用のクラスを利用しているので、テスト環境用にも同様のクラスを作成し、テスト実行時にはそちらを利用してDB接続するようにしてテストを行うようにする。まずこちらが優先。

Dockerでdumpファイルから空のデータベースを作成するDockerfileを作成し、開発にすぐに利用できるようにする。

その上で、上記の運用で品質をさらに高めていく。

Docker Container 起動失敗

Docker Hostのスタートアップサービスにて、Docker ContainerをBuild, Upするスクリプトを実行しているのですが、以下のようなエラーが大量に発生してUpしていませんでした。

 8月 26 03:07:44 sever-name dockerd-current[864]: time="2018-08-26T03:07:44.615597202+09:00" level=error msg="could not calculate checksum for \"fb1077f711d4fc436c0b6e115f8cdb0c871f46c818ec998efbf489df5e4a4de5\", \"devmapper: Unknown device fb1077f711d4fc436c0b6e115f8cdb0c871f46c818ec998efbf489df5e4a4de5\""
...
 8月 26 03:07:44 server-name dockerd-current[864]: time="2018-08-26T03:07:44.617971873+09:00" level=error msg="migration failed for 866ae31005298fd6f1bb2944418eb34969b16ead2a18ed332fa011a311f3b4b2, err: open /var/lib/docker/graph/60e65a8e4030022260a4f84166814b2683e1cdfc9725a9c262e90ba9c5ae2332/json: no such file or directory"
...

ログの内容を見ると、以下のissueと同じように見える。再起動前にDockerのバージョンが1.13.1-74 に上がったようだし...

github.com

対処方法は記事からは判明せず。

スタートアップスクリプトを手動で実行したところ、普通にupしたので、docker containerが起動していなければスクリプトを再度実行するcronジョブを登録することで暫定対処した。

CentOS7のDocker構築ではまったこと

storage driverがdevice mapperの場合のディスク容量

device mapperの場合は、既定のディスク容量が10GBほどとなる。Oracle DatabaseのDockerコンテナをbuildするとこける。

storage driverを最初からoverlay2 にするための方法

インストール時にデバイスタイプにLVMを指定すると、Dockerのstorage dirverはdevice mapperになる。 docs.docker.com 基本ディスクを選んで、xfsを選んでやる必要がある。

さらに、CentOS7 1511(minimal)の場合は上記の手順でもやはりdevice mapperが既定となる。overlayを使用するための設定がされていないためと想像される。

docs.docker.com

CentOS7 1804(minimal)で基本ディスク(xfs)でインストールすれば、overlay2がstorage driverとして設定される。

箱入り娘のプログラムを書いて思う

実家に帰った際に箱入り娘のパズルがあったのでやっていた。

箱入り娘 (パズル) - Wikipedia

全然解けなかったが、プログラムで力技で解きたいと思い、やってみた
結論として、解けずに終わった。
Python再帰関数で解こうとして、再帰呼び出しの上限に引っかかって30sほどでエラーとなった。
将棋などと比較すると取ることができる手ににかなりきつい制限があるので、全探索余裕と思ってしまったのだが、完全に間違っていた。
一応、盤面を都度記録し、同じ盤面になったらそれ以上は探索しないようにしたのだが、それでも解空間は大きかった。

まず、再帰による解法の選択について。現代のプログラムにおいては、上限の大きさは違えど再帰呼出の階数には制限がある。ので、対象としている問題で想定される階数に比較してプログラミング言語の制約が十分かどうか判断しなければいけなかった。あるいは、階数をパラメータとして保持しておき、起動時に何階層まで探索するか指定するような形にすればよかった。

再帰ではなく、盤面をメモリかファイルに記録し、都度記録から次の盤面を探してスタックを使用しない形にしても良かった。

そもそも論で行くと、パズルは頭の体操として娯楽としてあるもので、力技で解くことに意味あるのか? というのもある。

今回は、初めてPythonを使って割としっかりとしたプログラムが書けたので、練習として良かったということにした。

Excelで「このワークシート内にある1つ以上の式の参照に問題が見つかりました」

Excelで解決がとてもめんどくさいエラー。

このワークシート内にある1つ以上の式の参照に問題がみつかりました。数式内のセル参照、範囲名、定義名、および他のブックへのリンクがすべて正しいことをご確認ください。

Excel 2013で発生し、どう考えても参照する箇所がなくなるくらい該当シート、セルを削除しても保存のたびにエラーが出る。

で、一旦保存して終了して開き直すと出なくなることも... 全てではないのだが、エラー箇所を修正しても保存して開き直すまでエラーが出続けることがあるらしい... そもそも、エラーを出すのだからそのエラー箇所を素直に指摘してくれよと思うのだが...

64bit OSでのレジストリ操作時の注意事項

tack41tu.hatenablog.comClickOnceアプリをインストールする際にレジストリを編集する必要がある事を書いた。

レジストリエディタで編集するのは面倒だし運用も大変なので、レジストリを編集するアプリを作成した。

How to: Configure the ClickOnce Trust Prompt Behavior にある以下のコードを書いて実行し、正常終了するのだがレジストリエディタで確認すると変更が反映されておらず、ClickOnceの動作も変わらない。

Microsoft.Win32.RegistryKey key;  
key = Microsoft.Win32.Registry.LocalMachine.CreateSubKey("SOFTWARE\\MICROSOFT\\.NETFramework\\Security\\TrustManager\\PromptingLevel");  
key.SetValue("LocalIntranet", "Enabled");  
key.Close();  

どうもレジストリは32bit, 64bitで別の領域らしく、プログラム作成時にターゲットCPUをAnyとし、x86優先とした結果、32bitの領域を更新してしまっているらしい。

aonasuzutsuki.hatenablog.jp を参考に以下のように記載したところ、想定通りに動作するようになった。

Microsoft.Win32.RegistryKey key_base, key;  
key_base = RegistryKey.OpenBaseKey(RegistryHive.LocalMachine, RegistryView.Registry64);
var key = prerKey.CreateSubKey("SOFTWARE\\MICROSOFT\\.NETFramework\\Security\\TrustManager\\PromptingLevel",);
key.SetValue("LocalIntranet", "Enabled");  
key.Close();