YAPC::Kyoto 2023にていろいろやった話

YAPC::Kyoto 2023 最高でした

わいとんです。

皆さん、YAPC::Kyoto 2023 最高でしたね!

わたしは今回、Gold Sponsor企業の関係者および裏トークMCとしてYAPC::Kyoto 2023に参加させていただきました。起業後初のYAPCでしたが、やはり同窓会という雰囲気があり、わたしもまたPerl Mongerなのだな、という実感がわきました。

大井町.pmの宣伝動画をつくった

YAPC::Kyoto 2023の会場に入った皆さんなら「あぁー、あれね!」と言われること請け合いかと思いますが、↓の動画を作ったのはわたしです。

この動画の裏話は、もりたつ技商の@myfinder(まいんだー)さんがPerl Sponsorになったことから話が始まります。

まいんだーさんからある日「パールスポンサーは幕間CM動画を出せるらしい」「特に宣伝することもないしどうしよう」という相談を受け、あれこれ話しているうちに「じゃあ大井町.pmの宣伝しちゃう?」ということになってしまったのです。大井町のおじさん達による悪ノリのはじまりです。

動画の流れを色々話し合った結果、まいんだーさん若しくはわたしが何かをいう度に@soudai(そーだい)さんが「それな」「わかるー」という反応をしまくるというものにしようか、となったのですが、いざ蓋をあけてみたところ、あのような形に…

そして収録のために、溝の口のお好み焼き屋さんにて大井町.pmを開催したのですが、およそ2時間程度飲んだ食ったした後に「そろそろエンジンがあったまってきたな?」ということで写真撮影&音声収録を行ったという流れです。悪ノリ、どんどん加速していきます。

そして編集はわたしが担当することになりました。素材の映像・写真・音声を色々吟味していくうちに、「〇曜どうでしょう」っぽい雰囲気をまとわせると面白くなるだろう、と直感し、制作。

どうでしょうっぽいアレ

しかし、実際に一番時間と手間がかかったのは、一番最後の協賛企業表示でした。

GIMP2でこの画像をつくったんですけど、昭和のテレビ特有のシャドー現象や青色部分に多少でてしまう色ムラなどを表現するのに結構苦戦したんですよ。

協賛企業表示のアレ

で、まず会場のオーロラビジョンでこれが流れている様子を見たとき、「あ、ホントにやっちゃったんだw」と思わず口走ってしまったくらいには驚きました。

いや、事前に承知してたんですよ、そんなこと。でも実際に見てみると、200人以上が集まっているところでこの動画が流れているのはだいぶ面白い状況だなって思ったんですよね。

驚いた…

スペシャルサンクスとして@bonnuさんを挙げていますが、これは音声収録を@bonnuさんにお願いしており、素材として提供していただいたためです(大井町pmのslackにて受け取りを行いました)。@bonnuさん、ありがとうございました。

フェイスタオルを配った

弊社もGold Sponsorということもあって、ノベルティ配布ができるということでした。

京都といえば銭湯・朝湯だろうということで、配布するものはフェイスタオルにしたのですが、これがなかなか嵩張る。300枚も発注したので、まだ社内に30枚ほど在庫が残っているんですよ。誰かもらってあげてください。

そして、そのフェイスタオルは畳まれていない状態で届いたものだから、これまた大変。毎日すこしずつ心を込めてフェイスタオルを畳む日々が数日ほど続いたのです。

タオルを畳む日々

しかし、当日は配布用の枚数もそれなりに余ってしまったので、急遽現地でタオル配りおじさん業を敢行したのでした。まぁ面白おかしく配布できたので、ひとまず良かったと思っています。

裏トークでMCをやった

裏トークという企画、ここ数年のYAPCでは特にオンラインにおけるにぎやかしということでやってきたのですが、今年はオフライン、しかもYouTubeで我々の様子がうかがい知れる状態での敢行でした。

オンラインで自分らの様子が流れることについては特に気にならなかったんですが、オフラインイベントということもあって、様々な方が飛び入り参加するというスタイルが斬新かつ面白かったです。@dankogaiさんや@motemenさん、@kazeburoさん、@mackee_w(まこぴー)さん、@uzullaさん、@bonnuさん、@__papix__さん、@karupaneruraさん、その他多数の方に飛び入り参加していただきました。本当にありがとうございます。

1点、反省点というか何とかできないものか、と思う点として、我々MC陣がなかなかブースを離れられないため、もっとたくさんの人たちとコミュニケーションをとりたかったなーという思いがあります。

