OmniAICreator/Qiita-1.07M huggingface dataset:
osxcでMacの開発環境構築を自動化する

## 概要

`brew bundle Brewfile` の代替を探していたところ、
`osxc` というものがありましたので、導入してみました。

* [osxc](http://osxc.github.io/)

`Ansible` を利用して `Homebrew` を操作しているツールです。
`Ansible` の要領で Mac のセットアップを記述できますので、
`brew bundle Brewfile` ではできなかった設定も施すことができます[^1]。

## 導入

[osxc/starter](https://github.com/osxc/starter) の README によると、
公式ページで紹介されているやり方は古くなっているようですので、
README に記載されている手順を参考に導入します（一部改変しています）。

1. `XCode Command-Line tools` 導入

    ```
    xcode-select --install
    ```

    上記のやり方でインストールできない場合、以下の対応を行います。

    > 参照:[Manual Install of Xcode command line tools not working](http://stackoverflow.com/questions/23260748/manual-install-of-xcode-command-line-tools-not-working)

    ```
    1) Open Xcode app.
    2) Click on Xcode > Open Developer Tools > More Developers Tools.
    3) Download Command Line Tools for your Mac OS X version.
    ```

    あるいは、 Xcode を介さずデベロッパポータルから直接インストールします。
    こちらの手順であれば、 Xcode のインストールは不要です。

    ```
    https://developer.apple.com/downloads/index.action
    Downloads for Apple Developers -> Command Line Tools
    ```

2. `Homebrew` 導入

    [公式ページ](http://brew.sh/)で最新の手順を確認し、導入します[^2]。

    ```
    ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
    brew doctor
    brew -v
    brew update
    ```

3. `Ansible` 導入

    ```
    brew install ansible
    ```

4. `osxc` 導入

    ```
    git clone https://github.com/osxc/starter.git ~/osxc
    cd ~/osxc
    ansible-galaxy install -r requirements.yml
    ```

5. インストール設定調整

    インストールしたいツール・行いたい処理に関して、
    既に記述されているサンプルを参考に設定を行います。

    ```
    vi configuarion.yml
    vi install.yml
    ```

6. `osxc` 実行

    ```
    ansible-playbook desktop.yml
    ```

2台目以降の PC であれば、
`osxc` は自分用にカスタマイズしたリポジトリからクローンする形が良さそうです。
GitHub 上で Fork したのであれば、そのリポジトリを使います。

## ディレクトリ構造

```
.
├── LICENSE
├── README.md
├── ansible.cfg
├── configuration.yml
├── desktop.yml
├── dotfiles
│   ├── tmux.conf.local
│   ├── vimrc.bundles.local
│   ├── vimrc.local
│   └── zshrc
├── install.yml
├── inventory
├── requirements.yml
└── roles
    ├── osxc.common-env
    ├── osxc.homebrew
    ├── osxc.packages
    └── osxc.repository
```

## ワークフロー

インストールする物に関しては `install.yml` に、
インストール後の設定ファイル設置などは `configuration.yml` に記述します。

`desktop.yml` から `install.yml`, `configuration.yml` の順に呼び出している形で、
`ansible-playbook desktop.yml` として実行します。

慣れない内は、`ansible-playbook install.yml` として、
`install.yml` のみを実行する形でも良さそうです。
それだけでも `brew bundle Brewfile` でやっていたことはカバーできます。

## 課題

* 結局、1~5までは手作業を強いられますね…。
* 管理者権限が求められる際、パスワード入力待ち状態になります。  
  処理を走らせて放置とはいかず、定期的に様子をみないとだめみたいですね…。
* `brew install` 時に指定するオプションをサポートするには、  
  [osxc/packages](https://github.com/osxc/packages) の更新が必要です。

[^1]:
  事前に用意した.vimrcをVimインストール後に設置する、などです。
[^2]:
  osxc側でHomebrewは入れてくれるのですが、
  AnsibleもHomebrewで管理させたかったため、先にHomebrewを導入しました。
CircleCIで並列テストを実行する


# タイトルの並列テストってなに？
ここで指しているのは、CircleCI上で複数のコンテナを使ってテストを実行することです！2コンテナと1コンテナの時の差はこんな感じです。

下記画像の赤い部分が差異になると思います。

## 2コンテナでビルドを行った時の画面
![parallele_02.png](https://qiita-image-store.s3.amazonaws.com/0/8377/89538a97-68b5-6a62-33e0-bd4d3a1d9add.png "parallele_02.png")

## 1コンテナでビルドを行った時の画面
![parallele_01.png](https://qiita-image-store.s3.amazonaws.com/0/8377/1afc3508-c616-13bf-f392-0d479e274e36.png "parallele_01.png")

では早速、並列テストを実行するまでの手順を追っていきます。

# 並列テストで使うコンテナ数の設定を変更する
## 設定画面へ行く
![settings_01.png](https://qiita-image-store.s3.amazonaws.com/0/8377/841973c9-beb6-c8f5-7e41-ce59c7debf0a.png "settings_01.png")

## Adjust Parrallelismを開く
![settings_02.png](https://qiita-image-store.s3.amazonaws.com/0/8377/270be7f7-ed97-2425-81f8-17945a0bfa7f.png "settings_02.png")

## 自分のプランにあった、並列処理する際の最大コンテナ数を選ぶ

特にApplyやOKなどのボタンはありません！

![settings_03.png](https://qiita-image-store.s3.amazonaws.com/0/8377/64d65f04-dda1-965d-6588-13f14d5a6855.png "settings_03.png")

# ビルド設定
下記の記入例のようにparallelオプションをtrueにしてあげて、回したいスペックファイルを渡してあげればOKです。当たり前ですがfactoriesファイルなどを渡してしまうと落ちます！

```circle.ymlへの記入例
test:
  override:
    - bundle exec rspec:
        parallel: true
        files:
          - spec/features/*.rb
```

参考：[Manually setting up parallelism - CircleCI](https://circleci.com/docs/parallel-manual-setup)

## 注意
当たり前ですが、specファイル間でテストデータが依存関係があるとテストが落ちます！必要があれば、上記URLに書いてある用にいい感じにバランシングのためのシェルファイルを書いてあげるとよさそうです。

## 速度の改善具合について
2コンテナにした場合、テストだけで約2分早くなりました！(๑´ڡ`๑)
「Markdownを表示する」ボタンを追加するユーザースクリプト

「Qiitaに対する要望の投稿の非公開化」に危機感を覚えた( https://twitter.com/cielavenir/status/559560248541712384 )ので。
[Qiita要望 | 記事の Markdown を読み取り専用で表示する raw ボタン の追加 #qiita](http://qiita.com/tbpgr/items/b9baa2d82a560f42abfc)に対するユーザースクリプトをおいておきます。「Gistを開く」からワンクリックインストールが可能なはず。

```js:qiita_source.user.js
// ==UserScript==
// @name        Qiita Source
// @namespace   com.cielavenir
// @description Show link to Qiita Markdown source.
// @include     http://qiita.com/*/items/*
// @include     http://qiita.com/*/private/*
// @version     0.0.0.3
// ==/UserScript==

(function(){
	var ul=document.getElementsByClassName('itemsShowHeaderTitle_status')[0];
	if(!ul)return;
	var li=document.createElement('li');
	var a=document.createElement('a');
	a.href=location.href.split('#')[0]+'.md';
	a.textContent='Markdownを表示する';
	li.appendChild(a);
	ul.appendChild(li);
})();
```

追伸

ポエムに成り下がる恐れがあるので、これ以上のことは書きません。 **意見** については、恐れ入りますが、この記事にコメントではなく上記ツイートへのリプでお願い申し上げます。
Unable to post a notification for the current user ($USER), as it has no running NotificationCenter instance.

tmux セッションの中で何か壊れている気がする

```
tmux kill-session
tmux
terminal-notifier -message hello
```

としたら直る。

[Can't find instance of NotificationCenter · Issue #70 · alloy/terminal-notifier](https://github.com/alloy/terminal-notifier/issues/70)
NSAttributedStringで縁取りを付けた文字の色が表示されない時

# はじめに
UILabelの文字に縁取りを付加したい場合、NSAttributedStringを設定することで実現できます。

```lang:縁取り(文字色は透明)

NSDictionary *attributes = @{NSForegroundColorAttributeName:[UIColor whiteColor],
                                 NSStrokeWidthAttributeName:@1.0],
                                 NSStrokeColorAttributeName:[UIColor blackColor]};

NSAttributedString *attributedString = [[NSAttributedString alloc]
    initWithString:@"文字色は透明"
        attributes:attributes];

label.attributedText = attributedString;
```

上記では文字色を指定していますが実際はclearColorとなっています。

# NSStrokeWidthAttributeNameに負の値を設定すれば良い

```lang:縁取り(文字色は白)

NSDictionary *attributes = @{NSForegroundColorAttributeName:[UIColor whiteColor],
                                 NSStrokeWidthAttributeName:@-1.0,
                                 NSStrokeColorAttributeName:[UIColor blackColor]};

NSAttributedString *attributedString = [[NSAttributedString alloc]
    initWithString:@"文字色は白"
        attributes:attributes];

label.attributedText = attributedString;
```

NSStrokeWidthAttributeNameが負の値のときは縁取りの内側は文字色(NSForegroundColorAttributeName)となります。

# おわりに
同じ現象で悩んだ人の参考になりましたら幸いです。
OverlayFSについて


CoreOSが最近btrfsをやめてoverlayfsに移行するという発表をしたのでoverlayfsについて簡単に調べてみた。

## そもそもFileSystemとは

Wikipedia 英語版 の説明がわかりやすい。

> In computing, a file system (or filesystem) is used to control how data is stored and retrieved. Without a file system, information placed in a storage area would be one large body of data with no way to tell where one piece of information stops and the next begins. By separating the data into individual pieces, and giving each piece a name, the information is easily separated and identified. Taking its name from the way paper-based information systems are named, each group of data is called a "file". The structure and logic rules used to manage the groups of information and their names is called a "file system".
http://en.wikipedia.org/wiki/File_system


簡単にポイントを抽出すると、

- ファイルシステムとは、どうやってデータを格納し探しだすかを制御する仕組み
- ファイルシステムが無いと、ストレージに入れられた情報が、ただのデータの塊になってしまい、どこからどこまでが1つの情報で次はどこから始まるかがわからなくなってしまう
- データを情報のピースに分けて、そのピースに名前を与える
- これら情報のピースの集合と名前をどう管理するかという仕組みがファイルシステムと呼ばれる


## OverlayFSとは

[UnionFS](http://ja.wikipedia.org/wiki/UnionFS)と言われる、分離したファイルシステムのファイルやディレクトリを透過的に重ねることができる仕組みの実装の1つ

https://git.kernel.org/cgit/linux/kernel/git/torvalds/linux.git/tree/Documentation/filesystems/overlayfs.txt
([日本語訳](https://sites.google.com/site/kandamotohiro/linux/overlayfs-txt))


以下メモ


- overlayfsは上の層と下の層をマージして1つのファイルシステムに見せる仕組み
- ディレクトリだけマージするが、その他のファイルは単純に上だけが見える。上がない場合は下が見える
- このマージは、statやreaddirなどのシステムコールの値を何と報告するかを適切に調整することにより行われる
- 下の層はReadonly、上の層はReadonly/Writableどちらでも良い
- Readonlyの層はNFSや別のoverlayfsでも良い
- Wratableの時は、trusted.*拡張属性と、readdirのd_typeを返す必要があり、NFSではいけない
- Readonlyな削除を実現するため、そのディレクトリ以下のファイルを見せなくするwhiteoutという機能がある
- 上だけを見せて下を見せないという不透明というモードもある
- 下の層に対して書き込みをする際、`copy_up`と言い、上の層に内容がディレクトリ階層/メタ情報ごとコピーされる


## OverlayFSに関するニュース

- [2014/12/6] [overlayfsはlinuxカーネル3.18にマージされた](http://www.phoronix.com/scan.php?page=news_item&px=MTg1NjA)
- [2014/12/9] [linux 3.19ではmultilayer overlayfsをサポート](http://www.phoronix.com/scan.php?page=news_item&px=MTg1Nzg)
- [2015/1/18] [CoreOSはbtrfsをext4+overlayfsに移すことに決めた](http://www.phoronix.com/scan.php?page=news_item&px=CoreOS-Btrfs-To-EXT4-OverlayFS)
 - [btrfs](https://git.kernel.org/cgit/linux/kernel/git/torvalds/linux.git/tree/Documentation/filesystems/btrfs.txt) は単にUnionFSなだけでなく、高速さや大きいファイルの扱いなどかなりアグレッシブな目標を掲げている分、仕様もFixしていなく、問題も多いらしい。

## 追記

OverlayFSの挙動を簡単に実験してみました！
http://qiita.com/awakia/items/af9b46c322905cdce1d7
Dreamweaver 文字のエンコードを変える

Dreamweaver CCで文字のエンコードを変える。

修正＞ページプロパティ
![無題1.png](https://qiita-image-store.s3.amazonaws.com/0/44278/a8fbd28d-a00a-5f25-9c99-7d2b94e2bca0.png)

ページプロパティ＞タイトル/エンコーディング
![無題2.png](https://qiita-image-store.s3.amazonaws.com/0/44278/a1944bb1-d1c1-dad7-78b0-09d1c96e5919.png)

タイトル/エンコーディング＞エンコーディングのプルダウンメニューから選択してOKボタン
![無題3.png](https://qiita-image-store.s3.amazonaws.com/0/44278/8b1b6e70-3ef7-3931-b497-e616e30533c6.png)

終わり！
Prestogresを用いてGUIアプリからPrestoへアドホッククエリを発行する方法

Prestoを利用する事で、TreasureDataへのクエリ発行がアドホックに使いやすくなりました。
さらにPrestogresというライブラリによるゲートウェイが整備され、postgresqlクライアントからの接続をサポートしました。

これを用いればダッシュボード機能を有するWebアプリケーションなどから、動的にクエリ発行も出来ますね。
そういった事を実現する手前、まずはどのように接続してクエリ発行ができるのか検証してみました。

### コマンドラインで接続

基本のコマンドラインからの接続を試してみます。
まずは必要となるライブラリなどが入っていなければインストールしましょう。

```bash
# Postgresqlクライアントをインストール
## OSXの場合
$ brew install postgresql
## CentOSの場合
$ sudo yum install postgresql

# Rubyから利用するためにpgをインストール
## CentOSの場合には事前に sudo yum install postgresql-devel を実行しましょう
$ gem install pg
Building native extensions.  This could take a while...
Successfully installed pg-0.18.1
1 gem installed
```

psqlコマンドを用いて、[Presto PostgreSQL Gateway | Treasure Data](http://docs.treasuredata.com/articles/presto-postgresql-gateway)の接続情報に従い実行します。
700ms程度で集計が完了して結果が返ってきました。Prestoさまさまのスピードです。

```bash
$ psql -h pggw.treasuredata.com -p 5439 -U TD1 -W
Password for user TD1:
psql (9.4.0, server 9.3.5)
SSL connection (protocol: TLSv1, cipher: AES256-SHA, bits: 256, compression: off)
Type "help" for help.

TD1=> \t
Tuples only is on.
TD1=> SELECT count(1) FROM sample_datasets.nasdaq;
 8807278

TD1-> \q
```

### GUIクライアントから接続

続けてOSXから[PG Commander](https://eggerapps.at/pgcommander/)を利用してみましょう。

次のページによると無料枠でも割と使えるようです。

* MacOSX - Macで使えるPostgreSQL GUI client - Qiita
http://qiita.com/fukayatsu/items/0a0befefcf026de80773

まずは左側に囲ったボタンからダウンロードしましょう。
![pgcommander-web.png](https://qiita-image-store.s3.amazonaws.com/0/19199/eb0406ed-0b7a-bc7b-08f6-987d7252612f.png)

解凍して出来たPG Commander.appをアプリケーションフォルダへ移動して起動します。
[Presto PostgreSQL Gateway | Treasure Data](http://docs.treasuredata.com/articles/presto-postgresql-gateway)の接続情報に従い、入力しましょう。
![pgcommander-start.png](https://qiita-image-store.s3.amazonaws.com/0/19199/074bf9e8-37a3-0afe-0350-b92160cc8012.png)

2回目からはこのようにショートカットが出来ます。
![pgcommander-welcome.png](https://qiita-image-store.s3.amazonaws.com/0/19199/c9fb5281-d6ae-6a22-da6c-963768097479.png)

データベースやテーブルの一覧もこのように見えます。
![pgcommander-dbs.png](https://qiita-image-store.s3.amazonaws.com/0/19199/e6e404c0-625b-f087-38e4-20a421379820.png)

SQL Terminalより、クエリを実行してみましょう。
![pgcommander-sql-terminal.png](https://qiita-image-store.s3.amazonaws.com/0/19199/91e6ef25-4a5e-6332-fea7-0c6b2977c542.png)

Execute Queryボタンを押すと、次のように結果が表示されます。
![pgcommander-sql-result.png](https://qiita-image-store.s3.amazonaws.com/0/19199/c8dd34ed-fc07-94d9-fd3b-e18247a2c6ce.png)

但し、このソフトから発行されるクエリとの相性問題により、テーブルのプレビューは出来ません。
しかしながらselect句を発行すれば支障なく結果が見えるので、そこまで大きな問題では無さそうです。
![pgcommander-error.png](https://qiita-image-store.s3.amazonaws.com/0/19199/034331a4-0caa-a865-f50a-4ce413b17b4e.png)
CreateJSのTextクラスにて、テキストを自動折り返しする


## コード

```JavaScript
/**
 * @description
 * `Text`クラスのインスタンス`textInstance`の`text`プロパティに、  
 * `textInstance`の幅をはみ出さないように、自動で折り返した`text`を格納する。
 * @param {Text} textInstance 自動で折り返した`text`を格納する`Text`クラスのインスタンス
 * @param {string} text `textInstance.text`に格納する自動で折り返す文字列
 */
function setWrapText(textInstance, text) {
  var initWidth = textInstance.lineWidth;
  var textArray = text.split('');
  var i = -1;
  var prevText = '';
  var lines = [];

  textInstance.text = '';

  while (textArray[++i]) {
    textInstance.text += textArray[i];

    if (textInstance.getMeasuredWidth() > initWidth) {
      lines.push(prevText);
      textInstance.text = textArray[i];
    }
    prevText = textInstance.text;
  }
  
  textInstance.text = lines.join('\n');
}
```

## 環境

EaselJS 0.7.1

## 参考

* http://jsdo.it/turusuke/voav
* http://qiita.com/utibenkei/items/cec530da018540591bed
WindowsをLinuxっぽく使う

>2015/02/11更新：TeraTermの接続マクロでパスワードを使った例を載せました。Vagrantのインストールの方法をCentOS7版に変えました。
>2015/02/06更新：やっぱりConsole2の不安定さが気になったので、TeraTermでやる手順も追加しました

# はじめに

WindowsでGit Bashを使っていると、やはり素のLinuxが使いたくなってきます。
かといって、VMでGUIを立ち上げて使うのはかったるいです。
また、Git Bashを立ち上げてvagrant sshを起動して、というのもやはりかったるいです。

そこでVagrant+Console2、もしくは、Vagrant+TeraTermを使って、Linuxを簡単に使えるようにします。

# Vagrantのインストール

Vagrantと好きなLinuxをインストールします。
refs: http://qiita.com/yhiranoo/items/6c91b9fccdcf56069ce6

# Console2を端末にする場合（不安定かも）

## Console2のインストール

以下の通りに、Console2をインストール・セットアップします。
refs: http://m-namiki.hatenablog.jp/entry/2014/08/04/220000

さらに以下の設定にしておくと、Tabを開くだけでゲストOSのコンソールになります。
vagrant upはどこかでしておきましょう。

```
Shell: "C:\Program Files (x86)\Git\bin\sh.exe" --login -i -c "vagrant ssh"
Start up dir: Vagrantfileがあるディレクトリ
Move upでタブの位置を一番上にしておく。
```

## キーボードショートカットの変更

SettingsのHotkeysで設定できます。
ここら辺はご自由に。

```
Next tab: Ctrl+Right
Previous tab: Ctrl+Left
Close tab, Remane tab, Clear selection: 無効化
Paste: Ctrl+V
```

# TeraTermを端末にする場合（おすすめ）

以下を実施します。
refs: http://fits.hatenablog.com/entry/20130331/1364740780

vagrant_login.ttlファイルをC:\Program Files (x86)\teratermに置いておきます。
合わせて、タスクバーにピン留めしておくなどします。
TTLファイルは、ttpmacro.exeに関連付けしておきます。

これでTTLファイルをクリックすると、ダイアログが表示された後、TeraTermProが勝手に立ち上がり、Vagrantに勝手につながります。

上のリンク先は、秘密鍵を使った例ですが、パスワードを使った例はこんな感じです。

```
HOSTADDR = '127.0.0.1' 
USERNAME = 'vagrant'
PASSWORD = 'vagrant' 

COMMAND = HOSTADDR 
strconcat COMMAND ':2222 /ssh /2 /auth=password /user=' 
strconcat COMMAND USERNAME 
strconcat COMMAND ' /passwd=' 
strconcat COMMAND PASSWORD
 
connect COMMAND
 
end
```

# 作業場所へのリンク

VagrantfileがあるホストOSのディレクトリは、ゲストOSの/vagrantで共有されています。
ですので、WindowsとLinuxで共有したいファイルをすべてこの下で管理し、ホームディレクトリに、ここへのシンボリックリンクを張っておくとよいでしょう。

例えば、このディレクトリにprojectsディレクトリを作り、その中でgit cloneをする場合、こうしておきます。
```
(ゲストOS) $ ln -s /vagrant/projects projects
```

こうしておくことで、ゲストOSではgitコマンドを使いつつ、ホストOSではNetBeans IDEを使って作業、などということが実現できます。

# Console2のTIPS

Console2はちょっと不安定なところがあります。

もし、表示が崩れたら、
```$ clear```
とか
```$ stty sane```
とかを入力してみましょう。

入力できなくなったときは、しばらく放置するか、Console2を再起動してみます。
smarty マルチバイト 36文字で改行

```lang:modifier.strlen.php
<?php

if(!function_exists('smarty_modifier_strlen')) {

    function smarty_modifier_strlen($str, $width=75, $break="\n", $cut=false)
    {
        $blocks = preg_split('/'. PHP_EOL . '/', $str);
        foreach($blocks as $block) {
            $ret[] = implode(PHP_EOL, mb_str_split($block, 36, 'UTF-8'));
        }
        return implode(PHP_EOL, $ret);
    }

    function mb_str_split($string, $split_length = 1, $encoding = null) {
        if ($split_length < 1) {
            return false;
        }
        if (func_num_args() < 3) {
            $encoding = mb_internal_encoding();
        }
        $ret = array();
        $len = mb_strlen($string, $encoding);
        for ($i = 0; $i < $len; $i += $split_length) {
            $ret[] = mb_substr($string, $i, $split_length, $encoding);
        }
        if (!$ret) {
            $ret[] = '';
        }
        return $ret;
    }

}
```
RHEL6でWindowsの共有フォルダを自動マウントする

#環境
 - RedHat Enterprise Linux Server release 6.5
 - Windows7 pro
 - autofs-5.0.5-88.el6.x86_64

#設定
##Windows側共有フォルダの作成
 - c:\にtestフォルダを作成
 - testフォルダを右クリックしプロパティを開く
 - 共有タブの「共有（S）」ボタンをクリック
 - 「共有（H）」ボタンをクリック
 - ネットワークから作成したtestフォルダが共有されているかどうか確認する

##RHEL側の設定
 - autofsのインストール
 - /etc/auto.miscに下記の行を追加
 
```ini:/etc/auto.misc

# ,の後にスペースを入れると自動マウントされない
test   -fstype=cifs,rw,username=hoge,password=fuga     ://{windowsのIPアドレス}/test
```

 - 下記コマンドを実行し、設定の適応が

```shell-session:
service autofs restart
```

##自動マウントされたかどうかの確認
 - windowsからtestフォルダにファイルを配置する
 - RHELで配置されているファイルが参照できるか確認

```shell-session:
ls -la /misc/test
```
MySQLで複数のデータをUPDATE/INSERTする

```sql
ON DUPLICATE KEY
```

でユニーク制約やPK制約違反のINSERTをハンドリング出来る。

```sql
INSERT INTO member (id, name, age) 
VALUES (:id1, :name1, :age1), (:id2, :name2, :age2) 
ON DUPLICATE KEY 
UPDATE name = VALUES(name), age = VALUES(age)
```

MySQLだと

```sql
REPLACE INTO
```

文もあるけど、そっちはDELETE+INSERTなので挙動が違う。INSERT+UPDATEの方は更新するカラムが絞れるので、インデックスの再生成コスト分で有利になる事があるかもしれない。ちゃんとは調べてない。
Coronium Cloudを入れてみた

簡単にCoronaのクラウド側が作れる[Coronium](http://coronium.io/)を入れて、
簡単に動かしてみた。
Coronaを使った事が無いのでCoronaは全くわかりません。

#環境

- サーバー
t2.microでUbuntu 14.04.1 LTSを動かしている。

- クライアント
[CoronaSDK 2014.2511](https://developer.coronalabs.com/downloads/corona-sdk)を使った。

#インストール

公式サイトに行く

![スクリーンショット 2015-01-26 10.38.44.png](https://qiita-image-store.s3.amazonaws.com/0/65887/7f73ad05-ea36-28aa-8d5f-9a0acfa958e1.png)

AWS EC2 installを選択したらよくわからなかったのでUbuntuの方を選択した。
このコマンドを打つだけでインストールされる。

```
#curl -O https://s3-us-west-2.amazonaws.com/coronium-installers/ubuntu/install.sh; chmod +x install.sh; ./install.sh

```

インストール時にcoroniumと言うユーザーが作られ、apache2でCoroniumが自動的に
動く。
インストールが終わったらcoroniumになり、Homeを見てみると

```
coronium@mydomain:~$ ls
conf  files  logs  lua  php  tpl  web
```

となっているはず。
実際には管理コンソールでいじくるので触らなくても良い。

#少し触ってみる

管理コンソールに入る

```
http://mydomain/admin
```


ログインを求められるので
user: admin
password: coroniumserver

で入る。



こんな画面がでる。
![スクリーンショット 2015-01-26 10.51.28.png](https://qiita-image-store.s3.amazonaws.com/0/65887/ea78e271-f4ed-e829-e87f-6ef5e8da5843.png)



コードを書いてみる。
リスト内のCodeを押すと管理画面が出るのでそこで書く。言語はlua。
公式トップページのコードはここで書く。

HELLO.lua

```
local in_data = coronium.input()
local answer = coronium.answer( { greeting = "Hello " .. in_data.username } )
coronium.output( answer )
```

以上でサーバー側の設定は終わり。

#クライアントの準備

###1.CoronaでProjectを作る。
![スクリーンショット 2015-01-26 11.02.00.png](https://qiita-image-store.s3.amazonaws.com/0/65887/7a4996d5-3f03-0854-611d-03f6bb181aa8.png)


###2.モジュールを入れる
[Using the Module](http://docs.coronium.io/103/)の[Coronium Module for Corona SDK](https://bitbucket.org/develephant/mod_coronium/get/default.zip)を押してモジュールをダウンロードする。解答して
mod_coronium.luaをProjectに入れる。


###3.main.luaを書く

```
local coronium = require( "mod_coronium" )
coronium:init( { appId = "MY_APP", apiKey = "MY_API_KEY" } )
coronium:appOpened()
coronium:run("HELLO",{username="mizuki"})
```

ここで、MYAPPはmydomain,MY_API_KEYはコンソールのSettingsにあるのを入力する。
runの第一引数にサーバーのコードファイル名、第二引数に渡すデータを書く

###4.実行

クライアントのコンソールを見てみると

```
Jan 26 11:12:29.783: status:200
Jan 26 11:12:29.783: result:
Jan 26 11:12:29.783:    greeting: Hello mizuki
```

となっており接続できている事がわかる。

#まとめ

- **Coroniumの日本語記事少ない！**

- 結構簡単に導入できた

- corona開発者は積極的に使っていくと良いと思う
[iOS・Android]Alloyでタイトルバーをテンプレート化して作業量を減らす


タイトルバーのコードを各画面のコードに記述した場合，
画面数が３画面とかならいいのですが，５画面や１０画面など画面数が増えた場合に，
タイトルバーの仕様を変更した時にすべての画面のコードを変更するのがとても辛いです．
そして絶対に直し忘れがあったりしてモチベーションだだ下がりです．

そうならないように，タイトルバーを各画面のコードから分離して気持よくなりましょう．

タイトルバーのビューを以下のように作成します．予めバックボタンの画像をassetsフォルダ以下に置いてます．

```app/views/titlebar.xml
<Alloy>
  <View id="titlebar">
    <ImageView id="backBtn" image="/backbtn_arrow.png" onClick="doWinBack" />
    <Label id="title" text="notTitle" />
  </View>
</Alloy>
```

次にタイトルバーのスタイルを定義します．iOSの場合ナビゲーションバーに被らないようにtopの位置を指定してます．

```app/styles/titlebar.tss
"#backBtn":{
  height:"50dp",
  width:"50dp",
  left:0
}

"#titlebar": {
  top:"0dp",
  height: "50dp",
  width: Ti.UI.FILL,
  backgroundColor: "red"
}

"#titlebar[platform=ios]": {
  top: "20dp",
}
```

最後にタイトル名を親から受け取った場合，タイトル名を付与する処理と，バックボタンの関数を作成します．

```app/controllers/titlebar.js
var titleName = arguments[0].title || {};

if (titleName) {
  $.title.setText(titleName); //タイトル名を追加
}

function doWinBack(e) {
  e.source.getParent().getParent().close(); //親ウィンドウを閉じる
}
```

今回はどうしてもtitlebar.jsに書きたかったので，親ウィンドウを取得するのにgetParentを使っていますが，公式ドキュメントが無いので動作が不安です．
それに，viewの階層が変わった場合正しく動作しない可能性もあります．
その場合，alloy.jsにカレントウィンドウを保持させて，alloy.js側にバックボタンの処理を書くのも手だと思います．

これで，タイトルバーをテンプレ化できたので，タイトルバーを使う画面のviewでこのタイトルバーを呼び出して使えます．Requireタグにtitleプロパティを付与し，タイトル名を渡しています．

```app/views/index.xml
<Alloy>
  <Window class="container">
    <Require src="titlebar" title="win1" type="view" />
    <Label id="label" onClick="doClick">Window1</Label>
  </Window>
</Alloy>
```


![スクリーンショット 2015-01-26 10.57.45.png](https://qiita-image-store.s3.amazonaws.com/0/46334/45819979-0af4-0690-f653-2166aa96b97a.png "スクリーンショット 2015-01-26 10.57.45.png")

本音を言えば，ちゃんとiOS，Androidでちゃんとしたタイトルバー使うべきなんだろうけど・・・
Dock のアプリを必要なもの以外まとめて終了するスクリプト

Swift でスクリプトを書いてみた。

```swift:killdock.swift
#!/usr/bin/env swift

import Cocoa

// Dock に表示されるアプリケーションの一覧を取得
func getRegularApplications() -> [NSRunningApplication] {
    let runningApps = NSWorkspace.sharedWorkspace().runningApplications as! [NSRunningApplication]
    let regularApps = runningApps.filter { (app: NSRunningApplication) in
        app.activationPolicy == NSApplicationActivationPolicy.Regular
    }
    return regularApps
}

// ホワイトリストに含まれないアプリケーションをまとめて終了
func killApplications(apps: [NSRunningApplication]) {
    let allowed = getAllowedBundleIdentifiers()
    for app in apps {
        if contains(allowed, app.bundleIdentifier!) {
            println("Skipped \(app.localizedName!) (\(app.bundleIdentifier!))")
            continue
        }
        println("Killed  \(app.localizedName!) (\(app.bundleIdentifier!))")
        app.terminate()
    }
}

// 終了させないアプリケーションのホワイトリスト
// Finder 以外の項目はお好みで
func getAllowedBundleIdentifiers() -> [String] {
    return ["com.apple.finder",
            "com.omnigroup.OmniFocus2.MacAppStore",
            "com.apple.Safari"]
}

killApplications(getRegularApplications())
```
Rakeとoptparseを組み合わせたら少し幸せになった


[鳥取Ruby会【とっとるびー】　第１７回](http://tweetvite.com/event/tottoruby_17)の「「RubyとRakeとリモート実行」の発表でいいこと聞いたのでまとめてみた。

# Rakeのバージョンによる挙動について

[2015/02/19追記]
コメントで教えていただいたのだがrake 10.4.0以降でここに書いたオプションの受け渡しができなくなっている。
ARGVに"--"が含まれているのが原因なので以下のような感じで一応対応可能

```rb
opt.parse!(ARGV.reject { |x| x == "--" })
```

# Rakeの引数の問題

今まで以下のようにRakeタスクの引数でオプション指定がしにくいのが不満だった。

### タスクの引数を使う方法

```bash
$ rake test[moge]
```

確実に渡す引数は良いがオプションが複数あると渡しにくい。
1番目以降の引数でオプションだけを指定する場合、以下のような感じになってしまう。

```bash
$ rake test[,,plain]
$ rake test[,verbose]
```

### 環境変数を使う方法

```bash
$ rake test format=plain
```

どの環境変数を指定できるかわからない。
タスクのdescにもかけるが長々しくなるしコードを修正すると追随して修正しなければならず面倒くさい。

# 幸せになる方法

以下のようなRakefileを実行してみる。

```rb
require 'optparse'

desc 'test task'
task :test do |task|
  OptionParser.new do |opt|
    opt.on('--hoge=VALUE', 'hoge option') { |v| p v }
    opt.parse!(ARGV)
  end  
end
```

普通にオプションを指定するとrakeのオプションとして認識されてしまう。

```bash
$ rake test --hoge=moge
invalid option: --hoge=moge
```

ハイフンを2回続けるとrakeのオプション解析はそこまでで止めてくれてタスクにくわせられる！
※ [ここ](http://stackoverflow.com/questions/5559319/rake-custom-arguments-for-all-tasks)らへんに書いてあるの見つけた。[optparseの機能](http://docs.ruby-lang.org/ja/2.1.0/library/optparse.html#hyphen_start_file)？

```bash
$ rake test -- --hoge=moge
"moge"
```

ヘルプも出せる！
これでどんなオプションが指定できるかわかる！

でも、Usage: rake [options]になってる。

```bash
$ rake test -- --help
Usage: rake [options]
        --hoge=VALUE                 hoge option
```

1行追加してみる。

```rb
require 'optparse'

desc 'test task'
task :test do |task|
  OptionParser.new do |opt|
    opt.program_name = "#{opt.program_name} #{task.name} --" # <= 追加
    opt.on('--hoge=VALUE', 'hoge option') { |v| p v }
    opt.parse!(ARGV)
  end  
end
```

綺麗に出た！

```bash
$ rake test -- --help
Usage: rake test -- [options]
        --hoge=VALUE                 hoge option
```

# おまけ：capistrano3でも幸せになる

capistrano3ではrakeが使われているので同様のことが行える。
以下のような感じでオプションが指定できる。

```bash
$ bundle exec cap production test -- --hoge=moge
```

helpは以下のような感じで綺麗に出せる。

```rb
require 'optparse'

task :test do |task|
  OptionParser.new do |opt|
    opt.program_name = "#{opt.program_name} #{task.application.top_level_tasks.join(" ")} --" # <= helpのUsage用
    opt.on("--hoge=VALUE", "hoge") { |v| p v } 
    opt.parse!(ARGV)
  end
end
```
Windows環境のVagrant上のChefDKでBerkshelf・chef-solo実行


Windows上で`Bekrshelf` × `Vagrant`の環境を構築しようと思ったら、意外と面倒だったので直接Vagrant上に`ChefDK(Chef Development Kit)`で構築した手順をメモ。

## Vagrantを準備
```bash
vagrant init #{Your Box}
# 好みに応じて
vagrant plugin install sahara
# Vagrant起動
vagrant up
# sandbox実行(saharaインストール時のみ)
vagrant sandbox on
```

## ターゲットOSにChefDKの準備
###Provisioning設定
ターゲットとなるOSに`Git`と`ChefDK`を準備する
provisioningに関する項目をVagrantfileに追記
##### ChefDK
ChefDKに関しては、各OS用のChefDKを[公式サイト](https://downloads.chef.io/chef-dk/)からダウンロード。
##### Git
Gitに関しては、`yum`でインストールするとバージョンが古いので、ソースからインストールすることとしている。

```ruby
config.vm.provision "shell", inline: <<-EOT
  yum -y install zlib-devel perl-ExtUtils-MakeMaker gettext
  cd ~/
  wget https://www.kernel.org/pub/software/scm/git/git-2.1.0.tar.gz
  tar xvzf git-2.1.0.tar.gz
  cd git-2.1.0
  ./configure
  make & install
  wget https://opscode-omnibus-packages.s3.amazonaws.com/el/6/x86_64/chefdk-0.3.6-1.x86_64.rpm
  rpm -Uvh chefdk-0.3.6-1.x86_64.rpm
EOT
```

###Vagrant reload & provisioningの実行

```bash
vagrant reload
vagrant provision
```

##構築した環境の確認

```bash
vagrant ssh
git --version
#
bekrs -v
#
chef-solo -v
#
```
それぞれが無事にインストールされていることが分かる。

## Berkshelfの準備・実行〜chef-soloの実行まで（おまけ）

### Berkshelfの準備

##### Berkshelfを利用できるようにする
```bash
berks init
```

#####Berksfileを編集
※今回はrbenvをお試してでインストールする。

```Bearksfile
site :opscode

cookbook "git"
```

### Cookbookの準備
`berkshelf`を用いて、Cookbookを外部から取得する。
##### Cookbookの取得
```bash
berks vender
```

### nodeファイルの準備
`nodes/localhost.rb`

```ruby
# recipe
{
  "run_list": [
    "recipe[git]"
  ]
}
```

### solo.rbの準備
`solo.rb`

```ruby
cookbook_path ["./cookbooks"]
log_level :info
```
必要に応じて、記述を追加
参考：[solo.rb](http://docs.chef.io/config_rb_solo.html)

### Chef-Soloを実行
準備が整ったところで、chef-soloを実行

```bash
chef-solo -c solo.rb -j nodes/localhost.json
```
【初心者向け】SeleniumのSeleniumによるSeleniumerのための学習デモ

# はじめに
* こんな方々を対象としています
 * そもそもSeleniumって何ができるの？
 * Selenium IDEやRCは使ったことはあるがSelenium2系(SeleniumWebdriver)は未知の世界
 * 自分はSeleniumはバリバリ使っているが、他の人に楽して布教したい
* Seleniumを使うと以下のようなことが自動でできるよというデモをSeleniumを使って紹介していきます
 * ボタン/リンクをクリックする
 * テキストボックスに文字を入力する
 * ページを開く
 * スクリーンショットを撮る
 * などなど
* デモではjavascriptのアラートを使って「何します/こんなコマンドでできます」などガイドを出しています

# 準備
* 以下が利用できる環境を用意してください
 * Ruby
 * git (リポジトリのcloneするだけなので、GitHubからzip取ってくるなどすれば必要ありません)
 * Firefox

# 使い方
* プロキシ環境であれば、環境変数HTTP_PROXYまたはhttp_proxyに入れておいてください
 * ex) export HTTP_PROXY=http://localhost:8080
* (Firefoxのドライバはselenium-webdriverに最初から入っています)

```bash
$ (sudo) gem install bundler # bundlerが入っていなければ

$ git clone git@github.com:RustyNail/selenium_demo.git
$ cd selenium_demo.git
$ bundle install
$ bundle exec rspec #=> 勝手にブラウザが立ち上がりデモが始まる
```

## 補足
* javascriptによるガイドアラートの表示時間は環境変数ALERT_TIMEで調節可能です
 * デフォルトのガイド表示時間は10秒です
 * ガイドは表示時間を超えると自動的に消えて進むのでクリックするなどの操作は一切必要ありません
 * ほんとうに眺めているだけでよいです

# ～ただの宣伝～
* [全国のSeleniumer必読](http://qiita.com/oh_rusty_nail/items/b8ba525d31ea7c522856)
* Seleniumerといっていますが、Selenium, SauceLabs, Travis, Jenkinsに関するノウハウ書いているのでよかったら参考にしてみてください
デフォルトオブジェクトがProcであるHashはダンプできない


データを集計してファイルに保存！をやろうとして詰まるやつ

```ruby
h = Hash.new{[]}
Marshal.dump(h) # => TypeError: can't dump hash with default proc
```

JSONを噛ませて（Procを浄化して）対処している

```ruby
h0 = JSON.parse( JSON.dump(h) )
Marshal.dump(h0) # => "\x04\b{\x00"
```

もうちょっと賢い方法はないものか

[Marshal フォーマット](
http://docs.ruby-lang.org/ja/2.0.0/doc/marshal_format.html)
Mac OS XでKarabinerを使ってEscapeキーへのショートカットを登録する

XcodeやIntelliJ系IDE(Android Studio, WebStorm, etc), SublimeなんかでVimモードで普段コードを書いていると、各ソフトでの設定ではなくMacの共通設定としてたとえばescapeキーの割り当てなんかはしておきたいなと思って調べたので、記録を残しておきます。

結論としてはMac OSの標準機能ではちょっと難しく、やはりKey Remappingのソフトとしては有名な[Karabiner](https://pqrs.org/osx/karabiner/)を使うのが一番簡単かなと思いました。

Karabinerはデフォルトでも使える設定が非常に豊富で、個人的には
- 英語キーボードでのCommandへの英数/かなキー割り当て
なんかは重宝していて、このためだけでもインストールがマストだと思っています。

で、今回やりたいのは何か他のキーを押した時にEscapeとして動いて欲しいということ。
僕の場合はCaps Lock + aをEscapeにしたかったのです。
Karabinerでは自身の設定ファイルであるprivate.xmlを編集することで独自カスタマイズもできるようになっています。

KarabinerのPreferenceからMisc&Installの項を見てもらえると、private.xmlを開けるボタンがあるので、そちらを押して出てきたxmlファイルをエディタで開いてください。

![Screen_Shot_2015-01-25_at_3_18_52_PM.png](https://qiita-image-store.s3.amazonaws.com/0/20470/43b84fdb-3454-68d4-c6d1-229d6f5b0ead.png)

「Ctrl + A」を「Escape + 英数」に変えるには以下のように書きます。

```xml
<?xml version="1.0"?>
<root>
 <item>
    <name>Ctrl-L+A also works as Escape</name>
    <identifier>private.ctrl_a_to_escape</identifier>
    <autogen>__KeyToKey__
	     KeyCode::A, ModifierFlag::CONTROL_L,
	     KeyCode::ESCAPE, KeyCode::JIS_EISUU
    </autogen>
  </item>
</root>
```
nameは実際にKarabinerの設定一覧で見える名前です。

![Screen Shot 2015-01-25 at 3.24.10 PM.png](https://qiita-image-store.s3.amazonaws.com/0/20470/76a6b35b-2759-84db-bd43-9c6b3b5bb35b.png)

identifierはこのitemを一意に特定するためのIDで、private設定なので
private.[一意になる名前]
を好きにつければ良いと思います。

その後に実際のキーのリマップ内容を記載します。
KeyToKeyであるキーから他のキーへのリマップであることを宣言し、左側のControlとKeyのAを押すと、Escapeと英数が同時に押されたとみなすという設定ですね。

Escapeだけでなく英数も入れているのは、Escapeで挿入モードを抜けたあとに文字入力モードが「かな」になっていると、再度たとえばi等を押して挿入モードに入ろうとしたときに「い」と入力されてしまい意図した動作にならないため、自動的に「英数」に戻るようにしています。

設定を終えればKarabinerの設定画面でReload XMLを押すと、入れた設定が出てくるはずなので、それを有効化するだけです。私の場合はCaps LockをCtrlに変えている(これはMac OS Xのキーボード設定から可能です)ので、これでCaps LockにAボタンという非常に押しやすいキーで挿入モードからEscapeすることが可能になりました。

簡単ですね。
その他、自分でもっといじりたいという方は
[こちら](https://pqrs.org/osx/karabiner/xml.html.en)を見ると色々な情報が載っています。ここでKeyCodeやModifierの一覧などが確認できます。

結局Karabinerのプライベートカスタム設定のやり方、になってしまいましたが、誰かのお役に立てば幸いです:smiley:
tsc 1.4.1.0で--out オプションがきかない？？

遅ればせながらTypeScriptを1.4.1.0にアップグレードしたら、--outで指定したファイルが空になるという現象が。

呼ばれる側

```ts:test1.ts
class hoge {

  public hoge():void {
    console.log("hoge");
  }

}

export = hoge;
```

呼ぶ側

```ts:test2.ts
import test1 = require('./test1');

var a:test1 = new test1();

a.hoge();
```

ちなみにコンパイルする際に渡しているオプションは以下のような感じ

```bash
tsc --out test.js test2.ts --target es5 --module commonjs --noImplicitAny
```

これを実行すると、test1.js、test2.jsは出力されるが、test.jsが出力されない。むむむ……
webpackやcommonjsとかで動的に読み込ませろという事なのか、何か罠を踏んでいるのか……
まあ最悪minifyする前にcatすれば多分同じ動作になると思うんですが。

# 追記
よく考えたら順序考えないとcatして結合しても普通に死んでしまいますね。ううむ。。。

# 20150128 さらに追記
どうも調べてみて、moduleオプションついてんだから、出ないのはどう考えても正しいだろという結論に至りました。
前は出ていたんですが、より正しい方向にコンパイラが向いたという事なのでしょうか。
おとなしく動的に読み込ませる方法をとろうと思います。
VagrantとAnsibleでMongoDB環境構築

ホストOSにAnsibleをインストールしてVagrantのプロビジョニングでゲストOSにMongoDB環境を構築する。

# ホストOSに必要なもの

* VirtualBox
* Vagrant
* Python 2.4 以上
* Ansible

# Vagrantfile

```rb:Vagrantfile
# -*- mode: ruby -*-
# vi: set ft=ruby :

Vagrant.configure(2) do |config|
  config.vm.box = "chef/centos-6.5"
  config.vm.network "private_network", ip: "192.168.33.10"

  config.vm.provision :ansible do |ansible|
    ansible.playbook = "playbook.yml"
    ansible.inventory_path = "hosts"
    ansible.limit = 'all'
  end
end
```

* AnsibleではSSHでログインするのでプライベートネットワークを設定しておく。
* Vagrant1.5からは`ansible.limit = 'all'`という記述がないとエラーになってしまうらしい。

# hosts

```:hosts
[vagrant]
192.168.33.10
```

# playbook

```yaml:playbook.yml
- hosts: vagrant
  sudo: true
  user: vagrant
  tasks:
    - name: install python-selinux
      yum: pkg=libselinux-python state=latest
    - name: disable selinux
      selinux: state=disabled
    - name: copy mongodb.repo
      copy: src=mongodb.repo dest=/etc/yum.repos.d/mongodb.repo owner=root
    - name: install mongodb
      yum: pkg=mongodb-org
    - name: start mongodb
      service: name=mongod state=started
```

* selinuxが有効になっているとansibleからroot権限で作業できないので、最初の２つのタスクでselinuxを無効にしている。
* ３つめ以降のタスクは[MongoDBのインストール手順](http://docs.mongodb.org/manual/tutorial/install-mongodb-on-red-hat-centos-or-fedora-linux/#configure-the-package-management-system-yum)に書いてある手順。

# mongodb.repo

```ini:mongodb.repo
[mongodb]
name=MongoDB Repository
baseurl=http://downloads-distro.mongodb.org/repo/redhat/os/x86_64/
gpgcheck=0
enabled=1
```

# VM起動

```bash:
vagrant up
```

# 参考

* [Ansible - Provisioning - Vagrant Documentation](https://docs.vagrantup.com/v2/provisioning/ansible.html)
* [Ansible Documentation — Ansible Documentation](http://docs.ansible.com/)
* [vagrant - Ansible コトハジメ - Qiita](http://qiita.com/seizans/items/54da2077ac8e2dcf5d6f)
* [Vagrant 1.5からAnsibleを使うのならlimit = 'all'が必要 - 今日のハック ](http://narusemotoki.tumblr.com/post/82475978900/vagrant-1-5-ansible-limit-all)
* [CentOS に Ansible で GitLab をインストール - Qiita](http://qiita.com/garbagetown/items/5a903e2c5035f5df0690)
android.support.v7.graphics.Paletteの導入

Lollipopの登場とともにSupport Libraryに追加されたPalette。
画像から目立つ色を自動的に抽出することができる便利なクラスです。
同時期に追加されたRecyclerView, Toolbarなどの花形に比べると地味ではありますが、どこかで使ってみたくなる魅力的な機能です。  

#導入
今のところsupport-v7とは別途インポートしなければなりませんので、build.gradleのdependenciesに下記を追加します。

```gradle
compile 'com.android.support:palette-v7:21.0.+'
```

#使い方
画像の読み込みには同期型のPalette.generate()と非同期型のPalette.generateAsync()が存在します。  
メインスレッドでお手軽に使えるのはgenerateAsyncですね。

```android
Palette.generateAsync(bitmap, new Palette.PaletteAsyncListener() {
    @Override
    public void onGenerated(Palette palette) {
        extractColors(palette);
    }
});
```

生成されたPaletteからは6種類のSwatch（色見本）が取得できます。

* Vibrant       - getVibrantSwatch()
* Vibrant Dark  - getDarkVibrantSwatch()
* Vibrant Light - getLightVibrantSwatch()
* Muted         - getMutedSwatch()
* Muted Dark    - getDarkMutedSwatch()
* Muted Light   - getLightMutedSwatch()

それぞれのSwatchからは、

```android
Palette.Swatch swatch  = palette.getVibrantSwatch();
if (swatch != null) {
    backgroundView.setBackgroundColor(swatch.getRgb()); // 抽出された色
    titleView.setTextColor(swatch.getTitleTextColor()); // 抽出色上に表示するためのタイトル文字色
    bodyView.setTextColor(swatch.getBodyTextColor());   // 抽出色上に表示するための本文文字色
}
```

のようにして色を取得することができます。  
該当のSwatchは確実に生成されるわけではないようなので注意です。

この6種類以外のSwatchも

```android
List<Palette.Swatch> swatches = palette.getSwatches();
```

とすると取得できます。  
ここで取得できるSwatchの数はデフォルトで最大16種類までですが、画像を読み込むときに最大数を指定することも可能です。

```android
// 最大24種類
Palette.generateAsync(bitmap, 24, new Palette.PaletteAsyncListener() {
    @Override
    public void onGenerated(Palette palette) {
        extractColors(palette);
    }
});
```

以上、Paletteの紹介でした。  
使い方も簡単なので、画像を扱うアプリではぜひ取り入れていきたい機能ですね！

#参考
[Palette v21 - Chris Banes](https://chris.banes.me/2014/10/20/palette-v21/)
Tesselからheroku上のサーバーにWebSocket通信する

目的
----

TesselではSocket.io Clientが使えないみたいで、違う方法でWebSocket通信を試してみました。今回はTesselのWebSocket通信でサンプルがあったnodejs-websocketのnpmを利用します。

ちなみに今回知ったんですが、Socket.ioは生のWebSocketだと接続できないっぽいですね。ソースとか見てないので確信ないですが、誰かやり方知ってる人いたら教えて下さい。

参考
----
Attempting to use socket.io client
https://forums.tessel.io/t/attempting-to-use-socket-io-client/40

Using Websockets
https://forums.tessel.io/t/using-websockets/821

Does socket.io have raw WebSocket access like sockjs?
http://stackoverflow.com/questions/15198242/does-socket-io-have-raw-websocket-access-like-sockjs

手順
----

#### サーバー側の実装

下記のソースコードを用意しました。

nodejs-websocketとmongooseをnpm installしておきます。こんな感じだと思います。mongooseはWebSocketで受けたJSONを確認用にストアしたかったから使ってます。

```
$npm install nodejs-websocket --save
$npm install mongoose --save
```

```js:server.js
var ws = require('nodejs-websocket');
var mongoose = require('mongoose');

var port = process.env.PORT || 8000;
var mongodb_uri = process.env.MONGOLAB_URI;

var db = mongoose.connect(mongodb_uri);

var HelloSchema = new mongoose.Schema({
     date:{type:String}
});
var Hello = db.model('hello', HelloSchema);

// Create the websocket server, provide connection callback
var server = ws.createServer(function (conn) {
  console.log('Accepted new connection...');

  // If get a binary stream is opened up
  conn.on('binary', function(stream) {
    // When we get data
    stream.on('data', function(data) {
      // Log the data
      console.log('Got data:', data.toString());

      var hello = new Hello(JSON.parse(data));
      hello.save(function(err){
          if(err){
            console.log(err);
            return;
          }
          console.log("saved");
      });

    });
  });

  conn.on("close", function (code, reason) {
      console.log("Connection closed");
  });

}).listen(port);

console.log('Listening on port', port);
```

MONGOLAB_URIは[mongolab](https://mongolab.com/)のサーバーのURIで、下記のような形式になっています。

```
mongodb://<USER>:<PASS>@xxxx.mongolab.com:49150/<SCHEMA>
```

#### herokuにデプロイ

こんな感じだったと思います。

```
$git init
$git add .
$git commit -m "initial commit"
$heroku craete <Application Name>
$git push heroku master
```

今回はWebのコンソールのほうからMONGODB_URIとPORTの2つの環境変数をセットしました。けどコマンドのほうが簡単ですね。
http://chomast.com/study/web/heroku-environment-variables.html

#### クライアント側の実装

```js:client.js
var ws = require('nodejs-websocket');

// Set the binary fragmentation to 1 byte so it instantly sends anything we write to it
ws.setBinaryFragmentation(1);

// When we get a connection
var connection = ws.connect('ws://<URI>', function(err) {

  if(err){
    console.log(err);
    return;
  }
  console.log("connected");

  setInterval(function (){
    var now = new Date();
    var str = '{ "date" : "' + now + '" }';
    connection.sendBinary(new Buffer(str));
  }, 1000);

});

```

事前にnodejs-websocketのnpm installが必要です。

普通にローカルから一旦動作確認しておくのが吉です。

```
$node client.js
```

今回はmongolabのメッセージを見て動作確認しました。

#### Tesselで動かす

```
$tessel run client.js
```

動いたようです。
zaif（取引所）でAPIを使って取引する

# はじめに

* この記事はnode.jsのモジュールzaif.jpを使った記事になります
* private apiと呼ばれる個人認証が必要なAPIを説明した記事になります
* monacoinなどの仮想通貨の取引所の記事になります

## 事前準備

1.モジュールをインストールします

```
npm install zaif.jp
```

2.zaifからapi keyとsecret keyを取得します

ログイン後以下のページにて作成
アカウント -> API Keys

## api使用例

認証ファイルはソース埋め込みではなくjsonにしておくことをおすすめします
gitでソースを管理するのであればconfig.jsonは.gitignoreに登録しておくと大惨事を防げます。

```config.json
{
 "apikey" : "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx",
 "secretkey" : "yyyyyyyyyyyyyyyyyyyyyyyyyyyyyy"
}
```

JSONファイルの読み込み～初期化は以下のように行います

```
var fs = require('fs');
var config = JSON.parse(fs.readFileSync('./config.json'));
var zaif = require('zaif.jp');
var api = zaif.createPrivateApi(config.apikey, config.secretkey, 'user agent is node-zaif');
```

### 残高を取得

```
api.getInfo().then(function(res){
    console.log(res)
});
```

### 買い注文をする

monaを5円で10000枚買う

```
api.trade('mona_jpy', 'bid', 5, 10000).then(function(res){
    console.log(res)
});
```

### 売り注文をする

monaを5円で10000枚売る

```
api.trade('mona_jpy', 'ask', 5, 10000).then(function(res){
    console.log(res)
});
```

### 有効な注文中一覧を取得する

板情報に乗っている自分の注文を取得

```
api.activeOrders().then(function(res){
    console.log(res)
});
```

### 注文をキャンセルする

orderidは注文した時に保存しておくかactiveOrdersの結果から取得する

```
var orderid = 10001;
api.cancelOrder(orderid).then(function(res){
    console.log(res)
});
```

## 使い道

このライブラリを使うとしたら以下の様な用途だと思います

* 暗号通貨を入金して円に自動で両替
* 他取引所との裁定取引
* トラップリピートイフダンなどのスプレッド売買
* RSI、MACDなどを利用したテクニカル売買
* 暗号通貨を時間をかけてゆっくり仕込みたい

このライブラリを公開した目的はもっとbitcoinやmonacoinの流動性が上がってほしいと思い公開しています。
pump and dumpとか正直困るので。。。

※MACD使えるnode.js製のトレーディングボットにgekkoというのがあります( https://github.com/askmike/gekko )

## プログラム例

### 発注している注文を全てキャンセルする

```
var Promise = require('bluebird');
api.activeOrders().then(function(res){
    return Promise.all(
        Object.keys(res).map(function(key){
            return api.cancelOrder(key);
        })
    );
});
```

買い注文だけ消したい場合

```
var Promise = require('bluebird');
api.activeOrders().then(function(res){
    return Promise.all(
        Object.keys(res).filter(function(key){
            return res[key].action === 'bid'
        }).map(function(key){
            return api.cancelOrder(key);
        })
    );
});
```

## その他

裁定取引を補佐するためのライブラリもあります https://github.com/you21979/node-trade-util

不具合あると思うので自己責任でお願いします。プルリクエストも歓迎しています
nginx-buildでTengineをビルドしよう

# Tengine

[Tengine](http://tengine.taobao.org/)はTaobaoが開発しているnginxのforkです。
ついさっき[nginx-build](https://github.com/cubicdaiya/nginx-build)を[Tengine](http://tengine.taobao.org/)に対応させたので、ついでにサクッと書きます。

## Tengineをnginx-buildでビルドする

Tengineをnginx-buildでビルドするにはnginx-buildのバージョンが0.3.0以上である必要があります。バージョンが古い場合はgo get -uでnginx-buildを更新するか、

```console
go get -u github.com/cubicdaiya/nginx-build
```

最新のバイナリを[こちら](https://github.com/cubicdaiya/nginx-build/releases)からダウンロードしてください。

それではnginx-buildでTengineをビルドしてみましょう。


```console
$ nginx-build -d work -tengine -pcre
nginx-build: 0.3.1
Compiler: gc go1.4.1
2015/01/26 05:07:59 Download tengine-2.1.0.....
2015/01/26 05:07:59 Download pcre-8.36.....
2015/01/26 05:08:01 Extract tengine-2.1.0.tar.gz.....
2015/01/26 05:08:05 Extract pcre-8.36.tar.gz.....
2015/01/26 05:08:05 Generate configure script for tengine-2.1.0.....
2015/01/26 05:08:05 Configure tengine-2.1.0.....
2015/01/26 05:08:12 Build tengine-2.1.0.....          ・
          ・
          ・
          ・
2015/01/26 05:08:27 Enter the following command for install nginx.

   $ cd work/2.1.0/tengine-2.1.0
   $ sudo make install
$
```

というわけでnginx-buildをTengineに対応させた話でした。
最新版 Chrome において、『 ＥＲＲＯＲ：referer情報が変です。(ref1) 』というエラーが出て拡張機能から2ちゃんねるに書き込めない

##なぜ起こるのか
Google Chrome のアップデートにより拡張機能からのリファラの扱いが変わったからです。

2 ちゃんねるでは BOT による連投や荒らしを防ぐため、書き込みに
リファラの送信が必須となっています。

『 ＥＲＲＯＲ：referer情報が変です。(ref1) 』というエラーは、そのリファラを 2 ちゃんねる側が受け取れなかった際に表示されるエラーです。
つまりリファラを送信しましょう。

詳しい説明をすると長くなるのと、これを書いているのが午前4時半ということもあり、
対処法だけを簡単に載せるだけにしておきます。

##対処法
まず**リファラコントロール**という拡張機能をインストールします。
以下URLよりインストール可能です。
[リファラコントロール - Chrome ウェブストア](https://chrome.google.com/webstore/detail/referer-control/acehenlbileblompmkkoimgobmcdkgeb)

インストールが完了したら、chrome://extensions/ よりリファラコントロールの設定画面を開きます。

左上の『 インポート / import 』より、
以下のプロファイルをインポートします。

```
{"matchingUrl":"http://*.2ch.net/*","newRefType":"dynamic","newRefData":{"newRefTarget":"to","newRefMatch":"url"},"accessType":["main_frame","sub_frame","image"]}
```

以上です。

なお、同システムを利用するしたらば掲示板などでも同じ問題が発生しており、
その場合も同じように上のプロファイルの`http://*.2ch.net/*`という部分を`http://*.shitaraba.net/* `のように書き換えてインポートしてやれば大丈夫です。

##最後に

Chrome 恒例、害悪(？)アプデシリーズにもだいぶ慣れてきました
constとreadonly

C#の定数は
コンパイル時定数と実行時定数の２つある

コンパイル時定数

```csharp
private const int hoge = 1;
```
実行時定数

```csharp
private readonly int hogehoge =  2;
```
コンパイル時定数
実行時定数よりもすこし高速
staticがついていなくてもstaticであるかのように扱える


実行時定数
コンストラクタで値が決定されるので生成されたインスタンス毎に固有の値を持てる
new演算子により生成されるオブジェクトを定義できる。

```csharp
//使える
public readonly System.DateTime readonlyDateTime = new System.DateTime ();
//使えない
public const System.DateTime constDateTime = new System.DateTime ();
```


constはswitchのcaseに使えてreadonlyは使えない

```csharp
enum HogeHoge
{
    AAAA,BBBB,CCCC
}
	
const HogeHoge aaaa = HogeHoge.AAAA;
readonly HogeHoge bbbb = HogeHoge.BBBB;

void Hoge()
{
    HogeHoge cccc = HogeHoge.CCCC;
    switch(cccc)
    {
        //使える
        case aaaa:
        break;

        //使えない
        case bbbb:
        break;

　　　　　case HogeHoge.CCCC:
        break;
    }
}
```
Railsでgemをinstallする際に意図したgemと違うgemがinstallされる事がある

プロダクトのissueを見ていた所動かなくなったというissueがあったので調べていた所出くわした

対象のGemは [rails-erd](https://rubygems.org/gems/rails-erd)

Gemfileのsource先は `https://rubygems.org` になっている

```rb:Gemfile
gem 'rails-erd'
```

と書いてあるので、 `bundle install` すると何故か [paulwittmann/rails-erd](https://github.com/paulwittmann/rails-erd/tree/master) がinstallされてくる
(リンク先に飛んでもらえれば分かるが、[voormedia/rails-erd](https://github.com/voormedia/rails-erd)のforkのforkである)

で、上の [rails-erd](https://rubygems.org/gems/rails-erd) のリンクを飛んでもらえば分かるが、1.2.2とversionsがある所から間違いなく [paulwittmann/rails-erd](https://github.com/paulwittmann/rails-erd/tree/master) ではない

何故fork先が一番始めに落ちてくるのか、まだ追えてない

こういうのすぐに分かる方法が無いのかな？

## 追記
解決した
active_record 3.2に依存している為にRails 4に対応していなかったのが問題
つまり、勝手にgemの方で対応関係を見てinstallするものを変えていた
ちょっと感動したのと同時に [issue#115](https://github.com/voormedia/rails-erd/issues/115) にも書いてあった

しかし愚痴を言う訳ではないが、いきなり使った事無いgemでそうなるとあれ？ってなる
JS: ブラウザの言語設定の取得方法

ブラウザ or OSの言語設定を読み取り、処理を分岐鎖せる方法です。

```html:index.html
<script>
// 日本語
if( browserLanguage() == 'ja' ){
  location.href = '/ja';
}
// その他
else{
  location.href = '/en';
}
</script>
```

```js:browserLanguage.js
var browserLanguage = function() {
  var ua = window.navigator.userAgent.toLowerCase();
  try {
    // chrome
    if( ua.indexOf( 'chrome' ) != -1 ){
      return ( navigator.languages[0] || navigator.browserLanguage || navigator.language || navigator.userLanguage).substr(0,2);
    }
    // それ以外
    else{
      return ( navigator.browserLanguage || navigator.language || navigator.userLanguage).substr(0,2);
    }
  }
  catch( e ) {
    return undefined;
  }
}
```

Chormeのみ下記の場所に言語設定が置かれるようで、それ以外のブラウザではエラーになるのでUAを調べて分岐しています。
- navigator.languages[0]
JS: FacebookのLikeボタンが押された時にCallbackを取得する

自サイトにいいねボタンを設置したのはいいけど、コメント欄が画面外にはみ出てしまう問題が多々あります。
その場合はGraph APIを使いLikeボタンのCallbackを取得し、DOMオブジェクト毎画面内に移動させることで、なんとかなる場合があります。

以下はその際のコールバックの取得方法。
``position:absolute;``で配置しないと他要素にも影響を与えてしまうので、そこだけ注意。
あとはパフォーマンスを重視するサイトの場合、API側でイベントの監視が行われるので若干処理が重くなる可能性があります。

**[URL]**: 設置するURL

```file:index.html
<div id="fb-container">
<div id="fb-root"></div>
<div class="fb-like" data-href="[URL]" data-width="80" data-layout="button" data-action="like" data-show-faces="false" data-share="false"></div>
</div>
```

**[Facebook App ID]**: FacebookのアプリID

```file:fb.js
window.fbAsyncInit = function() {
  FB.init({
    appId      : '[Facebook App ID]',
    xfbml      : true,
    version    : 'v2.2'
  });

  var dom = $('#fb-container');

  FB.Event.subscribe( 'edge.create', function(response) {
    dom.animate({ right: 370 }, 0, 'swing', function(){});
  });

  FB.Event.subscribe( 'edge.remove', function(response) {
    dom.animate({ right: '' }, 0, 'swing', function(){});
  });

  FB.Event.subscribe( 'comment.create', function(response) {
    dom.animate({ right: '' }, 0, 'swing', function(){});
  });

  FB.Event.subscribe( 'comment.remove', function(response) {
    dom.animate({ right: '' }, 0, 'swing', function(){});
  });
};

(function(d, s, id){
   var js, fjs = d.getElementsByTagName(s)[0];
   if (d.getElementById(id)) {return;}
   js = d.createElement(s); js.id = id;
   js.src = "//connect.facebook.net/ja_JP/sdk.js";
   fjs.parentNode.insertBefore(js, fjs);
 }(document, 'script', 'facebook-jssdk'));
```

## イベントの説明
- edge.create: Likeボタンが押された時
- edge.remove: Likeボタンをキャンセルした時
- comment.create: コメントを投稿した時
- comment.remove: コメントをキャンセルした時

その他のイベントは以下を参照。
https://developers.facebook.com/docs/reference/javascript/FB.Event.subscribe/v2.2
Vimでキャプチャを利用して置換をする例など


下のファイルを例にして、いくつかの書いてみます。
すべてノーマルVimで利用できます。

**変更前**
![スクリーンショット 2015-01-26 1.37.08.png](https://qiita-image-store.s3.amazonaws.com/0/30588/b3f6d1f8-be63-cc4e-f44c-a96a5609eb97.png "スクリーンショット 2015-01-26 1.37.08.png")


## 1.英単語の先頭に `_` (アンダースコア) をつけたいとき

**変更後**
![スクリーンショット 2015-01-26 1.40.10.png](https://qiita-image-store.s3.amazonaws.com/0/30588/fccc4735-4725-2e69-4c0c-dcf3e8d08187.png "スクリーンショット 2015-01-26 1.40.10.png")

このケースでは **最初の正規表現にマッチした部分 = キャプチャしたい部分** なので、検索部分で `()` を利用しなくても `\0` でマッチ全体を参照できます。

```vim
:%s/[a-zA-Z]\+/_\0/g
```

`[a-zA-Z]` は文字クラス `\a` を利用できるので以下のようにも書けます。 (※ 文字クラスについては `:h /character-classes` で詳しい情報を参照できます。)

```vim
:%s/\a\+\/_\0/g
```

また、`\0` は `&` でもよいです。

```vim
:%s/\a\+/_&/g
```
上記の３つの方法はすべて同じ結果を得ることができます。


## 2.各単語の先頭の文字を大文字にしたいとき

上記と同じファイルで各単語の先頭の文字だけ大文字にしたい場合。
1で利用したもの(`\v`, `\a`, `&`) に加えて `\u` を使います。
※ `\u` はその次にくる文字を大文字に変更する特殊文字です。`\l` だとその逆(小文字)ができます。

```vim
:%s/\v\a+/\u&/g
```
**動作**
![1](http://zippy.gfycat.com/MerryEnchantingAmericancrocodile.gif)


## 3.各単語の先頭の文字だけ大文字にして、後に続く文字は小文字にしたいとき

```vim
:%s/\v\a+/\u\L&/g
```

**動作 (`POSIX`の文字に注目してください)**
![2](http://zippy.gfycat.com/LinearFearfulKarakul.gif)

2,3で書いた `\u` や `\L` の説明や他にも利用できる物などは
 `:h sub-replace-special` を見てみてください。

## あとがき

今回はパターンマッチが簡単なものでしたが、
複雑なパターンマッチ書くときはエスケープのバックスラッシュだらけになってややこしくなってくるので、
`\v` でパターンスイッチ してしまう事も多いです。


Vimは便利な上に楽しいですね。