MySQL接続でSSL connection error: error:1425F102:SSL routines:ssl_choose_client_version:unsupported protocolが出たときの対応

まえがき

MySQLへの接続で、ERROR 2026 (HY000): SSL connection error: error:1425F102:SSL routines:ssl_choose_client_version:unsupported protocol というエラーが出たときのメモ書き。
エラーの内容はssl_choose_client_version:unsupported protocolって書いてあるので、恐らくクライアント側で選択されているTLSのバージョンが新しい or 古くて許容されてないだけっぽい。
ぐぐると、update-crypto-policies --set LEGACY で解決した方もいたみたいだが、自分は解決しなかった。

環境

  • Ubuntu:20.04
  • mysql-client: mysql Ver 8.0.20-0ubuntu0.20.04.1 for Linux on x86_64 *1
  • DB側の設定やバージョンは省略

ログ

$ mysql -u db_user -h db_host -p
ERROR 2026 (HY000): SSL connection error: error:1425F102:SSL routines:ssl_choose_client_version:unsupported protocol
$

対応

そもそも手元の開発ではtlsにしなくて良い&してないので、--ssl-mode=DISABLED ででなくなった。

$ mysql -u db_user -h db_host -p --ssl-mode=DISABLED
Enter password:
ERROR 1045 (28000): Access denied for user 'db_user'@'X.X.X.X' (using password: YES)
$

参考

*1:Ubuntu

ImageMagickとmulticropコマンドで1枚の画像を空白区切りで分割してみる

まえがき

友人から複数枚の画像を1枚の画像としてスキャンしたものをいい感じに分割する方法がなさそうか困っていそうだった。
見てググって出てきた内容は今後使う時がありそうな気がしたのでメモを残しておく。

やりたいこと

こういう1枚のスキャン画像に複数枚の画像がまとめられている。
これを1枚ずつ分割して保存したい。
以下の例でいうと、4分割してimage-1.png, image-2.png, image-3.png, image-4.pngといった具合に分割保存したい。

f:id:st1t:20200604223202p:plain

調べた結果

ImageMagickをラップしたmulticropというスクリプトを使うと良さそう。

www.fmwconcepts.com

インストール方法

ImageMagick

imagemagick.org

multicrop

以下公式サイトの Download Script からダウンロードして実行権限と付与しておく。
Fred's ImageMagick Scripts: MULTICROP

multicrop依存のもの

REQUIREMENTS: If using unrotate method 2, then my script, unrotate, is required. If using innertrim, then my script, autotrim is required.

作者の別のスクリプトも必要みたいなのでダウンロードして実行権限とpathを通しておく。
今回はunrotateだけあれば動いたのでそれだけ紹介。

Fred's ImageMagick Scripts: UNROTATE

実行コマンド

f:id:st1t:20200604223202p:plain

↑の画像をtest-image.pngとして実行。

$ ./multicrop -b white test-image.png image.png

Processing Image 0
Initial Crop Box: 220x188+37+41

convert: profile 'icc': 'RGB ': RGB color space not permitted on grayscale PNG `image-000.png' @ warning/png.c/MagickPNGWarningHandler/1748.
Processing Image 1
Initial Crop Box: 220x188+309+41

convert: profile 'icc': 'RGB ': RGB color space not permitted on grayscale PNG `image-001.png' @ warning/png.c/MagickPNGWarningHandler/1748.
Processing Image 2
Initial Crop Box: 220x188+37+279

convert: profile 'icc': 'RGB ': RGB color space not permitted on grayscale PNG `image-002.png' @ warning/png.c/MagickPNGWarningHandler/1748.
Processing Image 3
Initial Crop Box: 220x188+309+279

convert: profile 'icc': 'RGB ': RGB color space not permitted on grayscale PNG `image-003.png' @ warning/png.c/MagickPNGWarningHandler/1748.

$ 

実行結果

以下のように4分割されて出力された。
ただ、実際はスキャン画像の解像度や色によって画像と画像の間の部分を認識する精度がそのままだとでなさそうだった。
この辺はmulticropのパラメータを調整してみる必要がありそう。

f:id:st1t:20200604225226p:plain

SlackでLegacy BotでRTM APIを使うためのSlack Appの追加の仕方