ちなみにわたしが個人的に好きだなーとなったトーク、本編では@mackee_w(まこぴー)さんの「デプロイ今昔物語 〜CGIからサーバーレスまで〜 」がとても良かったと思いますし、@moznionさんの「ソフトウェアエンジニアリングサバイバルガイド: 廃墟を直す、廃墟を出る、廃墟を壊す、あるいは廃墟に暮らす、廃墟に死す」は弊社若手エンジニアのお気に入りだったようでした。前日祭のRejectConでは@codehexさんの「Customer Experience Journey in NOT A HOTEL」がぶっ刺さりましたね。

学生さんと話した

弊社、なんと学生旅費支援プログラムのスポンサーもやっていました。そのため、学生さんとランチ休憩の時間帯にお話をする企画に参加しており、まぁなんというか、非常に雑な会社紹介LTをさせていただきました。

また、学生さんたちの質問に答えるビンゴ企画というものもあり、こちらではわたしの飾らない率直な回答をさせていただきました。

なかなか学生さんと語らう機会は少ないですので、こちらとしても学生さんが気にしている点等、大変勉強となりました。

前日祭LTバトルの査読をやった

うちの会社の@mini_bg_pro_N(あきた)さんが前日祭LTバトルで東側MVCを受賞したんですが、その査読をさせていただきました。

その中で、Perlに関する感想をが書いてあるスライドがあり、TIOVEのあのグラフを引用していたので、あきたさんには「ここを少しだけ説明したら飛ばすと笑いが取れそう」とアドバイス。

そうしたところ、あきたさん、適宜「飛ばし芸」を入れると面白いと悟ったのか、本番では彼自身の判断で時間が足りなくなる可能性も考慮し、Expressの解説も飛ばしてもうひと笑いを取るという職人技をやってのけたのでした。凄い。

世界一の笑顔を撮った

最高の朝食を食べた

さいごに

@ar_tama(あらたま)さん、ベストスピーカー賞おめでとうございます。わたしはトークを聴くことができなかったので、アーカイブが出たら絶対見るぞ!という気持ちで心待ちにしております。

そしてスタッフの皆さん、本当にお疲れさまでした&ありがとうございます。終わった後、スタッフの人たちともコミュニケーションをとる機会が得られたのはとても良かったです。

裏トークMCの仲間である@myfinderさんと@soudaiさん、お疲れさまでした。およそ12時間にわたる長丁場を我々は全部楽しんで過ごしましたね。それだけやったら、そりゃまぁ疲れると思いますので、風呂でも入ってしっかり体力回復しましょう。ついでに弊社のタオルも使ってやってくださいw

そして最後に、@__papix__さんと@azumakuniyukiさん、本当にお疲れさまでした。3年ぶりにオフライン開催のYAPCが復活できたのは、紛れもなくお二方の不屈の精神のおかげです。ありがとう。

DBのDumpファイルからスキーマクラスを作りたい

Rarmani - Dumpファイルからスキーマクラスを作ってくれるツール

わいとんです。まずはこちらの動画をご覧ください。

要するにこれはDumpファイルの中からCREATE TABLE文を抜き出して、それらを全て Moo basedなスキーマファイルにしてしまうというものです。

インストール方法

まだMetaCPANに上げるようなクオリティではないので、github止まりモジュールとなっています。

そのため、まずは git clone してくる必要があります。

$ git clone https://github.com/ytnobody/Rarmani.git

あとは cpanm 等をつかってインストールすればOK。

$ cd Rarmani

$ cpanm .

無事にインストールが完了すると rarmani コマンドが使えるようになります。

rarmaniコマンドの使い方とオプション

動画でも実際に rarmani コマンドの使い方を解説していましたが、改めて説明しておきますと、概ね以下のような使い方をします。

1
$ rarmani --driver=[ドライバー名] --namespace=[スキーマクラスの名前空間] < [ダンプファイル]

一応、全てのオプションについて解説しておきます。動画に登場しなかったオプションもあります。

  • driver : SQLの構文には細かい方言のようなものがあります。Rarmaniでは、DBMSごとのSQLの方言をdriverというもので吸収しております。現時点では MySQL, Pg, SQLite のいずれかを指定することができます。

  • namespace : 生成されるスキーマファイルの名前空間を指定する必要があります。動画内では MyApp::Schema としていましたが、ご自由に設定していただくとよろしいでしょう。

  • path : スキーマファイルをどのディレクトリに生成するかを指定できます。指定しない場合は現在のディレクトリを基準にスキーマファイルが出力されます。

  • roles : スキーマファイルはMooのクラスとなりますが、各スキーマクラスにて Moo::Role に準拠したロールクラスを複数指定することができます。例えば、DBIx::Mint::TableMoo::Role::ToJSON を指定する、等が可能です。

