OmniAICreator/Qiita-1.07M huggingface dataset:
Retrofit-2.0.0beta2でのどハマりポイント(Retrofit.Builder#baseUrl)

SORACOM APIをRetrofit-2.0.0beta2で書く作業をしていたときにはまったポイントを記載します。Retrofit-1.x代とはコンセプトが違う部分なのでv2.0.0に移行するときは気をつけたほうがいいところでもあります。

☆今回はRetrofitとは何か、というのは説明しません。知りたい方は
http://square.github.io/retrofit/
やQiita内で投稿されているドキュメントなどをみてください。

# 今回私がはまったソース
私が最初Retrofit2.0.0-beta2を使って書いたSORACOM APIのクラスがこちらです。


```java:soracom.java
public final class Soracom {

    public static final Api API;

    static {
        Retrofit retrofit = new Retrofit.Builder()
                .baseUrl("https://api.soracom.io/v1" )
                .addConverterFactory(GsonConverterFactory.create())
                .build();
        API = retrofit.create(Api.class);
    }

    private Soracom() {
    }

    public interface Api {
        @POST("/auth" )
        Call<AuthInfo> auth(@Body AuthRequest authRequest);
    }
}
```

一見正しそうに見えますが、ダメでした。(ステータスコード500でかえってきます。)

# ダメな理由
上記のコードがダメな理由は`Retrofit.Builder#baseUrl`と`@POST(@GET)`でつくられるURLのルールに沿って作られていなかったからです。
実は、上記コードでは`https://api.soracom.io/auth` にアクセスしてしまいます。（`https://api.soracom.io/v1/auth`にアクセスするのが正しい。）

Retrofit2.0.0-beta2の仕様で
**・`Retrofit.Builder#baseUrl`に指定したURLの後ろに「/」が付いていない場合は強制的に「[schema]://[authority]」(上記でいうとschema=http, authrityはapi.soracom.io)という形を使ってアクセス先のURLを構築する。**
**・`@GET`,`@POST`の中に指定するURLの先頭に「/」が付いていると`baseUrl`で指定したURLの「[schema]://[authority]」のすぐ後ろにくっつけてしまう。**
となっています。
(http://www.github.comをみたいな形のURLを指定すれば何も問題ないんですけどね…)

# 解決策
なので解決策として
**・`Retrofit.Builder#baseUrl`に定めるURLは必ず「/」で終わるようにする。**
**・`@GET`,`@POST`の中に指定するURLは「/」で始めないようにする。**
を採択しました。
対応したコードは以下のようになります。

```java:soracom.java
public final class Soracom {

    public static final Api API;

    static {
        Retrofit retrofit = new Retrofit.Builder()
                .baseUrl("https://api.soracom.io/v1/" )
                .addConverterFactory(GsonConverterFactory.create())
                .build();
        API = retrofit.create(Api.class);
    }

    private Soracom() {
    }

    public interface Api {
        @POST("auth" )
        Call<AuthInfo> auth(@Body AuthRequest authRequest);
    }
}
```

こうすると想定したURLにきちんとアクセスしてくれるので問題が解決されました。


# まとめ

Retrofit2.0.0-beta2を使うときには`baseUrl`,`@GET`,`@POST`に指定するURLのフォーマットには十分に気をつけましょう！！具体的には

・`Retrofit.Builder#baseUrl`に定めるURLは必ず「/」で終わるようにする。
・`@GET`,`@POST`の中に指定するURLは「/」で始めないようにする。

をしていただければ問題ないと思います。

# 参考URL

http://inthecheesefactory.com/blog/retrofit-2.0/en
・このサイトの「New URL resolving concept. The same way as `<a href>`」というところに同じような内容が書いてあります。
virtualenvとvirtualenvwrapperでpython仮想環境構築

## 概要
python2.7を良く使う！けど急に、python3系を使わなければならない！
python2.7の環境は崩さずにpython3系使えるようにならない？
という時に便利なvirtualenvの覚え書き。

### virtualenvのインスコ
```
brew install pyenv-virtualenv
```

### virtualenvwrapperのインスコ
```
pip install virtualenvwrapper
```

### bash_profileなどに以下を追記して、sourceコマンドで実行。
```
if [ -f /usr/local/bin/virtualenvwrapper.sh ]; then
    export WORKON_HOME=$HOME/.virtualenvs
    source /usr/local/bin/virtualenvwrapper.sh
fi
```
※　virtualenvwrapper.shの場所は変わるかもしれないので、whichで確かめて適宜変えること。

### python3系のダウンロードと確認
```
pyenv install 3.3.6
pyenv versions
```

これで以下のようになる。

```
MacBook-Pro:~ hoge$ pyenv versions
* system
  3.3.6 (set by /Users/hoge/.pyenv/version)
```

python3.3.6は、/Users/hoge/.pyenv/shims/python3.3に格納される。

### python3.3環境を作る
```
mkvirtualenv --python=/Users/hoge/.pyenv/shims/python3.3 python3.3[任意の名前]

(python3.3)MacBook-Pro:~ hoge$ python -V
Python 3.3.6  # python3.3.6を利用可能。
(python3.3)MacBook-Pro:~ hoge$  # 前の()が上のコマンドで作った環境を使っていることを表す。
(python3.3)MacBook-Pro:~ hoge$ which python
/Users/hoge/.virtualenvs/python3.3/bin/python # mkvirtualenvで指定したパスとなっている。
(python3.3)yusuke-no-MacBook-Pro:~ hoge$ which pip
/Users/hoge/.virtualenvs/python3.3/bin/pip # pipもパスが変わる。
```

### ディアクティベート（使ってる環境から抜ける）とアクティベート（環境を変える）
```
deactivate       # ディアクティベート
workon python3.3 # アクティベート
```

これで、例えばpython3.3環境にてpipでPILLOWをインストールしたら3.3環境では使えるけど、ディアクティベートしたらPILLOWが使えない、などの環境切り分けが可能となる。
bitbucketのあれこれをslackに通知しよう

# slack Advent Calenderの18日目です

Adventカレンダー初参加です。ちょうど今日の欄が開いていたので参加させてもらいます。よろしくお願いします。

つい最近友達とアプリケーション開発で遊ぼうとなりまして、メッセージングはslack、遊びなのでソース管理は無料でプライベートリポジトリが使えるbitbucketを使用しています。

最近インターンさせていただいた会社がgithubの通知をガンガンslackに投げていました。これはbitbucketでもできるのでは?となり試してみました。思った以上に簡単だったので記事にしたいと思った次第です。

# 目次

* slack側の設定
* bitbucket側の設定

## slack側の設定

### AppDirectoryからbitbucketを追加

つい最近[App Directory](https://slack.com/apps)なるものができまして
そちらからbitbucketを探し出します。

検索窓に「bitbucket」と入力しbitbucketを選択します。
<img width="783" alt="スクリーンショット 2015-12-19 1.26.10.png" src="https://qiita-image-store.s3.amazonaws.com/0/20865/43c3c57d-960a-68f3-1e01-5f98cf8ae96c.png">

するとアプリの詳細画面がでてきますので、installをクリック。
<img width="1013" alt="2.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/20865/842f8140-3656-f5c4-8d1e-c449d66c9d85.jpeg">

### Appの設定

遷移した先のページでbitbucketの通知を配信するslackのchannelを選択します。
私は#developとか新しく作成してそこに作成したりしました。なんかそれっぽかったので。
<img width="993" alt="3.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/20865/822f8068-db19-dbfb-03ec-3ed6bad527a3.jpeg">

選択したらその下のボタンを選択します。
これでslack側の設定は完了です。遷移した先のページは、次のbitbucketに設定する方法が書かれています。これに従って設定していきます。
その説明の下に、WEBHOOK URLが記載されています。これはこのあとのbitbucketの設定で使用します。
<img width="938" alt="4.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/20865/b00e8d05-9034-2ea5-33be-788711c15325.jpeg">

## bitbucket側の設定

bitbucket側の設定を行います。
基本的には操作を通知したいレポジトリにWEBHOOKURLを設定する感じです。

### webhook設定ページに移動

まず、操作を通知したいレポジトリに移動し「Settings」のページに移動します。
<img width="270" alt="5.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/20865/7af7340c-354b-720a-1da8-4733d65b9d7c.jpeg">

遷移先のメニューの中にある「Webhooks」を選択します。
<img width="225" alt="6.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/20865/f6de9dd4-1e8a-975a-a29d-0a38c5e2d000.jpeg">

「Add webhook」を選択します。
<img width="638" alt="7.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/20865/e1d8b9e2-9dd2-5964-36c4-bbadff2f2a2b.jpeg">

### Webhookの設定

遷移したページに表示された項目を埋めていきます。

先ほどのslackで作成したWebhookURLはURLの部分にペーストします。
Triggersの部分はChoose ... を選択するとそれぞれのトリガーが表示されるので必要そうなものだけ選択します(私たちはあんまり頻度が高くなさそうなので、全部選択したいました。)以前はどうもpushのみしか対応していなかったようなんですが、かなり多くのフックがあるのでわーいって感じですね。

<img width="437" alt="8.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/20865/3f3eb52d-925e-1736-f6a0-a445e8a304f0.jpeg">
終わったらSaveしましょう。

以上でbitbucketの設定も終了です。さきほどNo hookとなっている部分に今設定したものが追加されると思います。
slackで作ったWebhookURLは、他のレポジトリにも同様の設定をすることで設定可能です。

## 実際の通知

実際に設定したレポジトリにpushをしてみると以下のようにslackに通知することが確認できました。
<img width="475" alt="9.jpg" src="https://qiita-image-store.s3.amazonaws.com/0/20865/6d695966-78c3-318a-737e-28664ce214ca.jpeg">

大成功ですねー。

# 最後に

自前でやると結構ちゃんとスクリプト書かなければ行けなかったりしますが、slackが用意しているものを利用するとスクリプトが掛けない人でも簡単にこういうものが作れてしまったりします。
slackへのpush通知は、リポジトリのWatcherにはメールなり通知なりがbitbucketで見れますが、slackで飛ばすことで普段の生活の流れで見れたり開発には関わってないけどslackの中にいる人に様子の一端を伝えられて良さそうです(もしかしたら一長一短ですが)。いやほんとう簡単。AppDirectoryも相当数揃ったから本当すごい楽だなーslackかわいいよslack。

以上で初Adbvent Calenderをおえたいと思いますーありがとうございます。

明日は Kinoppyd さんだそうですー。
ベンチャーが陥りがちなオレオレUXとそれを防ぐ方法について

はじめまして。manaboで働いているデザイナーの佐野彩といいます。
manaboは「スマホ家庭教師」サービスです。


![IMG_7319.JPG](https://qiita-image-store.s3.amazonaws.com/0/19185/5f3d19e0-e797-a26e-026b-f2b0998b74d1.jpeg)


manaboは先日行われたHeartCatch2015という試みに参加しました。
マーケティング、デザインのメンタリングをうけ、その中でアプリのUIを変更するなどの施作をうち、コンバージョンを2.5倍にあげるなどの結果を残す事が出来ました。

私たちは、heartcatchに参加する前は、何故コンバージョンが2.5倍にならなかったのでしょうか？




## Before

私たちのチームの課題は山積していました。

マーケティングに予算はなく、デザインもエンジニアに比べリソースは少なく、プロダクト開発の仮説も着実に検証されているとは言い辛い状態でした。

プロダクトの一貫した戦略がない状態でも仕事は忙しく、どんどん新機能は実装されていきました。

そんな中、開発ディレクター達は有料転換ユーザーを追いかけて彼らの特徴を掴んでいました。

しかし、足りない開発リソースを何処に割くかは必ずしもチーム全員の思い通りにはなりません。

それに、ある決定的な視点が足りませんでした。


manaboは何か。どう人を幸せにするのか。では何をすべきか。



## HeartCatch2015に参加！

私達は幸運でした。
heartcatch2015とは
「スタートアップが一流のマーケターとデザイナーのメンタリングをうけ、どう変わったかを発表」するイベント。
まさにこれが欲しかった、鴨がネギをしょってやって来たというやつです :hatched_chick: 


### マーケティングも、デザインも、ある意味スポ根

マーケティングのメンタリングは、徹底的に棚卸しから始まりました。その時にデザインのメンターも同席し、アプリからセールスのトークまで、ユーザーとの接点で見かけられる問題点を指摘されました。

そして数々のユーザーインタビュー、たくさんの宿題、何回もの発散と収束(つまり夜遅くまでの会議)を経て、一つの結論まで辿り着きました。

マーケティング側でポジショニングの結論を出す傍で、デザイン側は競合のデザインの調査や、カスタマージャーニーマップ作成など既存の穴を見つけ出す作業を経て、確からしい結論を導き出していました。
ここまででも両メンターの素晴らしい経験値がなければ、到底たどり着けなかったでしょう。

しかし、まだ折り返し地点でしかありません。
どうするか決まったら、今度は実装し、計測まで行かなくてはいけません。

時間をかけずに、アウトプットの質を上げるというのも難しい課題です。
高いお金を払い、素晴らしい制作会社に時間をかけて外注している余裕はありません。
そこでも、デザインのメンターから数々の学びがありました。
その一つがこちらです。

### ベンチャーのデザインの質を上げる一つのアドバイス

(もちろんこれが全てではないですが、するとしないでは全然変わります)

 - スタディをしよう。素早く、確実に。

スタディというのは、デザインの方向性を探る為、手を動かして作ってみる事です。完成度は60%を目標にしましょう。
最初に競合のデザインをリサーチした事がここで生きます。
たとえマーケティングやユーザー調査でで結論がひっくり返ったとしても、スタディをした事で柔軟に対応する事が出来るのです。

また、UI改善もチーム全員でワイヤーフレームを描き、長所短所、予測される結果について明確にしながら筋の良さそうなものを実装するという方法で短期間で効果を出せたのだと思います。





## After

当日の発表について書かれた記事です。

http://thebridge.jp/2015/12/heart-catch-2015-round-up

結果は、前述したアプリUIの改善だけではなく、ターゲットユーザーの絞り込み、それにふさわしいデザインのトーンマナーの決定、ランディングページの作成など沢山のアウトプットを残す事が出来ました。

もちろん、ここから最適化していき、仮説を検証していきます。



### 振り返って

ここまでお読みいただきありがとうございます。
ユーザー調査や、プロダクトの本質の抽出に余念のないチームにいる方はこの記事はあまり役に立たないものかもしれません。

小さい機動性の高いチームだから陥りがちな、ほんの数日間でも立ち止まって濃密に考える時間がないままにしてしまうことが、UX／UI、ひいてはコンバージョンに非常に関係してくるという事がおわかり頂けたのではないでしょうか。


以上、HeartCatch2015に参加して私たちのマインドがどう変わったか、参加した側からの感想をお伝えしましたが、いかがでしたでしょうか。

正しくものを作る事が結局近道なのだなぁ、と強烈に感じることが出来たプログラムでした。



そしてこの記事を、素晴らしいマーケター彌野さんと素晴らしいデザイナー深津さんに、情熱の塊HeartCatch西村さんに、また社内で一番苦労して頑張ったディレクターとマーケター両氏に捧げます。



## 最後に

manaboはカスタマーサポート、インフラエンジニアなどたくさんの職種を募集しています！
詳しくは是非↓から！
https://mana.bo/corp/recruit/


HeartCatch2015の記事はこちら
http://thebridge.jp/2015/12/heart-catch-2015-round-up

HeartCatchオフィシャルサイトはこちら
http://events.heartcatch.me/

THE GUILD
http://theguild.jp/

B&C | Bloom & Co

Bloom & Co.
http://www.bloom-and-co.com/
CentOSの初期設定

#概要#
Mac OSXにvagrantを用いてCentOSを導入し、ローカル開発環境を構築した。
今回はCentOSの初期設定について記述する。

##一般ユーザの追加##

```lang:コマンド
# useradd masaki(任意) 
```

パスワードの設定

```lang:コマンド
# passwd mask
新しいパスワード：****
新しいパスワードを再入力してください：****
passwd: 全ての認証トークンが正しく更新できました。
```

##rootになれるユーザを管理者のみに##

```lang:コマンド
# usermod -G wheel mask
```

/etc/pam.d/suを編集し、

```lang:/etc/pa.d/su
#auth    required    pam_wheel.so use_uid
```

のコメントを解除する。

##パッケージ管理システムの設定##

####yum-cronのインストール####

```lang:コマンド
# yum -y install yum-cron
```

####パッケージのダウンロード＆インストールを自動化####
yum-cron.confを編集し、パッケージのダウンロードとアップロードを自動に行うようにする。

```lang:コマンド
# vi /etc/yum/yum-cron.conf
apply_updates = yes
# systemctl start yum-cron
# systemctl enable yum-cron
```

設定は以上で完了し、システムを再起動する

```lang:コマンド
# reboot
```

なお、上記の設定は私が必要と考えたものであり、個人の用途によって設定項目は変わるので注意してください。
Smarty 3.1.28 にアップグレードしたら、エラーになってしまう！


Smarty 3.1.28にアップグレートしたら、意外なところで問題があったので共有します。
3.1.27 では全く問題なかったのですが、こんなマイナーバージョン・アップで問題が…

問題の部分というのは、`generator` をテンプレート変数に `assign` した場合に起こりました。
問題を再現するミニマムコードは以下のようになります。

```php:index.php
<?php
require_once '/usr/share/php/Smarty/Smarty.class.php';

$smarty = new Smarty();
$smarty->setTemplateDir('../../templates')
	->setCompileDir('../../templates_c')
	->addPluginsDir('../../smarty_plugins')
	->setCacheDir('../../cache')
	->setConfigDir('../../smartyconfigs');

function gen()
{
	$arrSample = [
		0 => 'a'
		, 1 => 'b'
		, 2 => 'c'
		, 3 => 'd'
	];

	foreach ($arrSample as $val) {
		yield $val;
	}
}

$smarty->assign('generator', gen());
$smarty->display('sandbox/index.tpl');
```

```html:index.tpl
<!DOCTYPE HTML>
<html lang="ja-JP">
	<head>
		<meta charset="UTF-8">
		<meta name="robots" content="NOINDEX,NOFOLLOW" />
		<meta http-equiv="content-language" content="ja" />
		<meta content='width=device-width, initial-scale=1, maximum-scale=1, user-scalable=no' name='viewport' />
		<link rel="icon" href="favicon.ico" />
		<link href="/css/bootstrap.min.css" rel="stylesheet" type="text/css" />
		<link href="https://maxcdn.bootstrapcdn.com/font-awesome/4.4.0/css/font-awesome.min.css" rel="stylesheet" />
		<link href="https://code.ionicframework.com/ionicons/2.0.1/css/ionicons.min.css" rel="stylesheet" type="text/css" />
		<title></title>
	</head>
	<body>
		<div class="container">
			{foreach $generator as $val}
				{$val}
			{/foreach}
		</div>
		<script src="https://code.jquery.com/jquery-2.1.4.min.js"></script>
		<script src="https://code.jquery.com/ui/1.11.4/jquery-ui.min.js"></script>
		<script src="/js/bootstrap.min.js"></script>
	</body>
</html>
```

再現するエラーはこちら。

![スクリーンショット 2015-12-19 2.02.35.png](https://qiita-image-store.s3.amazonaws.com/0/46841/f43b6360-e3a5-f4ae-9e04-06866a6e44e7.png "スクリーンショット 2015-12-19 2.02.35.png")

テンプレートの展開時にどうもforeach が2回回ってしまう様子…
autocomplete-mode で C-n, C-p で上下の選択肢に移動する

autocomplete の際、TABを連打していると、欲しい選択肢を通り過ぎてしまう場合がよくある。デフォルトのキーバインドでは、矢印キーの上下で、選択肢の上下移動ができたが、普段のカーソル移動に矢印キーを使わないのと同じ理由で、この場合にもそれを行いたくない。

探した結果、次の設定で改善できる。

```el:init.el
(define-key ac-completing-map (kbd "C-n") 'ac-next)
(define-key ac-completing-map (kbd "C-p") 'ac-previous)
```

ソース: http://dev.ariel-networks.com/wp/documents/aritcles/emacs/part9
仕様を決定するための実験してエビデンスを残そう。

ソフトウェアを開発するとき、どうしてそのような設計にするのか、
どうしてそのアルゴリズムを使うのか
仕様を決めるための根拠が必要なことがある。

その場合、実装したアルゴリズムが良好な結果になっているのかを、グラフでチェックすることが多い。
複数の手法の中からその手法を選択する理由を示す必要がある。
計算して一見それっぽい値がでているからOKとするわけにはいかない。
アルゴリズムが必要な精度を満たしているかの確認は、そのコードを書くことよりももっと手間がかかる。
そのエビデンスを示すためのコードとデータとを、部署の別な人が再現実験をできるように部署で共有しよう。
PDF出力時に半角スペースが改行になってしまう問題

PDF出力すると予期せぬviewの崩れが起きるもので、今回もその一つです。
PDFはやっかいです...
## 開発環境
- rails4.2
- wicked_pdf
- wkhtmltopdf-binary-edge

railsエンジニアがhtmlで普段表示しているページをPDF化するときの王道の組み合わせだと思います。

最近まではChart.js用にwkhtmltopdf-binary-11を使っていたのですが、edgeでもChart.jsはきちんと表示できるので移行しました。updateは大切です。

## 発生した問題
ユーザー名を本名フルネームで出力するときに、last nameとfirst nameの間に半角スペースを空けると思います。

例：<b>Taro Yamada</b>

これをPDF出力してみたところ

<b>Taro
Yamada</b>

となってしまったわけです。ちなみに、wicked_pdfはPDF化したページのweb版も見れるので、そちらを確認してみると改行されずに
<b>Taro Yamada</b>
になっているわけです。

### 原因
調べてみましたが、根本的な理由は見当たりませんでした。一言でまとめてしまえば、PDF出力を担うwkhtmltopdf-binary-edgeの仕様バグと言えると思いますが、関連する投稿をみつけたので、それだけ紹介しておきます。

[PDF出力時にマルチバイトを含む行が半角スペース箇所で改行される](https://www.ricksoft.jp/qa/questions/3866749/pdf)

このページの質問で出ているソフトウェアは今回のものとは全く別物ですが、関連はあると思います。

僕がこの質問を見て思ったのは、wkhtmltopdf-binary-edgeがマルチバイト文字とシングルバイト文字を変換するアルゴリズムが原因となっているのではないかと考えています。特に、シングルバイト文字だけのときと、マルチバイト文字と一緒になったときのアルゴリズムが今回のような事象を引き起こしているのだと思います（まぁ、binaryの蓋を開けて中を覗いたわけではないので、想像に過ぎませんが）。
<br>

ちなみに、マルチバイト文字とは何？となる人もいると思いますので、そういった方はこちら→ [マルチバイト文字を扱う際に気をつけること
](http://qiita.com/mpyw/items/a8dba1b80fe68523b8eb)


## 解決方法
それでは解決方法はどうするかといえば、<b>spanタグで囲う</b>につきます。

```
<div>
'Taro'<span>' '</span>'Yamada'
</div>
```

これでPDFのときに、<b>Taro Yamada</b>と表示してくれるようになります。

もちろん、last nameとfirst nameをそれぞれdivで囲ってfloatとmarginで調整する方法もありだと思います。

## まとめ
文字コードというのはパソコンを扱う上で、最も基礎になることの一つだと思います。その重要性を改めて認識させられました。
そして、<b>日本以外の国にいればそもそも全角スペースがない</b>ということにも途中で気づかされました。
当たり前ですが、日本人向けにこれだけ対応が進んで、様々な環境が整っているのって、随分幸せなことなのですね。

## 参考サイト
https://www.ricksoft.jp/qa/questions/3866749/pdf
http://qiita.com/mpyw/items/a8dba1b80fe68523b8eb
ローカル開発環境（CentOS）の各種パッケージインストール


#概要#
vagrantを用いて、構築したローカル開発環境の設定を行う


#コマンド#
以下は、MacのTerminalを用いて作業を行う

###CentOSの起動###
```lang:コマンド
$ vagrant ssh
```

今回は
・git
・Java
・Apache
・PHP
・MariaDB
・Ruby
のインストールを行う。

####git####
```lang:Download
$ sudo yum -y install git
```

####Java8のダウンロード####
```lang:Download
$ wget --no-check-certificate --no-cookies --header "Cookie: oraclelicense=accept-securebackup-cookie" "http://download.oracle.com/otn-pub/java/jdk/8u45-b14/jdk-8u45-linux-x64.tar.gz"
```

ダウンロードしたファイルは
```
/home/vagrant/
```
にあるため、```/usr/local/java/```に移動し解答する。

```lang:コマンド
# mv /home/vagrant/jdk-8u45-linux-x64.tar.gz /usr/local/java/
# tar xvf idk-8u45-linux-x64.tar.gz
```

シンボリックリンクを当てておく

```lang:コマンド
# ln -s jdk1.8.0_45 latest
```

環境設定にJAVA_HOMEを設定
/etc/profile.dにjavaenv.shとjavaenv.cshを作成

```lang:javaenv.sh
export JAVA_HOME=/usr/local/java/latest
export PATH=$PATH:$JAVA_HOME/bin
```

```lang:javaenv.csh
setenv JAVA_HOME=/usr/local/java/latest
setenv PATH=$PATH:$JAVA_HOME/bin
```

####Apache／PHP####
ApacheおよびPHPのインストール

```lang:Install
# yum -y install http
# yum -y install php php-mbstring
```


####MariaDB####

```lang:Install
# yum -y install mariadb-server
```

MariaDB設定を行うのに、設定ファイルの編集

```lang:server.cf
[mysqld]
character-set-server = utf8
```

上記を追加する。
MariaDBを起動し、自動起動設定を行う。

```lang:コマンド
# systemctl start mariadb
# systemctl enable mariadb
```

####Ruby####
Rubyおよび各種必要なパッケージのインストール

```lang:Install
$ sudo yum -y install ruby ruby-devel libxml2-devel libxslt-devel
```

各種インストールはこれで完了である。
その他、設定は各自必要な仕様で行ってください。
Javaのサブセットコンパイラの作成

この記事は[言語実装 Advent Calendar 2015](http://qiita.com/advent-calendar/2015/lang_dev) と [ML Advent Calendar 2015](http://www.adventar.org/calendars/848)の19日目の記事です。

今日はJavaのサブセットのコンパイラCamljoos0<a name="r1"></a>[[1]](#1)について書くザマス。
joos0<a name="r2"></a>[[2]](#2)というおデンマークはオーフス大学の授業用に作成された由緒正しいJavaのサブセット言語があったのでザマス。joos0はおフランス製のOCamlで書かれていたザマス。
![オーフス大学経路1](https://qiita-image-store.s3.amazonaws.com/0/25489/62ef47bf-6b75-bb53-0256-3021ee854df5.png)

![スクリーンショット 2015-12-02 22.04.55.png](https://qiita-image-store.s3.amazonaws.com/0/25489/f2e352ce-bf64-a857-a087-a191bab68113.png)
![スクリーンショット 2015-12-02 22.06.30.png](https://qiita-image-store.s3.amazonaws.com/0/25489/a92ef526-3bae-597b-b92e-49ba157a567a.png)

日本から飛行機でたった13時間25分で着いて、その後、車か電車で1時間ってトコロザマス。ほとんどまっすぐ電車が通ってて便利ザマスね。

![オーフス大学経路2](https://qiita-image-store.s3.amazonaws.com/0/25489/e0d46038-426f-b730-fe3f-cfd350179257.png)

ミーも一度、おデンマークに行って寿司を食った覚えがあるザマス。

https://web.archive.org/web/20020613131007/http://web500.com/tempfiles/92.asp?funcpostinglink=157&funcpostingID=1&funcextensionID=515

探したらコペンハーゲンのここらへんに行ったみたいザマス。

Nansensgade 19, Floors 7 and 8
1366 Copenhagen K

![スクリーンショット 2015-12-02 22.10.46.png](https://qiita-image-store.s3.amazonaws.com/0/25489/472419f3-b2a3-2259-bddd-febae2d08eaf.png)

完全にネタになってるザマスね。もうミーは疲れたザマス。本題に移るザマス。

## camljoos0

joos0はお作法的に、どうもJava等のお作法で作られていて長ったらしかったザマス。そこでミーの登場でザマス。ミーは MinCaml的に書き換えてjoos0をたった1行に書き換えてやったザマス。いや、1行は嘘ザマス。物の例えザマス。でもかなり短くなった事は間違いないザマス。


そういう事でですね、joos0っていう言語があったのですけど、Javaっぽい作りだったので、4000行のコードを2600行位まで書き換える事が出来ました。MinCamlのように書き換えたらかなり短く出来ましたっていう話でした。

ScalaをOCamlで描きたい場合にもしかしたら参考になるかもしれないし、ならないかもしれません。
MokkosuをOCamlに移植したらスッキリしそうだなぁなんて思う今日この頃です。

## 参考文献

- [[1]](#r1) Camljoos0
    <https://github.com/hsk/camljoos0>

- [[2]](#r2) joos 0 language
    <http://users-cs.au.dk/mis/dOvs/>

- [[3]](#r3) オーフス大学
    <http://www.au.dk/>
プログラマとそうでない人を見分ける略語／単語集

この記事はジーズアカデミーAdvent Calendar 2015の6日目に後から足しました。

---

プログラマとそうでない人を見分けるには、
以下の略語／単語を示して反応をチェックする方法がある。

| ことば | A.プログラマ | B.そうでない人 |
|:-----------|:------------:|:------------:|
| DB       |     データベース |     ドラゴンボール     |
|JSon|データ形式|ホッケーマスクかぶってるキャラ or 厚切り|
|LL|軽量プログラミング言語|服のサイズ|
| PHP         |          プログラミング言語 |      出版社     |
| PR       |  プルリクエスト |     プレスリリース     |
| Swift    |      プログラミング言語 |    車種 or 歌手    |
|キャッシュ|メモリ内のデータ|現金|
|ターミナル| Mac付属ソフト| 飛行機やバスの発着所|
|ホスト| コンピュータ| 職業|

私自身ひよっこプログラマなので、↑に書いたのもどこか違うかもしれない。
その場合は生暖かく見守りつつ、コメントください。
未経験からプログラミング始めてみて

ジーズ２期生で入学して、現在は３期生のチューターとして授業にも参加させていただいておりますshiinoです。
自分もジーズアカデミーでプログラミングを始めたのですが、３期生の授業に参加させていただくにあたりもっと努力しなければ！！
と毎週刺激を受けております。

<h2>ジーズアカデミー２期スタート〜</h2>
みんな仕事もあってわざわざ週末に授業受けに来るって決してラクな事じゃないと思うんだけど、毎週限られた時間の中で面白いものを作ってくる同期の皆に毎回驚かされていた。
提出前日や当日は明け方くらいまでコード書いてたりしてしんどい時があっても、他の人の課題の発表を見てたり、自分が発表できたりすると楽しくて、時に全然わからないことに遭遇しても先生やチューターや同期の仲間と一緒に解決できるから毎回の授業がすごく楽しみだった。
未経験者も経験者もいろんな人がいて、教え合って面白いものを作ろうとするエネルギーがあるから、3~4ヶ月でアプリ制作の基礎的なところが身につくんだと思う。(独学だとたぶん挫折していた)

[授業期間中の反省点]
・勉強会に行ってみる
ITの勉強会は都内では毎日のようにどこかでやっているので、HTML5、Javascript、PHPなど言語別の物もあれば、メンターのびすけさんが主催されているIoT縛りの勉強会(IoTLT)など、自分の知らない技術について知ることができたり、注目の技術について知る機会にもなり、授業とはまた違う刺激をたくさん受ける事ができるのでオススメです！


・課題は、提出後が面白い
課題提出が一旦間に合ったら、安心して気を抜いてしまう事も。
ぜひ次の授業までの時間を使ってプラスアルファで勉強した事を実装したり、周りを驚かすモノをつくったほうがいい。<strong>みんなびっくりさせてやる！</strong>っていう気持ちが出てくると、勉強してコードを書くのはすごく楽しいです。

・時々、誰かと一緒に勉強する
わからない事にぶつかった時、１人だと解決できなかったり、できてもすごく時間がかかってしまうこともある。
授業以外でも同じように複数人で勉強しているとすぐに解決できたり、モチベーションを高めたり、どんな本を使ってるかなどの情報交換などもできるので、こういう機会は大事だなってとても思います。
卒業制作期間になると、同期メンバーにあまり会わなくなるので、意識的に集まる機会を作りたいです。年が明けたらやりたいですね！！
　
<h2>卒業制作期間に向けて</h2>
授業のことに必死で、あまり何を作るか考えてこなかった自分は出遅れてます。
まだ決まってない人は、人気アプリを使用しながら、なぜ人気なのか？どういう風に作られているのか？自分ならどうやって作るか？といったことを考えてみながら、企画を早めに考えておきましょう。

書いてるうちにまたテンションが上がってきたので、気を引き締めて卒業制作に挑みます！

長くなりましたが、明日はジーズ忘年会ですね！！
楽しみですね！！
1行もコードを書かずに、キーボードが表示されたときにTextFieldが隠れないようにする

# テーマ
テキストフィールドをタップすると
キーボードが隠れてしまうことがありますよね。

一行も書かずに、これを解決します。

# ゴール
下記のように、テキストフィールドをタップすると、
画面全体がスクロールし、テキストフィールドが隠れないようにします。

![sample.gif](https://qiita-image-store.s3.amazonaws.com/0/71694/3e81fa67-390f-54f5-b7ec-4671c0686493.gif)

# 答えは、
TPKeyboardAvoidingというライブラリを使用します。

https://github.com/michaeltyson/TPKeyboardAvoiding

フォーカスが外れたときも、キーボードを消してくれます。
NSNotificationCenterとか使わなくてもOKです。

# 実装手順
1. ライブラリを追加する。
2. 画面のベースにUIScrollViewを設置する。
3. UIScrollViewのカスタムクラスに「TPKeyboardAvoidingScrollView」を指定する。
4. テキストフィールドを設置する。

それでは、やってみます。

# 1. ライブラリを追加する。
残念ながら、CarthageやCocoa Podsに対応していないので、
ダウンロードして、プロジェクトに追加してください。

# 2. 画面のベースにUIScrollViewを設置する。
ソースコードとのひも付けも不要です。

<img width="361" alt="スクリーンショット 2015-12-19 0.34.32.png" src="https://qiita-image-store.s3.amazonaws.com/0/71694/81aed53b-32c6-9331-1769-e4b850f096a7.png">

# 3. UIScrollViewのカスタムクラスに「TPKeyboardAvoidingScrollView」を指定する。
<img width="347" alt="スクリーンショット 2015-12-19 0.34.45.png" src="https://qiita-image-store.s3.amazonaws.com/0/71694/ac1d00ad-298a-35eb-0aa8-03fa50760448.png">

# 4. テキストフィールドを設置する。
あえて、キーボードで隠れそうな位置に、UITextFieldを設置する。

<img width="361" alt="スクリーンショット 2015-12-19 0.35.05.png" src="https://qiita-image-store.s3.amazonaws.com/0/71694/f6281868-fbe5-844f-7fe5-9496b995c81a.png">

以上です。

# まとめ
簡単ですね。
ぜひ、ご活用ください。
Android StudioでlibGDX入門

libGDXとは
--  
libGDXとはゲーム開発を行うためのフレームワークです。  
libGDXを使うことのメリットはJavaで開発できることとクロスプラットフォームで開発できることです。  
ほかにも2Dゲームだけではなく3Dゲームもサポートしていることと、オープンソースであること等が挙げられます。  
  
同じスマホアプリ開発フレームワークのライバルであるUnityやCocos2d-Xと比べると日本語の情報が圧倒的に少ないですが、開発環境構築は簡単です。  
今回はlibGDXをダウンロードして、Androidプロジェクトにインポートするところまでをメモしていきます。  

セットアップ用実行ファイルをダウンロードする
--  
<a href="https://libgdx.badlogicgames.com/">libGDX公式サイト</a>へアクセスし`Download` > `Download Setup App`の順にクリック。  
`gdx-setup.jar`というファイルがダウンロードされます。  

プロジェクトを作成  
--
ダウンロードしたファイル`gdx-setup.jar`をダブルクリックするとプロジェクト作成画面が立ち上がります。  
今回はAndroidアプリを作成するので`Sub Projects`にはAndroidのみにチェックを入れる。  
そのほかの欄はデフォルトのまま`Generate`をクリックしたらエラーが出ました。  
原因は`Android SDK`のインストール場所が違っていたようです。  
Android SDKのインストール場所がわからず、ここで30分程度ハマってしまいましたがAndroid studioを起動して`Configure` > `SDK Manager` > `Android Location`の欄をコピペで解決。  
他にもAndroidビルドツールに関するメッセージやAndroid APIに関するメーッセージが英語で出て来る場合があるようですが、大抵の場合は「はい」をクリック。  
  
ビルドには数分かかるので気長に待ちましょう。  

[![https://gyazo.com/bc073cdd6c69cdeb848a18caab39458a](https://i.gyazo.com/bc073cdd6c69cdeb848a18caab39458a.png)](https://gyazo.com/bc073cdd6c69cdeb848a18caab39458a)  
この画面が出たらビルド成功です。  

Android Studioでプロジェクトを開く  
-
Android Srudioを起動し`Import project(Eclipse ADT,Gradle,etc.)`をクリック。  
先ほど作成したプロジェクト内の`build.gradle`を選択し`OK`をクリック。  
インポートには数分かかるのでここでも気長に待ちましょう。  
インポートされたら早速、実行してみましょう。  
Android端末を接続するかエミュレータを起動し実行ボタンをクリック。  
[![https://gyazo.com/a4ece1c13d441160cb8ff356c19e2e4c](https://i.gyazo.com/a4ece1c13d441160cb8ff356c19e2e4c.png)](https://gyazo.com/a4ece1c13d441160cb8ff356c19e2e4c)  
お疲れ様でした。
デザインパターン #1 〜Iterator〜

デザインパターン #1 〜Iterator〜

本当に今更ですがデザインパターンを紹介していきます。
記念すべき第一回目は **Iteratorパターン** です。


## 概要
「Iterate」という英単語は、何かを「繰返す」という意味です。
「Iterator パターン」とは, ある集合体の要素一つ一つに, 順次アクセスする方法を提供するパターンです。

## サンプルコード
では簡単なサンプルをJavaで作っていきます。

```java:Aggregate.java
public interface Aggregate {
    public abstract Iterator iterator();
}
```

```java:Book.java
public class Book {
    private String name = null;
    public Book(String name) {
        this.name = name;
    }
    public String getName() {
        return name;
    }
}
```

```java:Iterator.java
public interface Iterator {
    public abstract boolean hasNext();
    public abstract Object next();
}
```

```java:BookShelf.java
import java.util.ArrayList;
import java.util.List;

public class BookShelf implements Aggregate {
    private List<Book> books = new ArrayList<Book>();

    public Book getBookAt(int index) {
        return books.get(index);
    }

    public void appendBook(Book book) {
        this.books.add(book);
    }

    public int size() {
        return this.books.size();
    }

    @Override
    public Iterator iterator() {
        return new BookShelfIterator(this);
    }
}
```

```java:BookShelfIterator.java
public class BookShelfIterator implements Iterator {

    private BookShelf bookShlef;
    private int index;

    public BookShelfIterator(BookShelf bookShelf) {
        this.bookShlef = bookShelf;
        this.index = 0;

    }
    @Override
    public boolean hasNext() {
        if (index < this.bookShlef.size()) {
            return true;
        } else {
            return false;
        }
    }

    @Override
    public Object next() {
        Book book = bookShlef.getBookAt(this.index);
        this.index++;
        return book;
    }

}
```

```java:Main.java
public class Main {
    public static void main(String[] args) {
        BookShelf bookShelf = new BookShelf();
        bookShelf.appendBook(new Book("80 days"));
        bookShelf.appendBook(new Book("81 days"));
        bookShelf.appendBook(new Book("82 days"));
        bookShelf.appendBook(new Book("83 days"));

        Iterator it = bookShelf.iterator();

        while(it.hasNext()) {
            Book book = (Book)it.next();
            System.out.println(book.getName());
        }
    }
}
```

結果

```
80 days
81 days
82 days
83 days

Process finished with exit code 0
```
fluentdのplugin 「in_kinesis」を作ってみた

#はじめに
とあるきっかけで、AWS kinesisからlogを取得する、fluentdのInput Plugin、
<b>in_kinesis</b> なるものを作ったので、その話を書きます。

ちなみに[【in_kinesis】はこちら](https://github.com/yusukeyamatani/fluent-plugin-in-kinesis)になります。
[gem版はこちら](https://rubygems.org/gems/fluent-plugin-in-kinesis/versions/0.0.1)になります。

#きっかけ
今回、なぜPluginを作ったかというと、
会社で新たにリアルタイムバトルを導入する事になり、そのlog周りに携わる事になったのがきっかけでした。
そこで、今まで通りのアーキテクチャで良いのかどうかの検討から行う事にしました。
その時のlogの要件はこんな感じでした。

* とにかくログがBigQueryに入れば良い。
* ログの数の上限値が不明

fluentdのBigQuery pluginが有るからBigQueryに入れるのは簡単だね！
と思っていたのですが、
ここで問題となるのが「ログの数の上限値が不明」<b>←これでした!!</b>

* もし秒間数千件とかだったら、fluentd１台でさばけるの？
 * 無理そう...

* fluentdServerを増やせば良いんじゃない？
 * Serverを増やす際のコストは？工数とか手間は？増やすかどうかの判断は誰がする？
 * そもそも、増やすの間に合う？誰が捌ききれてるかを監視するの？
 * Server増やす運用って結構問題も多いし、手間じゃない？？

* じゃあGameServer側で、一旦logファイルに書き出して、それをfluentdで取り込む？
 * GameServerのI/O負荷が凄い事になった。

* 他にもうちょっとマシな方法とかないのかな？

こんなやり取りがあり、白羽の矢がたったのが<b>kinesis</b>でした。

#kinesisとはなんぞや？
まずAWSのkinesisというサービスをご存知ですか？
kinesisとはAWSが提供している、大規模なストリーミングデータをリアルタイムで処理する完全マネージド型サービスだそうです。

大量のデータを捌くパイプみたいなイメージです。
![kinsis_image.png](https://qiita-image-store.s3.amazonaws.com/0/93763/3f7eb9d2-c492-b244-d0c2-38c8d038f1ee.png)


kinesisのメリットとしてはこの2点が大きいかと思います。
・リアルタイムに大量のデータが捌けて、Shardによるスケールの容易な変更が可能。
・取り込んだデータを最大7日間保持する。

#kinesisを検討してみる
そこでもう一度、問題点と照らし合わせます。

* 問題点
 * 量が多いとfluentdServer1台じゃ捌けない。
 * かといって、Serverを増やす解決法は運用コストが大きい。
 * GameServer側で負荷を請け負うとI/O負荷が凄い事に。


* kinesisで解決できる事
 * kinesisに投げられたデータは最大7日間保存されるため、バッファリングが可能になる事で、fluentdServerの負荷を抑えられる。
 * スケールの調整が簡単に出来るので、運用コストも低い。
 * kinesisは大量のデータをリアルタイムで受ける事ができるので、kinesisにlogを直接投げる事によって、GameServer側のI/O負荷が起きない。

なんという事でしょう。
色んな問題が一気に解決されたではありませんか。
と、いうわけでkinesisを使う事にしました。

構成はこんな感じです。
![SQS (1).png](https://qiita-image-store.s3.amazonaws.com/0/93763/0ce6b4c7-2768-cc99-bb57-40bd5ed15443.png)

しかし！
肝心の、kineisに対応したinput pluginが無かったのです。
そこで、pluginは自作する事にしました。

#in_kinesisの作成
自作の際に気をつけたい事は、kinesisの良さを損なわないプラグインにする事でした。
そこで、主に下記機能を備えました。

* kinesisからlogを取得して、outputに渡す。
* 各shard毎にマルチスレッドで並列処理をする。
* shard毎に最後に取得したレコードの位置を記憶、続きから再会できる。
* スケール調整による、shardの増減の自動追尾。
* 使用するshardを意図的に指定できる。
* logの形式はfluentdのdefaultのformatに準拠する。

shard毎にマルチスレッドで並列処理を行う事で、kinesisのリアルタイム処理を極力損なわない様にしています。

あと、１番の目玉は「shardの増減の自動追尾」です。
ここが自動じゃないと、結局人による管理が必要になり、運用コストがかかってしまうので、kinesisの良さを損なってしまうと考えました。

そこで、shardの増減の自動追尾を可能にする為に、各shardにアクセスするshardスレッドを管理する、「<b>supervisorスレッド</b>」を用意して各shardの状態を監視させる事にしました。

【in_kinesisの内部構成】
![kinesis.png](https://qiita-image-store.s3.amazonaws.com/0/93763/d0cf4ae3-ebe6-f8a7-4d13-9f09c8c1b44a.png)

supervisorスレッドはメインスレッドとjoinせずに独立して動きます。
そして、supervisorスレッドが定期的にkinesisの状態を取得し、それに合わせてshardスレッドを起動させたり終了させしりします。

それにより、shardの増減の自動追尾が可能になりました。

あとは、多様性を上げる為に、使用するshardを意図的に指定できる機能も備えました。
これはshard毎に用途を変えて使用する事を考慮して入れているのですが、この機能を使用した場合は自動追尾ができなくなってしまうので、ストリーム毎に管理する事をお勧めします。

#最後に
in_kinesisを使う事でコンシューマーを手作りする必要が無く、fluentdでいろんなoutputに吐き出せるため、意外にも欲している人は多いのでは？と思い、今回初めてオープンソースとして作ってみることにしました。

しかし、初めてのRubyという事で、つたないRubyになってしまい、そういった面でも機能面でも、
まだまだ改良の余地あると思うので、気軽にpull request等送ってください^^ノ
優しい鉞、心よりお待ちしています。

[【in_kinesis】はこちら](https://github.com/yusukeyamatani/fluent-plugin-in-kinesis)
[gem版はこちら](https://rubygems.org/gems/fluent-plugin-in-kinesis/versions/0.0.1)になります。
Enjoy Easy English

![imgres.jpg](https://qiita-image-store.s3.amazonaws.com/0/25489/6b3a4564-0176-a720-6fe5-46461db27223.jpeg)
OK.

Now, I write very crazy english.
I am not think deep.

My English is very poor.

But. I am fun.

Many Japanese don't know crazy but funny english.

I think enjoy english.

English is not danger.

If you miss take writing english, but you don't get damage.

English is not math.

English is communication tool.

You can communication using english, when you hope communicate any one.

Let's forget Japanese school english for Test.

But we need thinking about Time , Place and O....

Perfect is very nice. But, Life is not longer.

If you are afraid, Drinking Alcohol.

Alcohol power is very strong.

Drinking and enjoy speak crazy English. but, if you student don't be drink Alcohol. Adult only.

It's very fun. very Easy. don't be afraid.

This is not valid. Grammar ? Forget.

We are not machine. We are natural life. Using! We brain inference power.
Go 1.5 on Solaris 11 x86

[Go](https://golang.org)!!
クマなのかネズミなのか分からないけれど、
手元の Solaris 環境でもコンパイルできたら良いのに。
・・ならやってみましょう。ものは試し。

[Go 1.5 Bootstrap Plan](https://docs.google.com/document/d/1OaatvGhEAq7VseQ9kkavxKNAfepWy2yhPUBs96FGV28/) によると、
go1.5 では C ソースを撤廃し go1.4 を利用した toolchain ビルドで生成できるとのことです。

さっそく [official](https://golang.org/dl/) からソースを入手。

今回試したコンパイル環境は以下の通り。

* SunOS 5.11 11.2 i86pc i386 i86pc
* gcc version 4.5.2 (GCC)
* GNU Make 3.82 Built for i386-pc-solaris2.11

# Compile Go 1.4

```
$ tar xzf go1.4.3.src.tar.gz 
$ mv go go1.4.3
$ cd gol1.4.3/src
$ ./make.bash
(Snip)
---
Installed Go for solaris/amd64 in /opt/local/src/golang/go1.4.3
Installed commands in /opt/local/src/golang/go1.4.3/bin
```

# Compile Go 1.5


```
$ export GOROOT_BOOTSTRAP=/opt/local/src/golang/go1.4.3
$ tar xzf go1.5.2.src.tar.gz
$ mv go go1.5.2
$ cd go1.5.2/src
$ ./make.bash
(snip)
---
Installed Go for solaris/amd64 in /opt/local/src/golang/go1.5.2
Installed commands in /opt/local/src/golang/go1.5.2/bin
```

あっさり、できてしまった。

# Cross-compile environment

GOROOT_BOOTSTRAP は /opt/local/src/golang/go1.4.3 のまま。

ちなみに勇んで GOROOT_BOOTSTRAP を 1.5.2 のパスに切り替えると、
compile コマンドが見つからない、というエラーが出る。
https://github.com/golang/go/issues/12214

```
$ env  | grep GOROOT
GOROOT_BOOTSTRAP=/opt/local/src/golang/go1.4.3
$ GOOS=linux GOARCH=amd64 ./make.bash 
(snip)
---
Installed Go for linux/amd64 in /opt/local/src/golang/go1.5.2
Installed commands in /opt/local/src/golang/go1.5.2/bin
```

できあがり。
iOSでRubyが書けるPictRuby - 平成を求める


PictRuby 0.2 がリリースされました。

http://pictruby.ongaeshi.me/

- タスクの自動化
- アプリケーションの実行
- Webへのアクセス
- 計算
- イメージフィルタの作成

テキストを返すとテキストが表示されるようになりました。`Browser.get(url)`や`Browser.json(url)`でインターネットから情報を取得することも可能です。全然Pictじゃ無くなってきましたが。

例えば以下のプログラムを入力するといつでも平成を求めることができます。

https://github.com/ongaeshi/PictRubyGems/blob/master/ja/%E5%B9%B3%E6%88%90.rb

```ruby
# # ja/平成
#
# ## 概要
# 今が平成何年か表示します。

def convert
  t = Time.now
  h = t.year - 1989 + 1
  "平成#{h}年#{t.month}月#{t.day}日"
end
```

![2015-12-19-000219-1.png](https://qiita-image-store.s3.amazonaws.com/0/3885/588f6cbe-0edc-3d38-0e6f-1659c51a5cbf.png "2015-12-19-000219-1.png")
![2015-12-19-000219-2.png](https://qiita-image-store.s3.amazonaws.com/0/3885/472e7f22-8c4d-4b58-b833-571ee43a869e.png "2015-12-19-000219-2.png")

小さなプログラムですがモバイルで書いて実行できることにちょっとだけ意義があります、お楽しみください。

[PictRubyGems](https://github.com/ongaeshi/PictRubyGems)にサンプルコードが色々置いてあります。
HTML文字列と«class HTML»データを変換するAppleScriptハンドラ


* AppleScriptでクリップボードを取得すると、しばしば`«class HTML»`というクラスのデータが出現
* `«class HTML»`のデータはHTML文字列と相互変換できる


## dataHTMLFromHTML

```applescript:dataHTMLFromHTML.scpt
my dataHTMLFromHTML("<p>あいうえお</p>")
--> «data HTML3C703EE38182E38184E38186E38188E3818A3C2F703E»

on dataHTMLFromHTML(HTML as text)
	return do shell script "echo " & quoted form of HTML as «class HTML»
end dataHTMLFromHTML
```


### 更新履歴

* 2011-08-14: HTML文字列のASCII numberを変換する形式で作成
* 2012-03-13: hexdumpを使った`do shell script`に変更
* 2016-01-10: echoを使った`do shell script`に変更



## dataHTMLToHTML


```applescript:dataHTMLToHTML.scpt
use scripting additions
use framework "Foundation"

my dataHTMLToHTML(«data HTML3C703EE38182E38184E38186E38188E3818A3C2F703E»)
--> "<p>あいうえお</p>"

on dataHTMLToHTML(dataHTML as «class HTML»)
	try
		dataHTML as text
	on error e
	end try
	return my doShellScript("echo " & quoted form of text 5 thru -1 of word 2 of e & " | xxd -r -p")
end dataHTMLToHTML

on doShellScript(command as text)
	--require framework: Foundation
	set task to current application's NSTask's alloc()'s init()
	set task's launchPath to "/bin/sh"
	set task's arguments to {"-c", command}
	set outPipe to current application's NSPipe's pipe()
	set task's standardOutput to outPipe
	set errorPipe to current application's NSPipe's pipe()
	set task's standardError to errorPipe
	task's |launch|()
	set outData to outPipe's fileHandleForReading()'s readDataToEndOfFile()
	if outData = missing value or outData's |length|() as integer = 0 then
		set errorData to errorPipe's fileHandleForReading()'s readDataToEndOfFile()
		if errorData = missing value or errorData's |length|() as integer = 0 then
			error "0 以外の状況でコマンドが終了しました。" number 1
		else
			error (current application's NSString's alloc()'s initWithData:errorData encoding:(current application's NSUTF8StringEncoding)) as text number 1
		end if
	end if
	return (current application's NSString's alloc()'s initWithData:outData encoding:(current application's NSUTF8StringEncoding)) as text
end doShellScript
```

### 更新履歴

* 2015-12-16: URLデコードを使う方法で作成
* 2015-12-18: data部分の取得方法を`offset`から`word`に変更
* 2016-01-10: `URLDecode`ハンドラを、PHPを使った`do shell script`からCocoa機能での変換へと変更
* 2016-01-11: xxdを使った`do shell script`に変更
* 2016-02-20: シェルコマンドの実行をObjective-Cに変更
node-red用websocketブリッヂ

#概要
node-redのwebsocketは、sangoにつなげない。
sangoは、websocketにmqttが走っているようだ。
実証するため、以下のコードをjsdo.itで走らせた。
pahoを使った。
つながった。

#写真
![websocket.jpg](https://qiita-image-store.s3.amazonaws.com/0/18104/a5e2d6cc-9746-7f98-7e9a-602ac949a9e2.jpeg)

#サンプルコード
```
var ws;
var ph;
function setup() {
    var userName = 'sango user';
    var password = 'sango pass';
    var websocketUrl = 'ws://lite.mqtt.shiguredo.jp:8080/mqtt';
    ws = new WebSocket("ws://node-red/test0");
    ws.onopen = onOpen;
    ws.onmessage = onMessage;
    ph = new Paho.MQTT.Client(websocketUrl, 'papo');
    ph.connect({
         userName: userName,
         password: password,
         onSuccess: onConnect,
         onFailure: failConnect
    });
    ph.onConnectionLost = onConnectionLost;
    ph.onMessageArrived = onMessageArrived;
}
function onOpen(e) {
    //alert("ws open");
};
function onMessage(e) {
    //alert("ws received data : " + e.data);
    ph.publish('sango user/test0', "ohisama");
};
function failConnect(e) {
    alert('ph ng0');
}
function onConnect() {
    //alert("ph connect");
    ph.subscribe('ohisama@github/test0');
}
function onMessageArrived(message) {
    //alert("ph recive msg");
    var val = message.payloadString;
    ws.send("ohisama");
}
function onConnectionLost(responseObject) {
    if (responseObject.errorCode !== 0) 
    {
        alert("ph onConnectionLost:" + responseObject.errorMessage);
    }
}
setup();
```
スタートアップのWiFi 環境改善 Tips

# あらすじ
スタートアップにおいてオフィスの WiFi をとりあえず構築したものの、オフィスが広くなったり、人が増えたりすることで困ることがでてきたりするかもしれません。今日は WiFi 環境の改善 Tips をいくつかまとめてみました。


# 電波届かない問題

会議室が増えたり、増床によって WiFi ルーターでは、電波が微妙に届かない。そんな時は、WiFi 中継器を検討してみても良いかもしれません。電源だけ供給すればよいので設置はお手軽です。

[BUFFALO 無線LAN中継機 11ac/n/g/b 433+300Mbps エアステーション ハイパワー コンセント直挿し WEX-733DHP](http://www.amazon.co.jp/gp/product/B014UDYWG0/ref=as_li_ss_il?ie=UTF8&camp=247&creative=7399&creativeASIN=B014UDYWG0&linkCode=as2&tag=mabotsblog-22)

![画像](http://ws-fe.amazon-adsystem.com/widgets/q?_encoding=UTF8&ASIN=B014UDYWG0&Format=_SL110_&ID=AsinImage&MarketPlace=JP&ServiceVersion=20070822&WS=1&tag=mabotsblog-22)

# なんか・・電波悪い

「なんか電波・・・悪い」そんな時に考えられるいくつか原因を分解してみます。

## 人多すぎて不安定問題

家庭用の WiFi ルーターでは同時接続数が 10 端末程度とみなしておいたほうが良いでしょう。それを超えると、パフォーマンスが劣化したりエラーパケットが増える場合があります。最近だと、PC 以外にもスマートフォンなどのデバイスもあるので、あっさりと端末数は増えてしまい困ったものです。

解決方法としては、WiFi ルーターではなく、ルーターとより多くの同時接続数に対応した強力な WiFi アクセスポイントの構成にすることです。手元の WiFi ルーターの WiFi 機能を OFF にして単にルーターとして使えるならそのまま使いまわせば費用も抑制できます。

[BUFFALO 法人様向け 管理者機能 無線LANアクセスポイント WAPS-APG600H](http://www.amazon.co.jp/gp/product/B008562ZN6/ref=as_li_ss_il?ie=UTF8&camp=247&creative=7399&creativeASIN=B008562ZN6&linkCode=as2&tag=mabotsblog-22)

![画像](http://ws-fe.amazon-adsystem.com/widgets/q?_encoding=UTF8&ASIN=B008562ZN6&Format=_SL110_&ID=AsinImage&MarketPlace=JP&ServiceVersion=20070822&WS=1&tag=mabotsblog-22)


## 電波が干渉する

前述の WiFi 中継器と中継器やルーターの間で電波が不安定な場合は、干渉している場合があります。各々の距離を取ることで対策します。

## 2Ghz 帯が混雑

他のテナントの WiFi やテザリングしている端末があると、動作が不安定になります。2Ghz 帯は混雑しているので、5Ghz 帯をメインにするのも端末がサポートしているのであれば検討できるかと思います。

# 便利なアイテム

WiFi 中継器や WiFi アクセスポイントの設置において、便利なアイテムとして結束バンドがあります。以外とこの名前を知らない人がいるのですが、画像をみれば、「あれね」と納得するアイテムです。ごちゃごちゃしたケーブルの整理にも使えるかと思います。

[ELPA 耐候性結束バンド ワンタッチロック方式 200mm 20本入 ブラック KBF-200020C(BK)](http://www.amazon.co.jp/gp/product/B000THVZ2G/ref=as_li_ss_il?ie=UTF8&camp=247&creative=7399&creativeASIN=B000THVZ2G&linkCode=as2&tag=mabotsblog-22)

![画像](http://ws-fe.amazon-adsystem.com/widgets/q?_encoding=UTF8&ASIN=B000THVZ2G&Format=_SL110_&ID=AsinImage&MarketPlace=JP&ServiceVersion=20070822&WS=1&tag=mabotsblog-22)


電波強度の調査や、混戦状況の調査については、[WiFi Analyzer](https://play.google.com/store/apps/details?id=com.farproc.wifi.analyzer&hl=ja)といったアプリが便利です。


それでは良い WiFi ライフを。
FreeBSD-updateの無いバージョンで,リモートアップデートする方法

現在のFreeBSDには、freebsd-updateという、便利なコマンドがあって
データセンターに設置したマシンのバイナリアップデートを現地に行かないでおこなうことができます。
また、FreeBSD-8.2以降には、upgradeオプションがついたので、メジャーバージョンのアップデートも可能です。(もちろん、ソースからアップデートする方法は、昔からあります。)

しかし、FreeBSD-8.2未満では、このupgradeオプションがありません。

わたしは、FreeBSD4の頃から、リモートでアップデートする場合に
ソースからでは、ダルイので、ここに示す方法で、アップデートしていました。
メジャーバージョンアップももマイナーバージョンアップも同じ方法でできます。

FreeBSD5の頃に書いたメモですが、8.1の頃に中途半端に書き直してるので
記述に矛盾があります。

重要なのは、インストールCDの中に、

XXX-RELEASE/kernels/install.sh
XXX-RELEASE/base/install.sh
XXX-RELEASE/lib32/install.sh

というスクリプトがあるので、それを実行するという事です。

ーーーーーーーー
注意:４系列->6へは、いきなりやると、バイナリが読めなくなる。
ーーーーーーーー

FreeBSD-5系列のリモートによるバージョンアップ法

これは、FreeBSD-5.Xがインストールされている環境に
最新版のFreeBSD-5.Xを上書きインストールする事を目的としている。

ただし、その環境を、最初にインストールしたものが
FreeBSD-4系列以前のバージョンであり、
その環境から、なんらかの方法で、FreeBSD-5.X系列にアップデートした環境から
さらに、最新版にすることは想定していない。
（できないわけではないが、注意点が多いのでここでは割愛する）

なんらかの理由で再起動に失敗すると悲惨なことになるので
稼働中の環境のアップデートには使用しないこと。
するならば、別のマシンからシリアル経由でログインすることができる環境でのみするベキである。

どちらかといえば、新設のサーバにOSをインストールしてデータセンターに設置、
リモートで、そのほかのソフトの設定などをしてる間に
アップデートが出てしまった場合などに向いている。
つまり、/etcがあまり変更されていない場合
稼働中マシンにするならば、rc.confやrc.dの自動起動を殺しておいてからにした方がいい。
とくに、MTAの停止は必須。

# カレントに8.1-XXXX-disc1.isoに、ISO_IMAGEがある想定

mkdir /iso
mdconfig -a -t vnode -f FreeBSD-8.1-RELEASE-i386-disc1.iso -u 0
mdconfig -a -t vnode -f FreeBSD-8.1-RELEASE-amd64-disc1.iso -u 0
mount -t cd9660 /dev/md0 /iso

umount /mnt
mdconfig -d -u 0

（注意）
インストール中に、アカウントとエイリアスがデフォルトで上書きされる。
そのため、作業の開始前に、MTAを停止をすること
また、このため、リモートで作業中のシエルからログアウトすると、コンソールからrootで
ログインするしか方法がなくなるので、予備に別のシエルでログインしておくこと。
また、Winodws版のターミナルソフトなどで、暇になると勝手にセッションをきるものがあるので
予備のシエルでは、topなどを実行させておいた法がいいだろう。
*NIXな環境で作業する方がベターだろう。私はMAC OS XのTerminalを使用している。

ここから作業開始

chflags -R noschg /old/*

rm -rf /old
mkdir -p /old/usr
cp -rp /etc /old/etc
mv /rescue /old/rescue

chflags -R noschg /boot/*
chflags -R noschg /bin/*
chflags -R noschg /sbin/*
chflags -R noschg /lib/*
chflags -R noschg /libexec/*
chflags -R noschg /usr/bin/*
chflags -R noschg /usr/sbin/*
chflags -R noschg /usr/lib/*
chflags -R noschg /var/*
chflags -R noschg /usr/lib32/*

cd /iso/8.1-RELEASE/kernels
sh install.sh generic
rm -r /boot/kernel.old
mv /boot/kernel /boot/kernel.old
mv /boot/GENERIC /boot/kernel

rm -r /usr/include

cd ../lib32
sh install.sh

cd ../base
sh install.sh

cd /etc
/old/rescue/cp ../old/etc/ttys .

/old/rescue/cp ../old/etc/master.passwd .
/old/rescue/cp ../old/etc/passwd .
/old/rescue/cp ../old/etc/pwd.db .
/old/rescue/cp ../old/etc/spwd.db .
/old/rescue/cp ../old/etc/group .
/old/rescue/cp ../old/etc/hosts .

/old/rescue/cp ../old/etc/remote .
/old/rescue/cp ../old/etc/sysctl.conf .

/old/rescue/cp ../old/etc/make.conf .
/old/rescue/cp ../old/etc/shells .
/old/rescue/cp ../old/etc/inetd.conf .

/old/rescue/cp ../old/etc/mail/mailer.conf mail
/old/rescue/cp ../old/etc/mail/aliases mail
/old/rescue/cp ../old/etc/mail/aliases.db mail
newaliases
ls
外部からログインできる事を確認する。

/old/rescue/reboot

神に祈って再起動を待つ......合掌
Gem install で Operation not permitted された時の対応（追記あり）

もう散々いろいろなところで書かれているかもしれませんが。
El Capitanにおいて、`gem install` でちょっとだけひっかかったのでまとめ。  

## sudo なし
「oauth」をインストールしようとしました。

```
$ gem install oauth
Fetching: oauth-0.4.7.gem (100%)
ERROR:  While executing gem ... (Gem::FilePermissionError)
You don't have write permissions for the /Library/Ruby/Gems/2.0.0 directory.
```
ということでsudoつけます

## sudo 追加

```
$ sudo gem install oauth
Fetching: oauth-0.4.7.gem (100%)
ERROR:  While executing gem ... (Errno::EPERM)
Operation not permitted - /usr/bin/oauth
```

/usr/bin/には入らないらしい。

## install場所の変更

```
$ sudo gem install oauth -n /usr/local/bin/
Successfully installed oauth-0.4.7
Parsing documentation for oauth-0.4.7
Installing ri documentation for oauth-0.4.7
Done installing documentation for oauth after 1 seconds
1 gem installed
```

無事成功しました！


## 追記
### rbenvを使用している場合
El Capitanのrootless機能の影響により、上記手順を踏まなければならないと思っていましたが、rbenvを使っているならば `/.rbenv/' 以下にインストールされるため、問題なく進むようです。（@riocampos さん ありがとうございました）
私の場合は、rbenvのPATHが正しく設定されていなかったようでした...
pixi.jsのフィルターを試してみました

LIGアドベントカレンダー19日目です！ こんにちは@jun01itoです。デザイナーやってます。アワードなんかを見ていると、WebGL系がすごい勢いですね~中でも、

+ WebGL 2D系 pixi.js
+ WebGL 3D系 three.js

を使っているなぁという印象です。そんなわけでWebGL~シェーダーを簡単に追加できるpixi.jsのフィルターを試してみました。公式サンプル見ながらやってみます。
[公式のpixi sample](http://www.goodboydigital.com/pixijs/examples/15/indexAll.html "公式のpixi.filter sample")



# 今回のバージョンは Pixi.js 3.0.8
　
## サンプルがv3じゃない...
sampleとドキュメントを見比べてみるのが良さそうです。
[pixi docs](https://pixijs.github.io/docs/PIXI.filters.html "pixi docs")

+ new PIXI.filtersに変更されてる
+ フィルター数も増えてる


### はじめにテクスチャを読み込んでみます
```js
	var WW = document.documentElement.clientWidth;
	var WH = document.documentElement.clientHeight;

	var renderer = PIXI.autoDetectRenderer(WW, WH,{backgroundColor : 0x000000});
		renderer.view.style.position = "absolute"
		renderer.view.style.width = window.innerWidth + "px";
		renderer.view.style.height = window.innerHeight + "px";
		renderer.view.style.display = "block";
	
	document.body.appendChild(renderer.view);
	
	var stage = new PIXI.Container();
	var texture = PIXI.Texture.fromImage("テクスチャ画像のパス");
	var sprite1 = new PIXI.Sprite(texture);
	stage.addChild(sprite1);

    //- ここでフィルターを呼ぶ

	render();
	function render() {
	    requestAnimationFrame(render);
	    renderer.render(stage);
	}
```
これだけでcanvasにテクスチャ画像が読み込まれます。

![01.png](https://qiita-image-store.s3.amazonaws.com/0/15507/2d367305-9705-83cb-9f0c-7de6ede4489a.png "HELLO WORLD!")


### 次にフィルターを適応してみます
以下を追加するだけ。

```javascript:
var twistFilter = new PIXI.filters.TwistFilter();
stage.filters = [ twistFilter ];
```
![02.png](https://qiita-image-store.s3.amazonaws.com/0/15507/65f95d5b-5ede-d9cc-f5cb-51e1f0d46f89.png "twistFilter")

たったの2行でした。。。
フィルターの追加は、filtersの配列に追加すればOKのようです。
読み込む順番も関係しているようで、sampleに合わせた順番で。

### 他のフィルターも試してみます
他のフィルターも試してみて、displacementFilterというフィルターが他のと少し違うフィルターでした。displacementは「置換」という意味通りで、テクスチャ画像をフィルター画像に置き換えるエフェクトのようです。

#### sampleではこんな画像を読み込んでいました
![displacement.jpg](https://qiita-image-store.s3.amazonaws.com/0/15507/d7897b84-4b0e-39c6-4be3-69411772cad9.jpeg "displacement.jpg")

##### photoshopでdisplacement.jpg
+ ベタ塗り(#000000)
+ 描画(ファイバー)
+ 描画(雲模様1)
+ 白黒

の順番で効果をかけると似たような画像が作れました。この画像でよければご自由にお使いください。読み込んだテクスチャ画像でフィルターエフェクトがかけられますので色々応用できそうです。

### displacementFilter
```javascript:
var displacementFilter = new PIXI.filters.DisplacementFilter(PIXI.Sprite.fromImage("フィルター用の画像パス"));
displacementFilter.scale.x = 70;
displacementFilter.scale.y = 70;
```

![03.png](https://qiita-image-store.s3.amazonaws.com/0/15507/b04a03b8-e937-2f5c-e2b9-f3dea16d4840.png "displacementFilter")

分かりやすいように、displacementFilterだけ適用してみました。いい感じです。

## まとめ
+ filterの追加は、filters配列に追加する
+ 複数読み込みの場合は順番に注意

あとは、blurのエフェクトがキレイな感じで使いどころ多そう。

![04.png](https://qiita-image-store.s3.amazonaws.com/0/15507/3e055722-f298-32a4-0260-af2100c99f6f.png "blurFilter")
![05.png](https://qiita-image-store.s3.amazonaws.com/0/15507/f3329201-aaa0-c827-0e11-ae1018231671.png "twistFilter")
![06.png](https://qiita-image-store.s3.amazonaws.com/0/15507/7075c428-2107-1064-59e5-2468d310745c.png "displacementFilter + dotScreenFilter + dotScreenFilter")

pixi.jsいいですねー／それではまた＿(・・)／
JIRAやConfluenceのテスト環境を簡単に作る3つの方法

こんにちは。
Atlassian Expert の一員として、JIRA や Confluence のアドオン開発や導入支援をしている者です。

Atlassian 製品は開発サイクルが速く、次々と新しいバージョンがリリースされます。
新しいバージョンがリリースされたら出来るだけ早く新機能や変更点を確認したいですよね。
そんなときに使える、クリーンなテスト環境を作る方法を紹介します。
ちなみに今回の記事は Server 版を対象にしています。

# Windows インストーラを使う
普段使いのパソコンが Windows の場合はこの方法が最も手っ取り早いでしょう。
Atlassian のウェブサイトからインストーラをダウンロードして実行するだけです。
インストーラのウィザードにそって進めるだけなので特に難しいこともありません。

JIRA 7.0 のインストール方法はこちら。
https://confluence.atlassian.com/adminjiraserver070/installing-jira-applications-on-windows-749382631.html

# 仮想マシンを使う
VirtualBox や VMWare などの仮想マシンを使う方法です。
OS や JIRA/Confluence のセットアップを毎度手動で実行するのは手間なので、私は Vagrant でシェルスクリプトを実行させています。

Github で Vagrantfile を公開しています。
https://github.com/thirota/atlassian-vagrant/tree/master/centos-6.7/jira-software-7.0
https://github.com/thirota/atlassian-vagrant/tree/master/centos-6.7/confluence-5.9

VirtualBox と Vagrant がインストールされていれば、`vagrant up`で CentOS が立ち上がり、JIRA が起動します。あとは、Web ブラウザで JIRA のセットアップウィザードをいつも通り実行します。
テスト用のため、データベースは内蔵DB、`localhost:18080`でポートフォワードさせています。

私がいつも使っている Vagrantfile では、上述のスクリプトをもう少しカスタマイズして PostgreSQL のインストールや設定ファイルの書き換えなどもやっております。

# Atlassian SDK を使う
開発者向けの開発キット（SDK）を使う方法です。
SDK と聞くと少し敷居が高く感じられますが、手順さえ覚えればそれほど難しい方法ではありません。

簡単に手順をまとめると・・・

* Atlassian Plugin SDK のインストール
    * Windows ならインストーラをダウンロードして実行するだけです。詳しくは Atlassian Developers をご参照ください。
        * https://developer.atlassian.com/docs/getting-started/set-up-the-atlassian-plugin-sdk-and-build-a-project

* SDK のコマンドで JIRA を起動
    * `atlas-run-standalone --product jira --version 7.0.2 --data-version 7.0.2`
        * https://developer.atlassian.com/docs/developer-tools/working-with-the-sdk/command-reference/atlas-run-standalone

これだけで、開発者ライセンスや初期設定の完了した Charlie Lawson's JIRA が起動します。簡単ですね！
起動まで時間がかかることと（特に初回）、ディスクの空き容量にご注意ください。

![charlie-jira.png](https://qiita-image-store.s3.amazonaws.com/0/83323/2e2cf82c-88c4-9a89-8103-d0ab34621672.png)


# まとめ
私はJIRAやConfluenceのセットアップウィザードの挙動を確認したいことも多いので、2番目に紹介した VirtualBox＋Vagrant の構成を最も多用しています。
上記で紹介した以外にも、AWS の AMI イメージや、Docker イメージを使う方法もありますが、私は実戦投入していないため、今後の学習課題にしたいと思います。

* https://confluence.atlassian.com/bitbucketserver/launching-bitbucket-server-in-aws-manually-776640204.html
* https://bitbucket.org/atlassianlabs/atlassian-docker
React Native - In app purchase/アプリ内課金(iOS)

今日はReact Nativeでアプリ内課金を実装してみます。iOSのモジュール[react-native-in-app-utils](https://github.com/chirag04/react-native-in-app-utils)を利用します。


## 環境設定

1) インストール

```
 $ npm install react-native-in-app-utils --save.
```

2)ライブラリのリンク

いつものように[ここ](https://facebook.github.io/react-native/docs/linking-libraries-ios.html#content)を参照しながら、Xcodeでライブラリをリンクさせる。`node_modules/react-native-in-app-utils/InAppUtils.xcodeproj/`をドラックアンドドロップでXcodeのライブラリに追加後、link binaryする。


##　使い方

iTunes connectで課金の設定をしていることを前提とします。課金自体は非常にシンプルで、`InAppUtils.loadProducts`でproductsをAppleから取得し、そのプロダクトを買う場合に、`InAppUtils.purchaseProduct`を行うだけです。

```
let InAppUtils = require('NativeModules').InAppUtils;
let productID = 'com.xxx.yyy.10_credit';

let profile = React.createClass({

  getInitialState(){
    return {
      user: {}
    }
  },

  componentDidMount(){
    var products = [
      productID,
    ];
    InAppUtils.loadProducts(products, (error, products) => {
      //console.log(products);
      //console.log(error);
      if(!error){
        this.setState({price: `(10 credit/${products[0].priceString})` });
      }
    });
  },

  onPressPurchase(){
    InAppUtils.purchaseProduct(productID, (error, response) => {
      if(error){
　　　　　//課金失敗時の処理
        AlertIOS.alert("Error", "Failed to purchase. Please contact info@wazalab.com")
        purchaseHistoryActions.trackError(error);
      }else if(response && response.productIdentifier) {
　　　　　//課金成功時の処理。ここでは、Historyにログを残し、ユーザに10クレジット追加かする処理。
        purchaseHistoryActions.trackRecord(response.transactionIdentifier);
        userActions.addCredit(10);
      }
    });
  },

  render(){
    return (
      <Button onPress="onPressPurchase">Buy</Button>
    )
  }
}

```

## Summary

このように既存のライブラリをいい感じに抽象化していて、そのライブラリを使うインストールもドラックアンドドロップとLink Binaryするだけで非常に簡単です。私は他のハイブリッドをあまり触ったことがありませんが、Podcastを聞くとこのインストールの容易さがReacg Nativeの人気のひとつの理由となっているようです。現行コードとの共存も容易となるわけです。