コネヒト開発者ブログ

コネヒト開発者ブログ

RxSwift.Variableはdeprecatedになりました

こんにちは、ガチエリアS帯のリードエンジニアの田村(@Utmrer)です。他のルールもS帯にいくため、Splatoon2サントラを聴きながら日々コーディングをしております。
この記事はConnehito Advent Calendar 2017の4日目の記事です。

今日はRxSwiftのコードを覗いていたら気づいたことを書きました。
(2017年12月4日現在の情報です)

Variableとは

VariableはRxSwiftで提供されているBehaviorSubjectのwrapperで値の取り出しや代入を直感的に扱うことができるSubjectの1つです。
MVVMでステートフルなViewModelのpropertyとして使っている人が多いのではないでしょうか。

// Example
class VM {
    let name = Variable("")
}
class VC {
    func f() {
        textField.rx.text.orEmpty
            .bind(to: vm.name)
            .disposed(by: disposeBag)
    }
}

RxSwift4でVariableはしれっとdeprecatedに

ある日RxSwift repositoryのコードを読んでいたらDeprecated.swiftという非推奨のAPIをまとめたファイルを見つけ、Variableが記載されているのを見つけました。
Warningが出ていないので気づけなかったのですが、Warningを出していないのは利用者が多いことなどが理由のようです。*1
ではVariableが非推奨になった時代に私たちはどうすればいいのでしょう。

安全なBehaviorSubjectであるBehaviorRelay

Variableのdeprecatedと同時に追加されたBehaviorRelayはBehaviorSubjectのwrapperでerrorの流れることが無い、安全なBehaviorSubjectです。この点においてVariableとほぼ同じ特性を持ちます。
Variableではvalue propertyのsetter/getterで値の操作を行っていたのが、BehaviorRelayでは下記のようなaccept() methodとvalue propertyでアクセスします。

let relay = BehaviorRelay<Int>(value: 0)
relay.asDriver()
    .drive(onNext: { value in
        print(value)
    })
    .disposed(by: disposeBag)
relay.accept(1)
print(relay.value)

Variableが非推奨になったので、同様の性質をもつBehaviorRelayに移行していくのが正道となるでしょう。

BehaviorRelayはRxCocoa

今までVariableはRxSwift moduleの一部でしたが、BehaviorRelayはRxCocoa moduleの一部になっています。BehaviorRelayと同時期に実装された安全なPublishSubjectであるPublishRelayもRxCocoaです。
これは「Relayは特定の環境で求められるものであり、Reactive Extensionsのコンセプト外である」というのが理由のようです。*2
ではRxCocoaに含まれるのが適切なのでしょうか?RelayにはCocoaへの依存はありません。ちなみに、これらRelayの設計元になったと思われるRxJavaのRxRelayはRxJavaのユーティリティという立ち位置でRxJava, RxAndroidには実装されていません。
このままRxCocoaに含まれていくような気がしますが、RxRelayとして分離されることがあるかもしれません。

BehaviorRelayへの移行はやるべき?

今すぐにでもVariableからBehaviorRelayへの移行を行うべきか、というと個人的にはちょっと待とうと思っています。なぜならば、Variableで提供されていたbind(to:)というmethodがまだBehaviorRelayには提供されていないからです。*3 RxSwiftの中の人も「ちゃんと移行方法を決めたら@availability付けて本当にdeprecatedにするよ」と言っているのでそれまで待ってもいいかなと思っています。*4
下記のようにextensionを書くことでbind(to:)を使うこともできるので待てなくなったら移行します。(副作用がちょっとわからないのでまだやってないのですが)

extension BehaviorRelay: ObserverType {
    public func on(_ event: Event<Element>) {
        switch event {
        case .next(let value):
            accept(value)
        default:
            break
        }
    }
}

まとめ

以上、RxSwift4でのVariableとBehaviorRelayについてでした。@availabilityが付くと大量のwarningが出る可能性があるので備えておきたいですね。 明日は@fortkleによるファビュラスマックスな5日目の記事をお送りします。

qiita.com

早速AWS Fargateで、ECSで動かしているタスクを動かしてみた!