コードファーストとDBファースト

最近では「コードでスキーマを表現して、それをもとにDBにテーブルをつくる」というアプローチの「コードファースト」が流行しているようです。これ自体は開発速度の向上やDBのバージョニングの観点でメリットがあり、採用できるならしたほうが良いかな、というのが私の意見です。代表的なところですと、TypeScriptにおけるPrismaなどが該当するでしょう。

一方で、既存DBがある(しかも顧客情報満載である)場合やDBが軸となって設計されたシステム等、いつもコードファーストが最善とは言えないだろう、というのもまた私の意見です。その場合は旧来の「DBファースト」を選択せざるを得ません。

RarmaniはDBファーストのアプローチを、もう少し良い開発体験で進められるようにしたい、という思いから開発が始められました。Go言語では結構有名なORMapperであるSQLBoilerから少なからず影響をうけています。

さいごに

Rarmaniはまだまだテストコードが足りず、ドキュメンテーションが貧弱です。ドライバーも3種類しかありません。有志のご協力をいただけるととてもありがたいです。

そして、このエントリはPerl Advent Calendar 2022の10日目のエントリとなります。明日11日目はまだ埋まっていませんが、きっとどなたかPerlに愛のある方が書いてくださるのではないか、と期待しております。

ミニマルな開発会社を作りました

ミニマルな開発会社を作りました

※テクノロジーの話題ではありませんが、ご了承ください。

この度、私わいとんは 合同会社Y.pm(Y.pm LLC) というシステム開発会社を設立し、代表社員に就任いたしました。

きっかけは部門閉鎖

会社設立のきっかけは、それまでに勤務していた会社(以後「なんとか社」としておきます)において、部門閉鎖に伴う退職勧奨をうけたことでした。

退職勧奨についての詳細についてはここでは触れませんが、なんとか社は部門メンバー(全員エンジニア、私含め3名)に対し、誠意ある対応と手厚い処遇で退職オプションを設定してくれていました。

また、私個人としても40代の中だるみのようなものを感じておりました。具体的には、よりダイレクトに利益へ貢献する状況に身を置きたい、とひっそりと考えていたところでした。

そのようなことから、なんとか社の退職オプションはまさに「渡りに船」だったのです。

途中、なんとか社ではIoT関連のチャレンジや新規事業のシステム開発を行ったりなど、エンジニアとしてはなかなか新しいことをやらせていただいていたこともあり、とても感謝しています。

会社設立という選択をした理由

会社を辞めただけなら、再就職をするとか個人事業主としてやっていくなど、他の方法はいくらでもありました。

ただ、これらの方法を取らずに会社設立という方法を取ったのには、いくつか理由があります。

1. 案件の引き合いがあった。

もうこれはラッキーと言う他ないかもしれません。

むしろ案件の引き合いがあったからこそ、スムーズに会社設立の判断ができたのです。持つべきものは仲間だということが骨身に沁みました。この案件を紹介してくれた方には本当に感謝しています。

2. なんとか社の元同僚エンジニアたちと案件融通の見通しが立った。

実は元同僚エンジニアたちとは結構早い段階で「ひとまず個人事業主のギルドでも立ち上げよう」という話が出ていました。彼らとは今でも案件の融通や趣味の話、各自のスペシャリティ領域の情報共有などを日々行っています。

また、お互いの得意領域が見事にバラけていることも強みです。私たちが力を合わせればシステムがひとつでき上がります。特定分野だけの受注も可能で、誰が窓口になっても適切なメンバーに話が行くという体制ができ上がっています。

3. やってみたい開発組織構成案があった。

2とも一部被るのですが、受発注をベースとした最小構成の開発チームを作って動かしてみたいという思いがどこかにありまして、今回はその野望を実現するための下地をつくったに過ぎません。

受発注ベースの開発チームの亜種として、ニアショア開発のチームを動かし育てたいという野望もあります。

現時点ではあまり多くを語れませんが、恐らく近々にニアショア開発チームを組織して開発を進めることになるのではないか、と勝手に想像しています。

参考にしたサイト

大いに参考にさせていただいたのが以下のサイトです。

