OmniAICreator/Qiita-1.07M huggingface dataset:
Chrome でユーザを一発で切り替えるショートカット



こんにちは、 isseium です。

この記事は、岩手県立大学アドベントカレンダー2015 9日目の記事です。

今年の春に社会人入学した大学院を卒業しました。いまは岩手に住みながらエンジニアしています。
前潟の盛岡イオンか本宮の盛岡南イオンによく生息しています。見かけたら話かけてください。

# Chrome で複数ユーザアカウントつかってますか？

Chrome には、複数のユーザアカウントを切り分けて使う機能がありますが、みなさんは利用されていますか？

会社とプライベートで gmail を分けて読んだり、ブックマークを別で管理したり、開発時とテスト時でエクステンションを変えたりとなにかと役立ちますよね。

## 切替が面倒！！！

便利な機能ですが、指定のユーザに切り替えるショートカットがみあたりません！！！（2015/12/8時点）
なので、違うユーザのウィンドウを表示したいときは、いちいちウィンドウを探す必要があって面倒なんですよね。

というわけで、Mac ユーザ限定ですがショートカットを追加する方法をまとめたいと思います。
OS標準機能だけでできるので特別なソフトウェアのインストールは不要です！


# 設定方法

## 1. 「システム環境設定」-> 「キーボード] -> 「ショートカット」

<img src="https://www.evernote.com/l/AB-OZYjdXuJPlqnlMD_yw_fSmlu3oYhn_0cB/image.png" width="500px" />


<img src="https://www.evernote.com/l/AB-TH7rV-mJOw602VIuOe2ViYKFbWCuOvgkB/image.png" width="500px" />

## 2. 設定の追加



左のリストから「アプリケーション」を選択、次に、右のリストの下にある「+」をクリックします。

<img src="https://www.evernote.com/l/AB_W01dUTSZC2ZBAID2QSs5X6gmkt0MZH3gB/image.png" width="500px" />

すると、ダイアログが表示されるので次のように入力します。

<img src="https://www.evernote.com/l/AB8YaLbdA_xAsKcTqYxDGI8H94kCjTqJqf0B/image.png" />


「メニュータイトル」のところは、Chromeのメニューの「ユーザー」のところに表示されているユーザ名を入力します。

<img src="https://www.evernote.com/l/AB9dU7N_B_ZIOIg3qESqAml56oVdvk1zv4AB/image.png" width="400px" />


キーボードショートカットは、好きなものを入力しましょう。
僕は `Ctrl + Command + 連番` にしています。

ユーザが2つのときは、 `Ctrl + [` と `Ctrl + ]` も使いやすかったです。
使いやすくて、他のショートカットとぶつからないいいショートカットがあればぜひ教えてください！


## 3. ショートカットが動いているか確かめる


Chrome を起動します。



メニューバーの「ユーザ」をみてみましょう。



<img src="https://www.evernote.com/l/AB-mtCDz8e5P7rgBQl4jVAAY5omLJwsBU7cB/image.png" width="400px" />


おやおや、なにやらさきほど追加したショートカット表記が追加されていますね。

ためしに `Ctrl + Command + 2` を押してみましょう。2 で指定したユーザのウィンドウが表示されましたか？
では、 2 の画面で　`Ctrl + Command + 1` を押してみましょう。1 に戻りましたね！！！


これで、ゴールだった「Chromeのユーザを一発で切り替えるショートカット」が実現できました！

# おわりに

すでにお気づきの人もいるかと思いますが、この方法は Chrome 以外のアプリケーションでも使えます！

こんなショートカット設定すると便利だよ！！なんていう情報がありましたらぜひ教えてください！！

それでは10日目は、@arthur87 さんです。いつも便利アプリを作っているイメージですが、どんな記事が公開されるか期待ですね！！！！！！！


# 参考文献

3年以上前から要望はあるみたいなんですけどね。

https://code.google.com/p/chromium/issues/detail?id=112281
https://productforums.google.com/forum/#!topic/chrome/ORE7X2zARQM
http://superuser.com/questions/438039/how-to-quickly-change-user-profile-in-google-chrome
[Mac]arduinoとavrdudeでhexファイルをatmega328に書き込む

# WHAT
Macのターミナルからhexファイルを直接ATmega328に書き込む。
hexファイルのArduinoIDEでの生成方法は下記記事から
<a href="http://qiita.com/ZeroCrossroad/items/d9e1ff1b55297e7b0a43">[Mac]ArduinoIDEでHEXファイルを出力する</a> 

# PURPOSE
* 大量生産したいけど、AtmelStudio使いたくない。
* 石だけ焼きゃいいんだよ！なんで治具なんざ作らなあかんのや！！

# HOW
## 1. 下準備
Arduinoを2台使用します。
接続方法は下記記事と同じです。
<a href="http://qiita.com/ZeroCrossroad/items/22abe2cf857c6adf1106">ArduinoUnoを2台使ってブートローダを書き込む</a>

また、前出の記事同様片方のArduinoに空のATmega328を載せ、もう片方のArduinoにはArduinoISPを書き込んでおきます。

## 2. ターミナルから書き込む
ターミナルを起動して、次のコマンドを打ちます。
` sudo /Applications/Arduino.app/Contents/Java/hardware/tools/avr/bin/avrdude -C /Applications/Arduino.app/Contents/Java/hardware/tools/avr/etc/avrdude.conf  -b 19200 -c avrisp -P /dev/tty.usbmodem1421 -p t2313 -e -U flash:w:/Applications/Arduino.app/temp/Blink.cpp.hex:i -F `

必要に応じて変更してください。
第9引数のUSBデバイスの選択ですが、ArduinoISPが書き込まれたArduinoを選択してください。
ArduinoIDEのToolから表示名を見ることができます。
第14引数ですが、書き込むhexファイルを示します。
が、ファイル名の頭には` flash:w: `をつけてください。
CircleCIからAWSのプライベートサブネットにGitHubのプライベートリポジトリをクローンする