こんにちは。インフラエンジニアの永井(shnagai)です。

AWS re:Invent今年は大豊作ですごいですね。 特に待ちに待っていた、フルマネージドのコンテナサービスが発表されて、ECSでEC2の管理したくないなと思ってた勢としてはとても喜びを感じています。 EKSとの棲み分けも気になる所ですね。

AWS Fargateの紹介 – インフラストラクチャの管理不要でコンテナを起動 | Amazon Web Services ブログ

今回は、検証を兼ねてECS上で動かしているバッチ処理をFargateで動かしてみたのでそのレポートをお送りします。

この記事はコネヒト Advent Calendar 2017 3日目の記事です。

qiita.com

ゴール

既にECS環境で動いているDockerイメージとタスク定義をベースに、Fargateで一本バッチ処理を動かしてみて使用感を確かめてみる。

所感

検証メインの記事なので、はじめに所感から

Fargateいいですね!まさにこの願いが叶えられたといったトコロです!! f:id:nagais:20171201190518p:plain

【良かったところ】

  • クラスタマネジメントが不要になるので、運用コストは更に減るというかオートスケールをうまく組めればほぼECSクラスタを意識する必要はなくなりそう
  • コスト面で見ても、ECSだと耐障害性を意識して、multiAZ構成で余分なリソース(EC2)を持っていたのが捨てられるのは大きいし、従量課金なので素晴らしい
  • 既にECSを使っている人なら、既存のECS資産をかなり活かせるので移行コストはほぼかからないと実際に触ってみて思った。

【気になったところ】

  • 起動がECSと比べると遅い  ※バックエンドのEC2側でDokcerイメージのキャッシュが効かないから、起動が遅くなる気がする
  • Fargateにバージョンの概念がありそうなので、そこは詳しく学びたい

検証手順

  • タスク定義とdockerイメージをus-east-1に作る
  • クラスタとタスクのワンタイム実行
  • 感想

タスク定義とdockerイメージをus-east-1に作る

現状だと、Fargateはus-east-1でしか利用できないのでまずはap-northeast-1にあるDockerイメージとタスク定義をus-east-1に移動します。

ECRのリポジトリを作ってDockerイメージ を登録する

ECRで[test]というリポジトリを作ってそこにイメージを手元からpushします。

※aws cliのリージョン(~/.aws/config)をus-east-1に変更

※AWSIDはAWSアカウント毎に割り振られるIDを入れる。(ECRのリポジトリ画面で確認出来ます)

# ECRにログイン
$ $(aws ecr get-login --region us-east-1 --no-include-email)
# リポジトリの作成
$ aws ecr create-repository --repository-name test
# dockerイメージのビルド
$ docker build -t [AWSID].dkr.ecr.us-east-1.amazonaws.com/test:latest .
# dockerイメージのpush
$ docker push [AWSID].dkr.ecr.us-east-1.amazonaws.com/test:latest
# イメージがpushされている事を確認
$ aws ecr list-images --repository-name test
{
    "imageIds": [
        {
            "imageTag": "latest",
            "imageDigest": "sha256:6cda52f3decf045bccce7e1161c6667f24958cc192fae48681014e0c8e9474f8"
        }
    ]
}

タスク定義を登録する

[タスク定義]→[新しいタスク定義の作成]

早速Fargateの文字が!! どうやらタスク定義の時点で、EC2で動かすかFargateで動かすかを選択する必要があるようです。 ※既存のタスク定義を簡単に移行する方法が提供されるとWebinerで言っていたような気がするので東京リージョンに来る時にはそこら辺が整っていることに期待ですね。

f:id:nagais:20171201171417p:plain

続いて設定画面 Task execution IAM ロールという新しい概念がありますね! 「新しいロールの作成」にしておくと最適なロールが作られます。 f:id:nagais:20171201172246p:plain

メモリ,CPUリソースは関連性があり1Gだと0.25〜0.5vCPUしか使えません。

何となくバックエンドにいるEC2が感じられますね。

1コンテナあたりに使えるメモリは、0.5G〜6G f:id:nagais:20171201172311p:plain