そのほか

  • 正社員採用はしていないんですか?

    • してません。こちらの必要に応じて発注をかける可能性はゼロではありませんので、貴方のスペシャリティを教えてください。
  • 御社のサイト、代表の写真がおかしいんですけど・・・

    • すみません、まともなセルフィーがなかったので、仮です。私のことをかっこよく素敵に撮影してくれる人がいたらいいのですが・・・

YAPC::Japan::Online 2022 の裏番組でMCを務めます!

YAPC::Japan::Online 2022 の裏トークチャンネルでMCを務めます!

Japan.pm 2021からYAPC::Japan::Online 2022へ

みなさんこんにちは。@ytnobodyです。

さて、昨年開催されたJapan.pm 2021というカンファレンスをご存知でしょうか。

Japan.pm 2021は、Perlの祭典YAPC::JapanのDNAを受け継いだ、オンラインカンファレンスでした。このイベントには日本全国のPerl愛好家やエンジニアたちが集い、情報交換を行う場も提供され、結果大変盛り上がりました。

また当時は私わいとん(@ytnobody)のほかに、まいんだー(@myfinder)氏とそーだい(@soudai1025)氏の3人がMCとして裏トークチャンネルを切り盛りしまして、こちらも大盛況となりました。

そんなJapan.pmですが、YAPC::Japan::Online 2022としてさらにスケールアップし、来る3/4(金)および3/5(土)に開催されます!

そしてそして!!!YAPC::Japan::Online 2022 でも裏トークチャンネルの開設が決定しており、私を含め昨年と同じ3名のMC(通称:大井町.pm)が場を盛り上げます!!!!!

さらに今年は、Perl入学式で大活躍中のお二方@xtetsuji氏と@sironekotoro氏による裏トークチャンネルも開設されるそうです!

詳しくはYAPC::Japan::Online 2022の運営ブログで!

近況報告

近況報告

公には書きづらい状況にあります。必要があれば対面で話す用意がありますので、ご希望の方はTwitterにてご連絡ください。

昨年アウトプットしなかった理由

基本的には「業務に差し支える可能性があるため」なのですが、実際のところはもう少し込み入っておりまして・・・お察しください。

今なにしてるの?

これを書いている時点ではまだ兼業フリーランスをやってますが、のっぴきならない事情により、4/12~は完全に無職となる予定です。それ以降でお仕事下さる方、いましたらお知らせください。

会社を起こすかもって話をしてた気がしますが?

高確率で会社(マイクロ法人)を起こすことになると思います。ただし、それは4/15以降の話になりそうです。また、その会社はITの会社ではないと思います。

IT辞めるんですか?

辞めません。まだ公には書けませんが、少なくとも食い扶持を稼ぐ必要がある以上、IT業界にはまだまだお世話になる所存です。

一つ前の項目で書いた通りマイクロ法人を起こす可能性が高いのですが、必要に応じてIT関連の法人も用意する可能性があります。

元気がない気がするんですけど・・・

めちゃくちゃ元気です!おかれている状況が複雑なだけであり、心身ともに元気ビンビンであります!

多忙なんですか?

暇です!つとめて時間的余裕がある生活を送ることを心がけております!

ところであんた誰?

詳しくはこちらをどうぞ。

コピペコード検出で定番のPMDはdockerから使うと楽

PMDをつかうとコピペコードの検出ができる

ある程度プロジェクトが進捗して運用フェーズに入る頃、コードの要所要所にコピペの跡が垣間見えた、なんて経験があるエンジニア諸氏は結構いるのではないでしょうか。

こういった重複コード(いわゆるコピペコード)を検出するのに便利なツールとして、比較的枯れたものの一つにPMDというものがあります。

このPMDはもともとJavaのソースコードについて、以下のような、リファクタリングに役立つ解析を行ってくれるものです。Javaには詳しくありませんが、どうやらJavaでは定番のツールかと思われます。

  • 予測可能なバグの検出(空のtry/catchなど)
  • 未使用のコード(Dead code)の検出
  • 最適ではないコードの検出(無駄なString/StringBufferの使用など)
  • 複雑すぎるコードの検出(不要なif, whichに置き換え可能なforなど)
  • 重複したコードの検出

そしてPMDは今ではプラグインを通じ、Javaの他に以下の言語に対応しています。

  • C++
  • C#
  • Fortran
  • Go
  • JavaScript
  • JSP
  • Matlab
  • Objective-C
  • PHP
  • PL/SQL
  • Python
  • Ruby
  • Velocity
  • XMLおよびXSL
  • Scala