まえがき

SlackでReal Time Messaging API(RTM API)を使いたい時があったが、
今(2020/05/28現在)だと通常のSlack APPだと動かないため、Classic Slack Appを作ってRTM APIを使えるようにするためのメモを残しておきます。

RTM APIとEvents APIについて

今はRTM APIと似た挙動をするAPIとしてEvents APIというものがあります。

RTM APIについて

api.slack.com

Events APIについて

api.slack.com

RTM APIとEvents APIの使い分けについて

以下リンク先の When should I use the Events API and when should I use the RTM API? を見ると良さそうです。

api.slack.com

Classic Slack Appの作成

以下リンク先から作成できます。

api.slack.com

legacy bot userの追加について

Features -> App Home -> Add Legacy Bot Userから追加 f:id:st1t:20200528130611p:plain

tokenについて

f:id:st1t:20200528131641p:plain

f:id:st1t:20200528131819p:plain

tcpdumpの使い方

まえがき

tcpdumpの使い方、TCPヘッダフラグの位置、その他雑多なものをメモしておく。

tcpdumpのよく使うやつ

やる前に気をつけたほうが良いこと

  • 何のため、どういう状態であると仮定してを意識してから取得する
    • 闇雲にとってもパケットおじさんじゃないと多分難しい
    • ex. トラブル対応で特定のリクエストのコネクションの状態を確認するため
      • APPサーバの処理時間は短かかった。WEBサーバのアクセスログの処理時間は長い
      • sarの毎分の状況からWEBサーバのログ。システム負荷状況は問題なさそう(秒単位では待ちがある可能性はある)
      • LB - WEBサーバ / WEBサーバ - APPサーバのコネクション確立から閉じるまでで待ちが発生していると仮定
      • そのため、KeepAliveを切った上で、LB - WEB / WEB - APPの2つのコネクションの処理状況を調査する
      • NW的に問題がなさそうであれば、LinuxKernel/Middlewareの設定やバグが疑われるため、straceを用いてコール状況を確認する
  • 負荷に要注意
    • アクセスログの処理時間/ステータスコード
      • 基本的にはインターネットに一番近いところのログを確認する
      • AWSのELBログならElasticのfilebeatで突っ込むのが非常に楽で良い
      • www.elastic.co
    • システム負荷: dstat -af
  • KeepAliveを使ってると後でパケットを眺めるときにしんどいから、デバッグするときはリクエスト数を薄めて切ったほうが良い

コマンド

# 80ポートを60秒ごとに、ファイル名にタイムスタンプ入りで取得。-Zはローテートしたときにファイルのユーザーを指定
$ tcpdump -s0 -i any -A port 80 -G 60 -w tcpdump_%Y%m%d_%H%M.cap -Z root

# ↑のやつをバックグラウンドで回し続ける
$ tcpdump -s0 -i any -A port 80 -G 60 -w tcpdump_%Y%m%d_%H%M.cap -Z root > /dev/null 2>&1 &

tcpdumpでflagを指定する

f:id:st1t:20200520005831p:plain

↑の例でいうと

Ack: 16
Push: 8
なので、16 + 8 = 24
$ tcpdump 'tcp[13] = 24'

tcpdumpで色んなtcpヘッダーを指定するときの早見表

f:id:st1t:20200525224637p:plain

Wiresharkの使い方

filter

# Warning or Errorパケットを探す
_ws.expert.severity == "Warning" or _ws.expert.severity == "Error"
# 

URLとかでざっくり検索する

Command + Fで検索画面を出して、ドロップボックスをStringにしてキーワード検索できる

f:id:st1t:20200520002752p:plain

multipart/form-dataのデータを確認する

デフォルトの設定だとエンコードされてるので、右クリックして設定すると見えるようにする ※基本的には暗号化されてるので開発環境等でのデバッグ用 f:id:st1t:20200520000026p:plain

参考

TCPヘッダオフセットについて

serverfault.com www.packetlevel.ch

コピペするときによく使うやつ

blog.livedoor.jp

ELBアクセスログをElasticsearchに突っ込んだ後にPainlessでクエリストリングを除外したフィールドを追加する

まえがき

