OmniAICreator/Qiita-1.07M huggingface dataset:
man読書のためのman2pdf

# はじめに

皆さんはman読書やってますか!?

ちなみに僕はあんまりやってないです。

でも，ちょっと時間のあるときにいつも使っているコマンドやツールのmanページを読むと，それまで知らなかった便利機能やオプションを知ることができていろいろ効率が上がったり，自分でツールを作る際の参考になったりしてとても良いと思います。

良いことであることは分かっているので，これを習慣化すればいいわけです。

時間があるとき(ただしPCの前にいない時)に僕が何をやるかというと，スマホをおもむろに取り出して，ニュースやTwitterなどを眺めていることが多いです。

そこで，スマホあるいはタブレットでmanページを読めるように，manページをpdf化してDropboxに保存することにしました。変換用のコマンドを元にシェルスクリプトを書いたのが以下となります。

# man2pdf

> [dotfiles/man2pdf at master · ssh0/dotfiles](https://github.com/ssh0/dotfiles/blob/master/bin/man2pdf)


```bash
#!/bin/bash
# written by Shotaro Fujimoto (https://github.com/ssh0)
# first edited: 2016-03-29
#=#=#=
# Convert man page to pdf file using ps2pdf
#
# You can change `${output_dir}`
# (Dropbox is useful; you can read the pdf documents anywhere)
#
# Example:
#
# ```
# man2pdf awk
# ```
#=#=

output_dir="$HOME/Dropbox/document/pdf/man"

if ret="$(command -p man -t "$1")"; then
  echo "${ret}" | ps2pdf -sPAPERSIZE=a4 -sOutputFile="${output_dir}/$1".pdf - &&
    (echo "[man2pdf] Succefully done" >&2 ;
     echo "[man2pdf] outfile file is '${output_dir}/$1.pdf'" >&2)
fi
```

特に変わったことはしていませんが，`$output_dir`にDropboxのフォルダを指定することで，Dropboxが使える端末ならどこからでもこのpdfを見ることができます。

ちょっとだけ解説すると，

`man -t <command>`で標準出力にpostscript形式として変換されてmanページが出力されるので，これを受けとって`ps2pdf`コマンドを用いてpdfファイルに変換しています。

`ps2pdf`コマンド自体は`gs`コマンドのオプションを受け取ることができるそうなので，用紙サイズをA4にして出力しています。

実際にタブレットで表示すると以下のようになります。

<img width="768" alt="ファイル 2016-04-06 20 27 51.png" src="https://qiita-image-store.s3.amazonaws.com/0/54869/41397691-ea55-2a57-34f0-cc0e90b4052f.png">


# 補完を有効にして使い勝手を良くする

普通にmanコマンドを打つときにはTabキーを押すとコマンド名を補完してくれて便利なので，man2pdfコマンドに関しても，補完が使えるようにしておきます。

自分がZshを使っているのでZshに限って話を進めます。申し訳ありません。

~/.zshrcなどで

```zsh
compdef _man man2pdf
```

などと書いていれば，manコマンド用の補完関数であるところの`_man`を`man2pdf`コマンドに関しても適用することができ，補完を利用することができるようになります。


# 問題点と今後の課題

**日本語を含む場合にpdf化することができません。**

man側の出力エンコーディングを以下のようにUTF8に指定すると，端末内では日本語が表示されるようになりますが，ps2pdfに食わせようとするとエラーが走ります。

```
man -R UTF8 -t man
```

フォントがないというだけの問題のような気もしますが，今のところ解決していません。

もしこういった事情(文字コード，`gs`スクリプトのフォントなど)についてご存知の方いたら，アドバイスよろしくお願いいたします(本題)。
s3 へPOSTでファイルをアップロードする（AWS SDK for RubyでPOSTパラメタを組み立てる）


SDKを使うと簡単にPOSTできる

```s3upload_presigned_post.rb
require "aws-sdk-resources"
require "net/http"

target_file = "test.txt"
s3 = Aws::S3::Resource.new(region: "ap-northeast-1")

obj = s3.bucket("mybucket").object(target_file)
presigned = obj.presigned_post(server_side_encryption: "AES256")

cmd = "curl -v -X POST"
presigned.fields.each do |k, v|
  cmd << " -F \"#{k}=#{v}\""
end
cmd << " -F file=@#{target_file}"
cmd << " "
cmd << presigned.url

puts cmd
puts `#{cmd}`
```
MAGELLAN BLOCKS VisionAPIの結果をBQ 複数ファイルが有る場合　後編

[前編](http://qiita.com/atusi/items/f594fe95aeb57902e6a9)では、最終的に単品ファイルの画像解析を行った。
後編では、複数ファイルがある場合のサンプルを紹介する。


# MAGGELAN BLOCKS
MBの各ブロックは、原則としてハードコードされたURLに対してアクセスするように設計されている。単品で実行する場合には条件分岐や、ワイルドカードが使えない。（2016/04/06現在）

動的に挙動を変えたい場合には、外部からボードのAPIを叩くことで任意の変数を渡すことで、特定ブロック内のフィールドに任意の文字列を渡すことができる。

`${hoge}` という記述が、ブロック内で利用可能となっており。
APIでPOSTする際に、 hogeに対して値を渡すと、ブロック内で展開される。

今回のフローでは、1フローにつき1画像の解析とBQへの1インサートとなっている。100枚の画像解析を行いたい場合には、100リクエストする必要がある。

# ボードのAPIの叩き方
各ボードはユニークなURLが割り当てられている。このURLに対して、トークン付きのPOSTを行うことでAPIを叩くことができる。

## トークンの作成方法

ボード設定内の下部にトークン生成ボタンが有ります。
<img width="655" alt="API_token.png" src="https://qiita-image-store.s3.amazonaws.com/0/4036/e50effd4-8884-d3a1-bfeb-5f97aa41ea06.png">

<img width="715" alt="API_token2.png" src="https://qiita-image-store.s3.amazonaws.com/0/4036/59dd8e4d-4324-02fb-e1a9-e905ba596071.png">

トークンコピーしておいてください。

## ブロックに変数を埋め込んでおく
今回、GCSのフルパスを外部から指定したいので、VisionAPIのブロック内の設定に変数を埋め込みます。

<img width="602" alt="VisionAPI_option.png" src="https://qiita-image-store.s3.amazonaws.com/0/4036/4ff94e16-6098-0eff-5726-6f4724d46e64.png">

２）の項目に
`${gcs_url}`
の文字列を書いておきます。

忘れずにボードを保存します。

## 単発叩いてみましょう。

```:bash
wget --post-data="" https://<YOUR-BORAD-URL>/admin/schedules/2.json?api_token="<YOUR-API-TOKEN>"&gcs_url=gs://<YOUR-BUCKET>/<SOMEWHERE>/<FILE-NAME>
```

横で、ボードのWebUI開いておくと勝手にフローがキックされるのがワカリマス。

# 画像一杯叩くには？
地味にめんどくさいです。

## 手順
1) GCSに複数ファイルをアップ
2) ファイルリストを用意する
3) ひたすらキックする。

### ファイルをアップロードする
今回は、善意の提供者より頂いた3枚の画像をアップロードしてみる

```:bash
➜  sample ls
saisyu1.jpg saisyu2.jpg saisyu3.jpg
➜  sample gsutil cp ./*.jpg gs://<YOUR-BUCKET>/mb_img_src/
Copying file://./saisyu1.jpg [Content-Type=image/jpeg]...
Uploading   gs://<YOUR-BUCKET>/mb_img_src/saisyu1.jpg:       53.88 KiB/53.88 KiB
Copying file://./saisyu2.jpg [Content-Type=image/jpeg]...
Uploading   gs://<YOUR-BUCKET>/mb_img_src/saisyu2.jpg:       57.71 KiB/57.71 KiB
Copying file://./saisyu3.jpg [Content-Type=image/jpeg]...
Uploading   gs://<YOUR-BUCKET>/mb_img_src/saisyu3.jpg:       70.21 KiB/70.21 KiB
```

### ファイル名を列挙したファイルを作る

```:bash
$ ls -1 > filelist.txt
$ cat filelist.txt
saisyu1.jpg
saisyu2.jpg
saisyu3.jpg
```


### リストに従ってキックshell

ファイルリストからファイル名抜いてきて、適当にwgetしちゃいましょう。

```:sh
#!/bin/sh

MYTOKEN="<YOUR-TOKEN>"
SRCFILE=./filelist.txt
BASEURL="https://<YOUR-BOARD-URL>/admin/schedules/2.json?"
QUERY="api_token="$MYTOKEN"&gcs_url=gs://<YOUR-BUCKET>/<SOMEWHERE-PATH>/"

echo $BASEURL

while read line; do
  wget --post-data="" $BASEURL$QUERY$line
done < $SRCFILE
```

```:shell
➜  sample ./go_visionAPI.sh
```

<img width="393" alt="result.png" src="https://qiita-image-store.s3.amazonaws.com/0/4036/51fe23f0-93d4-abdc-f055-8b1196e7b587.png">

こんな感じで、WebUI操作せずにフローが勝手に走っていきます。ちょいちょい失敗しますね。

## 結果発表
ラベル抜いてみました。

### その1

```
eyewear
sunglasses
hair
vision care
glasses
```

上記ラベルが付いた画像は↓
![saisyu2.jpg](https://qiita-image-store.s3.amazonaws.com/0/4036/34956b5b-ff9a-0ec6-ad79-c683f84c5e81.jpeg)

### その２

```
lingerie
clothing
photo shoot
dress
```

上記ラベルが付いた画像は↓
![saisyu3.jpg](https://qiita-image-store.s3.amazonaws.com/0/4036/918539cc-a5c7-90cf-61fb-0fa4c65fb1ee.jpeg)


# まとめ

ランジェリーだそうです。ｗｗｗ
ASUS Transformer t100ta タッチパッドの不具合

t100ta トランスフォーマー windows 10

なにかの拍子に、突然、
2本指操作によるスクロールや
3本指操作が効かなくなった。

windowsコントロールパネルの「プログラムのアンインストール」から
「ASUS Smart Gesture」を右クリックして「修復」を行う。

元に戻った。

サポートから、ダウンロードもできる。
http://www.asus.com/jp/2-in-1-PCs/ASUS_TransBook_T100TA/HelpDesk_Download/
カメラロールにビットマップを保存する

# 概要
TBitmap のインスタンスをカメラロールに保存したい！

# 実装

超簡単！

IFMXPhotoLibraryインターフェースを TPlatformServices から取り出して、AddImageToSavedPhotosAlbum を呼べば完了！

```delphi
uses
  FMX.Platform, FMX.MediaLibrary;

procedure SaveToCameraRoll(const iBmp: TBitmap);
var
  PhotoLib: IFMXPhotoLibrary;
begin
  if
    TPlatformServices.Current.SupportsPlatformService(
      IFMXPhotoLibrary,
      PhotoLib)
  then
    PhotoLib.AddImageToSavedPhotosAlbum(iBmp);
end;
```

#おまけ
この IFMXPhotoLibrary は Android でも定義されていて、適切な場所に保存してくれます！
OracleのSQLをdashDBのSQLへ変換するツール

OracleのSQLをdashDBのSQLへ変換するツールがあります。DCW (Database Conversion Workbench) という名前です。100%変換！とはいきませんが、かなり使えると思います。

１．必要なものをインストール/ダウンロード
　・IBM Data Studio のインストール (ibm data studio でgoole検索)
　・必要なレベルの DCW をインターネットからダウンロード (ibm dcw でgoogle検索)
　　IBM_DCW_pluginをダウンロード

２．DCWの導入（IBM Data StudioへDCWプラグインをインストール）
　・IBM Data Studioでヘルプ＞新規ソフトウエアのインストール
　・インストールウィザードで、追加＞リポジトリーの追加へいき、DCW pluginの場所を指定し、終了をクリックするとインストール開始

３．ツールを使って変換する
　・IBM Data Studioで下記のように遷移し、DCW Projectを開く
　　![1.png](https://qiita-image-store.s3.amazonaws.com/0/116483/dd9b5f1d-bfca-f915-a8dc-7f2b5398658a.png)

　・Source databaseとTarget databaseを選ぶ
　　Source database
　　![2.png](https://qiita-image-store.s3.amazonaws.com/0/116483/2a406fec-19f5-9cae-dbab-10c9eb7a682c.png)

　　Target database
　　![3.png](https://qiita-image-store.s3.amazonaws.com/0/116483/17926bc7-5380-3f7f-fecb-3cdb46435cce.png)

　・作成したProjectを右クリックし、インポートを選択
　　![4.png](https://qiita-image-store.s3.amazonaws.com/0/116483/9edcc718-0a91-0d47-c025-de52d1c9b9cc.png)

　・一般＞ファイルシステムを選択
　　![5.png](https://qiita-image-store.s3.amazonaws.com/0/116483/a2744383-32e7-517f-215a-5c51da6f5045.png)

　・ソースディレクトリの右の参照をクリックし、変換したいファイルを選択。
　　　※注意！ファイル名はかならず.sqlにすること

　・選択したファイルを右クリックし、Database Conversion＞Convert Codeを選択

　・成功すると、xxxxxx_converted.sqlが生成される
　　![7.png](https://qiita-image-store.s3.amazonaws.com/0/116483/17298e4e-01b3-cc02-8100-63503e289100.png)

以上
s3 へPOSTでファイルをアップロードする（署名バージョン4）


使用するには

* 環境変数 AWS_SECRET_ACCESS_KEY にシークレットアクセスキー
* 環境変数 AWS_ACCESS_KEY_ID にアクセスキーID
* s3_bucket に対象のバケット名
* region にバケットのリージョン
* target_file にアップロード対象のファイル名

をそれぞれ設定する必要あり

実行方法は `ruby s3upload_signature_v4.rb` のように実行。

## コード

```s3upload_signature_v4.rb
#
# POST with signature v4
#
require "base64"
require "openssl"
require "digest/sha1"
require "time"

aws_access_key_id = ENV["AWS_ACCESS_KEY_ID"]
aws_secret_key = ENV["AWS_SECRET_ACCESS_KEY"]

acl = "private"
s3_bucket = "mybucket"
current_time = Time.now
date = current_time.strftime("%Y%m%d")
region = "ap-northeast-1"
target_file = "test.txt"

timestamp = current_time.utc.iso8601.delete("-:")

# policy document
policy_document = <<EOS
{"expiration": "#{(current_time + 60 * 60).utc.iso8601}",
  "conditions": [
    {"acl": "#{acl}"},
    {"bucket": "#{s3_bucket}"},
    ["starts-with", "$key", ""],
    {"x-amz-algorithm": "AWS4-HMAC-SHA256"},
    {"x-amz-credential": "#{aws_access_key_id}/#{date}/#{region}/s3/aws4_request"},
    {"x-amz-date": "#{timestamp}"},
    {"x-amz-server-side-encryption": "AES256"}
  ]
}
EOS
policy = Base64.encode64(policy_document).delete("\n")

# calc signature(v4)
sha256 = OpenSSL::Digest::SHA256.new
date_key = OpenSSL::HMAC.digest(sha256, "AWS4#{aws_secret_key}", date)
date_region_key = OpenSSL::HMAC.digest(sha256, date_key, region)
date_region_service_key = OpenSSL::HMAC.digest(sha256, date_region_key, "s3")
signing_key = OpenSSL::HMAC.digest(sha256, date_region_service_key, "aws4_request")
signature = OpenSSL::HMAC.hexdigest(sha256, signing_key, policy)

# upload
cmd = <<__CURL_COMMAND__
curl -v -X POST \\
     -F acl="#{acl}" \\
     -F key="#{target_file}" \\
     -F policy="#{policy}" \\
     -F x-amz-algorithm="AWS4-HMAC-SHA256" \\
     -F x-amz-credential="#{aws_access_key_id}/#{date}/#{region}/s3/aws4_request" \\
     -F x-amz-date="#{timestamp}" \\
     -F x-amz-signature="#{signature}" \\
     -F x-amz-server-side-encryption="AES256" \\
     -F "file=@#{target_file}" \\
     https://#{s3_bucket}.s3.amazonaws.com/
__CURL_COMMAND__
puts cmd
puts `#{cmd}`
```

# 補足

[s3 へPOSTでファイルをアップロードする（署名バージョン2）](http://qiita.com/snaka/items/e1fbeb5c928aef1b5990#%E6%8D%95%E6%8D%89) の補足も参考に

# 参考

* [Authenticating Requests (AWS Signature Version 4) - Amazon Simple Storage Service](http://docs.aws.amazon.com/ja_jp/AmazonS3/latest/API/sig-v4-authenticating-requests.html)
Delphi で NSObject 派生クラスの型を確認する

# はじめに
型が不明なインスタンスを Object Pascal から使う方法をメモしておきます。

# 概要
今回遭遇したのは渡した引数によって返ってくるインスタンスが NSDictionary か NSArray のどちらかという凶悪なライブラリ。
型に厳格な我らが Object Pascal ではとてもピンチな状況でした。

…ていうか Objective-C だって、これ面倒でしょ…

# Objective-C の型
Objective-C は、セレクタ（メソッド）が呼べるかどうか実行時に動的に解決します。
そのため、例えば NSDictionary と NSArray のどちらかのインスタンス obj があったとき

```objc
int c = [obj count];
```

こんなコードが動作します。
これは NSDictionary にも NSArray にも同じ名前のセレクタがあるからです。

# Object Pascal の型
Object Pascal は Pascal なので型に非常に厳格です。
なので、基本的には別のクラスに同じ名前のメソッドがあっても呼び出すことはできません（基本的じゃない例外は [COM のオートメーションオブジェクト](http://docwiki.embarcadero.com/RADStudio/Seattle/ja/%E3%82%AA%E3%83%BC%E3%83%88%E3%83%A1%E3%83%BC%E3%82%B7%E3%83%A7%E3%83%B3_%E3%82%AA%E3%83%96%E3%82%B8%E3%82%A7%E3%82%AF%E3%83%88#.E3.82.AA.E3.83.BC.E3.83.88.E3.83.A1.E3.83.BC.E3.82.B7.E3.83.A7.E3.83.B3_.E3.82.AA.E3.83.96.E3.82.B8.E3.82.A7.E3.82.AF.E3.83.88.E3.81.B8.E3.81.AE.E3.82.A2.E3.82.AF.E3.82.BB.E3.82.B9)）。

```delphi
var
  C: Integer;
  Obj: NSObject;
begin
  Obj := ArrayObject; // NSArray のインスタンスを Obj に代入

  // NSObject には Count は無いので呼べない
  C := Obj.count; 

  // このようにキャストが必要 
  C := TNSArray.Wrap(Obj).count; 
end.
```

# 型が不明なインスタンスの型を決定する

ということで、Object Pascal で Objective-C のインスタンスを呼ぶ時、型が不明ながらも今回のようにある程度決まっている場合は

```objc
[NSObject isKindOfClass]
```
が使えます。

先ほどの例では

```delphi
var
  C: Integer;
  Obj: NSObject;
begin
  Obj := Somethig; // なにか

  // NSDictionary なら NSDictionary にキャスト
  if obj.isKindOfClass(objc_getClass('NSDictionary')) then
    C := TNSDictionary.Wrap(Obj).count;

  // NSArray なら NSArray にキャスト
  if obj.isKindOfClass(objc_getClass('NSArray')) then
    C := TNSArray.Wrap(Obj).count; 
end.
```

こんな風に書けます。
これで普通にアクセス出来るよ！やったね！！

#objc_getClass について

isKindOfClass の引数に Objective-C のクラスを渡す必要があるため、

```delphi
objc_getClass('クラス名') // Macapi.ObjCRuntime ユニットで定義
```
を使いました。
objc_getClass を使うとクラス名文字列から Objective-C クラスへのポインタが返ってきます。
クラスを要求するメソッドでは、この関数が使えるので覚えておくと希に良いことがあるかもしれません！

#まとめ
クラスがある程度判っている場合は isKindeOfClass が使えます！
呼び出しには objc_getClass を使います！

#おまけ：セレクタがあるか？を特定する方法

```objc
[NSObject respondsToSelector]
```

を使います。
が、Object Pascal では型が確定しないと、そのセレクタ（メソッド）も呼び出せないので、あまり意味が無いと思います。
（実際 FireMonkey のソース内でも使われていません）

それでは！アデュー！
s3 へPOSTでファイルをアップロードする（署名バージョン2）


ちょっとしたデバッグのためs3へファイルをアップロードするスクリプトを書いた

使用するには

* 環境変数 AWS_SECRET_ACCESS_KEY にシークレットアクセスキー
* 環境変数 AWS_ACCESS_KEY_ID にアクセスキーID
* s3_bucket に対象のバケット名
* target_file にアップロード対象のファイル名

をそれぞれ設定する必要あり

実行方法は `ruby s3upload_signature_v2.rb` のように実行。

## コード

```s3upload_signature_v2.rb
#
# POST with signature v2
#
require "base64"
require "openssl"
require "digest/sha1"

aws_secret_key = ENV["AWS_SECRET_ACCESS_KEY"]
aws_access_key_id = ENV["AWS_ACCESS_KEY_ID"]
s3_bucket = "mybucket"
target_file = "test.txt"

policy_document = <<EOS
{"expiration": "2016-12-31T00:00:00Z",
  "conditions": [
    {"bucket": "#{s3_bucket}"},
    {"acl": "private"},
    ["starts-with", "$key", ""],
    {"x-amz-server-side-encryption": "AES256"}
  ]
}
EOS

policy = Base64.encode64(policy_document).delete("\n")

signature = Base64.encode64(
  OpenSSL::HMAC.digest(
    OpenSSL::Digest::SHA1.new,
    aws_secret_key,
    policy
  )
).delete("\n")

cmd = <<__CURL_COMMAND__
curl -v -X POST \\
     -F x-amz-server-side-encryption="AES256" \\
     -F key=#{target_file} \\
     -F AWSAccessKeyId="#{aws_access_key_id}" \\
     -F acl="private" \\
     -F policy="#{policy}" \\
     -F signature="#{signature}" \\
     -F "file=@#{target_file}" \\
     https://#{s3_bucket}.s3.amazonaws.com/
__CURL_COMMAND__
puts cmd
puts `#{cmd}`
```

## 補足

上記コードを動作するためには以下も必要

* IAMユーザのポリシーで s3:PutObject の権限が付与されている必要あり
* acl を "private" 以外("public-read"など)に設定する場合は s3:PutObjectAcl の権限も必要

## 参考

* [HTML Forms (AWS Signature Version 2) - Amazon Simple Storage Service](https://docs.aws.amazon.com/AmazonS3/latest/dev/HTTPPOSTForms.html)
Terminalを使ってファイル名を一括置換する方法


36歳にして重度の花粉症になったかと思いきや、花粉さんとのつきあい方にすでに順応しているアトラエデザイナーの紺谷です。

さて、assetsの中にある `.css` ファイルをすべて `.scss` に変更するというかなり地味目の作業を後輩の橋川くんから依頼され、terminalとかでできるんだろうな、と思って調べてみた次第です。

まずは `assets` の `stylesheets` に移動。

```
cd app/assets/stylesheets/
```

以下のコマンドを打つと、サブディレクトリの中のファイルまで全部置換してくれる。

```
find . -name "*.css" | while read file; do mv $file ${file/.css/.scss}; done
```
LinuxにConfluenceをインストール後に発生する文字化けを解決する

# 起こった事象

LinuxにConfluenceをインストールした後に、日本語でスペースを作成すると文字化けしてしまいました。


# 原因

JDBCのドライバークラス名設定時に、文字コードの設定をしていなかったためになります。初回起動時のウィザードで、MySQL用のJDBCコネクターを使ってドライバークラス名を設定する箇所があるのですが、デフォルトでは下記のようになっています。

**デフォルト**

```
jdbc:mysql://localhost/confluence?sessionVariables=storage_engine%3DInnoDB
```


# 解決方法

こちらの設定を下記のように文字コード設定用のパラメーターをつけてあげることで解消します。

**修正後**

```
jdbc:mysql://localhost/confluence?sessionVariables=storage_engine%3DInnoDB&useUnicode=true&characterEncoding=utf8
```

とはいえ、すでにパラメータをつけずに設定をしてしまったので、confluenceをインストールしたhomeディレクトリにある`confluence.cfg.xml`に上記の記述を加えます。記述方法は下記を参照。

- [Configuring Database Character Encoding](https://confluence.atlassian.com/doc/configuring-database-character-encoding-177698.html)

```confluence.cfg.xml
<property name="hibernate.connection.url">jdbc:mysql://localhost/confluence?useUnicode=true&amp;characterEncoding=utf8</property>
```

その後、confluenceを再起動すれば解決！
オールアバウトで使っている画像リサイズシステム

先月、オールアバウトのサービス全般で使用している、画像のリサイズシステムのリプレイスを行いました。 
今まで負荷を懸念してリアルタイム変換は行っていなかったのですが、スマートフォンなど画像容量にシビアな端末が中心になったこともあり、 このタイミングでリアルタイムでリサイズできるシステムを構築することにしました。  
また、トラフィックの多いサイトでは画像の転送量がかなりの金額になるということもわかりました。特にアクセスの多い画像だと１ヶ月あたり１万円以上の転送量が掛かっていることなど、非常に興味深い数字も見ることができました。

## オールアバウトのサービスたち
* [総合情報サイトAll About](http://allabout.co.jp)
* [CafeSnap (iOS/Android向けアプリ)](http://cafesnap.me)
* [All Aboutまとめコンテンツ](http://allabout.co.jp/matome/)
* [All About News Dig](http://allabout.co.jp/newsdig/)
* [For M](http://form.allabout.co.jp/)
* [All About Japan](http://allabout-japan.com/en/)
* その他いろいろ

## 旧構成
### インフラ
* EC2(m3.large) x 2
    * ①リクエストを受ける
    * ②変換後の画像があるか確認
    * ③なければオリジナルを取得して、クライアントに返却
    * ④変換のジョブをSQSに登録
* EC2(m3.xlarge) x 1
    * ⑤バッチでキューを取得
    * ⑥オリジナル画像を取得し、リサイズ
    * ⑦変換後の画像をS3にアップロード
* SQS
* S3(変換後画像の保存用)
* CDN(Akamai)
* S3 or NFS(バックエンドの画像サーバー)

![旧画像変換構成.jpg](https://qiita-image-store.s3.amazonaws.com/0/10532/5a689c2a-6793-0b23-468c-4aa695c527f7.jpeg)
※ちょっと複雑に書いてます（実際複雑なんだけど。。）

### リサイズに使っていたもの
* PHPで書かれたアプリケーション
* ImageMagick

### 問題点
* 複雑なインフラ構成
    * トラブルの時に原因を追いにくい
    * インフラコストがかさむ
* リアルタイムじゃない
    * SPなどでは表示速度などに関わる
    * 画像がメモリを圧迫し、アプリがクラッシュする
* 高スペックのサーバーが必要
    * PHPでの処理に向いていないため、サーバースペックでカバーする必要があった

## 新構成
### インフラ
* EC2(c4large) x 2
* ELB x 1
* CDN(Akamai)
* S3 or NFS(バックエンドの画像サーバー)

![画像変換外部向け.jpg](https://qiita-image-store.s3.amazonaws.com/0/10532/c46f1b8b-670d-3805-f128-4f6f30fb5e13.jpeg)

### リサイズに使っているもの
* nginx1.8.1
* nginx_small_light
* ImageMagick
* http_perl_module
    * nginx.confだけではできない、変換サイズチェックなど

### 負荷
* 現状1台あたり、ピーク時で20req/sec
* CPU負荷10~30%
* メモリは全然使わない。4GBで十分。
* ベンチマークでは、80req/secまでは耐えられそう

![スクリーンショット 2016-04-05 21.40.32.png](https://qiita-image-store.s3.amazonaws.com/0/10532/14979bf9-80ae-02c1-69d0-00e1224b259e.png)


### コスト
* AWSのコスト削減
* 画質チューニングによるCDNのコスト削減

## Tips
* 理由がない限りはpngは避け、jpgを使うべき
    * 900x600の画像で、pngをjpgにするだけで1.5→0.35MBくらいに減る
* 画像のリサイズ処理はwidth/height最低限片方は指定するべき
    * 画質の変更のみだと殆ど容量削減が見込めない
* 画質は90くらいが妥当？GitHubやBitbucketの画像差分が便利(2-up/Swipe/Onion Skinの部分)
    * https://github.com/musclemikiya/ImageTest/commit/10452e5118b2669b5f2b7d7c155711fa214d22ee?diff=unified
* jpeghintは有効にする
* オリジンの画像サーバーが複数ある場合は、リクエストのURLパスの特定の部分から、nginxのconf内で分岐して振り分ける
* http-headerのキャッシュ時間はサービスごとに適切に設定すると、転送量削減につながる

```nginx:nginx.confの一部例
add_header Cache-Control "public";
expires 1M;
```

## 参考にしたサイト
* [nginx_small_light開発者のスライド](https://speakerdeck.com/cubicdaiya/shi-jian-ngx-small-lightru-men)
* [公式ドキュメント](https://github.com/cubicdaiya/ngx_small_light)
* [wantedlyで使用しているdockerのコンテナ](https://github.com/wantedly/nginx-image-server)
* [ベンチマークなど行っているサイト](https://siguniang.wordpress.com/2014/01/12/nginx-image-processing-server-with-s3-and-ngx_small_light/)
Immutable.jsの高階関数の引数は参照を持っている

最近Immutable.jsを導入してウキウキしていました。特にJavaScriptはオブジェクトが基本的に参照渡しなので、意識していないと変なところで値が変わることがあったので大変価値があるライブラリでした。

ところがオブジェクトの値が変なところで書き換わっていることに気がつきました。

以下のようなケースです。

```js
var objects = [
	{
		id: 1,
		name: 'Jack',
		city: 'New York'
	},
	{
		id: 2,
		name: 'Tom',
		city: 'Berkeley'
	}
];

var modified = Immutable.Seq(objects)
	.map(object => {
		object.name = object.name.toUpperCase();
		return object; 
	}).toArray();
```

元のオブジェクトは以下のように書き換わります。

```js
[
	{
		id: 1,
		name: 'JACK',
		city: 'New York'
	},
	{
		id: 1,
		name: 'TOM',
		city: 'Berkeley'
	}
]
```


途中の高階関数で与えられる引数は元の参照を持っていることがわかりました。
Blender で python スクリプトを指定したディレクトリから読む

漢なら git で Blender python スクリプト(addon)を管理したいですよね!

Blender では, なんと! 指定したパスから .py モジュールを呼んでくれる機能があります.

`User Preferences` から, `File` タブの Scripts にパスを記載します.

![blender.PNG](https://qiita-image-store.s3.amazonaws.com/0/36275/d6d84dea-cb23-0d0f-c549-a84f5a14fc15.png)


これにより, たとえば `C:\Users\syoyo\MyAwesomeScript` 以下のスクリプトを読むようになります.


## 注意事項

Blender では, `addons` ディレクトリを含んでいないとスクリプトを読んでくれないので気をつけましょう.
たとえば, 上記の設定では,

    C:\Users\syoyo\MyAwesomeScript\addons\yourmodule\*.py

のようなディレクトリとファイル構成にする必要があります.

## まとめ

これで毎回 Blender の指定したディレクトリに .py をコピーせずとも, git 管理化のディレクトリを Script s パスに指定することで効率的な Blender python スクリプト開発ができるようになります.

Happy Blender python scripting!

## 参考情報　

* Add-ons development guidelines https://wiki.blender.org/index.php/Dev:Py/Scripts/Guidelines/Addons
Macのターミナルで時間のかかるコマンドが終わったら通知を受け取る方法

最近docker buildとか時間のかかるコマンドを実行する時に終わったら通知が欲しいなーと思って調べたら以下の方法で出来ました。


# 準備
terminal-notifierパッケージをインストールするだけです

```
brew install terminal-notifier
```

# 実行
`terminal-notifier -message '{メッセージ}'`で通知を受け取れるので、これを実行するコマンドの後に繋げる形で書きます

```
{コマンド} && terminal-notifier -message '{メッセージ}'
```

実際に試してみましょう
3秒スリープした後に通知を受け取るようにします

```
sleep 3s && terminal-notifier -message 'コマンド完了'
```

<img width="358" alt="スクリーンショット 2016-04-05 17.51.05.png" src="https://qiita-image-store.s3.amazonaws.com/0/71113/33f190a3-e1d1-3d16-21ad-70b074a45eaa.png">

おお、通知キタコレ(ﾟ▽ﾟ)

ついでにコマンドをもっと簡単にしたいのでエイリアス設定をしておきます。

```~/.bashrc
alias noti='terminal-notifier -message "コマンド完了"'
```

これで`{コマンド} && noti`で通知を受け取れるので地味に便利になりました
厄介者XCTest.frameworkを使うライブラリとの戦い

ひたすら苦労した結果です。

# シュミレーターなら動く
僕は最近自分のアプリにRxSwiftを導入しはじめてチュートリアルなどの流れでRxTestも一緒に入れていたのですが、これが起動時にクラッシュを起こす厄介者でした。

同様の症状はみんな起こっているようでエラーメッセージで調べて色々思考錯誤した結果、
![スクリーンショット 2016-04-05 16.59.43.png](https://qiita-image-store.s3.amazonaws.com/0/10943/43d9c50e-c0b0-d7a9-c0b2-3e9ba72ab20a.png)
とりあえずこのように設定することでシュミレーターで動かすことが出来るようになりました。

# しかし...
しばらくはシュミレーターだけでテストしていていざ実機に入れようと思ったのですがするとまた起動時に同じエラーでクラッシュしてしまいました。

問題はiPhoneのどこのディレクトリにXCTest.frameworkが入ってるかなんですがどうやって検索しても正解は出てこず。。。


最終的にはRxTestを削除して解決しました。
公式のサンプルもRxExample-iOSはRxTestを使っていないようで結局なんだったのかという感じです。

もしなにか他の解決法あればご教授いただきたいです。
git addできないCRLFのファイルたちに向けて放つgit alias

何度もこのQiitaにお世話になった。
http://qiita.com/mist_dev/items/f3f2bb04ef57e6474779

気づけばCRLFのファイルにぶち当たる度、このページを開いてコピペしてターン

~~~
$ git add .
fatal: CRLF would be replaced by LF in repo/file.
$ find ./* -type f | xargs -n 256 nkf -Lu --overwrite
$
$ git add .
$ 
# いけたいけたふ～
~~~

って繰り返すなら一発でいける方法取ろうと思った今日

~~~
# git alias として登録 
$ git config --global alias.filter '!find ./* -type f | xargs -n 256 nkf -Lu --overwrite'

# こんな感じで使えます(filterの文言はお好みで)
$ git filter
~~~

`git add`叩くだけで`git filter`通しちゃうのもありかもしれない
Visual Studio Marketplaceからバージョンとインストール数を取得しバッジ表示

# Badge for Visual Studio Marketplace
Visual Studio Marketplaceのバッジ表示が見当たらなかったので[Shields.io](http://shields.io/)を利用し、[AppHarbor](https://appharbor.com/)上で公開してみた。
[VSMarketplaceBadge](http://vsmarketplacebadge.apphb.com/)

> Version and installs badge for Visual Studio Marketplace.

[cssho/VSMarketplaceBadge: Badge for Visual Studio Code Extension](https://github.com/cssho/VSMarketplaceBadge)

## Shields.io
オープンソース向けのバッジ提供サービス。通常、CIやホスティングサービス向けのバッジはID等を指定するだけで利用できる。
Visual Studio Marketplace向けのテンプレートはなし。
`https://img.shields.io/badge/<SUBJECT>-<STATUS>-<COLOR>.svg`で独自のバッジを作成可能。

## AppHarbor
.NET向けのPaaS。`( Azure + Heroku ) ÷ 2`みたいな感じ？

## Visual Studio Marketplace
~~Visual Studio Marketplaceの各エクステンションのページ（`https://marketplace.visualstudio.com/items?itemName={アイテム名}`）にアクセスすると`<script class="vss-extension" ...`の中にjson形式でバージョン情報やインストール数が格納されている。~~

↑の方法だとエクステンションによってデータ取得に時間のかかる物があり、GitHubのCamoのタイムアウトにひっかかる[事象](https://github.com/cssho/VSMarketplaceBadge/issues/6)が発生した。

[Microsoft/vscode]
(https://github.com/Microsoft/vscode)の[機能拡張関連の処理]
(https://github.com/Microsoft/vscode/blob/bb35b07c436eac4b170c4dac906719264d1835f6/build/lib/extensions.ts#L54)を参考にAPI経由で直接Jsonを取得できるように修正して[回避](https://github.com/cssho/VSMarketplaceBadge/commit/df913be9172e73b5fbb26a8588f89db81d3599bb)。


## VSMarketplaceBadge
`Item Name`にアイテム名：`{パブリッシャ名}.{エクステンション名}`を入力し、`Find`をクリック。
SVGへのURLとSVGイメージ自体が表示される。

![image](https://qiita-image-store.s3.amazonaws.com/0/54591/ca052f7b-8e51-bd40-bd8a-2130a29bfa18.png)

### GitHub
`README.md`に設定してみる。
![image](https://qiita-image-store.s3.amazonaws.com/0/54591/7280fbf0-3db1-551f-ce88-57e9a9e1d5e7.png)


![image](https://qiita-image-store.s3.amazonaws.com/0/54591/8fa918ad-bd2a-5c72-1492-e2e170dbf9bf.png)

### 実装

ASP.NET Web API + C#で実装。

0. リクエストから取得したアイテム名からMarketplaceにアクセスし、詳細情報を取得
1. 詳細情報からバージョンまたはインストール数を取得
2. Shields.ioにサブジェクトとバージョンまたはインストール数を投げてSVGを取得
3. SVGをレスポンスに設定

#### AppHarbor + VS2015の注意点
そのままだとビルドでコケる。
[Can't Build Asp.net mvc project generated from vstudio 2015 enterprise / Support / Discussion Area - AppHarbor Support](https://support.appharbor.com/discussions/problems/78633-cant-build-aspnet-mvc-project-generated-from-vstudio-2015-enterprise)

対応策だけ抜き出すとこれ :arrow_right: [Copy roslyn files to web project output dir after build · runesoerensen/roslyn-sample@ba145b4](https://github.com/runesoerensen/roslyn-sample/commit/ba145b4c164e07e9bb2c931581ebac90863775bc)

以下の設定をプロジェクトファイルに追記。

```xml:hoge.csproj
<PropertyGroup>
  <PostBuildEvent>
    if not exist "$(WebProjectOutputDir)\bin\Roslyn" md "$(WebProjectOutputDir)\bin\Roslyn"
    start /MIN xcopy /s /y /R "$(OutDir)roslyn\*.*" "$(WebProjectOutputDir)\bin\Roslyn"
  </PostBuildEvent>
</PropertyGroup>
```
Ubuntu16.04にelixirを入れてみた

## はじめに


唐突にElixirを試したくなったので、[エーフィーのアトリエ-アランビックの錬金術師](http://hayabusa333.tumblr.com/) を入手してみました。とりあえずいろいろ参考にしながら、環境整備を行います。

## なぜにUbuntu16.04

特に意味は無いのですが、どうせ触ることになるので、今のうちから慣れておく意味合いもあってUbuntu16.04にしました。

## Ubuntu16.04のセットアップ

こちらはがっつり割愛します・・・
これを書いている時点はBeta2ですが、14.04と同じような感じでさくさく進みました。

## Elixirのセットアップ

### apt一発

```shell-session:
# sudo apt-get install elixir
```

これで実は入ってしまうんですが、Beta2の時点では1.1.0DEVがインストールされてしまいます。
1.2系を入れたいので、ソースから入れることにします。

### まずはerlang

Erlang Solutionsのesl-erlangが、まだ16.04対応していないので、標準のerlangにします。
今回は、serverに入れるので`erlang-nox`を使いました。
また、後でelixirビルドするための`erlang-dev`と、HiPEにするための`erlang-base-hipe`もインストールします。

```shell-session:
# sudo apt-get install erlang-nox erlang-dev
# sudo apt-get install erlang-base-hipe
```

これで、Erlang/OTP 18が入ります。

### 続いてelixir

gitからelixirを落としてきます。
インストールしたばっかりでgitが入っていない場合は、gitも入れます。
うちはproxy越えの環境なので、gitにproxy設定も行いました。

```shell-session:
# sudo apt-get install git
# sudo git config --global http.proxy http://.....
# sudo git config --global https.proxy http://.....
```

gitから持ってきます。

```shell-session:
# git clone https://github.com/elixir-lang/elixir.git
```

書いている時点だと1.3.0DEVになっています。
さすがにそこまでチャレンジャーでは無いので、1.2系にしておきます。

```shell-session:
# cd elixir
# git checkout refs/tags/v1.2.4
```

後は、makeしてinstallします。

```shell-session:
# make
# sudo make install
```

では、確認してみましょう。

```shell-session:
# iex -v
Erlang/OTP 18 [erts-7.3] [source] [64-bit] [smp:4:4] [async-threads:10] [hipe] [kernel-poll:false]

IEx 1.2.4
```

okっぽいです。
Unity3dBuilder Pluginを使ってJenkinsでUnityのビルドを自動化。Androidのapkを作ってみた

#はじめに
UnityもJenkinsも初心者な筆者が、浅はかな知識でAndroidのapk出力までを自動化してみたチラ裏メモ。

##前提
- Unityは書籍とか公式ドキュメントをザッと読んでちょっとわかった気になったレベル
- JenkinsもUnity同様ちょっとわかった気になったレベル
- Unityの適当なサンプルプロジェクト用意して動かせる状態
- Jenkins環境は[Macのローカルで構築済み](http://qiita.com/unsoluble_sugar/items/db26dca5fc7df0033ae8)でジョブが動かせる状態
- とりあえずUnityでアプリのビルドを自動化する流れを掴みたい
- こまけぇこたぁいいんだよ！！

#Unity3dBuilder Pluginを使う
Unityの知見が全然無いため「バッチモードで起動」とか言われてもちょっとよくわからなかったので、そのあたりを良い感じにやってくれるプラグイン『[Unity3dBuilder Plugin](https://wiki.jenkins-ci.org/display/JENKINS/Unity3dBuilder+Plugin)』を使って楽することにした。
##Jenkinsにプラグインをインストール
[Jenkinsの管理] - [プラグインの管理] - [利用可能] から「Unity3dBuilder Plugin」をインストールしてJenkinsを再起動

## プラグインの設定
[Jenkinsの管理] - [システムの設定] - [Unity3d] の項目にて「名前」とUnityの「インストールディレクトリ」を設定

```
例）
名前：Unity5
インストールディレクトリ：/Applications/Unity/Unity.app
```

## ビルド用のスクリプトを用意
1. UnityプロジェクトのAssetsフォルダ配下に「Editor」フォルダを作成
2. ビルド用のスクリプトを配置

```Editor/MyBuilder.cs

using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using UnityEditor;

public class MyBuilder {
	// ビルド実行でAndroidのapkを作成する例
	[UnityEditor.MenuItem("Tools/Build Project AllScene Android")]
	public static void BuildProjectAllSceneAndroid() {
		EditorUserBuildSettings.SwitchActiveBuildTarget( BuildTarget.Android );
		List<string> allScene = new List<string>();
		foreach( EditorBuildSettingsScene scene in EditorBuildSettings.scenes ){
			if (scene.enabled) {
				allScene.Add (scene.path);
			}
		}	
		PlayerSettings.bundleIdentifier = "com.yourcompany.newgame";
		PlayerSettings.statusBarHidden = true;
		BuildPipeline.BuildPlayer( 
			allScene.ToArray(),
			"newgame.apk",
			BuildTarget.Android,
			BuildOptions.None
		);
	}
}
```



## ジョブの設定

### Invoke Unity3d Editor
1. ジョブの設定 [ビルド] - [ビルド手順の追加] で [Invole Unity3d Editor] を選択
2. 「Unity3d installation name」にシステム設定で指定したUnityの名前を選択
3.  「Editor command line arguments」にUnityをバッチモードで起動するコマンドを指定

```   
-quit -batchmode -executeMethod MyBuilder.BuildProjectAllSceneAndroid
```

### ビルド後の処理
1. ジョブの設定 [ビルド] - [ビルド後の処理追加] で「成果物を保存」を追加
2. 「保存するファイル」を指定（例：newgame.apk）

## ビルドの実行
1. Jenkinsでビルド実行
2. ビルドが成功すればJenkinsのジョブ画面に「最新成功ビルドの成果物」としてapkのダウンロードリンクが張られている
3. apkを実機にインストールするなどして動作確認する

おわり。

# 追記：iOSのXcodeプロジェクトを自動作成する
iOS向けにXcode用プロジェクトを自動化するスクリプトも書いたので、本件と合わせてGitHubに上げておきました。
[UnintyアプリのビルドをJenkinsで自動化するためのスクリプト]
(https://github.com/unsolublesugar/jenkins-build)

関連記事も書いたのでご参考までに。
[UnityのiOSビルドで出力されるXcodeプロジェクトの設定自動化。ファイル毎のARC無効設定を追加する - Qiita](http://qiita.com/unsoluble_sugar/items/c459352af2bef8a4699e)
[UnityのiOSビルドで出力されるXcodeプロジェクトのEnable Bitcodeを自動でNoにする - Qiita](http://qiita.com/unsoluble_sugar/items/4096b37c8ea045d48b2e)

#参考
[UnityのビルドをJenkins氏に任せて楽したい。 - ともち屋](http://tomocha.hatenablog.com/entry/2013/07/23/001305)
[Jenkinsを使ったUnityのバッチビルド | TRIDENT Mobile &amp; Network Lab. Blog](http://www.trident-game.com/blog/2013/06/05/jenkins%E3%82%92%E4%BD%BF%E3%81%A3%E3%81%9Funity%E3%81%AE%E3%83%90%E3%83%83%E3%83%81%E3%83%93%E3%83%AB%E3%83%89/)
GitBookで体制図を書きたい


シーケンス図やフローだけじゃなくて、体制図や連絡フローにも利用してみたかった。

## 1. gitbookの環境づくり
ディレクトリを作る。

```
mkdir organization-chart
```

gitbookの初期化。

```
gitbook init

info: init book at /Users/bearjet/Develop/e-book/organization-chart
info: detect structure from SUMMARY (if it exists)
info: create SUMMARY.md
info: create README.md
info: initialization is finished

Done, without error
```

gitbookをビルドしておく。

```
gitbook build
info: loading book configuration....OK
info: load plugin gitbook-plugin-highlight ....OK
info: load plugin gitbook-plugin-search ....OK
info: load plugin gitbook-plugin-sharing ....OK
info: load plugin gitbook-plugin-fontsettings ....OK
info: >> 4 plugins loaded
info: start generation with website generator
info: clean website generatorOK
info: generation is finished

Done, without error
```

gitbookを見る。

```
gitbook serve
Live reload server started on port: 35729
Press CTRL+C to quit ...

info: loading book configuration....OK
info: load plugin gitbook-plugin-mermaid-2 ....OK
info: load plugin gitbook-plugin-highlight ....OK
info: load plugin gitbook-plugin-search ....OK
info: load plugin gitbook-plugin-sharing ....OK
info: load plugin gitbook-plugin-fontsettings ....OK
info: load plugin gitbook-plugin-livereload ....OK
info: >> 6 plugins loaded
info: start generation with website generator
info: clean website generator
info: OK
info: generation is finished

Starting server ...
Serving book on http://localhost:4000
```

http://localhost:4000


## 2. 図をmarkdownで描きたい
http://knsv.github.io/mermaid/
mermaidを利用する。


### gitbook-plugin-mermaid-2
https://github.com/morlay/gitbook-plugin-mermaid-2
`2`ってついているほうが、良いみたい。普通のmarkdownのコードの中に書ける。

```
npm init
npm install gitbook-plugin-mermaid-2
```

バージョンを確認。

```package.json
.
.
.
  "dependencies": {
    "gitbook-plugin-mermaid-2": "0.0.3"
  },
.
.
.
```

book.jsonを作成する。
themeは通常とforestが最初に用意されているようでした。
お好みの色合いでイケるのかな？

```book.json
{
    "plugins": ["mermaid-2"],
    "pluginsConfig": {
      "mermaid-2": {
         "theme": "forest"
      }
    }
}
```

試しに、連絡フローを書いてみる！

```README.md
	# 連絡フロー
	
	```mermaid
	graph LR;
	    Aさん-->Bさん;
	    Bさん-->Cさん;
	    Cさん-->Dさん;
	    Cさん-->Eさん;
	    Cさん-->Fさん;
	```
```

gitbookをビルドする。

```
gitbook build
```

![連絡フロー](https://qiita-image-store.s3.amazonaws.com/0/41774/8250b44e-f6a0-59e1-a53a-84d0fd826f9e.png "スクリーンショット 2016-04-06 17.46.33.png")

体制図もイケそうです。

### Atomエディタのプラグイン
https://github.com/y-takey/atom-mermaid
いちいちビルドするのは辛いから。助けてもらいます！！
`node-gyp`が必要。

```
npm install -g node-gyp
```

markdown文書全体だとPreviewできず、チャートのみで利用可能。

```ng.md
	# Introduction

	```mermaid
	graph TD;
		A-->B;
		A-->C;
		B-->D;
		C-->D;
	```
```

```ok.md
	graph TD;
		A-->B;
		A-->C;
		B-->D;
		C-->D;
```
【AWS】Lmabdaでinstance（running）を監視してslackに通知する

####起動しているインスタンスをチェックして通知します。
####クーロンで回す想定で書いてます。お遊び



外部モジュールのslackwebを使っているのでローカルでzip化してアップロードします。
その辺は[過去の記事](http://qiita.com/Yuki_BB3/items/51ba644208099e6fe2d4)に書いているので参考にしてみてください。
slack周りの設定は[ここ](https://www.hands-lab.com/tech/entry/1077.html)に詳しく書いてます。




```python:lambda_function.py
from __future__ import print_function
import json
import slackweb
import boto3



ec2 = boto3.client('ec2')
SLACK_POST_URL = "https://hooks.slack.com/*****"




def lambda_handler(event, context):
    print('Loading function')
    result = chk_running_instances()
    if result == []:
    	slack_post("[INFO] 0 running-instance ")
    else:
    	i = len(result)
    	for a in range(0, i):
    		instance_id = result[a].keys()
    		instance_type = result[a].values()
    		post_message = "[INFO] Running instance is... instance_id: %s, instance_type: %s"%(instance_id, instance_type)
    		slack_post(post_message)

    		
    		    		
    		    		    		    		
def chk_running_instances():
    response = ec2.describe_instances(
        Filters=[
            {
                'Name': 'instance-state-name',
                'Values': [
                    'running',
                ],
            },
        ],
    )
    
    instance_ids = []
    instance_type = []
    info = []
    i = len(response['Reservations'])
    
    for a in range(0, i):
        instance_ids.insert(a, response['Reservations'][a]['Instances'][0]['InstanceId'])
        instance_type.insert(a, response['Reservations'][a]['Instances'][0]['InstanceType'])
        info.insert(a, {instance_ids[a]:instance_type[a]})
    return info




def slack_post(post_massage):
    slack = slackweb.Slack(url=SLACK_POST_URL)
    slack.notify(text=post_massage, username="coffee-bot", icon_emoji=":coffee:")

```

昔書いた書きかけの記事が出てきたので公開。
余力があったら最近書いたやつをそのうち上げる・・・
ターミナル（コマンドプロンプト）のウィンドウ（タブ）によってコマンドが効かない（command not foundとなる）

「node -v」とか「gulp」とコマンドをうっても、
command not found となってしまう。

#原因：
新しく開いたシェル？ウィンドウ（タブ）で、新しくインストールしたものが、それ以前に開いていたシェルには反映されていないため

#解決策シ
シェルの設定ファイル（zshなら　.zshrc）の再読み込み
source ~/.zshrc

これで、再度コマンド

で、解決
Windows10でPackageManagementを使ってみた

Windows10 からパッケージ管理ツールとして `PackageManagement` がプリインストールされたとのことで `Chocolatey` を飛び越して使ってみた。（実際は `Chocolatey` からアプリケーションをインストールしている）

# スクリプト実行ポリシーの変更

管理者権限で PowerShell を起動し、以下を実行。

```
> Set-ExecutionPolicy RemoteSigned
```

以降、管理者権限で作業は続けた。
通常ユーザーでもできそうな情報はあるがうまくいかなかった。

# フォント変更

日本語が文字化けするためプロパティから日本語フォント（今回はラスター）を選択。

日本語フォントを選択できない場合は、以下のコマンドで文字コードを変更する。

```
> chcp 932
```

# PackageProvider に chocolatey 追加

```
> Get-PackageProvider chocolatey
```

# アプリケーションのインストール

`Find-Package` でインストールしたいアプリケーションを検索し、インストール。

```
> Find-Package -Name xxxx
> Install-Package -Name xxxx
```

途中で `NuGet` のインストールを求められたらインストールする。
アプリケーションによって成功するもの失敗するものがあり、不安定だった。

以下は出力されたエラー。
解決しないので `PackageManagement` は使わずにインストールした。

```
> Install-Package GoogleChrome

パッケージは、信頼済みとマークされていないパッケージ ソースから取得されています。
'chocolatey' からソフトウェアをアンインストールしますか?
[Y] はい(Y)  [A] すべて続行(A)  [N] いいえ(N)  [L] すべて無視(L)  [S] 中断(S)  [?] ヘルプ (既定値は "N"): A
Install-Package : パッケージの参照 'C:\Users\shiza\AppData\Local\Temp\chocolatey\GoogleChrome\GoogleChromeinstall.msi' を解決できません。
発生場所 行:1 文字:1
+ Install-Package GoogleChrome
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidOperation: (C:\Users\shiza\...romeinstall.msi:String) [Install-Package]、Exception
    + FullyQualifiedErrorId : UnableToResolvePackage,Microsoft.PowerShell.PackageManagement.Cmdlets.InstallPackage
```

その他、エラーも出ずにインストールが成功したように見せかけるケースもあった。
インストール処理は実際はインストーラを実行しているだけのため、成功していればスタートメニューに表示される。

インストール時に以下の警告も表示された。
`ExecutionPolicy` が効いていればでないという情報もあったが。。。
とりあえず「すべて続行」でうまくいった。

```
> Install-Package -ProviderName Chocolatey vim

パッケージは、信頼済みとマークされていないパッケージ ソースから取得されています。
'chocolatey' からソフトウェアをアンインストールしますか?
[Y] はい(Y)  [A] すべて続行(A)  [N] いいえ(N)  [L] すべて無視(L)  [S] 中断(S)  [?] ヘルプ (既定値は "N"): A

```


# git インストール

```
Install-Package -Name git
```

# posh-git インストール

PowerShell から便利に git を使えるらしいのでインストールしてみた。

## PsGet インストール

```
> (new-object Net.WebClient).DownloadString("http://psget.net/GetPsGet.ps1") | iex
```

## posh-git インストール

```
> Install-Module posh-git -Startup
"C:\Users\shiza\OneDrive\ドキュメント\WindowsPowerShell\Modules" is added to the PSModulePath environment variable
Creating PowerShell profile...
C:\Users\shiza\OneDrive\ドキュメント\WindowsPowerShell\Microsoft.PowerShell_profile.ps1
Adding posh-git to profile...
posh-git sucessfully installed!
Please reload your profile for the changes to take effect:
    . $PROFILE
Module posh-git was successfully installed.
```

## プロファイルのロード

```
> . $PROFILE
```


# 感想

調子が良いときは Homebrew 的に使えて便利だが、不安定な挙動もあり「もう少し」といった感想。
インストーラを実行しているだけなので、全部デフォルトの設定でインストールされる点も不満。
自分はデスクトップにアイコンを作らないようにインストールする派のため、 PackageManagement でインストール後、ショートカットを自分で削除した。
OpenSSL＆cURLのバージョンアップ時に自己証明書の設定でドハマリした

## 経緯
脆弱性対応のためにOpenSSLをアップデート。
それに伴い同時にcURLのアップデートも行った。
アップデート後のバージョンは以下の物。
**・OpenSSL v1.0.1s**
libcrypto.a, libssl.a
**・cURL v7.48.0**
libcurl.a

## 問題発生
通信を実行すると以下のログが出力された。

```
SSL: CA certificate set, but certificate verification is disabled
```

## 原因
問題が発生したプロジェクトでは以下のように ifdef を使いデバッグ時（テスト環境）では証明書のチェックを無効にしていた。

```sample.c
    curl_easy_setopt(curl, CURLOPT_CAINFO, caPath);
#ifdef DEBUG
    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0);
    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 0);
#else
    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 1);
    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 2);
#endif
```

問題の原因は **CURLOPT_CAINFO** であった。
このコードでは証明書のチェックを行う場合も行わない場合も証明書のパスをセットしていた。
アップデート後のcURLでは**証明書のチェックを行わない場合はパスのセットも行わない**必要がある。

## 解決
以下のように改修することで正常に通信を行うことができた。

```sample.c
#ifdef DEBUG
    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0);
    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 0);
#else
    // 証明書のチェックを行う場合にパスをセットする
    curl_easy_setopt(curl, CURLOPT_CAINFO, caPath);
    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 1);
    curl_easy_setopt(curl, CURLOPT_SSL_VERIFYHOST, 2);
#endif
```
Oracle APEX体験チュートリアルがステキな件

Oracle APEXとは、、

> Oracle APEXはOracle Database/Oracle Database Cloud Serviceに付属しており、無償でご利用いただくことができます。モバイルにも対応したデータベース・アプリケーションを手軽に作成できるツールで、さまざまな情報をOracle Databaseで一元管理するための環境を"ノンプログラミング"で作ることができます。

さて、APEXで作ったサンプルサイトが[こちら](https://apex.oracle.com/pls/apex/f?p=96826:1:4942759859647:::::)にあるのですが、とてもよく出来ています。
![Snap1.jpg](https://qiita-image-store.s3.amazonaws.com/0/108349/0b67a88a-e431-337e-8614-8c2b424c7176.jpeg)


このサイトにアプリの一部を作成してみるチュートリアル資料が貼ってあります（[これ](https://faq.oracle.co.jp/app/answers/detail/a_id/2854)）。とてもよく出来ているチュートリアルですが、1点だけつまづいたので以下に共有します

資料P.34-6でサンプルデータCSVをUPするところで、資料通りの手順(copy&paste)だと列を認識してくれませんでした。P.34で"Upload file"を選択、その後文字コードを"Japanese ShiftJIS"にすると文字化けせず上手くUPできました

これ以外は全く無問題で、表のメンテ画面やグラフで分析画面等がコーディングレスで簡単に作れます。試すと感動するのでぜひどうぞ。資料は（[こちら](https://faq.oracle.co.jp/app/answers/detail/a_id/2854)）です
停止時刻を用いたAR(1)単位根検定

##背景
　AR過程は定常か非定常かという判断基準は単位根を持つか持たないかとなります。単位根検定で、よく知られる方法はDicky-Fullerテスト(ADF)です。サンプリングサイズが小さい場合、ADFテストの検出パワーはそれほど高くありません。なぜならば、単位根過程(❘β❘=1)と定常過程(❘β❘<1)の収束分布は違うのです。もし、単位根過程と定常過程は同じ分布に収束するなら、検出パワーは上がるのではないか。実は、停止時刻を用いて、単位根過程と定常過程は同じ収束分布になります。
##AR(1)モデル
![unitroot.png](https://qiita-image-store.s3.amazonaws.com/0/114190/fb14ee6f-1aa8-53c2-cacd-6f2ef5731483.png)
誤差項は期待値0、分散σ^2を持つとします。  
##停止時刻
![unitroot2.png](https://qiita-image-store.s3.amazonaws.com/0/114190/e4bb57df-81d0-703c-9db1-53cd0d2e83e2.png)
 ある観測値の関数は初めて設定値m^2を超えたらサンプリングが止まります。止まった時点のサンプリングサイズTmは停止時刻といいます。停止時刻を使う場合、サンプリング数は一定ではないが、設定値m^2より大きいことは共通なのです。設定値mを無限大にするとサンプリングを無限まで取るのは可能です。単位根過程と定常過程は同じ収束分布を持つようになります。ここで、理論の展開しません。興味がある方に、別途で論文を紹介をさせていただます。
Lai,T.L. and Siegmund,D.(1983) Fixed accuracy estimation of an autoregressive parameter. Ann.Statist.11 478-485
##検定
観測値{yt} t=0,1,2,...,T
最小二乗法で、βの推定値bは
![unitroot3.png](https://qiita-image-store.s3.amazonaws.com/0/114190/75f4c436-9c83-8e4a-1ef1-e8cbd55b0f6a.png)
統計量
![unitroot4.png](https://qiita-image-store.s3.amazonaws.com/0/114190/1fc6c9de-9fdb-28c9-c816-16c9b7d1d26e.png)
データから推定されたm(b-β)は標準正規分布に従うことになります。

　まず、β=1の設定で、時系列データを作ります。実行回数を1000回、棄却率を0.05に設定します。mの設定値は100にします。

　帰無仮説：β=1(単位根を持つ)
　対立仮説：β<1(単位根を持たない)
##結果
：![unitroot5.png](https://qiita-image-store.s3.amazonaws.com/0/114190/6fe953ff-f57c-79cd-9daf-bcf8ff10d6e6.png)
###停止時刻を用いた単位根検定
サンプリングサイズの平均：204.946
βの推定値：1.000395
棄却率：0.038　(1000回の中に、38回が単位根を持たない)
###ADF検定
サンプリングサイズ：1000
棄却率:0.188　(1000回の中に、188回が単位根を持たない)

##結論
1．ADF検定と比べ、サンプリング数が少ないのに、停止時刻を用いたAR(1)単位根検定はより精度高く単位根を検出できる。
2．定常過程と単位根過程は同じ収束分布を持つ。

##コード

```r:
p=1    # order
a<-0.05    # 棄却率
sp<-1000    # サンプリング数
n<-1000    # 実行回数
m<-100    # mの設定値
s<-1    # 誤差項の分散
b<-1    # βの設定値
b0<-1    # 帰無仮説
result<-matrix(0,1,7)
colnames(result)<-c("stopping time","bh","sh","z","rule","reject rate","adf")
R<-matrix(0,nrow=n,ncol=6)
y0<-matrix(0,nrow=1,ncol=n)
e<-matrix(rnorm((sp+p)*n,0,s),nrow=sp+p,ncol=n)
e[1:p,]<-0
y<-matrix(0,nrow=sp+p,ncol=n)

# Data
for(i in (p+1):(p+sp)){y[i,]<-b*y[i-1,]+e[i,]}

# SURT
for(j in 1:n){
  for(k in 5:sp){
    Y0<-cbind(y[1:k,j])
    Y1<-cbind(y[2:(k+1),j])
    f<-t(Y0)%*%Y0/m^2
    bh<-solve(t(Y0)%*%Y0/m^2)%*%(t(Y0)%*%Y1/m^2)
    s2h<-t(Y1-c(bh)*Y0)%*%(Y1-c(bh)*Y0)/(k-1)
    if(f/s2h>=1)
      break}
  R[j,1]<-k
  R[j,2]<-bh
  R[j,3]<-s2h
  R[j,4]<-m*(bh-b0)
  R[j,5]<-f/s2h
  }
R[which(R[,4]< qnorm(0.05)),6]<-1

# ADF test
Radf<-matrix(0,n,2)
for(l in 1:n){
  df<-tseries::adf.test(y[,l])
  Radf[l,1]<-df$statistic
  }
Radf[which(Radf[,1]< -2.86),2]<-1

result[1,1]<-mean(R[,1])
result[1,2]<-mean(R[,2])
result[1,3]<-mean(R[,3])
result[1,4]<-mean(R[,4])
result[1,5]<-mean(R[,5])
result[1,6]<-sum(R[,6])/n
result[1,7]<-sum(Radf[,2])/n
result
```
2016年から始めるCSS~環境構築編~

## 使用するSyntax
PostCSSを使用することで、W3C標準や独自定義など、様々なSyntaxに対応できるようにします。

## PostCSS
* [公式サイト](https://github.com/postcss/postcss)
* jsでいうところのbabelのようなものです(cssが付いているからややこしい・・やっぱbabelって神だな・・)
* 本体はcssファイルを読み込んでAST(Abstract Syntax Tree)を作成するだけです
* ASTからのtransformはPluginが実行します
* transformの書き出し(stringify)はPostCSSが実行します
* codeはbabelよりも読みやすいです :+1: 
* cssのsyntaxの一種ではないです
* syntaxを定義するのはPluginの方でやります

## 環境構築
webpackを使用します。基本的な使用方法は前提となっています。

```bash:install
$ npm install --save-dev postcss-loader

# browser-vendor個々のprefixを設定するautoprefixerと
# sassのような記法が使えるprecssのpluginもインストールします
$ npm install --save-dev autoprefixer precss
```

webpack.config.jsを編集します

```js:webpack.config.js
'use strict';

var webpack = require('webpack');
var path = require('path');
var precss = require('precss');
var autoprefixer = require('autoprefixer');

var env = process.env.NODE_ENV;
var config = {
  module: {
    loaders: [
      ...,

      {
        test: /\.css$/,
        loader: "style-loader!css-loader!postcss-loader"
      },

      ...,
    ]
  },
  ...,

  postcss: function() {
    return [autoprefixer, precss];
  }
};

module.exports = config;
```

参考： https://github.com/postcss/postcss-loader
参考： https://github.com/jonathantneal/precss (postcss-scssをインストールすると書いてあるが、実際なしでも動く)

buildすれば正常に動作します。

これだけだとただscssをビルドしているだけ(それでも便利)ですが、pluginを使用すれば色々なsyntaxが利用できるようになります。
pluginを作れば自分だけのsyntaxを定義することも可能です。

PostCSS Plugin使用編に続く・・・（完）
MySQLがERROR! The server quit without updating PID fileで起動できないときにやったこと

# 事象

Mac OS XでMySQLを起動しようとしたところ、エラーで起動できない。
(MySQLはbrew経由でインストール)

## コンソールのエラーメッセージ

```bash
mysql.server start
... ERROR! The server quit without updating PID file [ディレクトリパス].
```

# 結論
/tmp/mysql.sockの削除で解消。

# やったこと

## エラーログ見る

```bash
$ tail -f /usr/local/var/mysql/[マシン名].local.err
```

参考：http://easyramble.com/mysql-server-pid-file-error.html

### 結果

```
Can't start server : Bind on unix socket: Address already in use
Do you already have another mysqld server running on socket: /tmp/mysql.sock ?
```

他のMySQL動いてね？と言われるのでプロセス見にいく

## プロセスをチェック

```bash
$ ps aux |grep mysql
```

### 結果
プロセスはなし。一応ポートも見にいく。

参考：http://stackoverflow.com/questions/14179434/mysql-service-does-not-startaddress-already-in-use

## ポートが空いてるか確認

```bash
$ netstat -na | grep LISTEN
```

or

```bash
$ sudo lsof -i :3306
```

### 結果

3306(MySQLのデフォルト)は空いてた。

## /tmp/mysql.sockを削除

```bash
$ rm /tmp/mysql.sock
```

参考：http://iainbarnett.me.uk/articles/mysql-cant-start-server/

### 結果

解決。
vagrant起動不可、再び

ま～た上がらない。
久しぶりにvagrant upしたら上がらない。

結構あいだ空いてしまって、その間にやった事と言えば、windows10へのupdate。

以下、エラーメッセージ。
The guest machine **entered an invalid state** while waiting for it
to boot. Valid states are 'restoring, running'. The machine **is in the
'saved' state**. Please verify everything is configured
properly and try again.

If the provider you're using has a GUI that comes with it,
it is often helpful to open that and watch the machine, since the
GUI often has more helpful error messages than Vagrant can retrieve.
For example, if you're using VirtualBox, run `vagrant up` while the
VirtualBox GUI is open.

The primary issue for this error **is that the provider you're using
is not properly configured**. This is **very rarely a Vagrant issue**.

まず、関係ないかもしれないが、
https://www.virtualbox.org/wiki/Downloads
にて、extension packをダウンロードし、インストール。
これはインストールというより、機能追加的な動き。

次に、以下のブログを参考に、
http://blog.offline-net.com/2014/03/30/virtualbox-host-only-network-unable-to-connect/

virtual-box host-only ethernet adapter #3
を作成した。

![2016-04-06.png](https://qiita-image-store.s3.amazonaws.com/0/111408/fad3c0b1-52cc-f42e-eb65-7c9ec763e6eb.png)

はじめはこのホストオンリーアダプタータブ内は何もなかったのですが、
一度「＋」ボタンを押すと、adapter #2が作成された。

この状態でvagrant up しても変わらず。

もう一度「＋」を押すと#3が作成された。

ネットワークのところのホストオンリーアダプターに、adapter #3とあるので、#3が
必要だったのだろう。

この後のvagrant upで起動ＯＫ！

ブログにある、dhcpタグを含めたipアドレス等の設定は何も行っていない。
ただ、「＋」ボタンを２度押しただけだ。

ちなみに、以下のブログの
http://d.hatena.ne.jp/kobarn/20150805
はやってみたが、自分の事象には効果なかった。
SQLITEにて混乱したこと。

http://dotinstall.com/lessons/basic_sqlite

sqlite。なかなか扱いやすい。コマンドも直観的でよい。


http://dotinstall.com/lessons/basic_sqlite/6418

.outputコマンドは、混乱しました。

sqlite> .output users.dump

これ以降、
sqlite> .show
しても、全然画面に出てこない。

.showで、outputの値が変わった事を確認したかった訳なんですが・・・

要は、すべての出力がusers.dumpに向かうんですね。
当たり前ちゃ当たり前ですね。

sqlite> .output users.dump
この段階で、users.dump（空ファイル）が作成される。
それ以降に、user.dumpに全て出力する準備状態となる。

sqlite> .output stdout
これを叩くまで、上記の状態が続く訳です。
RubyOnRails続き

規約。
直観的にはピンと来ないけど、規約自体はあった方が絶対よい。

規約）
①　model → Project
②　tabel → projects
③　class → Project
④　controller → Projects

以下、例文）
①　$ rails g model Project title

②　sqlite> select * from projects;
   resources :projects

③　irb(main):004:0> Project.create(title: "p2")

④　$ rails g controller Projects


http://dotinstall.com/lessons/basic_rails_v2/24915


project.rb

class Project < ActiveRecord::Base
    validates :title, presence: true
end

から、↓に変更したら、

class Project < ActiveRecord::Base
    validates :title, 
    presence: { message: "入力してください" },
    length: { minimum: 3, message: "短すぎ！" }
end

どうしても、
We're sorry, but something went wrong.
になってしまう。

後日、project.rbを開いてみたら、

    presence: { message: "入力してください" },
    length: { minimum: 3, message: "短すぎ！" }

この、日本語部分が文字化けしてました。
（本当はvimの画面をコピペしたいが、できない）

しょうがないので、日本語を使わないようにした。
（本質とは関係ないので、取り敢えずあきらめる）
Spring Boot で @Async の処理が待ってから落ちるようにする

Spring Boot で `@Async` をつけた処理は非同期で実行されますが、
そのままだとアプリ停止時に容赦なく途中で落ちます。
悲劇……それを回避したい。

以下の手順で実現できます。

0. `@Async`で使われるプールを指定
0. アプリ停止時に、プール内のタスクが完了するまで待つようにする

## プールの定義

```
@Bean
public ThreadPoolTaskExecutor asyncExecutor() {
    ThreadPoolTaskExecutor threadPool = new ThreadPoolTaskExecutor();

    // 最大3タスク
    threadPool.setCorePoolSize(3);
    threadPool.setMaxPoolSize(3);

    // アプリ終了時にshutdown
    threadPool.setWaitForTasksToCompleteOnShutdown(true);
    // shutdown時に実行完了を最大15分待つ
    threadPool.setAwaitTerminationSeconds(60 * 15);

    return threadPool;
}
```

`setAwaitTerminationSeconds`も設定しないと、結局待たないので注意

## `@Async`の設定でプールを指定

```
@Configuration
@EnableAsync
class AsyncConfigurer extends AsyncConfigurerSupport {

    @Autowired
    private ThreadPoolTaskExecutor asyncExecutor;

    @Override
    public Executor getAsyncExecutor() {
        return asyncExecutor;
    }
}
```

`@Async`で実行するプールを指定する事もできる。これはデフォルトで使われる物を指定。

`ThreadPoolTaskExecutor` を `getAsyncExecutor` で作ればよくね？とも思ったけど、停止時のあれこれが動かなくなる。Beanである事が大事。

これで動かした感じ、`kill -15`しても終わってから落ちる。イェイ！