OmniAICreator/Qiita-1.07M huggingface dataset:
[Zabbix]SSLサーバ証明書期限切れ○日前チェックをする


**これはQiita:Teamからの転載です。**

# 参考および同じようなことをされていたエントリ

* [ZabbixでSSL証明書の有効期限監視(１つのサーバーに複数のホストがあるとき) - Qiita](http://qiita.com/manabuishiirb/items/e958dab61bcde1d788c7 "ZabbixでSSL証明書の有効期限監視(１つのサーバーに複数のホストがあるとき) - Qiita")
* [ZabbixでSSL証明書の有効期限を監視する - Qiita](http://qiita.com/ma3ki/items/302205c0402c3746c9ff "ZabbixでSSL証明書の有効期限を監視する - Qiita")
* [Zabbix3.0でSSL証明書有効期限を監視する - Qiita](http://qiita.com/skouno/items/a98bc384b4734a6e20a7 "Zabbix3.0でSSL証明書有効期限を監視する - Qiita")

# 前提

* **サーバ証明書の有効期限が切れる○日前にZabbixからアラートがあがる** と嬉しい
* **いま○日前か** をZabbixが把握する必要はない
* **有効期限切れまで○日前を切ったことを知れる** のが重要

上記前提に基づいている

# Zabbix Userparameter で以下を設定

* ワンライナーで完結するようした

```bash:/etc/zabbix/zabbix_agentd.d/userparameter_sslcertificatecheck.conf
UserParameter=sslcert.notaftercheck[*],echo $$(( $$(date -d "$$(openssl s_client -connect $1:$2 -servername $1 < /dev/null 2> /dev/null |openssl x509 -text |grep 'Not After' | cut -d':' -f 2-)" +'%Y%m%d') > $$(date -d "$3 days" +'%Y%m%d') ))
```

||||
|:--|:--|:--|
|sslcert.notaftercheck[*]|[]の中にカンマ区切りで引数設定可能|
|$1|[]内引数の1番目|確認したい証明書が設置されているFQDN[^1]|
|$2|[]内引数の2番目|443[^2]|
|$3|[]内引数の3番目|60 とか 30 とか[^3]|
|$$|ワンライナー実行時に $ になる|$$(command) -> $(command)|

[^1]: ```*.example.com``` の証明書確認なら実際のサーバで使用している ```subdomain.example.com``` を指定する、のような使い分け
[^2]: HTTPS通信が可能ならば ```443``` の限りではない
[^3]: 期限切れまで残り ```60 or 30 日未満``` になったらzabbixは echo 出力から ```0``` を受け取りアラートメール発報させることを想定


```bash:やってることはこういうことです
#!/bin/bash

FQDN=subdomain.example.com
HTTPSPORT=443
DAY=30        # この場合30日前check

DOLLAR_1=${FQDN}
DOLLAR_2=${HTTPSPORT}
DOLLAR_3=${DAY}

NOTAFTER_YYYYMMDD=$(date -d "$(openssl s_client -connect ${DOLLAR_1}:${DOLLAR_2} -servername ${DOLLAR_1} < /dev/null 2> /dev/null |
                               openssl x509 -text                                                                                 |
                               grep 'Not After'                                                                                   |
                               cut -d':' -f 2-)"   +'%Y%m%d') 
N_DAYS_LATER_YYYYMMDD=$(date -d "${DOLLAR_3} days" +'%Y%m%d') # この場合実行日から30日後の日付
echo  ${NOTAFTER_YYYYMMDD} \> ${N_DAYS_LATER_YYYYMMDD}
echo $(( ${NOTAFTER_YYYYMMDD} > ${N_DAYS_LATER_YYYYMMDD} ))   # 偽なら0が返る前提なのでZabbixのトリガーは0を待ち構える形
```

```:output
20160908 > 20160703
1
```
Angular2  + RxJS + Redux

Angular2 + Redux で[ngrx/store](https://github.com/ngrx/store)に注目していましたが、その周辺も充実してきています。
ng-confでも紹介されています。⇒[こちら](https://www.youtube.com/watch?v=mhA7zZ23Odw&index=32)
Angular2 + RxJS は本当にパワフルです。今後が楽しみです。

# ngrx
https://github.com/ngrx

RxJSを使った、Angular2の拡張
すべて使った[サンプル example-app ](https://github.com/ngrx/example-app)はなかなかキレイです。

##  store

RxJSを使ったRedux風の実装
async pipeがあるので相性がいいですね。
最近v2になりmiddleware回りが変わりました。
ドキュメントやサンプルが充実しています。

 [Comprehensive Introduction to @ngrx/store](https://gist.github.com/btroncone/a6e4347326749f938510)　
仕組みから簡単なサンプルまで解説してくれています。

 https://github.com/btroncone/ngrx-examples
Rudux公式のサンプルを作ってくれていたり、関連ドキュメントをまとめてくれています。

## effects 
redux-sagaみたいに副作用をわかりやすくかけるようにしてくれます。
もともとは[store-saga](https://github.com/CodeSequence/store-saga)でしたがstoreがv2になった際により書きやすくなり、リネームされました。

## router

Angular2のrouterとは別のrouter
非同期読み込みやGuardsが便利そうです。まだβ

## devtools、router-store、db

storeを使う際の開発を便利にしてくれます
[logger](https://github.com/btroncone/ngrx-store-logger)ももちろんあります。
めざせpythonライブラリマスター （25）orderedset

#【ライブラリ説明】
　集合を簡単に扱える

#【準備】
　python2.7ではインストール時にエラーが出たため、python3.5を使用

#【プログラム】
```py:orderedset.py
# -*- coding: utf-8 -*-

from orderedset import OrderedSet

oset = OrderedSet([1, 2, 3])
oset2 = OrderedSet([3, 2, 1])
oset3 = OrderedSet([1, 2, 3, 4])

print (oset == oset2)
# False
print (oset <= oset2)
# True

# 部分集合かどうか
print (oset.isorderedsubset(oset2))
# False
print (oset.isorderedsubset(oset3))
# True

oset = OrderedSet([1, 2, 3])
lst = [1, 2, 3]
tes = {1, 2, 3, 4}

print (oset == lst)
# True
print (oset <= tes)
# True

print (oset | lst)
# OrderedSet([1, 2, 3])
print (oset | tes)
# OrderedSet([1, 2, 3, 4])
```

#【参考サイト】
　[document](http://orderedset.readthedocs.io/en/latest/index.html)
vagrant provisionした時にundefined method `lazy' for Chef::Resource::Fileと言われた時の対処


# エラー内容

「vagrant reload --provision」を実行すると下記エラーが発生した。


```
NoMethodError
-------------
undefined method `lazy' for Chef::Resource::File 
```

これは、プロビジョン対象のイメージ内に入っているchefのバージョンが古いのでエラーが出てる。

#対処
vagrant-omnibusをインストールすることでchefのバージョンアップをして対処できる。

vagrant-omnibusをインストールするには下記コマンドを実行する。
 
```
$ vagrant plugin install vagrant-omnibus
```

その後、Vagrantfileに下記行を追加する。
:latestを指定した場合は最新のバージョンがインストールされる。
特定のバージョンをインストールしたい場合は、バージョン番号を入力する。

```sh:Vagrantfile
config.omnibus.chef_version = :latest
```

これで「vagrant up」すると起動時にchefのバージョンアップを実施してくれるようになる。
めざせpythonライブラリマスター （24）combi

#【ライブラリ説明】
　順列、組み合わせを表示

#【プログラム】
```py:combi.py
# -*- coding: utf-8 -*-

from combi import PermSpace, CombSpace

# 順列
perm_space = PermSpace('meow')
print len(perm_space)
# 24

for i in xrange(len(perm_space)):
    print perm_space[i]
'''
<Perm: ('m', 'e', 'o', 'w')>
<Perm: ('m', 'e', 'w', 'o')>
<Perm: ('m', 'o', 'e', 'w')>
<Perm: ('m', 'o', 'w', 'e')>
<Perm: ('m', 'w', 'e', 'o')>
<Perm: ('m', 'w', 'o', 'e')>
<Perm: ('e', 'm', 'o', 'w')>
<Perm: ('e', 'm', 'w', 'o')>
<Perm: ('e', 'o', 'm', 'w')>
<Perm: ('e', 'o', 'w', 'm')>
<Perm: ('e', 'w', 'm', 'o')>
<Perm: ('e', 'w', 'o', 'm')>
<Perm: ('o', 'm', 'e', 'w')>
<Perm: ('o', 'm', 'w', 'e')>
<Perm: ('o', 'e', 'm', 'w')>
<Perm: ('o', 'e', 'w', 'm')>
<Perm: ('o', 'w', 'm', 'e')>
<Perm: ('o', 'w', 'e', 'm')>
<Perm: ('w', 'm', 'e', 'o')>
<Perm: ('w', 'm', 'o', 'e')>
<Perm: ('w', 'e', 'm', 'o')>
<Perm: ('w', 'e', 'o', 'm')>
<Perm: ('w', 'o', 'm', 'e')>
<Perm: ('w', 'o', 'e', 'm')>
'''

print perm_space.index('mowe')
# 3



# ３つから２つ選ぶ組み合わせ
comb_space = CombSpace(('vanilla', 'chocolate', 'strawberry'), 2)

print len(comb_space)
# 3

for i in xrange(len(comb_space)):
    print comb_space[i]
'''
<Comb, n_elements=2: ('vanilla', 'chocolate')>
<Comb, n_elements=2: ('vanilla', 'strawberry')>
<Comb, n_elements=2: ('chocolate', 'strawberry')>
'''
```

#【参考サイト】
　[pypi](https://pypi.python.org/pypi/combi/1.1.1)
　[github](https://github.com/cool-RR/combi)
VHDL > Link > A'high(N) > オブジェクトAのインデックス範囲の上限値

http://qiita.com/7of9/items/18510bb32cd5e1ea673c
にて出てきた

`res_int(res_int'high - 1 DOWNTO 0)`
という書き方。

以下に詳しい
http://homepage3.nifty.com/hdl_design/vhdl2.htm

> A'high(N) オブジェクトAのインデックス範囲の上限値
Zybo > Chronicles blog 28 > DMAとは / DMAモード > Burst Mode / Cycle Stealing / Transparent Mode

MicroZed Chronicles リスト http://adiuvoengineering.com/?page_id=285
@ Adam Taylor blog
https://forums.xilinx.com/t5/Xcell-Daily-Blog/The-Zynq-PS-PL-Part-Eight-Zynq-DMA-Adam-Taylor-s-MicroZed/ba-p/441092

### DMAとは

> DMA transfers data into or out of memory without processor intervention once the processor has set up the transfer.

### three modes

> Typically DMA controllers operate in one of three modes:

> - Burst Mode - Transfers an entire data block in one continuous operation. In many applications, burst-mode transfers deny bus access to the processor while the DMA is taking place. This could be perfectly fine or it could be a very bad thing depending on the system.
- Cycle Stealing – Interleaves individual DMA byte or word transfers with processor accesses to the system bus. This mode prevents processor starvation.
- Transparent mode – The most efficient mode. Data is only transferred when the processor is performing tasks that don’t require access to the system bus.
Zybo > Chronicles blog 27 > 140 clocks on PL / 25 clocks on PS > DMA使用の検討

MicroZed Chronicles リスト http://adiuvoengineering.com/?page_id=285
@ Adam Taylor blog
https://forums.xilinx.com/t5/Xcell-Daily-Blog/The-Zynq-PS-PL-Part-Seven-Adam-Taylor-s-MicroZed-Chronicles-Part/ba-p/438888

計算を実装したところ

> Although the numeric result is the same, the big difference is the time it takes to perform the calculations. Although the actual computation requires only 5 clocks by the peripheral design, generating the result consumes 140 clocks or 420ns versus 25 CPU clocks using the ARM Cortex-A9 processor on the PS side of the Zynq SoC.

PLでは140CPU clocksかかり、PSでは25CPU clocksだという結果。PLを使っているのに遅いのは何故か。

AXI busのオーバヘッドということのようだ。

> If we were to take a more reasonable approach, we would send a block of inputs requiring calculation to our peripheral using DMA as I explained in part 1 of this blog series on PL/PL interfacing. This example establishes why DMA is so important, which now permits me to explore how we use this experimental result in the next blog.
 
DMAを使う話につながる。
Zybo > Chronicles blog 27 > -0.0088x2 + 1.7673x + 131.29 のVHDL実装 / XSDKでの使用

MicroZed Chronicles リスト http://adiuvoengineering.com/?page_id=285
@ Adam Taylor blog
https://forums.xilinx.com/t5/Xcell-Daily-Blog/The-Zynq-PS-PL-Part-Seven-Adam-Taylor-s-MicroZed-Chronicles-Part/ba-p/438888

http://qiita.com/7of9/items/7d4394b9a05ed7b97e6f
の計算の実装


> Having calculated the above we are ready to implement the design within the Vivado peripheral that we created in previous installments. The first implementation step is to open up the block diagram view within Vivado, <font color=red>right click on the peripheral</font>, and select <font color=red>“Edit in IP Packager”</font>. Once the IP Packager opens within the top-level file, we can easily implement a simple process that performs the calculation over a number of clock cycles. (<font color=red>Five clocks in this example</font>, although you could optimize this further.)


```.vhd
PROCESS(s00_axi_aclk)
BEGIN
    IF rising_edge(s00_axi_aclk) THEN
      squared <= signed( '0' & reg1(15 DOWNTO 0)) * signed('0' & reg1(15 DOWNTO 0));
      cx2 <= (squared * c);
      bx <= (signed('0' & reg1(15 DOWNTO 0)) * b);
      res_int <= a + cx2(48 DOWNTO 32) + ("000" & bx(32 DOWNTO 19));
      result(15 DOWNTO 0) <= std_logic_vector(res_int(res_int'high - 1 DOWNTO 0));
    END IF;
END PROCESS;
```

`res_int'high`という書き方は未消化。


XSDKでは以下のようにiをレジスタに書込んで、その結果を読込みしている。

```c
for(i=0; i<2560; i = i+25 ){
      XScuTimer_LoadTimer(&Timer, TIMER_LOAD_VALUE);
      timer_start = XScuTimer_GetCounterValue(&Timer);
      XScuTimer_Start(&Timer);
      ADAMS_PERIHPERAL_mWriteReg(Adam_Low, 4, i);
      result = ADAMS_PERIHPERAL_mReadReg(Adam_Low, 12);
      XScuTimer_Stop(&Timer);
      timer_value = XScuTimer_GetCounterValue(&Timer);
      printf("%d,%lu,%lu,%lu, \n\r",i,result,timer_start, timer_value);
}
```
横向き画面キーボードが表示されない問題

DialogFragmentで初期表示時にEditTextにフォーカスするが、キーボードが表示されない問題について、色々調べまして、解決方法をメモします。

下記は、Android.5.0で検証済みです。

#プログラムでキーボードを強制的に表示
縦向きの場合、キーボードがうまく表示されますが、横向きの場合、EditTextをタッチしないと、キーボードが表示してくれません。

```
    public static void show(final Context context, final EditText edit, int delayTime) {
        final Runnable showKeyboardDelay = new Runnable() {
            @Override
            public void run() {
                if (context != null) {
                    InputMethodManager imm = (InputMethodManager)context.getSystemService(Context.INPUT_METHOD_SERVICE);
                    imm.showSoftInput(edit, InputMethodManager.SHOW_IMPLICIT);
                }
            }
        };
        new Handler().postDelayed(showKeyboardDelay, delayTime);
    }
```

#横向きの場合も強制表示
showSoftInputメソッドの第2パラメータをInputMethodManager.SHOW_FORCEDに変更したら、やっと表示されるようになりました。

```
    public static void show(final Context context, final EditText edit, int delayTime) {
        final Runnable showKeyboardDelay = new Runnable() {
            @Override
            public void run() {
                if (context != null) {
                    InputMethodManager imm = (InputMethodManager)context.getSystemService(Context.INPUT_METHOD_SERVICE);
                    imm.showSoftInput(edit, InputMethodManager.SHOW_FORCED);
                }
            }
        };
        new Handler().postDelayed(showKeyboardDelay, delayTime);
    }
```

#参考記事
[Show soft keyboard automatically when EditText receives focus](https://turbomanage.wordpress.com/2012/05/02/show-soft-keyboard-automatically-when-edittext-receives-focus/)
[Show soft keyboard when the device is landscape mode](http://stackoverflow.com/questions/4761741/show-soft-keyboard-when-the-device-is-landscape-mode)
技術英語 > But to [talk the talk] on the environment is one thing. / [walk the walk], as well

@ LOE > May 16, 2003
http://loe.org/shows/shows.html?programID=03-P13-00020
> But to <font color=red>talk the talk</font> on the environment is one thing. 

> and all political candidates <font color=red>walk the walk</font>, as well.


http://eow.alc.co.jp/search?q=talk+the+talk
> talk the talk
きちんと話す
 
http://eow.alc.co.jp/search?q=walk+the+walk
> walk the walk
物事をきちんと実行する

talk the talkの訳からwalk the walkを類推したが、違った。
めざせpythonライブラリマスター （23）memory_utils

#【ライブラリ説明】
　メモリ操作

#【プログラム】
```py:memory_utils.py
# -*- coding: utf-8 -*-

import memory_utils as memo

x = []
for i in xrange(100000):
    x.append(i)
    # メモリの上限を設定
    memo.set_memory_limit(12800000)
    # 上限を超えたら例外を発生させる
    memo.check_memory()
    # メモリプリント
    memo.print_memory()
```

#【結果】
<img width="459" alt="memory.png" src="https://qiita-image-store.s3.amazonaws.com/0/121997/50996d9c-0e7f-7995-f553-c4b93743e7b3.png">

#【参考サイト】
　[github](https://github.com/jtushman/memory_utils)
Travis で PhantomJS 2.1.1 を使う

# 更新（2018年2月14日）
コメントで教えて頂いた通り、[2017年12月12日のアップデート](https://docs.travis-ci.com/user/build-environment-updates/2017-12-12/#Changed)で、PhantomJS 2.1.1 がデフォルトになったようです。

# 概要
[Travis CI](https://travis-ci.org/) で [PhantomJS](http://phantomjs.org/) と [Selenium](http://www.seleniumhq.org/) を使ったテストを行っているのだが，PhantomJS のバージョンが古くて上手くいかなかった．PhantomJS 2.1.1 をインストールする方法を調べたのでまとめておく．

# 方法
Travis CI には PhantomJS 1.9.8 が予め用意されているので，このバージョンで問題ない場合は何もする必要は無い．バージョン 2.1.1 が必要な場合， `.travis.yml` に下記の項目を追加する．

```yaml:.travis.yml
before_script:
  - mkdir travis-phantomjs
  - wget https://assets.membergetmember.co/software/phantomjs-2.1.1-linux-x86_64.tar.bz2 -O $PWD/travis-phantomjs/phantomjs-2.1.1-linux-x86_64.tar.bz2
  - tar -xvf $PWD/travis-phantomjs/phantomjs-2.1.1-linux-x86_64.tar.bz2 -C $PWD/travis-phantomjs
  - export PATH=$PWD/travis-phantomjs/phantomjs-2.1.1-linux-x86_64/bin:$PATH
```

この https://assets.membergetmember.co/software/phantomjs-2.1.1-linux-x86_64.tar.bz2 が使えない場合は，代わりに https://bitbucket.org/ariya/phantomjs/downloads/phantomjs-2.1.1-linux-x86_64.tar.bz2 も使えるらしい．Bitbucket の方はブロックされたらしいと聞いたので，assets.membergetmember.co の方を使った．こちらは今のところ問題無い模様．

# 参考
https://github.com/travis-ci/travis-ci/issues/3225 （というか，このスレから解決方法を抜き出しただけ．）
function.nameを変更する方法

## function.nameについて

全てのfunctionはFunction.prototype.nameというプロパティを持ちます。
funciton.nameとはその名の通りFunctionの名前を取得することができます。

実行環境はnode v6.2.0です。

```javascript
var func1 = function hoge() {};
console.log(func1); // [Function: hoge]
console.log(func1.name); // "hoge"

var func2 = function() {};
console.log(func2); // [Function]
console.log(func2.name); // ""

function fuga() {}
console.log(fuga); // [Function: fuga]
console.log(fuga.name); // "fuga"
```

大きいプロジェクトになればなるほど、このfunctionはなんだっけかな。。ということが稀に発生します。名前をつけておくととても効率的にデバッグが行えるかと思います。

最近のv8のバージョンではbindした際には"bound xxx"というnameを保持するようになりましたが、以前のバージョンや実行環境によっては失われてしまうケースもあります。

```javascript
var func = function hoge() {};
console.log(func.bind(null)); // [Function: bound hoge]
console.log(func.bind(null)); // [Function] (node v0.12.12)
```

またfunction.nameは書き込み不可なプロパティです。

```javascript
var func = function hoge() {};
func.name = 'fuga';
console.log(func); // [Function: hoge]
console.log(func.name); // "hoge"
```

new Functionではnameを変更することができません。

```javascript
var func = new Function('val', '{ return val; }');
console.log(func); // [Function: anonymous]
console.log(func); // [Function] (node v0.12.12)
```

## Funciton.nameを変更する

実際には新しい名前付きの新しいFunctionを生成します。
新しい関数を生成しますので使用する際には十分気をつけてください。

```javascript
// Function
var name = 'hoge';
var str = '{ return function ' + name + '(val) { return val;}; }'
var func = new Function(str)();
console.log(func); // [Function: hoge]
```

既存の関数の名前を変更したい場合は、

```javascript
function rename(func, name) {
  var str = func.toString().replace(/^function(.*?)\(/, 'return function ' + name + '(');
  return new Function(str)();
}

var func1 = function hoge(val) { return val; };
var func2 = rename(func1, 'fuga');
console.log(func1); // [Function: hoge]
console.log(func2); // [Function: fuga]
```

## 新しい名前付きの関数を作成する

このようにすることで新しい名前付きの関数を作成できます。

```javascript
function makeFunc(name, args, fstr) {
  var arr = [name, args, fstr];
  var str = 'return function %s(%s) %s;';
  str = str.replace(/%s/g, function() {
    return arr.shift();
  });
  return new Function(str)();
}

var name = 'test';
var args = ['a', 'b'];
var fstr = '{ return a + b; }';
var func = makeFunc(name, args, fstr);
console.log(func(1, 2)); // 3
```

もう少しだけ汎用的にしたものをGitHubにあげてありますので、興味がある方は見てみてください。
[https://github.com/suguru03/make-function](https://github.com/suguru03/make-function#make-function)

## ソース
- [Function.name - JavaScript | MDN](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function/name)
- [Dynamic function names in JavaScript](http://marcosc.com/2012/03/dynamic-function-names-in-javascript)
python3 sqlite3 connect alway mistake

![2397.tmp.png](https://qiita-image-store.s3.amazonaws.com/0/127656/de4db0f4-8be9-5db6-bf77-2df658a5fcae.png)




![31CD.tmp.png](https://qiita-image-store.s3.amazonaws.com/0/127656/cff2780b-7516-b02d-a7f7-d4fa5c30824a.png)
Unityの2Dモードを最速で3Dモードに変える方法(逆も可能)

Unityで新規プロジェクトを**3Dモード**で作成したのに、なぜかたまに2Dモードで開かれてしまうバグ(?)にみなさん出会ったことはないでしょうか。

そんな時に、すぐに3Dモードに変える方法を伝授します。

例えば、このように間違えて2Dモードにしてしまった。もしくはバグでなぜか2Dモードになってしまったとします。

![image](https://qiita-image-store.s3.amazonaws.com/0/96970/63e3b450-0e60-6441-760b-e04c69e7bf5b.png)

3Dモードと比較したときの、2Dモードの特徴としては

+ シーンビューが2Dになってる(z軸方向が反映されなくなる)
+ Directional Lightがない。
+ Main CameraのProjectionがOrthographicモードになっている。

となっています。

これをいちいち変えるのは面倒ですよね。
今回はこれらを一気に変える方法を伝えます。

手順としては

+ [Edit] > [Project Settings] > [Editor]をクリック
+ [Default Behavior Mode]を2Dから3Dにする
+ 新しくシーンを作成する

となります。

# [Edit] > [Project Settings] > [Editor] をクリック

![image](https://qiita-image-store.s3.amazonaws.com/0/96970/8496ed85-3af0-e7a2-95b0-0737e3da8b73.png)

# [Default Behavior Mode]を2Dから3Dにする

![image](https://qiita-image-store.s3.amazonaws.com/0/96970/ce5d20e3-7035-4a52-c565-acc027925fdd.png)

# 新しくシーンを作成する

Macであれば[Command]+[N]を押すと...?
![image](https://qiita-image-store.s3.amazonaws.com/0/96970/11a3eff6-0568-190f-78ed-73e85bf1f455.png)

このように3Dモードになりました！
herokuでPHPを動かしてみた

# アカウントを作成
https://www.heroku.com/
![heroku_signup.png](https://qiita-image-store.s3.amazonaws.com/0/46776/afa225f5-a7a6-a7c5-c4ad-307a1aa7bf54.png)

# クライアントに Toolbelt をインストール
https://toolbelt.heroku.com/

インストール後、バージョンを確認して動けばOK

```
>heroku version
heroku/toolbelt/3.43.3 (i386-mingw32) ruby/2.1.7
heroku-cli/5.2.17-5db0bff (windows-386) go1.6.2
You have no installed plugins.
```

ついでにSSH鍵を登録する

```
>heroku login
Enter your Heroku credentials.
Email: hoge@example.com
Password (typing will be hidden):
Logged in as  hoge@example.com
```

ローカルにSSH鍵がない場合はここで作成するっぽい

# アプリを作成する

適当なディレクトリを作って、移動

```
> mkdir myheroku
> cd myheroku
```

ファイルを作っておく

- composer.json
(PHPのバージョン指定とかをするjsonだけど、とりあえずは空でOK)
- index.php

```php:index.php
<?php
echo "Hello Heroku World!";
?>
```

# gitに登録

HerokuではGitを使ってデプロイするので、さっき作ったアプリをGitに登録する

```
> git init
> git add .
> git commit -m "Add Heroku SampleApp"
```

# Herokuにアプリを作成

```
> heroku create
```
# アプリのデプロイ

```
> git push heroku master
```

# アプリをブラウザで起動

```
> heroku open
```

ブラウザが起動してHelloWorldが表示されればOK
簡単！
Triggered Segueを設定した場合のNSMenuItemの有効無効の切り替えは素直にできない


今回は[LGTM.app](https://itunes.apple.com/jp/app/lgtm/id1035132445?l=ja&mt=12
) の開発中に得たちょっとした知見の共有になります。

StoryboardというかnibからNSMenuItemのTriggered Actionを設定すると、対応するキーボードショートカット(keyEquivalent) が簡単に設定できてオススメです。

![Mac app Storyboard](https://qiita-image-store.s3.amazonaws.com/0/35008/2cf4c30a-5b81-05a1-0d92-7f1f9e0c785f.png "ss.png")


今回Storyboard上でNSMenuItemのTriggered Actionを直接Segueにつなげてみたのですが、Windowが何枚でも開けてしまうという状態になりました。設定画面なので、2枚以上開けないようにしたいところです。
![ss1.png](https://qiita-image-store.s3.amazonaws.com/0/35008/87961093-ed14-b688-9675-e33d2360dd34.png "ss1.png")


こういうとき、一般的にはNSMenuValidationのvalidateMenuItem(_:) をNSMenuItemのtargetとなるクラスに実装してメニューの有効無効を切り替えると思います。
しかしSegueをActionにした場合、NSMenuItemのtargetはStoryboardShowSegueTemplate というクラスのインスタンスになります。StoryboardShowSegueTemplateクラスは公開されていないため、NSMenuValidationを実装することができません。もしやと思いNSStoryboardSegueをサブクラスしてみましたが、ダメでした。というわけで、今回のケースではTriggered Segueは使わないというのが正解なようでした。

Sent ActionをIBActionに紐付け、IBActionを置いたクラスにNSMenuValidationを実装したところ、validateMenuItem(_:)が呼ばれるようになりました。あとはプログラムからNSWindowControllerをStoryboardIDで初期化して表示するようにすればいいでしょう。
logrotateした際にS3にアップロードする

Linuxの各種ログはlogrotateにより設定期間を過ぎるとパージされてしまいますが、証跡管理上、長期間保管したい要件はよくあるものと思います。
そんな要件には容量を気にせず保存できるオブジェクトストレージの活用が効率的かと思います。
そこでlogrotateによりローテーションされる際にS3にアップロードする方法をご紹介します。

<!-- more -->
動作確認済み環境：CentOS6,CentOS7
(※logrotateでのファイル名付与規則がdateext [-YYYYMMDD形式]であること）

##手順
1. AWS IAMにてアクセスキーを発行
1. awscliのインストール
1. S3バケットの作成
1. シェルスクリプトの設置
1. logrotate設定への埋め込み

IAMでのアクセスキー発行、awscliのインストール方法は他の記事を参照してください。
以下シェルスクリプトの記載例とlogrotate設定への記載方法を記します。

※注意
なお、通常はawscliインストール後に **`# aws configure`** としてアクセスキー等の初期設定を行いますが、cronからawscliを呼び出す場合には設定が反映されず、シェルスクリプト内にも記述する必要があります。

##シェルスクリプト記載例
以下のようなスクリプトを作成します。
logrotateにてsharedscriptsが設定されている場合は対象ログが纏めて引数として渡されるため、1つ1つに分解する必要があります。
なお、アクセスキーが含まれるため、rootオーナーでパーミッションは600とすることを忘れずに。

```bash
#!/bin/sh
##   s3upload.sh tool $@
##

# initial parameter
export AWS_CONFIG_FILE="/root/.aws/config"
export AWS_ACCESS_KEY_ID="xxxxxxxxxxxxxxxxx"
export AWS_SECRET_ACCESS_KEY="xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
LOG_FILE="/var/log/backup/logbackup.log"
BUCKET_NAME="s3://(バケット名)"

TOOL=$1
LOGS=${@:2}
YMDDATE=`date +%Y%m%d`
YEAR=`date +%Y`
DEST=$BUCKET_NAME/$YEAR/$YMDDATE/$TOOL
EXT=`echo "-"$YMDDATE`

# ログファイル準備
# フォルダが無い場合は作成
LOG_PATH=${LOG_FILE%/*}
if [ ! -d $LOG_PATH ]; then
     mkdir -p $LOG_PATH
fi
if [ ! -e $LOG_FILE ]; then
     touch $LOG_FILE
fi

echo "$0 START `date "+%Y/%m/%d %H:%M:%S"`">>$LOG_FILE

# 引数が無い場合は異常終了
if [ $# -eq 0 ]; then
    echo "引数が指定されていません" >> $LOG_FILE
    exit 1
else
    # 設定されている全てのログファイルを取得する
    for P in $LOGS; do
        for V in $P; do
            aws s3 cp $V$EXT $DEST/ >> $LOG_FILE 2>&1
        done
    done
fi
echo "$0 END `date "+%Y/%m/%d %H:%M:%S"`">>$LOG_FILE
echo >>$LOG_FILE
exit 0
```

以上の設定にて、**s3://(バケット名)/YYYY/YYYYMMDD/ツール名/ファイル名**
以下にローテーション直前のログが保存される。

##logrotateへの設定埋め込み
/etc/logrotate.d/以下にある各種設定ファイル内の、postrotateセッションにて呼び出すようにする。
以下は/etc/logrotate.d/syslogに埋め込む例となります。

    /var/log/cron
    /var/log/maillog
    /var/log/messages
    /var/log/secure
    /var/log/spooler
    {
        sharedscripts
        postrotate
            /bin/kill -HUP `cat /var/run/syslogd.pid 2> /dev/null` 2> /dev/null || true
            sh /usr/local/bin/s3upload.sh syslog $*
        endscript
    }

※注意
postrotateセッション中でプロセスリスタートを実行している場合は、必ずその後に記載する必要があります。
olddir設定とは併用できません。
compress設定とは併用可能です。
fzfをインストールする手順


選択的インターフェイスやインタラクティブフィルタなどと呼ばれるツールのひとつであるfzfについて。
もうひとつ有名なものであるpecoについては[他の記事](http://qiita.com/tdrk/items/264dddc86c031ee88930)を参照のこと。


githubのリポジトリをクローンしてきて、そこに用意されているインストールスクリプトを実行する。

``` bash
$ git clone https://github.com/junegunn/fzf.git ~/.fzf
Cloning into '/home/todoroki/.fzf'...
remote: Counting objects: 4463, done.
remote: Compressing objects: 100% (27/27), done.
remote: Total 4463 (delta 10), reused 0 (delta 0), pack-reused 4432
Receiving objects: 100% (4463/4463), 1.43 MiB | 819.00 KiB/s, done.
Resolving deltas: 100% (2735/2735), done.
Checking connectivity... done.

$ ~/.fzf/install
No prebuilt binary for Linux armv7l ...
Building binary (go get -u github.com/junegunn/fzf/src/fzf) ... OK
Do you want to enable fuzzy auto-completion? ([y]/n) y
Do you want to enable key bindings? ([y]/n) y

Generate ~/.fzf.bash ... OK
Generate ~/.fzf.zsh ... OK

Do you want to update your shell configuration files? ([y]/n) n

Update /home/todoroki/.bashrc:
  - [ -f ~/.fzf.bash ] && source ~/.fzf.bash
    ~ Skipped

Update /home/todoroki/.zshrc:
  - [ -f ~/.fzf.zsh ] && source ~/.fzf.zsh
    ~ Skipped

For more information, see: https://github.com/junegunn/fzf
```

インストールスクリプト実行中、zshrcを書き換えられたくなかったので途中で `no` を選択。
非同期のためのGCD処理を簡略化する

役に立つかどうかよくわからないTipsシリーズ

とある重い処理を行う時
メインスレッドとは別のスレッドでやりたいときは多いですね

そんなときに使うベタな手法がGCD(Grand Central Dispatch)なわけですが
そのまま書くとこんな感じになるかなと思います

```swift
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0)) {
    // 何か重たい処理
    dispatch_async(dispatch_get_main_queue()) {
        // UIの処理
    }
}
```

この`dispatch_async()`に渡す引数は、小難しい話になるので
[GCDについて情報整理する](http://qiita.com/sushichop/items/3fd3b49b9d4f9a457177)
↑こちらの方の記事にお任せするとして

複雑なスレッド処理をしないかぎりは、
この書き方で大抵のものは成立します

しかし、書くことが長いし、
もしiOS初心者には初見で何やってるのかよくわからないかも…なので
まずはラッピング関数を用意してしまいましょう

```swift
/// メインスレッドで処理を行う
/// - parameter block: メインスレッドで行う処理
func onMainThread(block: ()->()) {
    dispatch_async(dispatch_get_main_queue(), block)
}

/// メインスレッド以外の新しいスレッドで処理を行う
/// - parameter block: 新しいスレッドで行う処理
func onNewThread(block: ()->()) {
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), block)
}
```

こうすると、先ほどの実装は

```swift
onNewThread {
    // 何か重たい処理
    onMainThread {
        // UIの処理
    }
}
```
いかがでしょう?
「あー、新しいスレッドで何かやって、メインスレッドで何かやってるんですねー」って
何をしているか分かりやすくなったと思います

で、
あともう少し工夫を

別スレッドに回す時って
> メインスレッドに居て
> 重い処理をやるために別スレッドに処理を書いて
> 終わったらメインスレッドに戻す

って流れになることが多いので
こういう関数を作ってみました

```swift
/// 非同期処理を行う
/// - parameter async: 非同期でやりたい処理(別スレッドで実行)
/// - parameter completed: 完了時に行う処理(メインスレッドで実行)
func async(process asynchronousProcess: ()->(), completed completionHandler: ()->()) {
    onNewThread {
        asynchronousProcess()
        onMainThread {
            completionHandler()
        }
    }
}
```
使うときは、このような実装になります

```swift
async(
    process: {
        // 何か重たい処理
    },
    completed: {
        // UIの処理
    }
)
```
好みかもしれませんが

UIViewでのアニメーションを書く時の
この書き方に近しいものになるかと思います

```swift
UIView.animateWithDuration(
    0.1, // 0.1秒間で
    animations: {
        // こんなアニメーションを行って
    },
    completion: { _ in
        // 終わったらこれをやるよ
    }
)
```
なので、すっきりして個人的に満足です


これらを使って、こういう関数も作成できます

```swift
/// 秒を指定して非同期でスリープを行う
/// - parameter seconds: スリープ秒数
/// - parameter completed: スリープ完了時に行う処理
func asyncSleep(seconds sec: UInt32, completed: ()->()) {
    async(process: { sleep(sec) }, completed: completed)
}

/// ミリ秒を指定して非同期でスリープを行う
/// - parameter milliseconds: スリープのミリ秒数
/// - parameter completed: スリープ完了時に行う処理
func asyncSleep(milliseconds msec: useconds_t, completed: ()->()) {
    async(process: { usleep(msec) }, completed: completed)
}

/// スリープ間隔を指定して非同期でスリープを行う
/// - parameter duration: スリープ間隔
/// - parameter completed: スリープ完了時に行う処理
func asyncSleep(duration: NSTimeInterval, completed: ()->()) {
    async(process: { usleep(useconds_t(duration * 1000000)) }, completed: completed)
}
```

使用例

```swift
showIndicator()     // インジケータを表示して
asyncSleep(0.8) {   // 0.8秒待ったら
    hideIndicator() // インジケータを隠す
}
```

普通にスリープ関数使うとできないことが、簡単にできるようになると思います
ざっくりWordPressカスタマイズ

WordPressをカスタマイズしてメディア制作をする時に、必要になった項目をざっくり整理。

## フィルター
* WordPressがデータをデータベースまたはブラウザ画面へ送信する前に、変更することが出来る
* コンタクトフォームの表示前に値を変えるとか出来る
* `add_filter`で追加、受ける側は`apply_filter`

## アクションフック
* 特定のアクションに関数をフックできる
* これを活用すると、投稿保存時・管理画面表示時等に特定の処理を実行したり出来る

## カスタム投稿
* 通常の投稿以外に自分で好きな投稿を追加できる。
* メンバー登録、店舗登録などをユーザーに登録してもらって、表示する的なことが出来る

## カスタムフィールド
* 投稿者が投稿、ページにタイトルや内容以外に追加できる情報のこと
* この任意の情報は「メタデータ」と呼ばれ`get_post_meta($post->ID)`等で取得できる

### Advanced Custom Fields
* カスタムフィールドは`function.php`を編集することで利用できるが、面倒
* このプラグインを利用すると非常に楽。投稿以外にもユーザープロフィールにカスタムフィールドを設定できたりする

## カスタムタクソノミー(カスタム分類)
* 初期のカテゴリとタグ以外に自分の好きなカテゴリやタグを追加出来る機能
* `post_type`で表示する投稿、ページを選ぶことが出来、サイドバーにメタボックスとして表示される。
* 活用例 ネイルカラー
http://memorandums.3ki3ki.com/wp-custom-taxonomy/
* カスタム分類で追加出来るのは、カテゴリとタグのみなので独自のメタボックスを追加したい時は`add_meta_box`でPHPで自前で実装すれば出来る

## Nonce
* WordPressのワンタイムトークンの仕組み。フォームの送信元の制御、二重送信を防ぐことができる
* `wp_nonce_field`というメソッドを使うと、セッションのトークン、時間帯、ユーザーID、アクション名から生成される(これにより、予期したフォームからのPOST以外は許可しないことが出来る)

## 固定ページ
* 固定ページは管理画面から作成できる
* デフォルトのテンプレートはpage.php。固定ページ毎に表示を変えたい時は以下を上につけるとテンプレートを選択できるようになる

```
/**
 * Template Name: contact
 */
```

* 管理画面で入力した固定ページの内容を出力するにはテンプレートに、
以下のように書く必要がある

```php
< ?php while(have_posts()): the_post(); ?>
< ?php the_content(); ?>
< ?php endwhile; ?>
```

* ただ、自分で柔軟にHTMLを書きたいのであれば、直接テンプレートにタグを書いてしまった方がいい

## ショートコード
* WordPress2.5から導入された短いコードである機能を使えるようにするもの
* 例えば投稿画面で以下のように記述すると、自動で画像のギャラリー集のHTMLが出力される

```
[gallery]
```

* php側でこのショートコードを実行するには`echo do_shortcode(ショートコード)`にする

## 開発環境でメール送信をテストする方法
* WordPressのメールはデフォルトはPHPのmail関数を利用している
* この関数はWordPressがインストールされているサーバーのsendmailを通してメールを送信する。Contact Form7も内部では同じ。
* WP Mail SMTPというプラグインを使えば外部のサーバーのSMTPサーバーを使ってメール送信が出来るように設定してくれる

以下記事どおり設定したら、ContactForm7からのメール送信も出来るようになる。
http://blitzgate.co.jp/blog/250/

## WordPressループ
* WordPress は、アクセスしたURLに応じて、必要なデータを自動的に取得してくれる。これを「WordPressループ」と呼ぶ
* WordPress が自動的に取得したデータは、グローバル変数`$wp_query`に格納される。
* WordPressループの表示条件を変更したい場合は`query_posts()`を使う。
* WordPressループとは別に、新しいループを生成する場合は`get_posts()`を使う
* グローバル変数の`$post`に現在の投稿情報が保存される。`get_posts`を使うと現在の投稿情報が新しいループに更新されるので、ループが終わったら`wp_reset_postdata`でリセットが必要

## new WP_QUERYとget_postsの違い
* 両方ともメインループとは別のカスタムループを生成する
* 単純に投稿を取得するだけであれば違いは無い
* 指定できるパラメータも同じ。get_postsは内部でWP_QUERYを利用している
* ただ、`get_posts`が記事に関する情報(`WP_POST`)しか持っていないことに対して`new WP_QUERY`の場合は`is_page`など、ページに関する情報を持っている。そのため、`get_posts`と比べ`WP_Query`ほうがより複雑な処理を行うことができる
TeXで作った履歴書に顔写真をいい感じの大きさで載せる

履歴書作るとなったらやっぱりTeXですよね。基本的には以下を参考に作ります。

履歴書 LaTeX クラスファイル
http://bm.hus.osaka-u.ac.jp/~yusuke/archive/rireki/

ここで公開されてるクラスファイルを使うと良い感じになりますが、写真は印刷後貼り付けるという形になります。でも証明写真だって安くないですから、画像を埋め込みたくなります。それで調べて出てきたのが次のページ。

texで履歴書（写真貼りたい場合）
http://d.hatena.ne.jp/asmblr/20090625/1245940534

ここではstyファイルを修正してますが、clsファイルも似たような感じで修正できます。ただ上記のリンクだと元のファイルを倍にして調整してます。証明写真は縦横の長さが決まってるわけですから大きさも指定したいです。そこで下記のようにclsファイルを修正します。texファイルでusepackage{graphicx}するのも忘れずに。なお顔写真はface.pdfとしてます。適当な大きさの写真だとひしゃげてしまうので、顔写真は事前にそれっぽい大きさにトリミングする必要もあります。

```tex:rireki.cls
% 中略
\Put(0,0){\Large\bfseries\kanjiskip=5mm\historyname}
\Put(100,2){\makebox(0,5)[rc]{\scriptsize\@date 現在}}
%\Put(105,31){\dashbox{0.5}(28,38)[c]{\scriptsize %
%  \shortstack[c]{写真を貼る位置\\縦 36 〜 40 mm\\横 24 〜 30 mm}}} %コメントアウトした2行は削除
\Put(105,31){\includegraphics[width=3cm,height=4cm]{face.pdf}} % この行を追加
\@tempcnta=\number\paperheight
% 中略
```

これで幅3cm,高さ4cmの顔写真が貼れます。
Object#tapを使ってみて

Rubyの`Object`クラスにある割にはそこまで注目されないメソッドの1つに、`#tap`があります。使ってみたところ、個人的にはメリットがあるなと思いました。

# 返り値にするオブジェクトを組み上げる

よく、

```rb
def some_method
  a = []
  a << hoge
  a.concat piyo(:fuga)
  a[0] = false
  a
end
```

のような、返り値オブジェクトを組み立てるようなメソッドを書く場面がありますが、ときおり最後の`a`を書き忘れてでたらめなオブジェクトを返してしまうことがあります（Ruby以外では明示的な`return`が必要なので、忘れることはふつう起きませんが）。ここに`Object#tap`を使うと、

```rb
def some_method
  [].tap do |a|
    a << hoge
    a.concat piyo(:fuga)
    a[0] = false
  end
end
```

のように、変数の生成部が1つのブロックとなります。これなら返り値を書き忘れるということになりませんし、どこでこの変数を変更しているかもはっきりします。

参考リンク：[Object#tapでローカル変数を減らす。](http://qiita.com/shunsugai@github/items/f010189b8993fe6dd81d)

# 定数の生成
文字列1つとかシンプルな配列なら手間なく生成できるのですが、時にはメソッドを呼んだり、ローカル変数を使ったりして巨大な配列やハッシュの定数を作る必要があるかもしれません。とはいえ、定数を破壊的に変更し続けるのは見栄えが悪いですし、定数定義時に使ったローカル変数が散らばってしまうのもすっきりしないものです。

そこで、`tap`を使えばスコープもローカルにできますし、直接定数を変更するということにもならずに済みます。

```rb
SOME_CONSTANT = {}.tap do |h|
  h.merge! a: 1, b: 3
  i = some_method(5)
  h[i] = 100
  h[i + 80] = 7
  h.freeze
end
```

# 注意点
性質上、`tap`内部ではオブジェクトを**破壊的変更**で変えていく必要があります（`Sring#<<`、`Hash#merge!`など）。ブロックパラメータに別なオブジェクトを代入しても、うまく動きません。
Elm Architecture イントロダクション（テキストフィールド編）

前回は、最小構成ではじめるElm Architectureというタイトルのポストを投稿しました。

[最小構成ではじめるElm Architecture](http://qiita.com/chuck0523/items/610cbc5039b7f7db1eee)

ここでは、button関数を使った、簡単なカウンターを生成しました。

Elm Architecureのイントロダクションには、他にも豊富な例があります。
今回はElmのテキストフィールドについて。

[Text Fields - An Introduction to Elm](http://guide.elm-lang.org/architecture/user_input/text_fields.html)


ファイル構成等は、前回の記事を参照してください。

# 知識
## input

テキストの入力にinput関数を使いました。inputはHtmlパッケージに属しています。

[Html.input - Elm packages](http://package.elm-lang.org/packages/elm-lang/html/1.0.0/Html#input)

input関数は、Attribute型のリストとHtml型のリストを要求します。

## onInput

updateのフックとして、onInput関数を使いました。Html.Eventsパッケージに属します。

[Html.Events.onInput - Elm packages](http://package.elm-lang.org/packages/elm-lang/html/1.0.0/Html-Events#onInput)

event.target.valueをStringとして取得します。今回は、inputに渡して使いました。


# コード

書いたコードがこちら。


```hs

import Html exposing (Html, Attribute, div, input, text)
import Html.App as App
import Html.Attributes exposing (..)
import Html.Events exposing (onInput)
import String

main =
  App.beginnerProgram { model = model, view = view, update = update }

-- Model

type alias Model =
  { content: String

  }

model : Model
model =
  { content = "" }

-- Update

type Msg
  = Change String

update : Msg -> Model -> Model

update msg model =　-- 今回、msgにはonInputからStringの入力値が渡される
  case msg of
    Change newContent ->
      { model | content = newContent }

-- View

view : Model -> Html Msg
view model =
  div []
     -- onInputは入力ごとにvalueをupdateのChangeアクションに渡す。
    [ input [ placeholder "Text to reverse", onInput Change] []
    , div [] [ text (String.reverse model.content) ]
    ]
```
CMU41 私的にチャットbotを導入ネタ登壇（後半）

# こちらのスライドのつづきです

[私的にチャットbotを導入してみてしばらく経ったのであれこれ話す（前半）](http://www.slideshare.net/seigotanaka/bot-63431838)


----
# さて後半はIFTTT+Slack連携をいろいろ紹介します

　
![image](https://qiita-image-store.s3.amazonaws.com/0/56170/82e3b300-cd23-0d95-dba0-77c576373629.png)

----

### 初Qiitaスライド利用

----

# Mobile+Slack

----

## モバイル系は色々できる

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/b535af1e-2ffd-603a-c050-10bed938e1b6.png)

----

# Feed+Slack

----

## 例：AmazonのKindle新刊ランキングを表示

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/19580c6c-768f-268c-700f-eef3413e957d.png)

----

# 事例いろいろ

----

## 知りたい生活系

----

### お天気+Slack

出かける前に今日の予報を通知をする　など

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/511350df-13bb-22a9-6243-b6ad3ce55cc1.png)

----

### カレンダー+Slack

今日の予定を通知など

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/cced74ab-88a4-3c4f-7368-22854fa5be48.png)

----

### リマインダー+Slack

特定の予定を通知

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/9575a876-1b77-b64a-860f-ab71c087e7f4.png)

----

## 業務で使えそう

----

### メール

特定のラベルで分類されたメールをSlackに通知

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/5a8b6c4f-7fb6-9f3a-fde2-72597f35768a.png)

----

### Drobbox+Slack

共同で使っているスペースでファイルが更新れたら通知

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/61cfa471-35d1-c267-75f6-2eb955a05287.png)

----

### GitHub+Slack

特定のリポジトリの更新を通知

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/1a80046e-2768-ee66-1803-684ae8d8cb5b.png)

----

### Trello+Slack

タスクの完了や作成、ユーザーアサインを通知

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/69e15ed8-4493-21e7-2263-f98aa0224371.png)

----

# MakerChannel+Slack

----

## MakerChannelとは

自分で作ったオリジナルの情報を外部から送信することでIFTTTと連携できるデキるやつ。サーバーを作ればなんでもできる。

----

![image](https://qiita-image-store.s3.amazonaws.com/0/56170/c145b52c-f163-41a5-0ab3-b5780527a94a.png)

----

## デバイス連携デモ

----

IFTTTに反応を送るデバイス
![image](https://qiita-image-store.s3.amazonaws.com/0/56170/8fdc9b24-b1ba-652b-342c-ea0cab02a390.png)

----

ボタンを押します
![image](https://qiita-image-store.s3.amazonaws.com/0/56170/e848dec4-85de-7562-4d3a-592fc00c0136.png)

----

こんなかんじに送られる
![image](https://qiita-image-store.s3.amazonaws.com/0/56170/c19acc85-afe5-b63d-7d6b-ad33460f990e.png)

----

こういった直接見に行けない環境情報をリアルタイムにチャットに通知してしまうやりかた。

* 例
    * 人感センサーで玄関などの防犯検知
    * 光センサーで照明のON/OFFチェック
        * などなど

----

ご清聴いただきましてありがとうございました
![image](https://qiita-image-store.s3.amazonaws.com/0/56170/f9202bb5-d302-0076-951d-95007f39cfe8.png)

----

* スライド内の素材は以下を使用させて頂いております。ありがとうございます！ 
    * シルエットデザイン
        * http://kage-design.com/ 
    * human pictogram 2.0
        * http://pictogram2.com
    * FLAT ICON DESIGN
        * http://flat-icon-design.com/
GitLab Mattermost コマンドラインツールの使い方


# 動機
http://docs.mattermost.com/administration/command-line-tools.html のように、Mattermostにはチームやユーザーの追加・削除ができるコマンドラインツールがあります。
ただし、GitLab Mattermostではコマンド名が違ったりちょっとひと手間必要だったので情報をまとめました。
ついでにチームの削除やユーザーの削除について説明します。

# 環境
* Ubuntu 14.04
* GitLab CE 8.9 Omnibus package

# 内容
## ざっくりとしたまとめ
1. コマンドが、「platform」ではなく、「/opt/gitlab/embedded/bin/mattermost」
* mattermostアカウントで操作する必要がある
* 「-config="/var/opt/gitlab/mattermost/config.json"」を指定する必要がある
* 「panic: Failed to load system translations for 'en'」エラーがでるので、[ここ](https://forum.mattermost.org/t/solved-panic-failed-to-load-system-translations/959/3)を参考にen.jsonを実行パスに置く。

## 実行例
```
# curl -O https://raw.githubusercontent.com/mattermost/platform/master/i18n/en.json
# sudo -u mattermost -i bash
# /opt/gitlab/embedded/bin/mattermost -config='/var/opt/gitlab/mattermost/config.json' [option]
```

# コマンドの例
## チームの削除
チーム名を指定して削除します。バックアップとったか？とか本当に消していいか？とか聞かれるので、[YES]とタイプしてEnterします。

```
# /opt/gitlab/embedded/bin/mattermost -config='/var/opt/gitlab/mattermost/config.json' -permanent_delete_team -team_name="name"
```

## ユーザーの削除
メールアドレスを指定してユーザーを削除します。同じく2回確認されます。
アカウントだけでなく、そのユーザーの発言もすべて削除されます。

```
# /opt/gitlab/embedded/bin/mattermost -config='/var/opt/gitlab/mattermost/config.json' -permanent_delete_user -email="user@example.com"
```

# その他
なぜコマンドラインツールを使う必要が出たかというと、GitLab CE を8.9にアップデートして[色々なトラブル](https://forum.mattermost.org/t/upgrading-to-gitlab-mattermost-in-gitlab-8-9/1735)にあったからです。
バージョンアップするときには気を付けましょう。


# 参考リンク
https://forum.mattermost.org/t/upgrading-to-gitlab-mattermost-in-gitlab-8-9/1735
https://forum.mattermost.org/t/solved-panic-failed-to-load-system-translations/959
http://docs.mattermost.com/administration/command-line-tools.html
finatra 四歩目

# re-load
さて、これまではコードを書き換えるたびに sbt run で起動し直さないと反映されませんでした。

playframework であれば play ~run でコードを変えればコンパイルが走ってくれるので、毎回sbt runしなくても、常に最新の状態を確認できます。

流石に毎回 sbt run はつらいので play ~run のよう出来るようにします。

やり方は非常に単純でplugin.sbtに以下のように追加してやるだけです。

```scala:plugin.sbt
addSbtPlugin("io.spray" % "sbt-revolver" % "0.8.0")
```

そうすると `sbt "~re-start"` で起動してやれば、コードの変更を検知して最新の状態を反映してくれます。

# 参考
https://github.com/spray/sbt-revolver
GCEのインスタンス内からインスタンスのzoneを取得。ついでにメタデータの処理。


コメントで教えていただいた。

```
$ curl -s -H "Metadata-Flavor: Google" http://metadata.google.internal/computeMetadata/v1/instance/zone 
projects/XXXXXXXXXXX/zones/asia-east1-b
```

hostが`metadata.googl.internal`になっているのがミソっぽい。
Compute Engine API側になくて全然気づかなかった。

asia-east1-bだけ欲しいなら`basename`を使うのがよさそう。

```
$ basename $(curl -s -H "Metadata-Flavor: Google" http://metadata.google.internal/computeMetadata/v1/instance/zone)
asia-east1-b
```

# 蛇足

jqが使えるなら一括で取得しておいて使いまわすのもよいかもしれない。

```
$ METADATA=$(curl -s -H "Metadata-Flavor: Google" "http://metadata.google.internal/computeMetadata/v1/?recursive=true&alt=json")
$ echo $METADATA | jq '.instance.zone'
"projects/XXXXXXXXXXXXX/zones/asia-east1-b"
$ basename $(echo $METADATA | jq -r '.instance.zone')
asia-east1-b
```

メタデータをザクっと確認するなら

```
$ curl -s -H "Metadata-Flavor: Google" "http://metadata.google.internal/computeMeta
data/v1/?recursive=true&alt=text"
```

とするのがよさそう。

たとえば`instance/disks/1/device-name`のデータがとりたいなら

```
$ echo $METADATA | jq '.instance.disks[1].deviceName'
```

で取得できる。pathの変換が必要なのでいい感じに取得する方法がないか悩ましい。
rails ajaxでフォロー機能

フォロー機能作成までは割愛。
非同期処理のajaxを使ったフォローの実装。
自分用のメモなのでわかりにくいです。



```show.html.erb
<%= render 'follow_form' %>


<div class="follow" id = "follow-count">
  <%= render 'follow_count' %>
</div>
```

```_follow_form.html.erb
<% if user_signed_in? %>
<% if @user != current_user %>
<div id="follow_form">
  <% if current_user.following?(@user) %>
   <%= render 'unfollow' %>
  <% else %>
   <%= render 'follow' %>
  <% end %>
</div>
<% end %>
<% end %>
```
フォローボタンはここでcreateとdestroy両方にidが指定してあります。


```_follow.html.erb
<%= form_for(current_user.active_relationships.build, remote: true) do |f| %>
  <%= hidden_field_tag :following_id, @user.id %>
  <%= f.submit "フォローする", class: "follow-btn" %>
<% end %>
```

```_unfollow.html.erb
<%= form_for(current_user.active_relationships.find_by(following_id: @user.id), html: { method: :delete }, remote: true) do |f| %>
  <%= f.submit "フォロー中", class: "unfollow-btn" %>
<% end %>

```
それぞれにremote: trueを追加。

フォローボタンが押された時に、非同期処理で、フォローボタン⇄アンフォローボタンの表示を変える。

フォローボタンを押すということは、createアクションとdestroyアクションを使うことになる。


```relationships_controller.rb
  def create
    @user = User.find(params[:following_id])
    current_user.follow(@user)
    respond_to do |format|
     format.html { redirect_to @user }
     format.js
   end
  end

  def destroy
    @user = Relationship.find(params[:id]).following
    current_user.unfollow(@user)
    respond_to do |format|
     format.html { redirect_to @user }
     format.js
   end
  end
```

これでcreate.js.erbとdestroy.js.erbファイルを探すようになる。


create.js.erbとdestroy.js.erbの作成

```create.js.erb
$("#follow_form").html("<%= escape_javascript(render('users/unfollow')) %>");

$("#follow-count").html("<%= escape_javascript(render('users/follow_count')) %>");

```

```destroy.js.erb
$("#follow_form").html("<%= escape_javascript(render('users/follow')) %>");

$("#follow-count").html("<%= escape_javascript(render('users/follow_count')) %>");

```

renderは、当然非同期処理後に表示されて欲しいページを指定してあげる。
なので、フォローを非同期処理した後に表示されて欲しいのはunfollowボタンだから、unfollowページにリダイレクト。
逆も同じ。

それで、フォローする、はずすのあとに応じてフォロワー数は変わるはずだから、それも非同期でやりたい。

そこで、もう指定してあるが、createやdestroyボタンを押した時に数を変えたいから、create.js.erbとdestroy.js.erbにもその処理を記述する。
上を参照。


他にももし、`フォローボタンを押した時`にページのどこか一部を更新したいってなったら、それのパーシャルを作って、create.js.erbとdestroy.js.erbに記述すればよい。
ECSでCloudwatch Logsにログを出力する


cloudpack大阪の佐々木です。
Docker1.9からlogging driverにAWSのCloudwatch Logsが追加されたので、ECSで試してみました。

# logging driverとは
DockerはImmutable Infrastructureとして構成され、不要になったコンテナは削除され、必要に応じて用意に追加できる構成をとることが多いと思います。なので、ログをコンテナ内に保存させておくと、コンテナが削除されるとなくなってしまいます。そのために外部にログを出力させる必要が出てくるのですが、これを容易に実施できるのが、logging driverという機能です。標準出力にログを出力しておけば、logging driverを使ってログを外部に保存できます。

対応しているlogging driverは下記に記載されています。
https://docs.docker.com/engine/admin/logging/overview/

fluentdがよく使われると思いますが、splunkなんかもあります。

# Cloudwatch Logs logging driverの使い方

logging-driverにawslogsを指定して、オプションとして、リージョンとロググループを指定するだけ！
超簡単ですね

https://docs.docker.com/engine/admin/logging/awslogs/

# ECSで使ってみる

CloudWatch Logsの画面からロググループを作成します。

![Kobito.LjqebH.png](https://qiita-image-store.s3.amazonaws.com/0/3246/2165177a-7eb2-1eea-7571-1f3f9ed4b9b1.png "Kobito.LjqebH.png")


![Kobito.7mPSpE.png](https://qiita-image-store.s3.amazonaws.com/0/3246/7cd45071-f4ea-9e32-1ae3-be59414d4173.png "Kobito.7mPSpE.png")

ecs-cliでECSクラスタを作成します。
対応しているECS Agentのバージョンが1.9.0以降ということで、ECS optimized AMIの2016.03.bが必要になります。
http://docs.aws.amazon.com/ja_jp/AmazonECS/latest/developerguide/using_awslogs.html
今回は2016.03.c(ami-095dbf68)を使用しました。

```bash:
$ ecs-cli up --capability-iam --keypair KeyName --image-id ami-095dbf68
```
ecs-cliの使い方は下記も見てください。

http://qiita.com/taishin/items/076a7699c787da68e396

環境ができたらWordpressを立ち上げてみます。

```yml:docker-compose.yml
wordpress:
  image: wordpress
  mem_limit: 268435456
  ports:
    - "80:80"
  links:
    - mysql
  log_driver: awslogs
  log_opt:
    awslogs-group: "ecs-log-group"
    awslogs-region: "ap-northeast-1"
mysql:
  image: mysql
  mem_limit: 268435456
  environment:
    MYSQL_ROOT_PASSWORD: password
```

logging driver関連は下記の部分だけです。

```yml:
  log_driver: awslogs
  log_opt:
    awslogs-group: "ecs-log-group"
    awslogs-region: "ap-northeast-1"
```

起動します。

```bash:
$ ecs-cli compose service up
```

インスタンスのIPアドレスにブラウザでアクセスすると、Wordpressが立ち上がっています。
![Kobito.rAjF1B.png](https://qiita-image-store.s3.amazonaws.com/0/3246/6051bbeb-4a50-70ee-27a3-34c716383961.png "Kobito.rAjF1B.png")

Cloudwatch Logsを見てみます。

![Kobito.USOkS0.png](https://qiita-image-store.s3.amazonaws.com/0/3246/6f59cca4-22ee-5f38-53a0-047701cf0515.png "Kobito.USOkS0.png")

ログが出力されています。

# まとめ

Cloudwatch Logs logging driverを使えば、ECSのコンテナのログを簡単にCloudwatch Logsに保存できます。
Cloudwatch Logsのアラートと組み合わせることができるので、ログの管理だけでなく、監視等も簡単にできるのではないかと思います。
finatra 三歩目

# quill で select を投げて結果を取得する

```scala:GroupRepository.scala
  def list(): TwitterFuture[List[Groups]] = {
    val q = quote(query[Groups])
    (for {
      r <- db.run(q)
    } yield r)
```

selectで全件取得するのに必要なのはこれだけです。

さて、しかし困りました

Finatraが扱うのは `com.twitter.util.Future` であって `scala.concurrent.Future` ではありません。

[ドキュメント](http://twitter.github.io/finatra/user-guide/getting-started/#futures)には`twitter/bijection`使ったらええよって書いてあるんですが、`com.twitter.bijection.twitter_util.UtilBijections.twitter2ScalaFuture` のimportが上手く行かない・・・

なので
http://stackoverflow.com/questions/30317473/convert-scala-future-to-twitter-future
のコードを全部コピーします。

これでFutureの変換ができるようになって結果を取得できるようになります。

```scala:GroupController.scala
  get("/group") { request: Request =>

    val list = groupRepository.list()

    list
  }
```

# コード全容
https://github.com/FScoward/handshake-api/tree/0.3
Bash | シェルの計算は変数が文字列でもスペースが入っていても大丈夫

わりとファジーに計算してくれるっぽい。

```bash
a='    1    ' # a = 1

b=$(($a+1))   # b = a + 1

echo $b       # => 2
```

# 環境

- bash 3.2








<!-- Update From Qiita API -->

# チャットメンバー募集


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

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





# Twitter


https://twitter.com/YumaInaura


<!-- Update From Qiita API -->
Realtek AmebaのUARTについて

Realtek AmebaのUARTについて

Realtek Amebaのベアメタルな環境でUARTを使いたいので調べてみました。

ビルドは、https://github.com/eggman/rtl_ameba_gcc_sample のmain.cを書き換えて行いました。

# まとめ
* ROMにあるUARTの関数を呼べば動作する。
* UART初期化は起動時にROMのコードが行っている。その際のUARTの設定は38400bps,8,N,1になっている。
* いろいろな機能を使いたい場合は調査が必要。

# 送信
* １文字送信はROMに内蔵されている HalSerialPutcRtl8195a()を使う

```c
extern _LONG_CALL_ VOID
HalSerialPutcRtl8195a(
    IN  u8 c
    );
```

# 受信
* １文字受信は ROMに内蔵されている HalSerialGetcRtl8195a()を使う。引数PullModeには1を設定する。0だと動かなかった。

```c
extern _LONG_CALL_ u8
HalSerialGetcRtl8195a(
    IN  BOOL    PullMode
    );
```

# サンプルプログラム
* キーボードからの改行までの複数文字の入力を表示するサンプル

```c
#include "rtl8195a.h"

#define KEY_ENTER 13

char lbuf[128];

void _putc(char c)
{
    HalSerialPutcRtl8195a((u8) c);
}

char getc(void)
{
    return (char) HalSerialGetcRtl8195a(1);
}

void newline(void)
{
    _putc(13);
    _putc(10);
}

void _puts(const char *s)
{
    while (*s) _putc(*s++);
}

void gets(void)
{
    char c;
    size_t len;

    len=0;
    while( (c = getc()) != KEY_ENTER)
    {
        lbuf[len++] = c;
        _putc(c);
    }

    newline();
    lbuf[len] = 0;
}

int main(void)
{
    while (1) {
        _puts(">");

        gets();

        _puts(">> input is ");
        _puts(lbuf);
        newline();
    }
}
``` 

## 動作例

```
===== Enter Image 2 ====
>ABC
>> input is ABC
>DEF
>> input is DEF
>XYZ
>> input is XYZ
>
```
[Android] Crashlyticsでクラッシュレポートに情報を追加する

#はじめに
[Crashlytics](https://fabric.io/kits/android/crashlytics)は、ほぼ自動でアプリのクラッシュレポートを送信してくれるすごいやつですが、レポートをみて解析するときにユーザー情報や行動ログなど、もう少し情報持たせたいな、という時があります。
そんなときにCrashlyticsのログに追加情報を設定する方法を紹介します。

#追加情報の設定

- アプリが終了すると設定した情報はクリアされるので適切なタイミングで設定しましょう。
- 追加情報には容量制限があるようです。(送信時に重すぎないため)
- CrashLyticsがクラッシュレポートを送信するタイミングはアプリ起動時やクラッシュ時など複数あるようです。
- **注意: あくまでもアプリがクラッシュしたときの追加情報となるため、下記の追加情報を設定した瞬間にレポートが送られるわけではありません。(ちょっぴりハマった)**

##ログを追加する
```Crashlytics.log(int priority, String tag, String msg);```でCrashlyticsのレポートにLogが追加されます。priorityはandroid.util.Logのレベルを設定することができます。
LogCatにも出力されます。
引数が一つの方はDebugのTag:CrashlyticsCoreが設定される簡易版です。
ユーザーの行動ログの出力などに使用することができます。

- Logは最大64KBまで送信することができます。あふれた分は過去のログから削除されます。
- ***注意: クラッシュ直前に追加されたログは送信されないことがあるようです(めっちゃハマった)***

```java
Crashlytics.log(Log.WARN, "TAG_HOGE", "hogehoge");
//または
Crashlytics.log("hoge");
```
###ログの表示位置
一覧にLogは表示されないのでレポート詳細に入りView all sessionsから更にセッションの詳細から見ることができます。

![レポート詳細](https://qiita-image-store.s3.amazonaws.com/0/34084/e3962bb2-e424-cea9-700c-b9fce7ac6064.png)

Logはレポートのセッション詳細の上部のLogsに表示されます。

![スクリーンショット 2016-06-24 20.41.28.png](https://qiita-image-store.s3.amazonaws.com/0/34084/6e534086-2809-b74b-fdab-565a584bf358.png)


##ユーザー情報を追加する
ユーザーの情報をレポートに追加することができ、ユーザー特定に役に立ちます。
また、あとからCrashlyticsのコンソールからユーザー情報で検索することができます。

```java
Crashlytics.setUserEmail("hoge@hoge.com");
Crashlytics.setUserIdentifier("12345");
Crashlytics.setUserName("john");
```
###ユーザー情報の表示位置
ユーザー情報はレポート詳細のDevice Statsticsの下に表示されます。
![ユーザー情報.png](https://qiita-image-store.s3.amazonaws.com/0/34084/d46c0576-8b08-82fb-2a2a-461d37b0f352.png)

##key/valueを追加する
Stringやintのkey/valueのペアを設定することができます。
設定情報や状態など設定しておくと便利です。
ログはクラッシュの直前に追加すると送信されないことがあるようでしたが、こちらは直前でも反映されました。

- 同じKeyで設定すると上書きされて送信されます。
- 最大６４ペア設定できます。それを超えると送信されません。
- 1つのkey/valueは最大サイズ1KB。

```java
Crashlytics.setString("String", "string");
Crashlytics.setInt("int", 1);
Crashlytics.setFloat("float", 1f);
Crashlytics.setDouble("double", 1.0);
Crashlytics.setBool("bool", true);
Crashlytics.setLong("long", 1l);
```
###key/valueの表示位置
Keys/Logsトグルで切り替えるとLogと同じ箇所に表示されます。

![スクリーンショット 2016-06-24 20.49.55.png](https://qiita-image-store.s3.amazonaws.com/0/34084/7cd140bf-c84c-81e0-5ed9-609fc88a4aed.png)


#終わりに
以上になります。これでさらに快適なバグフィックスライフを送りましょう。

iOSはこちらが参考になると思います。
[Crashlyticsにカスタムログを送信する方法
](http://qiita.com/yo1106/items/08d99d4e2ed83903485e)

##参考
https://docs.fabric.io/android/crashlytics/enhanced-reports.html#custom-logging