1コンテナあたりに使えるvCPUは、0.25vCPU〜4vCPU f:id:nagais:20171201172327p:plain

メモリ、CPUリソースを入れるとこんな形で表記されます。 f:id:nagais:20171201173243p:plain

コンテナ設定の中身はほぼECSと同じですが、ログの部分だけAuto-configureがデフォルトでチェックされています。 おそらくFargateで動くコンテナは自動的にCloudWatch Logsに送られる作りになっているようです。

f:id:nagais:20171201172821p:plain

これまでは、CloudWatch Logsのロググループは手動で作成する必要があったのですが、勝手に作ってくれてちょっと便利になってます。 f:id:nagais:20171201173507p:plain

クラスタとタスクの実行

クラスタの作成

[クラスタ]→[クラスタの作成]

クラスタテンプレートという概念が生まれていますね。 ここでは、[Networking only]を選択します。

f:id:nagais:20171201174123p:plain

次の画面でクラスタ名を入れて、クラスタを作成します。

作成されたクラスタのUIはこれまでとほぼ同じですが、一部気になる所があったので抜粋します。

  • サービスとタスクのrunning数カウントに、FargateとEC2毎の数が出るようになっている

  • Fargateのクラスタを作ってもECSインスタンスのタブは出来るみたいです。(ココらへんは今後改善されていく予感)

f:id:nagais:20171201174526p:plain

タスクの実行

いよいよ本題のタスクの実行です。

[タスク]→[新しいタスクの実行] f:id:nagais:20171201184222p:plain

ここでも新しい設定で気になったものだけピックアップしてみます。

  • Launch typeにFARGATEが選択可能になっている
  • タスク定義が選択方式になっていてこれまでの入力方式に比べるとかなりいいですね。(手動作業する時にリビジョン番号忘れがちだったので)
  • Platform versionという概念が出来ている(Fargateのバージョンの話なのかな)
  • タスク実行ボタンを教えてからの反応がちょっと悪くすこし待ちが必要です。

無事タスクが起動しました!!

f:id:nagais:20171201184802p:plain

CloudWatch Logsからも動いていることが確認出来ますね。 f:id:nagais:20171201184108p:plain

簡単にですが、FargateでECSで動かしていたタスクを実行してみました。 これからもう少しちゃんと検証してみて、あまりコストかからないと思っているので、ECS環境のFargate化に向けて動いていこうかなと思っています。

明日は、 リードエンジニア @yutmr さんによる記事をお送りします。

コネヒトではコンテナ周りの基盤を整備したりサービス改善を行うエンジニアを募集しています。 少しでも興味もたれた方は、是非気軽にオフィスに遊びにきていただけるとうれしいです。

www.wantedly.com

今更始める Firebase + BigQueryを使った サクサクデータ分析

【DEPRECATED】本稿にある内容は、Firebaes AnaltyicsのBigQuery Exportのスキーマ変更(2018-06)以前の情報を基にしています。


こんにちは、サーバーサイドやっております金城(@o0h_)です。
最近通読した漫画はフットボールネーションです面白いですね・・・もちろん喧嘩稼業(9)も買いました!!!!
よろしくおねがいします。

あどべんと!

この記事は、Connehito Advent Calendarのday-2です!
やっぱりPHPer的には7.2がホットなネタ!?などとも思ったのですが、
@kiyoeshiの温かいUX改善を読んで、私もfumufumuとなりましたので
データ分析系のテーマで1本ぶっこんでみます。

ここのところ社内でデータ部分析基盤を整えていこうという動きがり、その流れで話題にした内容になります。
「Firebaseで集めた記録を、BigQueryで簡単に「生きたデータ」化しようね」という話です。

続きを読む

CakePHP3.5.6にアップデートしました

こんにちは。5年ぶりくらいにポケモンをやろうかなと思っている結城(@super_manner)です。 もう12月も目前ですっかり冬ですね、体調等くずされてないでしょうか。

さてさて、今日も元気にCakePHPのupdateをお知らせしたいと思います。 cakephp

bakery.cakephp.org

CakePHP3.5.6アップデート超訳

所感など