残念ながらElixirには未対応のようです。またPerlにはpmd-perlというプラグインがありましたので、もしかすると対応しているのかもしれません。

Docker Imageを使うと楽

さて、このPMDですが、Docker Hubにいくつかビルド済みイメージがあります。私のお気に入りは rawdee/pmd:6.19.0-alpine です。

では早速、コピペコードの検出を試してみましょう。

今回解析の対象としたのは frankrap/bybit-api です。これは暗号通貨取引所「ByBit」のGo向けAPIライブラリです。

これを対象として選んだ理由は、手元に既にあり、ざっとコードを読んでそこそこ重複するコードがありそうだと思ったのと、一般公開済みのコードだからです。

あなたの環境がdockerを利用可能な状態であれば、プロジェクトルート直下で以下のコマンドを実行するだけで、コピペコードの検出が可能となります。

1
2
3
4
5
$ docker run --rm -v $(pwd):/src rawdee/pmd:6.19.0-alpine \
cpd --language go \
--files ./**/*.go \
--minimum-tokens 100 \
--exclude ./**/*_test.go

実際に bybit-api に対して実行した結果が以下の通りとなります。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
$ docker run --rm -v $(pwd):/src rawdee/pmd:6.19.0-alpine cpd --language go --files ./**/*.go --minimum-tokens 100 --exclude ./**/*_test.go
Found a 25 line (108 tokens) duplication in the following files:
Starting at line 197 of /src/./rest/api.go
Starting at line 251 of /src/./rest/api.go

log.Printf("PublicRequest: %v", fullURL)
}
var binBody = bytes.NewReader(make([]byte, 0))

// get a http request
var request *http.Request
request, err = http.NewRequest(method, fullURL, binBody)
if err != nil {
return
}

var response *http.Response
response, err = b.client.Do(request)
if err != nil {
return
}
defer response.Body.Close()

resp, err = ioutil.ReadAll(response.Body)
if err != nil {
return
}

