言葉が持つ呪いにとらわれず生きたい

言葉は呪いを持つ。

 

趙の武霊王は紀元前310年、野台に立ち中山と斉を「望んだ」とある。

望むとは呪いを込めて見るということだそうだ(宮城谷昌光楽毅』より)

すなわち攻め取るということだ。

 

時に僕は自分の望んだ自分になろうとする余り自分自身の言葉にがんじがらめになって動けなくなることがある。たとえば「アメリカでプログラマとして職を得るにはコンピュータサイエンスのマスターの学位が必要だ」といった思い込みだ。これは僕自身に対する呪いとなっている。

これは実際に自分がかつてビザの問題で就職に頓挫しその時色々調べた結果、これが最も確度の高い方法らしいと学んだ結果なのであるが、現役高校生ではあるまいし、冷静に考えると僕がこの方法に執着するのはまったく馬鹿馬鹿しいのである。

見渡すと、学位などなくても右腕一本でこちらの会社に乗り込んで行って職を得ている人などゴマンといる。僕もそうすれば良いのだ。

 

ここまでは僕の話で、ここからは僕自身が放った言葉の呪いが思いがけず他人を縛るかも知れないということ。特に若い人がたまたまアメリカでプログラマとしてやっていきたいという夢を持っていて、たまたま僕のエントリを読んで「あゝ自分は文学部卒だから所詮叶わぬ夢…」などと思わせてしまったら遣る瀬ない。そんなことを思う必要はない。学位を持たぬおじさんの学歴コンプ爆発と鼻で笑って自分の夢を追いかけて欲しい。その呪いを断ち切るためにこのエントリを書いた。エーンガチョ!これで君も僕も自由である。

 

ところで冒頭の武霊王は胡服騎射と言って、かつての中国における貴族的な戦車による戦いから、戦士が直接騎馬に乗って戦場を蹂躙するという"野蛮な北方民族"の戦術を採り入れて趙を一大大国に押し上げた。

僕も学位はなくとも10年の実務経験があるのだ。胡服騎射して攻め入るのみ!

 

本当はビザ面接、ソーシャルセキュリティーナンバーの取得から免許の取得までをエントリにまとめようと思ったのにカリフォルニア州の運転免許試験に落ちたので訳の分からんエントリになってしまった…じゃあの。

基礎教養というのは人生の打率を上げるためのものかも知らん

なまじあり物のライブラリやなんかを組み合わせてそれなりのソフトウェアが作れてしまうし、10年もやってりゃそれなりに哲学のあるコード(良いコードとは言ってない)が書けるようになったので、ともすれば自分をいっぱしのシニアエンジニアだと勘違いしてしまうときがある。

 

ただそういったものがないフィールドで戦う必要が出たとして、僕は急に戦うすべを持たなくなってしまう。

たとえば難関大学の数学や物理を出たソフトウェア技術者が周りにゴロゴロいるわけだけど、こと2010年代後半のAndroidアプリ開発フレームワークより上のレイヤ)に限っていえば僕もそれなりに彼らと比肩できる自負があるが、彼らはこの世から急にAndroidが消えても次の何かにジャンプしてまた活躍する基礎がある。僕はそれが非常に恐怖だし羨ましい。

 

とかく自分は低レイヤに信仰にも似た崇拝感情をもっており、お釈迦様の手の上で楽しく踊っているとつい「この下はどうやって出来てるんだ」と不安を覚えてしまう。そして下に掘っていけば行くほどむき身の数学と対峙する必要がある。

 

ただこれは無意味な前提である。Androidは今日突然なくなりはしないし、低レイヤを突き詰めるとしてじゃあどこまでおりて行くんだ?半導体に電気ながしゃ気が済むんか?ということになるし、若干ノイローゼ気味なのかも知れない。

 

で、思うに、基礎教養っつーのは人生の打率を上げる以上の意味はないのかも知らんなぁというのが最近の気付きだ。

基礎教養はあるに超したことはない。そんなもんは僕だって分かりきっているが、さりとて高校のときにサボって10年寝かしちまったもんはもうしょうがないわけで、いまたまたま「上のレイヤ」でメシが食えてるんならそれでまあ良いじゃないと思うのが身の丈に合った幸せってもんなのかなぁと。

 

で、これも思うに、じゃあ基礎教養のないまま諦めるかっつーとこれはまあ僕の過去のエントリを見てもらうとお分かりのとおり僕は非常~~~に諦めの悪いおとこで、いまもチマチマやっとるわけである。ある日突然ハシゴが外されたときに僕も生き残る打率を上げたいんよ。

 