今回も細かなバグフィックスや、なんとなくスルーされがちな箇所が整っていったようです。 確かにsqlのdumpとかめっちゃ括弧多いなぁって思った事はあったので、実行に移してくださった世界中のエンジニアさんに感謝したいと思います。 もうじき3.6が出そうなのでそれも楽しみです!

ではまた!

個人で開発したOSSを会社のプロダクションコードに投入した話

f:id:itosho525:20171114185252p:plain

こんにちは。先日社内LTで乃木坂46の紹介をした@itoshoです。

いつもアイドルの話ばかりしたり、週末はアイドルのライブに行ったりしている僕ですが、実はちょっと前に忙しいヲタ活の合間を縫いながら、OSSをつくりまして、最終的にそれを弊社のサービスに混ぜ込んだ話を今日はしたいと思います。

会社のプロダクションコードに投入するために

せっかくOSSをつくったので、やっぱり実際に使いたい!使われたい!と思うのが自然な流れだと思いますが、いざ実際に動いている会社のプロダクションコードに実績もない個人のOSSを投入するのはつくった本人も怖いですし、周りも(一定以上の信頼関係があるとは言え)大丈夫かな?と心配してしまうと思います。

というわけで、今回個人で開発したOSSを会社のプロダクションコードに投入する際のガイドラインを作成してみました。

以下は、社内で公開したガイドラインの抜粋です。*1

心構え

  • 臆せずどんどんOSSをつくって公開していこう!
  • でも、会社のプロダクションコードに投入するのは責任を持とう!
    • これは別に不具合があった時に怒られるという意味ではなくプロフェッショナルとして誇りを持って投入していこうという意味です。
  • なので、投入する時はちゃんとチームでコンセンサスをとってから投入しましょう。
    • 相談された人も無下にせず、OSSをつくったことを讃え、リスペクトの気持ちを忘れないようにチェックしましょう。

投入するための最低条件

  • MITライセンスであること
  • コミットメッセージやIssueが英語で書かれていること
  • 各言語のパッケージ管理のスタンダードなエコシステムに乗っていること
    • バージョン管理もちゃんとすること
  • テストがきちんと書かれていること
    • CIをPassをしていること
    • カバレッジが高い水準にあること
      • OSSの特性に依ると思うので必ずしも100%である必要はありません
      • ただし、理由はちゃんとチームメンバーに説明しましょう
  • ドキュメントが整備されていること
    • 最低限使い方がREADME読んで理解出来ること
  • メンテし続けていく気概があること

投入までの流れ

  • 上記の条件を満たしてからチームメンバーに導入の相談をする。*2
  • 相談されたメンバーはコード等を確認して、適宜フィードバックを行う。
  • 必要に応じて修正を繰り返して、チームとしてGoサインが出たら、遂に投入です!

ガイドラインを作成してみて

公開してまだ日が浅いので、今後見直しが発生するかもしれませんが、一定の基準や方針が出来たのはよかったかなと思っています。

今回ガイドラインを作成したのは自分自身、基準がなくて困ったということもありますが、個人でつくったOSSが会社のシステムやサービスをよりよくするものであれば、絶対投入したほうがいいし、まして、それが心理的な障壁だけで投入を躊躇しているんだったらもったいないなと思ったので、このような方針を示してみました。

また、これにより少しでも会社のメンバーがOSSをつくるモチベーションが上がればいいなとも思っています!

ちなみに、どんなOSSをつくったの?

ここからはおまけですが、せっかくなので、どんなOSSをつくったか簡単に紹介させていただきます。

一言で言うと、複雑になりがちなDBへのクエリメソッドを簡単に記述出来るCakePHPのBehaviorプラグインです。

名前はそのままでEasy Queryと名付けました。

どれくらいEasyなの?

CakePHPではレコードの一括登録を行いたい時、 通常saveMany()という関数を利用します。

使い方としてはこんな感じです。

<?php

$data = [
    [
        'title' => 'First Article',
        'body' => 'First Article Body',
        'created' => '2012-02-22 00:00:00',
        'modified' => '2012-02-22 00:00:00'
    ],
    [
        'title' => 'Second Article',
        'body' => 'Second Article Body',
        'created' => '2012-02-22 00:00:00',
        'modified' => '2012-02-22 00:00:00'
    ]
];
$articles = TableRegistry::get('Articles');