この記事は[CircleCI Advent Calendar 2015](http://qiita.com/advent-calendar/2015/circleci)の7日目の記事です。

2016年01月30日 追記

2ヶ月遅刻しました(ヽ´ω`)

=> [CircleCI から AWS VPC の private subnet に private repo を git clone](http://qiita.com/kotatsu360/items/4853c7fcdb0752b9c0a6)
phpをスクリプトとして利用して大容量のログデータを検索出力する

むかし(2007年8月7日)作ったログデータ検索用phpスクリプト公開しておきます。

メリットとしては

- GZファイルのままでも検索できる
- １行ずつ読み込んでヒットしたら書き出すのでメモリを使わない？
- 複数キーワードで検索できる


以下をgzgrepor.phpなど適当なファイル名で保存して、
php gzgrepor.php [ファイル名] [キーワード１] ...
というように実行すると、キーワードでgrepした結果のファイルが作成されるものです。

キーワードは半角スペース区切りで複数指定できます。or検索ができるってところでしょうか。スペースも含むキーワードの場合はダブルコーテションで囲んで下さい。（windowsだけかも？）

このphpファイルをどこかに置いてパス通しておくと便利かもしれないけどまだ試したことない。

まだまだブラシュアップするところあると思いますのでアドバイスお待ちしております。
他にもnot検索させるのも作ったりしてます。


```php:gzgrepor.php
<?php

	
	// 引数チェック
	if ($argc < 3) {
		print "引数が不正です。\n";
		exit;
	}
	
	
	// 解析対象ファイル名取得
	$filename = $argv[1];
//	$keyword = $argv[2];
	
	// 検索結果出力ファイル名
	$dfilename = preg_replace("/\.log\.gz$/","",$filename);
	$dfilename = $dfilename . "_" . $keyword . ".txt";

	//情報出力
	print "検索対象ファイル　　：";
	print $filename . "\n";
	print "検索対象キーワード　：";
	print $keyword  . "\n";
	print "検索結果出力ファイル：";
	print $dfilename . "\n";

	//gzファイルオープン
	$zh = gzopen($filename,"rb");
	if ($zh == false) {
		print "gzファイルのオープンに失敗しました。\n";
		exit;
	}

	// 出力ファイルオープン
	$fp = fopen($dfilename,"wb");
	if ($fp == false) {
		print "出力ファイルのオープンに失敗しました。\n";
		exit;
	}

	// 検索キーワード取得
	array_shift($argv);
	array_shift($argv);
	
	$cnt = 0;
	while (gzeof($zh) == false) {
		// 1行取得
		$line = "";
		$line = gzgets($zh);

		$flg = 0;
		foreach ($argv as $tmp) {
			if (strstr($line,$tmp) != false && $flg == 0) {
				fputs($fp,$line);
				$cnt = $cnt + 1;
				$flg = 1;
			}
		}


	}

	//出力ファイルクローズ
	fclose($fp);

	//gzファイルクローズ
	gzclose($zh);

	print "\n";
	print "該当データは" . $cnt . "件ありました。\n";
	print "\n";
	print "処理が完了しました。\n";
```
git で branch を push しただけじゃ tag は push されない話

表題の件、git flow でリリースブランチをプッシュした時に、リモートの方でタグが反映されてなかったので気付きました。ブランチプッシュしたら、そのコミットのタグも一緒に反映されるもんだと思ってた。
　　
操作はブランチと一緒で、タグ名ごとに個別に

`$ git push origin TAGNAME`  (TAGNAME は任意のタグ名)

もしくは、全部一気に

`$ git push origin --tags`

で反映できます。  

また、タグのリモートからの削除もブランチと同様に

```terminal
$ git tag -d TAGNAME  
$ git push origin :TAGNAME
```
もしくは、
`$ git push --delete origin TAGNAME`
で削除。

忘れがちなので、自動化したい。
↓

2024/07/23 追記
コメントで、タグも同時にプッシュする設定があることを教えていただきました。
ありがとうございます。
```terminal
$ git config --global push.followTags true
```
Node-REDのNode作成2歩目

[前回](http://qiita.com/joeartsea/items/11cef78442c3e7154a07)に引き続き公式ドキュメントにあるNode作成の[HTML File](http://nodered.org/docs/creating-nodes/node-html.html#node-type)を読み解きます。

Nodeの`.html`ファイルにはNodeのEditorでの描写を定義します。これは3つの`<script>`タグで構成されます。

1. Editorに登録されている主Node定義。パレットのカテゴリ、編集可能なプロパティ（デフォルト）やアイコンを定義します。通常のJavascriptのScriptタグ内にあります。
2. Nodeの編集ダイアログの内容を定義。`type`に`text/x-red`、`data-template-name`にNodeのタイプ名を持つScriptタグで定義されています。
3. サイドバーのinfoタブに表示されるヘルプテキスト。`type`に`text/x-red`、`data-help-name`にNodeのタイプ名を持つScriptタグで定義されています。

## Nodeの定義

Nodeは`RED.nodes.registerType`関数を使用してEditorに登録する必要があります。この関数にはNodeのタイプとその定義の2つの引数があります。

```js:
<script type="text/javascript">
  RED.nodes.registerType('Nodeのタイプ', {
    // Nodeの定義
  });
</script>
```

### Nodeのタイプ

NodeタイプはEditor全体でNodeを識別するために使用されます。これは対応する`.js`ファイルと`RED.nodes.registerType`への呼び出しで使用される値が一致する必要があります。

タイプはパレット内のNodeのラベルとして使用されます。タイプが"in"または"out"で終わる場合は"in/out"部分はラベルから消去されます。たとえば、"mqtt in"や"mqtt out"の場合はラベルに"mqtt"と表示されます。

### Node定義

Node定義はEditorで必要なNodeに関するすべての情報が含まれています。それは次のプロパティを持つオブジェクトです。

* `category`: (string) Nodeを配置するパレットのカテゴリ
* `defaults`: (object) Nodeの編集可能なプロパティ
* `credentials`: (object) Nodeの認証系プロパティ
* `inputs`: (number) Nodeのインプットコネクタ数（0か1が指定可能）
* `outputs`: (number) Nodeのアウトプットコネクタ数（0かそれ以上指定可能）
* `icon`: (string) Nodeのアイコン
* `color`: (string) Nodeの背景色
* `label`: (string|function) Nodeのラベル
* `paletteLabel`: (string|function) Nodeのパレット上のラベル
* `labelStyle`: (string|function) ラベルのスタイル
* `align`: (string) アイコンとラベルの位置
* `oneditprepare`: (function) 編集ダイアログを開く時のイベント
* `oneditsave`: (function) 編集ダイアログを保存する時のイベント
* `oneditcancel`: (function) 編集ダイアログをキャンセルする時のイベント
* `oneditdelete`: (function) 編集ダイアログの削除ボタンが押された時のイベント
* `onpaletteadd`: (function) Nodeタイプがパレットに追加された時のイベント
* `onpaletteremove: (function) Nodeタイプがパレットから削除された時のイベント

## 編集ダイアログ

Nodeの編集ダイアログの内容を定義しています。

```
<script type="text/x-red" data-template-name="node-type">
  <div class="form-row">
    <label for="node-input-name"><i class="fa fa-tag"></i> Name</label>
    <input type="text" id="node-input-name" placeholder="Name">
  </div>
</script>
```

このテンプレートには以下の規則があります。

* `form-row`クラスを持つ`<div>`要素は編集ダイアログのひとつの行を表します
* 典型的な行はアイコンを持つラベルと対応する`<input>`要素を持ちます
* アイコンは`<i>`要素のクラスに[Awesome](http://fortawesome.github.io/Font-Awesome/icons/)フォントを指定します

## ヘルプテキスト

Nodeが選択されるとサイドバーのinfoタブにテキストが表示されます。ここで、Nodeへの入力メッセージと出力メッセージのプロパティの解説など、Nodeの内容について解説する必要があります。

パレット内のNodeをマウスオーバーすると`<p>`タグの内容がツールチップとして使用されます。

```
<script type="text/x-red" data-help-name="node-type">
   <p>Some useful help text about the node.</p>
   <p>Outputs an object called <b>msg</b> containing <b>msg.topic</b> and
   <b>msg.payload</b>. msg.payload is a String.</p>
</script>
```
Bazel で Android w/NDK や iOS アプリをビルド

# Bazelって？

Tensorflow 等のビルドシステムとして採用されている Google 謹製ビルドシステムです。
現在は βバージョンが利用可能で、 Android や iOSがビルドできます。
http://bazel.io/

既に先人による良記事が存在しているので、本稿では導入等の手順は割愛します。
[クックパッド開発者ブログ - 次世代ビルドツールBazelを使ってAndroidアプリをビルドする](http://techlife.cookpad.com/entry/introduce-bazel-build)

# Bazelでビルドする

gitに上げているソースを元にした詳解です。
Android NDK、及びiOSプロジェクトのビルドのサンプルを公開しています。
https://github.com/dolow/bazel-build-sample


# 本稿の開発環境

- Mac OSX 10.11.5
- Android NDK r10b
- Android SDK 23
- iOS SDK 10.0
- Xcode 8.2
- Bazel 0.4.3-homebrew

## Android NDKプロジェクト

### ソース

c/c++ と java 間の連携を確認するための h/cpp と java を用意します

### WORKSPACE

ビルド環境などを設定します。
本稿ではNDKを利用するので、NDKの設定を記述します。

```
android_sdk_repository(
    name="androidsdk",
    path="/path/to/android-sdk",
    api_level = 23,
    build_tools_version="24.0.0"
)

android_ndk_repository(
    name = "androidndk",
    path = "/path/to/android-ndk",
    api_level = 22,
)

```

### BUILD

ビルド対象やビルド時のオプションを設定します。

```
# cpp library
cc_library (
    name = "android_app_cpp",
    srcs = glob(["cpp/*.cpp"]),
    hdrs = glob(["cpp/*.h"]),
    copts = ["-std=c++11"], # compile option
    linkopts = ["-llog"],   # linker option for logging
)

# java project
android_binary (
    name = "android_app",
    srcs = glob(["java/**/*.java"]),
    custom_package = "jp.do_low.bazel.sample",
    manifest = "AndroidManifest.xml",
    resource_files = glob(["res/**"]),
    deps = [":android_app_cpp"], # name of cc_library
)
```

### ビルドコマンド

```
$ bazel build //Sandbox:android_app --crosstool_top=//external:android/crosstool --host_crosstool_top=@bazel_tools//tools/cpp:toolchain --cpu=x86_64
```

#### オプション

_//Sandbox:android_app_
_Sandox_ は WORKSPACE ディレクトリから、BUILDの置いてあるディレクトリへのパスです。
_:android\_app_ は、BUILDに設定したビルドターゲットの _android_binary_._name_ の値です。

_--crosstool\_top_
c++ のコンパイルに利用するクロスコンパイル用ツールの場所を指定します。
本稿の値は tensorflow のサンプルを参考にしたもので、正直どこを指しているのかわかりませんでした。

_--host\_crosstool\_top_
bazelで提供するクロスコンパイルツールを指定します。
本稿の値は tensorflow のサンプルを参考にしたもので、実態は _bazel-bazel-build-sample/external/bazel_tools/tools/cpp/BUILD_ で定義されているターゲットの _toolchain_ を指しています。

## iOS プロジェクト

### ソース

Obj-C のスクリプトを用意します。
iOS では c/c++ 連携に特に障壁はないので、それらは特に用意しません。

### WORKSPACE

iOS用の設定はありません。

### BUILD

_objc_binary_ はコンパイラに渡す情報、 _ios_application_ は主に Xcode に関わる設定を記述します。

```
objc_binary (
    name = "ios_app_binary",
    srcs = glob(["objc/*.m"]),
    hdrs = glob(["objc/*.h"]),
)

# ios project
ios_application (
    name      = "ios_app",
    bundle_id = "jp.do_low.bazel.sample",
    binary    = ":ios_app_binary",
    infoplist = "ios/Info.plist",
)
```

### ビルドコマンド

```
$  bazel build //Sandbox:ios_app --ios_sdk_version=9.0
```

_--ios\_sdk\_version_
UIKit などの iOS SDK の参照を解決させるために指定します。
バージョン番号は、実際にインストールされているものから任意の番号を指定してください。

----

以上です。


# おわりに

本稿の初稿は bazel 0.2.2 で記載しましたが、一年経って 0.4.3-homebrew にアップデートしても、この記事の範囲内での I/F に大きな変化は見られませんでした。
ただ、やはりビルド時のコマンドのオプション指定が煩雑な印象です。
iOS, Android 用のビルドができるものの、ストアに並べるようなものよりは社内ツールなどのユーティリティ向きと思いました。
[Mac]ArduinoIDEでHEXファイルを出力する

# WHAT
ArduinoIDEでスケッチをコンパイルして、AVRに書き込むためのhexファイルを出力する。

# PURPOSE
* AtmelStudioを使いたくない。
* ArduinoCoreライブラリを使いたい。

# HOW
## 1. ArduinoIDEの設定を変更する
`/Users/<UserName>/Library/Arduino/preferences.txt`
を編集する。
この時、ArduinoIDEは終了しておくこと。

次の行を追加
` build.path=/Applications/Arduino.app/temp/ ` 
次の行を探し出し
` preproc.save_build_files=false `
変更
` preproc.save_build_files=true `

buildpathに書いてしまったので、Arduinoのアプリケーションフォルダ内にtempというフォルダを作る。

## 2. コンパイルする
スケッチを書いたら、あとはコンパイルするだけ。
上述のフォルダ内にファイル名.hexファイルが出来上がる。
R Markdownでコードハイライトのテーマ設定

## この記事の目的
私が大好きなRMarkdownについて、Tipsを集中的に連載しようという思いつきの企画です。あと自分の中で進めている別企画のメモという位置づけでもあります。なので**大した中身はありません**。

### R Markdownとは
Markdown記法をベースに、チャンクという形でRのコードを記述して評価・出力することができるものです。RStudioのクイックリファレンスでは以下のように説明してあります:

> R Markdown is an easy-to-write plain text format for creating dynamic documents and reports. 

## コードハイライトのテーマ
R Markdownを使っていると、コードハイライトの色がどれも同じで「あ、これRmdの色だね」とすぐにわかります。でもたまにはこのテーマをスイッチしてみたいと思うこともありますね。実は簡単にテーマを変更することが可能です。例えば、Rmdファイル冒頭のyaml領域を以下のように変更すると変化します:

```
---
title: "hogehoge"
output:
  html_document:
    highlight: "tango"
---
```

これで青っぽいテーマに変わるかと思います。

## R Markdownでコードハイライトのテーマ設定
R Markdownで使用できるコードハイライトのテーマは、[rmarkdown reference(pdf)](http://www.rstudio.com/wp-content/uploads/2015/03/rmarkdown-reference.pdf)によると以下のように記述があります。

> Syntax highlighting style (e.g. "tango", "pygments", "kate", "zenburn", and "textmate") includes.

したがって、上述の`highlight: "tango"`のところを`highlight: "pygments"`のように指定すると変更できます。どんな感じになるかは、実際に試して確認してみてください。なお使用できるテーマは以下のとおりです:

- default(標準のテーマ)
- tango
- pygments
- kate
- monochrome
- espresso
- zenburn
- haddock
- textmate

## 補足: 標準の値とこまかい話

以前書いた、[「RStudioの"knit HTML"でPandocに送っている内容」のこの箇所](http://qiita.com/kazutan/items/eb15a42607f87f57b525#17%E8%A1%8C%E7%9B%AE-%E3%82%B7%E3%83%B3%E3%82%BF%E3%83%83%E3%82%AF%E3%82%B9%E3%83%8F%E3%82%A4%E3%83%A9%E3%82%A4%E3%83%88%E3%81%BE%E3%82%8F%E3%82%8A%E3%81%AE%E8%A8%AD%E5%AE%9A)で、デフォルト値はこのようになってました:

```
 --no-highlight
 --variable highlightjs=/Library/Frameworks/R.framework/Versions/3.2/Resources/library/rmarkdown/rmd/h/highlight 
```

この内容について説明します[^1]。

[^1]: なお以下の説明は、pandocのユーザーガイドの内容、{rmarkdown}内に含まれるファイルのコード、そして出力されたhtmlのソースを比較して、多分こうなってるんだろうと私が推測したものです。これが当たってて内容を読んだところで、普通にRmdを使う分には全く影響しないと思います。

まず最初の行の`--no-highlight`は、pandocのユーザーガイドによれば「強調表示をなしにする」というオプションです。つまりこれが指定してあることで、pandoc本体が内包してるコードハイライト機能がOFFになります。

そして次の行では`--variable highlightjs=...`とありますが、これは`{rmarkdown}`内にある`highlightjs`へのパスとなっています。`{rmarkdown}`は内部にhighlightjsを内包しており、こちらを利用するように設定されているのでしょう。

この二つのエンジンはキーワードの見つけ方などが異なります。そのためデフォルトのhighlightjsでは強調されなかったものがテーマ設定をすると強調されるようになる、といったことが起こります[^2]。割とめんどくさいです。

[^2]: たとえば`summary`は、highlightjsエンジンでは`span.identifier`になりますがpandoc内のエンジンでは`span.kw`となります。強調やカラーリングがあたるかどうかはcss(テーマ)次第です。

なお、highlightjs側のテーマは`default`と`textmate`で、残りは全てpandoc内のエンジンを使用するテーマとなります[^3]。またどうしても他のハイライトテーマを使用したい場合は、オンラインにあるhighlightjsをソースとして当てる方法がありますが、ここでは省略します。

Enjoy!

[^3]: 本来のhighlightjsはすごくたくさんのテンプレートがあるんですけどね…。
ローカルでtest kitchenする方法

ローカルにtest kitchen環境を作りました。
具体的には、Vagrantを使ってMac上でCentOSを動かし、その中でDockerを立ちあげtest kitchenします。
どこも汚さないので、カジュアルにレシピを書いてテストできます。

# そもそもtest kitchenとは
こちらで詳しく紹介されてます。
http://qiita.com/eielh/items/64e197f4f1eaf5ff6097

# 今回の環境構成
・Mac OSX 10.10
・Vagrant 1.7.4
・CentOS 6.7
・Docker 1.7.1

# 構築手順
## vagrantのインストール
CentOS環境を構築するにあたって、まずはvagrantをインストールします。
homebrewを使うと簡単にインストールできます。

```lang:sh
brew install vagrant
```

## test kitchenを走らせるCentOSの構築
bootstrap.shとsetup.shを用意しておけば初回のvagrant up実行時に、
自動でtest kitchen環境が構築されるので、かなり便利です。
### VagrantFileの作成
まずは好きなディレクトリ配下でvagrant initしてください。

```lang:sh
cd hogehoge
vagrant init
```
これにより、VagrantFileが作成されました。下記2点を修正してください

```lang:sh
・・・省略・・・

config.vm.box = "bento/centos-6.7"

・・・省略・・・

config.vm.provision :shell, :path => "bootstrap.sh"
```

### bootstrap.sh
bootstrap.shファイルを作成します。
vagrantユーザで環境を作成するために必要です。
これをやらないとすべてrootユーザで作成されてしまいます。

```lang:sh
sudo -u vagrant sh /vagrant/setup.sh
```

### setup.sh
bootstrap.shからこのsetup.shが呼び出されます。
下記の手順がすべて自動実行されます。

```lang:sh
#!/usr/bin/env bash
curl -L -O https://opscode-omnibus-packages.s3.amazonaws.com/el/6/x86_64/chefdk-0.10.0-1.el6.x86_64.rpm
sudo rpm -ivh chefdk-0.10.0-1.el6.x86_64.rpm
echo 'eval "$(chef shell-init bash)"' >> ~/.bash_profile
echo 'export PATH=/opt/chefdk/bin:$PATH' >> ~/.bash_profile
rm chefdk-0.10.0-1.el6.x86_64.rpm
sudo yum -y install git docker-io.x86_64 docker-io-devel.x86_64
gem install berkshelf knife-zero knife-ec2 test-kitchen kitchen-docker serverspec
sudo usermod -aG docker vagrant
sudo service docker start
```

### 完成したtest kitchen環境を使ってみる
まずはログイン

```lang:sh
vagrant ssh
```

sampleをとってきてkitchen testしてみます。

```lang:sh
git clone https://github.com/hiramotoys/cookbook-sample.git
cd cookbook-sample
kitchen test
```
kitchen testは結構時間がかかります。
環境構築に成功していれば、dockerが立ち上がって、そこにレシピが適用され、serverspecが実行されるはずです。
### 参考　kitchen testが実行される環境の選択方法について
今回使ったcookbook-sample/.kitchen.ymlを参照してください。そこに、

```lang:sh
driver:
  name: docker
```

というのが書かれてあります。ここを変更することで、docker以外の環境でtest kitchenできます。

# ハマりどころ
dockerで動かすレシピ適用先のゲストkernelが、vagrantで動かしているホストのkernelよりも新しすぎる場合、
kernel too old と怒られます。
docker上でubuntu14などの新しめのディストリを使う場合は注意してください。

gemはtest-kitchenという名前だが、実行コマンドは、「kitchen test」です。
「Nox App Player」でスクリプトレコーディングを実現

「Nox App Player」は、モバイルゲームやアプリをPCで楽しめる新しいAndroidエミュレータです。

Nox App Player 3.0でいろんな新機能が追加されましたけど、今回はスクリプトレコーディング機能を紹介します。

スクリプトレコーディング機能とは、エミュレータでのマウスときキー操作の入力信号を記録・再生する機能です。

ボタンは右側のツールバーにあります。

![1.png](https://qiita-image-store.s3.amazonaws.com/0/98372/7938bf99-4e2c-65b4-0f9e-50cf22c36156.png)


クリックすれば、下図のように記録ができます。

![2.png](https://qiita-image-store.s3.amazonaws.com/0/98372/9e1784e8-6f42-5d5a-9c06-f354d839cf44.png)


終了すると自動的に保存できます。

![3.png](https://qiita-image-store.s3.amazonaws.com/0/98372/468ec395-e9c0-f91c-ae8f-31e471623877.png)


再生するには一回と無限再生が可能です。

もう一回クリックすれば終了できます。

![4.png](https://qiita-image-store.s3.amazonaws.com/0/98372/cefaa5a8-fb9b-acfb-4ccd-8186afb972f2.png)


再生するとさっきマウスのクリック信号が見えます。


![7.png](https://qiita-image-store.s3.amazonaws.com/0/98372/dd1fa1df-7ce7-0c64-ee0f-5ef2028b21ce.png)

![8.png](https://qiita-image-store.s3.amazonaws.com/0/98372/5239d27b-e76d-04f9-27a9-1ec503d0d5e7.png)


勿論仮想キーの設定でキーの入力信号も記録・再生できます。


![5.png](https://qiita-image-store.s3.amazonaws.com/0/98372/82d784c1-b9ae-184c-3a7f-4b13a3bda420.png)

![6.png](https://qiita-image-store.s3.amazonaws.com/0/98372/856b2bea-ac7e-d531-826b-6ec3afb6bae8.png)


この機能で重複動作があるのゲームやAndroid操作が簡単になります。

公式：jp.bignox.com
Node.jsのソース修正後、nodemonで自動再起動

![](https://camo.githubusercontent.com/fd1ea21338ceeef34920e44e97d099f3c47a78c3/687474703a2f2f6e6f64656d6f6e2e696f2f6e6f64656d6f6e2e737667)

#nodemon

*ソース変更を検知してプロセスを自動で再起動*
[nodemon公式サイト](http://nodemon.io/)
[nodemon - github](https://github.com/remy/nodemon)

***  
  
##Node.js開発時の問題
Node.jsで開発するとき、ソース修正後、手動でnode.jsプロセスを再起動しないと反映されないという問題があります。

これはNode.jsで読み込まれたJavascriptファイルがキャッシュされるため、ソースコードを更新しても、Node.jsの再起動をしないとソースが反映されないためです。


![](https://github-camo.global.ssl.fastly.net/970c26097c7d7e51021fcdee8a4cec7d9fa16de2/687474703a2f2f6e6f64656d6f6e2e696f2f6e6f64656d6f6e2e706e67)


##nodemonの特徴  
nodemonを利用すれば、手動でnode.jsプロセスを再起動せずにソースが自動的に反映されます。  

- プロジェクトのソースを変える必要がない  
- node.jsアプリをwrapする  
- フォルダ下のソースを監視し、何か変わったら自動的にnode.jsを再起動する  

***
##nodemonを実際に使ってみる  

**nodemonのインストール**

```shell-session
npm install nodemon -g
```

**package.json**  

```json:package.json
"scripts": {
    "start": "nodemon ./bin/www"
}
```

※上記のstartはフレームワークの[expres](http://qiita.com/twipg/items/b20895504a87d6b46a00)を利用しているので、./bin/www

**サーバーの起動**  

```shell-session
% node start
> hoge@0.0.0 start /Users/hoge  
> nodemon ./bin/www  

[nodemon] 1.8.1  
[nodemon] to restart at any time, enter `rs`  
[nodemon] watching: *.*  
[nodemon] starting `node ./bin/www`  
```

**ファイルに変更があると自動で再起動される**

```shell-session
[nodemon] restarting due to changes...  
[nodemon] starting `node ./bin/www`  
```
Swiftで競技プログラミング

[paizaでSwiftがつかえるオンラインハッカソン](https://paiza.jp/poh/ando?read=true)が始まりました。
OSSで公開されたので今後使える環境も増えていくかと思います([Atcoderにも入りそうな兆し？](https://twitter.com/chokudai/status/672611947255214081))。

さて、実際に競技プログラミングでSwift使ってみて、困ったこと等が幾つかあったので、ここに共有しておきます。

なお、Swiftの構文等はこの記事では扱わないので別のところを参照してください。

## 基本的な書き方

とくにmain関数のようなものは必要ないので直接コードを書いていけばいいです。
環境がないとかであればコードを書くのは[このサイト](http://swiftstub.com/)を使うのが良いかと思います。実際Xcodeでプロジェクト作ってとかはめんどくさかったので、私はここで書きました。

## 標準入力について

ここが一番ハマりました。ググるとNSFileHandleを使うとでてきますがどうもNSxxxx系のクラスは利用できないっぽいです(Linux上で動いてる関係？詳しい理由はわかりません。)。
`readLine`という関数で標準入力から一行取ってくることができました。
以下の感じで使います。

```swift
let line: String = readLine()!
let n: Int = Int(readLine()!)!
```

`!`が随所に入ってくるのが微妙ですが、言語仕様上どうしようもないです。

標準出力に関しては普通に`print`を使えばいいです。

## 一行にたくさん数値がくる系の入力

scanfのようなものがないので、splitしてmapしたいところです。が、よく使われるであろう`line.componentsSeparatedByString(" ")`が使えません(多分NSxxxx系が使えないせい)。
`String`に`split`メソッドはありませんが、幸い`CollectionType`にあるのでそちらを使います。

```swift
extension String: CollectionType {} // splitを使うためのおまじない

let a: [Int] = readLine()!.split(" ").map { Int($0)! }
```

長ったらしいので、関数化しておくと良いかと思います。

```swift
func readInts() -> [Int] {
    return readLine()!.split(" ").map { Int($0)! }
}
```

なお、固定数の数値が入力されて、それぞれに名前が付けたい場合があると思いますが、以下のようにすると楽で良いと思います。

```swift
prefix operator * {} // Pythonのリストを展開するオペレーターのイメージで*
prefix func * <T> (a: [T]) -> (T, T) { return (a[0], a[1]) }
prefix func * <T> (a: [T]) -> (T, T, T) { return (a[0], a[1], a[2]) }

let (w, h) = *readInts()
let (a, b, c) = *readInts()
```

ちなみに文字列のjoinは特に何もしなくても使えます。
競技プログラミングでも出力時に結構使いますね。

```swift
["a", "b", "c"].joinWithSeparator(" ") // "a b c"
```

## 配列の作成

これは私は困らなかったですが、困る人がいそうな気がするので。
ぱっと思い浮かぶので2通りほどあるので、好きな方を使えばよいかと思います。

```swift
let a1: [Int] = [Int](count: 3, repeatedValue: 0) // [0, 0, 0]
let a2: [Int] = (0..<3).map { _ in 0 } // [0, 0, 0]

// 後者のほうが応用が効くので使いやすいかもしれないです
let b: [Int] = (0..<3).map { $0 } // [0, 1, 2]
```

## まとめ

RubyとかのLL系ほどではないけど、気軽に書けるけどちゃんと型がついてるので安心できるので、競技プログラミングでSwiftという選択肢はありかなという感じ(同じ用途ならScalaとかのほうが今のところは現実的かなという感じがするが)。
未検証ですが、コンパイルされて実行されるので実行速度的にもそこそこ速そうです。

今後Swiftが使える環境が増えていくといいですね。
今頃CentOS7系を触りだした

#CentOS7.1をVPSにインストール
RHEL系のフリーディストリビューションを使ってきましたが大幅にコマンド体系が変わったのを体感。
下地を構築中なのでメモに近い内容で初投稿です。

Firewalldを試そうとしたけど動かすとなぜかSSHもHTTPも繋がらなくなる。
調べるとVPS側の仕様で使えないことが判明してiptablesとip6tablesに書き直す。

[Let's encrypt](https://letsencrypt.org/)も色々参照しながらApacheでHTTPSで警告なく使えるところまでできました。

##systemctlコマンド
ifconfigやserviceにchkconfigもなくなっていくんだなと。
でもsystemctl start smb nmbのように一行でstartしたりstopしたりenableにしたりdisableにできるのは便利ですね。
まだコマンド自体に慣れてないのでついserviceと入力してしまう。

落とし穴？
**systemctl save iptables**
はありませんでした。
とりあえずservice iptables saveで保存しておきました。
まだ調べてません…
JAVA hashCode()のオーバーライド

▪️Test56.java

```java
import java.util.*;

public class Test56 {
	public static void main(String[] args) {
		Set<Hare56> hare = new HashSet<Hare56>();
		Hare56 h1 = new Hare56();
		Hare56 h2 = new Hare56();
		Hare56 h3 = new Hare56();
		h1.name = "野うさぎ";
		h2.name = "野うさぎ２";
		h3.name = "野うさぎ３";
		h1.item = "にんじん";
		h2.item = "にんじん";
		h3.item = "にんじん";
		h1.item2 = "レタス";
		h2.item2 = "レタス";
		h3.item2 = "レタス";
		hare.add(h1);
		hare.add(h2);
		hare.add(h3);
		System.out.println(hare.size());
		hare.remove(h2);
		System.out.println(hare.size());

	}

}
```

▪️Hare56.java

```java
public class Hare56 {
	public String name;
	public int hp;
	public String item;
	public String item2;

	public boolean equals(Object o) {
		if (this.name == o && this.item == o && this.item2 == o) {
			return true;
		}
		return false;
	}

	public int hashCode() {
		int result = 35;
		result = result * 31 + name.hashCode();
		result = result * 31 + item.hashCode();
		result = result * 31 + item2.hashCode();
		return result;
	}

}
```

▪️Test56.java 実行結果
3
2
cybozu.com developer networkの使い方

kintone Advent Calenderももうすぐ折り返しですね。
後半もどのようなネタがアップされてくるのかが楽しみです。

さて、kintoneの開発をしていく上で悩みの一つがネット上での情報がまだまだ少ないことだと思います。
幾つか優良なサイトはありますが、一番活用されているのはやはりサイボウズ社が運営している [cybozu.com developer network](https://cybozudev.zendesk.com/hc/ja) でしょう。

<img width="967" alt="スクリーンショット 2015-12-08 13.25.48.png" src="https://qiita-image-store.s3.amazonaws.com/0/100592/2c31ad3d-8001-67cc-16d8-817eb59ba9fe.png">

今回はdeveloper networkの使い方についてポイントを５つ挙げてみたいとおもいます。

#【その１】開発者ライセンスを申し込もう
開発をする上でいきなりお客様の環境で開発するわけにはいかないので、開発環境が必要になりますよね。

　　　　　　![license.png](https://qiita-image-store.s3.amazonaws.com/0/100592/eafaddda-1fdc-80b9-9309-80dc4707ced0.png)


トップページのここから申し込むとなんと**１年間利用可能な開発環境を無償でもらえちゃいます。**
ユーザーは５ユーザー、ディスク容量も10GB付いているので開発する上では全く問題ない環境です。
もちろん、**自社利用したり、お客様にそのまま提供しちゃだめですよ！**

#【その２】APIマニュアルを使い倒そう
kintone APIに関するマニュアルはここにしかありません！
[kintone API マニュアル](https://cybozudev.zendesk.com/hc/ja/categories/200147600)

JavaScriptのAPI、REST APIの仕様で分からないことがでたらまずはここを確認しましょう。
個人的にオススメなのは [PC/スマートフォン早見表](https://cybozudev.zendesk.com/hc/ja/articles/202738940-PC-%E3%82%B9%E3%83%9E%E3%83%BC%E3%83%88%E3%83%95%E3%82%A9%E3%83%B3-%E6%97%A9%E8%A6%8B%E8%A1%A8) です。

kintoneはスマートフォンでアクセスするとスマホ専用の画面になります。
ですので、カスタマイズしたJavaScriptファイルもPC用とスマホ用で分かれて適用する必要があります。

![admin.png](https://qiita-image-store.s3.amazonaws.com/0/100592/c98cd533-0c7e-bc1f-ef7d-9e5cc24b5a4b.png)

PCとスマホでは利用できるJavaScript APIも異なりスマホのほうができることが少ないので、お気をつけください！

あと、初めてkintoneのカスタマイズをされる場合は、[kintone JavaScript コーディングガイドライン](https://cybozudev.zendesk.com/hc/ja/articles/201793484) は必ず目を通しておいたほうが良いです。

ちなみに[Garoon API](https://cybozudev.zendesk.com/hc/ja/categories/200157760)のマニュアルもありますよ。。

#【その３】Tipsを実際にやってみよう
「kintoneのカスタマイズ開発をやりたいけど、どこから手をつけたらいいんだろう？」とお悩みのあなた。
[はじめよう kintone JavaScript API](https://cybozudev.zendesk.com/hc/ja/sections/200332780-%E3%81%AF%E3%81%98%E3%82%81%E3%82%88%E3%81%86-kintone-JavaScript-API)を見ながら実際にやってみましょう！

全12回の中でJavaScript APIからREST APIまで、さらにはカスタマイズ開発では絶対に外せないjQueryの使い方までkintoneのカスタマイズ開発で必要なテクニックが網羅されています。
この連載は[サイボウズスタートアップス](http://cstap.com/)の落合さんが書かれているのですが、今まで多くの方が落合さんに感謝されてるんじゃないでしょうか（笑）

#【その４】質問をしてみよう
開発をしていて「これってどうやって実現するんだろう？ネットで調べても分からない！」という時は[コミュニティ](https://cybozudev.zendesk.com/hc/ja/community/topics)で質問しましょう。

![community.png](https://qiita-image-store.s3.amazonaws.com/0/100592/e5fcd03a-7c96-dcc7-3a96-738756597334.png)

ここではほぼ毎日のように何かしらの質問が投稿されていますが、回答率もかなり高いです。
しかもkintoneエバンジェリストが直接回答されるケースが多いので的確な回答が得られると思います。

そして質問する側、回答する側双方が楽しめるコミュニティにするためにも以下の点には注意していただいたほうがよいと思います。

- kintoneの開発に関するコミュニティなのでJavaScript自体に関する質問ではなく、kintoneのAPIやkintoneの仕様に絞った質問をしましょう
- サンプルコードをすぐに求めるのではなく自分が試したけどダメだったコードを示すなど回答者が回答しやすい質問にしましょう
- 回答があったら必ず返信をしましょう

#【その５】質問に答えよう
**ただ質問をするだけではなく積極的にフォーラムへの質問に答えていきましょう！**
質問に答えるために自分で色々と検証しますので、自ずと自分のスキルも上がります。
そして、何よりもみんなが質問をしてみんなが答えることでコミュニティが盛り上がり、developer netowrkのサイトが今以上にどんどんと優良なサイトになり多くの方に活用してもらえる生きたサイトになっていきます。

#まとめ
と、以上５つほどポイントを挙げさせていただきました。
他にも[プラグインのサンプル](https://cybozudev.zendesk.com/hc/ja/sections/200681620-kintone-%E3%83%97%E3%83%A9%E3%82%B0%E3%82%A4%E3%83%B3)であったり、APIに関するアップデート情報など有用な情報は盛りだくさんなので、ここは定期的にチェックすることをおすすめします。

そして、**developer networkはサイボウズさんが運営されていますので積極的に参加し、機能の要望も上げていくことでご希望の機能実装も行われるかもしれません（笑）**
衝撃のUX!Initimate Mobilesとは


#はじめに
ベルリン大学の[Design Research Lab](http://www.design-research-lab.org/about/)が開発した[Initimate Mobiles](http://www.design-research-lab.org/projects/17/)を紹介します。
このシステムは、[Fabian Hemmert博士](Fabian Hemmert)により開発され、[論文](http://www.fabianhemmert.com/download/hemmert2010m_erotichci10_intimatemobiles.pdf)が書かれています。
![im_comm_moisture.jpg](https://qiita-image-store.s3.amazonaws.com/0/100280/367bcd3b-7a04-a706-3d2e-131f4b1784c4.jpeg)

#Initimate Mobilesとは
Initeimate Mobilesは電話で話している恋人同士に新たな感覚をフィードバックすることでコミュニケーションを活性化させる目的で作られたシステムです。


##触覚フィードバック
従来の電話によるコミュニケーションは、主にバーバルコミュニケーション（言語）に集中していました。このシステムは通常の電話をする動きの中に、
- 手を握る
- キスをする
- 息を吹きかける
というようなノンバーバルコミュニケーションの導線を追加しました。
###手を握る
これは端末を握るという動作を用いたインタラクションです。このシステムの側面にはボタンが設置されています。そのボタンを握るように押すことで、相手の端末についている、ベルト部分が締まることで、手をつないでいるような感覚を呈示します。
![55e82cd4c3146d98454a4c6f2787dd89.png](https://qiita-image-store.s3.amazonaws.com/0/100280/9d266e52-5ddb-136f-7178-9962d240fbba.png)

###キスをする
端末の受話器部分にキスをすることで、相手の端末についている濡れたスポンジが動き、ホッペにキスをしている感覚を呈示します。
![0a4ae7955e96001044b338d0972785e9.png](https://qiita-image-store.s3.amazonaws.com/0/100280/5f71aecb-3df7-32bc-1192-37764437a4c1.png)


###息を吹きかける
端末に息を吹きかけることで、相手の耳に風を送ります。
![08ea1e3fcc4b50c0b7261d3ebcbcd3d8.png](https://qiita-image-store.s3.amazonaws.com/0/100280/2b5bc472-a462-e76f-d7f8-27f66dd49859.png)

#さいごに
Initimate Mobilesはコンセプトとして開発されたため実用化はされていません。私はこのシステムを紹介した理由は、「携帯電話を用いた会話」という社会的にも確立されている行動内に恋人のコミュニケーションを拡張させるUXがあったからです。
他のシステムは、ユーザに学習させる必要があるデバイスや行動を発生させるものがありますが、通常の枠内から逸脱することなく、スマートなコミュニケーションを取れていると思っています。
ArduinoUnoを2台使ってブートローダを書き込む

# WHAT
ArduinoUnoを2台使って真っ新なATmega328PにArduinoBootloaderを書き込みます。
回路作るのが面倒で、でもArduinoを2台以上持ってる人向け。
簡単。

# PURPOSE
<a href="http://www.aitendo.com/product/10793">びんぼうでいいの</a>などに使う石の生産

# USE
<a rel="nofollow" href="http://www.amazon.co.jp/gp/product/B0044X2E5S/ref=as_li_qf_sp_asin_tl?ie=UTF8&camp=247&creative=1211&creativeASIN=B0044X2E5S&linkCode=as2&tag=zerocr-22">Arduino Uno</a> * 2台
PC(本稿ではMacを使用する)
ArduinoIDE(本稿では1.0.5)
ATmega328

# HOW
以下、2台のArduinoをそれぞれAとBとする。
## 1. 下準備
まず、AからATmega328を(足折ったりしないように)取り外して、まっさらなATmega328を載せる。
ここでは向きに注意して載せる。
インデックス(切り欠き)がある方が、基板の端っこのほうになるように載せる。

## 2. 接続
以下のようにピンを接続する。

| A |  | B |
|:-----------:|:------------:|:------------:|
| 5V | <-> |     5V    |
| GND |      <-> |    GND    |
| RESET |        <-> |     10     |
| 11 |          <-> |     11      |
| 12 |       <-> |    12    |
| 13 |     <-> |   13    |

## 3. ArduinoISPの用意
BをPCに接続してArduinoISPを書き込む。
スケッチの例の中にArduinoISPがあるので、選択し、出てきたスケッチをそのままBにアップロードする。
終わったらTool > 書き込み装置からArduino as ISPを選択しておく。

## 4. Bootloaderの書き込み
Tool > ブートローダの書き込みを選択し、正しく接続されていれば書き込みが始まり、約30秒ほどで書き込みが終わる。
AとBの接続を外し、AをPCに繋いだ時にArduino基板上のL(と横に書いてあるLED)が点滅したあと、点灯していれば成功と思われる。

# 追記
思い立ってArduinoISPを1.6.6で試してみたら、10秒足らずで終わってしまった。
はじめてE-JAWSカンファレンスに参加してきました

E-JAWSカンファレンスに参加してきました。
内容を簡単にご紹介します。

# AWSのご紹介
AWSエバンジェリスト渥美さん(前職はSIer)が20分ほどAWSのサービスを簡単にご紹介。
・今やIT企業の25%はパブリッククラウドを導入
・AWSはサービスインしてから9年間で50回の値下げ
・新規サービスは2015年で既に500のサービス更改を実施
・パブリッククラウドはセキュリティ面で懸念される経営陣およびエンジニアが多いが
　DCと変わらんとのこと。ソニー銀行もAWSに移行している
・スシローはAmazon Machine Learning(機械学習)を使って、時間帯によってどのネタを提供するか調整している

ここから企業の情シス、インフラ担当の方が壇上に上がり、AWSの取組をご紹介

# 丸紅ITソリューション
## AWS導入前はどうなっていたか。
・某ベンダーのプライベートクラウドでよろしくやっていた、ハード・運用保守のコストで頭を悩ます
・3.11の震災でDR対策としてDC(東京)のクローンを大阪に作る→当然コストも2倍近くになって頭を悩ます
・丸紅グループさんではそれぞれで物理サーバをもっていて管理が乱雑になっていた
→上記を改善するためAWS導入を検討。

## AWS導入方法
1. 一旦物理サーバをVMに仮想化
2. VMインポートツールより、仮想マシンをクラウドに移行
3. ↑すべてが自動で移行できるわけもなく、微調整しながら移行
4. 現時点で150サーバ、30システムがAWSで頑張っている
※日立、サーバーワークスにAWSに関してサポートしてもらった

## 導入効果
・要員の最適化
・オンプレミスを止めることはなかなかできないが、AWSではDRテストがし易くなった (年1でやってるそう)

## 今後の方針
・IT部隊を運用ではなく、企画部門などの会社の事業方針に係る部署にしていく

# NTTドコモ
## いつからAWS利用した？
2009年、知見をためるために検証機や小さいシステムから利用開始。
2012年、しゃべってコンシェルで本格利用。
現在、ドコモの外部APIなどで利用。

## AWS利用スタイル
複数アカウントを使用し、個々のシステム(サービス)でそれぞれ独立性を重視して運用・管理を行っている。

## 社内体制
AWS導入にあたり、監査部門を強化。外部攻撃だけでなく内部攻撃に対して特に強化したとこのと。
NW管理者、データ管理者などそれぞれ管理者を設け、一方通行だけではデータが取れない体制。

## その他
ドコモでAWS利用した知見を、コンサルティングしてるらしい(19万円/年)

# パネルディスカッション、懇親会
スポットインスタンスという比較的マイナーな機能を本田技研さんで使用しているとのこと。
本田技研さんは普通のEC2インスタンスのコストを1/7〜10程度に抑えられているとのこと。
なのでHPCとかハイスペックが求められることでもコストを気にせずに出来ているらしい。

検証サーバをスポットインスタンスで構築、勤務時間外はEC2を止めておくなどを
組み合わせれば、非常にコストを抑えられそうだなという印象でした。
また処理が重いバッチを夜間に集中し、バッチサーバを特定時間だけ起動させるとか素敵だなと。

自社の場合、オンプレミスからAWS移管にあたり、コスト的なメリットをどれだけ上層部に伝えられるかが鍵だなと
感じました。
WindowsにChocolatey+VirtualBox+VagrantでCentOS7作ってNode.jsを入れてみた

Node.jsの勉強環境が欲しかったので表題のソフト使って仮想マシンを作ってみました。
私の環境はWindows7 64bitです。
参考にした文書は末尾にまとめましたが、この辺の情報は進歩が早いので既にそのままでは使えなかったりしました。ココに書いた情報も3ヶ月後には動かないかもしれませんw

**なんか上手く行ってない感じもあるのでコメントもご覧下さい。**
まずは結論として最短インストール手順です。
#管理者でコマンドウィンドウを起動
スタートメニューから`cmd[Ctrl]+[Shift]+[Enter]`
以下コマンドウィンドウで操作。

#Chocolateyのインストール
https://chocolatey.org/
```>@powershell -NoProfile -ExecutionPolicy Bypass -Command "iex ((new-object net.webclient).DownloadString('https://chocolatey.org/install.ps1'))" && SET PATH=%PATH%;%ALLUSERSPROFILE%\chocolatey\bin```
以下chocoコマンドを使ってインストール。
**既にイントール済みのソフトはコントロールパネルから通常の手順で事前削除して下さい。**

##VirtualBoxをインストール
```>choco install virtualbox -version 4.3.12 -y```
これやる前、4.3.26インストール済みだったんですけど上手く動かなくて色んなページ見て4.3.12が確実と判断しました。

##Vagrantをインストール
```>choco install vagrant -y```

これで必要ツールが入ったので、コマンドウインドウを開き直す。(このままだとvagrantコマンドにPATHが通ってないため）

#CentOSをインストール
https://atlas.hashicorp.com/bento/
Vagrantファイル用のディレクトリを作ってそこに移動して、
```C:\_vm\centos7>vagrant init bento/centos-7.1```
```C:\_vm\centos7>vagrant up```
```C:\_vm\centos7>vagrant ssh```

##Node.jsをインストール
```$sudo yum install epel-release```
```$sudo yum update```
```$sudo yum install nodejs npm --enablerepo=epel```
###疎通確認
```$ node -v
v0.10.36
$ npm -v
1.3.6
$ node -e 'console.log("hello world");' > /vagrant/hello.txt
$ exit
logout
Connection to 127.0.0.1 closed.
C:\_vm\centos7>type hello.txt
hello world```
/vagrantはホストOSと繋がってるんですね♪

#以下この手順に辿り着くために参考にした文書
基本的にこの手順をベースに実施
http://qiita.com/wakaba260/items/759c24451ddda1f1d2a6

chef/centos-6.5がNotFoundだったので見たのがコチラ
http://qiita.com/yokomotod/items/e69d3cc69a1e16704089

CentOS入れる手順も変わってそうだったので見たのがコチラ
http://snowlong.hatenablog.com/entry/2015/12/01/224341

`vagrant up`でエラーになったので見たのがコチラ
http://qiita.com/medaka5/items/d70751a562a5604c2115
http://blue-goheimochi.hatenablog.com/entry/2014/07/25/Windwos7%E3%81%A7Virtualbox%E3%81%A8Vagrant%E3%81%A7%E4%BB%AE%E6%83%B3%E3%83%9E%E3%82%B7%E3%83%B3%E3%81%8C%E8%B5%B7%E5%8B%95%E3%81%A7%E3%81%8D%E3%81%9A%E3%83%8F%E3%83%9E%E3%81%A3%E3%81%9F

ここでChocolateyって初めて知ったのでお勉強
http://millkeyweb.com/win-chocolatey/
http://qiita.com/konta220/items/95b40b4647a737cb51aa

Vagrantもここでお勉強
http://qiita.com/KentoKarakawa/items/7f0fe31d26a484432ca7
Railsで動的にroutesを追加する

本当はやっちゃいけないことだけど、Engineのテストとかするときにテストの間だけRoutesを追加したいっていうことがある。
**良い子は絶対に真似しないでください**


# 結論

```rb
Rails.application.routes.disable_clear_and_finalize = true
Rails.application.routes.draw do
  get "awesome", to: "hatobin/awesome#index"
end
Rails.application.routes.disable_clear_and_finalize = false
```

または

```rb
Rails.application.routes.send(:eval_block, ->{ get "awesome", to: "awesome#index" } )
```

こう書くとできる。


# 解説

良い子なら普段、

```rb 
Rails.application.routes.draw do
end
```

こんな感じでroutesを定義してると思います。
実はこのdrawメソッド、デフォルトだと呼ばれるたびに以前までに定義していたroutesをクリアするので、準備なしに後から呼ぶと大変なことになります。
disable_clear_and_finalizeはフラグで、こいつの評価結果を真にしてあげればクリアしなくなります。
または、ブロックを書いて直接評価させる、と言う方法をとっています

ぶっちゃけroutes.rbに`if Rails.env.test?`とかすればいいじゃんって感じなんですけど、テストのためだけにroutes生やすのがどうしても気に入らなかったのでやってみました。と言う内容でした。
他にいい方法知ってる人がいたら教えてください〜
Instagram APIをPHPでさくっと使う

#最初に
InstagramではAPIを利用する際にアクセストークンが必要になります。
今回の記事はPHPでAPIを使用するケースなので、
そこを知りたい場合は「instagram アクセストークン 取得」で検索してください。


#本題
APIを利用しようとした時、[Packagist](https://packagist.org/)に公開されているライブラリをいくつか使ってみましたが、利用したいAPIの使用方法が記載されてなかったり、指定ができないscopeがあったりと、微妙に使いにくいものばかりでした。（良いのがあったらごめんなさい）
OAuth認証するのであれば便利なのですが、サーバからAPIを利用するだけなので、これなら自分で実装した方が楽だなと感じて自作しました。
使いたいAPIは、[公式ドキュメント](https://www.instagram.com/developer/)を参照して下さい。

### サンプルコード

```php
class Instagram
{

	private $access_token = 'xxx'; // dummy

	/**
	 * リクエスト
	 *   例1：$instagram->request('users/self');
	 *   例2：$instagram->request('users/self/media/recent', ['count' => 50]);
	 */
	public function request($url, $parameters=[])
	{
		$parameters = $parameters + ['access_token' => $this->access_token];
		$request_url = http_build_url($url, [
			"scheme" => "https",
			"host"   => "api.instagram.com",
			"path"   => "/v1/{$url}/",
			"query"  => http_build_query($parameters),
		]);
		if ($request_url === false)
		{
			return false;
		}

		$ch = curl_init();
		curl_setopt($ch, CURLOPT_URL, $request_url);
		curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
		$result = curl_exec($ch);
		curl_close($ch);
		if (!$response = json_decode($result))
		{
			return false;
		}
		return $response;
	}
}

$instagram = new Instagram();
$user_info = $instagram->request('users/self');
$my_media  = $instagram->request('users/self/media/recent', ['count' => 50]);

```

まだ試していない関数も多いですが、たぶんこれで大半はカバーできるかなと思います。
もし、http_build_queryが使えない環境であれば、下記ライブラリを利用してみてください。
https://packagist.org/packages/jakeasmith/http_build_url
iOSアプリ開発:OpenGLで使う画像

※個人で管理しているHPに引っ越ししました。
リンク切れ等考慮して本ページは残しておきますが、今後は[HP](https://kittenkitten.net/2015/12/08/ios_dev_opengl_image/)のほうで更新します。

## 現象
数年前開発してた頃は、iOSでのOpenGLを使う際画像は2の冪乗じゃないと駄目！と思ってました。
この頃はAppleが公開してたサンプルのimageUtil.mを使ってテストしてました。

## 調査
調べてみると、今はGLKitのGLKTextureLoaderを使えば2の冪乗じゃなくても使えました。

## 対応
このように実装すると、textureInfoに様々な情報が設定され、glBindTextureで使える情報も得られます。

```objc:Test.m
// Load texture
NSString* filePath = [[NSBundle mainBundle] pathForResource:@"test" ofType:@"png"];
GLKTextureInfo* textureInfo =
	[GLKTextureLoader textureWithContentsOfFile:filePath options:nil error:nil];
if (textureInfo) {
    NSLog(@"Texture Loaded. name = %d size = (%d x %d)", textureInfo.name, textureInfo.width, textureInfo.height);
}
glBindTexture(GL_TEXTURE, textureInfo.name);
```
Rails プロジェクトのリポジトリ名を変更した際に必要だったこと

# <i class="fa fa-fw fa-flag"></i> やりたいこと

Rails プロジェクトのリポジトリ名を変更したい。
また Capistrano でリモート環境にデプロイしているので、変更後もデプロイが成功するようにしたい。

# <i class="fa fa-fw fa-info-circle"></i> バージョン情報

* Rails : 4.2.5
* Git : 2.6.3
* Capistrano : 3.4.0

# <i class="fa fa-fw fa-cubes"></i> 手順

以下の手順は [Bitbucket](https://bitbucket.org/) で管理している `yuno` という名前のリポジトリを `miyako` に変更するという想定です。

## 01. リポジトリ名を変更する

Bitbucket のリポジトリ設定画面でリポジトリ名を `miyako` 変更します。
テキストボックスの値を書き換えて保存するだけなので、具体的な方法は割愛します。

## 02. ローカル環境のディレクトリ名とリポジトリ URL を更新する

```
$ mv ~/workspace/yuno ~/workspace/miyako
$ cd ~/workspace/miyako
$ git remote set-url origin git@bitbucket.org:quanon/miyako.git
```

## 03. Capistrano の設定ファイルを更新する

`:application` と `:repo_url` の行を更新します。

```config/deploy.rb
set :application, 'miyako' # 更新
set :repo_url, 'git@bitbucket.org:quanon/miyako.git' # 更新
set :deploy_to, "/var/www/#{fetch(:application)}"
set :scm, :git
```

## 04. デプロイ先のディレクトリ名とリポジトリ URL を更新する

`:deploy_to` 配下にある `repo` ディレクトリで `git remote set-url` を行います。

```
$ ssh deploy-target-server
$ mv /var/www/yuno /var/www/miyako
$ cd /var/www/miyako/repo
$ git remote set-url origin git@bitbucket.org:quanon/miyako.git
```

## 05. Webサーバーの設定を更新する

必要に応じて Apache や Nginx の設定ファイルを更新します。具体的な方法は割愛します。

## 終わり

以上で、リポジトリ名変更後も Capistrano によるデプロイが成功するようになりました。
Exiting; no certificate found and waitforcert is disabled の対処法

古い設定のPuppetなどで、

```
Exiting; no certificate found and waitforcert is disabled
```

って言われてagent実行が進まなくなることがあります。以下を見直してみましょう。

### masterのautosignの設定は？

`/etc/puppet/autosign.conf` を見てみましょう。

```
*
```

となっていればなんでもサインします。

```
*.example.com
*.dev.example.com
```

のように、domainを限定している場合もあります。agent側のdomainが一致しない場合は設定を調整する必要があります。

### 一度署名待ちになってしまったら

あるdomainが一度「設定待ち」状態になったら、autosignの設定を変更しても解除されません。

その場合、masterで手動で

```bash
$ puppet cert sign --all
```

を実行する必要があります。

----

ということで「えっ」となりがちで情報が少ないのでメモ程度ですが、書いてきます。
参考資料: 

* http://www.atmarkit.co.jp/ait/articles/1410/08/news016_3.html
昨日の日付がこんなに簡単に・・・。

```javascript:
var now = new Date();
var yesterday = new Date(now.getFullYear(), now.getMonth(), now.getDate() - 1);
```
って書くと、

```js
console.log(now);       // Thu Jul 01 2021 07:08:25 GMT+0900 (日本標準時)
console.log(yesterday); // Wed Jun 30 2021 00:00:00 GMT+0900 (日本標準時)
```

こうなる・・・。

ずーーーーーっと、日付だけマイナス１されて、月はそのままだと思ってました。
（でもなんか違和感があるなぁー）

覚えようっと♪
Ubuntu/Debianにおいて再起動無しでLinux Bonding(VLAN-tagged)を構成するための黒魔術

`/etc/network/interfaces`を以下のように編集してタグVLANがついたbondインターフェースを構成する場合、一度再起動する必要があると、ずっと思っていた。

```shell-session
$ cat /etc/network/interfaces
auto lo
iface lo inet loopback

auto bond0
iface bond0 inet manual
        mtu 1500
        bond-mode balance-alb
        bond-miimon 100
        bond-slaves em1 em2

auto bond0.1234
iface bond0.1234 inet static
        address 10.x.y.50
        netmask 255.255.255.0
        gateway 10.x.y.1
        network 10.x.y.0
        vlan_raw_device bond0

auto em1
iface em1 inet manual
bond-master bond0

auto em2
iface em2 inet manual
bond-master bond0
```

> `1234`は、VLANのIDである。

上記のNIC構成の場合、`root`ユーザで以下のコマンドを打つことで、再起動を避けることが可能である。

```shell-session
$ ifdown bond0 && ifup bond0 && ifup em1 && ifup em2 && ifup bond0.1234
```
アルゴリズム1000本ノック #2. Longest common substrings

#### Problem
```
与えられた２つの文字列に対し, 共通で持つ部分文字列の最大長を求めよ.
例) "abcdefg" と "cdeg" が与えられたとして, 最大の部分文字列は "cde" なので答えは３.

```

#### Solution
DP（ダイナミックプログラミング）の中では古典的な問題です。

２つの文字列を S1 と S2, それぞれの長さをM, Nとします.
総当りでS1からすべての部分文字列を抽出して, それらがS2に含まれているかを１つずつチェックすることでも解けますが, 計算量は O(M^2*N) となってしまいます.

効率的に解くために, 配列 m[M][N] を用意して m[i][j] に S1[i] と S2[j] がそれぞれ共通の部分文字列の何文字目にあたるかを格納するようにします. （共通の部分文字列に含まれていない場合は0を入れる）

![example](http://f.st-hatena.com/images/fotolife/r/rdtr/20151102/20151102165321.png?1446512129)

上の例を見ると, S1[3] も S2[1] も 'd', かつ and m[2][0] = 1 なので m[3][1] = 2 となります. つまり, S1[3] and S2[1] は部分文字列の２文字目（１つ前の文字が１文字目なので）ということになります. 
これを一般化して, m[i][j] は S1[i] =S2[j] ならm[i-1][j-1]+1, そうでなければ0と値を求めていくことができます.

これがいわゆるボトムアップのダイナミックプログラミングです。

```python:algorithms_dp_longest_common_substring.py
def LCS(s1, s2):
    if not s1 or not s2:
        return 0
    
    len1, len2 = len(s1), len(s2)
    
    # memorization
    m = []
    for i in range(len1):
        m.append([0]*len2) #m[len1][len2]
    
    lcs = 0
    
    # set 1st index value
    for i, ch in enumerate(s1):
        if ch == s2[0]:
            m[i][0] = 1
            lcs = 1
    for i, ch in enumerate(s2):
        if ch == s1[0]:
            m[0][i] = 1
            lcs = 1
            
    # m[i][j] stands for s1[i] and s2[j]
    # is the m[i][j] th bit of a common substring
    for i in range(1, len1):
        for j in range(1, len2):
            if s1[i] == s2[j]:
                m[i][j] = m[i-1][j-1] + 1
                lcs = max(m[i][j], lcs)
            else:
                m[i][j] = 0
    return lcs
```

この場合, 計算量と空間料は O(MN)となります.

Jave版のコードはこちら:

```java:algorithms_dp_longest_common_substring.java
public class Solution
{
  public static int LCS(String s1, String s2) {
    int l1 = s1.length();
    int l2 = s2.length();
    if (l1 == 0 || l2 == 0) return 0; // no common strings
    
    // memorization
    int[][] m = new int[l1][l2];
    int maxLen = 0;
    
    // set 1st index value
    for (int i = 0; i < l1; i++) {
      if (s1.charAt(i) == s2.charAt(0)) {
    	m[i][0] = 1;
        maxLen = 1;
      } else m[i][0] = 0;
    }
    for (int i = 0; i < l2; i++) {
      if (s2.charAt(i) == s1.charAt(0)) {
    	m[0][i] = 1;
        maxLen = 1;
      } else m[0][i] = 0;
    }
    
	// m[i][j] stands for s1.charAt(i) and s2.charAt(j)
    // is the m[i][j] th bit of a common substring
    for (int i = 1; i < l1; i++) {
      for (int j = 1; j < l2; j++) {
      	if (s1.charAt(i) != s2.charAt(j)) m[i][j] = 0;
        else {
          m[i][j] = m[i-1][j-1] + 1;
          maxLen = (m[i][j] > maxLen)? m[i][j] : maxLen;
        }
      }
    }
    return maxLen;
  }
}
```
Deviseで指定ユーザ認証を手動で行う


Devise使って、指定ユーザの認証を手動で行うには、普通にユーザのオブジェクトを渡すだけ。

```ruby
class User::RegistrationsController < Devise::RegistrationsController

  def manual_auth
    user = User.find(100)
    sign_in_and_redirect(user)
    # sign_in(user)
  end
  
end
```
Slackのはなし

この記事は、[モバイルファクトリー Advent Calendar 2015](http://qiita.com/advent-calendar/2015/mobilefactory) 九日目担当の@hiyoko9191です。

# はじめに
2015年から、業務もプライベートもSlackを使い始めました。botとか情報収集とかでSlack APIを結構触ったので、途中で得た知見を共有したいと思います。

# Slackアプリで困ったこと
### Slackアプリのハイライトの仕組み
- ハイライトワードの設定はコンマで切り離します。（知らずにスペースや別のシンボルを使う人はたまにいる）
- ハイライトワードは大文字と小文字を区別しないです。
- ハイライトしたいワードは基本分離符で分離してください。
- （漢字・ひらかな・カタカナ）で挟む英語は分離符で分離しなくても大丈夫。たとえ`「この件は@hogeさんにお願いします」`はちゃんとhogeさんのときに届きます。
    - 句点、はてなの後ろにうっかり直接`@hoge`でハイライトさせたい場合はたまにあると思うが、ちゃんと分離符で分離しないとダメです。たとえ`「この件どうしよう？@hoge」`はハイライトしないです。
    - botの発言はアプリ内で見るときはハイライトするけど、実際は通知を飛ばないです。（bot書くときの要注意点）
 
### Slackアプリのメンション機能は強いけど、ハイライトメッセージの拾いは若干足りない感じで自分ルールで通知飛ばしたいです。
- 向うのミスでメンションが届いてない場合も気づきたいです。（分離符を使ってなかったとか、約束してない単語を使ったとか）
- 誰かが酒やラーメンや気になる技術のことを話したらすぐ反応したいです。（弊社の先着お土産情報も早めに気づきたい）
- botで流してるalert情報や、タスク情報とか、大事なものが多いけど、人目で確認するのは反応遅いしそしてよく漏れるし、いちいち`@group`とか使ったら多くの人の手を止めるので、プログラムでうまく拾いたいです。

### 他にSlackアプリに不満なこと
- editedやdeletedの内容が気になります。
    - Slackの製作者の意図に反してるかもしれないです。
    - でも気になるものは気になります。
- チームやチャンネルが増えると、最新のメッセージを全部チェックするのはすごい手作業になっています。
    - まとめにどこかに流したいです。
    - 黒い画面で流して、コードを書きながら見たいです。

# Slackに関して書いたもの
### 様々なbot（遊び系やリマインド系とか）
- bot書くときの注意事項についてちょっと話します。
- 前にも話した通りで、botの発言は公式の`@group`や`@username`以外はアプリ内で見るときはハイライトしてるけど、実際は通知飛ばないです。どうしても通知を飛ばしたい場合は：
    - １、https://api.slack.com/methods/chat.postMessage の`as_user`を`true`にして、発言するのはbotじゃなくて本人になると、普通にハイライトします。
    - ２、公式の`@group`や`@username`を使って確実にハイライトさせます。
- 公式の`@group`や`@username`を使うときは`<@group>`と`<@U11223444>`を使います。
    - アプリで見るときリンクがついてる`@username`、裏のコードは`<@U11223344>`みたいな文字列です。
    - 一回ミスして、APIのドキュメントを読んだら分かることです。
    - チームメンバーのIDは https://api.slack.com/methods/users.list で分かります。
    - 便利に使えるように、ユーザーネームとIDの参照はローカルに保存して、毎日更新する仕組みになっています。
- ファイルのアップロードとsnippetはbotでできないです。本人でアップロードすることになります。

### 複数チームの全チャンネルのメッセージをまとめて流します。
- 実現についてはブログを書きました。
    - [黒い画面で三つのslackチームのメセッジーを同時に流れてみた](http://hiyoko91.hatenablog.jp/entry/20150615/1434367239)
- リアルタイムのメッセージをもらうAPI： https://api.slack.com/rtm
- リアルタイムでもらったもの（イベント）の解析： https://api.slack.com/events
    - リアルタイムのAPIは割と分かりやすくて、簡単に書けたけど、もらったイベントの解析は大変なことになりました。
    - 解析に関しては[SlackParser](https://github.com/hiyoko9191/SlackParser)を書きました。解析・表示できるように、必要なものだけパーサーします。基本自分用です。
- 最初はすべての黒い画面で流してみたが、結構見づらいです。流してきたものも思ったよりほとんど見てなかったので、結局アプリのほうで見ています。
- 次はチャンネルを整理して、業務と強く関わったチャンネルの内容だけ流すことになって、そして流してきたものを必ず全部確認します。
    - そこそこ使えます。

### 個人用slackで情報をまとめ
- 特定の内容に関する発言をまとめて個人用Slackに流します。
    - botはアイコンとネームが指定できるので、あらかじめユーザーのネームとアイコンのurlをローカルに保存したら、それを使ってもとの発言者を真似することはできます。本物と似すぎてたまに返事したくなります。
- 様々なところからラーメン情報やランチ会情報や勉強会情報などを拾って、個人用slackに流しています。
    - 情強感
    - おみやげ情報最高
- 天気、毎日のスケジュール、メール通知や自分用のツールとか、個人用Slackがだんだん充実してきました。


# まとめ
- Slack APIのドキュメントは充実してて分かりやすいです。
- botを書くのが楽しいです。
- 確実に自分の効率を高めるものを書くのも楽しいです。
- 明日はまた@rymizukiさんです。よろしくお願いします。
深夜の本番作業を安全に 半自動化エンジン「migrationTTL」

10年近く前に作ったやつなのですが、いまだ当時と同じ課題を抱えているシステムエンジニアが多いので、この記事を書きます。

以前に、DevLoveで発表した内容です(後述する手順読み上げ機能を、Windows7に対応させています)。

Slideshare
[![image](https://qiita-image-store.s3.amazonaws.com/0/8475/443db91c-717b-cab5-d999-05f43a12c2c3.png)](http://www.slideshare.net/kawasima/ss-4763619)

## システムエンジニアの本番作業

システムエンジニアの本番作業は、オンライン停止後の深夜帯しかできないという現場も多いかと思います。より作業ミスも発生しやすくなるってもんです。私も若い頃は、そういう現場にいて当時飛び交っていた格言をメモっていたようです。

<blockquote class="twitter-tweet" lang="ja"><p lang="ja" dir="ltr">昔のEvernoteを見返していたら「移行」という謎メモが出てきた…&#10;&#10;・準備の段階で勝負は決まっている。&#10;・「君はEnterキー押すのが早いな」&#10;・「パスワードってのは体で覚えるんだ」&#10;・慌ててCtrl+Cするんじゃない、落ち着いてrollbackだ。&#10;・「一回とめますか？」</p>&mdash; :SIer/kawasima (@kawasima) <a href="https://twitter.com/kawasima/status/672776569237200897">2015, 12月 4</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>

## 本番作業のこころえ

謎メモを読み解くと、以下のようなことが、本番作業およびスクリプトには求められます。

- 本番作業はリハーサルを入念におこなうべし。
- Enter押す前に、指差し確認をおこなうべし。
- 本番で流すスクリプトにパスワードを書かないこと。
- 期待する結果と違ったら、立ち止まって対策うつべし。

## migrationTTL

さて、これらの本番作業をサポートするツールです。

https://github.com/kawasima/migrationTTL/

もともと移行作業のために作ったので、migrationTTLという名前になっていますが、本番作業全般で使えます。
TeraTermマクロとして動作します。

### 使い方

本番作業前に、開発環境でリハーサルをおこない、手順のスクリプトを作ります。

```bash
# 景気づけにls
ls

# ホームに移動
# 複数行のコメントはまとめて表示されます
cd
cd work/devlove

# SQL*Plusもシームレスにいけます
sqlplus system

# *****と書いておくとパスワード入力ダイアログがでます
*****

# SQLを実行します
select * from tab;

# SQLを終了
exit
```

基本的には、シェルスクリプトと同じノリです。


あとは、TeraTermからmigrationTTLを実行し、手順をロードすると作業がスタートします。

実行前のコマンドの確認と、Enterを押す前の確認が順次おこなわれ、自動的にターミナルに打ち込まれます。

### メリット

- 検証済みの手順をクリックしていくだけで、本番での作業を安全かつ速やかに実行できる。
- パスワードがスクリプトに入らずセキュア
- 変なことが起こったら、途中で止めてリカバリできる。
- ログも自動的に取得される
- サーバをまたいで作業する場合も同じスクリプトでいける(TeraTermマクロなので)

## コマンドの読み上げ

目だけで手順を追うと、ミスに気づかないこともあります。そこでmigrationTTLでは、コメントを音声で読み上げる機能があります。

### SAPIのセットアップ

昔のWindowsでは、イルカや魔法使いを簡単に喋らせることができたのですが、最近は音声合成機能は別途インストールすれば使えるようになっています。Windows7では「Speech Platform Server Runtime」をSAPI経由で使うのが簡単なので、これを使います。

http://blog.mogya.com/2012/01/windows7text-to-speech.html

## デモ

これで、以下のような本番作業イメージになります。

↓Youtubeリンク
[![screencast](http://img.youtube.com/vi/65HLnGRjWfs/0.jpg)](https://www.youtube.com/watch?v=65HLnGRjWfs)

もう深夜作業でも大丈夫ですね！
CentOS7.xでのAnsibleのインストール

忘れそうなのでメモ。

# 環境

* CentOS7

# やり方

pip(Pythonのパッケージ管理ツール)のインストール

```bash
# curl https://bootstrap.pypa.io/get-pip.py | python
```
pythonビルド環境とsshのパスワード認証ライブラリのインストール

```bash
# yum install python-devel ssh-pass
```

Ansibleインストール

```bash
# pip install ansible
```
static変数へのアクセスが思ってたのと違ったのでメモ

php5.3以降では遅延静的束縛が使えるようになったので、getやsetのメソッドは親クラスで定義して、値をstatic変数に保持しておくということがやりたかった

```php
<?php

class A
{
	static $hoge;
	
	static function get()
	{
		echo static::$hoge;
	}
	
	static function set($value)
	{
		static::$hoge = $value;
	}
}

class B extends A
{
}

class C extends A
{
}

B::set('b');

C::set('c');

B::get(); // 'b'が返ってきて欲しいけど'c'が返ってくる
```

`self`じゃなくて`static`で呼べば勝手に子クラスで継承された`$hoge`に値が入ると思ってたけどそうじゃなかった

```php
// Aの定義は省略

class B extends A
{
	static $hoge;
}

class C extends A
{
	static $hoge;
}

B::set('b');

C::set('c');

B::get(); // 'b'が返ってくる
```

子クラスで`$hoge`を宣言してやれば解決した