https://hoge.com?hoge=hogehoge&fuga=fugafuga みたいなアクセスログをそのまま集計するとクエリストリングが邪魔でほぼユニークなリクエストになる。
そのため、Painlessを使って https://hoge.com として表示するフィールドを追加する。

ELBアクセスログのElasticsearchへの投入

www.elastic.co

betaなのでクリティカルなところでは考えたほうが良いが、これ使っておけば間違いない。
ELBアクセスログを集約していれば大体2,30分もあれば慣れてる人ならサクッと導入できる。
しかもELBアクセスログ発行 -> S3 -> SQSの流れは全てAWSがやってくれるからいちいち細かいことを気にしなくて良い。
filebeatはSQSにデータを取得&Elasticsearchにpushするだけだし、本当に便利。

最初はLogstashのpatterns-coreにあるからそれでよいかと思ったが、 パターンが古くて駄目っぽい。
また、PRの反応も最近は薄そうなのでそのへんも加味して使うのを辞めた。

github.com

画面

f:id:st1t:20200522125242p:plain

実際のコード

def v_size = doc['http.request.referrer.keyword'].size();
if (v_size == 0) {
    return "path size is 0";
} else {
    def path = doc['http.request.referrer.keyword'].value;
    if (path != null) {
        int lastSlashIndex = path.lastIndexOf('?');
        if (lastSlashIndex > 0) {
            return path.substring(0, lastSlashIndex);
        } else {
            return path;
        }
    }
    return "path is null";
}

Ubuntu 18.04でLogicool MX Master 3をカスタマイズする

まえがき

Ubuntu 20.04だとデフォルトで動きました。
HHKBに合わせてLogicool MX Master 3をぽちった。
しかしWindows/Mac以外だとデフォルトではジェスチャーボタンやモードシフト、戻る、進むボタンが使えない。
調べたらlogiopsというOSSで色々とカスタマイズが可能っぽかったので設定したときのメモを残しておく。

github.com

インストール

$ apt install cmake 
$ git clone git@github.com:PixlOne/logiops.git
$ cd logiops/
$ mkdir build
$ cd build
$ cmake ..
$ make
$ sudo make install

libconfig.h++が存在しない

$ make
[ 88%] Built target hidpp
[ 89%] Building CXX object src/logid/CMakeFiles/logid.dir/logid.cpp.o
In file included from /home/st1t/github.com/logiops/src/logid/Device.h:6:0,
                 from /home/st1t/github.com/logiops/src/logid/Actions.h:3,
                 from /home/st1t/github.com/logiops/src/logid/util.h:4,
                 from /home/st1t/github.com/logiops/src/logid/logid.cpp:12:
/home/st1t/github.com/logiops/src/logid/Configuration.h:5:10: fatal error: libconfig.h++: そのようなファイルやディレクトリはありません
 #include <libconfig.h++>
          ^~~~~~~~~~~~~~~
compilation terminated.
src/logid/CMakeFiles/logid.dir/build.make:62: recipe for target 'src/logid/CMakeFiles/logid.dir/logid.cpp.o' failed
make[2]: *** [src/logid/CMakeFiles/logid.dir/logid.cpp.o] Error 1
CMakeFiles/Makefile2:87: recipe for target 'src/logid/CMakeFiles/logid.dir/all' failed
make[1]: *** [src/logid/CMakeFiles/logid.dir/all] Error 2
Makefile:129: recipe for target 'all' failed
make: *** [all] Error 2
$ 

$ sudo apt install libconfig++-dev
パッケージリストを読み込んでいます... 完了
依存関係ツリーを作成しています                
状態情報を読み取っています... 完了
以下の追加パッケージがインストールされます:
  libconfig++9v5
以下のパッケージが新たにインストールされます:
  libconfig++-dev libconfig++9v5