$entities = $articles->newEntities($data);
$result = $articles->saveMany($entities);

分かりやすいですね。*3

ただ、このsaveMany()とっても便利なのですが、いわゆるBulk Insertではないので、大量のデータを一括登録したい時はパフォーマンスが問題になる場合があります。

どうしても、Cake的な書き方で、Bulk Insertしたい時はこんな書き方をします。

<?php

$data = [
    [
        'title' => 'First Article',
        'body' => 'First Article Body',
        'created' => '2012-02-22 00:00:00',
        'modified' => '2012-02-22 00:00:00'
    ],
    [
        'title' => 'Second Article',
        'body' => 'Second Article Body',
        'created' => '2012-02-22 00:00:00',
        'modified' => '2012-02-22 00:00:00'
    ]
];
$articles = TableRegistry::get('Articles');

$query = $articles->query()->insert([
    'title', 
    'body',
    'created',
    'modified'
]);
$query->clause('values')->values($data);
$result = $query->execute();

コード量はほとんど変わらないですが、やや直感的じゃなくなっちゃいますね。

というわけでBulk Insertのような複雑になっちゃうクエリを抽象化して、簡単に扱えるようにしたのが、今回開発したEasy Queryです。

Bulk Insertの例で言うと、こういう感じで書けます。

<?php

$data = [
    [
        'title' => 'First Article',
        'body' => 'First Article Body',
        'created' => '2012-02-22 00:00:00',
        'modified' => '2012-02-22 00:00:00'
    ],
    [
        'title' => 'Second Article',
        'body' => 'Second Article Body',
        'created' => '2012-02-22 00:00:00',
        'modified' => '2012-02-22 00:00:00'
    ]
];
$articles = TableRegistry::get('Articles');
$articles->addBehavior('Itosho/EasyQuery.Insert');

$entities = $this->Articles->newEntities($data);
$result = $this->Articles->bulkInsert($entities);

saveMany()と同じようなI/Fで書けるので(自分で言うのも何ですが)直感的ですね!

補足

今回はOSSの紹介がメインではないので、インストール方法や細かい利用方法はGithubやPackagistをご覧いただければと思いますが、Bulk Insert以外にもUpsertやBulk Upsertにも対応しておりますので、よかったら使ってみてください。*4

現状MySQLしかサポートしていなかったり、createdmodifiedが自動で更新されなかったりというIssueがありますが、鋭意対応中です!

最後に

僕自身もこれから乃木坂46のようなビックなOSSをつくれるように頑張るぞ!

脚注

*1:一部内容を加筆・修正しております。

*2:もちろん、つくっている途中で相談してもOKですが最終的にはこの条件を満たすようにする。

*3:timestamp behaviorを利用すれば、createdとmodifiedは省略出来ます。

*4:一生懸命つくっていますが、利用に際しては自己責任でお願いいたします。

KotlinConfに行ってきました!

こんにちは!Androidエンジニアの富田です。今回は11/2、11/3に行われたKotlinConfというKotlinの海外カンファレンスに参加してきましたので、簡単にカンファレンス内容からカンファレンスを通じてトライしたことを共有します。

KotlinConfとは

KotlinConfとは、Kotlinに関するプログラミングカンファレンスで今回サンフランシスコで初開催でした。参加者は1200名と初開催ながら大規模なカンファレンスで、なんとAndroidの神Jake Whartonさん、関数型プログラミングのErik Meijerさん、Kotlinのリード設計エンジニアAndrey Breslavさんなど超有名な方々がスピーカーとして登壇されました!日本からもしらじさんが登壇されて国内でも大きな反響がありましたね!

海外カンファレンスに行こうと思ったきっかけ

僕が海外カンファレンスに参加したことがなかったので参加してみたいと思っていました。また、ほとんどの社内の開発メンバーも海外カンファレンスに参加した経験がなかったので、みんなにも少しでも興味をもってもらえたらと思い参加しました。加えて、社内制度として「技術支援制度」ができたので、この制度を活用し活性化させたいと考えていました。

