OmniAICreator/Qiita-1.07M huggingface dataset:
Twilio Autopilot で英会話練習用BOTを作ってみた　その１

# はじめに

一年ぶりに投稿します、すーです。
この記事は、[Twilio Advent Calendar 2019](https://qiita.com/advent-calendar/2019/twilio) の記事です。
はじめにお断りしますが、申し訳ないことに途中までしかできていないので、その１としてあげさせてください！
年末年始に完成を目指したいと思います。

# なぜ英会話にAutopilot?

いきなり余談ですが、今年、ベル〇ッツさんに通ったり2回ほど海外出張に行ったり、そこで打ち合わせしたりブレゼンしてみたり、結構英語を話す機会に恵まれてたんですよね。
ところが英会話教室も終わってしまったし、今のところ次の海外出張の予定はないし、このままでは元の木阿弥になってしまう予感が。。。
でもまた英会話教室に通うお金はないし、オンライン英会話とか続く気が全くしない。

そこでもっと気軽に話せて、日本語なんて間違っても話さなくて、しかも自分好みにカスタマイズできる素晴らしい方が居たのを思い出しました！
そう、Twilio Autopilotさんです。

Autopilotには最初からテンプレートのBOTが用意されています。
「予約受付」とか「アンケート」など、サンプルの学習データ込みで準備されています。
おまけに、ブラウザからいきなり音声BOTを試せるシミュレーション機能まであります。
それらを利用すれば、
・音声認識エンジンに理解してもらえるレベルの英語の発音ができているか
・特定のシーンで一般的に使われる言葉で回答できているか
を意識しながら会話することができます。

もちろん、BOTが話す内容やトリガーする言葉などはいくらでもカスタマイズできますので、
・これまで覚えた英語のイディオムをちゃんと使えるか
をチェックすることができます。
いわゆるAI英会話BOTですね。


# 簡単なお試し方法
Twilioのアカウントをおもちなら、Autopilotの画面を開いて「Create a new Bot」ボタンを押してみてください↓
<img width="670" alt="さいしょ.PNG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272318/29108c67-eb73-7967-c73a-8d32bb9ab68d.png">

※お持ちでない方は[高橋さんのわかりやすい記事](https://qiita.com/mobilebiz/items/932eb21ff6ed36f524d8)がありますので是非そちらから！

たくさんのテンプレートBOTが表示されます
<img width="897" alt="２.PNG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272318/46ab47a7-d5cb-6554-228e-9038ebbd3a35.png">

今回は一番上、Appointment Schedulingを使ってみました。
BOTの名前などを入れてCreateボタンを押すと、タスク（＝BOTがやる仕事。英語でうまいこと話すとトリガーされてくれる）の一覧が表示されます。
<img width="886" alt="５.PNG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272318/7fe5a583-e95e-e964-b2ca-abd00157924e.png">

まずは深く考えずに「Simulator」をクリックしてみます。
<img width="451" alt="6.PNG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272318/63a7e49c-47a4-57e4-1faa-faa9efb4c25f.png">

真ん中の電話ボタンを押せば・・・英会話の始まりです！
優し気な男性が話しかけてくれます。（PollyのMatthewさん）

音声乗っけるのはあまりにも恥ずかしいので、同じシミュレーターで試せるテキストメッセージの方を乗っけておきます。
<img width="293" alt="１０.PNG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272318/32310333-b47f-5022-e888-7240d092941f.png">
<img width="293" alt="12.PNG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272318/ca96ba55-18bf-7709-ee0e-3fc36f116ced.png">

テキストメッセージでシミュレートすれば、右側にどのタスクがトリガーされたのか、変数にどの値を入力したのか、確認することができます。
<img width="711" alt="13.PNG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272318/11c87a8b-46d0-6ca4-2fcd-2991917d2bb0.png">


# Let's カスタマイズ・・・？

Tasks>Programをいじれば、自分で自由にBOTをカスタマイズできるはず、と思ったのですが。
<img width="886" alt="まっしろ.PNG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272318/b78f90e4-8945-7d8b-baa7-c947c4321add.png">
なぜか今現在、真っ白表示です。
F12を押してみるとエラーが。
<img width="931" alt="ERROR.PNG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272318/9a32a533-790c-8205-cb25-4f68d65c38ef.png">
ちょっとまずげな感じですね。

というわけで一旦この記事はここまでです。
コンソール直り次第続きを作ってみたいと思います！
TensorFlowで安倍乙と石原さとみの顔認識をやってみた

# はじめに
- ずっと前に、`TensorFlow` で `MNIST` のチュートリアルをやりました。その後、何か関連アプリケーションを作りたかったが、時間がすぎました。
- 今回、題材として `安倍乙` さん、`石原さとみ` さんが似ているとの話があり、識別をしてみるアプリケーションを作りました。
- あくまで、遊びの範囲でしたが、一連の流れを理解出来たのは良かったです。
- `MNIST` を元にしたので、その他の方々8人にも登場して頂きました。
- アプリケーションは https://abe-or-ishihara.herokuapp.com/ です。


# アプリケーション
- アプリケーションは、`TensorFlow` `Django` `OpenCV` `Pillow` `Heroku` `S3` 等々を利用しています。

![predict.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/68632/d377f0aa-803d-0a30-6703-3710fc69e8e5.gif)


# 概要
- アプリケーションに至る一連の作業工程になります。結構色々やる事がありました。
- かなり辛かった箇所は、#4の顔画像の選別ですね。当初は、`Mac` の `Finder` で作業していましたが、辛すぎたので、`Flask` の簡易管理アプリを作りました。

![スクリーンショット 2019-12-22 0.29.48（2）.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/68632/77213a1a-6891-d398-1532-38bfae319416.png)


# 登場人物
- 安倍乙さん、石原さとみさんは、今回の顔認識の主役です。また、その他の方々は、私的に注目している方々です。ご了承下さい！
- 安倍乙
- 石原さとみ
- 大原優乃
- 小芝風花
- 川口春奈
- 森七菜
- 浜辺美波
- 清原果耶
- 福原遥
- 黒島結菜


# 記事一覧
- [Google カスタム検索エンジンで画像リンクを取得する](https://qiita.com/maeda_mikio/items/bf6e0686db489a4bf67b)
- [URLを記載したテキストファイルから画像をダウンロード](https://qiita.com/maeda_mikio/items/43370ba00fcd7d4c0592)
- [OpenCV Haar Cascades で顔認識](https://qiita.com/maeda_mikio/items/58ce4eb5f31c59099872)
- [ダウンロード画像と顔画像の簡易管理アプリ](https://qiita.com/maeda_mikio/items/c283ba78dc88175ce100)
- [学習画像の水増し](https://qiita.com/maeda_mikio/items/7c8d029680d18c242994)
- [学習に利用する画像のデータセットを作成する](https://qiita.com/maeda_mikio/items/02437029fe89df9cc6e0)
- [データセットのローダーの作成](https://qiita.com/maeda_mikio/items/c55855cd7371ee4cf5b1)
- [学習モデルの作成、学習と推論](https://qiita.com/maeda_mikio/items/c68c612a9820501de68f)
- [FlaskとTensorFlowを利用した、顔画像の推論](https://qiita.com/maeda_mikio/items/a0e611249b74efa0e186)
- [DjangoとTensorFlowを利用した、顔画像の推論](https://qiita.com/maeda_mikio/items/9a5e722b1248091401ba)
- [HerokuとTensorFlowを利用した、顔画像の推論](https://qiita.com/maeda_mikio/items/99d614f1d79e03ef9028)


# おわりに
- `TensorFlow` 等を使った一連の流れを把握し、アプリケーションを作ってみました。
- 正直、`Google Cloud AutoML` であっという間に終わる件だと思いつつ、意味があるんだろうか？と悩む事もありました。
- なんか、私には遠い世界に思えたってのが、正直なところです。システムの下側、横側から機械学習等を支えて行ければと思います。
【Hyperledger Fabric】Fabricのコンテナ群とSDKアプリを別々のマシンで動かす時の注意点

#はじめに
Fabricのコンテナ群とSDKアプリを別々のマシンで動かす時の注意点を書きます。
今回は[fabric-samples](https://github.com/hyperledger/fabric-samples)の`first-network`をネットワーク設定に用いるものとします。
fabric-node-sdkを使ったSDKアプリはdockerコンテナとして動いています。

状況を表したものが以下です。
マシン2ではCAやordererも動作していますが、図からは除いています。
<img width="1088" alt="スクリーンショット 2019-12-21 23.47.47.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/326169/0b837f80-c900-9c59-b809-82a0597b99d7.png">

#設定
SDKアプリを使用する際に用いるconnection profileは以下になります。

```
{
    "name": "first-network-org1",
    "version": "1.0.0",
    "client": {
        "organization": "Org1",
        "connection": {
            "timeout": {
                "peer": {
                    "endorser": "300"
                }
            }
        }
    },
    "organizations": {
        "Org1": {
            "mspid": "Org1MSP",
            "peers": [
                "peer0.org1.example.com",
                "peer1.org1.example.com"
            ],
            "certificateAuthorities": [
                "ca.org1.example.com"
            ]
        }
    },
    "peers": {
        "peer0.org1.example.com": {
            "url": "grpcs://マシン2のipアドレス:7051",
            "tlsCACerts": {
                "pem": "-----BEGIN CERTIFICATE----------END CERTIFICATE-----\n"
            },
            "grpcOptions": {
                "ssl-target-name-override": "peer0.org1.example.com",
                "hostnameOverride": "peer0.org1.example.com"
            }
        },
        "peer1.org1.example.com": {
            "url": "grpcs://マシン2のipアドレス:8051",
            "tlsCACerts": {
                "pem": "-----BEGIN CERTIFICATE----------END CERTIFICATE-----\n"
            },
            "grpcOptions": {
                "ssl-target-name-override": "peer1.org1.example.com",
                "hostnameOverride": "peer1.org1.example.com"
            }
        }
    },
    "certificateAuthorities": {
        "ca.org1.example.com": {
            "url": "https://マシン2のipアドレス:7054",
            "caName": "ca-org1",
            "tlsCACerts": {
                "pem": "-----BEGIN CERTIFICATE----------END CERTIFICATE-----\n"
            },
            "httpOptions": {
                "verify": false
            }
        }
    }
}
```

invokeやqueryの際にfabricのネットワークに接続する処理は以下のようになります。
`asLocalhost`を`false`にしておかなければいけません。

```
await gateway.connect(ccpPath, { wallet, identity: 'user1', discovery: { enabled: true, asLocalhost: false } });
```

そして肝がSDKコンテナのdocker-composeファイルです。
SDKアプリがコンテナではない場合も、マシン1でドメイン名の解釈を以下のように設定する必要があります。

```:docker-compose.yml
extra_hosts:
      - "peer0.org1.example.com:マシン2のipアドレス"
      - "peer1.org1.example.com:マシン2のipアドレス"
      - "peer0.org2.example.com:マシン2のipアドレス"
      - "peer1.org2.example.com:マシン2のipアドレス"
      - "orderer.example.com:マシン2のipアドレス"
```
#参考記事
- https://stackoverflow.com/questions/56885082/endorsement-fails-when-node-js-fabric-client-application-is-run-on-a-separate-no
書評：カイゼンジャーニー

# はじめに
書籍「カイゼンジャーニー」を読みました。
自分にとって紛れもない良書でした。
書籍だけの学びはすぐ流れてしまうので、感想文を残しています。
(ネタバレに当たる内容があるかもしれないので、ご注意願います。)

![Amazon](https://m.media-amazon.com/images/I/71fBpU884fL._AC_UL640_FMwebp_QL65_.jpg)

# 第1部 一人から始める
主人公(江島)が一人であれこれアジャイル開発の手法を試みて、
最後に一人の限界を感じるところで終わる部です。

「分割して、統治せよ」という言葉が印象に残ってます。

### 取り扱っている主なプラクティス
- タスクマネジメント、タスクボード、朝会、ふりかえり
- 緊急・重要のマトリクス
- 1on1

*仕事をよりうまくやるためには一体何からやったら良いか？と聞かれることは少なくない。
そのとき、私が挙げるのは次の4つ、タスクマネジメント、タスクボード、朝会、ふりかえりだ。
なぜ、この4つなのかというと、仕事のカイゼンは、まず状態の見える化から始めるべきだからだ。*

*4つのプラクティスのうち、時間がないとふりかえりを最初にやらなくなることが多い。
しかし、私としては他の3つよりもむしろ、ふりかえりだけは続けることようにした方が良いと考えている。
ふりかえりがなければ、仕事のやり方に向き合い、より良くする機会を失ってしまうからだ。*

# 第2部 チームで強くなる
個人的に印象深い部でした。
話の流れの中でそれまで続けていたある取り組みを止めるのですが、
個人的に最近考えている
「アジャイル開発とはアジャイル開発のプラクティスを行うことではなく、チームがそういう状態になることではないか？」
という問いに答えてくれた気がします。

アジャイルな状態になるためにはどうしたら良いのか？という問いには、
「開発メンバーが開発する時間を多く取れるように各プロセスを効率化すること」
もあれば、
「メンバーが各々の強みを生かせるように星取表を作って、強み弱みを共有すること」
もあると思います。あるいは、
「誰かが仕様の窓口になって、メンバーは開発に集中できるようにすること」
かもしれません。

開発で成果を出さないといけないので、まずは時間を確保するのが第一かもしれません。
質を保持しないと後半で失速するのでレビューの時間を綿密に持つことが必要なのかもしれません。
詰まるところ、フレームワークはないので目的の状態に達するためにプラクティスを維持する必要はないのだと思いました。

### 取り扱っている主なプラクティス
- スクラム(スプリント、スプリントプランニング、デイリースクラム、スプリントレビュー、スプリントレトロスペクティブ)
- インセプションデッキ
- Working Agreement
- ドラッカー風エクササイズ
- ファイブフィンガー
- リファイメント
- 狩野モデル
- むきなおり
- 星取表(スキルマップ)
- モブプログラミング
- バリューストリームマッピング
- カンバン
- ポストモーテム
- タックマンモデル

*チームやプロジェクトが立ち上がるチームビルディングの初期段階で、
星取表を作成するのが良いだろう。
これまで紹介した3つの取り組みをセットにすることでプロジェクトとチームメンバーとスキルが一気に共有できる。
チームビルディング三種の神器だ！
・インセプションデッキ: プロジェクトやプロダクトの目的や方法論
・ドラッカー風エクササイズ: チームメンバーの価値観
・星取表: 目的を達成するために必要なスキル*

# 第3部 みんなを巻き込む
主人公が自身がリーダーを務めるPJを成功に導くために
あらゆるステークホルダーとの交渉・折衝を行っていくのがこの部のメインだと思います。
スーパーSEというかコンサルというかかなり難易度が高く勇気がいる行動を繰り返しています。
(ただ、真に優れたリーダーやPMの取る行動ってこれなのかなとも思いました...)

多分、一つ一つを実践するだけでも相当難しいですが、
大事なのは度々出てくる言葉「越境」なのかなと思います。

### 取り扱っている主なプラクティス
- リーダーズインテグレーション
- モダンアジャイル
- プランニングポーカー
- パーキンソンの法則
- CCPM
- スクラムオブスクラム
- デイリーカクテルパーティー
- ユーザーストーリー
- 仮説キャンバス
- ユーザーストーリーマッピング
- MVP
- ユーザーインタビュー
- SL理論
- ハンガーフライト

# まとめ
各部ごとに印象に残った部分の感想をまとめましたが、
自分にとっては「越境」という言葉が全てだったのかもしれません。
おそらく誰しもが自分が大変な時に相手の越境を受け入れたり、
自分から越境することを行うのは難しいことだと思います。

越境か境界線を引くかは普段の業務の中でも常にせめぎ合いですが、
エンジニア経験の中で「越境」出来たプロジェクトが楽しく、
自分自身が評価をいただけたことが多いので、
2020年は「越境」をキーワードに頑張ろうかと思えました。
CentOSにプリインストールされたnodejsとnpmをアップデートする

nvmとかだとログインしてるユーザごとにパスが通らないといけなくて手間だったのでプリインストールされてるnodeとnpmをアップデートした

```sh
docker run -w /root --rm -it --entrypoint /bin/sh centos:centos7
```

```sh
# node.jsのv10をインストール
curl -sL https://rpm.nodesource.com/setup_10.x | bash -
yum remove nodejs npm
su
yum install nodejs -y
```

```sh
# 確認
bash-4.2# node -v
v10.18.0
bash-4.2# npm -v
6.13.4
bash-4.2#
```
simple_nested_form_for の子 & 孫関係で動的にフォームを追加する


## モデリング
```app/models/user.rb
class User < ApplicationRecord
  has_many :articles, :dependent => :destroy
  accepts_nested_attributes_for :articles, allow_destroy: true
end
```

```app/models/article.rb
  belongs_to :user
  has_many :cmments, :dependent => :destroy
  accepts_nested_attributes_for :comments, allow_destroy: true
```

```app/models/comment.rb
  belongs_to :article
```

- `article`をまとめて設定する為には、親要素の`User`に対して、`accepts_nested_attributes_for `を記述。
- `comment`をまとめて設定する為には、親要素の`Article`に対して、`accepts_nested_attributes_for`を記述。

こうすることで、孫要素までnested_formを使うことが可能。
- allow_destroy: true　としていないと子項目の削除ができないようになっています。


# controller
```users_controoler.rb
def new
  @user = User.new
  @article = @user.articles.build
  @comment = @article.comments.build
end

private
  def user_params
    params.requrie(:user).permit(:name, :email, articles_attributes: [:id, :description, :_destroy,
                                                         comments_attributes: [:id, :comment, :_destroy]])
  end
```

- 合わせてストロングパラメーターの _destroy も入れておく必要がある（入れないと削除できない）
- 子要素は親要素のストロングパラメーターに含めて記述できる(孫要素もこちらにまとめて記述する)
- 基本的に、newのページ以外でも必ずbuildして、インスタンス変数を作成しておく必要がある。

```new.html.haml
    = simple_nested_form_for @user, url: ~~~~path do |f|
      = f.simple_fields_for :comments do |f|
        = f.text_field :comments
      = f.link_to_remove '削除'`
      = f.link_to_add '追加', :shift_patterns
      = f.submit '保存'
```

こんな感じで書いてやれば、ちゃんと動くはず。
あとは、`create`のアクションも`users_controller.rb`に追加してやれば動くはず。

```application.js
  //= require jquery
　//= require jquery_ujs
　//= require jquery-ui
　//= require jquery-ui/i18n/datepicker-ja
  //= require remodal.min
  //= require activestorage
  //= require serviceworker-companion
  //= require jquery_nested_form　← 
```
`//= require jquery_nested_form`
`require jqurey`のあとに入れてやらないと動かないので注意！！

## 参考
https://qiita.com/obmshk/items/0e942177d8a44091bf09
今回はこちらの記事を参考に書いています。


# 最後に
- 普通なら、jquery などで、追加や削除の記述をしないといけない。
- updateとcreateを同時に実行するとき調べると、かなりややこしいことをしないといけなさそうだった。
- そんなときにめちゃくちゃ便利でした。記述も簡単なので実際に使ってみるとすごい楽なので是非つかってください。
herokuでビンゴ作ってherokuボタン付けた話

Heroku Advent Calendar 2019 の２１日目の記事です

# ビンゴ作ったよ
12月13日にあった[heroku meetup](https://herokujp.doorkeeper.jp/) で使ったビンゴアプリを作りました


アプリはこちら　https://heroku-binbinbingo.herokuapp.com/

リポジトリはこちら　https://github.com/sizukutamago/heroku-bingo

ぜひイベントとかで使ってみてください！

# herokuボタンも付けたよ
herokuボタンを付けて誰でもデプロイできるようにしました
とういうことで作り方紹介

https://devcenter.heroku.com/articles/heroku-button

rootディレクトリに `app.json` を作るだけで設定は終わりです
githubのリポジトリはOPENである必要があります

```json
{
"name": "binbinbingo!",
"description": "bingoです",
"repository": "https://github.com/sizukutamago/heroku-bingo", // githubのrepository
"keywords": [
  "php",
  "laravel",
  "vue",
  "bingo"
],
"scripts": {
  "postdeploy": ""  // deploy後に実行するコマンド
},
"env": {                                              // 環境変数
  "DB_CONNECTION": {
    "value": "pgsql"
  },
  "APP_ENV": {
    "value": "production"
  }
},
"addons": [
  "heroku-postgresql"    // 必要なアドオン
],
"buildpacks": [
  {
    "url": "heroku/nodejs"
  },
  {
    "url": "heroku/php"
  }
]
}
```

あとは `https://heroku.com/deploy?template=[githubリポジトリのURL]` にアクセスするとherokuデプロイできます!
意外と知らない(?)pythonの豆知識

#python 豆知識
詳しいことはここでは書きません。自分で調べてください。僕が伝えたいのは、こんなこと出来るよ！って紹介です。
###指定したkeyでのsort
なんだそれ？って感じですね。例えば、二次元配列をソートするときに、どの列でソートするか決めれます。

```
aa = [[1,2,3], [2,5,3], [3,3,4]]
```

という配列があって、んー、2番目の数字で昇順に並べ替えたいんだよなーってとき、

```
aa.sort(key=lambda x:x[1])
```

でいけます。詳しくは自分で調べろ
##指定したkeyでの最大値
さっきと同じようなやつ。ほかの要素は文字とかでもいいよ。

```
aa = [["a",2], ["c", 90], ["d", 8]]
```
とかを

```
aa.max(key=lambda x:x[1])
#["c",90] って返ってくるはず
```
これも詳しくは自分で調べてね

##重複要素消したいとき
set関数つかう。これくそ便利だから覚えといて
集合型にしてくれます。詳しくは略

```
aa = [1,1,1,1,2,3,4,5]
set(aa)
#{1,2,3,4,5}
```

こうすると何がいいかというと、重複除いた要素の個数がわかる。

```
len(set(aa))
#5
```
set型はめちゃくちゃよくお世話になる
#おわり♡
お名前.comとAWS SESとNetowl(coreSSL)で個人ドメインへのサーバ証明書を発行する

サーバ証明書発行は初めてだったので備忘録

ドメインは取得済みのところからstart
coreSSLを選択した理由としては安かったからです

# AWS SESの設定
証明書取得時にコモンネームに紐づいたメールサーバを求められます、一時的に必要なだけ & 簡単なのでメールサーバの代わりにSESを利用します
基本的には下記手順に従うだけなのですが, Rout53を利用する前提で書かれているので必要な部分だけ注釈します
https://docs.aws.amazon.com/ja_jp/ses/latest/DeveloperGuide/receiving-email-getting-started.html
使えるリージョンが限られているため、当記事では「バージニア北部」を前提に進めます

### ドメインの検証
SES側でドメインを設定したあと、お名前.comの「DNSレコード設定」より `TXTレコード` を設定します
ついでに `MXレコード` も設定しちゃいましょう
「DNSレコード設定」は 画面上部の「ドメイン設定」 > サイドメニューの「ネームサーバの設定」 > 「DNS設定/転送設定」より設定画面に入れます
`TXTレコード` はAWS SESのDomains画面から取得可能で
`MXレコード` は `inbound-smtp.us-east-1.amazonaws.com` 固定(リージョンごとでは違います)で優先値を `10` で設定しましょう, ホスト名は証明書申請するコモンネームと同じになるように設定してください

### Rule Setsの作成
手順通りで問題ありません、`Recipient` もとくに作成する必要はありません

# CSRの作成
基本的には下記手順に従う形で大丈夫だと思います
https://www.sslbox.jp/support/man/csr_make_flow_openssl.php
Apacheを使用する前提で書かれていますが、当記事では確認にnginxを使用しますので、Apacheに関する項目はスルーしても大丈夫です

### 秘密鍵の作成
```
$ openssl genrsa -out <任意の名前>.key 2048 
```

### Requestの作成
```
openssl req -sha256 -new -key <任意の名前>.key -out <任意の名前>.csr
```
- `coreSSL` で利用できるアルゴリズムはSHA256になっているので引数で指定します `-sha256`
- `Country Name` は `JP` を入力します
- 個人用なので `Organization Name` は `None` , `Organizational Unit Name` は空(何も入力せずRET)でよいでしょう

# Netowlで証明書の発行申請
証明書の申請にはNetowlのSSL boxというサービスを利用します
https://www.sslbox.jp/?_ga=2.96678746.437584196.1576937387-1773080192.1576932664
登録後, 管理画面にて 「SSLボックスの管理」 > 「新規取得」 > 「他者サーバで利用」 で新規取得の作成ができます
作成後「取得証明書一覧」より申請画面に入ることができます
申請画面ではCSRを貼り付ける画面と、申請内容の入力画面を順に入力すれば、申請内容入力画面にて選択したメールアドレスに承認メールが届きます（SESを利用した場合は直接S3バケットにメールが入っています）
* CSRの貼り付けフォームは末尾改行なしの状態でないと通りませんでした、気をつけましょう
承認メール内に書かれている内容に従い、`validation code` を入力後、しばらく待てば、管理画面より証明書を直接DLできるようになります

# 証明書の設置とnginxの設定
- `/etc/nginx/conf.d/default.conf` へ証明書の設置情報を記載

```
server {
    listen       443 ssl;
    server_name  _;

    ssl_certificate /etc/nginx/ssl/nginx.cert;
    ssl_certificate_key /etc/nginx/ssl/nginx.key;
    location / {
        ...
    }
}
```

443 sslをlistenし、`ssl_certificate` `ssl_certificate_key` それぞれに証明書と秘密鍵の設置pathを記載します
証明書と秘密鍵は実際に記載した設置pathへ置きましょう(当然ですが

上記作業後、nginxを再起動し、ブラウザで `https://` でアクセスすれば、警告も出ず、見慣れた鍵マークが表示されていることを確認できるはずです
Linuxコマンド

勉強したことをメモ

 【基本コマンド】
・pwd（Print Working Directory）
　今いるディレクトリの表示

```
$ pwd
 /home/test
```

・mkdir（Make Directory）
　新規ディレクトリを作成

```
$ mkdir test（作成したいディレクトリ名）
```


・cd（Change Directory）
　ディレクトリを移動

```
$ cd test（移動したいディレクトリ名）
```

・cd ..
 １つ上のディレクトリに移動

```
$ cd ..
```

・cd
 ホームディレクトリに移動

```
$ cd
```

・ls（LiSt derectory contents）
 ディレクトリの中身を表示

```
$ ls
test/
```

・touch
　ファイルを作成

```
$ touch hello.rb（作成したいファイル名）
```
heroku run rails db:migrate:status のコマンドの意味

# 目的

- 表題のコマンドをあまり理解せず実行していたのでまとめる。
- コミュニティやtwitterで教えていただいた内容を忘れないようにまとめる。

# heroku run rails db:migrate:statusとは

- herokuサーバでのマイグレーションステータスを出力するコマンドである。
- ちなみにherokuサーバへのマイグレーションを行うコマンドは`$ heroku run rails db:migrate`である。

# 結論

- 

# コマンドを分解してみる

- `heroku run`の意味を下記に記す。
    - run a one-off process inside a Heroku dyno→「
Heroku dyno内で1回限りのプロセスを実行する。」(コマンド`$ heroku --help`で調べた。)
    - dynoはアプリを実行するためのコンテナのことらしい、「そのコンテナ内で後述するプロセスを実行するよ〜」って感じ。
- `rails db:migrate:status`の意味を下記に記す。
    - 「マイグレーションのステータス（upまたはdown）を表示する。」(こちらのリンク先に記載があった[https://railsguides.jp/active_record_migrations.html](https://railsguides.jp/active_record_migrations.html))

# ちなみに

- Rails５以降は`rails`コマンドを実行すれば`rake`コマンドを探して実行してくれるらしい。
- なので下記コマンドは同じ挙動をする。

```terminal
$ heroku run rails db:migrate:status
$ heroku run rake db:migrate:status
```

# だけど

- `rails`コマンドを実行すると`rake`までコマンドを探しに行って実行してくれる。
- `rake`コマンドを実行しても`rails`コマンドを探しに行ってくれない。

# 参考にしたリンクを載せる

- rails db:migrate:statusコマンドの説明
    - [https://railsguides.jp/active_record_migrations.html](https://railsguides.jp/active_record_migrations.html)

- Rakeコマンドの実行
    - [https://devcenter.heroku.com/articles/rake](https://devcenter.heroku.com/articles/rake)

- dynoの説明
    - [https://jp.heroku.com/dynos](https://jp.heroku.com/dynos)

# 謝辞

- 本投稿内容はTwitter、コミュニティのslack、キャリアアドバイザーさんからいただいた知識です。
- 毎度知恵をおお貸しいただき本当にありがとうございます。
モンテカルロ法による探索

この記事は[データ構造とアルゴリズム Advent Calendar 2019](https://qiita.com/advent-calendar/2019/str) 22日目の記事です。

# はじめに
エージェントが目的を達成するために、どのような行動を取ればよいか、状態空間を探索して「望ましい行動」を取れるような方策を獲得する問題で、近年、モンテカルロ法に基づく手法が活用されています。

この「方策」を獲得する観点から、モンテカルロ法による探索について記述します。

# プレイアウト
前提として、シミュレーション環境または実験環境により、任意の状態を観測できるとします。初期の状態から、何か一つ行動を選び、その行動で得られた状態から、また次の行動を選ぶ問題を考えます。

このとき、囲碁や将棋などのゲームを含む複雑な問題では、行動によって起こり得る状態が広がりすぎて、探索が難しくなります。かりに強化学習で解くための「報酬」を定義しようとしても、ゲームの途中段階で適切な報酬を定義することは容易ではありません。

探索するための手法として、モンテカルロ法による「プレイアウト」があります。プレイアウトは、乱数を用いて最終状態まで進めるものです。自分や相手の行動を、擬似乱数で一様ランダムに選んで、勝ち負けなどの最終状態になるまで継続します。

もちろん、一回のプレイアウトで得られる結果は「でたらめ」ですが、何回も繰り返すことにより統計的な分布が得られます。プレイアウトで得られる分布を、次の行動を選ぶための方策に使うだけでも、簡単なゲームでは「それなりに」賢く行動します。

囲碁におけるプレイアウトは、現在は理研AIPの美添先生による[コンピュータ囲碁におけるモンテカルロ法～理論編～](http://minerva.cs.uec.ac.jp/~ito/entcog/contents/lecture/date/5-yoshizoe.pdf)の「原始モンテカルロ囲碁」に説明があります。

なお、[コンピュータ囲碁―モンテカルロ法の理論と実践―](http://www.kyoritsu-pub.co.jp/bookdetail/9784320123274)でも解説されていますが、原始モンテカルロ囲碁では「相手のミスを期待した手を選択することがある」ため、現在では性能向上のための対策を講じた「モンテカルロ木探索」が使用されています。

# AlphaGoのrollout
前項では、簡単のためプレイアウトは一様ランダムとして説明しましたが、一様ランダム以外のランダムな方法も考えられ、Zeroではない[AlphaGoの論文](https://www.nature.com/articles/nature16961)では「rollout」と呼称して使われています。

[AlphaGoのしくみ](https://www.slideshare.net/yuk1yoshida/alphago-61311712)にも説明されていますが、800万の盤面で機械学習を行って得られた方策を確率分布として、擬似乱数で確率的に行動を選んで最終状態まで進めるのがrolloutです。例えば、3種類の行動を選べる状況で、方策が(0.7, 0.2, 0.1)のとき、rolloutでは70%、20%、10%の確率でランダムに行動を選びます。

このrolloutは、[AlphaGo Zero](https://deepmind.com/blog/alphago-zero-learning-scratch/)以降では採用されていませんが、機械学習や深層学習で得られた方策を使ってランダムに行動を選ぶことは、問題を解くアプローチの一つとして有効ではないかと考えます。

なお、AlphaGoのrolloutで使用していた方策は、CNNを使った深層学習ではなく、盤面から計算できる約11万個の特徴量を入力とした線形回帰です。深層学習ではなく線形回帰とした理由は、rolloutを繰り返し高速に実行できるだけの速度が要求されていたからと思われます。

# おわりに
AI-SCHOLARの[MuZeroの衝撃。囲碁のルールを自ら学習しAlphaZeroを凌駕。]( https://ai-scholar.tech/treatise/muzero-ai-355/ )では、Google DeepMind発表の最新手法「MuZero」が、わかりやすく解説されています。

[MuZero](https://arxiv.org/abs/1911.08265)は、ルールを与えなくても方策を学習できることが特色ですが、知能を作りたい立場から少し離れた「特定の問題を解きたい」立場なら、ルールを与えてもかまわないのではないかと考えています。

今後、モンテカルロ木探索などのモンテカルロ法を活用したアプローチで、リーズナブルな計算資源でも現実の問題を解くことができる手法の発展を期待したく思います。
機械学習における分類と回帰について

こんばんわ。
先ほどAirpots紛失事件（見つかりました。）が起きてひと段落がつきました。

今日は機械学習に置いての分類と回帰をまとめたいなーって思います。


#分類について
分類の大きな目的は、**データが属するクラス（Yes,No）を予測すること**です。
予測するクラス数が2クラスの場合、**2値分類**と呼ばれます。
ex)
- ユーザーの利用履歴から、ある定期購読を退会するかしないかを判断。
- 生徒のプロフィールで、合格か不合格か
- メール情報で、スパムかスパムではないか
- などなど

もし、２クラスより多い分類ならば、それは**多クラス分類**と呼ばれる。
ex)
- 学生の評価
- 画像認識
- などなど

# 回帰について
回帰の大きな目的は、**値の予測**です。
もっと深くいうならば、**説明変数（特徴量）**から**目的変数**を説明するタスク。
ex)
- 数学の点数を理科の点数で説明。（説明変数：理科の点数、目的変数：数学の点数）
- 家賃を物件の広さと地域で説明。（説明変数：広さと地域、目的変数：家賃）

また線形回帰というものに着手するならば、
目的変数をy、説明変数がn個あると仮定して$x_1$,$x_2$,・・・,$x_n$とした時に,

```math
y = a_0 + a_1x_1 + ・・・ + a_nx_n
```
として、$a_0, a_1, ・・・, a_n$を求める。
これらを求めるために、**最尤法**や**最小二乗法**などがある。
また$n = 1$のとき、**単回帰**といい、それ以外を**重回帰**と呼ぶ。


# 違いの例
下記の参考文献さんの例を挙げさせていただくと、
顧客の過去訪れた飲食店の情報があるとします。
分類　：　新しいレストランが好きor好きじゃないかを予測
回帰　：　新しいレストランに今後何回訪れるかを予測

# 二つの共通点
最後に二つの共通点を述べておきます。
それはどちらとも「**教師あり学習**」であるということ。
ちなみに、教師あり学習とは、データに付随する正解ラベルを用いた学習。


簡単ではありますが、分類回帰をまとめてみました。
ありがとうございました。


# 参考文献
[機械学習入門者向け 分類と回帰の違い](https://avinton.com/academy/classification-regression/)
Introducing Rust

#はじめに
この記事はシステムプログラミング言語であるRustのゆるい紹介記事となっています。
そのため、細かい文法や概念には触れません。興味のある方は公式の[tutorial](https://doc.rust-jp.rs/book/second-edition/)を確認してみてください。
これからRustに触れてみようかなと考えている人の背中を押せるような記事になれば幸いです。

#Rustとは
FireFoxで有名なMozilaが支援しているシステムプログラミング言語です。
6週間ごとにアップデートされており、現在の最新版は1.39.0です。
強力な型システムとリソース管理によりメモリ安全が保証されており、最近ではマイクロソフトが既存のC/C++をRustへ移行しています。


#Rustのもつ特徴
Rustにはさまざまな特徴があります。この記事ではOwnerShip(所有権)・LifeTime(生存期間)を中心として紹介します。

##所有権
Rustには所有権とよばれる機能があります。
所有権になれるまでは、ボローチェッカとの戦いを強いられることとなるでしょう。
実際のコード例とともに紹介します。コードの説明はコメントとしてコード内に埋めているので
是非一緒に確認してみてください。

```rust
fn take_vec(_: Vec<i32>){}

fn main() {
    let a: Vec<i32> = vec![1,2,3];  // aは[1,2,3]という配列の所有権を持つ(所有する)
    let b = a;                     // bにaが有している所有権を移譲する。-> aは所有権を失ったので何も入っていない状態
    println!("{:?}", a);           // aは何も所有していないのでerror
    
    let c: Vec<i32> = vec![1, 2, 3];
    take_vec(c);                   // 関数に渡しても所有権はmoveする
    println!("{:?}", c);
}
```

Rustではそれぞれの変数が値を所有するという考え方があります。
`let a = b;`のように書くと、所有権がbからaに移り、bは未初期化状態になります。
未初期化状態の変数にアクセスすることはできず、アクセスした場合はコンパイルエラーになります。
これによりuse after freeや、多重フリーを防いでいます。

一部の型(i32やu8等)は所有権の例外とされており、値がmoveするのではなくcopyされます。

```rust
fn take_vec(_: i32){}

fn main() {
    let a: i32 = 100; //i32はmoveしない
    let b = a;
    take_vec(a);
    println!("{}", a);
}
```

Copyトレイトが実装されているとCopyされるようになります。本記事ではトレイトについては解説をしないので、
[公式の解説](https://doc.rust-jp.rs/the-rust-programming-language-ja/1.6/book/traits.html)を参照してください。

##借用
所有権により、それぞれの変数は様々なところへmoveしてしまいます。
これだけでは不便に感じることが多いかと思われますが、Rustは借用と呼ばれる機能でこの不便さを解消しています。
借用を利用することで、一時的に値を参照することが可能となります。借用したものがスコープを外れるときは、借用を終了するだけで
借用元の値を解放することはありません。
借用元に`&`をつけることで不変な借用となります。

```rust
fn take_vec(_: &Vec<i32>){}

fn main() {
    let a: Vec<i32> = vec![1,2,3];  // aは[1,2,3]という配列の所有権を持つ(所有する)
    let b = &a;                     // bはaを借用する
    println!("{:?}", a);           // aは借用されているだけでmoveしていない
    
    let c: Vec<i32> = vec![1, 2, 3];
    take_vec(&c);                   // 関数に借用を渡す
    println!("{:?}", c);            // 解放されていない
}
```

また`&mut`をつけることで可変な借用になります。

```rust
fn main() {
    let mut a = vec![0, 1, 2];
    let b = &mut a;
    b.push(3); //可変な借用なので変更可能
    println!("{:?}", b);
}
```

不変な借用と可変な借用は共存できず、それぞれの値はいくつかの不変な借用をとるか、
たった一つの可変な借用をとるかのどちらかのみ可能です。


##ライフタイム
それぞれの変数はライフタイムとよばれるパラメータを持っています。
ライフタイムにより、スコープ終了時に自動的に解放されるのでガベージコレクションが不要となります。

```rust
fn main() {
    let a = 10;
    {
        let b = 100;
    } //ここでbはスコープが終了するので解放される
} //aが解放される
```

さきほど紹介した借用とライフタイムは密接に関係しています。
借用した値のライフタイムは、借用元の値より長生きしてはいけません。
もし、そういったコードを書いてしまった場合はコンパイル時に指摘されます。

```rust
fn main() {
    let a = String::new();
    {
        let b = "aaa".to_owned();
        a = &b; //ライフタイムが自分より短いものを借用してはいけない
    }
    
    println!("{}", a);
}
```


#さいごに
Rustはエラーがあるコードを許容しないとともに、エラーの可能性のあるコードも許容しません。
所有権等にもまれながらコードを書くうちにきれいなコードになっていくことかと思います。
最初はボローチェッカとの戦いでとてもしんどく感じるかもしれませんが、ぜひRustに触れてみてください。
初級編：「HTTPリクエスト」と「HTTPレスポンス」の基礎理解

#enebular初級レベルとしての理解のために
初級レベルとして、「httpノード」と「http responseノード」で、httpリクエストを行うことを通じて、httpリクエストとhttpレスポンスの基礎を理解したいと思います。

具体的には、現在の時刻をブラウザに表示するhttpリクエストとhttpレスポンスを、enebularが行う仕組みを作ります。

#ノードを使って処理の流れを作る
enebularを起動して
左のパレットから入力としてhttp、出力としてhttp response、機能としてfunctionとtemplateを、それぞれワークスペースにドラッグ＆ドロップして追加します。
![20191221_22-21-41.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/e1e51b74-1d5d-ad12-5d0f-1646e5dd1996.jpeg)


ドラッグ＆ドロップして並べたところ
![20191221_22-26-47.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/b8392aca-1310-c0e8-c0f7-f71b2d84c6c5.jpeg)

httpノード![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/8ae04863-6db0-7d28-ebf5-e9dcee0dccc2.png)をダブルクリックしてURLに /site01 と設定して　右上の完了ボタンを押す。


![20191221_22-28-34.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/e1911368-93a4-334d-07f3-849ddbfd54d5.jpeg)

functionノード![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/ff7fafed-777f-43ef-fd37-303b5a4d1c07.png)をダブルクリックして、名前に current time, コード欄に以下のコードを設定し、右上の完了ボタンを押す。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/799b3341-f7c4-7388-70e4-3ea5522dfc33.png)

template![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/a97a329f-ce45-3f00-4cc9-cbfa11d40c4e.png)をダブルクリックして以下の通り設定する
![20191221_23-16-21.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/0eaf2daf-6fe9-23c9-5302-6e16c525e29f.jpeg)


http responseノード![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/8d5c34c6-13f8-1f46-191e-d6a2e459273c.png)の中は設定変更しない。

http,　function,　template,　http responseの4つのノードを順につないで、右上のデプロイを押す。

![20191221_22-58-35.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/683752bc-0634-8f14-67ac-c65a4330cdf2.jpeg)

最終的な全体図
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/fb0e6c20-976a-8522-e303-12288d6da381.png)


httpサイトのURLをデプロイボタンの左の![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/e6d83463-23e1-2e5a-3c81-0879c6955898.png)マークを押してURL情報をコピーする。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/e47b696c-d585-795a-8717-cd98faca0fb1.png)

新しいブラウザに、コピーしたURLをペーストして、その後ろに、httpノード設定画面内で入力したURL（今回は/site01)を追加する。

![20191221_23-05-29.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/a175385c-b22f-1570-6837-84ff0fa00e5d.jpeg)

以下の通り表示される。
![20191221_23-13-44.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/269534/17155df5-d362-a67e-9b79-b134bd5c879f.jpeg)

#ノードの流れのおさらい
/site01のURLに、ブラウザから「HTTPリクエスト」（GETメソッド）を送信することで「httpノード」が処理を開始し、時間データを取得し、template内に記述したHTMLに時間データを加えて、そのHTMLを「http responseノード」に伝え、「HTTPレスポンス」をブラウザに送信する流れで、現在時刻が表示されます。

enebularを使って、「HTTPリクエスト」と「HTTPレスポンス」のことが初級編として理解できました。
再帰的に素数を求める

#はじめに
　Python学習の一環として、素数を再帰的に求めるコードを作成しました。

#コード
　今回はエラトステネスの篩を用いました。
>エラトステネスの篩 (エラトステネスのふるい、英: Sieve of Eratosthenes) は、指定された整数以下の全ての素数を発見するための単純なアルゴリズムである。古代ギリシアの科学者、エラトステネスが考案したとされるため、この名がある。
（Wikipedia「[エラトステネスの篩](https://ja.wikipedia.org/wiki/%E3%82%A8%E3%83%A9%E3%83%88%E3%82%B9%E3%83%86%E3%83%8D%E3%82%B9%E3%81%AE%E7%AF%A9)」より引用）


　以下がコードです。

```python:Sieve.py
array = [i for i in range(2, 100)]  #求めたい値の範囲  
prime = [2]                  #素数のリスト

def Sieve(array, prime):     #エラトステネスの篩
  newArray = []
  for i in array:
    if i%prime[-1] != 0:
      newArray.append(i)
  prime.append(newArray[0])  #リストに素数を追加
  if array[-1] == prime[-1]:
    return prime             #素数のリストを返す
  return Sieve(newArray, prime)

Prime = Sieve(array, prime)
print(Prime) #出力
```

　結果、2から~~100~~ 99までにある素数が求まりました（2019年12月22日訂正）。

```python:出力
[2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97]
```

#おわりに
　Pythonで再帰を扱うときは上限があるそうですね。上限と変更方法が[こちらの記事](https://note.nkmk.me/python-sys-recursionlimit/)で解説されていました。

　ご覧いただきありがとうございました。ご指摘等ありましたらコメント欄にお願いします。
LinuxサーバーをTimeMachineのバックアップ先にしてみる

この記事は[琉大 Advent Calendar 2019](https://adventar.org/calendars/4060)の21日目の記事です。

この時期ぐらいから3月ぐらいまでで怖いことの1つが「**論文やレポート作成中にPCが壊れる**」こと。

バックアップを取っていればいつ壊れても怖くないけど、ずっと外付けHDDを繋いでいるのはUSBポートの無駄遣いになってしまう...
ネットに繋がっている時にバックアップしてくれたらいいのにな...

研究とかで使っていたり、研究室とかに置いてある(あるいは使われていない)Linuxサーバーをバックアップ先にしてしまえば、論文書いてる間に勝手にバックアップしてくれる様になるのでは...!!

## そもそもTimeMachineって何？
Time Machineの説明は[Appleのサポートの記事](https://support.apple.com/ja-jp/HT201250)にあるので、~~そっちに丸投げ(おい)~~
> Time Machine は、Mac に組み込まれているバックアップ機能です。この機能を使って、App、音楽、写真、メール、書類、システムファイルなど、すべてのファイルを自動的にバックアップしておけます。バックアップしてあれば、Mac から削除したファイルでもバックアップから復元できます。Mac のハードディスク (または SSD) を消去または交換した場合でも大丈夫です。

システム環境設定の共有をいじることで、別のMacのTime Machineのバックアップ先にもなることができるらしいです。([Appleのサポートの記事](https://support.apple.com/ja-jp/HT202784#mac))

## LinuxサーバーをTimeMachineのバックアップ先にしていく

今回は以下の環境をTimeMachineのバックアップ先にしました。


- CPU: AMD Ryzen 3 2200G
- メモリ: 2GB
- ストレージ: 931GB(1TBでパーティション切ったら、フォーマットすると容量減るのを忘れて中途半端な容量に)
- OS: Ubuntu 18.04 LTS

事前にバックアップ先となるディレクトリを作成しておきます。

Netatalkというものが必要になるので、`sudo apt install netatalk`で必要なパッケージをインストールします。

`/etc/netatalk/afpd.conf`の最終行のコメントアウトを解除します。

``` /etc/netatalk/afpd.conf
# - -tcp -noddp -uamlist uams_dhx.so,uams_dhx2.so (← この行のメントアウトを解除する)
```
続いて、`/etc/netatalk/AppleVolumes.default`の編集をしていきます。
180行付近にある

``` /etc/netatalk/AppleVolumes.default
~/                     "Home Directory"
```

をコメントアウトして、最終行に下記を追加します。

``` /etc/netatalk/AppleVolumes.default
[バックアップ先のPATH] "[Time Machineのバックアップ先選択画面での表示名]" allow:[ユーザー名] cnidscheme:dbd options:usedots,upriv,tm
```
[バックアップ先のPATH]、[Time Machineのバックアップ先選択画面での表示名]、[ユーザー名]は実際のものに変更してください。

`sudo systemctl restart netatalk.service`でNetatalkを再起動します。

後は[Appleのサポートの記事](https://support.apple.com/ja-jp/HT201250)の手順に従って設定してください。
その時にバックアップ先には`/etc/netatalk/AppleVolumes.default`に追記した表示名のものを選択して、ユーザー名とパスワードを聞かれた場合はLinuxサーバーの該当ユーザーのユーザー名とパスワードを入力してください。

初回バックアップにはかなりの時間かかると思うので、辛抱強く待ってください。(自分の場合wi-fi経由で8時間くらいかかりました)


## 最後に
明日の担当は[優桃原](https://adventar.org/users/21759)さんです。
UiPathを触り初めてからの難しかった点を振り返る

UiPathを初めて触ったのは2017年の3月だったかと思います。
その時は、こんなに簡単に自動化できてしまうのかとかなり衝撃的だったですが、
それからUiPathを扱っていくなかでいくつかの困った事がありました。
本記事ではそれら困ったことを、これまでを振り返りながら整理したいと思います。

## UiPathを初めて触ってから

今思い出すのは、まずRPAチャレンジです。
[RPA Challenge](http://rpachallenge.com/?lang=JA)

おそらくUiPathを使用している人は挑戦しているのではないかと思います。
UiPathを使用して10個あるフォームに指定のデータを入力するのですが、フォームのパターンが様々で位置がバラバラだったり順番がバラバラだったりと、始めたての頃は案外難しいものでした。
久しぶりに見てみるとなんだか見た目が変わっていますが、内容は変わってませんよね？
セレクターというものを理解したのもこのRPAチャレンジがきっかけでした。

次に行ったことが、webのページからスクレイピングでした。
具体的なサイトは忘れてしまったのですが、webの情報ページからリスト表示されている各詳細ページにアクセスして、その内容をとってくるというものでした。
ここでは、単純にスクレイピングしただけでは表面上の情報しか取ることができず、リンク先のURLを取得するために色々と苦労しました。
また、リスト表示も1ページ目、2ページ目とあり、最終ページがループする形になっていたため、スクレイピングの標準のページ送りが正常に機能しないトラブルも発生しました。
結局その機能は使用せずに、自作の次ページへの遷移を行う処理を実装しました。
セレクタを自動取得するだけでなく、セレクタに変数を埋め込み動的に変化させるなど、より自在に扱えるようになりました。
要素を探すなどのアクティビティもここで使用方法を学びました。

その次に行ったこともwebスクレイピングだったのですが、上記の場合に比べて必要な処理が非常に多く、重厚長大なワークフローになりました。
そのころはまだ、フローチャートを上手く使えておらず、ひたすらシーケンスで対応していたり、「ワークフローファイルを呼び出し」アクティビティ(Invoke Workflow File)の存在を知らなかったりと、超縦に長いワークフローができてしまい、更にはIF文の中にもIF文が多重に入っているため横にも太いという、なんとも人に絶対に見せられない形になっていました。
フローチャートを使用したり、適度にワークフローを分割したりと、UiPathといえども予め設計を考えて置かなければ大変な事になるなと気が付かされました。
また、設定をExcelに外だししておいて、ワークフローの初期化処理で読み込みをしたり、そこから派生してRe:Frameworkの扱い方を学んだりと、もう1歩進んだワークフロー作成ができるようになりました。

## 1年経過後

UiPathの扱いはかなり分かってきて、簡単なことならちょちょいとできるようになったのですが、UiPath Orchestratorを扱うことも増えてきたところで、マシンやらロボットやらロボットグループといった概念に少し戸惑いました。
ただ、理解すれば全然たいした問題ではなかったのですが、各端末のロボットで使用されるパッケージの配布元がどうなっているのか、ライセンスの消費方法がどうなっているのかといった細かい不明点が多く出てきたのも印象深いです。
正直、今でもよく分かっていない部分もあったりしますが、UiPath社さんのOrchestrator研修に参加させて頂いたおかげで広範囲に渡って理解することができました。

思い返せばもっと色々と困ったことがでてきそうですが、一旦ここまでで、また後日続きを投稿したいと思います。

そういえば、困ったことではありませんが、今年になってからはUiPath DevComにも毎回参加させていただき、様々な情報共有やユーザ同士のふれあいといったとても多くの刺激をうけることができました。
ご興味ある方は是非ご参加されることをオススメします。

一応、下記の記事も今回のアドベントカレンダーに合わせて書きましたので、良ければ覗いてみて下さい。（一方に時間を割き過ぎて、こちらがラフな感じに…）
[Alteryx Designerによるデータ処理をUiPathで自動化してみる](https://qiita.com/toshiki_takatsuki/items/3ae9c5f27b0483217fcb)
LGT8f328P Arduino互換ボードを使ってみる


![](https://raw.githubusercontent.com/dbuezas/lgt8fx/master/docs/boards/ssop20.png)
[わずか80円！謎のArduino互換機を動かしてみた 記事](https://qiita.com/SamOnodera/items/fd614066a46c56865530)にネタを提供した [とも](https://www.facebook.com/tomon777) です。
ArduinoIDE 1.8.9で [このボード](https://github.com/dbuezas/lgt8fx/wiki/Pro-Mini-Style---SSOP20)を使ってみました。
#LGT8F328P：ATmega328互換中華MCU 
[深浅のLogic Greenが設計したLGT8F328P](http://www.lgtic.com/lgt8fx8p/) というチップは、Arduino UNOに載っているATmega328と命令互換でI/O拡張されており、[MPUが大陸で安く出回ってます](https://item.taobao.com/item.htm?id=549915535039)。
#ArdunoIDE 1.8.9を設定してみる
[ArduinoIDE用の設定ファイル](http://www.lgtic.com/upload/tools/arduino/Larduino_HSP_latest.rar)ダウンロードして解凍します。

```:readme.txt
//==============================================================
// LogicGreen 2018/02/23
//
// Ardunio 3rd-party hardware package for LGT8F
//	Installation Guide
// 
// Update memo:
// v3.6c
//	- update arduino core based on arduino 1.8.5 
//
//==============================================================

1. Features
	> Support arduino > 1.8.x
	> Support bootloader by optiboot
	> Bootloader baudrate: 57600bps
	> Support board: Larduino & LGT8F88A MiniDev
	> Support board: Larduino w/ LGT8FX8D and LGT8FX8P

2. Package contents
	Larduino_HSP_v3.6c : package root directory
	|
	+ hardware : 3rd party hardware support package
	|    |
	|    + LGT : package for support arduino
	|
	+ libraries : 3rd party hardware library

3. Installation:
	> Unzip Larduino_HSP_v3.6x.rar
	> Copy [sketches], [hardware] and [libraries] directories to arduino's sketchbook direcotry
	> Restart Arduino, you will see new board from [Tools]->[Border] menu.

4. about arduino's sketchbook directory:
	You can always find this directory from [File]->[Preferences] menu.
	Here is the default sketchbook directory for most popluar system:
	> Windows: C:\Users\<Username>\Documents\Arduino
	> Mac OSX: /Users/user/Documents/Arduino
	> LINUX: /home/<Username>/sketchbook
```
readme.txtの指示に従って、[sketches], [hardware] , [libraries] 各フォルダをArduinoフォルダ下(Windowsでは、ドキュメントフォルダのArduinoフォルダ)にコピーして、ArduinoIDEを起動します。

#ArdunoIDE 1.8.9で使ってみる
USBシリアルは、CH340搭載ArduinoMiniPro用PC直結タイプを接続しました。
![KIMG3939 (2).JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/106489/7806f997-aee2-bc5e-ccc7-14cb99e23db1.jpeg)
USBシリアルをPCに接続して、デバイスマネージャーでCOM番号を確認しておきます。
ArduinoIDEで「ツール」プルダウンメニューから「ボード」をクリックして、「LGT8F328P-SSOP20 MiniEVB」を選択します。
<img width="532" alt="SnapCrab_19-12-21_23-48-16_00.jpg" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/106489/58e898de-3d61-bfe8-0d6e-dbfe1b544d5b.jpeg">
ArduinoIDEで「ファイル」プルダウンメニューから「スケッチ例 - basics」をクリックして、blinkサンプルスケッチを開き、アップロードします。
<img width="522" alt="SnapCrab_19-12-21_23-54-52_00.jpg" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/106489/9152983e-d4d0-5b41-579a-39f833e281ef.jpeg">
コンパイル後に、青ランプ早く点滅してから、アップロードが完了して、青LEDが1秒点滅すれば、動作確認OKです。
![KIMG3937.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/106489/fb076649-6558-6097-a6d5-1455aeb47a7b.jpeg)
Go1.14で来るGo Modules関連の変更を見てみる

この記事は [Go3 Advent Calendar 2019](https://qiita.com/advent-calendar/2019/go3) の21日目です。

本日(12/21)時点でのGoの最新バージョンは1.13.5ですが、次バージョンであるGo1.14が2020年２月頃にリリース予定です。

ここ数バージョンで急激に発展してきたGo Modules周りにもいくつか変更が入る予定です。

そこでGo1.14ではどのような変更が入るか簡単に追ってみたいと思います。

## Vendoringまわりの変更

### vendorディレクトリが存在する場合の`-mod`フラグの挙動

Go1.13時点では`go mod vendor`を行うとプロジェクト配下にvendorディレクトリが作成され、そこに全ての必要なパッケージが配置されます。

Go1.14ではvendorディレクトリが存在し、`go.mod`ファイルによるGoのバージョン指定が`go1.14`以上である場合、`go`コマンドがデフォルトで`-mod=vendor`フラグを受け入れます。

### `-mod=mod`の追加
 
新たに`-mod=mod`フラグが追加され、`-mod=mod`を指定する場合は従来のモジュールキャッシュからモジュールをロードするようになります。

また`-mod=vendor`が指定されている場合は、`go`コマンドは`vendor/modules.txt`ファイルと`go.mod`に一貫性があるか検証を行います。

### `go list -m`の暗黙的な挙動変更

今まで`go list -m`はvendorディレクトリに存在しない暗黙的な依存関係を省略していましたが、それがなくなります。`-mod=vendor`が指定されている場合は明示的に失敗となります。

vendor周りはデプロイ時やコンテナイメージ作成でパッケージを配置する際によく使われることがあると思いますが、挙動の変化に注意したいですね。

## go getの変更

`go get`コマンドで`-mod`フラグを受け入れなくなります。
Go1.13までは`-mod`フラグが付与されている場合は無視されるか失敗となっていたので、明示的に付与しないようにする必要があります。

## フラグまわりの変更

### `-mod=readonly`のデフォルト適用追加

今までもCIやTest用途で`go.mod`に変更が必要ないことを確認するために役立つ`-mod=readonly`フラグですが、`go.mod`ファイルが読み取り専用かつvendorディレクトリが存在しない場合、`-mod=readonly`がデフォルトで設定されるようになります。

### `-modcacherw`フラグの追加

これは`-mod=readonly`のように変更がある場合は失敗させるのではなく、モジュールキャッシュに新しく作成したディレクトリを残すように支持するフラグです。これによってCIやテストによって検証されていないファイルを誤って追加されてしまう可能性が高まりますが、`go clean -modcache`ではなく`rm -rf`で明示的にモジュールキャッシュを消すことが可能です。

つまり全てのモジュールキャッシュを削除するのではなく、新たに追加された部分だけを明示的に`rm`コマンドで消せるようにするフラグだと思っています。

### `-modfile=file`フラグの追加

`-modfile=file`はトップディレクトリにある`go.mod`ではなく、明示的に読み込みたい`go.mod`ファイル(modfile)を読み取るフラグです。
本来modfileは暗黙的に読み込まれますが、このフラグを使うと指定したmodfileを読み込むようになります。
またmodfileを指定した場合、それに対応する`go.sum`ファイルも参照します。それはmodfileから`.mod`拡張子を削除し、`.sum`をつけて参照されます。

## モジュールの非互換バージョンの挙動変更

`go.mod`ファイルに最新バージョンのモジュールが含まれている場合、`go get`を行っても明示的にバージョンが指定されている場合を除いて、互換性のないメジャーバージョンにはアップデートをしなくなります。

## `go.mod`ファイルのメンテナンス

`go mod tidy`以外の`go`コマンドは、変更が表面的なものである場合`go.mod`ファイルを編集しなくなりました。明示的にメンテナンスするには`go mod tidy`する必要があります。

そして`-mod=readonly`を設定した場合、goディレクティブの欠如や誤った`indirect`コメントが原因で`go`コマンドが失敗しないようになります。

## その他

`go`コマンドはモジュールモードでSubversionをサポートするようになります。

また`go`コマンドはProxyや他のHTTPサーバからのプレーンテキストなエラーメッセージのスニペットを含むようになります。
エラーメッセージはUTF-8で、グラフィック文字(?)とスペースのみで構成されている場合に表示されます。

## 終わりに

Go1.14も更にモジュール管理がカッチリしたものになりそうな片鱗が見て取れますね。
またリリース後に検証して行きたいと思います。
Outsystems supportとRemote sessionを実施しました。

# 想定読者
Outsystems Supportと契約している開発者
#背景
Outsystems supportへの問い合わせで、その案件の特性により、Outsystems supportからRemote sessionを実施するリクエストが来ました。初回で私たちと同じように、Remote sessionとは何か、どうやって実施するのだろうと思う方がいると思い、この記事を書きました。
# Remote sessionについて
###Remote sessionとは###
Remote sessionは、ビデオチャットでミーティングを実施することです。権限を与えると、向こうはこちらの画面を操作することが可能になります。

###Remote sessionの準備###
- 送られたリンクで時間を予約します。

Remote sessionのリクエストと一緒に、可能な時間を選択できるリンクも一緒に送られます。そこで都合のいい時間（日本時間）を選べます。Outsystems support と時差があるため、選べる時間が朝早いか（7:30まで）、午後遅い（17:30以降）になります。しかし、Outsystems Supportは 24x7 のサポート体制で、リンクで選べられない昼の勤務時間を指定することも可能です（チケットで可能な時間をサポートに教えます）。

- 事前にツールのインストール

オンラインでMTGを実施するため、Cisco WebExというGoogle Chrome の extension ツールを事前にインストールする必要があります。

- 事前にサーバ環境にアクセス

案件により、調査対象になるサーバ環境にアクセスする必要があります。チケットで、どの環境にアクセスする必要があるかは事前に教えてくれますので、ミーティングを開始する前にアクセスしておくとスムーズになると思います。

###その他###
今回のお問い合わせは、Remote sessionですぐ解決できると思いましたが、意外に根深いところがありました。二回で 2 時間ずつ実施しましたが、まだ解決できておらず、次回は早めの時間から予約しています（調査を中断せず、一気にできるように）。Remote sessionのため、時間を長めにとっておいた方がよいと思います。また、今回、弊社の案件で、英語サポートも含め、関係者四人でミーティングに参加しました。一人より、それぞれ知識を持つ方が参加し、話し合うことで、よりスムーズに調査が進められました。

#終わりに
Remote sessionと聞いたら、英語が得意ではない方の中には、不安を持つ方もいると思います。Remote sessionで日本語のサポートも用意してくれるようで、英語に不安がある方は事前に確認した方がよいと思います。この記事は簡単な内容を書きましたが、初めてRemote sessionの実施で、どうすればいいか迷う方に、少しでも参考になれば幸いです。
toio にカメラを載せてOSC制御する

これは「toio™(ロボットトイ | toio（トイオ）) Advent Calendar 2019」の21日目の記事になります。

# はじめに
toioにカメラを載せたり、TouchDesignerとOSCで通信できるようにしました。
toioに物を載せたり、他のアプリと通信する時の参考になればと思います。

![DSC_0002_BURST20191221210130867.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/197729/38fdd730-d965-c55f-97f7-45c4d58144ea.jpeg)

# やったこと
- toio に DSC-RX0 をレゴパーツを組み合わせて固定した
- toio.py で倒れないように加速度を調節した
- Python TouchDesigner の間をOSCで繋いだ
- TouchDesingerで生成した色と同じ色がLEDで光るようにした（通信テスト）

# 環境
- MacBook Pro (2.7 GHz Intel Core i5,16 GB 1867 MHz DDR3)
- macOS Catalina
- python 2.7

# toio に カメラを載せて速度制御する

<blockquote class="twitter-tweet"><p lang="ja" dir="ltr">一気に止めるとこれ <a href="https://t.co/M9GR241T3i">pic.twitter.com/M9GR241T3i</a></p>&mdash; 水落 大 mizumasa (@_mizumasa) <a href="https://twitter.com/_mizumasa/status/1208396109300801537?ref_src=twsrc%5Etfw">December 21, 2019</a></blockquote> <script async src="https://platform.twitter.com/widgets.js" charset="utf-8"></script>

モーターの速度60ぐらいだと急に止めても大丈夫ですが、速度100から0に一気に落とすと倒れます。
0.3sぐらいかけて１００から0まで滑らかにスピードを落とすようにすると倒れずにすみます。
toio.pyに滑らかに速度を変化させる関数 write_data_motor_smooth 追加しました。


ちなみにこうなってます。
![DSC_0529.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/197729/a15a4eb8-04b7-6610-9bc4-efe1e0749b12.jpeg)

円形プレートに穴を開けて、ポッチ2x2に収まる三脚ネジが通るようにしています。
[オーディオファン ストラップアダプター 1/4インチ 三脚 ネジ穴用 2個セット オーディオファン](https://www.amazon.co.jp/dp/B07QJFV1RM/ref=cm_sw_r_tw_dp_U_x_97I.DbAR62EK4)

# OSCでTouchDesignerと繋ぐ

<blockquote class="twitter-tweet"><p lang="ja" dir="ltr">TouchDesignerからOSCでtoioのLED光らせられるようにした。分かりにくいけどこんな感じ<a href="https://twitter.com/hashtag/toio?src=hash&amp;ref_src=twsrc%5Etfw">#toio</a> <a href="https://twitter.com/hashtag/touchdesigner?src=hash&amp;ref_src=twsrc%5Etfw">#touchdesigner</a> <a href="https://twitter.com/hashtag/python?src=hash&amp;ref_src=twsrc%5Etfw">#python</a> <a href="https://t.co/zHnLuPGhrv">pic.twitter.com/zHnLuPGhrv</a></p>&mdash; 水落 大 mizumasa (@_mizumasa) <a href="https://twitter.com/_mizumasa/status/1208398538901803009?ref_src=twsrc%5Etfw">December 21, 2019</a></blockquote> <script async src="https://platform.twitter.com/widgets.js" charset="utf-8"></script>

### 環境構築
以前作成した Python 環境で使えるtoioライブラリ [toio.py](https://github.com/mizumasa/toio.py) を使用します。
インストール方法はこちら -> [「toio を Mac + Python で制御できるライブラリつくった」](https://qiita.com/mizumasa/items/2a350e4188a5904fa829)
加えて今回は、python用OSC通信ライブラリ [pyOSC](https://pypi.org/project/pyOSC/) をインストールしておきます。


<img width="1134" alt="スクリーンショット 2019-12-21 21.05.03.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/197729/24783bdc-72c6-6425-4f56-aee7a5be79dd.png">

今回の記事は経過だけでしたが、これで何をつくるのか、またどこかで共有させて頂きたいと思いますのでお楽しみに。
大学2年生がチーム開発のリーダーになって失敗と後悔をしまくった話〜始まりとアイデア出し編〜

2018年11月、僕は学部1年生にしてチーム開発のリーダーになりました。

そのチームは数々の失敗に見舞われ、一応形にはなり、発表はしたものの様々な後悔を抱えたまま2019年の11月、僕はリーダーを降りました。

このチームの1年間の失敗の数々、そして反省を振り返りたいと思います。

今回は始まりとアイデア出しについての話です。

# 始まり
当時の僕は大学からプログラミングを始めた初心者で右も左もわからず、C言語ならちょっとわかるようになってきたというレベルでした。

そんな僕は大学の情報系のサークルに所属していました。
このサークルでは1年後の大学の文化祭になんらかの作品を1年生だけで作り、発表するというのが恒例になっています。

チームでの開発に挑戦してみたかった僕はリーダーとして参加することにしました。
サークル内からメンバーを募り結果的に僕を含めて６人のメンバーが集まりました。

僕たちは作るものを決めるため、アイデア出しをはじめました。

# アイデア出し期
そんなわけで12月ごろからアイデア出しをはじめたわけですがこのアイデア出しの時点ですでにいくつかの失敗をしました。

当初の話し合いは盛り上がり、人工知能やVRゲーム、画像処理などアイデア自体はたくさん出ました。

ですが、各自のやりたいこと、開発のしやすさ、開発する意義、何を優先するべきかわからず、作るものを決め切ることがなかなかできませんでした。

全員がなかなか集まれないといった事情などもあり、話し合いは数カ月にわたり、4月を迎えました。

結果的にほぼ僕のゴリ押しでウェブアプリを作ることになりました。

## 何を失敗したのか
### 時間をかけすぎた
僕たちの場合は開発ができる期間の約半分が話し合いに費やされてしまいました。

アイデアを話すだけの時間で数ヶ月過ごしてもほぼ無駄です。
技術的な成長はほとんどありません。

確かに作るものは大切です。
ですが、初心者の集まりにどんなものが作りやすいかとかわかるわけがありません。

作るものにこだわらず作り始めることが大事だったと思います。

そうすれば、自分たちのいま持っている力や足りないものがわかるようになってきて、少しずつ成長していき、荒削りのアイデアももっと良くなっていきます。

とにかく手を動かすことがすごく大事です。

チームのみんなで手を動かせば、かって口も動いて進展があると思います。

### 難しいアイデアにびびってしまった
今回のチーム開発はなんでも作ることができます。人工知能でもVRゲームでも3DCGでもそれこそハード系のものを作ってもいいわけです。

そんな中で僕は一般的なウェブアプリにアイデアを決めてしまいました。

なぜ色々な意見があった中それを受け入れずウェブアプリを作ることにしたのか。

それは僕がビビったからです。

僕はこのチーム開発を絶対に完成させたいと意気込んでいました。
しかし、話し合いをしているうちに、こんな初心者の集まりでこんな難しそうなものが作れるのか、とんでもなくしんどい目にあうんじゃないか、みんな諦めてやめていってしまうんじゃないかとそんな気持ちが湧いてきました。

失敗を恐れて消極的な考えを持ってしまったのです。

成功させるためにウェブアプリに絶対したいと思ってしまいました。（決してウェブアプリを作ることが悪いわけではないです）

ウェブアプリならたくさんの資料がネットにあるしみんな作りやすいだろう、ウェブアプリを作る経験はみんなのためになるだろうと、ウェブアプリにみんなを誘導してしまいました。

大学生だし、みんなもっと挑戦がしたかったのかもしれません。
この時点でみんなで作りたいものではなく、僕が作らせたいものになってしまいました。
この頃から僕の中でみんなやる気がない、俺だけが頑張っているという気持ちが湧いてきました。

リーダーがやりたいことをみんなにぶつけて同意形成してから始めるのはいいと思いますが、リーダーがやらせたいことをやらせようとして、他の意見を受け入れる姿勢を失うとよくありません。
気をつけましょう。

### みんなで話ができなかった

もちろん話し合いは定期的にしていました。
ですが、僕の思い、それぞれの思い、これをみんなで話をすることができませんでした。

恥ずかしかったのもあるし、心を開いて相談できるほどみんなを信頼することができませんでした。

そういう話がしやすい環境にすることもできませんでした。
なんだか仕事で話すみたいに業務的な話し合いをいつもしているだけでした。

いまだに当時のみんながどんなことを思って話していたのかわかりません。

思っていることをみんなが言える環境じゃないと、作りたいもの、何を勉強したいのか、思っている不満、何もみんなで共有することができません。

そんな環境では誰もどの方向に進んでいけばいいかわかりません。
ただ漂流することになってしまいます。

そうならないためにみんなが話しやすい環境をリーダーが率先して作っていくのが大事だと思います。

# まとめ
* 何もわからないなら手を動かしながら話し合いを進めていく
* やりたいことをやろう、失敗を恐れたり気を使って縮こまってもあんまりいいことない
* みんな本音で語ろう、そういう環境を作るのがリーダーの大事な役目

# あとがき

今回はアイデア出しまでの話を書きました。
この続きはまた書きます。

まだまだ失敗はありますのでぜひ楽しみにしていてください！

読んでいただきありがとうございました！
【Vue.js】ローディング画面の実装方法（サンプルコード付き）

## はじめに
Vue.jsでローディング画面を実装する方法をサンプルコード付きでまとめました。

今回ローディングのモジュールは[vue-loading-template](https://github.com/jkchao/vue-loading)を使っています。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/483292/9c118e8a-c940-540a-2e47-1ba119bdffcd.png)
デモは[こちら](https://jkchao.github.io/vue-loading/)から確認出来ます。

## 環境
```yaml
OS: macOS Catalina 10.15.1
Vue: 2.6.10
vue-cli: 4.1.1
vue-router: 2.6.10
vuex: 3.1.2
vuetify: 2.1.0
```
## vue-loading-templateのインストール

```shell
$ yarn add vue-loading-template
```


## 1.`src/App.vue`

```vue:App.vue
<template>
  <v-app>
    <Loading v-show="loading"></Loading>
    <Home v-show="!loading"></Home>
  </v-app>
</template>

<script>

import Loading from '@/components/Loading'
import Home from './views/Home'

export default {
  name: 'App',
  data() {
    return {
      loading: true,
    }
  },
  mounted() {
    setTimeout(() => {
      this.loading = false;
    }, 1000);
  },
  components: {
    Loading,
    Home,
  },
};
</script>
```

### 前提
- **Vuetify**を使用しているので、`<v-app>`でくくられている

- `Loading`は**ローディング画面**コンポーネント
- `Home`は**アプリケーション本体**をまとめているコンポーネント

### ローディング画面の切り替え方法
- `v-show`を使用し、変数`loading`が`true`か`false`かでローディング画面の表示・非表示を行う

- 切り替えは`mounted`を使用

- `mounted`はDOMの作成が完了した段階で発動するので、
DOMの作成が完了した段階で`loading`が`false`になり、ローディング画面が非表示になる

### 2.`src/components/Loading.vue`
こちらが**ローディング画面**のコンポーネントです。

```vue:Loading.vue
<template>
  <div v-show="loading">
    <div class="fullview">
      <div class="loading-spacer"></div>
      <vue-loading 
        type="spiningDubbles"
        color="#aaa"
        :size="{ width: '100px', height: '100px' }"
        >
      </vue-loading>
    </div>
  </div>
</template>

<script>
import { VueLoading } from 'vue-loading-template'

export default {
  name: 'loading',
  components: {
    VueLoading,
  },

}
</script>

<style>
.fullview {
  width: 100%;
  height: 100%;
  background: #fefefe;
  position: fixed;
  top: 0;
  left: 0;
}
.loading-spacer {
  height: 30%;
}
</style>
```
- `VueLoading`をインポート

- `<vue-loading>`内で各種オプションを指定し、ローディングアニメーションの種類・色や大きさを指定

- `<div class="loading-spacer">`はローディングアニメーションを**画面上部から任意の位置**に持ってくるために利用


## おわりに
最後まで読んで頂きありがとうございました:bow_tone1:

ローディングアニメーションは**spiningDubbles**が好きです:v:

## 参考にさせて頂いたサイト（いつもありがとうございます）
- [Vue.jsでシンプルなローディングを表示する「vue-loading」の使い方 ｜ Developers.IO](https://dev.classmethod.jp/client-side/vue/vue-loading/)
- [GitHub - jkchao/vue-loading: 😄 vue-loading 😊](https://github.com/jkchao/vue-loading)