今回のScala関西サミットは、自分にとって3つのミッションがありました。
それぞれ別種の忙しさがありましたが、なんとか乗り切ることができたので、ようやく肩の荷がちょっと降りた気持ちです。
最近僕がどんな仕事をしているか見えにくいと思いますので、良い機会ですし今回の記事では上記3つそれぞれについて、ご紹介しようと思います。
今回Androidネタは封印して、Dottyネタで喋ってきました。
内容としては、Scala2系のつらみと、その対処法を2系とDottyで比較する話です。Dottyは非常に面白いけどまだ色々変わりうるし、それ単体で今すぐ役立つ話ではないので、敢えてScala2系にスポットをあてました。
サブトピックとして、暗黙展開の発散(implicit expansion divergence
)についてきちんと説明しているドキュメントがあまり見当たらなかったので、丁寧目に解説を書いてみました。
9/8のプレスリリースの通り、株式会社エフ・コードの商品開発部顧問に就任しました。
エフ・コード取締役の門田(@yoshinorikadota)さんが4年来の友人で、かつエフ・コード社にScalaMatsuri 2017のスポンサーになっていただいたことがご縁の始まりです。
会社のビジネスモデルを転換するにあたり、ソフトウェア部門を組織建てる初期から関われることが面白く、顧問のオファーをお引き受けすることにしました。職務内容としては、エンジニア組織の設計・プロセス改善を主として、自分が貢献できそうなところを見つけては落穂拾い的に様々なお手伝いをしています。
僕は基本的には黒子の立場だと自認しているのですが、同時期にがくぞ(@gakuzzzz)さんの入社と水島(@kmizu)さんの技術顧問就任という一大ニュースがあるということで、これを機にエフ・コード社をScala企業として認知してもらうため、既にエフ・コード社がスポンサーすることが決まっていたScala関西サミットにプレスリリースを合わせましょう、と持ちかけました。
スケジュールの言い出しっぺということもありまして、プレスの構成及び文面レビュー、撮影のセッティング、パネルをふくめた写真の構図決めなど、お手伝い諸々をしていました。
その結果のプレスリリースがこちら。お陰様でTwitter上でもScala関西サミットでも話題になりました。
エフ・コード、中村学氏がチーフアーキテクトとして入社、水島宏太氏・麻植泰輔氏が顧問に https://t.co/IDaDEdk1B6
— CodeZine (@codezine) September 8, 2017
そして当日にブースで配布する、来場者の記憶に残るノベルティグッズを何にしようか、というミーティングで僭越ながら僕がアイディアを出しまして、とてもキャッチーなコピーやポップとともに実現していただきました。
そう、null消しです。
株式会社エフ・コードでは本日大阪で行われているScala関西サミットにスポンサードさせていただいております。ブースでは煩わしいNullを消すためのCleanerを配布し、大阪からNullを一掃する構えです。よろしくお願いいたします。#scala_ks pic.twitter.com/R0afY5yURZ
— まつさか (@ma2saka) September 9, 2017
お察しのとおり、がくぞさん公式の肩書き Professional Null Cleaner
(参考)に因んでいます。がくぞさん、ネタにするのを快く承諾くださりありがとうございました。
こちらも非常にご好評いただいたので、ホッと胸を撫で下ろしています。
社内でエフコードさんからいただいたnull消しを配布している。これで弊社からnullぽが撲滅されるはずだ…。 pic.twitter.com/varGAYvprI
— Naoki Takezoe (@takezoen) September 12, 2017
一刻も早いnullの撲滅を祈っています。
技術アドバイザーをさせていただいているセプテーニ・オリジナルさんと、前述のエフ・コードさんからスピーカーが総勢7名(顧問も入れたらのべ11名?)も出るのを受けまして、せっかくなので社内練習会やりましょうと言い出したり、希望者ベースですが発表資料レビューのお手伝いをしていました。
どんなレビューをしたか振り返ると、そのときの準備の進捗度によって、ざっくり4パターンありました。
皆さん優秀ですし、教えるというよりもむしろ論旨を明確にしたり迷子にならないよう誘導するための、壁打ち相手としてレビュアー参加させてもらいました。
僕は基本的にカンファレンスには、本体よりむしろそれ付随する懇親会等で、集った人達とわいわい議論したり喋るのを楽しみに参加しています。
というわけで、河内(@kawachi)さん主催の前夜祭?(@airbnbの宿)に乗っかったり、2次会、3次会を企画させていただきました。
前夜祭?
Scala関西サミット参加者でairbnbの宿に集合してます! #scala_ks pic.twitter.com/EBweC9qo0p
— Taisuke OE (@OE_uia) September 8, 2017
2次会
Scala関西 Summit 懇親会二次会!おえさんの幹事力ぱねぇ (東京勢なのに!!) #scala_ks pic.twitter.com/IWT6dvqfZW
— Hiroshi (@itohiro73) September 9, 2017
3次会
Scala関西サミット史上最大?の2次回、3次会参加者数で、色んな方とも喋れてとても楽しかった!ご参加いただいた皆さん、ありがとうございました 🙌
カンファレンス翌日の9/10は、なんとなく3次会で「和装したいよね!」という話になり、京都でこんな感じになって、ぶらぶらと清水のあたりを散策していました。
和装の手配をしてくれた堀内(@noriakihoriuch)さん、どうもありがとうございました。
せっかく関西に来たということで、ご厚意に甘えて関西のScala企業にもお邪魔させていただきました。
粕谷(@daiksy)さんに連れられて、はてなさんでランチごちそうになりつつ、Scalaの事例のお話をお伺いしてました。有り難うございました!
また藤井(@yoshiyoshifujii)さんのご厚意で、MOTEXさんにお邪魔してモブプロ初体験してきました。
ペアプロだと「ここは〜を使う方が良いですよ」でその場では終わりやすいですが、モブプロだと更に他の人が乗っかって「それなら〜という方法もありますよ」と複数の手段のどちらが適切か議論しやすい点が面白いですね。その文脈において、ペアプロは並列数上げたスキルエクスチェンジが捗りますが、モブプロはレビュアー含めて弁証法的に知見が深まるのが良いところだと感じました。必要な場面でそれぞれ使い分けたいです。
藤井さん、体験ツアー組んでくださり有り難うございました!
]]>2015年5月から関わっていた BONX社の最終出社を7/31に済ませまして、来る8月末で退職 します。
これを機に、自分のBONX社での仕事を公に出来る範囲でまとめてみることにしました。
BONXの創業当初からずっとAndroidアプリを作ってました。
マンションの一室で、社内にはCEO,CTOと僕含め4,5人しかいないぐらいのアーリーステージのスタートアップということもありまして、 プロジェクト開始当初の状況を振り返ると、なかなかチャレンジング でした。
まず、人生で初めてVoIPクライアントをスクラッチから書くことになったものの、Androidではどのような設計にするのが一番良いか見当つかなかったので、とにかく試行錯誤の連続でした。何度書き直したかもう覚えていません。
また、悪名高きAndroidのBluetooth Low Energyを初めて、しかもCentralとPeripheral両面で使い倒すことになりました。最終的には機種依存バグとの戦いで、バッドノウハウがひたすら溜まり続けました。
また、BONXイヤフォンのBLE/SPP絡みのハードウェアのファーム仕様を策定することになったり、スポットですがBONXイヤフォンのファームウェア改善のために中国に飛んだり、IoTスタートアップっぽい仕事も若干ありました。
ただアプリ開発とハードウェア生産が並列して同時に走ったときが一番体力的に厳しく、最初のバージョンのリリース直前で心身ともにすり減っていた時期(しかもScalaMatsuri 2016開催前月)に、 当日夜に急遽中国行きの深夜フライトが決まって、翌朝から工場で中国のエンジニア達と缶詰で喧々諤々の議論をした のがピークでした。
そのとき、非エンジニアの通訳を介して、排他制御などの並行プログラミングの概念を伝えるのがいかに無理ゲー かもよく分かりました。やっぱりエンジニアでも語学大事 だと改めて思ったし、英語だけだと厳しい…という初めての経験でした。
今晩急遽中国行くことになりました(今年2回目) pic.twitter.com/gV0WGTjIxS
— Taisuke OE (@OE_uia) December 7, 2015
色々しんどかったけど、だからこそ面白くて、2年以上関わることになったんだろうなと思います。
そうこうしているうちに、ユーザーからの評価も安定しだしてちゃんと遊べるプロダクトになり、今年駆け足ながらもDDD/Clean Architectureベースの設計にリファクタリングできて、 ようやく一区切りつけられたかなと思っています。
その集大成として、世界最大のScalaカンファレンスScalaDaysに出したプロポーザルが幸運にも通りまして、BONXの事例についてシカゴとコペンハーゲンで講演することができました(※)。
※ 元々のスライド及び発表は英語ですが、以下のスライドは新宿Geek Loungeで喋った日本語版の資料になります
Bluetoothの話は、日本の勉強会で喋ったこちらのスライドにまとめてあります。
BONX社以外の、個人ワークでやりたいことが溜まりすぎた、というのが一番の原因です。
幾度となくBONX社の仕事をする傍らやろうと試していたのですが、トータルの活動時間が自分のキャパを越えてしまって体調を崩す ということを繰り返し、頓挫していました。 ある時、これ以上タスクを増やすのは現実的ではないなということに気づき、今取り組んでいる何かを諦めることを決めました。
では今携わっているプロジェクトの中でも、なぜBONXを辞めることにしたのか?というと:
BONX自体は今でも好き だし、たぶん来冬も一ユーザーとして使って遊んでると思います。
今もBONX社はAndroidエンジニア含め色んなポジションで募集してるので、よかったら是非どうぞ(宣伝)。
今後しばらくはフルタイムの仕事はせず、アドバイザーの仕事を続けながら サバティカルのつもりで個人プロジェクト中心に進捗出していきたい 所存です。具体的には下記に挙げたようなことを、少なくとも3ヶ月は取り組むつもりです。
このサバティカル後のことは未定ですが、近々発表できそうな進行中の話があったり、近い将来チャレンジしたいことも色々あったりするので、何らかの形で追々アップデートできたら良いなと思います。
そんなわけでこれから所属は若干変わりますが、引き続きどうぞよろしくお願いします。
]]>ScalaMatsuri座長の麻植(@OE_uia)です。
2017年2月25日、26日に開催されたScalaMatsuri 2017では、一般販売のチケット販売+スポンサー招待枠+関係者もろもろを合わせまして、 総勢600名程度 の方にご参加いただきました(実数はまだ集計中です)。 参加、登壇、協賛、そしてスタッフとして、皆さんがScalaMatsuriという神輿を担いでくださったお陰で、今年も盛況のうちに幕を閉じることが出来ました。
昨年の振り返りブログでは言及したScalaMatsuriの国際化はさらに進み、フィリピンのパーペチュアル・ヘルプ大学から30人ほどの団体参加者と、Scala Taiwanの団体参加者、そしてその他の国からの参加者も増えました。
Thank you very much @ScalaMatsuri team for having me again this year. The conf is growing and becoming more international - wow! :-)
— Konrad Malawski (@ktosopl) February 28, 2017
また、それ以上に参加者全体の意識の変化も見て取れました。去年はまだまだ日本ローカルの参加者と、海外からの参加者が別れて交流しがちだったのですが、2日目夜の有志による寿司ディナーでは入り混じり、国際カンファレンスらしい交流がそこかしこで繰り広げられるようになりました。
@ScalaMatsuri my wife and kids are saying hi back :) pic.twitter.com/SKSq4TGKMG
— Paweł Szulc (@rabbitonweb) February 26, 2017
とまあ、国際化は引き続き順調に進んでいるので敢えて言うほどのこともないですし、今回の振り返りブログはScalaMatsuri運営の内情と、今年度の構造改革の中身についてお話します。
なお、お気づきの方も多いかと思いますが、タイトルはかとじゅんさんの今回のScalaMatsuriセッションタイトルのパロディです。
ScalaMatsuriの各セッションも好評で、その中でも非常に注目を集めたセッションとして、かとじゅんさんによる「ChatWorkのScala採用プロダクト “Falcon” リリースまでの失敗と成功の歴史」というものがありました。
ユーザーににさほどの意識をさせることなく、このままでは破綻が見えていたレガシーシステムから、スケーラブルなシステムへの移行を成功させた、日本のScala業界でもエポックメイキングなものでした。当日は大盛況でしたし、来れなかった方も、(録画はありませんが)スライドは公開される予定ですのでお楽しみに。
さて実はScalaMatsuri準備委員会、そしてその母体となる一般社団法人Japan Scala Associationも、同じように皆さんから見えないところで、このままでは破綻が見えていたシステムから、スケーラブルとは言わない間でも、十分持続可能なシステムへ移行をしていました。
それは、コミュニティカンファレンスとしてボランティア有志で運営していたところに、創業以来初となる従業員を雇い入れたことです 。
コミュニティカンファレンスと商業カンファレンスの最大の違いは、スタッフが皆他の仕事をしながら、ボランティアベースで運営している点でしょう。 コミュニティカンファレンスはコミュニティの中の人がつくり上げるため、特定の企業に依存せず、より公平で民意を取り入れやすいというメリットがある一方で、運営スタッフは他の仕事する傍らに準備をするため、工数が確保しにくいというデメリットがあります。実際のところ、ScalaMatsuriが大きくなるにつれ、ボランティアベースでの運営は年々厳しさを増していました。
例えば、昨年は私の場合開催1ヶ月前は殆どの時間がMatsuriに吸い取られる状態で、他の仕事は週1~2程度しか出来ませんでした し、 他のスタッフもそこまでひどくないにはしろ、かなりの疲弊感が漂っていました。
特にメール対応業務は平日昼間に発生することが多く、他の仕事を並行して行っているスタッフは対応の限界がとうに訪れていました。 どのくらいマズイ状態だったかといえば、メール対応を行っていたスタッフは、ほぼ例外なく燃え尽きて、次年度のスタッフ参加を避ける、という状態でした。
コミュニティカンファレンスでは、どこも程度の大小は有れど、共通の問題として抱えてることだと思います。例えば、一昨年のフランスのScala.IOカンファレンスでも、リードボランティアの時間が取れない等の理由により、開催自体が突然中止されました。ScalaMatsuriも実際、昨年までは僕を含めた数人が単一障害点/Single Point of Failureでしたので、同じことがいつ起きても不思議ではありませんでした。
そんな状態だったので、昨年のScalaMatsuri振り返りブログを書いた後、竹添さんとこんな会話をしたことを覚えています。
無理なくって書いてあるけどだいぶ無理してる気がする(主におえさんが)。/ ローカルカンファレンスを無理なく国際化する方法 - ScalaMatsuri 2016を振り返って - OE_uia Tech Blog https://t.co/ET02skgDOU
— Naoki Takezoe (@takezoen) February 6, 2016
@takezoen ありがとうございます。
— Taisuke OE (@OE_uia) February 7, 2016
今でも他の準備委員にサポートいただいてはいるんですが、全員ボランティアベースなので、規模が大きくなるにつれて無理は出ちゃってますね・・・
なので、そっちの無理もなくすべく、アウトソースやバイトとか、運営形態の見直しも考え中であります。
時は前後しますがこの半年ほど前、私が信頼を寄せている友人である高橋さんが、結婚したので家事と両立できる仕事を事務職で探している、という話を聞いた時、ScalaMatsuriの事務仕事はほぼ100%リモートワークだけど、興味はないかと申し出ました。
そのときから、給与体系、勤務体系、仕事内容などなどの説明や調整をしながら、およそ1年弱の時を経て、今年度のScalaMatsuri準備委員会の事務サポートとして入ってもらうことになったのです。
彼女が入ったことで、ScalaMatsuriの事務は驚くほどうまく回るようになりました。
平日昼間に発生しがちなメール対応業務は、即座に返せることが多くなりました。 また日中Slackやissueを見て回ってもらえることで、ボールの取りこぼしが起きにくくなりました。 その他でも当初は予定していなかったような細々とした仕事、例えば翻訳後テキストをスライドに字幕としてつけるなど、定形作業が発生しがちな翻訳チームのサポートなど、多岐に渡って仕事を見つけて動いてくれました。 個人的には、僕の時間を取られていた経理業務の大半を彼女に渡せたことで、より全体を見るという仕事に時間を割くことができるようになりました。
結果として、特定の準備委員に負担がしわ寄せされるという事態も、相当に軽減されました。
振り返って考えてみると、このスキームが上手く行った理由は幾つかあります。
このように、実は今回が特殊ケースというより、コミュニティカンファレンスの人手需要と、リモートワークの事務仕事に対する需要はとても相性が良い ものだと思います。事務系業務の重さに苦しんでいるコミュニティカンファレンスの運営者は、社員ないしは業務委託という形で、お仕事で事務をしてくれる人を引き入れることをぜひ検討してみてください。
とはいえ、ノウハウが全くない状態でいきなり人を入れるのはハードルが高いと思いますので、仕事内容・労働条件・その他もろもろについて、出来るだけ詳細に書いていこうと思います。
お願いする業務は、業務への慣れや季節性をふまえて、以下のように徐々に増えていきました。
元々はスポンサー対応や経理をしてもらえれば十分、と思っていました。 ですが、彼女はとても意欲を持って取り組んでくれて、上記の通り様々な業務に取り組んでもらっています。
2016年の7月から12月までは業務委託、2017年1月からは従業員として働いていただいてます。
2016年はどのみち彼女の確定申告が必要だったということ、並びに従業員を雇うということに対し最初は何も知見がなく抵抗があったこと、またお互いのお試し期間は少し欲しいよね、というもろもろ事情もありまして、業務委託にさせてもらっていました。 実際のところ、このスキームは全く新しい試みだったので、果たして上手くいくのかどうかという不安も正直なところありました。 ですが蓋をあけてみると、準備委員会のスタッフからも、彼女からも大好評で、ぜひともお互い一緒に仕事を続けたいということになりまして、従業員になっていただきました。
余談ですが、これが僕の人生初の雇用経験だったので、給与や雇用保険の計算から各種書類の作成・ハローワークへの届け出まで、高橋さんと一緒に色々と右往左往しながら対応したのは良い思い出ですw
労働契約としては裁量労働制で、通年で平均すると、およそフルタイムの半分程度の時間を割いてもらっている計算です。 とはいえ、カンファレンスは季節性のある仕事なので、カンファレンス開催前後はとても忙しく、逆に終わって残務整理が落ち着いた後は、非常に仕事が少なくなります。
土日は基本的に休みで、ミーティングは月1の準備委員会定例ミーティングのみに必ず出てもらい、そのぶん他の平日に代休を取ってもらうような運用です。 その他、彼女から休暇の申請があったときには、僕や他のスタッフがサポートに入るなどし、適宜調整しています。
それ以外のミーティングとしては、全体のもくもく会を月1程度でやったり、必要に応じて僕と彼女で毎週1回のぷちもくもく会を設定して引き継ぎ含め、業務の相談等を一緒にやっていました。
なお、給与については、彼女が既婚であり扶養に入っていることをふまえ、カンファレンスの現予算でも十分賄うことができる金額で調整し、設定しています。
100%事務仕事をリモートワーク可にする仕組みにもひと工夫ありました。
経理業務など、書類を扱う仕事ではリモートワーク化が難しいと思います。というのも、書類で請求書等などの管理が必要な会社は多いですし、規模感・業界も様々な協賛企業との間で業務が発生する弊社では、完全にペーパーレスにすることは困難です。
Japan Scala Associationでは、今年度から 郵送物転送サービスのあるバーチャルオフィスを登記先に変更することで、住所に一枚抽象レイヤを追加 しました。 これによって彼女の住所を晒すことなく、請求書などの郵送物を彼女に直接受け取ってもらい、経理処理を進めてもらえる体制が出来ました。
また、業務連絡はSlack、タスク管理はGitHub issues、ファイル管理はGitHubとGoogle Drive、各種提出物はGoogle Form、スポンサー関連の各種管理はGoogle Spreadsheet、各種自動化はZapierと、リモートワークでもそのまま使えるツール群は既に採用し運用実績が有りました。
また、スポンサーのWebロゴ掲載のサイズ変更等の編集にはImage Magick CLIを使用しています。
もちろん、非エンジニアにgit、Zapier、Image Magickといったツールを使いこなしてもらうのは簡単なことではありませんが、gitの場合はSource TreeなどのGUIツールも有りますし、特に高橋さんの場合は意欲高く学んでもらえました。
最初に丁寧に教えて、あと困った時の質問への回答を何度かした程度で、実際に彼女は今ではGitHubにも慣れIssue管理をしたりPullRequestを送れるようになったり、またZapierでGoogle FormとSlackの連携の自動化をしたり、その他ツール周りにも慣れてもらうまでになりました。
ここは様子をみながら調整する必要が有りますが、基本的にビジネス上の決定は座長(僕)やチームリーダーが行い、経理業務も実際の振込作業だけは座長が行っています。
また、出来るだけドキュメントやWikiなどに決定事項を残すことで、彼女が誰かに聞かずとも答えられる・判断できる範囲を広げることが重要です。
このようにして、無理のない形で徐々に仕事の移管ができ、ようやく継続可能で、かつコミュニティ色を失わないScalaMatsuri運営体制を作り上げることができました。
また実は、彼女以外にも、スタッフであるEugene Yokotaさんの友人のSandyに、 英語ドキュメントのネイティブチェックについて、リモートベースでお仕事としてお願いするという試み をスタートしました。ここについては、Yokotaさんにスキームのリードをしていただいています。この仕組みも非常に上手くワークしました。 (なお、Sandyについては、従業員ではなく、飽くまで業務委託として発注しています)
まだまだ進行中ですが、今まで属人性の高かった各種業務のドキュメント化、マニュアル化を今年度から様々な面で進め始めました。ここについては @noriakihoriuchi さんや、 @takezoux2 さんにリードしていただいたりしています。
これにより、万が一誰かが動けなくなっても、他の人がバックアップしやすい体制を強化していきたいと思っています。
振り返ってみると、より持続可能で耐障害性の高いスキームを作って、リクルーティング・導入・運用をして成功を収めた ことが、僕の座長としての初年度の、ちょっと胸の張れる成果なのかなと思っています。
これによってスタッフの事務作業に割かなければいけない時間が減り「どうやってScalaMatsuriを改善していくか」という本質的な問題について考える時間がとれるようになってきました。今まではリソース的制約により、やりたいけど出来なかったことが幾つも有りましたが、今後はそういったことにも取り組める体制ができたのではないかと思っています。
このブログを読んで、「次年度にScalaMatsuriスタッフとして参加してみたい!」 という気になった方がいましたら、3月下旬〜4月頭に都内で開催を予定している、ScalaMatsuri2017スタッフ打ち上げにぜひご参加ください。実費分の参加費を頂戴しますが、今年度スタッフだけでなく、次年度のスタッフ参加を検討している方もご参加いただけますので、雰囲気や内情など色々見聞きしてもらえる機会になると思います。詳細は決まり次第、@OE_uiaのアカウントで告知します。
また この件や、その他ScalaMatsuriの運営について詳しく話が聞きたいカンファレンス運営者がいたら、お気軽に@OE_uiaまでメンションを飛ばして下さい。 僕がPyConやその他先輩カンファレンスのみなさんにしていただいたように、次の世代へ知見を伝えていきたいと思っています。
最後になりますが、 今年度大活躍してくれた高橋さん、本当にありがとうございました。 今後共よろしくお願いします!
]]>何を書こうかと考えていたら、そもそも10/8に開催されたScala関西サミットの話をブログに書いてないことに気づきました。
なので今回はそのことを紹介しつつ、色々補足できたらと思っています。
その前に。
時期を逸した感じがしますが(きの子さんすいません…)、去年にも増して楽しかったです!
(結果的に)タイムテーブルの組み方が非常によくできていて、特にB会場のトラックがActorモデルの解説から、Akka-Stream、と続いていき、最後にAkka Clusterの闇の話が入る、という最高の流れでした。
そして日本各地からだけでなく、台湾からの参加者もいらっしゃるなど、多様性という意味でも大きくグレードアップしていました。
これが無料イベントって… 運営のことが非常に心配になりますので、お金払いますから今後もぜひ続けて下さい、という気持ちです。
ScalaMatsuriも負けてられません!
というわけで、ただいまセッション投票の集計&選考&タイムテーブル準備などの真っ最中でございます。
近々、遅くとも年内にはまとまった情報を出せると思いますので、しばしお待ちくださいませ。
僕の主観ですが、今までにも増して豪華で面白いトークの集まる、素晴らしい2日間になると思います。
さて、本題。
このトークではActorモデルの解説と、ActorモデルがなぜBONXというVoIPアプリにフィットしたのか、という話をさせていただきました。
ただ、あまりAkkaのカスタマイズ性がVoIPのチューニングにどう役立つのか、という話は出来ずじまいでした。 今回はそこにフォーカスをあてます。
VoIPアプリの場合、機能要件の実装・テストより、非機能要件の改善に時間を使います。 具体的には音質と遅延の改善です。
Actorモデルで設計されたVoIPモジュールにおいて何が一番音質の劣化原因になるかといえば、フレーム間で発生した遅延や、フレームの欠落です。
あるフレームが再生されてから、次のフレームが再生されるまでに間に大きく遅延すると、そこで波形が途切れること(非線形)になりますので聴感上ブツッというノイズに感じます。
同様にして、フレームの欠落が起きると、やはり前後のフレームが非連続になりますのでノイズに感じます。
大雑把に言えば、遅延の改善が音質の改善に繋がります。
では、遅延をどのように改善したら良いでしょう。
安定している条件では、Akkaというより、個々の計算量を減らすなどモジュールごとのチューニングが必要となることが多いです。
しかし音声ストリーム処理の、しかもグループ通話など負荷が時間とともに変わりうる場合だと、Actorシステムにボトルネックが生じることが往々にしてあります。
まず測定・監視して詰まりやすいhotspotになる場所を探し出し、その後で負荷を分散・解消する方策を考え試行錯誤する必要があります。
解決策は十分にdispatcherの並列度を上げる必要があるときもあれば、局所的にActorを並列化するべきなケース、throughtputなどのパラメーターが重要になるケースなど様々です。
Akkaではこういた実行モデルのチューニングの大部分を、confファイルで簡便に変更出来る点で優れています。
また、Mailboxのサイズを適切に設定することも重要です。
小さすぎて溢れるとフレームの欠落になりますし、かといって大きすぎると遅延の解消に時間がかかります。
音声ストリーム処理の改善、とても難しいけど、チューニングがユーザー体験に直結するのはなかなかレアなので面白いです。
そんなAkkaのチューニングをやりたい方、今Androidエンジニアを絶賛募集中ですので、よかったらこちらからどうぞ。
それでは。
]]>550名ほどの来場者と、16万人を超えるニコ生来場者を迎え、大盛況のうちに幕を閉じることが出来ました。
ご参加いただいた皆さん、ご協賛いただいたスポンサーの皆さん、そして準備に尽力してくださったスタッフの皆さん、本当にありがとうございました。
スライド類はだいたい出揃ってきました。また動画は納品後に順次アップロードします。問い合わせの多い翻訳の提供については、現時点で確約はできないですが何らかの形で提供できないか調整しています。
さて、今回は振り返りをするにあたって、「ローカルカンファレンスを無理なく国際化する方法」というタイトルにしました。
なぜか。理由は2つあります。
1つは、そもそもScalaMatsuriの前身となる第一回目のScala Conference in Japan発起の理由として、日本と海外のコミュニティの交流をうたって開催されたからです。
ScalaMatsuriの存在意義はもはやこれだけではありませんが、1つの大きな柱ではあります
もう1つは、今回のScalaMatsuri 2016では、ようやく無理のない国際化の第一歩が踏み出せたからです。
海外のカンファレンスのスピンオフではないローカルな独自カンファレンスで、知名度0からのスタートだったので、当初は招待講演者4名+関係者のみ海外参加者と、今思えばとてもローカルなものでした。ここから改善して今にいたっています。
フィードバックについてはまだ集計中ですが、Twitterハッシュタグを確認する限りにおいて、マジョリティの日本人参加者と、海外からの一般参加者、どちらに寄り過ぎることもなく、楽しんでもらうことができたと感じています。
Serious respect for #ScalaMatsuri staff and speakers. What an amazing experience, already looking forward to the next one.
— Devon Stewart (@blast_hardchese) January 31, 2016
そのことが、個人的にはちょっとした節目のように感じており、なぜ国際化をしたいのか、無理なく国際化をする上で何をしたのかについて、整理するいい機会なのでしたいと思います。
普段の仕事や勉強会で会う人たちとの議論もいいですが、普段なかなか会えない人の話を聞いたり、議論したりするのは楽しいですよね。
別に海外に限らず言える話ではありますが、国をまたいだ人と会う機会はことさらないですし、通訳を交えて話せる機会は更にありません。
それをScalaMatsuriという口実で会えて話せる環境を用意しちゃおう、ということです。
じゃあスピーカーとして来てくれれば十分じゃん、という意見もあるかもしれませんが、スピーカーとして来るだけでなく一般参加者として来てもらっても、例えばScalaTest作者のBill Vennersさんのようにアンカンファレンスで登壇してくれるケースもあります。
またもし登壇しなかったとしても、懇親会などで議論するチャンスが出てきます。
例えば@xuwei_kさんのブログでも紹介されてましたが、たまたま居合わせたので彼とBillとの議論を通訳したり、女性エンジニアを増やしたいと考えている海外スピーカーの方にきの子さんの取り組みを通訳して紹介させてもらったりしていました。
その他にも、日本で面白いことをしている人たちを、海外から来た関連分野の人に色々紹介するという草の根活動をしていました。
例えていうならば、暖流と寒流がぶつかる潮目は栄養豊富で良い漁場になることが知られていますが、日本と海外のコミュニティが交わるScalaMatsuriもまた面白い議論を巻き起こす潮目になれたら、と考えています。
この潮目の発生を初めて感じたのが、ようやく今年のScalaMatsuri 2016だったりします。
Scala By The Bay主催者のAlexyさんとも話すのですが、OSSコミュニティをどこかに作る時には最初のモーメンタムが効いてきたりします。
勉強会やハッカソン、なんでもいいんですが、開発者とユーザーの物理的な距離が近いことが最初のcontribution、PullRequestを送る敷居を下げてくれたりするという意味です。
実際、僕がND4Sを作ったり、ND4Jにcontributionしだしたのも、DeepLearning4j作者のAdamさんと物理的に会ったというのがきっかけでした。
僕は、ScalaMatsuriではそんな初期モーメンタムを提供できる場になれたらいいと思っています。
具体的には、日本発のOSSをもっと紹介していきたいと思っていますし、日本のコミュニティが興味を持ちそうな海外のOSSの関係者を連れてこれたら、と考えています。(これに関してはまだちょっと出来てるとは言いがたいですが)
ScalaMatsuri 2016は、アジアでは最大規模のScalaカンファレンスですし、世界的にも少なくとも5指、ひょっとすると3指に入る程度には大きいです。
世界最大のScala Daysが1日あたりおよそ800人程度、ヨーロッパ圏最大のScala eXchangeが1000人(但し3日間合計の可能性あり)、そしてScalaMatsuriの1日あたり550人、といった具合です。その他のScalaの国際カンファレンスは、大抵200人〜300人程度のレンジに収まっていることが多いようです。
海外から来た参加者が口を揃えて規模の大きさに驚きますし、それ以上に実利的な理由が3つあります。
1つが、CFPに応募するときの理由になるということです。多くの観客の前で話せる、というのはモチベーションになりますし、実際応募前に「どのくらいの規模?」と聞いてきた人もいます。CFPの応募が集まるほど魅力的なトークが来る確率が上がりますし、競争率が上がることはトークの質を担保する上で重要な要素です。
1つは、規模が大きいと遠方から参加しやすくなるということです。規模が大きければ、旅費が職場の経費で落としやすくなります。海外からの参加者にとってはとても重要です。実際、今回スピーカーには旅費サポートをオファーしていましたが、職場の経費で来てくれて旅費サポートは不要だと断るスピーカーもいました。
1つは、主にScalaエンジニアの採用をしたい企業が、協賛する動機になるということです。集まるエンジニアの数が多ければ、同じコストをかけたときでもリーチ出来る人数が増え、また採用のチャンスにつながります。協賛企業が集まるということは、その協賛金をつかってより広い会場を借りたり、翻訳などの参加者向けのサービスを向上させたり、海外公演者の旅費サポートの原資にすることができます。
どうやって規模を大きくするかについては、鶏と卵の関係でもあるのですが、質の高いトークを集める、チケット代を抑える、宣伝をする、など色々あります。
質の高いトークを集める、と書きましたが、実際にはとても難しいことです。
なぜなら特に海外から日本に来るには、お金もそうですが、時間も体力も大変に使います。そのハードルを乗り越えてもらう魅力を、カンファレンス内外で構築しなければなりません。これにはとても苦労しました。
まず、時期を敢えて真冬にしました。これはScala Days SF 2015に僕が参加したときに、色々な人達にScalaMatsuriの宣伝をしていたところ、日本に興味を持ってくれる人が軒並みスキー・スノボに興味を示していたことが原因です。
なぜかといえば、ご存知の通りScalaはスイス工科大学のEPFLで作られた言語なので、その周辺国出身者が多く、Scala関係者にスキーヤー・スノーボーダーが多くなっているということ。そして、どうも日本は世界的なパウダー・スノーのメッカとして知られているからでした。
もっといえば、Scala Daysの1日目までの段階では正直なところ、秋開催のつもりで考えていました。ただあまりにも冬を希望する声が多く、また他の日本の言語カンファレンスがことごとく秋開催で日付がかぶるリスクなどがあったこと、またCFPでの応募集めという大きな課題への解決策になってくれる可能性を鑑みて、その日のうちに同じく参加していたYokotaさんや、夜に日本のメンバーとチャットで相談して冬開催に決めました。2日目から改めて冬開催ということで宣伝したところ、そのときScalaMatsuriの話をしたJonasさん、Konradさん、Billさん、Tomerさん、Alexyさんなどが今回実際にScalaMatsuriに来てくれました。特にTypesafeチームはScalaMatsuriの前に北海道のニセコでスキーを楽しんでいたようです。(僕も行きたかった…)
Enjoying Japan's amazing powder. pic.twitter.com/WvmaCtDxoU
— Jonas Bonér (@jboner) January 27, 2016
次に今回から思い切ってCFPを投票制にし、投票上位者には最大$2,000の旅費サポートを提供することにしました。これによりありがちな政治色を排除することと、金銭的なハードルを超えられるようにしました。結果的に、従来招待講演者として招聘していたような人たちが続々と応募してくれて、また実際に多くの人が参加してくれたので、十二分に元は取れています。
また投票制を採用するにあたり、翻訳チームがCFPの応募を原文の雰囲気に忠実な形で日<->英双方向の翻訳をしてくれたお陰で、日本の参加者も海外の参加者も、さほど意識することなく投票に臨んでもらえる体制ができました。
今回からプロによる同時音声通訳を2会場分提供することで、英語話者でも複数のトラックから聞きたいものを選んでもらえるようにしました。これにより日本人参加者もより英語講演を楽しみやすくなりますし、海外からの参加者も日本語講演を無理なく楽しめるような仕組みになったと思います。
その次に、イギリスのScala Worldにも僕が参加し、CFPの宣伝と口説きを一人ひとりに行いました。このときに話した人たちで何人もCFPに応募してくれましたし、実際来れない人でも他に興味を持ちそうな人を紹介してくれたりしました。
オンラインでも、興味を持ってくれそうな海外のOSSの人たちに、メールやメッセージを飛ばしました。実際に応募してくれて来てくれた人や、自分は参加できないけどMeetupで宣伝してくれたりなど、効果がありました。
最後に、海外から来た参加者を含めた飲みチームを組成して、開催前日や2日目の夜に有志で飲みに行ったりしました。これもカンファレンス外で楽しんでもらう1つの方法だと思っています。
こういった草の根的な努力が実を結び、CFPの競争率としては過去最高の5倍以上、そして海外からの一般参加者を集められ始めています。
セッション募集終了と、投票開始のお知らせ - ScalaMatsuri運営ブログ
日本人が海外参加者の講演を聞く場合、またその逆において、最大の壁は言語だと思います。
昨年まではボランティアベースのテキスト翻訳をA会場のみ提供していましたが、やはり通訳者としては素人のスタッフの提供には限界が有り、今年からA,B会場ではプロフェッショナルによる同時音声通訳を提供しました。
今回のケイワイトレードさんはかなりハイクオリティな翻訳を提供してくれて、好評でした。次回は全会場翻訳を提供できたらと考えています。
その一方で、懇親会の日・英通訳のリソースについてはまだまだ改善の余地があると思います。
私は気づく限りにおいて通訳を買ってでていましたが、やはりリソースとしては全然不足しており、良い方法がないか勘案中です。もしご意見などあればぜひシェアしてください。
1 2 |
|
今回から、多様な背景をもつ参加者が安心して参加できる環境を目指した行動規範の実運用を開始しました。
行動規範については、以前私のものや運営ブログでも紹介しましたので、そちらを参照してください。
ScalaMatsuri 行動規範を掲げた経緯 - OE_uia Tech Blog
「グローバルな技術カンファレンス」と「日本のコミュニティの交流」の両立 - ScalaMatsuri運営ブログ
海外のカンファレンスでは当たり前になってきているとはいえ、日本ではまだまだ行動規範について認知度は高いとは言えない状態でした。
そこで、今回は行動規範の紹介と、それに準じたマナーを啓蒙するための動画を友人のプロのイラストレーターのひなたかほり(@hinatique)さんに依頼して制作しました。動画自体は楽しんでいただけたようでホッとしています。
ただその一方で、3分半程度と短い動画の中に色々詰め込まなければいけないため、かなりの部分を簡略化した、わかりやすさを重視した作りになっているのも事実です。
そのため、幾つか表現上気になる部分については指摘をいただいたりしております。元々は必要に応じて改善を入れることを前提に制作した動画なので、次回以降に向けて反映・改善していきたいと思っています。
また、お気づきかもしれませんが、エンドロール以外はScalaMatsuriという単語が出てきません。
これは、ScalaMatsuriと同じような技術カンファレンスでも使いやすいようにと敢えて排除しています。ScalaMatsuriの行動規範に同意していただいている限りにおいて、ご自由に使ってください。
車輪の再発明はできるだけやめて、Scalaコミュニティに限らず皆が技術的な議論に集中できるようにしたいという思いを込めています。
もしご使用されたら、ぜひ #ScalaMatsuri のハッシュタグをつけてツイートで報告してくださると、とても嬉しいです。
マジョリティの日本人参加者の体験を損なわずに、いかに海外参加者にも楽しんでもらえる仕組みを作るかについて、ご紹介してきました。もちろん、これ以外の仕事も大量にこなしては居ましたが、個人的には今年いちばんチャレンジした部分で、かつ成果に結びついたところなので、思い入れもありまして、知見として共有させてもらいました。
また、この3年間で色々な先輩カンファレンス、特に PyCon JPさんなど、日本で実績のあるカンファレンスの仕組みは色々と真似させていただき、また寺田さんから直接アドバイスを頂戴したりしまして、いつも勉強させて頂いています。本当にありがとうございます。
ようやく3年目にしてScalaMatsuriとしての独自色を出せるようになってきましたので、そこで蓄えた知見を少しでもコミュニティ内外に還元できたらと考えています。その一環としての、このブログ記事という側面もあったりします。
これからも ScalaMatsuriをどうぞよろしくお願いします。
]]>先日はAndroidのBLEにつきまして、記事を書きました。
そこまで怖くないAndroid BLE - OE_uia Tech Blog
今回は、AndroidとiOSがBLE連携する際に気をつけるべき点を挙げたいと思います。
BLE Advertiseには、Advertising Packetと呼ばれる上限31byteのデータをAdvertiseに含めることができます。
このAdvertising Packetは規格化されており、Service UUIDやlocal name、manufacturer dataなどを含めるようにデザインされています。重要な点として、BLE CentralからBLE PeripheralのAdvertising PacketはBLE接続せずに取得することができるので、BLE Scanのフィルタリングに使えます。
例えば、特定のService UUIDをAdvertising Packetに含んでいるBLE PeripheralのみBLE Scanに引っかかるようにすることが出来ます。このUUID指定のBLE Scanは、高速に意中のBLE Advertiseを発見するために非常に効果的です。
…しかし、AndroidとiOSが混在する場合で、なおかつiOSアプリがバックグラウンド状態でもAdvertiseする場合は注意 が必要です。
なぜなら、iOSデバイスからのBLE Advertiseは、アプリがバックグラウンド状態ではAdvertising Packetからlocal nameとUUIDが抜け落ちるという、独特の癖が有ります。(バグかと思ったら、ドキュメント化もされており公式な仕様のようです。)
しかし、他のiOSデバイスからは、この癖については特に意識することなくBLE Scanで見つけることができたりするのです。どうやら、iOS独自の overflow
領域にAdvertising Packetの情報を保存しており、他のiOSアプリからはその overflow
領域も含めてBLE Scan時に参照することができ、結果として今Service UUIDを保存しているのがAdvertising Packetなのか overflow
領域かを意識せずにUUID指定のスキャンができます。
Advertising in background, getting UUID | Apple Developer Forums
しかし、AndroidはこのiOSの overflow
領域を参照することができません。つまり、iOSがBLE Peripheralで、かつAdvertiseしているアプリがバックグラウンドにいってしまった場合、CentralのAndroidからUUID指定のBLE ScanでiOSを見つけることができなくなります 。
すなわち、アプリがBLE Advertiseしたままバックグラウンドに行くことが前提の場合、Central側のAndroidはUUID指定せずにBLE Scan をしなければいけません。その一方で、iOSは気にせずUUID指定してBLE Scanできます。
iOSがBLE Characteristicにデータを書き込む場合、NSDataをコンテナとして使用してバイト列を書き込むと思うのですが、その場合バイト列のorderはリトル・エンディアンです。これはLightBlueなどを使って確認できます。
その一方、Androidのbyte orderは(少なくとも BluetoothGattCharacteristic#getValue
から取得できるバイト列は)ビッグ・エンディアンなので、Characteristicを介してバイト列の受け渡しをする場合は、どこかでbyte orderを反転してあげる必要が有ります。
これについては決めごとの問題でしか無いので、BLE Characteristic上でバイト列を保持するのがビッグ・エンディアンなのか、リトル・エンディアンなのか、仕様としてまず最初に決めておくと良いと思います。
エンディアンについてはこちら。
この記事について、間違いなどあれば@OE_uiaに教えてください。よろしくお願いします。
]]>AndroidのBluetooth Low Energy(BLE)について、どんなイメージをお持ちでしょうか?
安定してない?わかりにくい?
色々と怖いイメージをもたれがちと思います。確かに怖いところも色々とありますが、今ちょうどAndroid BLEをフルに使ったプロダクトBONX -Wearable Walkie-Talkie-を開発しているので、そこで溜まった知見を共有できればと思います。
BLEは、接続する2デバイス間の関係が明確に分かれています。CentralとPeripheralです。
-役割- | -Central- | -Peripheral- |
---|---|---|
動作 | Scan | Advertise |
GATT | Client | Server |
version | 4.3~ | 5.0~ |
まず、以下のpermissionとfeatureが必要になります。
1 2 3 |
|
Android 6.0から、以下のpermission(ACCESS_FINE_LOCATIONでも可)が必要になる上に、更にユーザーに明示的に位置情報使用許可 をもらう必要が有ります(iOSっぽいですね)。
1
|
|
使用許可は、以下のように求めましょう。許可を求めるDialogが表示され、一度許可をもらえば、その後はずっと(端末の設定で明示的にOFFにされない限り)有効です。
1 2 3 4 5 6 7 8 9 10 11 12 |
|
Bluetooth Low Energy startScan on Android 6.0 does not find devices - Stack Overflow
Android 4.3から、BLE Central機能のサポートを開始しました。
Android 4.4以下(API Level 20以下)ではBluetoothAdapter#startLeScan
を使います。
Android 5.0以上(API Level 21以上)では先の旧APIはdeprecatedになっていますので、BluetoothAdapter#getBluetoothLeScanner
からのBluetoothLeScanner#startScan
を使います。
5.0以上のほうが、ScanSettings
や、より細かなScanFilter
を指定できたり、AdvertisePacketの中身を生byte列ではなくScanResult
で取得できたりと、柔軟性高く利用できます。
APIの使いやすさもそうですが、Android 4.3, Android 4.4ではBLE Central機能があまり安定していない(よく接続やRead/Writeに失敗するし、遅い)ので、注意してください。
iOS BLEテスト用アプリといえば、Light Blueがデファクトだと思いますが、AndroidでCentral機能を試すときはBLE Scanner: Read,Write,Notifyです。
BLE CentralのWrite, Read, Notificationといった基礎機能を全て安定して使うことができますので、テストによく使います。
おおよその端末でBLE Scan自体は比較的安定しているのですが、BLE接続、具体的には接続にかかる時間及びRead/Writeの成功率には個体差が大きいです。
接続・切断処理を短時間の間に繰り返すアプリを作る場合は注意してください。
具体的には、BLE接続に失敗する、ないしはRead /Writeに失敗する確率が上がる、などです。
そうなった場合は、まずBluetooth ON/OFFを試して、もしダメなら端末再起動すると直ります。
BLEアプリを作る場合、大抵はクロスプラットフォーム(というかiOSで作っていて、そのAndroid版を作りたい場合)が多いと思います。
その場合は、ENDIANには注意してください。iOSはcharacteristicにはLITTLE ENDIANで読み書きする一方、AndroidはBIG ENDIANです。
BluetoothDevice#getType
がDEVICE_TYPE_DUAL
のデバイスへの接続が頻繁に失敗するstartLeScanで見つかったデバイスに対しても、Classic BTを接続を試みている?っぽいのが原因の模様です。
Dual-mode issue when connecting Android BLE - Google グループ
Android 5.0から、OS上はBLE Peripheralのサポートを開始しました。
しかしながら、何故か現在使われているBluedroidというBluetoothプロトコル・スタックでは、Broadcom製のチップセットのHCIコマンドmultiple advertisement
に依存しており、端末が搭載しているチップセットによってはBLE Peripheral機能が使えません。
bluetooth - Android 5.0でBLE advertising するための要件 - Qiita
BLE Peripheral機能を使えるかどうかは、以下のように判定できますので、チェックしましょう。但し端末がAdvertiseをサポートしていても、BluetoothがOFFになっているとき(BluetoothAdapter#isEnabled
がfalseのとき)は以下もfalse
を返すことに注意してください。
1 2 3 4 5 6 7 |
|
AndroidでBLEのAdvertise modeを使えるかどうかのメモ - Qiita
BLE Peripheral機能が使える端末のリストは、以下が一番まとまっていると思います。
ここにない端末で言えば、Galaxy S6, Zenfone 2 Laser, Galazy S5 Active, Nexus 6PなどはAdvertiseに対応しています。
GattServerの初期化はBluetoothManager#openGattServer
から行います。
Advertiseの開始はBluetoothAdapter#getBluetoothLeAdvertiser
からのBluetoothLeAdvertiser#startAdvertising
を使います。
AdvertiseData.Builder#setIncludeDeviceName
をtrue
にすると、Advertiseが不安定になることがある。不要な場合は、inludeするのをやめましょう。
Android BLE機能についてざくっと紹介しましたが、いかがでしょうか。
色々バグがあったりクセがあったりして確かに扱いにくいとは思いますが、頑張れば対応できるレベルだと思います。
まだまだ開発しながらノウハウを貯めている段階ですので、もし間違いなどあればぜひ@OE_uiaに教えてください。よろしくお願いします。
]]>今日はscala.concurrent.Promise
の話をします。
Promise - Scala Standard Library 2.11.7 - scala.concurrent.Promise
そもそもPromise
って使いどころがわかりにくいですよね。他人のコードで使ってるの、ほとんど見たことがありません。
公式ドキュメントではProducer-Consumerパターンでの使い方を解説していますが、現実にこの使い方が必要になるケースってあまり遭遇せず、たいていの場合はFuture同士のflatMapによる合成で事足りてしまうと思います。
Future と Promise - Scala Documentation
ところが、実はAndroidアプリ開発では頻繁に遭遇するあのパターンが、Promise
を使うと非常に取り回しが良くなりますので、紹介したいと思います。
それは、Intent
で外部Activity
から何かしらの値を取得し、onActivityResult
でその値を受け取るパターンです。
Activity#onActivityResult | Android Developers
Androidでは、アプリ外部との連携をIntent
という仕組みを使って制御しています。
取得したい情報や実行したい処理(Action)をIntent
にセットし、startActivityForResult
メソッドに渡すことで、外部アプリなどを起動し必要なデータを取得させたうえで、自分のアプリに返ってくる(onActivityResult
メソッドが呼ばれ、引数にデータが渡される)ことが出来ます。
このIntent
は大変便利な仕組みですが、その一方で一連のパイプラインの記述がstartActivityForResult
とonActivityResult
の間で分断されてしまい、データの流れが追いにくいコードになっています。
例えば以下のような、ボタンをクリックすると外部アプリで写真を選択させて、自アプリに表示するだけのアプリについて考えてみましょう。
~startActivityForResult |
onActivityResult ~ |
---|---|
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 |
|
これをPromise
を使って書き換えてみましょう。
Promise
によって、startActivityForResult
から onActivityResult
までの流れを、単一Future
インスタンスの中に閉じ込めたかのように扱うことが出来ます。
これでパイプラインの記述をスッキリ書くことが出来るようになりました。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
|
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 |
|
ビルド可能なサンプルソースコードはこちらです。
この例と似た、より一般的な例が以下のPromise
を使ったCallback APIのFuture
化です。
しかしCallback APIのFuture
化はscalaz.concurrent.Task.async
でも実現できますが、上記の例は実現できません(onActivityResult
のせい)。
ScalaFPEvent - ScalaStdFutureExmaple
Promise
って意外と使えるジャン、と思ってもらえれば幸いです。
それでは。
]]>1) implicit class …
2) implicit parameter (e.g. (implicit a:A) )
3) implicit def …
4) implicit (var | val) …
この中で1,2は(明示的に)型を書かざるを得ませんが、3のdefの戻り値、及び4については、型注釈を明示的に書かずに型推論を働かせることが(少なくとも最新の2.11.7でも)可能です。
しかし型注釈を書かなかった場合、以下のような(一見理由の分かりにくい)コンパイルエラーに遭遇する可能性が有ることはご存知でしょうか?
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
|
JIRAにも同種のissueが多数報告されています。
[SI-9130] destructuring binds, implicit resolution, and declaration order - Scala
[SI-5265] warn on implicit def without explicit result type - Scala
この問題を防ぐために、コンパイラチームは暗黙の値やメソッドに型注釈をつけることを強く推奨しています。
Implicits must be explicitly type annotated, otherwise the typechecker may ignore them from preceding parts of the same source file. This is done to avoid triggering spurious cycles in type inference.
暗黙(の値及びメソッド)には明示的に型注釈がつける必要があります。もし型注釈がないと、同じソースファイル上の前方から後方に向かって暗黙を参照している際に、型チェッカーが見落としてしまう恐れがあります。これは型推論をする際に、間違ったサイク ルを引き起こさないために行っています。
- Comment by Jason Zaugg on SI-9130
というわけで、Implicitsには必ず型注釈をつけましょう!
繰り返しscalajp/publicで話題になるし、gitterのログ遡るのつらいしで記事にしてみました(`・ω・')
]]>a tidy SQL-based access library for Scala Developers
(公式ドキュメントより抜粋)
SQL文をそのまま(より型安全な方法で)扱えるのが特長。AndroidでいえばSQLiteDatabase.rawQueryを好んで使う人向け。
今回はAndroidのSQLiteを使用するので、SQLite3に対応していることが必須。あとはPure Java実装か、Android NDKでAndroid用のNative Libraryを生成できる必要がある。
今回使用した、Android Database APIをラップしたJDBC Driver。ただあまり活発にメンテされていないようなので、プロダクションで使用するのは躊躇する。
Android NDKを使用しビルドすることで、Android用のNative Library(.so)を生成できる…が、unmanagedDependenciesとして追加する必要があるので、ちょっと扱いずらい。(なお、この記事を読む限り、Natvie Libraryを含めなくても動作する(=Pure Java実装に自動的に切り替わっている?)模様。)
現在Androidはサポートされておらず、実行すると
java.lang.UnsatisfiedLinkError: dalvik.system.PathClassLoader[DexPathList[[zip file “/system/framework/android.test.runner.jar”, zip file “/data/app/taisukeoe.scalikeroid-1/base.apk”],nativeLibraryDirectories=[/vendor/lib, /system/lib]]] couldn’t find “libsqlitejdbc.so”
というRuntimeエラーとともに落ちる。
Pure Java実装に切り替えるAPIのfeatureリクエストは上がっているようなので、これが実装されれば使えるはず。
serial
データ型が存在しないので、integer autoincrement
にする。timestmap
およびdatetime
データ型が存在せず、timestamp
指定するとyyyy-MM-dd hh:mm:ss
というISO8601フォーマットのTEXT型で保存されるため、WrappedResultSet.jodaDateTimeでDateTime型の値を抽出できない。integer
型にしておいてWrappedResultSet.timestampを使う。DatabseUtils.createDbFromSqlStatements
から手動でDatabaseを作成する必要があるjava.lang.IllegalArgumentException: already added: Lscala/util/parsing/combinator/JavaTokenParsers$class;
これを防ぐために、sbtビルド定義に以下を追加する。
proguardCache in Android += ProguardCache("parser-combinators") % "org.scala-lang.modules" %% "scala-parser-combinators"
ハッカソンではDEMOまでしか作成できなかったが
:power
モードは主眼ではありません。
ScalaのREPLは手元のローカルマシンでAPIを試してみたいときや、ちょっとした計算をしたいときにはとても便利なのですが、やや凝ったことをしたいときなど、そのまま使うには不便さを感じることがあります。
具体的にはAndroidのAPIをScalaのREPLから叩けるようにしたかったのですが、Android環境をJVMでエミュレートするためにはカスタムClassLoaderを使ってAndroid APIのClassを書き換える必要があって。。。という感じ。
これはちょっと特殊なモチベーションかもしれませんが、クラスター上などの特定の環境で実行させたいとき(e.g.spark-shell
)、自作ライブラリのsandbox環境を提供するにあたって特定の場面でよく使うコマンドを追加したい、など思われる方はいるかもしれません。
そんなとき、意外とScala REPLを拡張する記事を書いている人が少なかったので、今回はScalaのソースコードを読みながらカスタムClassLoaderを使用する方法、コマンドを追加する方法について書くことにしました。
参考:Create your custom Scala REPL … 数少ないREPL拡張方法に関する記事。
1 2 3 4 5 6 7 8 9 10 11 |
|
ClassLoaderの差し替え(Classのロード時にクラス名をprint)と、myCommandというコマンドの追加をしています。
Read–Eval–Print Loopの略で、対話型の開発環境。ユーザーの入力したコードを一行から評価する。
ScalaのREPLはscala
コマンドから開始できる。
scala.tools.nsc.interpreter
パッケージがREPLに相当。インタプリタのソースコードがそれなりの量あるので一見大変そうだが、構成自体はシンプル。REPLをカスタマイズする上で最低限見る必要がある場所に絞って、以下では解説します。
scalaのスクリプトの中身を見ると、以下の通りscala.tools.nsc.MainGenericRunner
のmain
関数をエントリポイントとしてREPLを起動していることがわかる。
1 2 3 4 5 6 7 8 9 10 |
|
scala.tools.nsc.MainGenericRunner
のmain
関数の処理は、同コンパニオンクラスのprocess
関数に移譲している。この関数の中で、ILoop
のprocess
関数を呼んでおり、このクラスがREPLのLoopに相当。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
|
参考:scala.tools.nsc.MainGenericRunner.run
scala.tools.nsc.interpreter.ILoop
はREPLのLoopに相当するクラス。コマンドの判定や、入力したコードのインタプリタへの移譲などを行っている。
REPLのコマンド(e.g.:help
)の定義はstandardCommands
変数。overrideしたcommands
関数において追加することでカスタムCommandを実装できる。
また、ILoop
のcreateInterpreter
関数内で、インタプリタのメンバ変数var intp:IMain
を初期化している。
なおインタプリタ intp
の実装クラスはIMain
を継承したILoopInterpreter
。
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 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 |
|
scala.tools.nsc.interpreter.IMain
がインタプリタの主たるコード。
private var _classLoader:ClassLoader
がClassLoaderのメンバ変数だが、privateなのでclassLoader関数をoverrideしてカスタムClassLoaderを生成する。
ただし、IMain
のclassLoader
関数の戻り値の型はscala.reflect.internal.util.AbstractFileClassLoader
になので、カスタムClassLoaderもこれを継承させる必要がある点に注意。
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 |
|
基本的には解説した以下のクラスに相当するものを継承なり自前で作るなりすれば、カスタムREPLが作れます。
scala.tools.nsc.MainGenericRunner
… REPLを起動するmain関数、Loopの呼び出しscala.tools.nsc.interpreter.ILoop
… Loopの実装。Commandの判定。インタプリタへ処理の移譲。scala.tools.nsc.interpreter.IMain
を継承したscala.tools.nsc.interpreter.ILoop.ILoopInterpreter
… インタプリタの実装。ClassLoaderの生成。scala.reflect.internal.util.AbstractFileClassLoader
を継承したカスタムClassLoader … インタプリタに使用させる。先ほども記載しましたが、完成物は以下の通り。試し方はREADME参照のこと。
Apache Sparkのspark-shellは、REPL上で入力したコマンドをcluster上で実行させるために、REPLを拡張している。以下のファイル群がカスタムREPLに相当する。
ScalaMatsuriで発表されたScaliveもREPLを拡張してJVM環境を触れるようにしている。
Scala REPLに備わっている:power
モードを使用すると、Scala REPLコードのpublicな変数・関数へのアクセスが可能で、varなら置き換えも可能。
例えば上記のカスタムClassLoader挿入は、:power
モードを利用してこんな風にも書けます。(ClassLoaderのサイズが膨らんでくるとつらさはありますが)
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 |
|
ただその一方でREPLのコマンドの判別はILoopクラスで行わており、MainGenericRunnerの内部関数中で直接呼び出されているのでPowerModeからのカスタムCommandの追加は不可能なはず(とはいいつつ、何がしかのhackもありそうな気がするのでもしあればコメント欄で教えてください。)
肝心の、オレオレClassLoaderを使ってAndroid APIを叩けるScala REPLアプリは間に合わず。現状でも、未解決のwarningが出る問題とか、タブ補完が効かない問題など、色々と雑な感じにはなっています。。。
そのあたりのフォローはまた後日に(‘・ω・`)
]]>@OE_uia STM is a failure, since removed from Akka.
— Jamie Allen (@jamie_allen) September 28, 20149/28のAkka Meetupで、AkkaでTransaction処理する話題が出たときに、こんなことをつぶやいたら、Effective Akka著者の@jamie_allenさんに「それはもうオワコンだよ」と教えていただいた(確かに調べてみると、Akka 2.3でdeprecated)ので記事化してみる。
Akka Transactors 公式ドキュメントより抜粋,翻訳。
Generally, the STM is not needed very often when working with Akka. Some use-cases (that we can think of) are:
- When you really need composable message flows across many actors updating their internal local state but need them to do that atomically in one big transaction. Might not be often but when you do need this then you are screwed without it.
- When you want to share a datastructure across actors.
一般的に、Akkaを使用しているときにSTMは殆どの場合必要ないけれども、(我々の考えている)ユースケースが幾つかある:
- 多数のアクター間の内部のローカルな状態を一つの大きなトランザクション内でアトミックに変更する為に合成可能なメッセージフローが必要なとき。こういうケースは余り頻繁にはないが、必要になったときTransactorsがないととても困るはずだ。
- データ構造をアクター間で共有したいとき
「Transactorsが無いととても困るはずだ」と書いておきながら、なんで削除されたのか気になったので聞いてみた。
Effective AkkaのCameo Patternという項で、short-lived actorで複数のActorのをコーディネートする例が書かれているのでご参考までに(でもコーディネートするところだけで、トランザクションに相当するコードはない)。
]]>
この行動規範について、突然Webサイトに追加されたので驚かれた方も多いかもしれない。この行動規範は、現実に発生しそうになった問題から、必要要件を考え、準備委員内で長期間に渡り議論を重ねた上で公開したものだ。
既にその目的については@eed3si9n_jaさんがカンファレンスでのユニバーサル・アクセスへ向けてという記事でまとめてくださっているが、来年から本格的に運用するにあたり、この行動規範を掲げた経緯も含めて紹介することが、ご理解とご協力をいただく上では重要ではないかと考えているため、この記事を書くに至った。
この記事では、行動規範が生まれた経緯を3つの側面から説明していきたい。
そもそもこういった注意喚起が必要だと考えた理由は、欧米圏のカンファレンスでハラスメント・フリーな行動規範を掲げる潮流があったこと、また他のカンファレンスなどで実際にトラブルに発展した事が発端だ。特に、ScalaMatsuriも現時点の参加者の大部分が日本人男性と偏った集団なので、同様のトラブルが起きるリスクを無視できない。こういった事故からScalaMatsuriに関わる人全員を守るために、何らかの注意喚起やガイドラインが必要であるという認識は、特に議論もなく準備委員会内でも共有できていたと思う。
実際今年のScalaMatsuriでも、運営内で議論が大きく別れたコンテンツがあった。なぜなら、(比較的"性"におおらかな)日本のイベントでは一般的なものでも、アメリカ東西海岸を中心としたScalaの国際カンファレンス(e.g. NEScala,PNWScala,ScalaDays)など、一部の海外カンファレンスでは望ましくないとされるものが少なくないからだ。
ScalaMatsuriとしての方針が明確でないままでは、トラブルに発展した際に対応が遅れて参加者・発表者・招待講演者・スポンサー全員に迷惑をかけてしまう恐れがある。ここで、どういった思想方針でScalaMatsuriで運営するのか明文化する必要が生まれた。
実運用、公平性、リソース確保などの現実的制約について議論を重ねた結果、以下のような必要要件に至った。
これらを満たすものとして、実績のあるPNWScala, NE ScalaやScalaDaysといったScalaの国際カンファレンスの行動規範を思想方針として全面的に採用することに決めた。
ScalaMatsuri発起の理由として海外コミュニティとの交流をうたっていること、直近では招待講演者やスポンサーとして、将来的には一般参加者として、先に挙げたカンファレンスに参加している層がScalaMatsuriに来ても居心地の悪い思いをしなくて済むような準備を整えるために、国際カンファレンスに追随した形だ。
これらのカンファレンスに限らず、日本国内でいえばRubyKaigiでもAnti-harassment-policyについて明示している通り、国際的なカンファレンスを視野に入れるためには、同様のガイドラインを掲げることは避けては通れないものだと考えている。但し、細部については実運用や時代の移り変わりに伴い、加筆修正される可能性はある。
今年のScalaMatsuri 2014では、行動規範の議論に時間を費やした結果、公開が直前となってしまった為、実運用は見送った形となった。ただ来年から運用を開始するにあたり、まだ幾つかの課題は残っている。例えば:
それぞれについて、まだ議論は続いているものの、どのようにクリアできる可能性があるかについて紹介していきたい。
審判制度での運用を検討している。具体的には、3人〜5人程度の審判の間で議論して最終的な判断を下すが、その際に、過去の代表事例との間に大きな矛盾が生じないかチェックをするというものだ。
確かに、幾ばくかのトレードオフがあることは事実だと思う。
しかしながら、ScalaMatsuri 2014のアンカンファレンスの異様な盛り上がりを経験した今振り返ってみると、行動規範を遵守したままでもイベントを盛り上げることは不可能ではないと思える。また代表的な事例をオープンにすることで、自主規制の参考にしていただけることを期待している。
行動規範は、ScalaMatsuriのコアである海外コミュニティとの交流を実現する上でも、ScalaMatsuriに関わる全ての人をトラブルから守る上でも無くてはならないものだと考えている。ScalaMatsuriを一緒にハラスメント・フリーなイベントするべく、ご理解とご協力を賜われれば幸いである。
最後に、この記事をレビューしてくださった@eed3si9n_jaさん、@gakuzzzzさん、@kmizuさん、@seratch_jaさん、@xuwei-kさんに感謝します。
]]>9/6,7の2日間、ScalaMatsuri 2014という日本最大(おそらくAsiaでも最大?)のScalaのカンファンレンスを開催し、総来場者数が400人強、ニコ生視聴者14万人超、昨年に引き続き#ScalaMatsuriがTwitterトレンド入りと、盛会のうちに幕を閉じました。 ご来場者、スポンサー企業、ニコ生視聴者、スタッフの皆様、本当にありがとうございました。
今回は、主にOMOTE / 表側の紹介です。写真なども後日この記事に追加予定。裏側紹介はアンケートデータの整理などが終わり次第、また書きます。
Scala作者のMartin Odersky教授 @oderskyによる、Pizza, FunnelといったScalaの前身の言語の紹介からDot計算の話まで含めた、Scalaの歴史と展望の紹介。Scalaが生まれてからの時間が、ちゃんとScalaMatsuriの日に合わせてあるという凝りっぷり、とは@qtamakiさんの談。
ScalaはPizzaで作られていた?という@xuwei_kさんの記事もご覧になると、より楽しめるかも。
sbtコミッタで、最近はほぼ一人?でsbtのコードを書いているEugene Yokota氏 @eed3si9n_jaのセッション。昨年のカンファレンスから、ずっと翻訳チームリーダーとしても活躍されています。
今回はmkdirから始まるライブコーディングや、sbt server, Auto Plugins, Consolidated resolutionといった新機能の紹介まで盛りだくさんなセッション。
Cake Patternの名付け親でもあるJon Pretty氏 @propensiveによるセッション。Rapture I/Oの1行コードを、50個一気に紹介するという構成でした。1行でパワフルなI/O操作ができるRapture I/Oの魅せ方として、大変上手いなと感心していました。 HTTPやFileのI/Oも簡単で魅力的ですが、JSON周り、特にString InterporlationでExtractor作れるあたりはすごく面白いなと。
1 2 3 |
|
また2日目のアンカンファレンスではRapture I/OのWorkshopも開催してくださいました。海外からJon Prettyさんのような方がもっと来やすくなるような仕組みを作って行きたい。
LinkedInでPlayチームのリーダーを務めていたYevgeniy(Jim) Brikman氏。 LinkedIn内で行っているWeb Framework比較結果の、一番良いところだけ見せていただいているという大変贅沢なセッション。網羅的で内容も大変参考になりますし、翻訳に先んじて日本人聴衆の笑いをかっさらっていく話の上手さ。後述しますが色んな意味でイケメン。
あと築地の寿司が大変美味しかったそうで、感激されていました。
Best sushi I've ever had. Really, one of the best meals I've ever had. pic.twitter.com/04Db2O1PMe
— Yevgeniy Brikman (@brikis98) September 4, 2014
@jamie_allen All I can say is Tokyo is a good place for a Scala conference :) http://t.co/sTwdrPaUpE
— Yevgeniy Brikman (@brikis98) September 4, 2014
Apache SparkコミッタのAaron Davidson氏による、Sparkの解説とLive Demo。
実はこのとき直前の映像関係のトラブルでAaron Davidson氏のPCがプロジェクタに映らず、急遽私のPCで発表からLive Demoまでやる(しかもハイクオリティ)という離れ業をやってのけました。昨年のJames Roper氏のデモといい、どうもScalaMatsuriのゲストはLive Demoが抜群に上手い傾向にあるようです。でもJISキーボードはだいぶ苦戦されてました。プレゼン中、私が隣に座って「"_“はどこ?」「ここだよ」みたいなことをずっとやっていたり。
皆さんの声を聞いていると、Databricks Cloudのvisualization機能に驚いた方も多かったようです。このサービスは現在closedβで、価格は未定なもののフリーミアムモデルを検討されているとか。
Twitter Inc.にお務めの丹羽さん @niwさんが、はるばる日本までいらしてくださいました。
バルス! => TPS(tweets per second)がやばい => じゃあどうやって測るの?
という風に、ネタスライドからScalding,Storm,Summingbirdに繋げる話の上手さ。
あと@xuwei_kさんがこんなことを仰ってるぐらい、講演以外のトークも面白かったです。ありがとうございました。
みんな小田好先生に会って話聞いて、感動などあったと思うし運営側の1人としてはそういう体験をしてもらうために頑張ったのもあるのでよかったのだけど、 個人としては小田好先生の発表内容の大半は既にネットで見れるものだしそれよりtwitterの中の人と直接話して色々聞けたのが一番よかった
— Kenji Yoshida (@xuwei_k) September 7, 2014
あと、SwiftとScalaの話は何かの機会にぜひ聞きたい(やりたい)です。Swiftで、Scalaのパターンマッチの文法を実装する話とか楽しい。
SAT型制約プログラミングシステムScarabのお話。ドキュメントはこちらにまとまっています。
私は不勉強ゆえ内容をよく理解できなかったのですが、どうやらsbt内でもSATを利用しているらしく、sbtコミッタのYokotaさんと熱く語ってらっしゃるのを隣でみていました。
宋さんのようなアカデミアにいらっしゃる方が、ScalaMatsuriのCFPに応募してくださって嬉しいですし、アカデミアの方が市井のScalaのコアな開発者と出会う機会をもっと作りたい。
実は、この前日の9/5がOdersky教授の56歳の誕生日。というわけで、サプライズで歌ってケーキをプレゼントしました。すごく喜んでいただけて良かった。
このアイディアをあの忙しい中考えついた@takezoux2さんの幹事力の高さが半端ない。
In some part of the world it is still @odersky's birthday, so he gets a cake! #ScalaMatsuri pic.twitter.com/cLal8xODiG
— Jon Pretty (@propensive) September 6, 2014
アンカンファレンスは、参加者がその場で聞きたいセッション、話したいセッションのアイディアを出し合いながら、その場で作って行くイベントです。今回初の試みでしたが、大いに盛り上がり、本当に良かった(内心結構心配でした)。。。
@j5ik2oさんによる、DDD(Diet Domain Driven Design)の解説。比喩から具体例まで、とても分かりやすく大変好評でした。
@xuwei_kさんによる、Akkaの初心者向けセッション。 そういえばTypesafe社のAkkaコミッタが今月日本にいらっしゃるので、Akka Meetupがドワンゴさんで9/28に開催されるとか。
最近転職した人の話を聞いた後、今すぐ転職したい人!と@kirisさんが聞いたら、数十人が一気に手をあげて大いに盛り上がり、運営側が逆に驚くくらいでした(@kirisさん、ナイス!)。ScalaMatsuri 2014が縁となって転職した方、ブログ待ってます!
是非よろしくお願いします。転職に限らず、 #ScalaMatsuri がきっかけでScalaを導入できた、PullReq送りはじめたなど、なにか変化があった方は教えてください! RT: @numa08 ScalaMatsuriで転職しましたエントリーが求められてる?
— scala_jp (@scala_jp) September 9, 2014
Odersky教授によるセッション2個目。一時期Twitterでも話題になった、CanBuildFromの話を直接聞けたのが私としては良かった。
Odersky教授を始めとしたゲストに、マサカリを直接投げてもらえるセッション。 ランチでぽろっと出たアイディアなのですが、Odersky教授が超乗り気で非常に盛り上がりました。
フィードバックの抜粋
1 2 3 4 5 |
|
より
1 2 3 4 |
|
1
|
|
より
1
|
|
という風に英語風に書いた方がScalaっぽいと言われる(去年のJoshua Suereth氏のセッションなど参照)けど、最近はOdersky教授自身はその判断に迷う事が多くなったそう。実際最近Odersky教授のも、ドットと括弧を付けて書いたりしているらしい。
但し
1
|
|
みたいなのはダメ。ドットと括弧を使った方が確実に見やすい、との談。
そして実はこのセッション、ゲストのYevgeniy Brikman氏によるアイディア。でもそれを紹介しようとしたら「自分のアイディアだっていうとバイアスがかかるから」といって固辞されたりで、本当にイケメン。
One of the highlights of #ScalaMatsuri: code review session w/ Martin @odersky. Great way to learn. I hope other conferences follow suit.
— Yevgeniy Brikman (@brikis98) September 8, 2014
ScalaMatsuri発のセッションとして、世界に広まってくれると嬉しいですね。
大変盛り上がっていたようですが、他の仕事をしていて聞けなかった(‘;ω;`)ブワッ ので@okapieさんのtogetterのこのへんをご参照ください。
昨年に比べて発表内容が非常に幅広くなり、日本でScalaの普及が進んでいる事をまざまざと感じさせるイベントとなりました。また予想を上回る数のスポンサー企業さまにお申し込みをいただきまして、逆にスポンサーLT枠が枯渇するというほどの盛況ぶりでした。特典枯渇のためお断りしてしまったスポンサー企業のみなさま、大変申し訳ありませんでした。もしよろしければ、また次回お声がけください。
あと、海外ゲストや一般参加者、スポンサー企業の多くの方から、日本のScalaコミュティが熱い & 勢いありますね!というお声を沢山、本当に沢山かけていただき、イベント運営を担っている身としては非常に嬉しく感じております。皆さんのお陰です。これからも一緒に盛り上げて行きましょう!
その一方で、初心者向けセッションが手薄になってしまったのは反省点。翻訳が足りない、という声も真摯に受け止めており、来年は同時音声通訳の導入を真剣に検討しております。その辺りはまた次回のエントリにて。
]]>が、このREADMEの通りにプロジェクトを作るのが面倒なので、giter8テンプレートも作ってみました。
1
|
|
からプロジェクトの雛形が作れます。 giter8が入っていない人はbrew install giter8とかで。
こんな感じです。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
|
簡単な説明。
local.properties, project.propertiesを修正したときは、ちゃんとsbt reloadしましょう。
proguard-project.textを修正したときは、sbt reload cleanしてclassファイルのキャッシュを消しましょう。
1 2 |
|
1 2 |
|
ちなみにScalaTestやspec2を入れようとすると、ScalaTestはサイズが大きすぎてmethod数64k問題に引っかかり端末にインストールできず、spec2は実行時にDalvikVMのOutOfMemoryErrorを引きおこしてしまいます。
まあ結局、端末上で行うテストはAndroidInstrumentationTestCase2とかを継承せざるをえませんし、Scalaで書けるだけ良しとしましょう。
]]>なぜか。
2013年6月にScalaでAndroidアプリを作るにはという記事を書いたのですが、その後Android SDKのディレクトリ構造が(r22〜?)変わったものの、記事中で使用していたjberkel/android-pluginがその変更に追従しておらず、Could not find tool “aapt”エラーが出てビルドできない問題が発生しています。
参考のSO記事はこちら。mavenのpluginの話ですが同じ問題。
また思い出したら上に書き足します。
あと、AndroidアプリをScalaで書くと、以下の問題にぶつかりやすくなります(DalvikVM自身の問題も多分に含まれるのですが)。
ちなみにLinearAlloc問題が起きるのは基本的にAndroid2.3以下だし、DalvikVMに代わるARTがAndroid4.4から試験導入されているので、時間とともに改善するという説もあります。
]]>LinkedInのブログで、EclipseベースのScalaによるAndroidアプリ開発環境が紹介されてました。(と、 @okapiesさんに教えていただきました。ありがとうございます。)
The technology behind EatIn: Android apps in Scala, iOS apps, and Play Framework web services
うちのAndroid Scala開発環境はIntelliJ IDEA + sbtなので、折角なのでこんな風にも出来ますよと紹介してみます。本当はLinkedInブログに対抗して (sorry eclipse users!!) って書きたかったw のですが、IntelliJはエディタとして使ってるだけなので、Eclipseに変えても大して支障ないです。というわけでお好きな方をどぞ。
Androidに馴染みが無い方にも、Scalaに馴染みが無い方にも試してもらえるよう、クドいぐらいに丁寧に書いてますので、慣れ親しんだ部分は読み飛ばしてください。
また、「もっとこうした方がいいんじゃない?」みたいな突っ込みは大歓迎です。
以下コマンド例はMac/Linux用なので、Windowsの方はお好きな方法で適宜書き換えてください。
強力なリファクタリングと、Android UI Designer機能が便利なIDE。
IntelliJ IDEA — The Best Java and Polyglot IDE
幸いなことに、IntelliJ IDEAのCommunity Edition(無料版)でもScalaとAndroidのサポートを使えます。 インストールしたら、以下の手順でScalaのPluginを入れましょう。
Configure => Plugins => Browse repositories
プラグインの一覧からscalaを右クリック => Download & Install
ちなみにsbtコンソールをIntelliJに追加するプラグインもありますが、このコンソールはTab補完が効かないので、コマンドが長めなandroid-pluginには不向き。Terminal経由でsbtコマンドを叩いた方が無難です。
Android APIのjarが含まれているほか、ビルドやデバッグに使用する各種便利ツールが入ってます。アップデートの度にちょこちょこ構成が変わるので、各種サードパーティ製のツールとの互換性がなくなったりします。なので新しいバージョンが出ても1個前のバージョンは消さずに、シンボリックリンクの切り替えで対応しとくと良いです。
Android SDK | Android Developers
IntelliJ IDEAを使う場合は、ADT BundleではなくUSE AN EXISITING IDEからSDK単体をDLます。ADT Bundleでも特に問題はないですが、余計な物(Eclipse+ADT)が入ってます。
その後、SDK環境変数ANDROID_HOMEとtools, platform-toolsのディレクトリにPATHを通します。
1 2 3 4 5 |
|
ちなみに上記SDKには最新版のAndroid versionのlibraryしか含まれていないので、回線に余裕があるときに、以下のコマンドでAndroid SDK Manager(GUI)を起動し、各versionのlibraryを落としておくと良いです。
1
|
|
なおSDKにAndroidエミュレーター作成用ツールも含まれていますが、起動と各種動作が重い上に、エミュレーターで試せない機能が多い(カメラなど各種ハードウェア、GCMを使用したpush通知、アプリ内課金)など、不便極まりないので実機でデバッグする方が無難です。 どうしても作りたい(特定のマイナーな解像度での見え方をチェックしたい、など)場合は、以下を参考にどうぞ。
Emulator - Android エミュレータ - ソフトウェア技術ドキュメントを勝手に翻訳
Githubのリポジトリに登録しておいたテンプレートからプロジェクトを生成するツール。Androidアプリのプロジェクトは色々構成がややこしいので、giter8経由で作成するのがオヌヌメです。
1
|
|
Scala本体。まだ入れていなければ。
1
|
|
Scalaプロジェクトのビルドによく使われるビルドツール。まだ入れていなければ。
1
|
|
giter8を使って作成します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
|
各変数の解説
作成したプロジェクトをIntelliJ IDEAで開くとこんな感じ。なおsbt pluginはjberkel/android-plugin及びmpeltonen/sbt-ideaを使用しています。
sbtのビルド定義ファイル(project/build.scala)でAndroid versionを変えたりライブラリ依存性を変更した場合は、忘れずにリロードして再度idea設定ファイルを生成します。でないとIntelliJの補完が効かなくなります。
1 2 3 |
|
USBデバッグモードをONにしたAndroid端末を接続しておくと、以下のコマンドでビルド及びデプロイが実行できます。
1 2 |
|
ビルドした実行ファイルはtarget/
なおAndroidプロジェクトのビルドには時間がかかりすぎる(MBP Retinaで30秒以上…)ので、コード書いてる最中は自動コンパイルだけにしておく方が無難です。
1 2 |
|
Androidアプリのテストは、Android上で行う必要がないもの(ex. Modelやユーティリティークラスの単体テスト)と、Android上で行う必要があるもの(ex. Activity(画面)やViewに関するテスト)の二通りがあり、実行方法も違います。
Android上では行う必要のないテストは、src/test/以下に書いて、以下の通りテストを実行。
1 2 |
|
Android上で行う必要のあるテストは、サブプロジェクトとして別途ビルド&デプロイします。ここまで記載した手順通りで作成している場合には、tests/src/main/以下にテストコードを書く形になります。実行コマンドはこんな感じです。
1 2 3 4 |
|
余談ですが、jberkel/android-pluginのTypedResourcesを利用したプロジェクトのテストをAndroid上で実行すると、IllegalAccessErrorで失敗するようです。TypedResourcesはただのユーティリティー的なtraitなので、使わなくても支障は特にありません。
主にAndroidSDK同梱のAndroid Device Monitorを使います。
Logの確認の他、Thread, Heapなどの状態をチェックしたり、スクリーンショットを撮ったり、hprofとったり割と便利です。
1
|
|
その他、よく使うandroid-pluginのsbtコマンド一覧
android:package-debug … プロジェクトをビルド。
android:prepare-market … プロジェクトをビルドし、指定した署名ファイル(<HOGE>.keystore)で署名。GooglePlayへのアップロード時に使用する。
android:install-device … プロジェクトをビルド、USB経由でAndroid端末にインストール
android:start-device … プロジェクトをビルド、USB経由でAndroid端末にインストール、アプリ実行
android:uninstall-device … USB経由でAndroid端末からアンインストール
android:test-device … USB経由でAndroid端末上でテストを実施。前もってテスト用apkをインストールする必要あり。
android:screenshot-device …USB経由でAndroid端末のスクリーンショットを撮影
# emulatorの場合は、上記コマンドのdeviceをemulatorに変えてください。
Wikiにも色々書かれていますので、一読しておくと良いかもです。
上記手順だけでも使えないことは無いですが、IntelliJ IDEAのAndroid UI Designer機能を使うためにはもう少し設定が必要です。ちなみに先日のGoogle I/Oで発表されたAndroid Studioのメイン機能も、このAndroid UI Designerを下敷きにしているぐらい強力だったりするので、折角IntelliJを使うのであれば、ぜひここまで設定しましょう!
以下、IntelliJ IDEAでプロジェクトを開いた後に行います。
File => Project Structure => Modules =>
メインプロジェクトを選択して Add => Android
追加した"Android"を選択し、Manifest file/ Resources directory/ Assets directoryのパス中の".idea_modules"を全て"src/main"に変更します。Native libs directoryは".idea_modules"を削除しましょう。下記スクリーンショットのような感じです。
続いてAndroid SDKのパスを追加します。
File => Project Structure => Platform Settings => SDKs =>
上の"+"ボタン => Android SDK => $ANDROID_HOME/platforms/android-17 を選択
File => Project Structure => Modules => メインプロジェクトのModule SDK => 今追加したAndroid SDKを選択。
以上を終えた後、src/main/res/layout/main.xmlを開くと、自動でAndroid UI Designer機能が立ち上がります。もちろん画面下タブのTextを選択すれば、xmlを直接編集できます。Previewを見ながらxmlを編集するだけでも便利です。
かなり丁寧に書いたので長くなってしまいましたが、突っ込みor質問orコメントなどあれば下記コメント欄か@OE_uiaまでお願いします。
]]>Google I/O 2013 初日(日本時間5/16 1:00)にて発表されました。IntelliJ IDEAベースのAndroidに特化したオープンソースのIDEだそうです。
そのほかの、Google I/O関連のまとめはこちら。Galaxy S4のNexus化モデルの販売やら、Google Mapの強化、PlatformとしてのChrome、GmailとGoogle Walletの統合など、他にも盛りだくさんな発表がありました。
これら発表を受けて、Googleの株価は過去1年間で最高の915ドルまで急騰した模様。
Google、Android向け統合開発環境「Android Studio」を発表 - ITmedia Mobile
Google I/O 2013 開幕、初日キーノート速報 - Engadget Japanese
【速報】 Google I/O 2013キーノート講演まとめ #io13-ノート|U-NOTE【ユーノート】-イベントまとめプラットフォーム
Google株、Google I/O初日に52週最高の915ドルで引ける。Apple再び下げる | TechCrunch Japan
もうWindows/Mac/Linux版が公開されています。ただしv0.1のearly access previewなので、productionには使わない方が良いとのこと。
Getting Started with Android Studio | Android Developers
(5/16追記) Macの場合、/Applications ディレクトリにコピーしないとエラーが出る模様。情報ありがとうございます!
インストールが完了して起動すると、IntelliJ IDEAっぽいスプラッシュ画面。
生成されるプロジェクトはこんな感じ。
ビルドはGradleなんですねー。Gradle Wrapperつき。
build.gradle
settings.gradle
gradlew
gradlew.bat
そしてIDEの設定ファイルは、IntelliJ IDEAと似たような構成みたい。
.idea/
<HOGEHOGE>.iml
Androidアプリ開発者のために、複数のディスプレイサイズでのレイアウトをプレビューできるレイアウトエディタ<中略>が用意されている
とのことなので、早速チェックしてみることに。どうやらIntelliJ IDEAのAndroid UI Designerをベースにしつつ、機能追加/画面の修正をしてPaletteという名前に変更したようです。
なんと、レイアウトファイルの各解像度での見え方のプレビューを一覧表示できる!!
これは便利すぎる…
…Android Studioのエラーの報告先がJetBrains(IntellIJ開発元)になってるのは、すごく迷惑だと思うけどw
Scala 2.10以上でAndroid4.1以上のライブラリと一緒にコンパイルしたプロジェクトを、Android4.0以下の端末で動作させるとNoSuchMethodErrorがthrowされます。原因はScala2.10.x系のコンパイラの不具合。親クラスで実装されたメソッドをそのまま継承した場合、2.9.x及びJavaではメソッドのqualifying typeの参照が子クラスになるのに対し、2.10.xではqualifying typeの参照が親クラスになってしまうことが直接の原因です。
詳しくは第99回rpscalaで発表したスライドをどうぞ。
このバグと同種のものがJIRAでも見つからなかったので、issue報告を上げた結果、3/23に無事修正されたようです。
rpscalaでの発表時によくわからなかった以下のポイントがクリアになったので、フォローアップとして記載しておきます。
特段意図されたものではなく、Scala2.10でコンパイラをfjbgからasmへ変更した際に、紛れ込んだ模様です。 (該当commitのauthorのPaul Phillipsさんが"I don’t think this is asm’s doing, but not sure of that either.(ASMのせいじゃないように思うけど、どうだか分からないな。)“と発言している。)
Fix for erroneous bytecode generation. · 0bea2ab · scala/scala
バグのようです。根拠として引用された、Java Language Specification(以下JLS)内のBinary Compatibilityに関する記述は以下の通り。
“Moving a method upward in the class hierarchy.”(メソッドがクラス構成の上流に移動することについては、バイナリ互換性を保たなければいけない)"
“A reference to a method must be resolved at compile time to a symbolic reference to the erasure (§4.6) of the qualifying type of the invocation, plus the erasure of the signature of the method (§8.4.2).”(メソッド又はコンストラクタへの参照は,そのqualifying typeへの記号参照に,そのメソッド又はコンストラクタのシグネチャを加えて,コンパイル時に解決しなければならない。)
If the expression is of the form Primary.f then:
If the compile-time type of Primary is an intersection type (§4.9) V1 & … & Vn, then the qualifying type of the reference is V1.
Otherwise, the compile-time type of Primary is the qualifying type of the reference."
(Pimary.fという表現があったとき、Primaryがintersectional type以外の場合、Primaryがqualifying typeとなる。)
それに対して、以下のような反論がありました(が、反論の発言主が"You got me, it’s a bug.“(やっぱりあれはバグだったよ。)と訂正済み。)
そもそもScalaがJLSに準拠すると明確に宣言しているソースを見つけられなかったのが個人的には気になっていましたが、そこは争点になりませんでした。 (注:というのも、以前Scala作者のMartin Odersky教授が別のissue [#SI-1806] Can’t access protected static inner classes of extended classes)] で “I disagree. We can never achieve 100% java interop without becoming Java.”(私は反対だ。Javaとの相互運用を100%達成するには、Java自体になる他ない。)と発言していたので。) とはいえ、僕が見落としているだけのような気がするので、もしその辺りご存知の方がいたら教えてください。
3/23に、本バグ修正のpull request(SI-7253: respect binary compatibility constraints by Blaisorblade)がmergeされましたので、おそらく2.10.2で反映されるものと思われます。
ここに関して、2.10系のbinary compatibilityを破壊するから2.11まではXfutureオプションに入れておくべきでは?という議論がありましたが、James Iryさん(Java to Scala with the Help of Experts | The Scala Programming Languageなどを書いてる方)の意見が通ったようです。
This patch will improve binary compatibility when source changes in the way that happened in SI-7253. That improvement won’t be available in prior 2.10.x versions so in that sense this commit is a change in behavior. But since the old behavior was to create a linkage error I’m okay with that change.
(このパッチは、SI-7253のようなソースコードの変更において、バイナリ互換性を改善します。以前の2.10.x versionでは使用不可能という意味で、このパッチはバイナリの振る舞いを変更しますが、以前の振る舞いがリンクエラーを生成してしまう以上、私はこの変更を適用しても構わないと思います。)
2.10.2がリリースされるまでは繰り返しになりますが、以下のような構成のプロジェクトは予期せぬNoSuchMethodErrorをruntimeでthrowするため、避けるべきです。
Android platform version 16以上 (4.1以上に相当)
Android minSDKversion 15以下 (4.0以下に相当)
scalaVersion 2.10.x
@jsuerethに褒められたヽ(・∀・)ノ ワーイ
@OE_uia wow, very good catch. Too much about BC in Java is non-intuitive, this example being one.
— Josh Suereth (@jsuereth) March 15, 2013
バグの再現手順。
再現用のrepositoryはこちら。 taisukeoe/scala_2_10_android_error · GitHub
Android platform version 16以上 (4.1以上に相当)
Android minSDKversion 15以下 (4.0以下に相当)
scalaVersion 2.10.x
で以下のようなソースコードのプロジェクトを実行すると、NoSuchMethodErrorがthrowされます。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
|
W/dalvikvm(7951): threadid=1: thread exiting with uncaught exception (group=0x40abd210)
E/AndroidRuntime(7951): FATAL EXCEPTION: main
E/AndroidRuntime(7951): java.lang.NoSuchMethodError: android.database.sqlite.SQLiteClosable.close
E/AndroidRuntime(7951): at com.hemplant.demo.no_such_method_in_2_10.DemoActivity.onCreate(DemoActivity.scala:18)
E/AndroidRuntime(7951): at android.app.Activity.performCreate(Activity.java:4465)
E/AndroidRuntime(7951): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1049)
E/AndroidRuntime(7951): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1931)
E/AndroidRuntime(7951): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:1992)
E/AndroidRuntime(7951): at android.app.ActivityThread.access$600(ActivityThread.java:127)
E/AndroidRuntime(7951): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1158)
E/AndroidRuntime(7951): at android.os.Handler.dispatchMessage(Handler.java:99)
E/AndroidRuntime(7951): at android.os.Looper.loop(Looper.java:137)
E/AndroidRuntime(7951): at android.app.ActivityThread.main(ActivityThread.java:4441)
E/AndroidRuntime(7951): at java.lang.reflect.Method.invokeNative(Native Method)
E/AndroidRuntime(7951): at java.lang.reflect.Method.invoke(Method.java:511)
E/AndroidRuntime(7951): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:823)
E/AndroidRuntime(7951): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:590)
E/AndroidRuntime(7951): at dalvik.system.NativeStart.main(Native Method)
]]>生物学の各領域(遺伝子、転写産物、タンパク質…etc)を総体(ome)として理解する学問(ics)。
元々大学ではin vitroな実験系分子生物学の研究室に3年間在籍していたものの、今はプログラミングばっかりやっているので、バイオインフォマティクス(情報生物学)はピッタリじゃないかなーとか。半分は完全に趣味ですが。
今はMicroArrayや質量分析機などの発展により、研究のボトルネックがデータ収集速度ではなく解析速度に来ている。これにより実験系の研究者にとっても、バイオインフォマティクスの重要性が上がっている。
データ解析には元々Fortranを使っていた研究室が多いものの、今はR言語が主流。対応解析(CorrespondenceAnalysys)用ライブラリのFactoMineRやネットワーク解析向けにigraphなどのライブラリの紹介もあった。
参考: R seminar on igraph - supplementary information - Kazuhiro Takemoto
ネットワーク解析は、社会学やSNSだけでなく、生物学にも利用されている(Network Biology)。Network Biologyの例として、タンパク質の相互作用ネットワークを次数中心性(ネットワーク上でのハブとしての枝数の多さに応じて重み付け)に基づいて解析した結果、次数中心性の高いタンパク質ほど進化の速度(ここでは変異の入る速度)が遅いことが分かりNatureに掲載。
気象学でよく使われる「データ同化」という手法の紹介。観測値と数理モデルから、パラメータの推定やノイズ除去を行うためのもの。有名どころはカルマンフィルタ(1960年代に月探査船の軌道計算に使用)や粒子フィルタなど。
ちなみに、データ同化におけるポリシーは「使えるものは何でも入れろ」。ErlangやScalaのActorモデルのポリシー"Let it crash (クラッシュさせろ)“もそうだけど、こういう雑で実践的なポリシーは大好きwww
現在集まっている大量のゲノミクス情報の再利用性を高めるために、遺伝子の役割に応じて注釈(遺伝子アノテーション)が付けられている。有名どころはGO(遺伝子オントロジー)とMeSH(Medical Subject Headings)。 MeSHの方が語彙が倍以上あり、グルーピングもずっと多いが、GOにあるけどMeSHに無い語彙などもあるので用途に応じて使い分けるべきとのこと。
バイオの知識だけじゃなく、統計学(とR)の知識が重要な模様。こういう複合領域の戦場にはどんどん攻め入りたいですね。
]]>