giantneco’s blog

技術メモ

ドキュメント作成用の Makefile

ドキュメント用の Makefile

仕事で Markdown 形式のドキュメントをつくることになったので、 そのための Makefile を作った。 pdf 生成と redpen でのチェックをするようにしたい。

.PHONY: help clean redpen docs

.DEFAULT_GOAL = help

# define docker container for each targets
# container.redpen = ainoya/redpen
container.redpen = pandoc
container.docs = pandoc

all: docs

help:
   @grep -E '^[a-zA-Z%_-]+:.*?## .*$$' $(MAKEFILE_LIST) | sort | awk 'BEGIN {FS = ":.*?## "}; {printf "\033[36m%-30s\033[0m %s\n", $$1, $$2}'

docs: golang.pdf python.pdf ## generate pdf files

%.pdf: %.md
  pandoc $< --toc --from=gfm -t html5 -o $@

docker-%: ## run make in the Docker container (ex, 'make docker-docs' runs 'make docs' on the docker container)
  $(eval target = $(subst docker-,,$@))
  docker run -v `pwd`:/root/docs -it $(container.$(target)) $(option.$(target)) /bin/bash -c "cd /root/docs; make $(target)"

install-dev-mac: ## install developer's file
  brew install pandoc
  brew install redpen
  brew install graphviz
  brew install plantuml
  brew cask install wkhtmltopdf

redpen:
  redpen --conf redpen-conf.xml --format markdown --result-format plain2 -L ja *.md

clean:
  rm -rf *.pdf

ポイントとしては、自己文書化していることと Docker 上で走らせられるようにしてあることの 2 点がある。

自己文書化のアイディアはhttps://postd.cc/auto-documented-makefile/から持ってきている。 make help を実行すると次のように表示される。

docker-%                       run make in the Docker container (ex, 'make docker-docs' runs 'make docs' on the docker container)
docs                           generate pdf files
install-dev-mac                install developer's file

また docker- をルールの前に付けると、そのルールを Docker 上で実行する。 Docker で環境を共有するようにしたほうがいいかと思ったが、これについてはオーバースペックと言われた。

他にも色々出来そうだが、文章を書くことが優先事項なので後は手が空いたら改良したい。

社内基礎勉強会 #2

slides.com

社内で行った勉強会第2回はソフトウェアテストを扱った。

最初はテスト駆動開発だけを取り上げるつもりだったが、新人向けに内容を考えていくうちにこんな形になった。 おまけに時間切れでテスト駆動開発の話は全然できてない。

社内の事情として、新人はとりあえずテストの担当(場合によっては手動でテストし、テストケースはエクセル)をするということが多い。 それにも関わらず実際テストについて学ぶ機会はあまりないので、テストに関する知識は共有するべきだと思ってた。 なお周りに新人がいなくなって久しいので、新人の教育事情はちょっと認識と合ってないかもしれない。

テスト計画については、プロジェクトの三角形は自分の新人研修時に聞いた覚えがあったのでそれに倣って3つの要素からなるように書いてみた。 若干無理やり詰め込んだ感じはあるが、社内のワークフローを考えると間違ったことは言ってないと思う。

ソフトウェアテスト技法については、同値分割、境界値分析の他、ディシジョンテーブルについて詳しく解説を入れた。 というのも以前周囲の誰かが知っときゃよかった、と言ってたのを聞いていた気がするので。 組み合わ絵テストについては自分が詳しくないのであまりいい説明ができたとは思えない。入れなくても良かったかも。

テストコードについては、実践JUnit で紹介されていた FIRST が、覚えやすそうなのもあって説明に使うことにした。内容的にも非常に同意できるのもある。 アンチパターンは軽く紹介するくらいにとどめた。説明を書くのが間に合わなかったのもある。 「失敗しないテスト」については言及している書籍はなかったが、自分が何回かした失敗なのもあって加えることにした。テストファーストを紹介する導入にもなるかと思う。

テスト駆動開発についてはデモと合わせて説明するつもりだったが、ちょっと時間がたりず説明が足りてない。うーむ。

次回は並列・並行処理にをテーマにすることになった。

Docker Meetup Tokyo #26 に参加してきたメモ

Docker Meetup Tokyo #26