最後にツイートにも書いたけど僕はマジで普段エラそうに「技術者の待遇をあげよ!」とか喚いてるわりに高校数学もおぼつかない有様なんだけど、その僕が移動時間や夜眠れないときの睡眠薬に使ってる数学の参考サイトがこれである。

 

 

 

これほど素晴らしいコンテンツが原初インターネットから存在しているのはこの世の救いである。なんとかして御本人にお礼を伝えたい。僕は数学が苦手だが数学が好きな生徒(34歳)です。ありがとう。

Macで貧弱なネットワーク回線を再現してスマホアプリをテストするTips

QAさんに口頭で伝えるのが大変そうだったのでブログエントリにする。

iPhone/AndroidアプリのQA時に貧弱なネットワーク回線を再現したいことがままある。そういうときは「Network Link Conditioner」と「インターネット共有」を使うと便利だよという話。

  1. Network Link Conditionerで速度を絞る
  2. Macを有線インターネット接続し、WiFiをアクセスポイントにする
  3. このアクセスポイントに任意のスマホをつなぐと低速回線が再現される

1. Network Link Conditioner

https://developer.apple.com/download/more/

から「Additional Tools for Xcode」をダウンロード。その時々で最新のものを選ぶと良さそう。今日時点でmacOS High Sierra (10.13.3) + Xcode 9.3用のAdditional Toolsで動作を確認。

f:id:fushiroyama:20180221120002p:plain

古いNetwork Link ConditionerはHigh Sierraで正しく動かないので注意。

 

展開。Hardware > Network Link Conditioner.prefPane をダブルクリック。

f:id:fushiroyama:20180221120110p:plain

 

こんな感じでSystem Preferencesに入る。

f:id:fushiroyama:20180221120132p:plain

 

任意のProfileを選んでONにするだけ。Profilesは帯域やパケットロスも含めて細かくカスタマイズ可能。

f:id:fushiroyama:20180221120134p:plain

 

2. インターネット共有

「共有する接続経路」に有線インターネットのデバイスを選択する。ここではUSBイーサネットアダプタを選択しているが環境によって読み替えて欲しい。

「相手のコンピュータでのポート」に「Wi-Fi」を選択して「インターネット共有」を有効にするとアクセスポイントができる。

f:id:fushiroyama:20180221120139p:plain

右下の「Wi-Fiのオプション」からSSIDとかパスフレーズとかを設定できる。

 

3. つなぐ

AndroidでもiPhoneでもなんでもつないでください。低速回線が再現されます。

f:id:fushiroyama:20180221120143j:plain

 

Androidも使える方法でもっと楽なのがあったら教えて。

DroidKaigi 2018で登壇してきたので振り返りとか補足とか

DroidKaigi 2018で登壇してきたよ!

 

資料はこれ。

speakerdeck.com

ハンズオンのサンプルプロジェクトと課題はこれ。

github.com

 

良かった点

前日こんなツイートしてかつDroidKaigi公式アカウントがそれをRTしてくれたせいか、ハンズオンなのに立ち見/地べた座り参加者が出るほどの盛況だった。

それから参加者の半分はUnit Testが初めてかそれに近い状況で、資料もハンズオン課題(の前半部分)もまさにそういった方に向けて一生懸命作ったのでそれに関しては満足している。

 

反省点

いっぱいある…

  • Robolectricが初回実行時にダウンロードするライブラリの差分が会場ネットワークの詰まりで進まず、ハンズオンがストップした。これは運営さんやインフラを責めているのでまったくなく、そのような可能性に思い至らなかった自分が悔しい。
  • GitHub APIが同一IPからの単位時間あたりの接続数上限に達してしまい会場でサンプルアプリが動かなくなった。これも事前の調査不足というか、実際にそういう目に遭ってみないと考えつきもしなかった。
  • サンプルアプリをAndroid-CleanArchitecture風に設計し、その各レイヤごとにUnit Testを書けるようになるとめちゃくちゃ有意義なのでは?という想定のもとすべてを準備したが、会場の参加者がそれを求めていたように感じられなかった。完全に自分の独りよがりになった。
  • ハンズオンとして参加者に書いてもらう部分の調整の甘さ。僕はUnit Testを書くことそのものは大好きだが、ハンズオンをそれほど主催したことがなく、課題として空欄にして埋めてもらう部分の難易度設定に難があったように思う。
  • ハンズオン課題を英語対応しなかった。会場には日本語を解さない海外からの参加者の方もいて、その方には個別に対応したが、そもそもこれだけの規模のイベントでそういう参加者が当然に来てくださることをもっと真剣に考慮すべきだった。

とまあこれらはすべてもし次回があったときの糧としたい。まだ初日が終わったところで、2日目の早朝にぐずる赤ん坊を抱っこしながらこのエントリを書いているので、最終的なフィードバックの集計を待ちたいところだ。

 

