OmniAICreator/Qiita-1.07M huggingface dataset:
#好きなエビ曲を10曲あげる で統計をまなぶ(その1. Twitter編)

## モチベーション
2ヶ月ほどまえに #好きなエビ曲を10曲あげる というハッシュタグがトレンド入りしました。
エビ曲とは私立恵比寿中学の曲を表すのですが、隠れではありますが、ファミリー(ファンのこと)である私はこのトレンド入りにすっかり乗り遅れておりました。
このハッシュについてはあとむさんがすでに集計をされておりました。

[好きなエビ曲を10曲あげる　[エビ中]](http://uya-muya-output.blog.so-net.ne.jp/2017-07-11)

とはいえ、最後に

`あと、誰かこの結果を受けていろいろ分析してくれると嬉しいな！（他人任せ）`

と書かれており、なにか面白いことが出来るんじゃないかなと思い立ったのがこのハッシュタグが流行ってから3週間経った2017年7月の末でした。
それから約2ヶ月間Web系、統計とはまったく縁遠い生活をしてきたクソSEの戦いは始まったのでした。

## Twitter APIを使えるようにする
スクレイピングしちゃおうかなぁと思ったらそれは規約で禁止とのことで正々堂々とTwitter APIを使うことにしました。
Twitter APIを使うにはTwitterアプリケーションを登録する必要があるので次のサイトなどを参考に登録しました。
[Twitter API キーの取得手順 - まだプログラマーですが何か？](http://dotnsf.blog.jp/archives/1044796238.html)

## ツイートを集める
### とりあえず公式APIを使ってみる
まぁ、ここでAPIを使えば楽勝でツイートなんて集められるでしょと思ってtwitterの公式(?)Gemをインストール

```gem install twitter```

簡単に検索をかけてみました。

```ruby
require 'twitter'

client = Twitter::REST::Client.new do |config|
  config.consumer_key = "xxxxxxxxxxxxxxxxxxxxxxxxx"
  config.consumer_secret = "yyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyy"
  config.access_token = "zzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzz"
  config.access_token_secret = "wwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwwww"
end

client.search("#好きなエビ曲を10曲あげる since:2017-06-30").each do |tweet|
  p tweet.id
  p tweet.created_at
  p tweet.text
end
```

なんか数件しか引っかからない・・・

調べてみるとTwitterの検索は数日分しか実施できないとのこと・・・この作業をしていたのは7月の末。祭りは過ぎた後・・・数ツイートしか引っかかりませんでした。
公式ページの検索では全部(?)ひっかかるのに・・・

1日ごとに検索したらうまくいくよなどの情報もありましたが、うまくいかず、数日経過、途方にくれました・・・

### まさかの人力
Collectionsという機能を発見。どうやらツイートをリストに保存できる機能らしく、保存したツイートからAPI経由で取得できることを知りました。
しかし、公式ページにも公式アプリにもコレクションに追加する方法が出ていません。なんじゃそりゃ・・・
調べてみるとTwitter公式のTweetDeckを使うとできると書かれていました。
コレだ！というわけで1件1件数時間かけてコレクションに追加していきました。

その間にベアラートークンなんていうことも学びちょっとTwitterの使い方も覚えていきました。

コレクションの取り出しスクリプト

```ruby
#!/usr/bin/env ruby
#-*- encoding:UTF-8 -*-

require 'oauth'
require 'json'

encoded_bearer_token = 'XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX'
consumer_key = "xxxxxxxxxxxxxxxxxxxxxxxxx"
consumer_secret = "yyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyy"
consumer = OAuth::Consumer.new(
    consumer_key,
    consumer_secret,
    site: 'https://api.twitter.com/'
)
endpoint = OAuth::AccessToken.new(consumer, access_token, access_token_secret)


response = endpoint.get("https://api.twitter.com/1.1/collections/entries.json?id=custom-ZZZZZZZZZZZZZZZZZZ&count=100&max_position=
YYYYYYYYYYYYYYYYYY")

json = JSON.parse(response.body)

puts JSON.pretty_generate(json)
```

これで約700件のツイートのJSONを取得することができました。
メニューや部品を D&D(ドラッグアンドドロップ) できない時はアイコン部分を掴んでみる

ポップアップメニューの項目や、GUI 上に配置された部品などを並び替えたい場面があると思います。が、なぜかドラッグできないことがあります。どんな時にそうなるのか今までわからなかったのですが、わかってみれば単純でした。

**アイコン部分を掴んでドラッグしてみる**。

これで大体上手くいきます。

# 具体例
いくつか具体例を挙げます。

## Windows のフォルダメニュー
メニュー項目のどこを掴んでも大体ドラッグできますが、たまにできない時があります。アイコン部分を掴んでやると確実にドラッグできるので混乱しなくなります。

![drag_on_quicklaunch.png](https://qiita-image-store.s3.amazonaws.com/0/191170/7f886c17-f238-1edd-755f-6977d0535703.png)

## GitHub の Pinned repositories
pinned repository を並び替えるには、左上のアイコン部分を掴みます。

![github_pinned_draggable.jpg](https://qiita-image-store.s3.amazonaws.com/0/191170/fdc52e05-2024-e673-741d-97e467305e5d.jpeg)

# おわりに
当たり前のしょうもないネタかもしれませんが、自分にとっては大きな発見だったのでまとめてみました。参考になれば幸いです。
DynamoDBで全文検索もどきをする

[CloudSearchの内部動作と、それを知らぬがゆえにハマったこと](http://qiita.com/kurimoto/items/3a869ad8dd7fab1bd3a6)を経験し、要件としては「姓名マスタから名前で検索したい」ってだけだったのに何でこんな苦労してんやろ、、
しかもCloudSearch意外に高いし、、インスタンスサイズがどんどん増えて、Multi-AZで数も増えてくとか辛い。辞書のメンテとかindex再構築とかもうやりたくない。

何とか既存システムの乗ってるDynamoDBで完結できないものだろうか？

# 一晩悩んでみた
もっとも簡単のはscan等で全件データ取得し、フィルターかける方式です。
ええ、はい、検索リクエスト来るたびに全件テーブル舐めていいなら、、

どうにかしてqueryで効率的に検索をしたいところ。
しかし単純に「名前で検索したい」といっても一般ユーザに解放しているサービスなので、漢字、平仮名、片仮名、アルファベット、姓のみ、名のみ、漢字と平仮名混合などなど、色々なパターンでリクエストが来ます。

一番簡単なのは、インデックスを利用する案でしょうか。

## 案1

### Table
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {IndividualId} |
### LSI-1
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {漢字氏名} |
### LSI-2
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {平仮名氏名} |
### LSI-3
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {カタカナ氏名} |
### LSI-4
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {アルファベット氏名} |

検索リクエストが来るたび、各indexにアクセスする案。sort keyをbegins_withで探せばいけそうです。
コストを考えるとLSIが良いかな？
しかしよく考えると氏名を別々に区切ってインデックスを貼らないと名前だけでの検索ができません。となると漢字カタカナ平仮名アルファベットを各々姓と名で用意しなければいけないので8index。LSIの制限を越えるので、GSIを貼る必要があります。

## 案2

### Table
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {IndividualId} |
### GSI-1
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {漢字姓} |
### GSI-2
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {漢字名} |
### GSI-3
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {カタカナ姓} |
### GSI-4
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {カタカナ名} |
### GSI-5
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {first name} |
### GSI-6
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {middle name} |
### GSI-7
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {family name} |

同じような構成なのにLSIとGSIが混じるのも何かトラブルの元になりそうなので、全部GSIと開き直ってみる。
リクエストに平仮名が来た場合はカタカナに変換するロジックを使えば平仮名用indexは貼らずにすみそうです。

しかし、検索リクエストのたびにgsiに7回アクセスするの、、、？
リクエストがカタカナだったらカタカナGSIへ、とかロジック書けば多少マシになりそうですが、無理やり感が否めない、、

将来的に他の属性で検索できる状態にしたい、とも思っていたので、その度にindex増えていくのも辛いです。

やはり全文検索専用のサービス様にはかなわないのか、、

# そこで閃き

### Table
| partition key | sort key |
|:-----------|:------------|
| {GroupId} | {IndividualId} |
| {GroupId} | 検索語句A: {IndividualId} |
| {GroupId} | 検索語句B: {IndividualId} |

じゃじゃーん！
検索語句には漢字姓やカタカナ名など、検索したい属性を入れていきます。検索語句の最後にIndividualIdを入れているのは一意性を担保するためです。

これなら属性がどれだけ増えても大丈夫。indexを増やす必要はありません。query1回、begins_withを利用するだけでほぼ全文検索が可能となります！

# 結果
この実装を持ってプロダクションリリースしたところ、無事にCloudSearchと同等のレベルのサービスを格安で提供することができるようになりました。やったじゃん！

ただし後から気づいたデメリットも。

- データ量が増えまくって書き込みスループットが増えた

GSIを貼って並列に書き込むか、直列に書き込むかという違いではあるのですが、batchPutを利用してもなかなか終わらない。これは仕方ないよね。

- 登録データ件数管理が必要になった

マスタデータにはカナが抜けてるもの、アルファベットが無いものと様々あるので、単純に登録件数の1/Xが人数、と保証できない。
そのため登録件数管理用のテーブルを用意する必要が出て来ましためんどくさい。

ただ、私の要件からすると十分にこれらのデメリットを補えるシステムとなりました。

DyanmoDBをこんな使い方すること自体色々間違ってるとか素直にCloudSearchに頼っとけとかRDSツカエヨって心の声はシャットダウンし、こんな方法でもプロダクション利用の実績ができました！というお話でした。
IE6でcanvasを使う

## 準備

https://github.com/arv/ExplorerCanvas/blob/master/excanvas.js

をダウンロード (Apache License, Version 2.0)

## 使用例

```html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">

<!--[if IE]>
<script type="text/javascript" src="excanvas.js"></script>
<![endif]-->

<script type="text/javascript">
function main() {
        var canvas = document.getElementById("myChart");
        if (canvas.getContext) {

                var context = canvas.getContext('2d');

                //左から20上から40の位置に、幅50高さ100の四角形を描く
                context.fillRect(20,40,50,100);

                //色を指定する
                context.strokeStyle = 'rgb(00,00,255)'; //枠線の色は青
                context.fillStyle = 'rgb(255,00,00)'; //塗りつぶしの色は赤

                //左から200上から80の位置に、幅100高さ50の四角の枠線を描く
                context.strokeRect(200,80,100,50);

                //左から150上から75の位置に、半径60の半円を反時計回り（左回り）で描く
                context.arc(150,75,60,Math.PI*1,Math.PI*2,true);
                context.fill();
        } 
}

window.onload = main;

</script>
</head>
<body>

<canvas id="myChart" width="400" height="400"></canvas>
aa
</body>
</html>
```

![スクリーンショット_2017-09-09_08-30-15.png](https://qiita-image-store.s3.amazonaws.com/0/25728/7211c1ea-7916-bf6d-cbb1-5e6a066b75d7.png)

![スクリーンショット_2017-09-09_08-37-49.png](https://qiita-image-store.s3.amazonaws.com/0/25728/56746aec-62d6-fbce-7937-04f7a8195ac7.png)

## onloadの注意

### 動いた例

```html:例1
<body onload="main();">
```

```html:例2
<script>
window.onload = main;
</script>
```

### 動かなかった例

```html:例1
...
<canvas id="myChart" width="400" height="400"></canvas>

<script type="text/javascript">
main();
</script>
```


```html:例2
...
<canvas id="myChart" width="400" height="400"></canvas>

<script type="text/javascript">
        var canvas = document.getElementById("myChart");
        if (canvas.getContext) {

                var context = canvas.getContext('2d');

                //左から20上から40の位置に、幅50高さ100の四角形を描く
                context.fillRect(20,40,50,100);

                //色を指定する
                context.strokeStyle = 'rgb(00,00,255)'; //枠線の色は青
                context.fillStyle = 'rgb(255,00,00)'; //塗りつぶしの色は赤

                //左から200上から80の位置に、幅100高さ50の四角の枠線を描く
                context.strokeRect(200,80,100,50);

                //左から150上から75の位置に、半径60の半円を反時計回り（左回り）で描く
                context.arc(150,75,60,Math.PI*1,Math.PI*2,true);
                context.fill();
        } 
</script>
```


## 動かないコード

* requestAnimationFrame が無い？
DynamoDB LocalとCognitoを併用する場合の注意点

## 先に結論

DynamoDB LocalとCognitoを併用する場合は、必ず**別々のendpoint**を定義する。
特にCognito側のendpointを書く事例はほとんど見かけないので忘れがち。

```utils/auth.js
import AWS from 'aws-sdk'

const cognitoIdentityServiceProvider = new AWS.CognitoIdentityServiceProvider({
  apiVersion: '2016-04-18',
  region: 'ap-northeast-1',
  endpoint: `https://cognito-idp.ap-northeast-1.amazonaws.com/`,
})

export default function auth(AccessToken) {
  return new Promise((resolve, reject)=>{
    cognitoIdentityServiceProvider.getUser({AccessToken}, (err, data)=>{
      if (err) return reject(err)
      return resolve(data)
    })
  })
}
```

```utils/dynamoose.js
import dynamoose from 'dynamoose'

dynamoose.AWS.config.update({region:'ap-northeast-1'})
if ( process.env.NODE_ENV === 'dev' ) {
  dynamoose.AWS.config.endpoint = new dynamoose.AWS.Endpoint('http://localhost:8000')
}
export default dynamoose
```

## 前提

* 今回のケースではNode.jsのdynamooseというORMを使っているが、その他のケースでも発生する可能性があるので念のためメモ。
* ServerlessFrameworkを使用しているが、それは今回の件とは関係ないはず？

## 経緯

* ServerlessFrameworkのプラグイン `serverless-dynamodb-local` を使って、DynamoDB Localを起動し、Cognitoでユーザー管理をしようとした
* アプリケーションを実行すると、１度目は成功するが２度目で必ず下記エラーが出ることに気づいた

```
MissingAuthenticationToken: Request must contain either a valid (registered) AWS access key ID or X.509 certificate.
```

* AccessTokenが間違えてるのかなと思ったが合ってた
* リージョン指定が間違えてるのかなと思ったが合ってた
* DynamoDBの向き先をローカルではなく本番に向けたらエラーが出なかった
* 向き先をローカルに戻して、CognitoのSDK側にendpointを指定したらエラーが出なかった

## 推察

* 恐らくCognito User Poolは内部でDynamoDBを使っていて、DynamoDBのendpointを変えるとCognitoのSDK側にも影響を及ぼしてしまうのではないか？
* このあたり詳しい人、もしくは中の人、今回の件について何かあれば教えてもらえたら嬉しいです
Reddieベータ版へようこそ

#Reddieベータ版へようこそ
**有限責任会社 The Department of Stuff & Things, Etc.（代表取締役：プライス・アダム、本社：オレゴン州ポートランド）が運営するRedisクラスタのマネジメントツール「[Reddie（レディ）](https://goo.gl/Na4USp)」は、無料でプロ機能を全てご利用いただける「Reddieベータ版」を2017年８月１７日にリリースいたしました。**

![Reddie-logo-jp-400.png](https://qiita-image-store.s3.amazonaws.com/0/199842/d8f20891-dc96-5193-36d0-f9a7de364b64.png)

##Reddieとは？
ReddieはDockerコンテナとして配信される、ウェブベースのRedisクラスタのマネジメントツールです。直感的な操作で複数ノード環境下でのRedisクラスタの扱いが、劇的に楽に！あなたのRedisクラスタ運用の、大幅な時間節約にも繋がります。

###どんな人の役に立つの？
Redisを使ってアプリ開発している方、Redisをモニター・管理している方には一際お役に立てるツールです。

###Reddieで何ができるの？
- リアルタイムでクラスタ全体のリソース・ユーセージや統計を閲覧
- 自動ヘルスチェックを実行し、クラスタの正常動作を保証
- ダウンタイムなしでノードをクラスタに追加
- configuration persistenceでクラスタ全体を一挙に再編成
- クラスタ全体をモニターして、リアルタイムでコマンド実行を確認
- Redis及びRedisクラスタに準拠したLua scriptsを作成
- などなど

ただいま「Reddieベータ版」のリリースを祝って、Reddie全機能を備えた「Reddieプロ」を無料で提供中。

<img width="600" alt="Reddie-Redis-Cluster.png" src="https://qiita-image-store.s3.amazonaws.com/0/199842/4c706f79-284d-b642-8458-abebe707e9c2.png">
クラスタのスロットページより。色値によりKeyの数が視覚的につかめる

:point_right: [Reddieをチェック](https://get-reddie.com/) 

##Reddieベータ版に参加しよう
Reddieベータ版は、どなたにでも参加いただけます。期間中にReddieアカウント（無料）を作り、ぜひReddieプロを無料でお試しください。

###ベータ版の参加方法
1. Reddieアカウントに[サインアップ](https://get-reddie.com/app/signup)
2. [インストール](https://get-reddie.com/documentation/installation/)して[実行](https://get-reddie.com/documentation/running-reddie/)
3. 作成したReddieアカウントで[アプリにログイン](https://get-reddie.com/documentation/licensing-reddie/)して、ライセンスを登録

ベータ期間が終了すると、アカウントは自動的に「Reddieフリー」になります。期間中に「Reddieベーシック」もしくは「Reddieプロ」をお買い上げの方は、ベータ期間終了後にお支払い期間開始となります。

##バグの報告をしよう
Reddie使用中に不具合が発生した際には、アプリの「レポート（Report）」ボタンよりバグレポートを送ってください。Reddieがより使いやすくなるようご協力ください :bow_tone2:  コメントや提案も大歓迎です！

##ベータ期間終了
ベータ期間は、Reddieチームが正式版へ移行すると判断した時に終了します。具体的な日付は、終了が近くなった段階で、メールや[ツイッター](https://twitter.com/Reddie_Japan)にてお知らせします。

##関連リンク
- [Reddieの無料デモ](https://get-reddie.com/app/demo)
- [アカウント作成](https://get-reddie.com/app/signup)
- [Reddieのインストール](https://get-reddie.com/documentation/installation/)
- [ドキュメンテーション](https://get-reddie.com/documentation/installation/)

##スペシャルオファー

:ideograph_advantage: *ベータ期間中に[メーリングリストに登録](https://get-reddie.com/mailinglist/)すると、お得な「一年間１０％オフ」のプロモコードがもらえます！*

![BetaOffer.png](https://qiita-image-store.s3.amazonaws.com/0/199842/79ba332d-c142-4af1-b6d1-135baeb37197.png)
writeIn,typeof javascript

writeln=テキストの文字列とその直後に続く改行文字を文書に書き込む。

単純にwriteに<br>が追加されただけのコードっぽい

typeof= 演算子は、評価を行われないままの状態のオペランドのデータ型を示す文字列を返す。

typeof operand
Herokuを使ってchromeでwebページのスクリーンショットをとる


作成したwebサービスにスクリーンショットを追加したいと思ったことはありませんか？

Heroku に Headless Chromeを入れると Heroku内でChromeを操作できるので、簡単にスクショを取ることができます。
rubyからchromeを呼び出しでスクショをとってみます。

# Herokuをsetupする

Herokuでアプリを作成しましょう(作成手順は他を参考にしてください）。
作成時にはchromeが入っていないので、Buildpacksに追加します。HerokuコンソールのSettingにBuildpacksの設定があるので、２つ追加します。

https://github.com/heroku/heroku-buildpack-chromedriver.git
https://github.com/heroku/heroku-buildpack-google-chrome.git

<img width="1139" alt="スクリーンショット 2017-09-09 5.41.44.png" src="https://qiita-image-store.s3.amazonaws.com/0/25071/edf125fd-6028-86dd-dbcf-ba655f7b7baf.png">

追加後にデプロイをすると、デプロイ時に関連するパッケージがインストールされます。

# Rubyからchromeを呼び出してスクリーンショットをとる

ruby からはcapybaraとseleniumを使ってchromeを呼び出します。
Gemfileに追加してbundle installします。

```ruby
gem 'capybara'
gem "selenium-webdriver"
```

コードの流れは、chromeの設定をしてsessionを作成、sessionでurlを指定してwebページを訪れ、そこでスクショをとります。
session.visit後に少し待たないとchromeが画面をrenderする前のスクショがとれる場合があるのでまっています。

```ruby
    require 'capybara'
    require 'selenium-webdriver'
    
    base_args = %w{headless no-sandbox disable-gpu}

    chrome_bin =  "/app/.apt/usr/bin/google-chrome"
    chrome_opts = chrome_bin ? { "chromeOptions" => { "binary" => chrome_bin, 'args' => base_args } } : {}

    Capybara.register_driver :chrome do |app|
      Capybara::Selenium::Driver.new(
        app,
        browser: :chrome,
        desired_capabilities: Selenium::WebDriver::Remote::Capabilities.chrome(chrome_opts)
      )
    end

    Capybara.default_driver = :chrome

    @session = Capybara::Session.new(:chrome)

    @session.visit(url)
    sleep 5 # waiting for getting assets                                                                                                                                                                

    @session.driver.browser.manage.window.move_to(0, 0)
    @session.driver.browser.manage.window.resize_to(800, 1200)
    sleep 1

    @session.save_screenshot(cache_file)
    @session.driver.quit

```

# 日本語 font
Herokuの環境では標準では日本語フォントが表示されないため、文字が化けます。フォントを用意する必要があります。herokuはfontconfigに対応しているため、ソースの直下に.fontsを作成して、そこにttsのフォントをおくとそのフォントが使われます。 http://okoneya.jp/font/ で配布しているフォントを使いました。

# ソース
sinatraに組み込んだソース一式をこちらに置いておきます。

https://github.com/isamu/heroku-screenshot

# Herokuで確認
完成したものをこちらにデプロイしています。qiita上のページに限定してスクショをとるようにしています。urlを変更すれば、他のページのスクショも取れます。

https://heroku-screenshot.herokuapp.com/thumbnail?url=http://qiita.com/isamua/items/c6a2f2ae5e2b03ebca6e

![thumbnail.png](https://qiita-image-store.s3.amazonaws.com/0/25071/310ae45f-7569-8930-f226-076a6f1a4d04.png)
vscodeのjsxでemmet

1週間前にatomでemmetする記事を書きました。

http://qiita.com/akameco/items/78d7d36e1389321ce45a

しかし、ここ最近vscodeを使っているので、vscodeでemmetする設定を書きます。
vscodeにはデフォルトでemmetが入ってているので、jsx用に設定を追記するだけで済みます。
`⌘ + ,`で設定ファイルを表示し、以下を追記します。

```json
  "emmet.includeLanguages": {
    "javascript": "javascriptreact",
    "vue-html": "html"
  },
  "emmet.syntaxProfiles": {
    "html": {
      "attr_quotes": "single"
    },
    "jsx": {
      "self_closing_tag": true
    }
  }
```
GraphQLでpixivのランキング取得するAPI


graphqlの練習がてらexpressでpixivのランキングを返すgraphql APIサーバを書いてみました。
ここで遊べます。

[デモ](https://t.co/q0oVjDFEkz)

[![https://gyazo.com/9738386ac8554007cc5ec8aba5bfcde2](https://i.gyazo.com/9738386ac8554007cc5ec8aba5bfcde2.gif)](https://gyazo.com/9738386ac8554007cc5ec8aba5bfcde2)

[**akameco/graphql-pixiv-api**](https://github.com/akameco/graphql-pixiv-api)

実装は、expressにexpress-graphqlミドルウェアを与えるだけです。
引数のオプションの`graphiql`というのはデモのアレですね。
すごく出来がいいです。

```js
const graphqlHTTP = require('express-graphql')

app.use(
  '/graphql',
  graphqlHTTP({
    schema,
    rootValue: resolver,
    graphiql: true,
  })
)
```

あとは、引数にgraphqlのbuildSchemaで作成したスキーマを与えます。


```js
const { buildSchema } = require('graphql')

const schema = buildSchema(`
type User {
  id: Int
  name: String
  account: String
  profileImageUrls: ProfileImageUrls
}
type ProfileImageUrls {
  medium: String
}
type Tag {
  name: String
}
type ImageUrls {
  squareMedium: String
  medium: String
  large: String
}
enum Mode {
  day
  week
  month
  day_male
  day_female
  week_original
  week_rookie
}
type MetaSinglePage {
  originalImageUrl: String
}
type Illust {
  id: Int
  title: String
  type: String
  caption: String
  tags: [Tag]!
  imageUrls: ImageUrls
  width: Int
  height: Int
  totalBookmarks: Int
  user: User
  tools: [String]
  metaSinglePage: MetaSinglePage
}
type Query {
  ranking(mode: Mode = "mode"): [Illust!]!
}
`)

module.exports = schema
```

非常に手軽ですね。
スキーマを除けば30行に満たないコードです。

書いた感じ、ルーティングを考えずに型だけを考えればいいので、気持ち実装のコストが低く、もしかすると普通にAPI書くより高速に作れるかもしれないという気持ちもしてきます。


## 気持ち
まだ良く見てないですが、flowとかtypescriptと型を共有したい場合どう書くのでしょうかね。
そのあたりの実装について知見がある人は、是非教えて下さい。
また、何か議論があれば、コメント欄またはtwitterまでお願いします。

<blockquote class="twitter-tweet" data-partner="tweetdeck"><p lang="ja" dir="ltr">Graphqlの練習にpixivのランキングのgraphql APIサーバ建てた。適当にポチれば遊べる <a href="https://t.co/q0oVjDFEkz">https://t.co/q0oVjDFEkz</a></p>&mdash; 無職.js (@akameco) <a href="https://twitter.com/akameco/status/906198288897941506">September 8, 2017</a></blockquote>
<script async src="//platform.twitter.com/widgets.js" charset="utf-8"></script>
<blockquote class="twitter-tweet" data-conversation="none" data-cards="hidden" data-partner="tweetdeck"><p lang="ja" dir="ltr">補完クソ便利 <a href="https://t.co/hgoDIhCQgR">pic.twitter.com/hgoDIhCQgR</a></p>&mdash; 無職.js (@akameco) <a href="https://twitter.com/akameco/status/906198763504492545">September 8, 2017</a></blockquote>


<blockquote class="twitter-tweet" data-conversation="none" data-cards="hidden" data-partner="tweetdeck"><p lang="en" dir="ltr">github<br> <a href="https://t.co/PFga0kQg5y">https://t.co/PFga0kQg5y</a></p>&mdash; 無職.js (@akameco) <a href="https://twitter.com/akameco/status/906200400939724800">September 8, 2017</a></blockquote>



## 注意
pixivから返却されるjsonについては、まあ非公開なので、完全なスキーマを書いてません。
こういうラッパする場合は、リクエストからgraphqlの型を自動生成するのが王道っぽい感じがします。
このあたりも今後の課題といった感じですね。
Colemak配列も試してみた

今度はDvorak配列ではなく、Colemak配列を試してみました。
諸般の都合により、Ctrl+cなどの機能をアプリケーションの設定などで変えるなどが出来なかっためです。
前回の記事から一か月がたち、もうDvořákの指になってしまっていますが、切り替えていきたいと思います。

# Colemak配列とは？
以下のリンクを見ていただくと分かりやすいです。
[Dvorakのその先へ（その2）](http://qiita.com/miyaoka/items/4f363059e831bd003775)

まとめると、QWERTYを継承した配列で、移行コストを軽減した配列になっています。
また左手ショートカット群の維持が出来るようになっています。

配列の変更の仕方は[Dvorak配列を試してみた（Windows）](http://qiita.com/kyusque/items/245d90227e8df2ad25f0)を参考にしてみてください。

# Colemak配列への道

だいたい２から３週間くらいで指が慣れるので、それくらいを目途に今回もつづけて行こうかとおもいます。

Colemak配列はqwerty配列からの学習コストが低いというメリットがあります。
ただ今回筆者はqwerty配列を忘れてDvorak配列に慣れたのにも関わらず、またColemak配列へ移行しようとしているのでこのメリットは消え去っています。

# 結果

Dvorak配列の感想とColemak配列の感想のメモが出てきたのでそれを箇条書きにします。
執筆段階では完璧に忘れているのですが、当時の気持ちとして書き留めます。
「kが打ちやすくなった（重要）」と書かれていて、今となっては記憶がないのですが重要だったのでしょう。

## Dvorak配列の感想

* 読点、句読点が押しやすかった。
* UNIXでlsが打ちにくくなった
* コピペに関してはアプリケーションで設定できるので問題は無かった。
* -が小指で打てたのは割りとよかった。
* ：とか；が打ちにくい


## Colemak配列の感想

* 確かに交互に打っている感はある。
* 日本語が打ちやすくなった。
* ｋが打ちやすくなった（重要）
* 安心してコピペができる。
* pがDvorak配列と一緒


## 最終的にどうなったか

最終的に筆者はColemak配列でハイフンだけ右の小指に来るような設定になりました。
やはり、日本語がDvorakよりも打ちやすかったのが重要だったと思います。
実はハードウェア的にキーボード配列を変えているので、コピペが変わらないのは非常に使いやすいです。
TravisCIでFortranをCIする

#TravisCIとは？
githubと連携してCIを行ってくれるサービス。
パブリックのリポジトリの場合は無料で利用できる。

#FortranはTravisCIの対応言語に入っていない
対応言語を調べてみるとメジャーな言語はほとんど対応しているみたいで、使いやすそうです。

<img src="https://qiita-image-store.s3.amazonaws.com/0/158368/b339f594-a3e9-5103-c26f-6f31b068643b.png" width=50%>

ただ、Fortranが入ってないので、それには対応していないのかと思いました。
が、良く調べてみると、apt-getでコンパイラをインストールできる場合は問題ないみたいです。
とりあえずやってみました！

# GitHubにパブリックのリポジトリを作成

まず初めにGitHubに適当なリポジトリをパブリックで作成します。
パブリックなら無料でTravisCIを使うことが出来ます
![無題.png](https://qiita-image-store.s3.amazonaws.com/0/158368/811116c0-4edf-ac2e-c616-6d6ea54f1dbe.png)

# TravisCIでやること

1. https://travis-ci.org/ よりTravis CIに登録する
1. 登録後、レポジトリを有効化する

![無題.png](https://qiita-image-store.s3.amazonaws.com/0/158368/ebed54f5-87b5-e911-9c47-ce24db86822a.png)

# Fortranのプログラムを書く

ファイル名　test.f90

```{fortran}
implicit none
real(8),allocatable::x(:,:),y(:,:)
integer::i,j
allocate(x(5000,5000))
allocate(y(5000,5000))

        do i=1,5000
                do j=1,5000
                        x(j,i)=0.0D+0
                        y(j,i)=dble(i)
                enddo
        enddo
        do i=1,5000
                do j=1,5000
                        x(j,i) = x(j,i)+y(j,i)
                enddo
        enddo
        write(*,*)x(5000,5000)
end
```

# TravisCI用の設定ファイルを書く
ファイル名　.travis.yml

```
addons:
  apt:
    packages:
    - gfortran
script: 
  - gfortran test.f90  && ./a.out
```

apt-getであらかじめインストールしておきたいものはpackages:の下に書いておくとテスト前に自動でインストールしてくれるみたいです。apt-getはubuntuのyumコマンドみたいなやつです。

テスト内容はscript:の下に書くとやってくれるみたいです。コンパイル後、実行するようなファイルを書きました。

![無題.png](https://qiita-image-store.s3.amazonaws.com/0/158368/4f57cda7-5cf7-85bc-7e3b-b4550ddbfe61.png)

# 適当なコミットを作ってプッシュする
push時に自動でテストしてくれるので適当にコミットしてpushします。

```
$ git add -A
$ git commit -m 'Testing Travis CI'
$ git push
```

# 結果

push後、もう一度https://travis-ci.org/ に行けば、このような感じでテストができています。

![無題.png](https://qiita-image-store.s3.amazonaws.com/0/158368/bf923201-50bd-65af-464b-d14337ee5d94.png)

# まとめ

TravisCIに関して、言語が指定されていたので、特定の言語しかできないのかな？と思っていました。
しかし、実際に触れてみるとそんなことはなく、自由度高く設定することが出来るみたいです。
テスト後のビルドをリリースページにデプロイすることも出来るみたいです。
結構使いやすく感じたので今後積極的に使っていこうと思います。

# 参考

* [Travis CI | ド素人のための使い方 (公式ガイドより)](http://qiita.com/YumaInaura/items/8021d38cb202950fb18c)
* [GitHubと連携できる継続的インテグレーションツール「Travis CI」入門](http://knowledge.sakura.ad.jp/tech/3754/)
[rspecメモ]チェーンの順番が変更されていないかチェック

以下のようなメソッドやスコープの処理のチェーンの順番をチェックしたいときは、

```rb
class Teston < ApplicationRecord
  〜省略〜
  scope :hogehoge, -> hoge, limit: 3 do
    joins(:hoge)
      .where(ids: hoge)
      .where.not(id: piyo)
      .order_by_fugafuga
      .fugapiyo
      .limit(4)
  end
  〜省略〜
end
```

こうする:hugging_face:

```rb
  expect(Teston).to receive_message_chain(
    :joins,
    :where,
    :where, :not,
    :order_by_fugafuga,
    :fugapiyo,
    :limit
  )
  Teston.hogehoge(hoge)
```

receive_message_chain内で順番にシンボルを並べれば、
並び順をチェックできます。

#注意

長いメソッドチェーンはデメテルの法則の反するので、できれば避けましょう。
避けられない場合は入出力のテストに加えて、
今回示したようなチェーンの順番を確認するようなテストもあると、
テストパターンの抜け漏れをカバーできるかもしれません:rocket::moon:
CentOS設定記録5 ssh鍵変更編

#はじめに
Linux初心者の設定記録
思いついた順で設定していきます

[設定記録1](http://qiita.com/ka_iwashita/items/aff837a2155a47416844)：IDCFクラウド登録～ssh接続
[設定記録2](http://qiita.com/ka_iwashita/items/6c625d7d57f1323a7c8c)：ログインユーザー作成～rootのSSH接続禁止
[設定記録3](http://qiita.com/ka_iwashita/items/de33d59721a7f349224f)：Apacheサーバー設定～DNS設定まで
[設定記録4](http://qiita.com/ka_iwashita/items/db33c3c37d4ad2e98622)：Digest認証導入
の続き

#今回の目的
- sshの設定変更

#sshの認証と通信
公開鍵・秘密鍵を使った認証で、ハッシュ関数で使う乱数シードを受け渡し。
以後はそのシードをもとに通信をやり取りする、という理解。
いまいち理解しきれていないが、いったんはその理解で進める。またいずれ調べる。

#ssh認証
##現状
- IDCFクラウド登録時に生成したSSH認証鍵はRSAのkey size 1024bit<br>
`ssh-keygen -l -f /home/username/.ssh/authorized_keys`<br>
`1024 54:03:ec:4b:15:98:85:c7:8d:88:29:72:06:83:28:9c   (RSA) #結果 1024bitのRSA`
- ググったらSSH認証で使用されるもので多いのはRSAの2048bit
- 1024bitでもすぐに危ないという感じではなさそうだが、あまりよろしくはなさそう

#暗号アルゴリズムの安全性
IPA 発行の[SSL/TLS 暗号設定 ガイドライン](https://www.ipa.go.jp/files/000045645.pdf)のP13に暗号アルゴリズムの安全性について記載あり
SSLではないけれど、暗号アルゴリズムの安全性ということでは同様のはずなので、新アルゴリズムはここを参考に選ぶ

- RSA 1024bitはビット安全性が80 ビット、つまり2^80の計算量で暗号ができる
- RSA 4096bitでもビット安全性は128～192ビットの間

RSAとは違うECDSA という暗号アルゴリズムも利用できる。
ECDSA 521bitはRSAの15360bitに匹敵するビット安全性らしい。
一定以上のkey sizeなら暗号速度がRSAより早くなるらしい。
また、521なのは512のtypoではなく、速度向上のためらしい。

ということでECDSA 521bitで設定してみることにする。



抜粋

| ビット安全性 | 暗号スイート |
|:-:|:-:|
| 80 ビット | RSA-1024<br>ECDSA-160 |
| 112 ビット | RSA-2048<br>ECDSA-224 |
| 128 ビット | ECDSA-256 |
| 128 ビット<br>～<br>192 ビット | RSA-4096 |
| 192 ビット | ECDSA-384 |
| 256 ビット | ECDSA-521 |


#ECDSAでの鍵生成

```bash:BashOnWindows
ssh-keygen -t ecdsa -b 521 -N ""
# -t でアルゴリズム指定 -b でkey size指定 -Nでパスフレーズ指定
#ファイル名はid_ecdsaがデフォルト設定なのでそのままEnterすれば ~/.ssh/id_ecdsa とecdsa.pubができる

#作った公開鍵をサーバーへ転送
scp -i ~/.ssh/id_rsa -P 2222 ~/.ssh/id_ecdsa.pub username@example.com:~/.ssh/

#サーバーへ接続
ssh idcfCloud
```
```bash
#まずは現在の公開鍵をバックアップ
cp ~/.ssh/authorized_keys ~/.ssh/authorized_keys.old
#公開鍵を上書き
cat ~/.ssh/id_ecdsa.pub > ~/.ssh/authorized_keys
```
```bash:BashOnWindows上で実行
#ecdsaでssh認証できるか確認
ssh -i ~/.ssh/id_ecdsa username@example.com -p 2222
```

認証に問題なければバックアップファイルとRSAの秘密鍵は削除してOK
`rm ~/.ssh/authorized_keys.old`

SSH接続用configファイルも書き換える

```bash:BashOnWindows上で実行
vim ~/.ssh/config
```
```bash
#IdentityFile ~/.ssh/id_rsa #コメントアウト
IdentityFile ~/.ssh/id_ecdsa #追記
```

これで行けるはず。
ダメならsshdのrestartや、サーバー側の~/.ssh/authorized_keysのパーミッションが600になってるか確認
`systemctl restart sshd.service`
`chmod 600 ~/.ssh/authorized_keys`

#セキュリティ

暗号方式について調べたときに知った副産物

```bash:/etc/ssh/sshd_config
#HostKey /etc/ssh/ssh_host_rsa_key #コメントアウト
AddressFamily inet #IPv4のみ
AllowUsers username #認証ユーザー指定、複数ユーザーはスペース区切り username username2
```

#参考URL
いろいろssh設定について書いてある
http://www.nca.gr.jp/imgs/nca_ssh_server_config_v01.pdf

P13にビット安全性の一覧表がある
https://www.ipa.go.jp/files/000045645.pdf

http://labunix.hateblo.jp/entry/20160228/1456586770
https://blog.ayurina.net/2016/07/15/ssh%E9%8D%B5%E3%81%AE%E6%9A%97%E5%8F%B7%E5%8C%96%E6%96%B9%E5%BC%8F%E3%82%92%E5%BC%B7%E5%8C%96%E3%81%97%E3%81%A6%E3%81%BF%E3%81%9F%E3%80%82/
https://wiki.archlinuxjp.org/index.php/SSH_鍵
http://qiita.com/suthio/items/2760e4cff0e185fe2db9
ansibleでmysqlのreplicationを設定する

mysqlのreplicationをansibleでやったのでメモ。

### mysqldumpをとる

dumpしてローカルにデータを落として来てる。今回はDBば小さかったので、これでよかったけど、サイズが大きい場合はあらかじめサーバ側でやっておく。 my.cnfとかはあらかじめ配布されてる前提です。

```
- hosts: [ master ]
  become : yes
  tasks:
    - mysql_db:
        state: dump
        name: all
        login_user: USER
        login_password: PASS
        target: /tmp/dump.sql
    - name: get sqldump to local
      local_action: shell scp -r {{ inventory_hostname }}:/tmp/dump.sql ./
```


### dbへdumpをインポート、replの設定をする
```
- hosts: [ master ]
  become : yes
  tasks:
    - name: get master status
      mysql_replication:
        mode: getmaster
        login_user: USER
        login_password: PASS
      register: result
    - debug: var=result
- hosts : [ slave ]
  become : yes
  vars_prompt:
    - name: mysqlfile
      prompt: "mysql.Fileを入力してください"
      private: no
    - name:  mysqlposition
      prompt: "mysql.Positionを入力してください"
      private: no
  tasks:
    - name: send sqldump
      local_action: shell scp dump.sql {{ inventory_hostname }}:/tmp/dump.sql
    - name: Import dump.sql
      mysql_db:
        state: import
        name: dump
        target: /tmp/dump.sql
        login_user: USER
        login_password: PASS
    - mysql_replication:
        mode: changemaster
        master_host: masterhost
        master_user: user
        master_password: pass
        master_log_file: "{{ mysqlfile }}"
        master_log_pos: "{{ mysqlposition }}"
        login_user: USER
        login_password: PASS    - mysql_replication:
        mode: getslave
        login_user: ROOT
        login_password: PASS
       register: result
    debug: var=result

#login_user, login_passwordは/root/.my.cnfを設定するならいらない
```

1.show master statusの表示
2.プロンプトにbinlogとpositionを入れる
3.dump.sqlのインポート
4. changemaster
5. start slave
6. show slave status

こんな感じの流れ。mysql.FIle、positionが結構微妙で、playbook内でgroupを超えた変数(グローバル)を宣言できないっぽいので、promptにしてみた。
昔やった時はもっとshellスクリプトを結構書かないといけない感じだったんですが、mysql_replicationのモジュールができて楽になった。

どうも、ansible描いてるとその場限りの感じが多くなるので、もうちょっと汎用化していきたい。
XBRLを読み込んで業績の変化を簡単に可視化してみる

# 概要

MarketHackに掲載されているようなグラフ↓を簡単に作れたらいいなぁと思い, 別途作成した有価証券報告書XBRLパーサーを使ってXBRLを突っ込むだけで業績グラフを吐くスクリプトを書いてみました.

[工業コモディティ価格堅調でテック・リソーシズが好調 - Market Hack](http://markethack.net/archives/52053665.html)
![MarketHack テック・リソーシズの株価](http://livedoor.blogimg.jp/hiroset/imgs/d/8/d8534b1c.png)

## コード

パーサーとして以下の自作クラスを利用します.

[UFOキャッチャーからXBRLをダウンロード&パースするクラスを作った - Qiita](http://qiita.com/sawadybomb/items/67059635545cf0a11c8e)

例として4686:ジャストシステムの2017年3月期有価証券報告書を使ってみます.

```py:
import numpy as np
import pandas as pd
from UfoDataReader.util.parser import UfoXBRLParser
from bokeh.io import show
from bokeh.models import ColumnDataSource, FactorRange
from bokeh.palettes import Spectral5
from bokeh.plotting import figure
from bokeh.transform import factor_cmap

ufoparser = UfoXBRLParser()

# target XBRL file
file = 'jpcrp030000-asr-001_E04996-000_2017-03-31_01_2017-06-23.xbrl'

xbrl = ufoparser.parse(file)
dei = ufoparser.parseDEI(xbrl)

# getting each years GAAP objects
contexts = ['Prior4', 'Prior3', 'Prior2', 'Prior1', 'Current']
gaaps = [ufoparser.parseGAAP(xbrl, context=context) for context in contexts]

# getting factors
share = np.array([float(gaap.shares_outstanding) for gaap in gaaps])
sale = np.array([float(gaap.netsales) for gaap in gaaps])
cf = np.array([float(gaap.cf_from_operating) +
               float(gaap.cf_from_financing) +
               float(gaap.cf_from_financing) for gaap in gaaps])

df = pd.DataFrame(
    dict(
        year=contexts,
        dps=np.array([float(gaap.dps) for gaap in gaaps]),
        eps=np.array([float(gaap.basic_eps) for gaap in gaaps]),
        cfps=cf / share,
        sps=sale / share
    )
)


# bokeh setting
years = contexts
factors = ['dps', 'eps', 'cfps', 'sps']

x = [(year, factor) for year in years for factor in factors]
amounts = sum(zip(df['dps'], df['eps'], df['cfps'], df['sps']), ())

source = ColumnDataSource(data=dict(x=x, counts=amounts))

p = figure(x_range=FactorRange(*x), plot_height=300, title=dei.company_name)

p.vbar(x='x', top='counts', width=1.0, source=source,
       fill_color=factor_cmap('x', palette=Spectral5, factors=factors, start=1, end=2))

p.y_range.start = 0
p.x_range.range_padding = 0.1
p.xaxis.major_label_orientation = 1
p.xgrid.grid_line_color = None

# open browser
show(p)
```

## 結果

こんな感じで出力されます.
Hoverを使ってtooltipなど付けると, よりよいかもしれません.
bokehは設定が豊富なのでまだまだ憶えるところが多いです.

![bokeh_plot.png](https://qiita-image-store.s3.amazonaws.com/0/89639/a6f7f17b-f38e-ef3e-f252-e5727cc464e7.png)
第1回 Friendly勉強会に参加してきました #Friendly勉強会

2017/08/31 [Friendly勉強会](https://friendly.connpass.com/event/63960/) の第1回に参加しました。参加してみての感想などを簡単に書いていきます。

## Friendlyとは？
テスト自動化を目的としたWindowsアプリの操作ライブラリです。ネイティブ、.NetのForm、WPFアプリケーションに対応しているようです。

## 何をやったか？
勉強会はハンズオン形式で参加者は説明を受けながらコードを打ち、わからなければ都度質問する、という形で進められました。今回はWPFアプリケーションを対象とし、「コントロールの特定方法」について学びました。以下、ハンズオンで記載したコードです。なお、ハンズオン資料は[こちら](http://www.codeer.co.jp/download/handson)からダウンロード可能です。

```c#:FriendlyTest.cs

// ウィンドウの特定 - バリエーション4つ
// 1. 最前面にあるウィンドウ
var main = WindowControl.FromZTop(_app);

// 2, 3. ウィンドウ情報を基に特定する - MainWindow.xamlに記載されている
main = WindowControl.IdentifyFromTypeFullName(_app, "WpfApplication.MainWindow");

main = WindowControl.IdentifyFromWindowText(_app, "Friendly Handson");

// 4. 現在操作中のアプリケーションのメインウィンドウ
var mainWindowCore = _app.Type<Application>().Current.MainWindow;
main = new WindowControl(mainWindowCore);

```

最初にウィンドウの特定方法について4パターン紹介して頂きました。どの方法でも操作対象アプリケーションのメインウィンドウを特定できますが、
`WindowText`を使った方法が良く使われるとのことです。アプリケーションのウィンドウ名は "Friendly Handson" ではなく、"FRIENDLY HANDSON" とすべて大文字になっていますが、
これは別途使用しているライブラリの関係でそうなっているのではないかということでした。そのため、`WindowText`を指定する時は WpfApplication の MainWindow.xaml にある`Title="Friendly Handson"`を参考にするのが良さそうです。

```c#:FriendlyTest.cs
// タブの特定
// logicalツリー：xamlファイルの木構造を取得する
var logicalMain = main.LogicalTree();

// AppVar => コントロールオブジェクトそのもの
// オブジェクトのポインタのようなものが入っているイメージ
AppVar tabCore = logicalMain.ByType<TabControl>().Single();
var tab = new WPFTabControl(tabCore);

// タブの操作
tab.EmulateChangeSelectedIndex(1);
tab.EmulateChangeSelectedIndex(0);

// 以下、テキストボックスの特定、コンボボックスの特定 と続いたが、ここでは省略
.
.
.
```

次にタブやテキストボックス、コンボボックスなど各種コントロールの特定・操作方法について紹介して頂きました。ここで、Friendly の大きな特徴である「対象プロセスのハッキング」が登場します。logicalツリーを使って MainWindow.xaml の木構造を取得した後、各コントロールを取得していきます。それを実現しているのが、`AppVar`クラスです。このクラスのオブジェクトには、コントロールオブジェクトのポインタのようなものが入っているイメージと説明を受けました。実際、`AppVar`オブジェクトの情報を基にタブを切り替えたり、テキストボックスから値を取得したり、といった各コントロールの操作や情報取得を体験することができました。

今回の勉強会では手を動かしたのはここまでで、最後に質問タイムがあって終了となりました。

## 所感
自分はWPFアプリケーションを触るのは今回初めてだったのですが、丁寧に教えて頂けたため楽しんでハンズオンを進めることができました。「対象プロセスのハッキング」がFriendlyの大きな特徴とおっしゃっていましたが、実際体験したことでその凄さを感じ、どうやって実現しているか興味もわいてきました。勉強会は今後も一回完結ものの形で継続的に行われるようなので、参加して理解を深めていきたいと思います。
Slackのローディングメッセージに何を表示させていますか？（ガイドラインを表示する）


# まえおき
Slackのローディングメッセージ（Loading Message）とは、Slackの画面ロード待ちの際に表示されるメッセージです。


![スクリーンショット_2017-09-08_23_41_13.png](https://qiita-image-store.s3.amazonaws.com/0/148986/03de53de-91d3-2bed-aff0-46842f754c6c.png "スクリーンショット_2017-09-08_23_41_13.png")

このメッセージは、何もしていなければSlack規定の英文メッセージが表示されますが、独自のメッセージを設定することもできます。

![スクリーンショット_2017-09-08_23_46_24.png](https://qiita-image-store.s3.amazonaws.com/0/148986/3fe8859e-3ad7-bfc1-1d2a-5d8e886e4d10.png "スクリーンショット_2017-09-08_23_46_24.png")

設定すると・・・

![スクリーンショット_2017-09-08_23_52_13.png](https://qiita-image-store.s3.amazonaws.com/0/148986/7e21368c-06d5-4737-f586-6e6ed23995fd.png "スクリーンショット_2017-09-08_23_52_13.png")


※補足
ローディングメッセージが表示される際は、登録した人のアカウント名とアイコンも表示されてしまいます。
Slackを利用している組織の規模や文化にもよりますが、私の関わっている組織では、ローディングメッセージを登録するためだけのマスコット的なアカウントを用意して、常にそのアカウントから登録しています。
そうすることで、誰が登録したかという情報が意識されずに、ローディングメッセージに注目されやすく、メッセージの登録も心理的に気軽になります。


# 本題

このローディングメッセージには、どんなメッセージが表示されるとよいのかなぁと、ずっと考えていました。

①社訓的なもの
②偉人の名言
③マンガやアニメなどの名台詞
④Slackの利用ガイドライン

など、これまでさまざまなメッセージ登録を試みてきました。
※①〜③はご想像いただけるかと思われるので、割愛します。今回は④のお話です。

## Slackの利用ガイドラインがオススメ

「④Slackの利用ガイドライン」は、テレビゲームなどでロード中に表示される操作ガイドや心得などを参考にしております。

たとえば下記のようなメッセージを登録しております。

* **チャット(文字)は感情や熱量が相手に伝わりづらく、誤解を招く恐れがあります。チャット上での相手への否定や叱責はせずに、大事なことは直接話しましょう。**

* **チャットで伝えることに固執せず、伝わりづらいものは直接話しましょう。チャットで2～3回同じ話が繰り返されている場合は、対面で話しましょう。**

ルール遵守＆周知徹底というほどでもないけれども、マナーとして意識してもらいたいようなお知らせについて、Slackのローディングメッセージを活用することで、自然に目にしてもらえる機会をつくれるのでオススメです。
※忘れた頃に思い出してもらえるといったリマインド効果もあります。



# あとがき


よそでSlackを利用されているチームでは、どんなローディングメッセージが設定されているのでしょうか。気になります。
もし、うちではこんなメッセージを登録しているよ、というのがありましたら、コメント欄に記載していただけますと幸いです。
mbed HRM1017の消費電力を下げる(USBライタを分離する)

HRM1017を電池で駆動しようとしていたのだが、どうしても10mA程度の電力が常に消費されている。
それもそのはず、mbed HRM1017はただのHRM1017のブレイクアウトボードではなくて
[LPC11U35](http://www.nxp-lpc.com/lpc_micon/cortex-m0/lpc11u00/)というCoretex-M0を積んだマイコンがついていて、ソフトの書き込みを行っている。

mbed HRM1017をはじめよう
https://developer.mbed.org/teams/Switch-Science/wiki/mbed-HRM1017をはじめよう

ここを見れば普通にそう書いてあるのだが(上記ページより参照図)・・・全く気づかなかったのでメモ。
![](https://developer.mbed.org/media/uploads/ytsuboi/hrm1017_block_chart_ja.png)

左側のLPC11U35がおそらく電池を食っているのでこれを切り離して電池駆動にしたい。よく見ればその方法もしっかり書いてあり、

>基板底面のソルダジャンパは、USB - レギュレータ - インターフェースチップの3V3と、BLEモジュール - ピンヘッダ の3V3をショートしてます。モジュール単体でバッテリ駆動したいときに、モジュールだけにピンヘッダから給電するときには、この底面のソルダジャンパのハンダを除いてください。
https://developer.mbed.org/teams/Switch-Science/wiki/mbed-HRM1017をはじめよう

とある。

ソルダジャンパ。。。？

![36963768041_0ea4929ba6_o.jpg](https://qiita-image-store.s3.amazonaws.com/0/59725/b7aa6ca0-a1a5-8707-fbef-9734b66f2246.jpeg)
どうやらこの右側小さな金属の膨らみのことを指すらしい。(写真は外したあとのもので、
外す前はぷっくりと膨らんでいます。)

はんだとはんだ吸取線を使い、このはんだを吸い取る。
無鉛はんだであるとおもわれるので、少々手こずる。

このソルダジャンパを取ると、いままでUSBからHRM1017に給電されていた線が切れることとなる。
<img width="359" alt="Screen Shot 2017-09-09 at 1.32.56.png" src="https://qiita-image-store.s3.amazonaws.com/0/59725/788823f7-9cd6-8a35-310a-37fe092bc07a.png">
回路図でみると、"SJ3"が今回外したジャンパにあたります。

これで、電池駆動をさせた際にLPC11U35の方に給電されることがなくなり、消費電力をかなり抑えることができる。(待機状態で1mA以下に。)

が、逆も然りで、USBを刺してもHRM1017への給電がなくなるで、ソフトウェアを書き込む際も、電池などでHRM1017に給電されていないとFAILします。
Python 3.6, Anaconda, Spyder使いに捧げるMayavi用の仮想環境構築

Python 3.6, Anaconda (Python 3.x), Spyderの環境下で、3D描画に特化したライブラリMayaviを導入する方法。

Mayaviは旧バージョンであるPyQt4を要求し、これと整合性を保つため(?)にもPython2.7の仮想環境を構築するのが手っ取り早いようです。




```
conda create -n py27mayavi python=2.7 pyqt=4 mayavi vtk spyder
```



ここではmayaviに必要な最低限のライブラリのみ記載しています。その他、必要なライブラリも適宜追加してください。




##仮想環境構築に際するチャンネルの問題
その後Mayavi用のSpyderが起動しないトラブルに見舞われましたが、チャンネルをconda-forgeからAnacondaに変更することで何故か解決しました。以下に成功した仮想環境設定を書いておきます。

```
conda create -n maya27 python=2.7 anaconda spyder mayavi pyqt=4 qt=4 vtk=6 matplotlib=1 --override-channels --channel anaconda
```

最後の```-override-channels --channel anaconda```がミソのようです[1]。
matplotlibのver=1はPyQtとの整合性を保つため(多分)、vtkのverは指定しなくていいかも。

この仮想環境にライブラリを追加するときも```-override-channels --channel anaconda```を忘れずに(もはや優先チャンネルをconda-forgeからAnacondaに設定し直したほうが早いかも。。)。

また、基本的に「動けばいいや」というスタンスなので原因については調べておりません。どうぞご容赦ください。。
【ここまで追記 (2018.07.18)】



##軸の表示に関するトラブルの解決
軸の目盛りを設定しようとすると何故かエラーが発生、カーネルがお亡くなりになられます。これはどうもmayaviのver4.5.0以降のバグのようです[2]。解決策は以下の通り。

<b> Step 1 </b>
"(Anacondaフォルダパス)/envs/(仮想環境名)/Lib/site-packages/mayavi" に移動

<b> Step 2 </b>
"modules" フォルダ内 "axes.py" の173行目

```python:  
self.configure_input_data(self.axes, src.outputs[0])
```

を

```python: 
data = src.outputs[0] if not hasattr(src.outputs[0], 'output') else src.outputs[0].output
self.configure_input_data(self.axes, data)
```
へと変更。

 <b> Step 3  </b>
"tools" フォルダ内 "decorations.py" の372行目

```python: 
axes.axes.ranges = axes.module_manager.source.outputs[0].bounds
```

を

```python: 
src = axes.module_manager.source
data = src.outputs[0] if not hasattr(src.outputs[0], 'output') else src.outputs[0].output
axes.axes.ranges = data.bounds
```

へと変更。


ただ参考サイト[2]の最後のほうを訳しただけですが・・。当方の環境ではこのやり方で解決し、今のところ順調に動いております。設定はなかなか面倒ですが、やはりMayaviで描く3Dプロットは美しいですね。
【ここまで追記2 (2018.07.18)】


##【参考にしたサイト】
[1] https://conda.io/docs/commands/conda-create.html
[2] https://github.com/enthought/mayavi/issues/474
AWX Installation (2017/09)


## 公式ドキュメント

https://github.com/ansible/awx


## やってみた

Jeff Geerlingさんのansible-galaxyのroleが利用しやすそうだったので活用
※2017/09時点でansible-galaxy内の唯一のawxタグのrole

https://galaxy.ansible.com/geerlingguy/awx/


### インストール

依存関係および対応OSについて明記してありかつ依存関係が簡単に解決できるようなドキュメントがあるため手順に従いインストール.

https://galaxy.ansible.com/geerlingguy/awx/#readme


※ awxレポジトリのgit cloneに結構時間がかかる

### ログイン

インストールしたホストの80番ポートにアクセスするとデフォルトでadmin/passwordで接続できる

![スクリーンショット 2017-09-09 0.43.34.png](https://qiita-image-store.s3.amazonaws.com/0/7625/3d1888b1-5420-9f4a-5a04-c72a6c7a75af.png "スクリーンショット 2017-09-09 0.43.34.png")

Ansible Tower的な感じキタ!!

![スクリーンショット 2017-09-09 0.44.27.png](https://qiita-image-store.s3.amazonaws.com/0/7625/4d5f5e80-171a-f27a-30da-93720b6b503a.png "スクリーンショット 2017-09-09 0.44.27.png")
【Tableau10.2以降】市区町村マップを簡単に作成する

#概要
Tableauで市区町村マップの表示が簡単にできたので書いときます。
現時点ではデフォルトで都道府県、郵便番号3桁でしかマッピングできず、ググっても難しそうなやり方しか出てこなかったのですが、Tableauが空間ファイルを扱えるようになったことでかなり楽にできました。

![Tableau市区町村マップ.jpg](https://qiita-image-store.s3.amazonaws.com/0/139176/60355f2d-2554-564d-4d22-58569326c6f3.jpeg)

#参考
http://qiita.com/shu_saito/items/95e96eea3a5f4e851a87

#環境
Windows10, Tableau DeskTop 10.3

#手順
1. 国土数値情報ダウンロードサービスの「GML(JPGIS2.1)シェープファイル」から「行政区域>全国」をダウンロードする
http://nlftp.mlit.go.jp/ksj/index.html

2. Tableauのデータソースで「空間ファイル」を選択し、1でダウンロードした中にある.shpファイルを選択する

3.メジャーの「Geometry」をダブルクリックする

行政区意外にもいろいろな区域のデータが置いてあるので分析し放題ですね。
Sympy 逆引きリファレンス


## LaTeX出力

```
In [59]: h_x
Out[59]: 
       2                          3
(x + 1) ⋅(x + 2)⋅(x + 3) + (x + 4) 

In [60]: latex(h_x)
Out[60]: '\\left(x + 1\\right)^{2} \\left(x + 2\\right) \\left(x + 3\\right) + \\left(x + 4\\right)^{3}'
```

## 式の展開

```
In [50]: f_x
Out[50]: 
       2                
(x + 1) ⋅(x + 2)⋅(x + 3)

In [51]: expand(f_x)
Out[51]: 
 4      3       2           
x  + 7⋅x  + 17⋅x  + 17⋅x + 6
```

## 因数分解

```
In [21]: g_x = x**2 + 2*x + 1

In [22]: factor(g_x,x)
Out[22]: 
       2
(x + 1) 
```

### 因数のリストを取得

```
In [21]: g_x = x**2 + 2*x + 1

In [22]: factor(g_x,x)
Out[22]: 
       2
(x + 1) 

In [23]: factor_list(g_x,x)
Out[23]: (1, [(x + 1, 2)])
```
http://docs.sympy.org/latest/modules/polys/reference.html?highlight=factor_list#sympy.polys.polytools.factor_list

## 積での因子分解

```
In [35]: f_x
Out[35]: 
 -2⋅x         
ℯ    ⋅sin(2⋅x)

In [39]: f_x.args
Out[39]: 
⎛ -2⋅x          ⎞
⎝ℯ    , sin(2⋅x)⎠
```

## 多項式の除算

```
In [25]: f 
Out[25]: x**2 + 4/x**2

In [26]: g = (x + 2/x)**2

In [27]: div(g, f)
Out[27]: (1, 4)

In [28]: q,r = div(g,f)

In [29]: h = q * f + r

In [30]: h
Out[30]: x**2 + 4 + 4/x**2

In [31]: g == h
Out[31]: False

In [32]: g.expand() == h
Out[32]: True
```
## 関数の変換

```
In [45]: f_x
Out[45]: 
   ⎛    π⎞
sin⎜x + ─⎟
   ⎝    4⎠

In [46]: f_x.rewrite(cos)
Out[46]: 
   ⎛    π⎞
cos⎜x - ─⎟
   ⎝    4⎠

In [47]: f_x.rewrite(tan)
Out[47]: 
       ⎛x   π⎞ 
  2⋅tan⎜─ + ─⎟ 
       ⎝2   8⎠ 
───────────────
   2⎛x   π⎞    
tan ⎜─ + ─⎟ + 1
    ⎝2   8⎠    

In [48]: f_x.rewrite(exp)
Out[48]: 
   ⎛     ⎛     π⎞      ⎛    π⎞⎞ 
   ⎜   ⅈ⋅⎜-x - ─⎟    ⅈ⋅⎜x + ─⎟⎟ 
   ⎜     ⎝     4⎠      ⎝    4⎠⎟ 
-ⅈ⋅⎝- ℯ           + ℯ         ⎠ 
────────────────────────────────
               2    
```

## 平面・空間ベクトル

行列で表示する方法もあるみたいだが、高校数学の範囲では `Point` でなんとかなる？

```
In [64]: Point([3,4])
Out[64]: Point2D(3, 4)
```

### スカラー倍

scaleで、各変数ごとにかける係数を指定すればいける。

```
In [65]: a = Point([2,-3])

In [70]: a.scale(3)
Out[70]: Point2D(6, -3)

In [71]: a.scale(3,3)
Out[71]: Point2D(6, -9)
```

### 距離

```
In [104]: a
Out[104]: Point2D(2, -3)

In [105]: a.origin
Out[105]: Point2D(0, 0)

In [106]: a.distance(a.origin)
Out[106]: √13

```

### 内積

```
In [92]: a
Out[92]: Point2D(2, -3)

In [93]: c
Out[93]: Point2D(4, 4)

In [94]: a.dot(c)
Out[94]: -4
```


### 直交方向ベクトル

```
In [108]: a
Out[108]: Point2D(2, -3)

In [109]: a.orthogonal_direction
Out[109]: Point2D(3, 2)

In [110]: a.dot(a.orthogonal_direction)
Out[110]: 0
```

## 確率

### サイコロの確率変数

```
In [1]: from sympy.stats import P, E, Die

In [2]: X = Die('X',6)

In [3]: X
Out[3]: X

In [4]: P(X>3)
Out[4]: 1/2

In [5]: E(X)
Out[5]: 7/2

In [6]: Y = Die('Y',6)

In [7]: E(X+Y)
Out[7]: 7

In [8]: P(X+Y>10)
Out[8]: 1/12
```

そのほかにも、コイン投げの確率分布とか、一様分布とか、だいたいは揃っている

http://docs.sympy.org/latest/modules/stats.html
udacity

#1 udacity 1-2

Quiz: Calculate And Format
In this quiz you're going to do some calculations for a tiler. Two parts of a floor need tiling. One part is 9 tiles wide by 7 tiles long, the other is 5 tiles wide by 7 tiles long. Tiles come in packages of 6.

How many tiles are needed?
You buy 17 packages of tiles containing 6 tiles each. How many tiles will be left over?
Remember to following the formatting guidelines above as you write your code.
クイズ：計算と書式
このクイズでは、タイラーの計算をいくつか行います。 床の2つの部分はタイリングが必要です。 1つの部分は9タイル幅で7タイル、もう1タイルは5タイル幅×7タイルです。 タイルは6のパッケージで来る。

いくつのタイルが必要ですか？
それぞれ6個のタイルを含む17個のタイルのパッケージを購入します。 いくつのタイルが残されますか？
上記の書式のガイドラインに従って、コードを記述することを忘れないでください。

google翻訳では以上になっているが意味不明である。

#私の解釈では、縦9タイル横7タイルの補修にかかる枚数は？

である。

print((9*7)+(5*7))
意地でもconstを使う方法

JavaScriptで`const`を意地でも使いたい方へ。
`try-catch`等でも`const`を使って代入を行う方法です。

# 前提条件
ES2015（の`const`）が使用できる環境。
なお、IE11でもconstは使用できるみたいです！わーい！
ただしArrow functionsは使用できないので、`function`文を使用してください。ひどいよー……。

# まえがき
`const`はES2015で追加された構文で、JavaScriptに定数という概念をもたらしました。
再代入を禁止したいので、できるだけ`const`を使いたいですよね。

しかし、問題となるのが`try-catch`等での代入処理。
`const` `let`ではブロックスコープとなるため、try文の中で変数宣言をすると、ブロックの外では変数の参照ができません。

そういった場面でも`const`を使いたいと人向けの内容です。

# ビフォーアフター

```js:Before
let fileContent;
try {
    fileContent = fs.readFileSync("/path/to/file");
} catch (e) {
    fileContent = "default value";
}
```

```js:After
const fileContent = (() => {
    try {
        return fs.readFileSync("/path/to/file");
    } catch (e) {
        return "default value";
    }
})();
```
## 解説
`try-catch`を即時関数で包んであげているだけです。
記述の仕方によっては上記のように行数が増えますが、`const`を使えるメリットと比べると些細なものですね。

## その他
### `switch-case`文
`return`を使用するため、`break`を書く必要がなくなります。
そのため、Scalaのパターンマッチライクな記述になり、かなり見通しが良くなります。

```js:before
let num = 0;
switch (flag) {
    case "A":
        num = 1;
        break;
    case "B":
        num = 2;
        break;
    case "C":
        num = 3;
        break;
}
```

```js:after
const num = (() => {
    switch (flag) {
        case "A": return 1;
        case "B": return 2;
        case "C": return 3;
        default : return 0;
    }
})();
```

### `if`文
三項演算子よりも見やすくなる……わけないですね。
今回の技を使わず、三項演算子を使ってください。
フレンズによって得意なこと違うから！

```js:bad
const bool = (() => {
    if (str === "str") {
        return "true";
    } else {
        return "false";
    }
})();
```

```js:good
const bool = (str === "str")
        ? "true"
        : "false";
```

### IE11
前述の通り、IE11ではArrow functionsが使えないため、IE向けにトランスパイルするか、`function`式を使用してください。

```js:IE11
const element = (function () {
    try {
        return document.getElementById("id");
    } catch (e) {
        return document.body;
    }
})();
```

# あとがき
軽くググっても出てこなかったので今回書いてみました。
これを使えば、ほとんど`const`でかけると思います。
もっといい方法などありましたら教えていただけると幸いです！

# 参考
- Can I use
    - const https://caniuse.com/#feat=const
    - Arrow functions https://caniuse.com/#feat=arrow-functions
macOS Sierra で bootcamp した後、sierraが起動しない -> 復旧できた。

#0. 私の環境
- MacBook Air 11 inch （おそらく） Late2013
- macOS Sierra 10.12.6 （以下sierra）

#1. 症状（経緯）
1. bootcampでwindows8.1（以下Win）をインストールした後、環境構築の為に数回再起動（自動的にWinが立ち上がるが問題ない。）
2. 一段落したので、 今度はsierraで起動しようとWin上のタスクトレイから「Mac OS X で再起動」を選択
![再起動](http://inforati.jp/images/2010/12/how-to-change-start-up-disk-between-mac-and-boot-camp-windows-2.jpg)
出典：http://inforati.jp/apple/mac-tips-techniques/windows-hints/how-to-change-start-up-disk-between-mac-and-boot-camp-windows.html
3. リンゴマークが出て、ユーザ選択のGUIが出現（ここまで正常）
![ログイン画面](https://qiita-image-store.s3.amazonaws.com/0/151205/b839cda0-9331-3186-e98a-3f167a56b461.png)
4. 自分のアカウント（左）を選び、パスワードを入力

### **ここから異常**
5.普段ならプログレスバーが出現するが…次の症状がランダムに発現

- リンゴマークが再び出現し、固まる（そのうちファンがうなりだす）
- 再びユーザ選択のGUIが出現し、固まる（同上）

こうなるど電源ボタン長押しで終了させるしかなくなる。

# 2. 試してみたこと（ダメだった）

こちらのサイトを参考に以下を進めた。
[【決定版】Macが起動しないときに僕がやってることリスト]
(https://blog.h-wd.info/2014/01/22/mac%E3%81%8C%E8%B5%B7%E5%8B%95%E3%81%97%E3%81%AA%E3%81%84%E3%81%A8%E3%81%8D%E3%81%AB%E5%83%95%E3%81%8C%E3%82%84%E3%81%A3%E3%81%A6%E3%82%8B%E3%81%93%E3%81%A8%E3%83%AA%E3%82%B9%E3%83%88/)

- NVRAM(PRAM)クリア
- SMCリセット
- セーフモードで起動する（起動できなかった）
- シングルユーザーモードで起動しディスクメンテナンスを実行する（起動できなかった）

最後の場合は、1度目のユーザ選択の直前に一瞬だけ
`BuildUser(): error building a user of type 0x20010008.`
が現れたのが見えたので、これを頼りに検索したら、[こんな感じのサイト](https://discussions.apple.com/thread/7474078?start=0&tstart=0)がヒット
なんかFileVaultを解除しないとダメらしい。
これの解除はよくわからなかった。が、`Cmd + R` にてリカバリーモードで起動し、ディスク・ユーティリティを一通り弄ったら解除できた（気がする、よく覚えていないすみません）。

ただし、FirstAidが直接改善に繋がったとは考えにくい（エラーは何も出なかった）。
色々なサイトを探したが、そもそもディスク・ユーティリティのUIがそもそも違う（古いOS）とかの記事しか無かったので断念。


# 3. 復旧（出来た手順）
ここまでで、`fsck` コマンドとかも意味ないことがわかっていたので、別のアプローチを取った。FileVaultって暗号化関連だから

**ログインパスワードを初期化すればいけるんじゃね？**

ってことでやってみた。[ここ](http://tokyo.secret.jp/macs/mavericks-reset-password.html)を参考に、パスワードの初期化を行う。

※ **macのユーザが紐付いたAppleID** と **インターネット環境** が必要です。

1. macをリカバリーモードで起動する（ `Cmd + R` を押したまま電源ボタンを押し、リンゴマークとプログレスバーが出たら全てはなす。）
2. 上の「ユーティリティ」だったかな？から `ターミナル` を起動。
3. `resetpassword` を入力Enter
4. 別GUIが立ち上がったら、ユーザ選択を行う（ユーザが1つしかない場合は選択済みかも）
5. ユーザアカウントと紐付いたAppleIDでログインする（WiFiに接続してないとかインターネットに繋がってない場合は接続する）
6. ユーザが認証されると、新しいパスワード等を入れるUIがでてくるので、入れる（ **古いパスワードと同じでもOKだった** ）
7. パスワード変更が適切に変更されたら、再起動。

ログインできたぁ。やったぁ〜〜

# あとがき
同じような症状がでた人がまあまあ居たにも関わらず、解決法が「リカバリー（初期化）しました（泣）」とかしか見当たらなかったので、（たまたまですが）リカバリーせずに回復できた情報を公開しようと思った結果のメモです。
肝心なところでスクショが無いのはごめんなさい…

要所要所で間違い等あるかもしれませんので、「それ違うのでは？」等のツッコミ、「この環境ではこうなった」等のご報告のコメントお待ちしております。

最後になりますが、
この記事に書いてることは私の経験だけなので、真似して復旧不能とかになっても一切責任取れません。
 **全て自己責任でお願いします** （わざわざ書くまでもないかも）
Unity で Lightmap のベイクが終わらないときに

Unity で Lightmap のベイクが終わらない場合のチェックポイントです。

とりあえず、[こちらの記事](http://tsubakit1.hateblo.jp/entry/2015/11/19/004627)のことを最初に確認します。

それでも、Unity のライトマップのベイクが終わらないというとき、以下を試すとなんとかなりました。

#### 開発環境
- Unity 5.6.2f1
- Windows 10 Pro 64bit / Intel Core i7-6700 3.40GHZ / RAM 16 GB

## 一度に大量にやらない
複数の Object を Static にする場合は、一度に行わず順番に Static をオンにしていく。
（一度にやるとメモリが足りなくなってスワップが起こったりしてほとんど進まなくなる？）

いったんプロセスが終わってベイクが成功したら、次のオブジェクトを Static にする前にセーブするのが無難です。

タスクマネージャーなどでメモリをフルに使い切って止まってないか確認してみるとよいです。

## Generate Lightmap UVs のチェックを on に
“5 / 11 Clustering Objects" という状態で止まるときは、インポートした Model で Generate Lightmap UVs のチェックを on にしてみる。

## Percomputed Realtime GUI Resolution の値を小さくする
“7 / 11 Light Transport “という状態で止まるときは、Lightmap parameter -> Percomputed Realtime GUI Resolution の値を小さくしてみる。
ラジオボタン・チェックボックスの大きさを変える

```index.html
<!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="utf-8">
  <link rel="stylesheet" href="style.css">
</head>
<body>
  <input type="checkbox" name="checkbox" /><label>チェックボックス</label>
  <input type="radio" name="radio" /><label>ラジオ</label>
  <input type="radio" name="radio" /><label>ボタン</label>
</body>
</html>
```

```style.css
input[type=checkbox] {
    width: 100px;
    height: 100px;
    vertical-align: middle;
}
input[type=radio] {
    width: 100px;
    height: 100px;
    vertical-align: middle;
}
```