OmniAICreator/Qiita-1.07M huggingface dataset:
文字列が整数かどうか判断するメソッドを考えた


ググっても納得のいく答えが見つからなったので・・・

引数に渡した文字列が整数に変換できるか判定する以下のようなメソッドを作りたい。

```rb
is_int?('1234') # true
is_int?('abcd') # false
```

## 案1

普通に正規表現を使う。

```rb
def is_int?(str)
  !str.match(/\D/)
end
```

## 案2

to_iの特性を利用して二重で変換した後に比較する。

```rb
def is_int?(str)
  str == str.to_i.to_s
end
```

どうするのがベストでしょうか。
d3.min() が正しく値を返さない？

    var data = [{value: "3"},{value: "10"},{value: ""},{value: "5"}];

上記のようなオブジェクトの配列"data"から、"value"の値の最小値を求めたい。


	var minVal = d3.min(data, function(e){
		return e["value"];
	});

これだと、

    ""

が最小値として返ってくる。
d3.min()は、undefinedやNaNを無視してくれるけど、""は、無視してくれないから。

	var minVal = d3.min(data, function(e){
		if(e["value"] == "") return undefined;
		return e["value"];
	});


とすれば、""も無視してくれる。
でも、今度は、

    "10"

が返ってくる。
d3.min()は、自然順(Natural sort order)*で最小値を返すから。
*（"1" < "10" < "2" < "25" < "3" みたいな順番）

文字列を、数値に変換する。

	var minVal = d3.min(data, function(e){
		if(e["value"] == "") return undefined;
		e["value"] = parseInt(e["value"]);
		return e["value"];
	});

これで無事、

    3

が返ってきた。
1分でelasticsearchが使用可能な状態にできるELASTIC CLOUDが便利すぎる件


elasticsearchについて調査していたら辿り着いた **ELASTIC CLOUD** がすこぶる簡単で便利そうだったのでまとめてみた。


# ELASTIC CLOUD