アップグレード: 0 個、新規インストール: 2 個、削除: 0 個、保留: 0 個。
65.7 kB のアーカイブを取得する必要があります。
この操作後に追加で 304 kB のディスク容量が消費されます。
続行しますか? [Y/n] Y
取得:1 http://jp.archive.ubuntu.com/ubuntu bionic/universe amd64 libconfig++9v5 amd64 1.5-0.4 [31.6 kB]
取得:2 http://jp.archive.ubuntu.com/ubuntu bionic/universe amd64 libconfig++-dev amd64 1.5-0.4 [34.1 kB]
65.7 kB を 0秒 で取得しました (844 kB/s)   
以前に未選択のパッケージ libconfig++9v5:amd64 を選択しています。
(データベースを読み込んでいます ... 現在 389870 個のファイルとディレクトリがインストールされています。)
.../libconfig++9v5_1.5-0.4_amd64.deb を展開する準備をしています ...
libconfig++9v5:amd64 (1.5-0.4) を展開しています...
以前に未選択のパッケージ libconfig++-dev:amd64 を選択しています。
.../libconfig++-dev_1.5-0.4_amd64.deb を展開する準備をしています ...
libconfig++-dev:amd64 (1.5-0.4) を展開しています...
libconfig++9v5:amd64 (1.5-0.4) を設定しています ...
libconfig++-dev:amd64 (1.5-0.4) を設定しています ...
libc-bin (2.27-3ubuntu1) のトリガを処理しています ...
$ 
$ make
$ sudo make install
[ 88%] Built target hidpp
[100%] Built target logid
Install the project...
-- Install configuration: ""
-- Installing: /usr/local/bin/logid
-- Set runtime path of "/usr/local/bin/logid" to ""
-- Installing: /lib/systemd/system/logid.service
-- Installing: /usr/local/include/hidpp
-- Installing: /usr/local/include/hidpp/misc
-- Installing: /usr/local/include/hidpp/misc/CRC.h
-- Installing: /usr/local/include/hidpp/misc/Log.h
-- Installing: /usr/local/include/hidpp/misc/Endian.h
-- Installing: /usr/local/include/hidpp/misc/EventQueue.h
-- Installing: /usr/local/include/hidpp/hid
-- Installing: /usr/local/include/hidpp/hid/RawDevice.h
-- Installing: /usr/local/include/hidpp/hid/UsageStrings.h
-- Installing: /usr/local/include/hidpp/hid/DeviceMonitor.h
-- Installing: /usr/local/include/hidpp/hid/windows
-- Installing: /usr/local/include/hidpp/hid/windows/DeviceData.h
-- Installing: /usr/local/include/hidpp/hid/windows/error_category.h
-- Installing: /usr/local/include/hidpp/hidpp
-- Installing: /usr/local/include/hidpp/hidpp/AbstractProfileDirectoryFormat.h
-- Installing: /usr/local/include/hidpp/hidpp/AbstractMacroFormat.h
-- Installing: /usr/local/include/hidpp/hidpp/DeviceInfo.h
-- Installing: /usr/local/include/hidpp/hidpp/ProfileDirectory.h
-- Installing: /usr/local/include/hidpp/hidpp/Report.h
-- Installing: /usr/local/include/hidpp/hidpp/Dispatcher.h
-- Installing: /usr/local/include/hidpp/hidpp/SettingLookup.h
-- Installing: /usr/local/include/hidpp/hidpp/AbstractProfileFormat.h
-- Installing: /usr/local/include/hidpp/hidpp/AbstractMemoryMapping.h
-- Installing: /usr/local/include/hidpp/hidpp/defs.h
-- Installing: /usr/local/include/hidpp/hidpp/Enum.h
-- Installing: /usr/local/include/hidpp/hidpp/Profile.h
-- Installing: /usr/local/include/hidpp/hidpp/SimpleDispatcher.h
-- Installing: /usr/local/include/hidpp/hidpp/Setting.h
-- Installing: /usr/local/include/hidpp/hidpp/Macro.h
-- Installing: /usr/local/include/hidpp/hidpp/Address.h
-- Installing: /usr/local/include/hidpp/hidpp/DispatcherThread.h
-- Installing: /usr/local/include/hidpp/hidpp/Device.h
-- Installing: /usr/local/include/hidpp/hidpp/ids.h
-- Installing: /usr/local/include/hidpp/hidpp/Field.h
-- Installing: /usr/local/include/hidpp/hidpp10
-- Installing: /usr/local/include/hidpp/hidpp10/ProfileFormatG9.h
-- Installing: /usr/local/include/hidpp/hidpp10/ProfileFormatG500.h
-- Installing: /usr/local/include/hidpp/hidpp10/DeviceInfo.h
-- Installing: /usr/local/include/hidpp/hidpp10/ProfileFormatCommon.h
-- Installing: /usr/local/include/hidpp/hidpp10/ProfileFormat.h
-- Installing: /usr/local/include/hidpp/hidpp10/ProfileDirectoryFormat.h
-- Installing: /usr/local/include/hidpp/hidpp10/RAMMapping.h
-- Installing: /usr/local/include/hidpp/hidpp10/IMemory.h
-- Installing: /usr/local/include/hidpp/hidpp10/MacroFormat.h
-- Installing: /usr/local/include/hidpp/hidpp10/IResolution.h
-- Installing: /usr/local/include/hidpp/hidpp10/IProfile.h
-- Installing: /usr/local/include/hidpp/hidpp10/Sensor.h
-- Installing: /usr/local/include/hidpp/hidpp10/defs.h
-- Installing: /usr/local/include/hidpp/hidpp10/IReceiver.h
-- Installing: /usr/local/include/hidpp/hidpp10/MemoryMapping.h
-- Installing: /usr/local/include/hidpp/hidpp10/ProfileFormatG700.h
-- Installing: /usr/local/include/hidpp/hidpp10/IIndividualFeatures.h
-- Installing: /usr/local/include/hidpp/hidpp10/Device.h
-- Installing: /usr/local/include/hidpp/hidpp10/Error.h
-- Installing: /usr/local/include/hidpp/hidpp10/WriteError.h
-- Installing: /usr/local/include/hidpp/hidpp20
-- Installing: /usr/local/include/hidpp/hidpp20/IBatteryLevelStatus.h
-- Installing: /usr/local/include/hidpp/hidpp20/IReset.h
-- Installing: /usr/local/include/hidpp/hidpp20/ProfileFormat.h
-- Installing: /usr/local/include/hidpp/hidpp20/IWirelessDeviceStatus.h
-- Installing: /usr/local/include/hidpp/hidpp20/ProfileDirectoryFormat.h
-- Installing: /usr/local/include/hidpp/hidpp20/MacroFormat.h
-- Installing: /usr/local/include/hidpp/hidpp20/IReprogControls.h
-- Installing: /usr/local/include/hidpp/hidpp20/UnsupportedFeature.h
-- Installing: /usr/local/include/hidpp/hidpp20/defs.h
-- Installing: /usr/local/include/hidpp/hidpp20/MemoryMapping.h
-- Installing: /usr/local/include/hidpp/hidpp20/IRoot.h
-- Installing: /usr/local/include/hidpp/hidpp20/FeatureInterface.h
-- Installing: /usr/local/include/hidpp/hidpp20/IHiresScroll.h
-- Installing: /usr/local/include/hidpp/hidpp20/IFeatureSet.h
-- Installing: /usr/local/include/hidpp/hidpp20/ISmartShift.h
-- Installing: /usr/local/include/hidpp/hidpp20/ITouchpadRawXY.h
-- Installing: /usr/local/include/hidpp/hidpp20/IAdjustableDPI.h
-- Installing: /usr/local/include/hidpp/hidpp20/Device.h
-- Installing: /usr/local/include/hidpp/hidpp20/Error.h
-- Installing: /usr/local/include/hidpp/hidpp20/IOnboardProfiles.h
-- Installing: /usr/local/include/hidpp/hidpp20/IMouseButtonSpy.h
-- Installing: /usr/local/include/hidpp/hidpp20/ILEDControl.h
-- Installing: /usr/local/lib/libhidpp.so
$
$ sudo systemctl enable logid