if b.debugMode {
log.Printf("PublicRequest: %v", string(resp))

上記のように、コピペ箇所の検出ができていることがわかるかと思います。ここでは ./rest/api.go の197行目から25行ぶんのコードについて、251行目にも同一のコードが登場していることを表しています。

それにしても、この長いdockerコマンドを毎回入力するのは非常に面倒なことです。もしご自身のプロジェクトでコピペ検出をちょいちょいやっていきたいと思っても、こんなに長いコマンドを入力するだけでやる気が萎えてしまうというものです。

ですので、Makefileに以下のようなタスクを追加しましょう(go言語のプロジェクトの場合です)。

1
2
cpd:
docker run --rm -v $(pwd):/src rawdee/pmd:6.19.0-alpine cpd --language go --files ./**/*.go --minimum-tokens 100 --exclude ./**/*_test.go

このようにすることで make cpd とするだけでプロジェクト配下のコードについてコピペ検出が可能となります。

なお、上記のタスクはコピペコードが存在するとmakeに失敗しますので、このことを利用して各種CIに組み込むなどの継続的な措置を取ることも可能です。

【Ubuntu Linux】 自宅サーバで健康維持

テレワーク時代の健康維持

私のようなITエンジニアの強みとして「どこでも仕事ができる」というものがあります。これは他の業種の人からすると、非常に大きなメリットなのですが、一方で気をつけなくてはいけなくなるのが「健康」です。ITエンジニアは長時間の座り仕事になりますし、しかもパソコンの画面を注視するものですから、どう考えても健康に良いわけがありません。

私のように中年も半ばに差し掛かると、どうしても皮下脂肪も付きやすくなりますし、筋肉量もどんどん目減りしていきます。さらに身体がしなやかさを失いますから、腰痛や偏頭痛、慢性的な疲労感に苛まれていくことになります。

そこで、ITエンジニアらしい方法を使い、毎日決まった時間に「アレ」をすることにしました。

国民の健康維持の為に開発された「アレ」を自宅サーバで

さて、「アレ」についてそろそろ説明しておきます。「アレ」とは国民の体力向上と健康の保持や増進を目的とした体操、つまり「ラジオ体操」です。

このラジオ体操を、自宅サーバとして稼働しているASUS EeePC 1015PEMカスタム(SSD化&RAM増設→4GB / OS: lubuntu-18.04 LTS [bionic])で毎日11:00に再生することで、強制的にラジオ体操の時間を作ってしまおうという目論見です。

Ubuntu Linuxをコマンドラインで操作できる程度の知識と、余ったノートPCがあればできる内容となっていますので、ぜひ健康維持の参考にしてみてください。

必要なパッケージのインストール

強制ラジオ体操タイムに必要なパッケージは以下のものとなります。すべてapt installで導入可能です。

  • mplayer
  • ffmpeg
  • youtube-dl
  • alsa-base
  • alsa-utils

導入のためのコマンドは以下の通りです。

1
2
3
4
5
6
7
$ sudo apt update &&
sudo apt install \
mplayer \
ffmpeg \
youtube-dl \
alsa-base \
alsa-utils

YouTubeからラジオ体操の動画をDLする

導入したyoutube-dlコマンドを使い、ラジオ体操の動画を自宅サーバにダウンロードします。

1
$ youtube-dl "$MOVIE_URL"

上記のコマンドを実行すると、動画タイトルと同じ名前のwebm形式のファイルが出来上がっていると思います。($MOVIE_URLは任意のYouTube動画のURLに置き換えてください。)

ただ、このままのファイル名ではかなり取り扱いが面倒ですから、以下のような感じで半角英数のファイル名に変更しましょう。

1
$ mv 'ラジオ体操 第1 ・第2、首の体操-jXXXXXXXXXX.webm' Radio-Taisou.webm

これで動画ファイルRadio-Taisou.webmが出来上がりました。

動画をmp3に変換する

実際に動画のまま取り扱っても問題はないのですが、動画のままではどうしても若干面倒ごとが増えてしまいます。しかも今回は映像部分は不要で、音声だけが欲しいので、動画をmp3に変換します。

動画からmp3音声を抜き出すのにffmpegを使います。以下のような感じで変換可能です。

1
2
3
4
5
6
$ ffmpeg \
-i Radio-Taisou.webm \
-vn \
-acodec mp3 \
-af "volume=1.3" \
Radio-Taisou-audio.mp3

上記コマンドの各オプションはそれぞれ以下のような意味となります。

  • -i Radio-Taisou.webm 変換元となるファイルを指定
  • -vn 映像(ビデオ)オフ
  • -acodec mp3 出力音声の形式をmp3にする
  • -af "volume=1.3" 出力音声のボリュームを1.3倍にする
  • Radio-Taisou-audio.mp3 出力先となるファイルを指定

このようにすると、Radio-Taisou-audio.mp3が作成されます。

再生デバイス(スピーカーなど)を確認する

次に、どの再生デバイスから音を出すのかを確認します。コマンドは以下の通りとなります(sudo権限が必要)。

1
$ sudo aplay --list-devices

私の環境では、出力先に利用できるデバイスが一つ(EeePCに標準付属のスピーカー)しかありませんでした。

1
2
3
4
5
6
7
ytnobody@lubuntu1804:~$ sudo aplay --list-devices
[sudo] ytnobody のパスワード:
**** ハードウェアデバイス PLAYBACK のリスト ****
Home directory not accessible: 許可がありません
カード 0: Intel [HDA Intel], デバイス 0: ALC269VB Analog [ALC269VB Analog]
サブデバイス: 1/1
サブデバイス #0: subdevice #0

ここで重要となるのが、カード 0デバイス 0のところです。このあと音声を再生するときにこの番号を使いますから、しっかりと覚えておきましょう。

再生してみる

それでは実際に再生してみましょう。コマンドラインからmp3を再生するにはmplayerを使います。コマンドは以下の通りです。

1
2
3
$ sudo mplayer \
-ao alsa:device=plughw=0.0 \
Radio-Taisou-audio.mp3

このコマンドでは、-ao alsa:device=plughw=0.0 の箇所で再生デバイスを指定しています。例えば再生デバイスがカード 0デバイス 1の場合はplughw=0.0の代わりにplughw=0.1とする必要があります。ご自身の環境に合わせて変更してください。

うまく再生できた場合、スピーカーなどからラジオ体操のピアノ伴奏が聞き取れるはずです。音声の再生を終了する場合はCrtl-CかEscでmplayerを終了させます。

定期実行させる

再生までできたら、あとは任意の時間に自動再生されるよう、cronで定期実行させるだけです。

私の場合、昔からの手癖で直接/etc/crontabに定期実行の設定を書いちゃったのですが、その内容は以下の通りです。

1
00 11 * * * root mplayer -ao alsa:device=plughw=0.0 /home/ytnobody/Radio-Taisou-audio.mp3 > /dev/null 2>&1

最後に&gt; /dev/null 2&gt;&amp;1を追加してありますが、これはcronジョブが実行される際に、mplayerのSTDOUTとSTDERRが邪魔だったので、両方とも/dev/nullに捨てるようにしたのです。

まとめ

テレワーク時代の健康維持の為に、自宅サーバでラジオ体操を毎朝11時に流すようにしました。

座り仕事が続き、腰痛などに悩まされることが多くなった人はぜひラジオ体操タイムを作って、健康維持に努めましょう。

Generating Kotlin code from Protocol Buffers (without JVN on your host)

Gradle? JVM? Looks as chainsaw in this case.

Protocol Buffers is famous IDL(Interface Description Language) in these days. And the uber/prototool is needful tool for generating interface codes in any languages.

However information about generating kotlin code is quiet few in today.

Basically I was knowledgeless about kotlin before generating kotlin codes. And the our project is written in golang.

Okay, then I found an entry that telling as “JVM and gradle are needed when generating kotlin code through protoc”.

Hmm, “place build.gradle will be in our project”? Sounds not so good. Because our project is written in golang. Don’t forget, I just want “generating kotlin codes from protocol buffers“. This method looks as cutting sashimi with chainsaw.

Conclusion: Docker solves as like sashimi knife

In this case, requirement to environment for solving the issue is so huge. “Huge requirement to environment… I’ve got it!” yes, it is the Docker Hub. So I found the container image that fits this case.

It is the moia/prototool-docker (codes on GitHub).

Usage is followings.

1
2
3
4
5
6
7
8
9
10
11
12
### prototool.dockerfile
FROM moia/prototool-docker

RUN mkdir /proj
WORKDIR /proj

CMD protoc --kotlin_out=./proto/kotlin ./proto/definition/*.proto

### In your terminal
$ docker build -f ./prototool.dockerfile -t prototool .
$ docker run --rm -v /path/to/myproj:/proj -t prototool

Finally I got succeed to generate kotlin code from protocol buffers, with moia/prototool-docker that is instead of JVM on my host.

plenvsetup v0.06 has been released

Let’s setup your own perl environment without system-perl

Today I released plenvsetup v0.06. plenvsetup is a quick setup tool for perl environment with plenv.

In the latest version, plenvsetup uses Shoichi Kaji(skaji)‘s perl-install instead of Perl-Build. This allows, we can install perl without system-perl under plenv.

Now we can use new plenvsetup with following one-liner.

1
$ curl -sL https://is.gd/plenvsetup | bash  

You may zsh instead of bash.

Build on a Docker container

plenvsetup works on a Docker container it based on latest alpine linux image too.

For example, following Dockerfile setups the perl-5.30.0 with plenvsetup on container.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
FROM alpine  
WORKDIR /root

### install required dependencies (perl not required!)
RUN apk add bash libc-dev gcc make patch git curl

### download plenvsetup
RUN curl -sL https://is.gd/plenvsetup > plenvsetup && chmod +x plenvsetup

### use plenvsetup on bash
ENV SHELL=/bin/bash
RUN bash plenvsetup

### install perl-5.30.0 with plenv
RUN .plenv/bin/plenv install 5.30.0
RUN .plenv/bin/plenv global 5.30.0
RUN .plenv/bin/plenv rehash

CMD /bin/bash

Then, you can build the Dockerfile, and run perl-5.30.0 within the container.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
$ docker build -t ytnobody/plenvsetup .  
Sending build context to Docker daemon 2.048kB
Step 1/10 : FROM alpine
---> cc0abc535e36
Step 2/10 : WORKDIR /root
---> Using cache
---> 5a63e9728352
Step 3/10 : RUN apk add bash libc-dev gcc make patch git curl
---> Using cache
---> 0fed43f11239
Step 4/10 : RUN curl -sL https://is.gd/plenvsetup > plenvsetup && chmod +x plenvsetup
---> Using cache
---> 2b8ce1c5f1fa
Step 5/10 : ENV SHELL=/bin/bash
---> Using cache
---> 6f661e8cf191
Step 6/10 : RUN bash plenvsetup
---> Using cache
---> 24f2c6c713f0
Step 7/10 : RUN .plenv/bin/plenv install 5.30.0
---> Running in 86f08ede1c38
---> Downloading https://cpan.metacpan.org/authors/id/X/XS/XSAWYERX/perl-5.30.0.tar.gz
---> Unpacking /root/.plenv/cache/perl-5.30.0.tar.gz
---> Applying Devel::PatchPerl 1.80 (patchperl-extracted 0.0.1)
---> Building perl 5.30.0
---> See /root/.plenv/build/1578556140.1/build.log for progress
---> ./Configure -des -Dprefix=/root/.plenv/versions/5.30.0 -Dscriptdir=/root/.plenv/versions/5.30.0/bin
---> make
---> make install
---> Successfully installed perl 5.30.0
Removing intermediate container 86f08ede1c38
---> 73c2b52fa025
Step 8/10 : RUN .plenv/bin/plenv global 5.30.0
---> Running in 439f41b196dd
Removing intermediate container 439f41b196dd
---> 8e819e1afd8c
Step 9/10 : RUN .plenv/bin/plenv rehash
---> Running in 31d3278595ce
Removing intermediate container 31d3278595ce
---> 28e28a126931
Step 10/10 : CMD /bin/bash
---> Running in c67a1e299db0
Removing intermediate container c67a1e299db0
---> 3ceac81cf2f4
Successfully built 3ceac81cf2f4
Successfully tagged ytnobody/plenvsetup:latest

$ docker run --rm -it ytnobody/plenvsetup
bash-5.0# perl -v
This is perl 5, version 30, subversion 0 (v5.30.0) built for x86\_64-linux
(with 1 registered patch, see perl -V for more detail)
Copyright 1987-2019, Larry Wall
Perl may be copied only under the terms of either the Artistic License or the
GNU General Public License, which may be found in the Perl 5 source kit.
Complete documentation for Perl, including FAQ lists, should be found on
this system using "man perl" or "perldoc perl". If you have access to the
Internet, point your browser at http://www.perl.org/, the Perl Home Page.

So easy.

Kichijoji.pm #20 に参加しました

2019-11-22、六本木はフリークアウト社にてKichijoji.pm #20が開催されました。大変楽しませていただきました。7年目に突入ということで非常にめでたい節目でもあったようです。

なお私は途中からの参加となったのですが、懇親会LTにて「昔作ったソシャゲーの裏側」というタイトルで発表させていただきました。資料はこちら(PDF)

当日の様子についてはHaskell入門の著者であり熟練YAPCレポーターでもある@hiratara氏がまとめてくれています。

個人的に印象に残ったものとして、@818uuuさんの発表を挙げておきます。「人間が検索結果をどのように見ているのか」という研究の引用に「検索結果の見方は6種類に大別できて、それを共通アルゴリズムで説明できるのでは?」という話を聞いて、目からウロコでした。

さて、私の発表に登場した技術たちについて、如何せん古い内容でしたので、よくわからなかったという方もいらっしゃるかと思います。そこで、雑な内容ではありますが、このエントリで少し補足をしておきます。

Catalyst

Catalystは、2005年後半~2008年ころにかけて流行したPerlのWeb App Frameworkです。

現在でもメンテナンスが継続されており、ルーティングに独自のルールがあることが特徴の一つと言えるでしょう。

gearman

gearmanはPerl製のジョブシステムです。job clientからgearmandと呼ばれるデーモンにキューを渡すと、perlのwhileループを軸に組まれたworkerプロセスに対して処理を委譲することができます。

動作が軽量なのですが、workerプロセスがダウンした際、処理途中の内容が全部揮発してしまうのが難点でした。

TheSchwartz

TheSchwartzもPerl製のジョブシステムですが、その構成にMySQLが必要となり、ジョブそのものの堅牢性をMySQLに委ねることで、gearmanのような途中処理の揮発という問題が起こりづらいとされていました。

現在は@akiym氏によってメンテナンスされているようです。

UltraMonkey L7

UltraMonkey L7は、Linuxなどにインストールして利用するタイプの、オープンソースのソフトウェアロードバランサーです。

名前に含まれている通り、OSI参照レイヤのレイヤ7プロトコル(HTTPなど)に対するルールを設定できる、大変貴重なソフトウェアロードバランサとなります。

heartbeat

heartbeatは、Linux/HAプロジェクトの成果物の一つで、IPアドレスの冗長化構成を行うソフトウェアです。

これのおかげでロードバランサーやルータを多重化することができました。

iptables

Linuxカーネルに組み込まれたパケットフィルターです。よくある用途としてはファイアウォールとしての利用でしょうけど、最近ですとdockerが内部的にexposeのために利用しているようです。