Kotlin で HelloWorld(コマンドライン編)
さて前回に続いて、今度はコマンドラインで Kotlin のHelloWorldをやってみたいと思います。
公式ドキュメントのチュートリアルを見ながら進めていきます.
インストール
まずは念のため既にインストールされていないか確認します。
$ kotlinc
zsh: command not found: kotlinc
IntelliJ IDEA で自動でインストールされてはいないようですね。
SDKMAN! のインストール
brewでインストールするのが手っ取り早いかと思ったのですが、 SDKMAN!という複数バージョンを共存させられるrbenvと似たようなツールがあるようです。
しかもKotlin以外の言語にも対応しているとのことで今後も使えそうなので、これを使ってインストールしてみます。
$ curl -s https://get.sdkman.io | bash ... All done! Please open a new terminal, or run the following in the existing one: source "/Users/yusuke/.sdkman/bin/sdkman-init.sh" Then issue the following command: sdk help Enjoy!!!
以下のコマンドを実行して有効にします。
$ source "/Users/yusuke/.sdkman/bin/sdkman-init.sh"
sdk help
と試しに打ってみると。
$ sdk help Usage: sdk <command> [candidate] [version] sdk offline <enable|disable> commands: install or i <candidate> [version] uninstall or rm <candidate> <version> list or ls [candidate] use or u <candidate> [version] default or d <candidate> [version] current or c [candidate] upgrade or ug [candidate] version or v broadcast or b help or h offline [enable|disable] selfupdate [force] flush <candidates|broadcast|archives|temp> candidate : the SDK to install: groovy, scala, grails, gradle, kotlin, etc. use list command for comprehensive list of candidates eg: $ sdk list version : where optional, defaults to latest stable if not provided eg: $ sdk install groovy
sdk list
というコマンドを使うとインストール可能なツールや言語の一覧が表示できるっぽいです。
================================================================================ Available Candidates ================================================================================ q-quit /-search down j-down ?-search up k-up h-help -------------------------------------------------------------------------------- Activator (1.3.10) http://www.lightbend.com/activator/download Typesafe is a GUI/CLI tool to help with building reactive applicaions. It uses sbt (simple build tool) behind the scenes to build, run, and test your project. It provides a code editing interface, and provides templaes and seeds for you to clone and use. $ sdk install activator -------------------------------------------------------------------------------- Ant (1.10.1) https://ant.apache.org/ ...
Kotlin のインストール
SDKMAN!を使ってインストールをします。
sdk list kotlin
コマンドで、一応インストール可能なバージョン一覧を見てみます。
$ sdk list kotlin ================================================================================ Available Kotlin Versions ================================================================================ 1.1.2-2 1.0.3 1.1.2 1.0.2 1.1.1 1.0.1-2 1.1-beta2 1.0.1-1 1.1-beta 1.0.1 1.1-RC 1.0.0 1.1-M04 1.1-M02 1.1-M01 1.1 1.0.7 1.0.6 1.0.5-2 1.0.5 1.0.4 ================================================================================ + - local version * - installed > - currently in use ================================================================================
なるほど今日時点の最新は1.1.2-2
なのですね。
sdk install kotlin
で最新版をインストールします。
$ sdk install kotlin Downloading: kotlin 1.1.2-2 In progress... ######################################################################## 100.0% Installing: kotlin 1.1.2-2 Done installing! Setting kotlin 1.1.2-2 as default.
もう一度sdk list kotlin
してみる、最新版がインストールされて有効になっているのが分かります。
$ sdk list kotlin ================================================================================ Available Kotlin Versions ================================================================================ > * 1.1.2-2 1.0.3 1.1.2 1.0.2 1.1.1 1.0.1-2 1.1-beta2 1.0.1-1 1.1-beta 1.0.1 1.1-RC 1.0.0 1.1-M04 1.1-M02 1.1-M01 1.1 1.0.7 1.0.6 1.0.5-2 1.0.5 1.0.4 ================================================================================ + - local version * - installed > - currently in use ================================================================================
下の方に書いてありますが、
*
がインストール済み>
が現在有効になっているバージョン
ということみたいですね。
+
はまだ表示されていないので断言できませんが、特定のディレクトリに適用されたバージョンが表示されるのでしょう。
Hello, world!
ソース作成
さてまずはhello.kt
を作成します。
$ touch hello.kt
$ vim hello.kt
fun main(args: Array<String>) { println("Hello, World!") }
コンパイル
つぎはコンパイルですね。
kotlinc
というコマンドを使ってコンパイルするようです。
(ちょっと長いのでktc
とかエイリアスを貼ってもいいかもですね)
$ kotlinc hello.kt -include-runtime -d hello.jar
-d
が出力を指定するもの、-include-runtime
が.jar
の中にKotlinのランタイムを同梱するオプションのようです。
ちなみに最初に拡張子を.kt
ではなく.tk
としてしまっていたのですが、そうした場合は以下のようなエラーが出てコンパイルできませんでした。
$ kotlinc hello.tk -include-runtime -d hello.jar error: source entry is not a Kotlin file: hello.tk
なるほど拡張子は.kt
でないとKotlinのソースとしては認識されないのですね。
実行
さてディレクトリの中身を見ると、hello.jar
がちゃんと出来ていますね。
$ ls
hello.jar hello.kt
java
コマンドを使ってjava -jar hello.jar
で実行できるようです。
$ java -jar hello.jar
Hello, World!
ちゃんと実行できましたね。
kotlinc
kotlinc -help
でヘルプが見られるようなので確認しておきます。
$ kotlinc -help Usage: kotlinc-jvm <options> <source files> where possible options include: -d <directory|jar> Destination for generated class files -classpath (-cp) <path> Paths where to find user class files -include-runtime Include Kotlin runtime in to resulting .jar -jdk-home <path> Path to JDK home directory to include into classpath, if differs from default JAVA_HOME -no-jdk Don't include Java runtime into classpath -no-stdlib Don't include Kotlin runtime into classpath -no-reflect Don't include Kotlin reflection implementation into classpath -module <path> Path to the module file to compile -script Evaluate the script file -script-templates <fully qualified class name[,]> Script definition template classes -kotlin-home <path> Path to Kotlin compiler home directory, used for runtime libraries discovery -module-name Module name -jvm-target <version> Target version of the generated JVM bytecode (1.6 or 1.8), default is 1.6 -java-parameters Generate metadata for Java 1.8 reflection on method parameters -language-version <version> Provide source compatibility with specified language version -api-version <version> Allow to use declarations only from the specified version of bundled libraries -nowarn Generate no warnings -verbose Enable verbose logging output -version Display compiler version -help (-h) Print a synopsis of standard options -X Print a synopsis of advanced options -P plugin:<pluginId>:<optionName>=<value> Pass an option to a plugin
もっと大量のオプションを予想していたのですが、思ったよりは少ないですね。(swiftc --help
の量が多すぎるのかも分かりませんが)
今後必要な時に見ていくことにします。
最後に
さて無事にコマンドラインでKotlinのHelloWorldを試すことが出来ました。 最近の言語は試すのが導入から試すまでが簡単で良いですね。
ちなみにチュートリアルのページには、ライブラリの作成方法やREPL、スクリプトとしての実行などが含まれているのですが、続きは別の記事にしたいと思います。
Kotlin で HelloWorld(IntelliJ IDEA編)
世の中はKotlin一色ですね。(言い過ぎ?)
そんなわけで私もKotlin始めてみようと思います。
まずは IntelliJ IDEA(Community Edition)をつかってサクッと。
IntelliJ IDEAのダウンロード
公式サイトからCE版をダウンロード。 www.jetbrains.com
無償のCE版でもKotlinが使えるってのはありがたいですね。
(JetBrainsからしたらそりゃ使ってほしいでしょうが)
プロジェクト作成
Create Project から作成します。
Kotlinの中に「Kotlin (JVM)」ってのがあるのでそれを選択します。
(というかJavaScript版?があるのに驚きました)
Project name は「HelloKotlin」にしてみます。
ウィンドウが表示されたものの殆ど表示されないので戸惑いましたが処理中のようです。 画面下の方にインジケータが表示されています。
Kotlinファイル作成
まだ良くわかっていませんが、srcディレクトリを右クリックして「New > Kotlin File/Class」を選んでみます。
ダイアログが表示されるので Name に「HelloWorld」と入れてみます。
コードを書く
エディタが表示されるので早速コードを書いてみます。
fun main(args: Array<String>) { println("Hello, world!") }
main関数の行に Kotlin のアイコンが表示されました。
実行
Kotlinアイコンをクリックしてみると、どうやらここから実行できるようです。(便利)
画面下の方に実行結果が出力されました。なにやらエラーっぽいものも表示されていますが、とりあえず実行はできているようです。
ディレクトリ構成
ちなみにサイドバーを見るとコンパイル後の結果は out ディレクトリ配下に格納されるようです。
最後に
とりあえず覚え書きとしてスクリーンショット多めで記事を書いてみました。
次回はコマンドラインでHelloWorldしてみたいと思います。
potatotips #40 に参加してきました。
はじめに
(2017/05/27追記) 新たに公開された発表資料を追加しました。
以下のイベントに参加してきました。 potatotips.connpass.com
実は当日まで参加予定ではなかったのですが、 偶然にもAndroidのブログまとめ枠が一人空いたとのことで急遽参加させていただきました。 (ちなみに「ブログまとめ枠」での参加は初めてです)
ちなみにここ数年はiOSエンジニアとしての活動が多いので、ポテチには一度は参加したいと思っていました。 本当は発表者として登壇したいという欲望もあったのですがそれは別の話。
Androidのブログまとめ枠での参加でしましたが、iOSも含めて記事にしちゃいたいと思います。 (大丈夫ですよね?)
箇条書きはリアルタイムで頑張って書いたものなので、間違いとかあるかもです・・・ご容赦を。 またスライドとかは後日公開とかもあると思うので、アップされしだいリンク追加していきます。
乾杯
まずは乾杯、というかもう飲んでる人多数。 Swift愛好会といい最近の勉強会は最初に乾杯ってパターンが多いんですかね?
事前説明
Rettyの中川さんより会場説明。
CMタイム、スポンサーだから当然許されます。 engineer.retty.me
iOSDCやPyConなどのスポンサーもやっているらしいです。 イベントスペースなどもレンタルもやっているとのこと。
Retty Android もくもく回?なるものもやっている、 勉強会などのコミュニティ活動もサポートしてくれる、とのこと。ふむふむ。
では、各発表のまとめです。
どうしたらログがちゃんと管理できるのか?(kosako)
- アプリの分析
- GA
- DB
- 自前(TD?, BigQuery)
- 今回はこれのお話
- よくあるパターン
- ここの数字をみたい
- ボタンのタップ数ってどっちが多いの?
- よくあるパターン
- 都度埋め込まれるログ
- 取りたいデータが取れない
- 後始末がされにくい
- etc
- アプローチ
- ログを送るメソッドを1つに
- コールする場所ではどこに送るか指定しない
- 送信設定ファイルを用意して集約
- イメージ
- ボタンタップ
- 送信メソッド(ここで設定ファイルを見る)
- 送信
- 設定ファイル(log.json)
- ログの設定を集約する
- ポイント
- JSONファイルを用意すれば
- ログの意味が分かりやすい
- ログ同士の対応表がそこにある
- 設定ファイルを変更すればOK
- 今後の野望
「ログをどう管理するか?」という課題に対して、1つの設定ファイル(JSON)に集約するというアプローチ。 個人的にはコード上に値が分散するよりも断然良いと感じたので、良いアプローチだと感じました。
Modern Java Libraries with Kotlin(Keisuke Kobayashi)
- 無料送金アプリ(Kyash)
- 今日
- JavaライブラリをKotlinでも
- 特別に対応が必要なケース
- Dagger2 + Orma
- kaptで自動生成されるクラスはDaggerでprovideできない
- OrmaDatabase
- OrmaDatabaseをラップすればOK
- Dagger Module
- ラップしたクラスを返す
- Data binding
- dependenciesに
kapt
を追加する - Androidバージョンに依存するのでバージョン番号も書く
- dependenciesに
- Parceler
- Parcelableのボイラープレートを自動生成
- Kotlinのデータクラスで使いたい
- data class
- toString, hashCodeの実装が不要
@Parcel
をつけるだけでは動かない- Kotlinのプロパティはフィールドではない
@Parcel(Parcel.Serialization.BEAN)
ってやつ- おまけ
- サンプル作ったよ(2ヶ月くらい)
JavaライブラリをKotlinで使う際に特別な対応が必要になるケースの紹介でした。 私はAnrdoid初学者でDaggerくらいしかライブラリを知らなかったのですが、なんとなくイメージは伝わってきました。
個人的に、Kotlinのプロパティはフィールドではない、というのは勉強になりました。
ゲームアプリの「ドット絵」をディープラーニングで自動生成(shu223)
- 結論:失敗したorz
- DCGAN
- ディープラーニングで画像を自動生成する技術
- 例
- アイドルの顔画像を大量にあつめて自動生成
- スライドに写されたのは元データではなく実際に生成された画像!!
- DCGAN-tensorflow
- サンプルデータだとセレブっぽい顔の画像をせいせい
- 自前のデータを食わせてみたい
- スーパークエスト
- ドット絵モンスターを自動生成できないか?
- やってみた
- 基本的にフォルダに置いて動かすだけ
- epoch
- 学習の進み具合
- 途中経過が面白い
- 学習は順調に見えた
- 過学習
- 学習データを元にしちゃってる?
- 何が違っていたのか?
- セレブは20万枚
- 目も鼻もある、だいたい似てる
- アイドルデータも似てる
- 学習データの量も変化も違う
- まとめ
- ダメだった
- 問題設定が悪かった&データ量が少なかった
- QA
- もう一度チャレンジしますか?
- しません。(ドット絵の題材はもうやらない)
- 解析にかかった時間
- MacBookProでまる1日くらい
- もう一度チャレンジしますか?
ドット絵をディープラーニングで自動生成しようとしたけれどダメだったというお話。 結果はさておき、失敗要因の分析がとても良いと思いました。
ちなみに epoch の過程を見るのは確かに楽しそうだと思いました。
Kotlin Reflection(hikaru_satoh)
- 自己紹介
- リフレクションのKotlinバージョン
- KClass、KPropertyを利用する
- プロジェクト設定
- app/build.gradleに追加する
- 書かなくてもビルドエラーにはならなかったが、エラーログとか
- 4.8kb多くなった
- Class References
- KClass型
User::class
で取得
member.properties
- private
- privateなプロパティがあると例外スロー
isAccesible = true
ってやれば見られるようになる
- Property References
- kProperty型
User::firstName.get(user)
みたいな感じで使える- privateメソッドは見られないのでコンパイルエラーになる
- KProperty1
p:KProperty1<User, *>
- KPropertyの種類
- 0: static変数を取得
- 1: メンバーのプロパティ取得
- 2: (聴き逃した)
- まとめ
- QA
- リフレクションの具体的な利用事例は?
- デバッグ出力を簡単にしたり、ホットパッチ?
- リフレクションの具体的な利用事例は?
Kotlinでのリフレクションの使い方についての説明。 Java8におけるメソッド参照みたいなことが出来る分、Kotlinのリフレクションは安全なのだなと感じました。
シークバーサムネイル作成Tips共有(satoshi0212)
- AbemaTVの人
- 何を作ったのか?
- シークバーのサムネイル表示機能
- アトラス画像表示
- サムネイル画像をまとめたもの
- APIを用意してもらって、番組ID、サイズ、時間
- 1枚で600秒分
- シークバーを初めて触った時に取得
- 再生時間を元に特定
- デザインの作り込み
- デザイナさんが思い入れ
- DEMO
- まとめ
- アトラス画像方式はわりと軽めで実装できた
- 画像取得タイミングを遅らせてみた
- 蛇足
- 作り込みたいけれど締切はあるね
- そういう部分を作る担当になる
- QA
- 画像の切り出しタイミングって?
- 実際に表示しようというタイミングで切り出してUIImageを生成している
- けれど質問されて、UIImageで切り出す必要はないかもと思った
- 画像の切り出しタイミングって?
動画再生においてシークバーをスライドするとサムネイルが表示される例のアレ。 アトラス画像といった考え方や、データ取得を遅延させるといったテクニックなどが聞けて面白かったです。
ちなみに、そういう部分を作れる担当になれるかが重要、というのはまさにだと思いました。
Android Instant App(Sam)
www.slideshare.net
- 自己紹介
- Android Instant Appとは
- 仕組み
- 機能ごとにダウンロードしてくる
- URLからの要求に対して必要な機能だけをダウンロード
- 2つのAPK
- Base Feature APK
- 2回目以降のダウンロードは不要
- 機能のAPK
- Base Feature APK
- 機能ごとにモジュール化させる
- 1つのモジュールは4MBまで
- 制限されている機能
- フアグラウンドは実行できる
- 外部ストレージアクセス
- 明示的インテント
- ブロードキャスト
- 使えない機能
- コンテンツプロバイダ使えない・・・
- コンテンツプロバイダ
- 現状
- 50個以上のアプリが対応済み
- ぶっちゃけ?
- 情報が少なすぎる。。。
- 導入する場合はユースケースを決める必要がある
- どんな体験を?どこの機能を?
Android Instant App についての紹介。 今まで噂に聞いたことがあるレベルだったので、具体的な内容が知れて良かったです。
ユーザにとっての利点は納得できるものの、これだけ制限が多い中、開発者的にはそんなに美味しいかしら、とも思いました。 日本のブロードバンド事情を考えると、Instant App を開発して公開するメリットを感じるアプリは少ない印象を受けました。
ちなみに私も暴君ハバネロは大好きで、箱買いしたこともあるレベルなので懇親会で話そうと思いつつ、 まとめに疲れてすっかり忘れてしまいました・・・またの機会に。
Universal Links 対応した話(Ridwy)
www.slideshare.net
- 自己紹介
- 音声処理技術が好き
- モチベーション
- iOS9以降の機能
- iOS10が普及したので
- 実際に対応して得られた知見
- Universal Linksとは
- アプリが起動する条件
- おさらい
- Entitlementにドメイン追加
- アプリが開かれた時に呼ばれるメソッドを実装
- 扱えないURLはopenで開きなおす
- でも見た目はいまいち
- サーバ側の対応
- AppIDのプリフィックス
- SKIP
- iOSが何をしているか?
- QA
- AASAファイルの更新が必須
iOS9から導入された「Universal Links」についての詳細な発表。 UI/UXに関わる意見や、内部的な実装がどうなっているかの予測など、なかなか深いところまで突っ込んだ内容でした。
発表者の方も言っていましたが、UIはもうちょっとどうにかならないかと感じました。
フル Kotlin で Mastodon クライアントを作ってみて(tomoya0x00)
- 自己紹介
- 組込系がメイン
- 最近アプリとかも
- Mastodonクライアント
- MVVM x フルKotlin
- なぜ?
- SwiftやってたらJava辛くなった
- どういったところが嬉しい?
- Realmとの親和性良いよ
- プロパティ名が取得できる
- lazyで遅延取得が出来る
- 拡張関数でUtilityクラス乱立防止
- coroutineで簡単非同期処理
- Realmとの親和性良いよ
- ハマリポイント
- 無名くらいのインスタンス化
- DataBinding方法
@get:Bindable
みたいな
- 例外処理
- 普通に囲めばOK
- UIスレッド実行
- coroutineビルダー
launchUI()
を使う
- coroutineのライフサイクル
- onDestroyでキャンセルするには
async
時に取得できる?
- QA
フルKotlinでMastodonクライアントを作ってみて得られた知見のシェア。 ハマリポイントとかの紹介があって、これからKotlinを使う人には役立つと感じました。
質問の回答でもありましたが、TwitterよりMastodonクライアントの方が作るのが楽、というのはなかなか意外でした。
ちなみに関係ないですが、最近良く聞く「coroutine」を未だに理解していません。 Go言語とかでもよく聞きますし、今度ちゃんと調べねばと思います。(たぶん、Promiseとは違うんですよね?)
いまから使えるSpreadsheetView(pancake)
- 自己紹介
- OSS
- 公開後1,500スター
- 作ったアプリ
- 機能
- ヘッダ固定
- 無限スクロール
- グリッド線とか枠線とか
- UICollectionView like
- サンプル付き
- スケジュール
- ガントチャート
- タイムテーブル
- とっつきやすい
- UICollectionView likeなAPIなので使いやすいかも?
- セルのマージ機能
- 5分刻みのセルを作ってみた
- ほかのライブラリは?
- ある
- セルのマージ機能があるのはスプレッドシートだけ?
- 標準だとリニアな探索のところ、2分探索が実装されている
- QA
- 結合されたセルのタップイベントはどうやって拾う?(インデックスとかどんな感じで?)
- 現状だと左半分しか反応しない?(実装ミスかも)
- 結合されたセルのタップイベントはどうやって拾う?(インデックスとかどんな感じで?)
岸川さんが開発されたSpreadsheetViewを使ってみたというお話。 github.com
私もiOSエンジニアなので噂は聞いていましたが、具体的にどういうことが出来るのか知らなかったので良かったです。 そしてセルの結合機能があるOSSは(おそらく)唯一なのですね。
しかしスター数1,490とは・・・凄まじいですね。
「Lottie」でお手軽アニメーション実装(shanonim)
- Lottie
- 意外と知ってる人が多い
- アニメーションのライブラリ
- Adobe After Effectsで作ったJSONをアプリで読み込める
- そのままアプリに組み込めちゃって楽ちん
- iOS/Android/ReactNativeすべてに対応
- AfterEffects
- 映像分野ではメジャーなソフト
- CM作成とかでも利用されているらしい
- アプリに組み込む(Android)
- 利用ケース
- ローディングとかアイコンとか
- 画面全体とかは微妙かも
- 導入までのハードル
- After Effects 誰がやるの問題
- LottieFiles.com
- CCライセンスで公開されている
- 見てるだけで楽しそう
- まとめ
- Lottie楽しい
- アニメーションでUXをあげよう
- QA
Adobe After Effectsというツールで作成したアニメーションをJSONでエクスポートして、そのままアニメーション出来るLottieについての紹介。 airbnb.design
不勉強なものでAfter Effects自体知らなかったのですが、デザイナさんがそれを利用してアニメーションを作成し、 それを殆どゼロコストで導入できる(デザイナの意図が100%反映される)というのは便利だと思いました。
CCライセンスで公開されているLottiefiles.comは、たしかに見ているだけで楽しいですし、何かアイディアに繋がりそうな気がしました。 www.lottiefiles.com
Lightweight Dependency Injection Tips(Motoki Narita)
- 放送事故(放送終了)
- (発表開始直後にディスプレイが消えてしまった)
- 自己紹介
- メルカリカウル
- 本、CDとかに特化した姉妹アプリ
- クラッシュレート1%を下回る
- 今回DIを取り入れた
- AppleでもDIのベストプラクティスをまとめている
- Qiita記事にもまとめている
- イケてない気がするところ
- Segueで依存オブジェクトを渡す必要がある
- DRYではない
- コンパイラがエラーを出さない
- Segueで依存オブジェクトを渡す必要がある
- “良い設計は誤った用法をコンパイルエラーにする"(ishikawa)
- ルール
- インスタンス化はコードで行う
- 経緯
- アッテの開発のなかでそういう話になっった
- 作り方
- プロトコルを宣言(typealias、makeメソッド)
- 作っていく中でリファクタリングを繰り返していった
- まとめ
- 良かったこと
- インスタンス化の方法が統一される
- 統一されることでDRY
- 再利用が楽に
- 良くなかったところ
- Storyboardを使っているけれど画面遷移が見えない
- 良かったこと
- 告知
- iOSDC(今年は2.5日)
LightweightなDIを使うと良いかもよ、という話。 個人的には今日のLTの中で一番面白く感じた内容でした。
Lightweightというのは誇張ではなく、本当に最低限の仕組みであるにも関わらず、 そこに本質がきれいに表現されていると感じました。
時間の関係上リファクタリングの過程が見られなかったので、発表資料の公開が待ち遠しい限りです。
Protocol Buffers(TakuSemba)
- 自己紹介
- 最近ProtocolBufferを使うことがあった
- CyberAgent, Inc.
- Protocol Bufferとは
- Quick Start
- Proto fileの定義
- スクエア制のツール
- Javaファイルが書き出される
- プロジェクトに追加する
- Let’s 通信
- dependenciesに追加
- Retrofit
- まとめ
最近何かと話題に上がるProtocol Buffer の話。 やはりデバッグしづらかったり、API変更が面倒だというのは、どこでも共通認識のようです。
Proto fileで共通認識が取れる、という視点は今までなかったので勉強になりました。
LicensePlist(mono)
www.slideshare.net
- 自己紹介
- mono
- LicensePlist
- ライセンス管理を自動的にやってくれる
- 今まで決定版がなかった
- 決定版を目指して作った
- SPMで管理
- 手動で入れたものまで検出してくれる
- 仕組み
- LICENSEファイルをかき集めている
- Cocoapods
- plistの生成
- PropertyListSerializationというものがある
- 最初は自分で書いてしまったら真っ白になることも
- YAMLファイルで柔軟性を担保
- install
- Homebrewに対応してます
- 設定
- Buildのpre-actionに設定するのがおすすめ
- QA
- 他の設定を生成したい場合は?
- 出力形式を変更するだけなので要望があれば対応する(ViewControllerとか)
- 他の設定を生成したい場合は?
ライセンス管理自動化の決定版的ライブラリを作ったよ、という話。 その宣伝文句に違わず、CocoaPods、Fastlane、手動など、様々なケースに対応していてとても良さそうでした。
懇親会
窯焼きのピッツァ(!)
最後に
ポテチの参加は初めてだったのですが、多彩な発表が聞けてとても楽しかったです。 会場、飲み物、食べ物を提供してくださったRettyさん、主催者、発表者、の方々、本当にありがとうございました。 (もちろん懇親会で話してくださった方も)
ちなみに勉強会では結構メモるタイプなので、ブログまとめなんて楽勝だと思っていたのですが、 LTはテンポが非常に早くて、メモをしながら発表についていくのは思ったよりもハードでした(笑)
ではまたの機会に参加できることを楽しみにしつつ、締めたいと思います。
技術用語メモ
新しく知った技術用語とかをダンプするようの記事。
Capistrano
Rubyによる構成管理ツール。AnsibleのRuby版っぽいイメージ?
用語を知った場所:
Capistranoを使ってS3等からpull型デプロイするgemを書いた、ほか — Mobage Developers Blog
GCP
Google Cloud Platform。 いわゆるGoogleが提供してるクラウドサービス。
Kubernetes
複数のDockerコンテナを管理するツールで、Googleが開発を始めたもの。
Docker単体では実現できない以下のような機能を提供する。
(オーケストレーション)
- 関連するコンテナのグルーピング
- コンテナに振られるIPアドレスの管理
- コンテナ間のネットワークルーティング
などなど
関連記事:
knowledge.sakura.ad.jp
GKE
Google Container Engine。
複数のDockerコンテナをKubernetesで管理するクラウドサービス。
GCPだとGoogle Cloud Platformと被るので、KubernetesのKを取ってGKEとなったらしい。
関連記事:
ブログをGKEでの運用に移行した | tsub's blog
セキュリティ
ソルト
憶測されるデータからハッシュ値を衝突させて元データを特定する、といった攻撃に対処するもの。
例えば、ハッシュ値が連番であると予想された場合、連番からハッシュ値を生成して一致するか確認することで総当りで元データが特定できてしまう。
それを避けるために元データに何らかの文字列を付与しておくことを「ソルト」という。 例えば、99xxyyzzとか元データ(今回は99)に対して特定の文字列(今回はxxyyzz)を付与する。
ソルトも当然ながら憶測されにくい文字列である必要がある。
関連記事:
speakerdeck.com
RubyでConsリスト
試しに書いてみた。 もうちょっと良い書き方ありそう。
ちなみに三項演算子を使おうとも思ったけれど、 xxx.nil? ? ...
という感じで?
が連続して違和感抜群だったので使わなかった。
メタプログラミングRuby第二版::一章 - 頭文字M
メタプログラミングRubyを読んで、理解のために自分なりにまとめていく。
基本的にテストコードをRSpecで記述していく。
メタプログラミングとは?
コードを記述するコードを書くこと。
Rubyは実行時にクラスやメソッド、インスタンス変数など、様々な情報を読み書きできるのでメタプログラミングに適している。
C/C++などの言語では、実行時には変数やメソッドなどの実体は消えてなくなってしまうので、プログラム実行中にそれらの情報にアクセスして何かすることは出来ない。
Javaについては、リフレクションを利用してクラスやメソッドの情報にアクセスすることが出来るが、Rubyほどに変更を加えることは出来ない。
Rubyはコンパイル時・実行時などの明確な区別がなく、あらゆる言語要素が常にそこにあり、操作できるといえる。(これはLispと同じ思想といえる)
ちなみにObjective-Cも(Rubyほどではないかもしれないが)動的にメソッドを追加したり、差し替えたり(Method Swizzling)、解決できなかったメソッド呼び出しを自分で解決する手段を用意しており、ここまで上げた言語のなかではメタプログラミングが得意と言える。
魔術
Rubyにおいてメタプログラミングを使った技法は「魔術」と言われる。
魔術には良いものと悪いもの、すなわち「白魔術」と「黒魔術」が存在する。
Rubyは全面的にプログラマを信用し、言語側で安全のためにブロックしたりするという考えは持っていない。”プログラマはミスを犯す”という視点に立って、安全性を重視しているJavaとは対照的と言える。
イントロスペクション
実行時に言語要素にアクセスすること。 JavaではリフレクションAPIを利用してアクセスする。
プロダクションコード:
class Greeting def initialize(text) @text = text end def welcome @text end end
テストコード:
require 'spec_helper' require 'introspection' describe 'introspection' do let(:greeting) { Greeting.new('hello') } it 'クラス名が取得できること' do expect(greeting.class.to_s).to eq 'Greeting' end it 'インスタンスメソッドの一覧が取得できること' do # 引数の`false`は継承したメソッドは対象にしないという意味 expect(greeting.class.instance_methods(false)).to eq [:welcome] end it 'インスタンス変数の一覧が取得できること' do expect(greeting.instance_variables).to eq [:@text] end end
テストコードにあるように、以下の情報がgreeting
インスタンスから取得できている。
ActiveRecordの例
ActiveRecordは Ruby on Rails で使用されているORMapperである。
以下はmovies
テーブルのレコードに対応するEntityクラスを定義した例である。
class Movie < ActiveRecord::Base end
このように特定のクラスを継承するだけで実現できる。
テーブル名はクラス名Movie
から取得し、カラムに対応するアクセサメソッドはDBのスキーマから取得し、実行時に動的にクラスに対してメソッドを追加することで実現できている。
実行時に情報が消えてしまうC/C++のような言語ではこのようなことは出来ず、ボイラープレートが増えてしまう。もちろんコードジェネレータを使用した「静的メタプログラミング」も可能だが、それは言語の外で行われるもので、プログラム実行時に行える「動的メタプログラミング」ほどスマートではない。(ジェネレータを実行する手間もあるだろうし、コード上からボイラープレートコードは消えない)
Rubyにおけるメタプログラミングは特殊ではない
MongoDBメモ(その1)
dot install のレッスン動画を見ながら勉強。
http://dotinstall.com/lessons/basic_mongodb_v3/35001
この記事の範囲。 - 01 MongoDBとはなにか? - 02 MongoDBをインストールしよう - 03 用語を理解しておこう - 04 データベースを操作してみよう - 05 コレクションを操作してみよう
概要
インストール
yumリポジトリを登録
リポジトリファイル作成
$ sudo vi /etc/yum.repos.d/mongodb-org-3.4.repo
記述内容
[mongodb-org-3.4] name=MongoDB Repository baseurl=https://repo.mongodb.org/yum/redhat/$releasever/mongodb-org/3.4/x86_64/ gpgcheck=1 enabled=1 gpgkey=https://www.mongodb.org/static/pgp/server-3.4.asc
yumでインストール
$ sudo yum install -y mongodb-org
起動
以下のコマンドで起動。
$ sudo service mongod start
次回以降も自動的に立ち上がるように設定。
$ sudo chkconfig mongod on
バージョン確認:
$ mongo --version
用語
階層構造
- Database
- Collection
- Document
- Collection
RDBに対応させると
- Database = データベース
- Collection = テーブル
- Document = レコード
データ格納
JSON形式で格納される。
{field: val, field: val ...}
MongoDBではキーのことをfield
と呼ばれることもある。
スキーマレスなのでDocumentの項目があったりなかったりしても大丈夫。
{name: "yusuke", score: 30} {name: "hosonuma", score: 58, team: 3}
データベース操作
アクセス:
$ mongo
データベースの一覧を表示
> show dbs; admin 0.000GB local 0.000GB
データベースの作成・切り替え
> db.createCollection("users"); { "ok" : 1 }
コレクションが存在しないとshow dbs;
では表示されないので注意。
> show dbs admin 0.000GB local 0.000GB
コレクションの作成
db.createCollection()
で作成。
> db.createCollection("users"); { "ok" : 1 }
コレクションが作成されればshow dbs;
で表示される。
> show dbs; admin 0.000GB local 0.000GB mydb 0.000GB
状態を確認する
db.stats()
で確認出来る。
> db.stats(); { "db" : "mydb", "collections" : 1, "views" : 0, "objects" : 0, "avgObjSize" : 0, "dataSize" : 0, "storageSize" : 4096, "numExtents" : 0, "indexes" : 1, "indexSize" : 4096, "ok" : 1 }
DBの削除
db.dropDatabase()
で現在のデータベースを削除する。
> db.dropDatabase(); { "dropped" : "mydb", "ok" : 1 }
mydb
が削除されている。
> show dbs; admin 0.000GB local 0.000GB
コレクションの操作
作成
db.createCollection()
で。
> db.createCollection("users"); { "ok" : 1 }
一覧表示
show collections;
を使う。
> show collections; users
リネーム
データベース名.Collection名.renameCollection("新しい名前");
。
オブジェクト指向っぽいAPI。
> db.users.renameCollection("customers"); { "ok" : 1 }
ドキュメントの操作
挿入
ドキュメントを挿入すれば、コレクションは自動的に作られる。
格納するデータはJSON形式で記述する。
> db.users.insert( ... { ... name: "taguchi", ... score: 30 ... } ... ); WriteResult({ "nInserted" : 1 }) > show collections; users
スキーマレスなのでデータ構造が違っても大丈夫。
> db.users.insert({ ... name: "fkoji", ... score: 50, ... tags: ["web", "mobile"] ... }); WriteResult({ "nInserted" : 1 })
JavaScriptを使う
JavaScriptを使って処理を記述できる。
> for (var i = 0; i < 10; i++) { ... db.users.insert({ ... score: Math.random() ... }); ... } WriteResult({ "nInserted" : 1 })
件数表示
> db.users.count(); 12
一覧表示
_id
は MogoDB が自動的に振る一意なID。
> db.users.find(); { "_id" : ObjectId("58c5458ca48b064d97084189"), "name" : "taguchi", "score" : 30 } { "_id" : ObjectId("58c545baa48b064d9708418a"), "name" : "fkoji", "score" : 50, "tags" : [ "web", "mobile" ] } { "_id" : ObjectId("58c545d2a48b064d9708418b"), "score" : 0.30322503633107833 } { "_id" : ObjectId("58c545d2a48b064d9708418c"), "score" : 0.5613546607214355 } { "_id" : ObjectId("58c545d2a48b064d9708418d"), "score" : 0.2844040596878158 } { "_id" : ObjectId("58c545d2a48b064d9708418e"), "score" : 0.9263121937224452 } { "_id" : ObjectId("58c545d2a48b064d9708418f"), "score" : 0.5939208256213909 } { "_id" : ObjectId("58c545d2a48b064d97084190"), "score" : 0.5308342673704005 } { "_id" : ObjectId("58c545d2a48b064d97084191"), "score" : 0.8924712820338384 } { "_id" : ObjectId("58c545d2a48b064d97084192"), "score" : 0.9430223426794738 } { "_id" : ObjectId("58c545d2a48b064d97084193"), "score" : 0.6797531592023286 } { "_id" : ObjectId("58c545d2a48b064d97084194"), "score" : 0.9737296169048628 }
削除
条件を指定しない場合は、以下のように空のJSONを渡す。
> db.users.remove({}); WriteResult({ "nRemoved" : 12 }) > db.users.find();