カンファレンスの風景

f:id:tommy_kw:20171113222511j:plain
カンファレンス会場のPIER27

f:id:tommy_kw:20171113222555j:plain
Architectures Using Functional Programming Conceptsセッション

f:id:tommy_kw:20171113222624j:plain
Kotlin水筒

f:id:tommy_kw:20171113222647j:plain
Kotlin可愛い!

f:id:tommy_kw:20171113222708j:plain
「connehito」と記載されたネームプレート!

セッション

まず初めにKotlinの発音は、「コトリン」ではなくて「コットリン」なんですね!うまく伝えられないのでこちらは近日公開されるKotlinConfの動画をご確認ください!それでは特に気になった3つのセッションについて簡単に紹介します。

Opening Keynote

Kotlinの勢いとマルチプラットフォームがメインの内容で、KotlinConfアプリは大変参考になるサンプルでした。日頃Android開発しかしていない僕でもサーバサイドKotlinを触ってみたい!と思う内容でした。

  • Kotlin1.2 RCリリース
  • KotlinConfアプリについて
  • サーバサイド、Android、iOS全てKotlinで記述できる
  • iOSはKotlin/Nativeを用いることで利用できるがまだ初期段階
  • サーバサイドフレームワークはKtorが良さそう
  • コード共通化の手法としてcommonモジュールの登場
  • Android StudioでのKotlin利用率は17%
  • Kotlin Style Guideの登場

Two Stones, One Bird: Implementation Tradeoffs

コレクション操作やスコープ関数などの説明や適切な利用方法について言及した内容で、Map vs Sequenceが興味深く、Mapは中間結果を作成するのに対してSequenceは一時的なリストを生成しない。詳しくはKotlinイン・アクションを読むことをオススメします。

  • Array vs IntArray
  • Map vs Sequence
  • Nullability
  • Inline fun vs Custom getter
  • Delegate.notNull vs lateinit

How to Kontribute

Kotlinのコントリビュート方法についてのお話で、IDEのinspection、intentionについてのコントリビュート方法が細かく説明されていました。これを見るときっとコントリビュートしたい!って気持ちになるのではないでしょうか。

  • IDEのInspection、intentionについて
  • 対応したissueとそれの実装とテストコードの説明
  • 困った時はslackチャンネルの#kontributorsで質問しましょう
  • issueに関しては、youtrackを漁りましょう
  • githubでPR投げたら気長に待ちましょう。なぜならJetbrainsのメンバーは忙しいから
  • 日本のもくもく会についても言及

カンファレンス終了後にトライしたこと

カンファレンスはとても熱量が高く、特に影響を受けた「How to Kontribute」、「Two Stones, One Bird: Implementation Tradeoffs」セッションに関連した以下の2つにトライをしました。

僕もしらじさんのようにInspection、Intentionにコントリビュート!と思い、Kotlin issueを眺めていたのですが、対応できそうなものがなかったため上記のトライをしました。またカンファレンスの中でもKotlinイン・アクションが話題に上がっていたため、気になり読んでみましたが、とてもボリュームがあり高度なサンプルも多く勉強になりました。特にトリプルクオート文字列を用いることによってエスケープ不要となる正規表現とスター投影のMutableList<*>MutableList<Any?>の違いについて言及されて面白かったです。

まとめ

カンファレンス自体は本当に有名人が多く、Dmitry Jemerovさんと一緒に写真を撮ってもらったことが最高の思い出です。カンファレンス動画は近日公開されると思いますので詳細はそちらをご確認ください。いつか日本でもKotlinConfが開催されるといいですね!それでは楽しいKotlinライフを!

CakePHP3.5.5にアップデートしました!

f:id:itosho525:20170430222524j:plain

こんにちは。先日乃木坂46の東京ドーム公演に行ってきた@itoshoです。控えめに言って最高でしたし、こんなにも人を幸せに出来るアイドルって尊いなと思いました。

というわけで、少し時間が空いてしまいましたが、例によって、CakePHPのアップデートを行いましたので、内容を共有させていただきます!

続きを読む