いま参加しているプロジェクトでは Docker を使っているのだが、自分は割と雰囲気で使っているところがあり、 また他のプロジェクトで Docker を使っているところは知らない。

ということで他のところでどういう使い方をしているのか知りたくて、ちょうどやってた Docker Meetup (https://dockerjp.connpass.com/event/106358/) に参加してきた。

スポンサーセッション (@algas)

負荷テストツール LOCUST の紹介。

LOCUST は分散して負荷をかけることができるツールで、同期実行の問題などを解決している。 Python から利用可能で、レポート機能もあり。ただしレコード機能はなく、プロトコルとしては http(s) しか対応していないことに注意。 Google Cloud から使うこともでき、簡単に構築できる。

負荷テストのときの注意点としては、ユーザ数は徐々に大きくし Hatch rate (= ユーザ増加率) は小さくすること。 一度に大きな負荷がかかることを避けることができる。

KubeCon China参加報告 (KubeCon China Recap) Kazuki Suda (@superbrothers)

中国で行われた KubeCon China のレポート。

普段は欧州やサンフランシスコで行われているが、中国でも開催されるようになった。 Alibaba などのコントリビュートは結構多いのにちょっと驚いた。 CNCF (クラウドネイティブな OSS 技術の推進を行う団体。k8s もこの団体がホスティングしている) の3つのサンドボックスプロジェクトが中国企業からの貢献で進められている。

キーノートでの話だと、k8s はすでに多くの企業で本番利用されていて、安心してビジネスに利用できる段階になっているとのこと。

あとセッションでは k8s をコントロールするのに k8s を使うという話が多かったらしい。これはどうなんだろ?わざわざ問題を作り出しているようにも思える。

いま話題のいろいろなコンテナランタイムを比較してみた (Comparison of several container runtimes) Kohei Tokunaga (@TokunagaKohei)

タイトルの通りいろいろなコンテナランタイムを主に性能面で比較した話。

コンテナには高レイヤと低レイヤの2種類がある。 高レイヤコンテナは kubelet からの指示で pod などを作るもので、 低レイヤコンテナは docker から直接作られるものと分類されている。

取り上げられたランタイムは:

  • 高レイヤ: containerd, cri-o, rkt
  • 低レイヤ: rnc, runsc(gVisor), runnc(nabla containers), kata-runtime (Kata containers)

まずコンテナにこれほど種類があるのは知らなかったので勉強になった。

Docker Swarm-mode Kohei Ota (@inductor)

あまり人気のない Docker の Swarm Mode の話。

NW 周りがしょぼい、Docker CE だと CNI (=Container Network Interface)使えないなど制限はあるものの、Docker を普段から使っていれば k8s に比べて Swarm の導入はかなり楽にできる。 なので大規模なコンテナの運用が必要でない場合には、 Swarm mode も検討してみるのがよいのでは、という話をしていた。

Docker v18.09の新機能の紹介 (Docker v18.09 new features) Akihiro Suda (@AkihiroSuda)

Docker 18.09 は 11/8 にリリースされ、BuildKit がの正式採用された。 BuildKit は新しい docker build のコマンドで、並列、早い、便利。

仕組みとして Dockerfile を DAG 付きの中間言語 LLB に変換して、並列実行可能な箇所を検出してくれるらしい。

また新しい Dockerfile のシンタックスが追加された。 これは Dockerfile 先頭に

# syntax = docker/dockefile:1.0-experimental

と書いておけば使えるようになり、RUN が次のようなオプションを持つようになる。

  • RUN --mount=type=cache : ビルド時にキャッシュを使う
  • RUN --mout=type=secret : 鍵を安全における
  • RUN --mout=type=ssh : クライアントの ssh-agent に接続

加えてリモートの Docker ホストに ssh 接続ができるようになった。環境変数を次のように設定する。

export DOCKER_HOST=ssh://user@host`

Docker が動いているホストに ssh で接続するのではなく、Docker 自体に接続するので手元の設定ファイルや認証情報が適用できる利点がある。

Multi-stage Docker Build @orisano

BuildKit 以前の話だが、Docker のビルドの話で、17.05 から導入された multi-stage build の使ったビルドパターンの紹介。 CI でどのようにしたらよいかがあったので、それも参考になった。

ただ BuildKit で結構変わるので、18.09 からまた事情が変わるようである。

感想

k8s の話もあって、インフラ視点寄りの話が多かった。 Docker ビルドの話から、他のところでの Docker の使い方が垣間見えたが、 現プロジェクトはやはりちょっとちがう使い方をしているように思える。 Docker イメージを作る際もスクリプトを通してなんとなくやってしまっているが、 他のところのやり方を聞くのはかなり参考になった。

18.09 の機能は良さそうだs使いたいが、出たばかりだしプロジェクトで使うのは先になりそうなのがちょっと残念。

あとやっぱり中国の勢いすごいな。中国語のドキュメントを読むのもそう遠くないのかも。 なんかまた中国でカンファレンスがあるんだったら近いし行ってみたい。

kubernetes に加えて Docker ももうちょっとまじめに使えるようにしておきたい。

社内基礎勉強会 #1

社内で行った勉強会の資料

slides.com

slides.com

他に社内で勉強会が走っているし、自分が勉強会に取り上げたいテーマで人が集まりそうなテーマが思いつなかった。 なので基礎勉強会という形で、再度初めから勉強し直したくはないが復習はしておきたいトピックで初心者にも受けが良さそうなものを紹介していく形の勉強会にした。 (どのみち人は集まらなかったが…)

Git の方は楽にスライド作れそうだし、現在のエンジニアは必須の知識だろうと思って最初のテーマに取り上げた。 楽に作れるかと思っていたが、「基礎」的な部分の定義がブレブレでどういうことを書くべきがかなり迷ってしまった。 Git について語りたいことは山ほどあったが、基礎的な話かというとそうでもない場合が多い。 結局結構スライドを削ることにした。脇道にそれるのはいけない。

次回についての要望がなかったので、独断でテスト駆動開発について話したいと思う。 TDD is dead と言われて久しいが、テストを先に書いたほうが良い場合は結構あるはずなので、うまいところ話しておきたい。

Scala 実践入門を読んだ

実践Scala入門

実践Scala入門

先月でた Scala 実践入門をようやく読んだ。

何か一つの言語(おそらく Java)を経験済みで Scala をこれから始めたいという人に勧めたい。

逆に Scala を超えて、関数型プログラミングアクターモデルなどは入門の範囲外ということであまり触れられておらず、 それらを学びたい人には向いていない。 そういう人は巻末の参考資料にある書籍から当たっていったほうがいいかも.

特に良かった点として、まず本のサイズをあげたい。 持ち運びが楽だし他の Scala 本の置き場所とおおよそ競合しない。 電子書籍にするにしても大きめの本だとコードとか見づらくなりがちなのでコンパクトなサイズは単純に嬉しい。 またこの分量で Scala でプログラミングを始めるのに必要な情報が揃うのは素晴らしいと思う。ビルドとテストのことも書いてあるし。 ただ短い分、若干説明が足りない部分もあったりするのがちょっと気になったか。

あと並行プログラミングに関する部分が薄かったのがちょっと残念。 最近流行りの言語では重要な機能なので、Scala が並行処理得意ですよというのがもっと書いてあっても良かったと思う。 そういうのは Akka でやっているので、おとなしくそちらを読んどけということなのかもしれない。

Kotlin Conf 2018 参加報告会 を見てきたメモ

10/15 と 10/19 に行われた Kotlin Conf 2018 の参加報告会を聞いてきた。

CA_kt の Kotlin Conf 2018 参加報告会

こちらは 10/15 に行われたサイバーエージェント主催の参加報告会。

Kotlin Conf 2018 Keynote Overview @satorufujiwara

Kotlin Conf 2018 Keynote を振り返る内容。

  • Kotlin Conf について
    • 今回で2回め
    • 参加者は 1300+
    • 今回はオランダ、アムステルダムで開催。前回はアメリカで開催だった
    • セッションはすべて動画で公開されている。見よう
    • 内容としてはコルーチン、マルチプラットフォーム、サーバサイドの話が多く、Android に関するセッションは 3 つ
  • キーノート
    • Kotlin 言語のデザイナー Andrey Brslav によるセッション
    • Be Pragmatic 実装者の考えをコードに落とし込めるようにしたい
      • Consicion < Readability
        • 簡潔さより読みやすさ
        • ボイラープレートは減らし、書いたコード全てに意味があるように
      • Expressiveness < Reuse
        • 表現力のためでなく、再利用のため
        • 標準ライブラリによく使われるパターンを入れている
      • Originality < Interoperability
        • 独自性<相互運用性
        • 他の言語にすでにある機能・知見を取り入れる
      • Soundness < Safety / Tooling
        • 言語的な堅牢さより、安全さ、ツールによるサポート
        • 静的型付き言語なのでツールも作りやすい
    • Kotlin 1.3
      • Coroutines -> stable
      • kotlin/native -> beta
      • build -> faster 75%
  • おすすめのセッション
    • coroutine exporing coroutines in kotlin
    • kotlin coroutines in practice
    • mutliplatform
    • kotlin/native concurrency
  • おすすめの Kotlin 教材

Kotlin 1.3 新機能 @_a_akira

  • 元になったセッションは New Type Inference and Related Language Features by Svetlana
  • Experimental features
    • Experimental features の目的は、アーリアダプターになるべく早く新しい機能を試してもらうこと
    • 使いかた
      • migration 1.2 to 1.3    * AndroidStudio で Tools > Kotlin > Enable migration option を選択
      • gradle
        • kotlin { experimental { coroutines 'enable' } }
      • 1.2 と 1.3 の import 違い
        • 1.2 import kotlinx.coroutines.experimental.*
        • 1.3 imoprt kotlinx.coroutines.*
    • ユーザ定義の experimental を作ることができるようになった
    • Contracts
      • Contract があると、そのコードが必ず一度だけ実行されることがコンパイラに保証される
        • run {} で変数を初期化するコードがコンパイルエラーにならなくなった
      • 自作もできる @ExperimentalContracts
    • New Type Inference
      • gradle で kotlin { experimental { newInference 'enable ' }}
      • SAM conversions
        • SAM = single abstract method の引数型が推論されるようになった
          • sequence<int> { yield 11, yield 42 }<int> を書かなくてもよい
      • Inference for call chains
      • Intersection types

優れたコードは小説のようか? @kaelaela31

  • 「よくかけたコード=小説」ということで文法に影響する Kotlin の機能の紹介
    • Kotlin Conf では表現について言及したセッションが多かった
    • Next Level DSLs
    • Writing The Next Great Kotlin Novel
  • Writing The Next Grewat Kotlin Novel
    • コードを自然言語のような書き方ができるとよい
      • 文脈、多様な表現, etc...
    • Kotlin では
      • 基本の語彙は英語、スコープが厳密、冗長な単語は省略、よりわかりやすいシンボルなどを使う
      • Object は名詞
      • Infix が便利
      • 受動態より能動態で書いた方が良い
        • food.isLikedBy(lisa) より lisa.likes(food)
      • Scope function を接続詞のように使うことができる
      • Kotln DSL
        • 内部DSL なのでコード汚染はあまりない

KotlinConf Report @takusemba

  • Best Practices for Unit Tesint in Kotlin, Phillipp Hauer から
    • MockK MockK<HogeFactory> verify() べんり メソッドがどのように呼ばれるかを検査できる
    • JUnit5
      • @TestInstance(TestInstance.Lifecycle.PER_CLASS)
        • テストごとにクラスを再生成できる
      • @Nested
        • テスト結果をグルーピングして IDE とかで見やすくなる
      • バッククォートでテスト名を記述できる
        • テスト結果などがかなり見やすくなる

JKUG の Kotlin Conf 2018 参加報告会

こちらは 10/19 に行われた Kotlin ユーザグループによる参加報告会。 会場は Line Cafe でとてもキレイな場所だった。

KotlinConf 2018 カンファレンス概要とトピックOverview @mhidaka

CA_kt のセッションとかぶるので、おすすめのセッションだけ。

  • おすすめのセッション
    • Keynote
    • Shaping your app's archiecture with kotlin and architecture components by Florina
    • Kotlin Coroutines in Practice by Roman Elizarov
      • コルーチンの使い方、Tips
    • Kotlin corutine bad practice and good practice

KotlinConf 2018 のワークショップに参加してきました あんざいゆき

今年の KotlinConf は初日が Workshop Day でした。 丸一日のワークショップに参加してきたのでその内容と様子についてお伝えします

ワークショップに参加してきた話

  • Kotlin Conf Workshop

    • 649 ユーロ 8万くらい ちょっと高い
    • 9:00 - 17:00
    • 朝食・昼食あり
    • 5 つのワークショップ
      • 変換プラグが C type で、穴にはめるタイプなので、ヨーロッパ行く人は注意
  • Acynchronous Programming with Kotlin

    • About
    • 内容
      • Asynchronous programming, introduction to coroutines ...
      • coroutine について一通り
    • サンプルプロジェクト
      • デスクトップアプリ
        • よく考えられたデモ
      • ちっさなTips
  • Kotiln での並行処理
    • thread
      • -> thread トップレベル関数でバックグラウンド実行
    • callbacks
      • -> Retrofitenqueue を利用
    • coroutine
      • thread の場合とそれほど変わらない書き方になる。シンプル
    • async, awaitAll
    • future
    • channel and actor

KotlinConf 2018 Android編 @hoshi_gaki

gyazo.com

  • Android Ssupenders, chris bane

    • coroutines on ndroid
    • jobs, scopes, reactivity
    • Reactivity
      • Rx のものは coroutine で置き換えられる
  • Shaping your app's archiecture with kotlin and architecture components, Florina

    • coroutine の why, where , how
      • why -> ease of learning, single/maybe/completale -> suspend fn
      • where -> ほぼ全部、どこでも使える
      • how to use -> retrofit2-kotlin-coroutines-adapter
    • Java とのつなぎ込み
      • suspend あ Continue を返すのでこれをどうにかしないといけない
      • callback 使うのが良さそう
    • Typing
      • これまで
        • data class UserId(val id: Long)
      • kotlin 1.3
        • inline class UserId(val id: Long)

「KotlinConf から見る、最近の Kotlin サーバーサイド事情」 @hktechno

gyazo.com

  • Server Side Kotlin
    • good: Null safety, tyep safety, functional programming, dsl
    • imporant: JVM 言語
  • Kotlin web framework
    • 選択肢はいくつかある: Ktor, http4k, spring boot
    • Spring Boot が多いっぽい
  • Which to use
    • Swagger, micrometer, zipkin を使う場合-> http4k, Spring Boot
    • coroutine を使う場合 -> ktor, spring boot(ただし unofficial)
      • Ktor は JetBrain 製なので coroutine もよく対応できている
  • Spring Boot を Kotlin で使うには
    • SpringFu, KoFu で Functional , DSL にできる(ただしincubating feature
    • annotation 対応の cofiguration ができる
      • annotation からは何が発生しているかが辿りにくい
  • API / Micoservices
    • RESTより GrapHQL(外部むけ), GRPC(内部向け), (Line ではThrift)がいいんじゃないか
    • REST bad: 型がない、スキーマが曖昧、パースにCPU使う
    • kubenetes kotlin DSL
    • 分散 Tracing の話が多かった
      • Opentracing , Zipkin
      • マイクロサービス使うなら導入しておきたい
  • Kotlin/Native
    • kotlin/Native はサーバサイドでもつかえるか
      • Concurrency 周りが難しそう
      • Ktor に期待, native をサポートしてほしい
      • Server-less な利用法では kotlin/jvm では startup time 問題があるので厳しい
        • サーバレスで使いたいなら GraalVM に期待したほうが良さそう

「Kotlinのユニットテスト ベストプラクティス」 @ngsw_taro

  • Best Practices for Unit Testing in kotlin @philipp_hauer
    • JUnit4
      • bad
        • boilerplate
        • @JvmStatic - kotlin には static がない
        • mutable な宣言
        • lateinit -> nullable の回避に使っているが煩わしい
        • mock -> mockit など java 用の mock は kotlin 向けでないのでツライ
        • kotlin 予約語と重複する関数があるので使いづらい
        • 読みにくいメソッド名
        • 貧弱なエラーメッセージ貧弱
        • テストごとにインスタンスを生成するので、static での初期化が必要なことがある
    • JUnit5 を使うのがベスト
      • @TestInstance
      • junit.jupiter.tesinstancelifecycyle.defaut = per_class
      • @Nested でグルーピング
      • バッククォートで読みやすいテスト名
  • おすすめライブラリ
    • どれもそこそこよい
    • おすすめは: JUnit5, mockK, AssertJ
  • mockK 注意
    • モックの生成は重い
    • 一度生成して clearMocks でクリアするのがよい
  • アサーション
    • データクラスのアサーション
      • フィールド毎でなく、データクラスをそのまま assertThat に渡すとよい。Assertion の結果が読みやすくなる

感想

  • 聞きに行く前は Android 関連の話が多いかなと思ってたが、Kotlin Conf ではサーバサイド向けの話が多かったらしい
  • コルーチンがあると並行処理に強くなるし、Kotlin/Native で起動時間も早くなるならコンテナ全盛の時流に乗れるかもしれないな、と思った次第
  • これから結構流行るんじゃないかとも思う
  • オランダのアムステルダムいいところらしい
    • 開催場所としては参加者に割と好評だった様子
    • サンフランシスコとかホテル代もどんどん高くなっているし、アメリカ以外での開催もこれから増えてもいいんじゃないかと思う

Visual Studio Code Extension 拡張を作成してみたメモ

最近 golang を書くのに Visual Studio Code を使っている。 で、使っていると当然不満も出てくるので拡張を書いてみることにした。 TypeScript は書き慣れていないのでその点の苦労はあったが、テンプレートや楽に試す環境ができているので割と楽に作ることができた。

一応欲しい機能は作れたのだが、その機能がすでにあることに気付いたのでとりあえず動くところまでやって終わりにしている。

準備

yoVisual Studio Code Extension のテンプレートがある。

yo を入れていない場合は次のコマンドでインストールする。

npm install -g yo generator-code

テンプレートの生成は次のようにする。

yo code

ウィザードに従って情報を入れればよい。

開発

テンプレート生成で作られたディレクトリに移動して、

code .

で workspace に拡張が入った状態で vscode を起動できる。

基本的には extension.ts をいじることになる。 拡張が読み込まれると activate が呼ばれるので、registerCommandでコマンドとして呼び出す関数を作ったり、イベントのサブスクリプトをしたりする。

デバッグする場合には、f5 で拡張を読み込んだ vscode を起動できる。

Ctrl+Shift+p で拡張で作ったコマンド(テンプレートのままだと Hello World)を指定して起動できる。

ハマったところ

拡張をつくるのは割とスムーズに行ったが、肝心の中身は慣れていない TypeScript を使う必要があったので苦労した。

やりたかったのは QuickPick を使って、ワークスペースのファイルを選択して開くということ。 (繰り返しになるが quickOpen というコマンドで完全に実現されている)

APIVisual Studio Code API Reference

このQuickPickを利用するには、showQuickPick に表示したい文字列のリストを渡すのだが、 リストをつくるのに時間がかかる場合にはThenableで包む。 非同期にやらないとエディタが泊まってしまうだろうし。

Thenable がちょっとハマった部分で、最初Tunableと読んでてググってもわからなかったり、 スペルミスに気付いて検索し直しても googleThen と解釈してやっぱりわからなかったりした。

一方、findFilesワークスペース中のファイルのリストをThenable<Uri[]>の形で得られる。 なので、showQuickPickに渡すにはThenable<Uri[]> -> Thenable<string[]>という変換ができればよいということで、これってファンクターだよねということで Thenable + functor で探したがそれっぽいのは見つからず‥

色々試してみると、.then(f: Uri[] -> string[]) とすればThenable<string>が得られることがわかった。

結局次のようなコードを書くことになった:

        var files = vscode.workspace.findFiles("*");
        vscode.window.showQuickPick(files.then((urls) => {
            return urls.map((url) => {
                return url.toString();
            });
        })).then((selectedItem) => {
            if (selectedItem) {
                var path = vscode.Uri.parse(selectedItem);
                vscode.workspace.openTextDocument(path).then(doc => {
                    vscode.window.showTextDocument(doc);
                })
            }
        });

変数の方とかは vscode 側が表示してくれていたので、実験しながらコードを書くのに非常に役に立った。 やっぱり型はあったほうがいい。

他、比較に === が必要だったりと、普段から JavaScript とか書いていないとしっくり部分があったが、 この点は vscode が優秀でちゃんと指摘してくれたのでなんとかなった。

参考