- 詳細は[こちら](https://www.elastic.co/cloud)

elasticが提供しているパッケージをまとめてドバっと使えるクラウドサービスです。
~~特にELK stackと呼ばれるものがほぼ設定なしで使えるのが便利そう。~~

~~※ ELK（elasticsearch, logstash, kibana）のこと~~

とりあえず今回がさくっと検索環境を構築してみるとこまでやってみました。

[20160706追記] すみません！Logstashは現状では含まれていないようです。
追加されないかなー

# 登録

[このページ](https://www.elastic.co/cloud)の "Try It Out" ってとこからページ遷移して、メールアドレス登録すればOK.

最初の二週間は無料で使えるので、その間に色々試してみましょう。


# クラスターの作成

###### 登録が完了してログインしたら、メニューの左上の "New Cluster"ってボタンから[このページ](https://cloud.elastic.co/#/clusters/create/)へ移動して、クラスターを作成します。

###### クラスターサイズ、AWSのリージョン、データセンター数を設定します。

  - ※トライアル中は、1GB, 1data centerしか選択できないです><

![スクリーンショット 2016-07-06 0.35.37.png](https://qiita-image-store.s3.amazonaws.com/0/18932/45a13271-47a7-d0d1-425d-1499e9e9add2.png "スクリーンショット 2016-07-06 0.35.37.png")


###### スクロールして、ShardingとNameを設定します。

![スクリーンショット 2016-07-06 0.36.01.png](https://qiita-image-store.s3.amazonaws.com/0/18932/2934a3da-a0b8-4e9b-62c0-371159c56bc8.png "スクリーンショット 2016-07-06 0.36.01.png")

![スクリーンショット 2016-07-06 0.36.10.png](https://qiita-image-store.s3.amazonaws.com/0/18932/e7d2dcfc-3b4e-a699-259f-aa785150ab2a.png "スクリーンショット 2016-07-06 0.36.10.png")


  
###### 上記で飛ばした設定は任意で設定してください。plugin系は色々便利なのがあるので気になるものにチェックをつけましょう。

###### Createボタンをクリック！これでもうelastic cloud上にクラスターができました、簡単！！



# セキュリティー設定

elasticsearchは通常だと認証なしで使うため、IPアドレスとポートがばれちゃうと誰でも使えてします。そこで公式で提供されている **shieldプラグイン** の設定をしましょう。

###### クラスターを選択した状態で、左側サイドメニューの "Configuration"をクリックします。

![スクリーンショット 2016-07-06 0.44.33.png](https://qiita-image-store.s3.amazonaws.com/0/18932/fbe11d0b-076c-c71b-1994-b9b0022602b4.png "スクリーンショット 2016-07-06 0.44.33.png")



###### Configuration画面の下の方に、Configure Shield のリンクをクリックします。

###### 赤枠のところにパスワードを設定しましょう。任意のユーザーも追加できます。入力したら右上のsaveボタンをクリックします。

- ※画像にはありませんが、画面下部にスクロールするとより細かな設定も可能です。

![スクリーンショット 2016-07-06 0.48.14.png](https://qiita-image-store.s3.amazonaws.com/0/18932/9855a129-e023-7977-f398-cf26f41c86bd.png "スクリーンショット 2016-07-06 0.48.14.png")


# 終わり

以上で基本的な設定は終了です。
あとはクラスターの管理画面にエンドポイントが表示されているはずなので、そこからクラスターを追加したり、検索してみたりしましょう。


pluginも設定画面からポチポチ追加できるので色々試してみてください！


ここまでの設定で月額が$64ぐらいになります。

クラスターの管理コストなどを考えたら全然お安いのではないでしょうか？

検索機能やログの収集管理を始めたいときは是非試してみてください。
独断と偏見によるx86命令拡張の印象

仕事すすまなすぎて辛いので何か出力したくなった。

- 16bit -> 32bit (386)
結構色々変わっていて、レジスタの自由度が上がって少しRISCっぽくなっている。

- 32bit -> mmx (MMX Pentium)
mmxはまじめに使ってないのでよく知らない。飽和加算はMMXではできるがSSEではできないとかそういう命令もある。


- MMX -> SSE (世代知らない)
単精度SIMD。80bit スタック型FPUというおもしろアーキテクチャをやめてしまった。


- SSE -> SSE2 (世代知らない)
整数、倍精度のSIMDが入っている。これ以降追加されるのは便利命令系ばっかりなので一旦完成した感がある。


- SSE2 -> SSE3 (世代知らない)
何が違うんだっけよく知らない
(今調べた)地味にx87 FPUも拡張されてて、これより前は整数への丸めが制御レジスタ変更しないと丸められない残念FPUだったが、丸めモード変えないでC言語の浮動小数→整数変換ができるようになってる

- SSE3 -> SSSE3 (世代知らない)
何が違うんだっけよく知らない


- 32bit -> 64bit
aaa とかのCISCっぽい命令が消えてるので少しRISCに近付いている。
r12かなんかが地味にオペランドフォーマットで不利になってる理不尽な目にあってるのが好き。
あと si,di の8bit部が使えるという拡張が入っているので、%sil とか %dil とかなんだっけってやっちゃう。
追記:rip相対が実装されてうれしい

- SSSE3 -> SSE4.1 (Core2のあとのほう)
pshufb が入ったのでうれしい(まちがい。今調べたらpshufb、SSSE3だった)


- SSE4.1 -> SSE4.2 (Nehalem)
文字列、CRCとかもうSIMDじゃない。
あと命令拡張じゃないけど、Nehalemからmovdquがmovdqaと同じ性能になったの非常に嬉しかったし、確実にSIMDプログラミングが楽になったので世界中の全SIMDは同じようにしてほしい。

- SSE4.2 -> AVX (SandyBridge)
256bit 3オペランド。
3オペランド速くなりそうなのだけど、いつも-mavx付けたら結果遅くなってる気がするがこれコンパイラが悪いの？そんなわけないと思うんだけど。

- AVX -> AVX2, FMA, gather (Haswell)
なんで整数あと付けなんですか？最初から付けてくださいよ。
全世界待望のgather命令登場からのガッカリ性能。

- AVX2 -> AVX512
KNLください。
CPUによって使える機能が違うみたいなことをやりはじめたので32bit ARMみたいな闇になるかもしれない。
512ビットになった以外も結構変わっていてレジスタx32、マスクレジスタが1要素1bitに、sae、broadcast
C# の例外メモ

# 乱暴なまとめ

* ある一連の処理が、その過程で継続不能な状態に陥ったことを、呼び出し元に伝えるための機能。
* 呼び出し元に対して伝えることになるので『お前の○○が悪い』という内容の通達になる。
    * お前の用意した引数に問題がある。
* 自分ではどうしようもない例外は `catch` してはいけないし、自分で管理していないリソースに関する例外を投げてもいけない。


# 文法

* `try` 文の中で例外が発生すると `catch` 文に飛ぶ。
* `catch` 文は複数書くことができる。
* `try` 文が無事に成功しても、失敗しても必ず `finally` 文は最後に実行される。

```csharp
try
{
    // try 文
}
catch (NotImplementedException ex)
{
    // catch 文 その1

}
catch (Exception ex)
{
    // catch 文 その2
}
finally
{
    // finally 文
}
```


# 例外の投げ方の方針

* 処理が継続不能になったことを理由を含めて呼び出し元に伝える
    * お前（呼び出し元）の引数 `null` やん・・・処理できひんし・・・
    * お前の引数、型はあってるけど、値がおかしいし・・・
* 自分が管理しているわけではないリソースに関する例外は投げてはいけない
    * それは、.net Framework などのリソースを管理している人が投げるべき
    * `OutOfMemoryException` など
* 例外は、役割分担を壊さない範囲で、なるべく呼び出し元に近いところで出すべき



# 例外の処理し方の方針

* 自分ではどうしようもない例外は `catch` しない
    * `OutOfMemoryException` とか
* 例外を `catch` したら、後始末を行う
    * リトライする
        * 規定された回数まで、失敗した処理を再試行する。
    * 規定値にする
        * うまくいかなかった時の規定値が決まっているのであれば、代わりにそれを返す。
    * 別の手段を試す
        * 他にうまくいくかもしれない手法があるならそちらを試す
    * エラーを返す・失敗させる
        * 出来なかった旨を伝え処理を終了する
    * 中止する
        * そこまでに、行ってしまった処理を戻して、その旨を伝える

# 投げるべき例外

## ArgumentNullException

* 関数の冒頭で、引数チェックを行い、 `null` ではダメな引数に `null` が入っていたら投げる
* 例外の引数の `message` には、問題となっている引数の名前を入れることが多い

## ArgumentOutOfRangeException

* 関数の冒頭で、引数チェックを行い、処理できる範囲外の値が入っていた場合に投げる
* `null` の場合は `ArgumentNullException` が優先される
* 例外の引数の `message` には、問題となっている引数の名前を入れることが多い

## InvalidOperationException

## ObjectDisposedException

* 既に `Dispose` されている `IDisposable` オブジェクトにアクセスしたとき
* オブジェクトの `Dispose` の管理はあなたが行うため

## FileNotFoundException, DirectoryNotFoundException

* 引数で与えられたファイルやディレクトリが存在しなかった場合に投げる

## FormatException

* 引数で与えられたフォーマットがおかしかった場合に投げる

## TimeoutException

* 何がしかの処理がタイムアウトした際に投げる

## NotImplementedException

* 未実装のメソッドで投げる
* 早く実装しよう

# 投げてはいけない例外

## .net Framework のリソースに関するもの

* `StackOverflowException`, `OutOfMemoryException` など
* .net Framework が管理するリソースのため

## NullReferenceException, DivideByZeroException

* おかしな値で処理を試みるべきではないので、引数のチェックを行い、引数に関する例外を投げるべき
* そもそも、引数のチェックをしていれば出るはずはない

## InvalidCastException

# 参考資料

* [try-catch (C# リファレンス)](https://msdn.microsoft.com/ja-jp/library/0yd65esw.aspx)
* [民の例外の投げ方](http://qiita.com/oika/items/1f8d8e423b2d0fad6da2)
* [標準の例外の種類のキャッチとスロー](https://msdn.microsoft.com/ja-jp/library/ms229007(v=vs.100).aspx)
* [例外の作成とスロー (C# プログラミング ガイド)](https://msdn.microsoft.com/ja-jp/library/ms173163.aspx)
* [例外処理 - C# によるプログラミング入門 | ++C++; // 未確認飛行 C](http://ufcpp.net/study/csharp/oo_exception.html)
[Crystal] HTTP::Clientで（UTF-8的に）不正なバイト列が紛れた文字列をダウンロードする

#<i class="fa fa-lightbulb-o"></i> メモ

`url` がUTF-8的に不正なバイト列を含む文字列を返してくる場合，普通に **HTTP::Client::Response** から `body` を取り出そうとするとエラーになる。

```rb
data = HTTP::Client.get(url).body # => invalid encoding: "utf-8" (ArgumentError)
```

こんなとき `get` なり `post` なりをブロック付きで呼ぶと，ブロック引数で渡される **HTTP::Client::Response** オブジェクトに対して **IO** 型の `#body_io` が使えるようになるので，`IO#set_encoding` で不正なバイト列を明示的にスキップさせるようにすれば，とりあえずエラーは回避可能。

```rb
data = HTTP::Client.get(url) do |res|
  res.body_io.set_encoding("utf-8", :skip)
  res.body_io.get_to_end
end
```
タスクランナーGulpでいろいろ自動コンパイルさせてみたお話

#Gulpとは
Node.js製で作られており
同じ作業をするのは無駄なので作業を自動化してくれるツールです。

#じゃあ、何ができるのか？
- 例えば
 - Scssを自動でコンパイルさせたい　 (大丈夫できます)
 - HamlやJadeでをコンパイルさせたい (大丈夫できます)
 - markdownから、htmlを自動で生成したい　(大丈夫できます)
 - 等々

#必要なこと
 - NodeJsのインストール
 - npmの理解
 
#早速やっていきたいと思います。
 - 作業ディレクトリに行き、npm_moduleのインストール

```terminal:terminal
cd workDirectory
npm i
```

 - 次にgulpfile.jsを作成します。

```terminal:terminal
touch gulpfile.js
```

まだ起動できません

 - gulpfileにどんどん記述して見たいと思います。
 - 今回はScssとMarkDownを入れてみたいと思います。
 - まずScssを導入していきたいと思います。

```gulpfile.js

var gulp = require('gulp');

var sass = require('gulp-sass');
var plumber = require('gulp-plumber');

var dir = {
  watchScss : "*.scss",
  exportCss : "./"
};

// Sassコンパイルタスク
gulp.task('scss', function(event) {
  return gulp.src(dir.watchScss)
    // エラーが気た時に処理が落ちるのでplumberでカバー
    .pipe(plumber())
    .pipe(sass().on('error', sass.logError))
    .pipe(gulp.dest(dir.exportCss))
});

// gulp.watch(dir, [task set name]);
gulp.task('watch',function(event){
	gulp.watch(dir.watchScss,['scss']);
});


gulp.task('default',['watch']);

```

####gulpを起動
-gulp等のnpmが入っていないので入れましょう

```terminal:terminal
npm install gulp
npm install gulp-sass
npm install gulp-plumber
gulp
```

###次にMarkDownを入れてみましょう

```gulpfile.js
var gulp = require('gulp');
var sass = require('gulp-sass');
var plumber = require('gulp-plumber');
var markdownDocs = require('gulp-markdown-docs');
var dir = {
  watchScss : "*.scss",
  watchReadme : "./README.md",
  exportCss : "./",
  exportReadme : "./README.html"
};

// Sassコンパイルタスク
gulp.task('scss', function(event) {
  return gulp.src(dir.watchScss)
    // エラーが気た時に処理が落ちるのでplumberでカバー
    .pipe(plumber())
    .pipe(sass().on('error', sass.logError))
    .pipe(gulp.dest(dir.exportCss))
});

// markdown コンパイルタスク
gulp.task('readme', function () {
  return gulp.src(dir.watchReadme)
    .pipe(markdown({encodings: "UTF-8"}))
    .pipe(gulp.dest(dir.exportReadme));
});

// readme task set
gulp.task('readme', function () {
  return gulp.src('*.md')
	.pipe(markdownDocs('README.html', {
        layoutStylesheetUrl: 'markdown.css'
  }))
	.pipe(gulp.dest('./'));
});

// gulp.watch(dir, [task set name]);
gulp.task('watch',function(event){
	gulp.watch(dir.watchScss,['scss']);
	gulp.watch(dir.watchReadme,['readme']);
});

gulp.task('default',['watch']);

```

####gulpを起動
-Markdownのnpmが入っていないので入れましょう

```terminal:terminal
npm install gulp-markdown-docs
gulp
```

#最後に

```
layoutStylesheetUrl: 'markdown.css'
```
とありますがこれは、MarkdownのHTMLしかgulpでは吐き出してくれないので
markdown.cssというファイルを作りcssを読み込ます作業が必要となります。
参考にしたcssです。
https://gist.github.com/tuzz/3331384

自動更新はされたでしょうか？
作ったものは載せておくのでいじってみてください。
いろいろ自動化していきましょう。
お疲れ様でした。

https://github.com/mizutamazukki/GulpRunner
riot.js + Material Design Lite で インフラエンジニアでもSPA書けたけど、動的に読み込まれたページだとMDLのjsがいうこと聞いてくれなかった話



たとえばこんなページを作ったとする
--------------------

<a href="http://plnkr.co/edit/RUfVPmTA679B67foxCTy?p=preview" target="_blank">NG版</a>


Material Design Lite を適用する前は何も問題なかった。

<img width="516" alt="スクリーンショット 2016-07-05 23.51.28.png" src="https://qiita-image-store.s3.amazonaws.com/0/17518/4972da07-9c9b-c366-cb8a-6e952782a6c7.png">

あれ。なんか text field 動いてない。

本当は

<img width="388" alt="スクリーンショット 2016-07-05 23.53.17.png" src="https://qiita-image-store.s3.amazonaws.com/0/17518/09d3a188-0648-a360-89e9-625f3203302a.png">

こんな感じで「みょっ」ってなってくれるはずなんだけど…

という話。


参考
--------------------

riot-js
https://muut.com/i/riot-js/using:are-there-material-design-c


修正版
--------------------

<a href="http://plnkr.co/edit/9RCRzD3eq5fDj9X3HE17?p=preview" target="_blank">修正版</a>


home.tag に

```
this.on('mount', function() {
    componentHandler.upgradeDom();
});
```
を追加。

text field に入力すると…

<img width="517" alt="スクリーンショット 2016-07-06 0.01.17.png" src="https://qiita-image-store.s3.amazonaws.com/0/17518/8c704093-da2d-579d-7747-d28ec7ecb322.png">

「みょっ」ってなった。

MDLが対応していないってことなのかな
navigation barの色をstoryboardで変更する方法

navigation barの色をstory boardで変更するのがどれかわからなかったのでメモ

1.navigation barを選択して
<img width="261" alt="スクリーンショット 2016-07-05 23.42.37.png" src="https://qiita-image-store.s3.amazonaws.com/0/64331/8b7dcba7-1b32-84ef-f232-f58ae4da323d.png">

2.Bar Tintで色を変更！
<img width="263" alt="スクリーンショット 2016-07-05 22.55.00.png" src="https://qiita-image-store.s3.amazonaws.com/0/64331/588430b1-2729-f0f1-ca56-75b842c520be.png">

これだけ！

コードでは以下のように書けばok

```
self.navigationController?.navigationBar.barTintColor = UIColor.redColor()
```
JavaでJSONを比較する

二つのJSONデータがあったときに比較をしたい。単に文字列で比較すると`[]`と`[ ]`ですら同じと判断できない。JSONを正規化する方法がどっかで決まっていたような記憶もあるがJavaのライブラリが探せなかった。

`org.json.json`を使ったらどうやら簡易的にできるようだ。

```build.gradle
dependencies {
    // https://mvnrepository.com/artifact/org.json/json
    compile group: 'org.json', name: 'json', version: '20160212'
}
```


```JsonCompare.java
package example.misc;

import org.json.JSONObject;

public class JsonCompare {

    public static void main(String[] args) {
        final JSONObject o1 = new JSONObject("{\'a\': 'hoge', b: 'bar', c: [1,3,5], bb: {e: 'あ'}}");
        final JSONObject o2 = new JSONObject("{b: 'bar',  \nc:[1,\n3,5], a: \n'hoge', \"bb\": {e: '\\u3042'}}");
        System.out.println(o1.toString());
        System.out.println(o2.toString());
        System.out.println(o1.toString().equals(o2.toString()));
    }
}
```

出力は次のとおり。

```
{"bb":{"e":"あ"},"a":"hoge","b":"bar","c":[1,3,5]}
{"bb":{"e":"あ"},"a":"hoge","b":"bar","c":[1,3,5]}
true
```
キーの並び順序が気にはなるがこれでJSONの比較ができそう？複雑なJSONでも大丈夫なのかは未確認。

# 参考
* https://github.com/skyscreamer/JSONassert - ユニットテストでいろいろやるならこれがいいのかも？
* https://github.com/lukas-krecan/JsonUnit - こういうのもある

ちゃんとやるならこういうのを使ったほうがいいのだろう。
Bash on Ubuntu on Windowsでnginxを動かす

Windows 10 Insider Preview Build 14379で確認。

インストールはふつうに

```
sudo apt-get install nginx
```
で、nginx/1.4.6 がインストールされるはず。(Ubuntu 14.04)

ユーザー `www-data` （グループ `www-data`） が存在することを確認

/etc/nginx/nginx.conf の設定

```
user www-data;
master_process off; # この行を追加
worker_processes 4;
pid /run/nginx.pid;

# 以下省略
```

/etc/nginx/sites-available/default の設定

```
server {
        listen 8080 default_server; # ポート番号は空いているところに適当に割り当てる
        # listen [::]:80 default_server ipv6only=on; # ipv6の設定はコメントアウトする

        # 以下省略
}
```

というわけで、master processの設定とipv6の設定を変えるのがポイント。

(補足)[nginxのFAQには「プロダクション環境ではmaster_processをoffにするな」と書いてある](http://nginx.org/en/docs/faq/daemon_master_process_off.html)わけですが、Bash on Ubuntu on Windows自体が開発者用機能であり、本番稼働のためのものではないということに留意しましょう。
Typescript で Material UI の App Bar を使用した際のメモ書き

# Typescript で Material UI の App Bar を使用した際のメモ書き
(2016.07.05 OS X El Capitan)

完成したアプリ: [summarize-text-data アプリ](http://nariset.github.io/summarize-text-data-appbar/)

[以前作成したテキストの文字数などを数えるウェブアプリ](http://qiita.com/NariseT/items/30ab79f7ed358c448226) に
Material UI を使用して、App Bar をつけてみる.

## 必要な npm パッケージのインストール

```
npm i material-ui react-tap-event-plugin --save-dev
```

## 型定義ファイルのインストール

```
typings i dt~material-ui --save --global
typings i dt~react-tap-event-plugin --save --global
```

## [App Bar](http://www.material-ui.com/#/components/app-bar)

App Bar の作成. [IconMenu](http://www.material-ui.com/#/components/icon-menu) を iconElementLeft に設定.

```
import * as React from 'react';
import {AppBar, IconButton, IconMenu, MenuItem} from 'material-ui';
import MoreVertIcon from 'material-ui/svg-icons/navigation/more-vert';

export default class AppBarIcon extends React.Component<any, any> {
    render () {
        return (
            <AppBar
                 title="Summarize Text Data"
                 titleStyle={{textAlign: "center"}}
                 iconElementLeft={
                     <IconMenu
                         iconButtonElement={<IconButton><MoreVertIcon /></IconButton>}
                         anchorOrigin={{horizontal: 'left', vertical: 'top'}}
                         targetOrigin={{horizontal: 'left', vertical: 'top'}}
                     >
                         <MenuItem primaryText="Version 0.0.1" />
                         <MenuItem primaryText="Version 0.0.1" />
                     </IconMenu>
                 }
            />
        );
    }
}
```

## App.tsx の編集

- http://www.material-ui.com/#/get-started/installation
- http://www.material-ui.com/#/get-started/usage

より

```
import * as React from 'react';
import AppBarIcon from './AppBarIcon';
import FileDropzoneContainer from '../containers/FileDropzoneContainer';
import TextAreaContainer from '../containers/TextAreaContainer';
import SummaryContainer from '../containers/SummaryContainer';

import * as injectTapEventPlugin from 'react-tap-event-plugin';
import getMuiTheme from 'material-ui/styles/getMuiTheme';
import MuiThemeProvider from 'material-ui/styles/MuiThemeProvider';

injectTapEventPlugin();

const App = () => (
    <MuiThemeProvider muiTheme={getMuiTheme()}>
        <div>
            <AppBarIcon />
            <FileDropzoneContainer />
            <TextAreaContainer />
            <SummaryContainer />
        </div>
    </MuiThemeProvider>
)

export default App
```

## index.html の編集

```
<html>
<head>
    <title>Summarize Text Data</title>
</head>
<body>
    <div id="root"></div>
    <script src="build.js"></script>
</body>
</html>
```

## その他

style でテキストエリアのマージンなどを調整した.
Google Sheets API の "Attempting to write column: 26, beyond the last requested column of: 25" というエラーの意味がわかった

# 問題
Spreadsheet API の create ( https://developers.google.com/sheets/reference/rest/v4/spreadsheets/create ) で、26番目以降の column にどうしてもデータを入力できないというエラーレスポンスでハマりました。英語は読めないし message でググってもわからなくて本当に参った。

```json
{
  "code" : 400,
  "errors" : [ {
    "domain" : "global",
    "message" : "Invalid sheets[1].data[4]: Attempting to write column: 26, beyond the last requested column of: 25",
    "reason" : "badRequest"
  } ],
  "message" : "Invalid sheets[1].data[4]: Attempting to write column: 26, beyond the last requested column of: 25",
  "status" : "INVALID_ARGUMENT"
}
```

# 原因
何かと思ったら Sheet デフォルトの最終列がアルファベット 0 ベースで 25 番目の Z なんですよね。それを超えるような位置に、 API リファレンスでいうところの `Sheet` の `GridData` の `RowData` の `CellData` を入力したとしても、自動では拡張してもらえず弾かれるということでした。
![image](https://qiita-image-store.s3.amazonaws.com/0/27471/8c4a07fa-1d69-d12a-8835-54297f857f91.png)

# 解決
それ用のオプションがあります。 `Sheet` の `SheetProperties` の `GridProperties` ( https://developers.google.com/sheets/reference/rest/v4/spreadsheets#gridproperties ) の `columnCount` を十分な大きさに設定してやることで解決しました。
![image](https://qiita-image-store.s3.amazonaws.com/0/27471/4b9c0cab-8966-760b-2f2e-81d77911efa6.png)

# あとがき
同じく `rowCount` を設定してやることが必要な場面もあるでしょう。もちろんこのオプションで逆に狭めることもできます。それにしてもスプレッドシートは複雑ですが、この API 群はよく作ってありますね。
NiFiでKerberizeされたKafka、HDFSに接続する

KerberizeされたKafkaにNiFiからアクセスするのに苦労している時、同僚が「KafkaをKerberizeすると非常にセキュア、セキュリティ頑丈過ぎて自分でも入れないw」なんてジョークを飛ばしてました。
それぐらい難しいんだなー、と少し安心しつつ、やっぱり結構苦労しました。久々にまとまった量の情報になったので残しておきます。

If you're looking for English, it's available [here](https://community.hortonworks.com/articles/43446/how-to-connect-nifi-with-kerberized-hdp-kafka-and.html).

NiFiからKafkaやHDFSに接続する記事は色々あるのですが、Kerberosが絡むと、Zookeeper、Kafka、HDFS、Ambari、Ranger、NiFiと設定が広範囲に渡り、ちらばったドキュメントを参照しないといけないので、まず全体像を把握するのがとても難しかったです。

以下の手順はHDP SandboxをKerberizeしてNiFiから接続するラフな手順をまとめたもので、不必要なものも、不足もあるかもしれませんが、全体的にはこんな感じの手順になります:

- HDPのSandboxに最新のHDFをダウンロードしてインストール
- Kafkaデフォルトでは起動していないので、Ambariから起動、メンテナンスモード解除
- 影響のあるサービスをリスタートする
- MIT KDCをインストールして設定する [参考](http://docs.hortonworks.com/HDPDocuments/HDP2/HDP-2.4.2/bk_Security_Guide/content/_optional_install_a_new_mit_kdc.html)
- AmbariからKerberosを有効にする
- AmbariのKerberosウィザードにしたがって進める
- Check Pigのテストが失敗するが、Completeボタンで前に進む
- いくつかのサービスが起動してない状態になったので、Ambariから起動
- Kerberos関連のKafka設定を行う [参考](http://docs.hortonworks.com/HDPDocuments/HDP2/HDP-2.4.2/bk_secure-kafka-ambari/content/ch_secure-kafka-overview.html)
- Kafka listenersの設定を`PLAINTEXT://localhost:6667`から`PLAINTEXTSASL://localhost:6667`にAmbariから変更
- AmbariのRanger設定から`Kafka ranger plugin`, Kafkaの設定から`Enable Ranger for KAFKA`をそれぞれ有効にする [参考](http://docs.hortonworks.com/HDPDocuments/HDP2/HDP-2.4.2/bk_Security_Guide/content/kafka_plugin.html)
- RangerでKafkaのACLを設定する [参考](https://docs.hortonworks.com/HDPDocuments/HDP2/HDP-2.3.0/bk_Ranger_User_Guide/content/kafka_service.html)
- 後から別ユーザで接続しようと思っても、すでに他のKerberosユーザでConsumer Group接続している場合は、同一のGroup idで他のKerberosユーザからは接続できないので注意
- KerberizedされたKafkaにNiFiが接続できるようにNiFiを設定 [参考](https://community.hortonworks.com/articles/28180/how-to-configure-hdf-12-to-send-to-and-get-data-fr.html?platform=hootsuite) サンプルコード貼り付けるときにダブルクォーテーショ
ンに注意
- `/etc/krb5.conf`をnifi.propertiesのnifi.kerberos.krb5.fileに設定
- HDFSのアクセス制御はRangerのみで管理することが推奨されている [参考](http://hortonworks.com/blog/best-practices-in-hdfs-authorization-with-apache-ranger/)
- PutKafka, GetKafka, PutHDFSなどを使ってNiFiのフローを作成する

[Gist](https://gist.github.com/ijokarumawak/efd46abec052aa49e54ea53c1a0806f4)にはサンプルのNiFi templateとかも置いてあります。何かのお役に立てばこれ幸い。
スマホで全画面モーダルを展開したときに後ろの要素を固定する

スマホのナビゲーション等の実装した時、全画面であっても下までスワイプしたりすると、後ろ側の要素(bodyやwrapperなど)まで動いてしまうのを止めたくて調べてみました。

##1. overflow: hidden

一番てっとり早いがiOSではスクロールを止めることは出来ない

##2.タッチイベントを停止

http://qiita.com/kokushin/items/ef96194bd0fa7c145d7b

この辺や

```js

//スクロール禁止用関数
function no_scroll(){
//PC用
var scroll_event = 'onwheel' in document ? 'wheel' : 'onmousewheel' in document ? 'mousewheel' : 'DOMMouseScroll';
$(document).on(scroll_event,function(e){e.preventDefault();});
//SP用
$(document).on('touchmove.noScroll', function(e) {e.preventDefault();});
}
```

こんなのとか。

スマートで楽なので、ほぼこれで良い気もするけど、問題点としてモーダル内にスクロール(iframeやjs擬似スクロール)があると、それも動かなくなってしまう。

https://github.com/noraesae/perfect-scrollbar
これ系のjsとか

###3. position:fixed + スクロール位置を記憶
http://qiita.com/gonshi_com/items/5a86fc415dcccfb04e2a#comment-475a95b4b8d993098233

ちょっと大げさだけど、手堅くいける気がする。
気になるのはfixedにしたときにスクロールで隠れたブラウザUIがまた出てくることくらいかな。

## 結論

2か3を使う
Javascript で object の中身を出力表示（Node.js 利用でコマンドライン）

こんにちは。
Javascript で object の中身を出力表示させ、JSON.stringify の出力と比較してみました。Node.js 利用でコマンドラインで動かしました[^1]。

[^1]: 「[node.jsによるコマンドラインツール 導入](http://qiita.com/linquanstudio/items/21587ab8ecefe62be855)」

```console
$ ./print.js 
{"0":["1","2"],"3":["4"]}  // JSON.stringify（比較用）
{0:[1,2],3:[4]}  // print_object()
```

```print.js
#!/usr/bin/env node

function tostring(x, braces) {
  var arr = [];
  if (x instanceof Array) {
    if (braces === undefined) braces = "[]";
    arr.push(braces[0]);
    for (var i=0; i < x.length; i++) {
      if (i>0) arr.push(",");
      arr.push(tostring(x[i]));
    }
    arr.push(braces[1]);
    return arr.join("");
  }
  else if (x instanceof Object) {
    for(var k in x){
      arr.push(k + ":" + tostring(x[k]));
    }
    return tostring(arr, "{}")
  }
  else return x.toString();
}

function print_object(x) {print(tostring(x));}

function print(str) {process.stdout.write(str + '\n')};

var obj = {"0": ["1", "2"], "3": ["4"]};
print(JSON.stringify(obj));
print_object(obj);
```

---------------
BeautifulSoup4でWEBスクレイピング（連番ページ）

# BeutifulSoup4でWEBスクレイピング

よくあるURLが連番になっているページで、後からまとめてダウンロードするためにURLリストを作成するコードを書いたのでメモ

## インストール

```
$ apt-get install lxml-python
$ pip install beautifulsoup4
```

## ソース

```python:scraper.py
# -*- coding: utf-8 -*-

from __future__ import absolute_import
from __future__ import division
from __future__ import print_function

try:
    # Python 3
    from urllib import request
except ImportError:
    # Python 2
    import urllib2 as request

from bs4 import BeautifulSoup
import codecs
import time

def getSoup(url):
    response = request.urlopen(url)
    body = response.read()
    # Parse HTML
    return BeautifulSoup(body, 'lxml')

wait_sec = 3
domain = 'http://hoge.com'
result_file = 'list.txt'
i = 1
while(True):
    url = '{domain}/{index:0>2}/'.format(domain = domain, index = i)
    try:
        soup = getSoup(url)
    except IOError:
        break

    div = soup.find('div', attrs = {'id': 'div_id'})
    all_a = div.find_all('a', attrs = {'class': 'a_class'})
    src_list = []
    for a in all_a:
        src_list.append(a.img['src'])
    with codecs.open(result_file, 'a', 'utf-8') as f:
        f.write('\n'.join(src_list))
    print(i)
    i += 1

    time.sleep(wait_sec)
```

## 参考ページ

[Python: BeautifulSoup4 を使って Web サイトをスクレイピングする](http://momijiame.tumblr.com/post/114227737756/python-beautifulsoup4-%E3%82%92%E4%BD%BF%E3%81%A3%E3%81%A6-web-%E3%82%B5%E3%82%A4%E3%83%88%E3%82%92%E3%82%B9%E3%82%AF%E3%83%AC%E3%82%A4%E3%83%94%E3%83%B3%E3%82%B0%E3%81%99%E3%82%8B)

[PythonとBeautiful Soupでスクレイピング](http://qiita.com/itkr/items/513318a9b5b92bd56185)
CocoaPodsのインストールについてのメモ

http://qiita.com/satoken0417/items/479bcdf91cff2634ffb1
において、

```
sudo gem install cocoapods

```
でつまづく。以下エラー文。

```
ERROR:  Error installing cocoapods:
	activesupport requires Ruby version >= 2.2.2.

```
以下のように、rbenvのバージョンを >= 2.2.2.になるようにしたが効果無し。

```
kimuraryouyuu-no-MacBook-Air:~ Ryosuke$ rbenv versions
  system
  2.2.0
* 2.2.3 (set by /Users/Ryosuke/.rbenv/version)
```

よくよく調べてみると、gemにおけるRUBY VERSIONが2.0.0であった。(もはやgemとrbenvの違いがわかってない汗)

```
kimuraryouyuu-no-MacBook-Air:~ Ryosuke$ gem environment
RubyGems Environment:
  - RUBYGEMS VERSION: 2.6.6
  - RUBY VERSION: 2.0.0 (2014-05-08 patchlevel 481) [universal.x86_64-darwin13]
  - INSTALLATION DIRECTORY: /Library/Ruby/Gems/2.0.0
  - USER INSTALLATION DIRECTORY: /Users/Ryosuke/.gem/ruby/2.0.0
  - RUBY EXECUTABLE: /System/Library/Frameworks/Ruby.framework/Versions/2.0/usr/bin/ruby
  - EXECUTABLE DIRECTORY: /usr/bin
  - SPEC CACHE DIRECTORY: /Users/Ryosuke/.gem/specs
  - SYSTEM CONFIGURATION DIRECTORY: /Library/Ruby/Site
  - RUBYGEMS PLATFORMS:
    - ruby
    - universal-darwin-13
  - GEM PATHS:
     - /Library/Ruby/Gems/2.0.0
     - /Users/Ryosuke/.gem/ruby/2.0.0
     - /System/Library/Frameworks/Ruby.framework/Versions/2.0/usr/lib/ruby/gems/2.0.0
  - GEM CONFIGURATION:
     - :update_sources => true
     - :verbose => true
     - :backtrace => false
     - :bulk_threshold => 1000
  - REMOTE SOURCES:
     - https://rubygems.org/
  - SHELL PATH:
     - /Users/Ryosuke/anaconda/bin
     - /Library/Frameworks/Python.framework/Versions/3.5/bin
     - /Users/Ryosuke/Library/Enthought/Canopy_64bit/User/bin
     - /Library/Frameworks/Python.framework/Versions/2.7/bin
     - /usr/bin
     - /bin
     - /usr/sbin
     - /sbin
     - /usr/local/bin
     - /opt/X11/bin
     - /usr/local/git/bin
```

RUBY VERSIONを上げる方法がわからなかったので、
シンプルに「ERROR: Error installing cocoapods: activesupport requires Ruby version >= 2.2.2.」と検索してみると
https://github.com/CocoaPods/CocoaPods/issues/4711

が見つかり、

```
sudo gem install activesupport -v 4.2.6

```
をして無事にcocoapodsをインストールできました。
Railsフォームでクラスがつかない場合の対処方法


ちょっとしたことだけど、忘れやすいのでメモ

## うまくいなかない例
```haml
= f.select :bar, {'hoge' => 'hoge', 'fuga' => 'fuga'}, :class => 'form-control'
```

## うまくいく例
```haml
= f.select :bar, {'hoge' => 'hoge', 'fuga' => 'fuga'}, {}, {:class => 'form-control'}
```
MySQL で全ユーザの権限をまるっと抽出

# はじめに

MySQL のサーバがたくさんあって、ユーザや権限がまちまちだったり、ちょっとずつ違う状態だったりするのを是正するために、全DBサーバから全アカウントと権限を抽出してみた。
DB機だけで60台くらいあるんで。。。

# これだけ

<pre>
$ mysql -u root -p -h server -N -e 'select concat("SHOW GRANTS FOR `",user, "`@`",host, "`;") from mysql.user order by user,host;' > showgrants.sql
$ mysql -u root -p -h server -N < showgrants.sql > createuser.sql
</pre>

まぁSQLでSQL作って実行するだけなんだけどね。

<pre>
$ cat showgrants.sql
SHOW GRANTS FOR `hoge`@`10.10.10.%`;
SHOW GRANTS FOR `munin`@`localhost`;
SHOW GRANTS FOR `root`@`localhost`;
SHOW GRANTS FOR `zabbix`@`localhost`;
</pre>

あ、もちろんはしょってあります。

<pre>
$ cat king-dbm01/createuser.sql
GRANT USAGE ON *.* TO 'hoge'@'10.10.10.%' IDENTIFIED BY PASSWORD 'パスワードな文字列'
GRANT SELECT, PROCESS, SUPER, REPLICATION CLIENT ON *.* TO 'munin'@'localhost' IDENTIFIED BY PASSWORD '*CF5C09FAD38AFB92F43C9BEE1A0F69CE3736770D' WITH GRANT OPTION
GRANT ALL PRIVILEGES ON *.* TO 'root'@'localhost' IDENTIFIED BY PASSWORD 'パスワードな文字列' WITH GRANT OPTION
GRANT PROXY ON ''@'' TO 'root'@'localhost' WITH GRANT OPTION
GRANT REPLICATION SLAVE, REPLICATION CLIENT ON *.* TO 'zabbix'@'localhost' IDENTIFIED BY PASSWORD 'パスワードな文字列'
</pre>

* シェルでサーバ毎にぶん回して（.my.cnf 書いてパスワード設定して -p とか外して）サーバ名/ファイル、みたいな感じで全部抽出した。
* 最初の SQL で user, host でソートしてるので、diff とるのも簡単。
* mysql.user からユーザ一覧作るだけでは漏れちゃう権限（FILEとか後付するようなやつ）もちゃんとチェックできた（漏れてた。。。_no
* -N でヘッダ消すのがミソ
* user,host を `` で括ることで無名アカウントとかもちゃんと処理できるのもGOOD

ずっと後でまた使うかもしれないから qiita にメモってことで。

# 検証求む

うちのDB機ではこれで問題なく全部チェックできたと思うんだけど、何か問題とかおかしいとことかあったらコメントで教えてくれるとうれしす。


# おまけ

## mysqldump

<pre>
$ mysqldump -u root -p -x --allow-keywords mysql > test.dump
</pre>

こういうのだと、いらんテーブル情報もごっそり入ってるし、MySQLのバージョン違いで困る（mysql_upgradeとかあるけど）し、なによりそもそも権限周りのチェックには使えない。

## select user,host,password from mysql.user

ユーザは一覧できるけど、この後 show grants 文作るのも１つずつ投げるのも面倒だったので作ったって感じ。
要件が定義できないことの説明の草案

# 要件は定義できない

と、思う。

昔はできた、けど、今は出来ない、と、思う。

## なぜ？

昔はそもそもシステムと関係なく「やりたいこと」が先にあって、それをシステム化していた。

つまり、システムとは関係ない文脈で、まず「やりたいことは何か？」を定義することができた。
なので、（システムの）要件を（システムと関係ない文脈で）定義できていた。

> Office Automationとか言ってた時代

今はどうかというと、「やりたいこと」を実現するためにはほぼ必ずといっていいほど「新たなシステム」を使うことが前提になっている。

「新たなシステム」、つまり、まだそのシステムが存在していないということ。

その状態においては「今はまだ存在しないシステムを使うことが前提となっている目指すべき姿」自体が明確にはならない。

その存在しないシステムを使うと世界がどう変わるかはわからない。

「目指すべき姿」が明確にはならなければ「システムの要件」は決まらない。

「システムの要件」が不明瞭なのだから「なってほしい状態」もまだ明確には決まらない。

「なってほしい状態」が明確になっていないので、当然、そのための「システムの要件」も明確にはならない。

「システムの要件」が明確にならないと「なってほしい状態」も明確にならない。

ニワトリが先か、たまごが先か、的な議論になって収集がつかない。

ということで要件は定義できそうにない。
Reduxのアクションを綺麗に書く方法の提案

### 皆さん

<br>
<br>
<br>

**Redux使ってますかー！**

<br>
<br>
<br>

使ってますよー！

<br>
<br>
<br>

でも疲れますよねー！

**アクションの定義**とかー！

**リデューサーの定義**とかー！

**アクションクリエイターの定義**とかー！

<br>
<br>
<br>

そもそもアクションを**定数で定義する**のってどうなんですかー！

いっぱい定義したらどこかで**同じ文字列書いちゃい**ませんかー！

<br>
<br>
<br>

そんなときー！

次のソースコードをコピって使いましょー！

```js
export default class ActionSchema {

  constructor(...props) {
    Object.assign(this, {
      ...props,
    });
  }

  static get actionType() {
    return this.name;
  }

  static action(props) {
    return {
      type: this.name,
      ...props,
    };
  }
}
```

これを使うとー！

アクションが次のように書けますー！

```js
export class CreateMessage extends ActionSchema {}
export class DeleteMessage extends ActionSchema {}
```

アクションクリエイターが次のように書けますー！

```js
import { CreateMessage, DeleteMessage } from './schema';

export function createMessage({messageType, content}) {
  const message = {
    type: messageType,
    content,
  }
  return dispatch => {
    dispatch(CreateMessage.action({message}));
    setTimeout(function () {
      dispatch(DeleteMessage.action({message}));
    }, 10000);
  };
}
```

リデューサーが次のように書けますー！

```js
import { CreateMessage, DeleteMessage } from '../actions/schema';

export default function messages(state = [], { type, ...rest }) {
  switch (type) {
    case CreateMessage.actionType:
      ...

    case DeleteMessage.actionType:
      ...

    default:
      return state;
  }
}
```

<br>
<br>
<br>

### ね、**便利**でしょう？

<br>
<br>
<br>

※この記事は往年のテキストサイトを意識して書かれました

<br>
<br>
<br>
Let's Encryptを使って快適ECDSA生活

Let's EncryptからECDSAの署名を出せるということだったので、使ってみることにしました。

# ECDSAのメリット
一般的に、SSLで使うサーバ証明書はRSAで署名されていますが、他の方式としてECDSAがあります[^1]。

ECDSAを使うことによるメリットは、RSAと比較した場合の安全性と高速性です。一般に、RSAによる署名は2048ビットですが、その強度はAES 128ビット相当にも満たず、同程度の強度を得ようとすれば3072ビットが必要となります。一方、ECDSAの強度は半分の長さのAESと同程度なので、証明書に使われる256ビットでAES 128ビット相当のセキュリティを得られます。

そして、サーバ負荷はRSA 2048ビットと比べてもECDSA 256ビットのほうが圧倒的に軽くなっています。クライアント側の負荷は少し増えますが、トータルすれば処理速度は上がることとなります。

# ECDSAのデメリット
RSAと比較して、ECDSAを使う場合のデメリットを並べていきます。

* 別に暗号鍵を交換する必要がある：ECDSAは楕円曲線デジタル署名アルゴリズム（Elliptic Curve Digital Signature Algorithm）の略であるというように[^2]署名専用なので、通信用の暗号鍵交換は別途のアルゴリズムで行う必要があります。
 * ただし、署名用のRSA鍵で暗号鍵配送も行うと、秘密鍵が漏れた場合に暗号文を解読されてしまうので、RSAでも別途で暗号鍵交換を行って、通信内容の秘匿はRSA鍵に頼らない[Forward Secrecy](https://ja.wikipedia.org/wiki/Forward_secrecy)が行われるようになっています。
* 楕円曲線暗号の特許や、演算する楕円曲線の恣意性が気になる
 * 現実問題としてRSA+ECDHEという、RSA署名に楕円曲線での鍵交換を行う方式も普及していますので、それを使うのとさほど問題は変わりません（あまり気にしないことが多いです）。
* RSA署名にしか対応していない環境がある
 * もっとも、ガラケーなどはRSAでもSHA-2署名に非対応ということもあって、RSA+SHA-2と比較してECDSAが使えないのはWindows XP以前やAndroid 2.3、ゲーム機のブラウザなど、かなり限られます。
* 出せる証明局が限られる（とりわけ安価な証明書がない）
 * タイトルのとおり、Let's Encryptで出せるようになったので、内輪向けなどで高級な証明書が不要な場面にも適用できるようになりました。

# ECDSA証明書を発行する
Qiitaにも[先行記事](http://qiita.com/TsutomuNakamura/items/e2e7be7c1f4d1638454d)はあるのですが、ACMEプロトコルを実装した別のクライアントである`letsencrypt.sh`を使うのも便利です（[lukas2511/letsencrypt.sh](https://github.com/lukas2511/letsencrypt.sh)）。詳しくは[別サイト](https://http2.try-and-test.net/letsencrypt_sh.html)に譲りますが、認証方法としてHTTP経由だけでなく**DNS経由**という方法もありますので、指定のドメインでHTTPサーバを立てづらい状況でも認証を通せます。

# CipherSuiteの設定
RSA証明書と合わせるCipherSuiteは山のようにあって、何をどう選べばいいのか迷いますが、ECDSA対応のCipherSuiteは、同じ楕円曲線暗号のECDHEとの組み合わせだけとなっています。

```
ECDHE-ECDSA-AES256-GCM-SHA384 TLSv1.2 Kx=ECDH     Au=ECDSA Enc=AESGCM(256) Mac=AEAD
ECDHE-ECDSA-AES256-SHA384 TLSv1.2 Kx=ECDH     Au=ECDSA Enc=AES(256)  Mac=SHA384
ECDHE-ECDSA-AES256-SHA  SSLv3 Kx=ECDH     Au=ECDSA Enc=AES(256)  Mac=SHA1
ECDHE-ECDSA-AES128-GCM-SHA256 TLSv1.2 Kx=ECDH     Au=ECDSA Enc=AESGCM(128) Mac=AEAD
ECDHE-ECDSA-AES128-SHA256 TLSv1.2 Kx=ECDH     Au=ECDSA Enc=AES(128)  Mac=SHA256
ECDHE-ECDSA-AES128-SHA  SSLv3 Kx=ECDH     Au=ECDSA Enc=AES(128)  Mac=SHA1
ECDHE-ECDSA-DES-CBC3-SHA SSLv3 Kx=ECDH     Au=ECDSA Enc=3DES(168) Mac=SHA1
ECDHE-ECDSA-RC4-SHA     SSLv3 Kx=ECDH     Au=ECDSA Enc=RC4(128)  Mac=SHA1
ECDHE-ECDSA-NULL-SHA    SSLv3 Kx=ECDH     Au=ECDSA Enc=None      Mac=SHA1
```

強度が112ビット分しかない3DES[^3]、安全性が崩壊しているRC4、暗号化しないNULLは当然除外して、残るはAESだけです。

* ECDHEが256ビットの場合、この鍵交換がAES128ビット相当の強度なので、AES128ビットを優先で強度的にも問題ありません（256ビットかけても過剰性能なだけです）。
* GCMモードを優先したほうが安全です。

ということで、OpenSSLのCipherSuiteとしては、`ECDSA+AESGCM+AES128:ECDSA+AESGCM:ECDSA+AES128:ECDSA+AES:!aRSA:!RC4:!3DES:!NULL`というような感じになります。

[^1]: いちおう、DSAやケルベロス認証、事前鍵共有（PSK）など、他の方式も定義されてはいますが、サーバやブラウザで対応していない、事前の設定が必要で不特定多数との通信には適さない、などの理由で、HTTPSで実用に値するのはほぼRSAとECDSAに限られます。
[^2]: いっぽうのRSAは、発明した3人（Rivest、Shamir、Adleman）の頭文字を繋いだもので、アルゴリズムの内容とは関係しません。
[^3]: ふつうの設定では、「最後の砦」的にRSA+3DESを入れておくことがありますが、ECDSA対応でAES非対応のクライアントは考えづらいので、この場合は入れなくていいでしょう。
Swaggerは使える

仕事でSwaggerなymlをもらいました。初めてでしたがSwaggerで簡単にモックAPIサーバが建てられてQOLが上がった感じがしました。

## swagger-codegenでモックサーバを立てる

### インストール

インストールは簡単で、brew一発です。公式でDockerを使ってビルドする方法もありましたが、mavenで一つ一つビルドしていくため時間がかかりますので、おすすめしません。

```bash
$ brew install swagger-codegen
$ which swagger-codegen
/usr/local/bin/swagger-codegen
```

もしかしたら事前にJavaが必要かもしれません

```bash
$ brew cask install java
```

### 使い方

下記のような感じで使います。

```bash
$ swagger-codegen generate \
  -i swagger.json \
  -l nodejs-server \
  -o api-mock
```

- `-i` 元にするjson
- `-l` 言語（クライアントとか、サーバとかもここで識別）
- `-o` 出力先のフォルダ

### APIサーバ起動

```bash
$ cd api-mock
$ npm install
...省略...
$ node .
notebook:api-mock foursue$ node .
Your server is listening on port 8080 (http://localhost:8080)
Swagger-ui is available on http://localhost:8080/docs
```

nodeのインストールしてない場合、下記のような感じでインストールしてから、上記の`npm install`しましょう。

```bash
$ brew install node brew
$ cat 'export PATH=$HOME/.nodebrew/current/bin:$PATH' >> ~/.bash_profile
$ . ~/.bash_profile
$ mkdir ~/.nodebrew/src
$ nodebrew install-binary stable
$ nodebrew use v6.2.2
```

## docker-composeにapi-mock入れて開発すると楽

docker-compose.ymlは下記のような感じでいいんじゃないでしょうか。
※webの方は適当です。

```docker-compose.yml
api:
    image: node:latest
    volumes:
        - ./api-mock/:/usr/src/app
    ports:
        - "8080:8080"
    working_dir: "/usr/src/app"
    command: "node ."
web:
    build: ./dockerfiles
    volumes:
        - ./:/var/www/
    ports:
        - "80:80"
    links:
        - api:api
```

phpだと下記のような感じで動作確認できます。

```bash
$ docker-compose up -d
$ docker exec -ti ***_web_1 bash
$ php -r "var_dump(jsondecode(file_get_contents('http://api:8080/v1.0/api/***')));"
```

自前のプロジェクトでもSwagger使ってみようかなと思わせるくらいには敷居が低い。学習コストも低い。Swaggerは使える。
PHPでトランザクションと関係なく排他制御したい

Webアプリケーションは基本はHTTPリクエストごとにステートレスなので、いくらプログラムが並列で動いていても、それをほとんど意識せずに書けて簡単です。が、データを保存するとなると少々厄介です。ユーザーが自分専用のデータを変更するときは問題ありません。同じ共有データに同時に複数の人から書き込みがある場合が問題です。

といっても、WebではRDBを使って当たり前というこの時代、トランザクションという高級で暗黙な排他制御があるんだから任せればいいやと、同時書き込みを気にする人は少なくなりました。むかしはファイルシステムのロックを利用したりして、アクセスを排他制御したものです。

なーんだ、いまどきトランザクション切れないSQLなんてないから、排他制御なんてもう忘れていいんじゃん... とは言えない事情が最近出てきています。NoSQLを併用したとき、バックグラウンドに非同期のジョブキューがあるとき、などなど。それらが必要になる負荷事情があるという時点で、すでにアプリケーションサーバーは2台以上になっているでしょう。懐かしのファイルシステムロックでは不十分な状況が多くなってきました。

でも大丈夫、YiiフレームワークではMutexコンポーネントが提供されていて、さまざまな排他ロックの実装に切り替えて使えます。

http://www.yiiframework.com/doc-2.0/yii-mutex-mutex.html

ひとまずアプリケーションサーバーのファイルシステムを使った排他処理でいい場合

```php
return [
    // ...
    'components' => [
        'mutex' => [
            'class' => 'yii\mutex\FileMutex'
        ],
    ],
]
```

```php
$mutex = \Yii::$app->get('mutex');
$timeout = 10; // sec
if ($mutex->acquire('hoge-lock'), $timeout) {
    // なにかする
    $mutex->release();
} else {
    throw new HogeException('ロック獲得に失敗しました');
}
```

で、10秒待ってだめならタイムアウトして例外を吐く排他制御ができます。

その後サーバを分散したくなったら、アプリケーションコードをそのまま変えず、コンポーネントを切り替えます。

```php
return [
    // ...
    'components' => [
        'mutex' => [
            'class' => 'yii\mutex\MySqlMutex'
            'db' => [
                'class' => 'yii\db\Connection',
                'dsn' => 'mysql:...',
                'username' => '...',
                'password' => '...',
            ],
        ],
    ],
]
```

MySQLの `SELECT GET_LOCK(...)` を使ってロックを獲得してくれます。`'db' =>` のところは、メインのと同じDB接続でいいなら、`'db' => 'db'` のようにコンポーネント名を書いてもかまいません。

PostgreSQL版もありますが、`pg_try_advisory_lock` がタイムアウトを指定できないので微妙でした。

他に、PHPの排他制御ライブラリには ninja-mutex があります。Yii以外では、これをフレームワークに統合するサードパーティーライブラリが多いようです。

https://github.com/arvenil/ninja-mutex

やっていることはYiiのものとだいたい同じで、ファイルシステムとMySQLの他に、memcacheやRedisのドライバがありました。Yiiのコンポーネントはユーザーが継承していろいろ作れるので、Yiiでも ninja-mutex を使うバージョンを作ることもできますね。

PHPみたいなステートレスな言語でも、また、PHPを使うのが適しているHTTPリクエストの文脈でも、やはり排他制御は大事なので、Yiiが最初からフレームワークにその抽象型を持っているのは偉いなあと思いました。
SourceTree のインストール手順

# ダウンロード

* [ダウンロードページ](https://www.sourcetreeapp.com/) からダウンロードしてください

[![download.jpg](https://qiita-image-store.s3.amazonaws.com/0/28936/4ae82aa7-5979-a1d6-1536-8b854ae9fdb9.jpeg)](https://www.sourcetreeapp.com/)


# インストール

* ダウンロードしたインストーラーを起動しインストールを行ってください


## SourceTree の設定

![start.jpg](https://qiita-image-store.s3.amazonaws.com/0/28936/dbfe0cc6-d346-4f3a-a7fc-c61480ee68c4.jpeg)


## グローバル設定

* PC 全体での共通の Git で無視するファイルのパターンを生成するかどうかです
* OS 共通の不要なファイルなどが登録されます（Windows なら `Thumbs.db` とか、MAC なら `.DS_Store` とか）
* グローバル無視設定ファイルは、あったほうがいいので `YES` が無難です。

![global-ignore.jpg](https://qiita-image-store.s3.amazonaws.com/0/28936/2a61f522-b5d0-8a39-0d09-d6b71fc5e6b3.jpeg)


## 外部アカウントの登録

* [BitBucket](https://bitbucket.org/), [GitHub](https://github.com/) のアカウントの登録です。

![sign-up.jpg](https://qiita-image-store.s3.amazonaws.com/0/28936/55ee6805-15b7-8275-e215-f573241578e3.jpeg)


## SSH キーの登録

* 暗号化通信のための SSH キーの読み込みを行います。

![start-ssh-key.jpg](https://qiita-image-store.s3.amazonaws.com/0/28936/12a38fbc-b377-00a8-08f7-9cd4dbd6bedc.jpeg)
Phoenixフレームワークをインストール

### 事前準備
Elixirのインストールを事前に行う必要があります。

参考:
[CentOS7にelixirをインストールする](http://qiita.com/ta__ho/items/8035fc64101519bd5a55)

### インストール

[公式のインストールページ](http://www.phoenixframework.org/docs/installation)を参考にインストールを実施

```
mix local.hex
mix archive.install https://github.com/phoenixframework/archives/raw/master/phoenix_new.ez
```

インストール完了後に、アプリケーションの雛形を作成

```
mix phoenix.new new_app
```

アプリケーションフォルダに移動して、サーバを起動

```
mix phoenix.server
```

デフォルトでpostgresqlが使われてようになっているらしく、
DB接続のエラーが出ました。

ただ、Webサーバ自体は起動しているみたいで、
`localhost:4000`にアクセスし、問題なく起動しているのを確認しました。

今日は以上です。
GitLabで特定のリポジトリだけ500エラー

## Thanks to

https://gitlab.com/gitlab-org/gitlab-ce/issues/17873

## 環境

- CentOS 6.8
- GitLab 8.3.4から8.9.3にアップデート
    - アップデートにはrpmを使用
- Ruby 2.3.1

## 症状

GitLabをアップデートしたあと、特定のリポジトリだけアクセス時に500エラーになる。

`/var/log/gitlab/gitlab-rails/production.log`を見ると、以下のようなエラーが出ていた。

```
Started GET "/xxxxxxxx/xxxxxxxx" for 127.0.0.1 at 2016-07-04 20:51:46 +0900
Processing by ProjectsController#show as HTML
  Parameters: {"namespace_id"=>"xxxxxxxx", "id"=>"xxxxxxxx"}
Completed 500 Internal Server Error in 57ms (ActiveRecord: 4.1ms)

OpenSSL::Cipher::CipherError (iv length too short):
  app/models/project.rb:456:in `import_url'
  app/models/project.rb:486:in `external_import?'
  app/models/project.rb:478:in `import?'
  app/models/project.rb:494:in `import_in_progress?'
  app/controllers/projects_controller.rb:93:in `show'
  lib/gitlab/middleware/go.rb:16:in `call'
```

## 解決

最初のURL先に書いてあった通り、

```
sudo gitlab-rails runner  "Project.where.not(import_url: nil).each { |p| p.import_data.destroy if p.import_data }"
```

を実行すると直った。
SwiftでRealmを使う時のTips

#目次

[SwiftでRealmを使う時のTips まえがき](http://qiita.com/nakau1/items/a591d9cc34e5b575ceb5)
[SwiftでRealmを使う時のTips(1) アクセサとエンティティ編](http://qiita.com/nakau1/items/21ed81e7f38c104f760e)
[SwiftでRealmを使う時のTips(2) 生成とオートインクリメント編](http://qiita.com/nakau1/items/0323807abed795a43393)
[SwiftでRealmを使う時のTips(3) NSPredicate編](http://qiita.com/nakau1/items/40865299dacc50d71604)

#まえがき

いくつかに分けて `Realm` の話を書こうかと思います

そもそもRealmとは

> Realmはオープンソースで開発されているモバイルアプリ向けのデータベースです。公式サイトに「Realm is a replacement for SQLite & Core Data.」とあるように、モバイルアプリ開発の現場では、何年も前に登場したSQLiteやCore Dataが未だに現役で使われており、それらを置き換えることを目的としているようです。大きな特徴として、SQLiteやCore Dataと比較した場合に非常に高速である点や、Android/iOSの両方をサポートしている点が挙げられます。
> 
> 参考: https://developers.eure.jp/tech/realm-java-for-production/

長らくiOSアプリ開発でデータベースといえば `SQLite` や `CoreData` を使ってきたわけですが
SQL文を使わず、複雑なコードを書かず、かつ高速で・・という文句をうたわれると
使わざるを得ないって感じですね

実は、前のお仕事で初めて `Realm` に触る機会を頂きました
むしろその時初めて存在を知ったといいますか

その際には試行錯誤が色々と続き、あまり使いこなすまでに至りませんでした
まぁ、今も偉そうに言えるほど使いこなせてません
いや、むしろまったく使いこなせてません

と、まぁ、そんな自虐をツラツラと書いても仕方ないのですが、
そんな中で少しずつノウハウといいますか、自分の中で見い出したベタープラクティスといいますか
そんな感じのものを書いていければと思います

なのでインストール方法やら、基本的な使い方やらは割愛します
公式ドキュメントも充実してますし
記事にしてくれている方も多いのでそちらにお任せします

[Realm Swift 公式日本語ドキュメント](https://realm.io/jp/docs/swift/latest/)
GoogleChrome 先生 | 「まだブックマークで消耗してるの？」 アドレスバーを多用すべき三つの理由

# 一、GoogleChrome先生は、昔のことをよく覚えている。

多くの人は気づいているかもしれないが。
実は最近のブラウザは「ページタイトル」を覚えていて、アドレスバーでもそこから検索できる。

なのでURLに含まれていない文字でも、候補を出してくれるのだ。

![image](https://qiita-image-store.s3.amazonaws.com/0/89618/b3c1b623-63e5-4549-6ebf-0b7423f01295.png)

# 一、GoogleChrome先生は、何が重要かを知っている。

優しさが溢れる。

たとえば僕はよく Qiita を使うので、アクセスしたいときは「新しいタブを開く」→「qと打つ」→「Enter」という手順をとる。
これは1秒もかからない。

「q」が先頭文字のサイトの中で、僕が一番良く使うものがQiitaなので、候補の一番上にあるからだ。


![image](https://qiita-image-store.s3.amazonaws.com/0/89618/653fef56-a84f-ce9c-2f36-a8c2ca8d6765.png)

# 一、GoogleChrome先生は、順序をあまり気にしない。

「このサイトの、このディレクトリ内のページが見たい」ってときに。

アドレスバーにディレクトリ構造を、順序正しく打ち込まなくても。
適当にキーワードを打てば、ファジーに候補を出してくれる。

次の例では `items` => `qiita` の順で入力しているにもかかわらず、`qiita.com/items/` ディレクトリを候補に出してくれているのが分かるだろう。

![image](https://qiita-image-store.s3.amazonaws.com/0/89618/dd1b2599-1ff0-d3d7-c2ba-b7f5695ae461.png)


生徒に優しいGoogleChrome先生。

# まとめ

GoogleChromeにかぎらず、最近のアドレスバーは優れている。
僕はこのおかげで、ほとんどブックマークというものを使わなくなった。

昔からの慣習で、ブックマークを多用している人もいると思うが、アドレスバーを使い慣れると、目的のページにはるかに素早くアクセスできるようになる。
特に、キーボードショートカットの基本を覚えている人にとっては役立つだろう。

## P.S

実は三つめの動作には僕も気づいてなくて、記事を書きながら実験したら、発覚した。
こういった動作を「意識しているか」「意識していないか」によって、ブラウザ使いのレベルは変わってくると思う。

# 環境

- バージョン 51.0.2704.103 (64-bit)








<!-- Update From Qiita API -->

# チャットメンバー募集


何か質問、悩み事、相談などあればLINEオープンチャットもご利用ください。

https://line.me/ti/g2/eEPltQ6Tzh3pYAZV8JXKZqc7PJ6L0rpm573dcQ





# Twitter


https://twitter.com/YumaInaura


<!-- Update From Qiita API -->
JNAeraror使用時のポインタ参照について

JavaからCのライブラリを呼ぶ際、ポインタの扱いで躓いた。

C側のインタフェース自体は、JNAeratorでヘッダファイルとライブラリからCUIで生成できるが、
いざ呼び出してみるとポインタから上手く値が取得できない…。

結論としては、ポインタが絡む場合、JNAeratorによって自動生成されるクラスに一手間加える必要がある模様です。
自動生成すればそのまま呼び出せると思い込んでいました…。

@IT様の記事（[JNIより簡単にJavaとC/C++をつなぐ「JNA」とは](http://www.atmarkit.co.jp/fjava/special/jna/jna_3.html#034)）にあるように、
ポインタを読むにはコンストラクタでメモリを確保してやればいい。
ただしJNAeratorで生成した場合、生成されたクラスを継承し、同様の記述を加えないとポインタは扱えないようです。
（生成されたクラスに記述がない以上、当たり前ではあるが）
>引用: @IT JNIより簡単にJavaとC/C++をつなぐ「JNA」とは　
>>Pointerを渡して、StructureクラスのメンバーメソッドuseMemoryとreadを呼び出して、渡したPointerと同じメモリを共有する_Employeeインスタンスを生成します。

```java:リスト6　Structure[]からPointerに変換するサンプルソースコード
 1 public interface StructureSample extends Library {
 2     public static class _Employee extends Structure {
 3         String id;        /*社員番号*/
 4         String name;　　  /*氏名*/
 5         int age;          /*年齢*/
 6         String sectionId; /*部署番号*/
 7     }
 8     public _Employee() {
 9         super();
10     }
11     public _Employee (Pointer p) {
12         super();
13         useMemory( p );
14         read();
15     }
16 }
```

自動だからと頼り切ってしまうと思わぬところで躓きますね。

JNAeratorの実行についてはこちらの記事にお世話になりました。
[JNA で java の SDL binding を書いてみた](http://noqisofon.hatenablog.com/entry/20120225/1330133510)
MacでRailsをインストールしようとするとNokogiriあたりでコケる


Rails5が出たのでインストールしようしてこけました。
なんか、毎回これやってる気がしているのでメモ。

## 実行時の環境

- OSX 10.11.5
- Homebrew
- rbenv
- ruby 2.3.1

## 手順

### Homebrewを最新に

```bash
$ brew update
$ brew upgrade
```

### Nokogiriに必要なライブラリインストール

```bash
$ brew tap homebrew/dupes
$ brew install libxml2 libxslt libiconv
$ brew link --force libxml2
$ brew link --force libxslt
```

### Railsインストール

__（追記）__

再度試したところ、わざわざ個別にnokogiriをインストールしなくてもrailsをインストール時にオプション指定すれば大丈夫でした。また、私の環境では `--use-system-libraries` のオプションだけでうまくいきました。
（とはいえ、これだとインストールするもの全て、オプション付きでインストールするので、心配な方は個別にnokogiriだけインストールした方がよいかもしれません。）

```bash
$ gem install rails -- --use-system-libraries
```

さらにこのままでは `bundle install` 時に同様にこけるので、 `bundle install` 時にもオプションを付けるように以下の設定をしました。

```bash
$ bundle config build.nokogiri --use-system-libraries
```

やはり、railsコマンド使うにはターミナルの再起動が必要でしたが、私の環境ではこれで問題なく動作しました。

----

__（以前まで）__

```bash
$ gem install rails
```

で、いけなかったりなのですが、今回は個別にNokogiriをインストールしたらいけました。
今回は1.6.8を要求されていたのでそれをインストールしましたが、適宜読み替えてください。

```bash
$ gem install nokogiri -v '1.6.8' -- --use-system-libraries --with-xml2-include=/usr/include/libxml2 --with-xml2-lib=/usr/lib
```

このあと、もう一度Railsをインストールして出来ました。

```
$ gem install rails
```

なお、自分の環境ではターミナルを一度再起動しないとダメでした。

## 参考

[Mac OS X Mavericksで”gem i nokogiri”失敗の解決方法](http://qiita.com/t_732_twit/items/a7956a170b1694f7ffc2)
TeXで書くのめんどくさい部分はmarkdownで書いちゃえば最強じゃないかな?【Vim + pandoc】

# シチュエーション

あなたはTeXで資料を作っているところです。
([Beamer](https://ja.wikipedia.org/wiki/Beamer)でスライドを作っていると置き換えてもいいです)

箇条書きって，書くの面倒くさくないですか?

```tex
\begin{itemize}
  \item
    hoge
  \item
    huga
  \item
    piyo
\end{itemize}
```

ましてローマ数字(`I`, `II`, ...)で番号を振りたいとなったら

```tex
\begin{enumerate}
  \def\labelenumi{\Roman{enumi})}
  \item
    hoge
  \item
    huga
  \item
    piyo
\end{enumerate}
```

書きたいのはhoge, huga, piyoとかなのに。

# Vimのformat機能 + pandocを使って解決

## `gq` コマンドと`formatprg`

`:help formatting`もしくは`:help gq`の項を見ると，
`gq`(+モーションコマンド)を使えば

1. `formatexpr`が空でなければその内容を実行
2. `formatprg`が空でなければその外部プログラムが使われる
3. 上記に当てはまらなければ内部でフォーマッティングが行われる

みたいなことが書いてあると思います。

注目するのは2番めの`formatprg`を指定してフォーマットを行う方法です。

## 文書変換ツールpandoc

[`pandoc`](http://pandoc.org/)というツールを使えば，markdownからLaTeXに変換するのも楽ちんです。

したがって，tex形式のファイルにおいて`gq`コマンドを実行した時にはpandocを使って選択範囲に対して markdown -> LaTeX 変換を行うようにすれば良さそうです。`~/.vimrc`に

```vim
augroup texfile
  autocmd BufRead,BufNewFile *.tex set filetype=tex
  let md_to_latex  = "pandoc --from=markdown --to=latex"
  autocmd Filetype tex let &formatprg=md_to_latex
augroup END
```

のように書いておきます。

# 使い方

texファイルを編集している最中に，「markdownで書いたらすぐなのになぁ」という事案に遭遇したら，とりあえずその場でmarkdownで書いて，範囲選択して，`gq`と押したら，その部分がTeX形式に変換されて編集終了です。

(markdownでとりあえず書いたリストを範囲指定)
![screen_004.png](https://qiita-image-store.s3.amazonaws.com/0/54869/c825288a-fc42-6ceb-9987-2d9317b83e98.png)


(`gq`と押せば一瞬で出力される)
![screen_005.png](https://qiita-image-store.s3.amazonaws.com/0/54869/8c1c6838-e9c9-e7c9-8269-800ce5908b46.png)

(pdfにするとこんな感じ。)
![screen_006.png](https://qiita-image-store.s3.amazonaws.com/0/54869/bebca823-1e63-c9be-0065-dce779063a90.png)

# まとめ

pandoc万能。Vim拡張性高すぎ。
スニペット挿入機能とかを使ってもいいのかもしれないけれど，そのコマンドを覚えるくらいなら，markdownで書いてしまったほうが速いよねって話。

あと，以前はmarkdownで全部書いてからpandocを通してTeXに変換していたのだけれど，変換後にTeX側を細かく修正してしまい,手直ししようと思うと結局TeXファイルを直にいじることになるので，逆に,基本はtexファイルを直接編集して，書きづらいところだけmarkdownで書くようにすればいいかなと思いました。

例ではTeXのリストしかあげていませんが，画像の貼り付けなどでも威力を発揮するので，TeX書かないといけない人はぜひお試しあれ。

(追記: 2016/07/20)

`formatprg`を活用する例

* [bibcleanでbibファイルを整形](http://qiita.com/ssh0/items/3fa170023f462913f9ac)

(追記ここまで)
vagrantのnginxで公開したhtmlなどをwindowsと同じネットワークのiphoneなどで確認する方法

## vagrantを動作させているパソコンで確認するまでの流れ
- `sudo yum install -y nginx`でnginxをインストール
- `sudo nginx`で起動
- 「services:」に「http」が含まれなければ、`sudo firewall-cmd --add-service=http --zone=public --permanent`で追加する  
- `sudo firewall-cmd --reload`で反映
- `firewall-cmd --list-all`でhttpが許可されたか再度確認
- vagrantを動作させているパソコンで[http://192.168.33.11/](http://192.168.33.11/)を見るとnginxのWelcome画面が表示される  
※vagrantのプライベートIPを[http://192.168.33.11/](http://192.168.33.11/)で動作させている場合

## iphoneで確認するまでの流れ
- `vagrant halt`でVMを一旦停止
- 「Vagrantfile」を下記のように修正

```text
  config.vm.box = "centos"
  config.vm.network :private_network, ip:"192.168.33.11"
```
↓↓↓↓↓↓↓↓↓↓↓

```text
  config.vm.box = "centos"
  config.vm.network :private_network, ip:"192.168.33.11"
  config.vm.network :forwarded_port, guest:80, host:8080, id:"http"
```
- `vagrant up`でVMを開始
- `sudo nginx`で起動
- iphoneで[http://192.168.10.101:8080/](http://192.168.10.101:8080/)を見るとnginxのWelcome画面が表示される  
※windowsでesetなどのファイアーウォールが入ってる場合は対話モードなどにしてiphoneとの通信を許可してください

## 参考
- [vagrantのネットワークについて](http://qiita.com/ftakao2007/items/0ec05c2ef3c14cdbea11)