サンプルアプリに関する補足

今回はスライドで座学をしたあと、前述のハンズオン課題をもくもく解いてもらった。

これはGitHubアカウントを入力したらその人のレポジトリ一覧を表示するという人類が一体どれだけ同じものを作ったのか想像もつかないほどありふれたアプリだが、設計には慎重な考慮を重ねてUnit Testもできるだけ「明日から仕事で使える感」を目指した。

 

個人的に課した縛りは次の2点。

理由は単純で、それぞれこのライブラリのことを説明するだけで50分のセッションができるほど習熟が大変だからだ。RxやDaggerが出てくることで今回の設計やUnit Testの本質がブレてしまうことを避けたかったのだ。

したがって非同期処理基盤には古き良きThreadPoolExecutorを用いDIはシンプルなコンストラクタインジェクションとFactoryパターンという古典に則った。

しかしながらシンプルで理解しやすさを求めて敢えてこれらの込み入ったライブラリを用いなかったことで却ってこれらのライブラリの恩恵でスマートに解決できている問題を自分で処理せねばならないという皮肉な結果となった。

このときには資料づくりは佳境でなかなか方向転換もままならなかった。参加者のみなさんの感想が楽しみでもあり怖くもあるが、なんとかこれらのライブラリを使わずありふれたJavaコンポーネントだけで書いたことによる可読性の方がわずかでも勝っていると信じたい🙏

 

で、サンプルアプリで特に注目して欲しいのはやはり各レイヤのテストコードだ。

前述のレポジトリはハンズオン向けにcloneしたらデフォルトでtasksというブランチがチェックアウトされるようになっている。こちらはUnit Testが空欄になっている。これをmasterブランチに切り替えると僕が普段書いているようなUnit Testをひととおり書いてある。興味のあるひとは是非見てみて欲しい。

Repositoryより下のビジネスロジックの部分はみんなも関心が高いしテストコードも結構書いてると思うんだけど、ちょうど同期と非同期が混じり合うUseCaseの部分はどうやってテスト書いていいか苦慮すると思うし、Presenterなんかもテスト書きづらいんじゃないかな。Presenterはちゃんと書くとViewとのインタラクションを検証できるので是非プロジェクトをcloneしてみてフィードバックが欲しい。

 

DroidKaigiの感想

とにかく最高のひと言。

After Partyでスピーカーには風船を付けさせるアイディアは最高で、これのお陰もあって「白山さんですよね?」と数え切れないほどの人に話しかけてもらって本当に光栄だった。

 

それからAndroid 設計パターン入門という本の著者陣がほとんど居るという豪華な状況が嬉しくて子供のようにサインを求めて回った。

 

返す返す、これほど素晴らしいAndroid関連イベントは世界でも早々ないであろう。代表の日高さん、スタッフのみなさん、登壇者のみなさん、そして参加者のみなさん全員に深く感謝したい。

まだ2日目が控えているが、こういうのは早ければ早いほどその時の熱気が文章に乗ると思ったので赤ん坊に3回目の授乳をして抱っこしたまま早朝の暗い部屋の片隅でこれを書いている。

今日もまたみなさん楽しみましょう。じゃあの。

DroidKaigi2018「はじめてのUnit Test」の資料事前共有とフィードバックのお願い

2/8の DroidKaigi 2018 にて「はじめてのUnit Test」というハンズオンを担当します。

で、setohさんのこのツイートにシビレたので僕も資料を事前共有することにします。

 

 

資料はこちら。

speakerdeck.com

 

念のため確認ですが、僕のセッションはあくまでハンズオンであって、

  1. 座学パートでこの資料をみながらUnit Testの書き方を解説する
  2. その後はチューターとしてサポートしながら各自ハンズオン形式でUnit Testを書いていく

ことを予定しています。ここで共有したのは前者の参考資料です。

本当はハンズオンのコードを共有したかったのですが、もうちょっと作り込みたいのでちょっと待って下さい。

一応、

  1. 初心者向け課題として、この資料にでてくるサンプルコード片のテストコードをひととおり用意しているので好きなように書いてもらいます。まったく初めての方はこれが達成できたら万々歳です。
  2. 中級者向け課題として、完全に動くシンプルなAndroidアプリを用意しており、これはいわゆるClean Architectureに範をとった構成になっています。これの各レイヤーのよくあるテストコードを書いてもらいます。かなり実践的な内容が詰まっていて、僕も共有するのが楽しみです。

という感じです。

 

で、これを見てくださったみなさんは資料でもうえに書いたハンズオン課題(構成案ですが)でもいいので、何でもコメントください。Twitter@fushiroyama にリプライでもDMでもください。

 