libhidpp.soがない

$ /usr/local/bin/logid --help
/usr/local/bin/logid: error while loading shared libraries: libhidpp.so: cannot open shared object file: No such file or directory

github.com

try symlinking /usr/lib/libhidpp.so to /usr/local/lib/libhidpp.so

って書いてあるが、

$ ls -la /usr/local/lib/libhidpp.so
-rw-r--r-- 1 root root 2407952  3月  9 20:14 /usr/local/lib/libhidpp.so
$ 

既にある。 実際どこを見に行ってるか確認すると、/usr/lib/libhidpp.soっぽい

$ strace -e trace=openat logid 2>&1 | grep libhidpp.so
openat(AT_FDCWD, "/lib/x86_64-linux-gnu/tls/haswell/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/x86_64-linux-gnu/tls/haswell/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/x86_64-linux-gnu/tls/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/x86_64-linux-gnu/tls/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/x86_64-linux-gnu/haswell/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/x86_64-linux-gnu/haswell/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/x86_64-linux-gnu/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/x86_64-linux-gnu/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/x86_64-linux-gnu/tls/haswell/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/x86_64-linux-gnu/tls/haswell/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/x86_64-linux-gnu/tls/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/x86_64-linux-gnu/tls/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/x86_64-linux-gnu/haswell/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/x86_64-linux-gnu/haswell/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/x86_64-linux-gnu/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/x86_64-linux-gnu/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/tls/haswell/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/tls/haswell/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/tls/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/tls/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/haswell/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/haswell/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/lib/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/tls/haswell/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/tls/haswell/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/tls/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/tls/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/haswell/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/haswell/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/x86_64/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
openat(AT_FDCWD, "/usr/lib/libhidpp.so", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
logid: error while loading shared libraries: libhidpp.so: cannot open shared object file: No such file or directory
$ 
$ sudo ln -s /usr/local/lib/libhidpp.so /usr/lib/libhidpp.so
$ logid --help
Usage: logid [options]
Possible options are:
    -v,--verbose [level]       Set log level to debug/info/warn/error (leave blank for debug)
    -c,--config [file path]    Change config file from default at /etc/logid.cfg
    -h,--help                  Print this message.
$ 

設定ファイルを用意する

$ sudo vim /etc/logid.cfg
devices: (
{
    name: "MX Master 3";
    smartshift:
    {
        on: false;
        threshold: 30;
    };
    hiresscroll:
    {
        hires: false;
        invert: false;
        target: false;
    };
    dpi: 1000;

    buttons: (
        {
            # 戻るボタン
            cid: 0x53;
            action =
            {
                type: "Keypress";
                keys: ["KEY_LEFTALT","KEY_LEFT"];
            };
        },
        {
            # 進むボタン
            cid: 0x56;
            action =
            {
                type: "Keypress";
                keys: ["KEY_LEFTALT","KEY_RIGHT"];
            };
        },
        {
            # ジェスチャーボタン
            cid: 0xc3;
            action =
            {
                type: "Gestures";
                gestures: (
                    {
                        direction: "Up";
                        mode: "OnRelease";
                        action =
                        {
                            type: "Keypress";
                            keys: ["KEY_LEFTALT","KEY_LEFTCTRL","KEY_UP"];
                        };
                    },
                    {
                        direction: "Down";
                        mode: "OnRelease";
                        action =
                        {
                            type: "Keypress";
                            keys: ["KEY_LEFTALT","KEY_LEFTCTRL","KEY_DOWN"];
                        };
                    },
                    {
                        direction: "Left";
                        mode: "OnRelease";
                        action =
                        {
                            type: "Keypress";
                            keys: ["KEY_LEFTSHIFT","KEY_LEFTALT","KEY_LEFTCTRL","KEY_DOWN"];
                        };
                    },
                    {
                        direction: "Right";
                        mode: "OnRelease";
                        action =
                        {
                            type: "Keypress";
                            keys: ["KEY_LEFTSHIFT","KEY_LEFTALT","KEY_LEFTCTRL","KEY_UP"];
                        }
                    },
                    {
                        direction: "None";
                        mode: "OnRelease";
                        action =
                        {
                            type: "Keypress";
                            keys: ["KEY_LEFTCTRL","KEY_W"];
                        }
                    }
                );
            };
        },
        {
            # SmartShiftボタン
            cid: 0xc4;
            action =
            {
                type = "ToggleSmartshift";
            };
        }
    );
}
);

転職ドラフトの自己推薦を使って転職しました

まえがき

こちらの記事は転職ドラフト体験談投稿キャンペーンに参加しています。

job-draft.jp

転職してから1年以上経過したのでHHKB買うためにも流石に書いても良いかなーと思って書いています。
転職したばかりだと客観的に書けないことも多いので💦

私の場合は、2018年の年末に転職ドラフトの指名制度ではなく自己推薦を使って転職しました。

転職ドラフトを使った経緯

転職は今回が初めてではなく、現職で5社目になります。

SIer ->ソシャゲ -> ISP -> オンライン英会話 -> 現職

現職でこそDevOpsという位置づけで働いているのですが、今までの職種は一貫してインフラになります。
ソシャゲ、ISPへの転職時には転職エージェント、オンライン英会話はSIer時代の先輩に誘っていただきました🙏

元々転職ドラフトは年収提示でスカウトというのが面白くて初期から(ジンバブエドルのプレゼント企画があったとき)登録していました。
ただ、頂いたメッセージが汎用的なメッセージで辞退させていただくことが多かったです。

逆に、なぜ指名してくださったのか明確にお話を頂いた方には極力会いに行っていました。
今回、自己推薦と合わせて指名を頂いた会社さんは社名こそ出せないのですが、
とてもおもしろい会社さんだったので正直自己推薦のやつがなければ選考を進めていただいていたと思います。

自己推薦を使ったのは、たまたま現職の募集要項が自分にマッチしていそうだったからです。

  • 今までやっていたことの経験を活かせそうだった
    • インフラのコード化
    • CI/CDの環境整備
  • もっとコードを書きたい
    • 今後のキャリアを考えた時にアプリケーションレイヤに近いところももっとやりたかった
  • 自己推薦機能を使った転職キャンペーンをやっていた
  • ぐぐったらCTOが強そうだった

実は話を聞きに行ったときは、CTOと話をしていたのですが本当に話を聞きに行っただけだったので、
今すぐ何がなんでも転職するつもりはなく、話を聞いてみたかっただけです。とその場で伝えていました。
カジュアル面談が本当にカジュアルに出来ていて良いなーと思ったのも一つポイントだったかもしれません。

転職ドラフトを使ってよかったこと

  • 年収について事前に知った上で面接に望むことが出来る
    • 大体どこの会社でも年収の提示は最終面接か、内定後に連絡が来ることが多いのでそこで折り合いがつかないと時間の無駄になってしまう
  • 自分と似た人がどういうオファーをどのくらいの年収でオファーを受けているのか知ることが出来る
  • 企業のルール違反をきちんと調査して公表するので運営に信用感がある

転職ドラフト利用時や転職する時に悩ましいこと

  • 自分に合いそうな企業を見つけることが難しい
    • 直近の転職を考えていなくても常に良さそうな会社があればメモするようにはしてる
    • トリガーは基本的にTwitter
  • 企業ごとの特色がわかりづらいのでラブコールがだしづらい(かも)
  • 自分と同じ職種の方がどんな感じか見ようと思っても職種別の検索機能がない
  • 転職エージェントと違ってキャリアや面接対策の相談とかできないので、転職経験者向け感はある
    • 私は相談したことないですが、周りは相談したいという方も見ます

さいごに

書くこともないので転職を何度かしてきて一緒に働くうえで大事だなーと実感したことを書いておきます。
自分の場合は面接受ける時とかにこの辺に絡んだ質問したりもします。

  • 質の良いレビュー
    • 質の良いレビューはレベルアップの一番の近道。Xさんだからよし!はみんなを不幸にする
  • 人は忘れる生き物。同じ質問をされても嫌な顔せずきちんと答える
  • 障害は必ず発生するもの。大事なのはフールプルーフな再発防止策
    • ダブルチェックをトリプルチェックします!は再発防止策ではない
  • 障害対応、パフォーマンスチューニングでも「仮説」と「検証」は必ずセット。仮説なくして検証にならず
    • なんかよくわからんけど、ググったらこの設定が出てきたので設定して解決しました、よし!は障害対応でも二次障害につながるから極力避ける
  • わからないことははっきりわからないと言う
    • あとからググるのも手ではあるけど、それでもわからなかったとき困るのでなるべくその場で確認する
  • パケットの気持ちになる
  • 転職こわくない
  • 5000兆円ほしい

追記@2020-03-06

Amazonギフト券がもう届いた、めっちゃ仕事早い、ありがとうございます!!!
1,2週間くらいかかるかな〜?と思ってたら1営業日だった!
これでHHKB買える