とにかく参加者のみなさんに「有益だった!」と言ってもらえる時間にしたい。そのためには一時的に恥をかいてもなんら構わない。なんでもコメントください。それではよい週末を。

 

macOS High Sierraのzshでちょっとハマったのでメモ

2年経って会社の開発マシンがリプレースの時期になったので今日からMacBook Pro (15-inch, 2017) Touch Barモデルで開発している。 思ったほど困ってないがzshの設定で少しハマったのでメモ。

ログインシェルをzshにできない

% brew install zsh
% chsh -s `which zsh`

としてもiTermを立ち上げ直すと $SHELL = /bin/bash に戻っている。

% sudo vim /etc/shells

/usr/local/bin/zsh # 追記

これで使えるようになった。

aliasと同名の関数を定義できない

Sierra環境で使っていたzshrcをそのまま使おうとすると

% source ~/.zshrc
/Users/shiroyama/.zshrc:188: defining function based on alias `ssh'
/Users/shiroyama/.zshrc:188: parse error near `()'

というようなパースエラーが出るようになった。たしかに alias sshssh() {} が存在する。 zshのことは全く詳しくないのでエラーでググったらどうやら関数に明示的に function ssh() {} のように function とつけてやれば良いようだ。 全部そのようにしたら晴れてエラーが解消した。

ちなみにHigh Sierraだからじゃなくて普通に考えてzshのバージョンだと思う。

% zsh --version
zsh 5.4.2 (x86_64-apple-darwin17.3.0)

Touch Barモデル雑感

よくESCがないとツライと聞くが、僕はESCC-jに割り当てているのでvimを使う上では何ひとつ困らない。 ただファンクションキーがないのは明確につらくて、カナ変換とかで思わず手がF7を探しちゃうし明るさも音量も調整にまごつく。 デスクに座ってる限りは外付けキーボードとトラックパッドを使っているので違いは感じないが携帯したときにストレスを感じるかもしれない。

あと、ポートがUSB-C * 4だけというのが一番気が狂いそうになる。電源もイーサネットアダプタ1もディスプレイケーブルもスマホも何もかも全部ぜーんぶUSB-Cである。 何年後かにこの世にほとんどUSB-Cだけが生き残っていたらもう少し生きやすいのかもしれないが、その前にAppleさんはiPhoneをUSB-Cにしなかったのはなんでなんですかね… そんくらいかな!

なお古いMacBookを返却する際にベタベタに貼りまくったステッカーを全部はがし終わるのに60分要した。 もう二度とこんなアホなマネはせえへんぞとステッカーをはがすたびに思うがどうしても再びやってしまうのは自分でも理解できない。


  1. ワイヤレスが不安定なのがストレスなのでデスクに座っているときはMacBookでも好んで有線接続している。

口が悪いエンジニア論争

通勤の暇にかこつけて今話題の「口は悪いが凄腕の技術者を雇うべきか」論争に対する自分の考えを残しておく。

まず大前提として「技術力も人間力もある」のがベストというのは揺るぎのないものであり、僕もここを目指したいと常々考えている。
その上でだけど、僕は「そうすることが必要な場面では口の悪さに目を瞑って技術力を取る」選択もありだと考える。

みんなこれには一家言あるようだけど、結局のところ全員前提としている状況が違うので意見が異なるのは当然のことだ。ただ僕が言いたいのは「ある種の問題はそれを解決することがそもそもできない絶対的な壁がある」ということだ。

本件に関して様々なツイートを拝見したが「そもそも技術力は育てられるが人間性は中々変えられない」という意見には、後半こそ賛同するものの前半には両手をあげて賛同できない。ある種の課題、プログラマのコンテキストで言えばいわゆるNP困難な問題は中庸なプログラマを100人並べても対処できない。ゼロだ。

なんでもいいんだけど例えば事業の課題としてGoogle Mapを超える最強の地図アプリを作ろうとするじゃない。そしたら最短経路とか求めないといけないけど、これそういう教育を受けてない人には無理じゃないですか。
ダイクストラ法ぐらいならググれば出てくるけどダイクストラ法はコストが負のノードがひとつでもあったら成り立たない。じゃあそれの改良版のコレコレを使いましょうとかね。

こういうのって数ヶ月から数年の教育と訓練と実務で身につける類のもので、人間性の優れた素人プログラマを10人集めても倒せない。こういうとき、酒癖も女癖も最悪だけど一騎当千呂布みたいな武将に力を借りざるを得ないのは仕方ないと思う。

なのでまとめとしては最初に書いたとおり、場合によっては口の悪さぐらいでは引き換えにならないぐらい技術力には壁があるんじゃないかしらということだ。それからこれが1番言いたいことなんだけど、みんな人間性の優れた呂布になろうな。僕も頑張る。