OmniAICreator/Qiita-1.07M huggingface dataset:
Angular with devcontainerで遅すぎて困った話

## ng serveが進まない

ぼく「凍結してたAngularプロジェクトを再開するぞ」

ぼく「Angularのバージョンアップついでにdevcontainerに移行しよう」

ぼく「``ng update --force``かけて、色々と更新したろ。」

ぼく「あとは他のライブラリもまとめてバージョンアップやな」

ぼく「おーわりっと。ちゃんと動くか``ng serve``して確認しよう」

〜〜５分後〜〜

ぼく「はて、``ng serve``のログすら一切流れてこんのだが。

ぼく「初めからやろう。``rm -rf node_modules``っと。」

〜〜10分後〜〜

ぼく「なんも消えてないんだが？？？」


## 原因？

ぼく「もしかして、コンテナにローカルボリュームをアタッチしているせいでIOが異様に重くなっている？」

ぼく「しゃーない。node_modulesだけでもVolumesにアタッチすっか」


## devcontainerの構成

以下のように、.devcontainerディレクトリを使う方式でdevcontainerを構成。

元々はVSCodeから生成できるdevcontainerのテンプレートを使っていたが、
上記の理由により全体的に変更をしていきます。

```shell-session
/ Project-Root
   ├ /.devcontainer
   │   ├ devcontainer.json
   │   ├ docker-compose.yml
   │   └ Dockerfile
   ├ /src
   ├ /e2e
   ├ angular.json
   ├ ...
  (その他略)
```

### 変更後の各ファイル

devcontainerは恐らくほぼデフォルト。

```json:devcontainer.json
{
    "name": "My App",

    "dockerComposeFile": "docker-compose.yml",
    "service": "app",
    "workspaceFolder": "/workspace",

    "settings": {
        "terminal.integrated.shell.linux": "/bin/sh"
    },

    "extensions": [
        "dbaeumer.vscode-eslint",
        "johnpapa.angular-essentials"
    ],
    "forwardPorts": [4200],
}
```

Dockerfileも、Dockerhubの公式Nodeイメージを使用するように変更。

```Dockerfile:Dockerfile
FROM node:14.15.4-buster

RUN npm install -g @angular/cli

EXPOSE 4200
```

最後に、docker-composeがキモ。

```yaml:docker-compose.yml
version: '3'

services:
  app:
    build: .
    tty: true
    volumes:
      - node_data:/workspace/node_modules
      - ../:/workspace:cached
volumes:
  node_data:
```

- ``node_data``という名前のボリュームを切る
- node_modulesに作成したボリュームをアタッチ

こうすることで、ローカルにはnode_modulesを置かなくなるので、
ある程度は早くなるらしい。

## やってみた

ぼく「うん、若干遅いけど数秒もあればビルドが始まるな。」

ぼく「これでなんとかなるな。」

ぼく「うーん。エラーはないけどレイアウト崩れまくっとるな」

ぼく「さすがに8->11はやりすぎたかな？」

## まとめ

- Angularはnode_modulesが肥大化するので、devcontainer使ってる場合は注意。
- バージョンアップはこまめにしましょう。

### さいごに

Angular on devcontainerのベストプラクティスがあったらどなたか教えてください・・・
【Vue.js】v-ifとv-showによる表示、非表示の切り替えの違い

```sample.vue

<script src="https://cdn.jsdelivr.net/npm/vue@2.5.16/dist/vue.js"></script>

<div id="app">
  <button @click="changeShow">ボタン</button>
  <p v-if="isActive">if</p>
  <p v-show="isActive">show</p>
</div>

<script>
  new Vue({
    el: '#app',
    data: {
      isActive: true
    },
    methods: {
      changeShow() {
        this.isActive = !this.isActive
      }
    }
  })
</script>
```
上記の様な、ボタンをクリックすると、「if」の文字と「show」の文字の表示・非表示が切り替わるプログラムがある。

v-ifの場合は、条件がfalseの場合、DOM自体

```
<p v-if="isActive">if</p>
```

が消滅する。

v-showの場合は、条件がfalseの場合、DOMに display:none　が追加されて非表示となる。

```
<p style="display:none">show</p>
```

##v-showのデメリット
・非表示時の挙動は、ページ読み込み時に一旦、全てのDOMを読み込んでからdisplay:noneで非表示にするため、DOMそのものを読み込まないv-ifに比べて初期読み込み時の動作が重くなる。

・v-elseのように、falseの場合に別処理を実行することができない。

・<templete>タグには使用できない。(templeteタグはそもそもhtmlに表示されないので、display:noneのつけようがない）

##v-ifのデメリット
表示・非表示の切り替え時に、DOMを直接操作するため、display:noneを与えるだけのv-showに比べて、動作が重くなる。

#適材適所は？
頻繁に表示・非表示を切り替える必要がある場合は、"v-show"。それ以外は、"v-if"を使うのがベター。
VBAでセルの値をフォルダ名としてmkdirしたかっただけ

メモ。
[VBAリファレンス(DIr)](https://docs.microsoft.com/ja-jp/office/vba/language/reference/user-interface-help/dir-function)


```

Sub createFolder()

    Dim targetDir As String: targetDir = "C:\test\"
        
    Dim i As Integer: For i = 1 To Cells(Rows.Count, 1).End(xlUp).Row
        Dim newDir As String: newDir = targetDir & Cells(i, 1).Value
        If Dir(newDir, vbDirectory) = vbNullString Then MkDir newDir
    Next i
    
    Debug.Print ("end")
    
End Sub

```
３週間で備えるAWS Certified Developer - Associateへの道

#はじめに
某ベンダで、クラウドの人材育成企画と研修トレーニングのデリバリを担当しています。自分で企画した「Developing on AWS」のトレーニング講師を務めることとなり、前提となる「AWS Certified Developer - Associate」（DOA）を受験することになりました。試験に備えて***ガッツリ***勉強したので、勉強ノウハウを共有したいと思います。

#勉強教材とスケジュール
DOA受験に際し、３週間の準備計画を立てました。ここ数年は企画畑を歩き回った分、開発現場から遠のいたので準備期間は長めに設定しました。長期戦になるとモチベーション維持が難しので、僕的には３週間の準備期間が、丁度良い結果となりました。

以下、受験に利用した教材です。

・[**A CLOUD GURU**] (https://acloudguru.com/)
AWS Solution Architectは、Amazon.co.jpで探すと試験対策問題が沢山見つかるのですが、DOAはピンポイントの対策問題集がないので、CLOUD GURUを利用しました。

全編英語版ですが、DOA以外の受験にも利用できること、AWSのイベントでよく見かけるベンダだったこと、ビデオ教材以外にオリジナルの模擬試験があったことが選定の決め手になりました。

・[**「AWS 認定 デベロッパー アソシエイトサンプル問題を解説します」**](https://qiita.com/hirosys-biz/items/a742fbae766ecc487f68)
 AWSが公開しているサンプル情報に注釈を入れた解説記事です。執筆された方はAWS Ambassadorの方ですかね、丁寧に解説が入ってます。シリーズものでDOA以外にも執筆されているようです。

・[**Exam Readiness: AWS Certified Developer – Associate (Japanese)**]
  (https://www.aws.training/SessionSearch?pageNumber=1&courseId=18953)
 AWSが提供している無償のデジタルトレーニングです。（APNアカウント前提？）試験のトピックの分野を詳しく学習し、都度分野ごとの理解度を確認できます。
　
・[**AWS サービス別資料（通称ブラックベルト）**](https://aws.amazon.com/jp/aws-jp-introduction/aws-jp-webinar-service-cut/)
サービス毎の概要がプレゼン形式で、わかりやすく丁寧に整理されています。個々の仕様書を読み込むのは骨が折れるので、毎回の試験時にお世話になるサイトです。今回は試験に関連する開発系の以下のサービスを読み込みました。

・AWS Lambda
・Amazon API Gateway
・Amazon DynamoDB
・AWS Step Functions
・Amazon ElastiCache
・AWS CodeCommit
・AWS CodeBuild
・AWS CodeDeploy

・**「AWS 設計のベストプラクティスで最低限知っておくべき 10 のこと」**の丸暗記
　基本の 「基」、AWS設計のベストプラクティスを丸暗記します。

    1.    スケーラビリティを確保する
    2.    環境を自動化する
    3.    使い捨て可能なリソースを使用する
    4.    コンポーネントを疎結合にする
    5.    サーバではなくサービスで設計する
    6.    適切なデータベースソリューションを選択する
    7.    単一障害点を排除する
    8.    コストを最適化する
    9.    キャッシュを使用する
    10.    すべてのレイヤーでセキュリティを確保する
    11.    +1. 増加するデータの管理

#勉強の過程
張り切って３週間の計画を立てたものの、、、年末を挟んでしたまったことでスタートダッシュに乗れず。子供のクリスマスプレゼントにした「鬼滅の刃」に親が没頭する羽目になり朝晩漫画漬けの日々。。。。（いやー、鬼滅の流行にはそれなりの根拠あり、面白い。)結局、２週間で試験対策することになりました。

まず最初に力試しに「AWS 認定 デベロッパー アソシエイトサンプル問題を解説します」に挑戦しましたが、半分くらいしか正答しない結果に。。。少し焦りを感じながら、CLOUD GURUの模擬試験を 2週間の間ひたすら繰り返しました。

模擬試験は、実際の問題に近い形式で非常に良くできています。全文英文なのですが、技術英語なので、そんなに難解な英単語は出てきません。最初は慣れないため時間がかかるものの、２０回近く繰り返すと英単語から正解が見えてきました。（これが後述の試験本番で大きな助けになった。）理解が浅い部分は、ブラックベルトでを見直しながら、正当率が９割近くになるまで”ガッツリ”模擬試験を繰り返しました。

試験１週間前には、Exam Readinessにトライしました。
さすがAWSの公式トレーニングだけあって、ポイントが綺麗に整理されていて、非常に秀逸です。内容は日本語、サンプル問題よりも難易度は低めな印象です。
   
「AWS 設計のベストプラクティスで最低限知っておくべき 10 のこと」は朝晩、マントラのごとく唱えて暗記しました。AWSの試験全般に言えることですが、選択問題だと割と最後の２択で迷うこと多くなります。一見、どっちも技術的には正解ポイですのが、”AWSとして正解”が回答として設定されているため、AWSのベストプラクティスに沿った回答を導く必要があります。この時に暗記したベストプラクティスが役に立ちます。

#試験当日
横浜のピアソン会場で受験しました。コロナの影響か、試験会場はあまり混んでおらず、試験2日前に予約しました。

実際の試験問題はAWSサービスと同じく定期的にupdateされているのか、想定した問題とは違う問題が出てきて、最初の10問といた時点でかなり焦りました。（直前まで聞いてたMegadethのSkin o' My Teethが頭の中で何度もリピート）

頭の中はメタル、問題和訳はメタメタで、これまで受験したAWS試験の中で、一番日本語になっていない和訳問題でした。幸いCLOUD GURUで**英語問題に慣れてたこと**、**基礎をしっかり学習できていた**ため、その場で対応することができました。

結果は800後半で、想定したよりも得点をとることができていました。（ふー）

#所感
AWSのサービスと同じく、DOAの試験内容も日々更新されるためか、模擬試験とは少し設問が違いました。単にサービスの名前を覚える一問一答な問題ではなく、サービス内容を深く問われる内容が多かった印象です。”AWSのサービスが、開発時におけるどのような問題を解決するか？”を意識しながら基礎学習を繰り返すと突破できる試験だと思います。
お前が人間スペルチェッカーになるんだよ

# はじめに
最近, 同僚の"wizerd"というスペルミスを直したため, スペルチェッカーを導入しないといけないなと思いました. Google先生お助けくださいと調べてみると, スペルチェック, スペルチェッカーの記事自体が, 誤字, 脱字の雨霰. どうなってんだこの国は.

## 人間は間違えるものなんだよ
間違えるからこそ, 自分自身にも疑いの目を向けないのかね？ 私が最も信用していない人間は私なのですが.

# お前が~~パパ~~スペルチェッカーになるんだよ
画像や動画は, 人間がスペルチェッカーになった方がいいと思います. AI, 機械学習万能と思っている人には悪いですが, 精度もコストも人間の方がずっと上です. 欠点は, 見ないことにはどうにもならない, 自動化ができないことです.

# まとめ
スペルチェッカーを悪くいうつもりはなく, 自らの誤字, 脱字に無頓着な人は, 道具を用意するより先に自らの姿勢を改めればどうですか？という提案です.
中央値を使ったデータフレームからの抽出

# データフレームから中央値を使った抽出の仕方

## 概要

最近は分析時にもベイズ的な観点を持って作業を行う事があり、
モデルを複数作成し、分析結果をbroomでデータフレームに保存し、
その中から各説明変数の評価を取り出したいと思った。
その際に、p.valueから適切なスコアを取り出したいと思ったが、
p値は最小値が0に収束していくのに対して、最大値は0.7などの値を取るため、
平均を取り出して評価すると説明変数を過小評価することになるため、
中央値を取り出すこととした。

だが中央値をsummariseで取り出してしまうと、それとペアとなっているestimateが取り出せないため、
事前にmedianで取り出したp値とイコールとなるp値を取り出そうとしてみるが、
変数の数が奇数であれば、中央値は一意に定まるが、偶数だと平均を作ってしまうため、
イコールで一意に定まらず、取り出せない事があったので、別の解を検討してみる。

### 使用していたライブラリ

- tidyverse

### うまく行かなかったケース

```R

broomed_DF %>% 
  group_by(term) %>% # 説明変数をグループ化する 
  mutate(median_pvalue = median(p.value)) %>% 
  filter(p.value == median_pvalue) # ここで想定したレコード数よりも減りすぎている


```

#### 行ったこと

- filter時にround関数をかけてn桁までで一致するものを取り出そうとしてみるがうまくいかない

### うまく行った方法

```
broomed_DF %>% 
  group_by(term) %>% # 説明変数をグループ化する 
  mutate(rank_pvalue = rank(p.value)) %>% # rank関数で整数の順序をつける
  mutate(rank_median_pvalue = as.integer(median(rank_pvalue))) %>% # median関数で中央値を取り出すが、同時に整数にすることで偶数時にも一意にスコアを取り出せる
  # この方法はどちらか片方に任意にすることには向いていないため、どちらでも大きく影響しないだろうというときに利用すると良い
  filter(rank_pvalue == rank_median_pvalue) # すべての変数について中央値を抽出できる

```
[Rails]postgreでDB作成が失敗したときに確認すべきこと

#前提
既にRailsのアプリ開発するための環境構築は完了している

#アプリ新規作成

```
$ rails new 〇〇 -d postgresql  //〇〇にはアプリ名が入る
```
postgreSQLを使用するため、「-d」オプションでデータベースの指定をしています。

アプリ新規作成ができたら

```
$ cd 〇〇  //先程入力したアプリ名のディレクトリに移動
```

# データベース作成

```
$ bin/rails db:create
```

コマンド打ったら本来は下記が表示されますが

```
Created database '〇〇_development'
Created database '〇〇_test' 
```

私の環境下では

```
could not connect to server: No such file or directory
	Is the server running locally and accepting
	connections on Unix domain socket "/tmp/.s.PGSQL.5432"?
Couldn't create 'scaffold_app_development' database. Please check your configuration.
rails aborted!
ActiveRecord::ConnectionNotEstablished: could not connect to server: No such file or directory
	Is the server running locally and accepting
	connections on Unix domain socket "/tmp/.s.PGSQL.5432"?
/Users/▲▲/dev/rails/scaffold_app/bin/rails:5:in `<top (required)>'
/Users/▲▲/dev/rails/scaffold_app/bin/spring:10:in `block in <top (required)>'
/Users/▲▲/dev/rails/scaffold_app/bin/spring:7:in `tap'
/Users/▲▲/dev/rails/scaffold_app/bin/spring:7:in `<top (required)>'

Caused by:
PG::ConnectionBad: could not connect to server: No such file or directory
	Is the server running locally and accepting
	connections on Unix domain socket "/tmp/.s.PGSQL.5432"?
/Users/▲▲/dev/rails/scaffold_app/bin/rails:5:in `<top (required)>'
/Users/▲▲/dev/rails/scaffold_app/bin/spring:10:in `block in <top (required)>'
/Users/▲▲/dev/rails/scaffold_app/bin/spring:7:in `tap'
/Users/▲▲/dev/rails/scaffold_app/bin/spring:7:in `<top (required)>'
Tasks: TOP => db:create
(See full trace by running task with --trace)
```

が表示されました。（▲▲はPCのユーザー名が入るはずです）

#データベース作成失敗の原因
こちらを参考にさせていただきました。
[postgresqlでDBが作れなかったのを解決(してもらった)]
(https://haayaaa.hatenablog.com/entry/2019/01/23/111745)

記事の内容をまとめると
①まずログ（`/usr/local/var/log/postgresql`）を確認する
②エラーログの出力箇所を見つけ、内容を確認する

私の場合、エラーログは下記の通り出力されていました。

```:/usr/local/var/log/postgresql
The data directory was initialized by PostgreSQL version 11, which is not compatible with this version 13.1.
```

postgresqlのデータディレクトリがバージョン11なのに、バージョン13のpostgresqlも入ってしまっていたせいで上手く行かなかったようです。

解決方法としては
`brew install`でバージョン11のpostgresqlを入れ直すか、
データディレクトリを消してどちらも13をインストールし直す必要があるとのことでした。

#解決方法(データベース作成)
先程あげた解決方法のうち、今回はデータディレクトリを消すことにしました。
まずは、データディレクトリとhomebrewを削除します。

```
ディレクトリの削除
$ rm -rf /usr/local/var/postgres
```

```
homebrewの削除
$ brew uninstall --force postgresql
```

次にpostgresqlのインストール、そしてディレクトリを再作成します。

```
postgresqlのインストール
$ brew install postgresql 
```

```
ディレクトリ再作成
$ initdb /usr/local/var/postgresql -E utf8
```

PostgreSQLサーバの起動します。

```
$ brew services start postgresql
```

最後にfishの設定ファイルにパスを追記します

```
vimで設定ファイルを開きます。
$ vim ~/.config/fish/config.fish
```

```
以下の内容を追記します。
export PGDATA="/usr/local/var/postgres"
```

```
読み込ませます。
$ source ~/.config/fish/config.fish
```

ここまで行った後にデータベースを作成します。

```
bin/rails db:create
```

上手くいくと下記が表示されます（アプリ名：scaffold_app）。

```
Created database 'scaffold_app_development'
Created database 'scaffold_app_test'
```
Alfred 4 で絵文字と絵文字コードを検索する

テキストを編集しているときに絵文字の入力が面倒です。
"かお" と入力してスペースバーを何度も押して "😃" に変換したり…。

slack のように ``` : ``` で絵文字検索できると便利だなと思って探してみたら、Alfred の Workflow が公開されていたので使ってみました。

### 環境
- macOS 11.1
- Alfred Powerpack 4.3.1

こちらから Workflow をダウンロードします。
[Search Emoji codes and symbols using Alfred 2](https://github.com/carlosgaldino/alfred-emoji-workflow)
ダウンロードした emoji-codes.alfredworkflow をインストールします。
Alfred の Workflows に Emoji codes が加わります。

### 使い方
Alfred を開いて ``` emoji [query] ``` を入力します。
```[query]```の部分は😄ならば ``` emoji smile ``` です。
![スクリーンショット 2021-01-28 23.58.55.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/38728/c65eabe2-96a1-dc56-137a-685ad3962082.png)
絵文字を選択するときに option key を押すことで絵文字の emoji code をコピーすることができます。
😄の emoji code : ``` :smile: ```

それでは👋
【kotlin】flowで非同期処理やローディングをいい感じにやりたい

# はじめに
本記事は主に初心者向けの記事になります。

-> Androidで非同期処理するにはコルーチンを使えばいいみたい。
-> 最近はflow, channelが熱いとか。
-> 基本的な使い方はわかったけど実際どんな感じで使えばいい？

って感じの方向けです。(自分の備忘録も兼ねてます)

#今回やること
以下の動作をする機能を実装します。

- APIリクエストを投げる
- レスポンスが返ってくるまでローディングを表示
- APIリクエストエラーハンドリング

#実装

成功、失敗、ローディングなどの状態を管理するために、リクエストのresultなどをラッピングするクラスを作って定義します。

```kotlin
sealed class State<T> {
    class Loading<T> : State<T>() // ローディング中
    data class Success<T>(val data: T) : State<T>() // 成功時
    data class Failure<T>(val e: Throwable) : State<T>() // 失敗時
}
```

この`State`クラスを使ってflowで流れてくるデータを判別して各々に処理を書きます。
今回はダミーの`weather flow `データを取得するweatherAPIをコールします。

```kotlin
val repository = WeatherRepository()
repository.getCurrentWeather()
    .flowOn(Dispatchers.Default) // これより上のflowの実行コンテキストの指定
    .onEach { result ->
        when (result) {
            is State.Loading -> {
                showLoadingProgress() // loadingDialogとかの表示
            }
            is State.Success -> {
                // do something
                Log.d("### flow result ###", result.data.toString())
                hideLoadingProgress() // loadingDialogとかを消す
            }
            is State.Failure -> {
                // do something
                Log.e("### flow result ###", result.e.stackTraceToString())
                hideLoadingProgress() // loadingDialogとかを消す
            }
        }
    }
    .launchIn(lifecycleScope) // 動作するコルーチンスコープの指定
```

`result`からAPIのレスポンスを取得できます。

`onEach`や`launchIn`は書き方が少し違うだけで以下と同じです。こっちの方がネストがちょっと浅くなって個人的に好き。

```kotlin
CoroutineScope.launch{
    flow.collect { result ->
        ...
    }
}
```

内容的にはflowで流れてきたデータをラッピングクラスのインスタンスで分けて処理をしていくだけです。

`repository`に関してはこんな感じになってます。
なお、`requestWeatherApi`は`suspend`関数です。

```kotlin:WeatherRepository.kt
class WeatherRepository(
    val weatherDataSource: WeatherDataSource = WeatherDataSource()
) {
    fun getCurrentWeather(): Flow<State<Weather>> = flow {
        val result = try {
            val weather = weatherDataSource.requestWeatherApi()
            State.Success(weather)
        } catch (e: Throwable) {
            State.Failure(e)
        }
        emit(result)
    }.onStart {
        // collectされた時にローディング状態を最初に流す
        emit(State.Loading())
    }
}
```

`try-catch`でエラーをキャッチし、flowのオペレータの一つである`onStart`でローディング状態を流します。

`onStart`を使えばflowに最初に流すデータを指定することができます。

flowに流れるデータは
1. `State.Loading()`  (collectされると同時にemit)
2. `State.Success(weather)`　(リクエストが完了したらemit)
になります。

`WeatherDataSource`はこんな感じの3秒待ってデータを吐き出すようなものです。今回はこれをAPIに見立てて実装しています。

```kotlin:WeatherDataSource.kt
class WeatherDataSource {
    suspend fun requestWeatherApi(): Weather {
        delay(3000)
        return Weather("sunny", Date())
    }
}

data class Weather(
    val weather: String,
    val date: Date
)
```

#おわり
短いですがこれにて終わりになります。
Utillクラスとかを作るともっとボイラープレート減ってよくなりそう。。。

rx java使いにとってはflowはとってもなじみやすくなりそうですね。自分はまだまだですが。
オペレータとかも一部previewとかexperimentalとかありますがstableになってきたりしているので今年から本格的に導入されていく気がする。
「新しいLinuxの教科書」のレビュー(お試し投稿)

みなさんこんにちは, spchanです. 
今回は初めてのQiita投稿ということで, 現在読んでいる**新しいLinuxの教科書**のレビューをしたいと思います.
#本の概要
まずは本の概要について説明します. この本では, Linux初心者がLinuxをインストールするところからLinuxの基本操作, vimの操作の簡単な説明, Gitの簡単な説明などなど, 幅広い知識を得ることができます.amazonでLinuxと検索したところ, 最も上位に上がっていたのがこの本であったため購入しました.
#良い点
現在読んでいるところまでで良かった点を述べます.
###1. 新しい単語が出た時にその説明をしたり, 後ほど説明することを伝えてくれる
巷にはあらゆる技術本が出回っていますが, 新しい単語が説明もなく突然出てくる本がたくさんあります. しかしこの本は初心者が１からLinuxを学べるように配慮がなされており, スムーズに読むことができます.
###2. chapter分けが効果的
この本は全部で20のchapterに分けて説明がなされているのですが, あるchapterを読んで飽きてくる頃にちょうどchapterの終わりに近くなっていて, あとちょっと読んだら休憩しようとなってとても良いです.(個人差あり)
#悪い点
###今のところありません
Linuxの説明に必ずあると言っても良いLinuxの歴史についての説明はありません. しかしこの本では初心者がLinuxを身につけることに重点を置いているため, 歴史の部分を省いた方が学習がスムーズにいきます.
#終わりに
今までいくつかのLinuxの本を読んできましたが, この本が最も幅広く丁寧に説明されていた印象を受けました. とてもおすすめです!
以上でレビューを終わります. 
最後まで読んでくださってありがとうございました.
XMLマスター：ベーシックを令和に受験して合格した話

<h1>はじめに</h1>
SIer界隈の方ならもしかしたら聞いたことのあるかもしれない資格、
「XMLマスターベーシック」という名のマイナー資格を取得しました。

勉強方法や当日の試験の内容などをまとめていきます。
<h1>XMLマスターとは</h1>
私が今回受験したベージックは一番簡単なものになります。<br>
公式サイトに詳細があるので参考までに。
http://www.xmlmaster.org/certification.html


<h1>前提知識と勉強時間</h1>
■前提知識
・業務でここ半年くらい毎日触っている。(要素の数値をいじる位で仕組みなど微塵も分からない)
・HTMLと同じマークアップ言語なので親戚か何かだと思っている。
・半年触っていたが1から作成したことがないので、エラー出たら詰む。
・XSDとかスキーマとか言われても分かりません。

■勉強時間
去年の10月くらいから参考書を読み始めて、受験したのは11月末に受験したので2ヶ月位勉強した。
平日は2日に一回一時間くらい参考書を読んだり、問題を解いたり。
11月の土日は計10時間くらいやっていました。

全て合計したら60h位？

<h1>勉強方法</h1>
使用した参考書を2冊です。

・XMLマスター教科書 ベーシックV2
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/976640/830e2535-af7d-d0b5-36d4-3e63c70746b2.png" width=200px>
緑本と言われている書籍です。
XMLを一度も触ったことがない人向けにかなり丁寧に解説が載っています。
HTMLなどのマークアップ言語の理解がある人には少し丁寧すぎるかもしれないですが、
XMLマスターベーシック自体の難易度が易しめであるのでとりあえずこれがあれば問題ないと思います。

・徹底攻略XMLマスター ベーシック問題集 V2試験対応
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/976640/131cf48f-e460-1940-73ef-c8060b17fc76.png"width=200px>
俗に言う黒本です
緑本にも練習問題がありますが、緑本と黒本では問題の難易度が桁違いです。
(緑本は簡単すぎるし、黒本はいきなりやるには難しすぎる)
特に黒本のDTD、XML Schema、XSLTの問題文の長さが凄まじいです。
後述しますが、本番で実際の出題は黒本レベルの長文問題は一個もなかったです。
ただ、緑本では物足りないので黒本で合格ラインを取れるほど学習すれば試験は問題ないので
購入をお勧めします。


・10月頭〜10月末
まずは緑本の内容をざっくりと把握して、緑本の内容量(=試験の範囲)がどのくらいなのかを見極めました。
初めて聞く単語が多かったですが、内容を全て理解するまで読み返すのは効率が悪いので、
「XSLTはXMLの変換ルールなんやなー、詳しい書き方は分からんけど」
これくらいの理解度でどんどん進めていきました。

とりあえず内容を一周してからは単元毎に集中的に学習をするように意識しました。
緑本は大きく分けて6単元あるので、
①1単元を2日間で復習して問題を解く
②間違えたところを再度復習
③次の単元の問題を解く
④一つ前の単元を再度復習
こんな感じのルーティンで学習して、「確実に勉強したけど抜けてしまった・・」
という状況を少しでも減らすように意識しました。
緑本の単元別問題も解けるようになったら、黒本の単元別問題を解きましょう。
急にレベルがあがりますが、本番よりやや難しいですが分からなくても
そこまで気にしなくていいと思います。


・11月頭〜受験
受験2週間くらい前からはひたすら黒本の模擬試験を解いていきました。
本試験は60分で50問出題ですので、時間配分をかなり意識して進める必要があります。
ちなみに黒本の模擬問題は難易度もそこそこ高く文章量もかなり多いので、
初めて解いた時は正答率は40%位しか届きませんでした、、、。
模擬試験は3週くらいして、最終的には80％くらいまで上がりました。

<h1>試験結果</h1>
結果はボーダーぴったりの正答率70％でクソギリギリの合格でした。
単元毎の正答率はこんな感じです。

・XML概要　　　　71％
・XML文章の作成　66％
・DTD　　　　　　80％
・XML Schema 　 80％
・XSLT,Xpath　　 70％
・名前空間　　　　33％

本番の試験は、黒本レベルの難易度はほぼ無く
一番時間が掛かるであろうXSLTの問題の文章量も緑本と同レベルの物ばかりでした。(黒本の半分くらい)
また本番の試験では選択問題の回答数が指定されているので、
黒本のように複数回答の問題で回答数が足りなかったり多かったりすることは無くなります。

体感的には8割は超えたと思っていたのですが、
結果見ると「XML概要」や「XML文章作成」が少し足を引っ張っています。
本来はここは取るべき単元で、後半の単元で時間との勝負になるので少し油断していました。
<h1>さいごに</h1>
ほとんどいないと思いますが、もしXMLマスターベーシックを受験予定の方の参考になれば。
IE11でテンプレートリテラルは使えない


#例
```html:index.html
<!doctype html>
<html lang="ja">
<head>
  <meta charset="UTF-8">
  <title>JavaScriptドリル</title>
</head>
<body>
  <script src="script.js">  </script>

</body>
</html>
```

```javascript:script.js
//キーイベント
document.addEventListener('keydown',function(event){
    var keyName = event.key;
    if(event.ctrlKey){
        console.log(`keydown:${keyName}`);
    } else if (event.shiftKey) {
        console.log(`keydown:${keyName}`);
    } else {
        console.log(`keydown:${keyName}`);
    }
});
 ie
```

#Chrome
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/700136/b1b9fa2f-1836-5be3-999e-92815307dc19.png)

#IE
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/700136/c2bb415f-3648-4c12-44b9-43da54d92498.png)
Railsアプリ作成のための下準備

#Railsのインストール
Railsのインストールをおこないます。参考文献に従い、バージョンは5.2.1を選択。

```
$ gem install rails -v 5.2.1
```

無事インストールできました！！

#アプリの雛形作成
アプリの雛形を作成します。

```
$ rails new tweet_app -d mysql
```

アプリケーションディレクトリに移動して…

```
% cd test_app
```

データベースを作成します。MySQLを起動した状態で次のコマンドを入力。

```
$ bin/rails db:create
```

これでDBが作成される…と思ったら、エラーが。

```
Mysql2::Error::ConnectionError: Access denied for user 'root'@'localhost' (using password: NO)
```

数時間対処法を探しましたが、一向に解決しないので急遽PostgreSQLを使うことに。

Homebrewでインストールし、先程の手順まで戻ります。

```
$ bin/rails db:create
```

今度は無事にDBが作成されました！
続いてサーバーを起動します。

```
$ bin/rails s
```

サーバーを起動させたら、ブラウザでhttp://localhost:3000 にアクセスします。
（サーバーを終了させるには[Control + C]）
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/999125/b43d2356-6ffa-0ef6-7b92-4f3268d7be34.png)

画像の通り、正常に動作しています。

#Slimの導入
Railsを用いた開発では、アプリの画面を「ERB」というテンプレートエンジン（最終的なHTMLを生成する仕組み）を使用しています。
その他に、ERBよりも簡潔な書き方ができる「Slim」があります。今回はこちらを使用することにします。
Slimの導入には2つのgemを使用します。

1.slim-rails: Slimのジェネレータを提供する
2.html2slim: ERB形式のファイルをslim形式に変換する

アプリのGemfileに定義し、

```
gem 'slim-rails'
gem 'html2slim'
```

bundleコマンドでインストール。

```
$ bundle
```

これで、生成されるテンプレートファイルはSlim形式になりました。
現時点でapp/views/layoutsディレクトリ内にERB形式のファイルが3つあるので、以下のコマンドでSlim形式にします。

```
$ bundle exec erb2slim app/views/layouts/ --delete
```
bundle exec [コマンド]で、Bundler管管理下のgemを利用できる状態でコマンドを実行します。

#BootstrapとSassの導入
自力でCSSを組むのは大変なので、フロントエンドフレームワークのBootstrapを導入します。
Gemfileに以下を追記し、bundleコマンドでインストール。

```
gem 'bootstrap'
```

CSSにもSlimと同じように効率的な書き方の形式「Sass」があります。
今回はSassの提供する、「SCSS」記法でCSSを買いていきます。

まず、app/assets/stylesheets/application.cssを削除し、

```
$ rm app/assets/stylesheets/application.css
```

app/assets/stylesheets/application.scssを作成し、以下をファイルに記述。

```
@import "bootstrap";
```

これで、画面をBootstrapが反映された状態にすることができます。
次に、見栄えを具体的に改善するため、app/views/layouts/application.html.slim
ファイルを以下のように編集します。

```
doctype html
html
  head
    title
      | TweetApp
    = csrf_meta_tags
    = csp_meta_tag
    = stylesheet_link_tag    'application', media: 'all', 'data-turbolinks-track': 'reload'
    = javascript_include_tag 'application', 'data-turbolinks-track': 'reload'
  body
    .app-title.navbar-expand-md.navbar-light.bg-light
      .navar-brand Tweet_app
    .container
    = yield
```

#エラーメッセージの日本語化
Railsのエラーメッセージは英語ですが、日本語にすることができます。
日本語翻訳ファイルがGitHub上にあるので、ダウンロードしましょう。

```
$ wget https://raw.githubusercontent.com/svenfuchs/rails-i18n/master/rails/locale/ja.yml --output-document=config/locales/ja.yml
```

続いて、デフォルトで日本語コンテンツを使うようにアプリの設定を変更します。
config/initializers/locale.rbを作成し以下を記入。

```
Rails.application.config.i8m.default_locale = :ja
```

これで、アプリ製作の下準備は完了です！

#参考
[現場で使える Ruby on Rails 5速習実践ガイド](https://www.amazon.co.jp/gp/product/B07JHQ9B5T/ref=ppx_yo_dt_b_d_asin_title_o03?ie=UTF8&psc=1)
2021年版Let's EncryptでのSSL証明書の発行方法/SSL化の方法

# 背景
これまでcertbot-autoで証明書の発行ができたと思いますが、2020年12月のリリース1.10.0からDebian系で非対応になり、2021年1月のリリース1.11.0では全てのOSで非対応となりました。certbot-autoではできなくなってしまったので、新しい設定方法を紹介します。

詳細や経緯はこちらから
[Certbot-auto no longer works on Debian based systems](https://community.letsencrypt.org/t/certbot-auto-no-longer-works-on-debian-based-systems/139702/7)
※記事タイトルではDebianといっていますが今では全OS非対応のようです。

# 現象
従来のやり方で証明書の発行を試みると、次のようなエラーが出ると思います。
Your system is not supported by certbot-auto anymore なので、もう非対応だよということです。

```
$ sudo ~/certbot/certbot-auto --no-bootstrap certonly --webroot -w /usr/share/nginx/html -d <独自ドメイン名> -m <メールアドレス> --agree-tos -n
Skipping bootstrap because certbot-auto is deprecated on this system.
/home/app_admin/certbot/certbot-auto has insecure permissions!
To learn how to fix them, visit https://community.letsencrypt.org/t/certbot-auto-deployment-best-practices/91979/
Your system is not supported by certbot-auto anymore.
Certbot cannot be installed.
Please visit https://certbot.eff.org/ to check for other alternatives.
```

# 設定方法
新しい設定方法は、環境によって変わってくるので、詳細は公式の案内を参考にしていただきたいですが、おおまかに

1. certbot-autoなどの旧式をアンイストール
2. snapdをインストール/アップグレード
3. snapでcertbotをインストール
4. certbotを実行

という流れになります。

詳細はこちらの公式の説明ページで、使用するミドルウェアとOSを指定すると、設定方法が案内されるのでそちらに従ってください。
[certbot instructions](https://certbot.eff.org/instructions)

注：snapdのインストール時には `enable classic snap support` の部分の設定も基本的に必要となると思います（設定しなかったら、snapでcertbotインストールする際にエラーが出ると思うのでわかると思います）

# SSL証明書の自動更新の設定

一部のOSを除いて、今回のcertbotでは証明書の更新を自動でやってくれるみたいです。なので、わざわざcronを設定する必要はないみたいです。必要があったら、先程の公式の説明ページにその旨記述があると思うので、そちらに従うようにお願いします。

# どうしてもcertbot-autoが使いたい場合
非推奨ですが、どうしてもcertbot-autoが使いたかったら下記URLからダウンロードして使える、と公式にありました。ただし、Debian系での動作は保証されていますが、それ以外ではわかりません。また、今後アップデートはないため、セキュリティ上のリスクや、Let's Encryptサーバーとの互換性を失うリスクを許容した上で注意してご利用ください、ということです。

また、実行時には必ず `--no-self-upgrade` をつけて、最新版に自動更新されないようにしてください。

https://raw.githubusercontent.com/certbot/certbot/v1.9.0/certbot-auto
GKEで複数domainを指定したManagedCertificate作成の簡単メモ

## Intro

ManagedCertificateは、googleによってマネージされているSSL証明書です。ドメイン名認証（DV)を行い、 GCPが自動更新と管理をしてくれます。OV、EV系の認証は行いません。

また、external HTTPS LBとSSLプロキシーLBでは使えますが、内部のHTTPS LBでは使えません。

`gcloud`からでなく、`kubectl`を使ってGKEリソースとしてManagedCertificateをデプロイしたい時があります。

**例えば、**

- defaultではないnamespaceにあるIngressなどのリソースから参照したい時（同じネームスペースにないとずっとProvisioningのままで、結局Failする時があります）。`kubens`＋`kubectl`で簡単に同じネームスペースにデプロイできます。
- そのspecを他のGKEのリソースと一緒にyamlとして管理したいです。

## やり方
例えば、以下のようなmanifestで実現できます。

<!--こんなやつです。-->

（exampleのため、シンプルにCloud Endpointsで作ったendpointを指定します）。

```yaml:mycert.yaml
apiVersion: networking.gke.io/v1beta1
kind: ManagedCertificate
metadata:
  name: what-a-cool-cert
spec:
  domains:
  - domain1.endpoints.a-gcp-project-name.cloud.goog
  - domain2.endpoints.a-gcp-project-name.cloud.goog
```
`domains`フィールドが複数形なので、複数ドメインのcertもデプロイできるはず、と想像できます。

しかし、トライすると怒られます:

```bash
The ManagedCertificate "what-a-cool-cert" is invalid: spec.domains: Invalid value: "": spec.domains in body should have at most 1 items
```

GKEの[official docs](https://cloud.google.com/kubernetes-engine/docs/how-to/managed-certs?hl=id#setting_up_the_managed_certificate)で確認すると、`v1beta1`では対応しておらず、そもそも`v1beta1`はdeprecatedのためもう使うな、ということのようです。

↑のdocsでは `networking.gke.io/v1`で複数ドメイン指定の例がありますが、実は`v1beta2`でも行けるようです。

```yaml:mycert.yaml
apiVersion: networking.gke.io/v1
kind: ManagedCertificate
metadata:
  name: what-a-cool-cert
spec:
  domains:
  - domain1.endpoints.a-gcp-project-name.cloud.goog
  - domain2.endpoints.a-gcp-project-name.cloud.goog
```

まず、`kubectl api-versions`でクラスターがこのAPIに対応していることを確認します:

```bash
$ kubectl api-versions
...
networking.gke.io/v1
networking.gke.io/v1beta1
networking.gke.io/v1beta2
networking.k8s.io/v1
networking.k8s.io/v1beta1
...
```

`networking.gke.io/v1`もしくは`networking.gke.io/v1beta2` が存在していればokです。どちらも存在していなければClusterが古すぎてdeprecatedなAPIバージョン（Master version1.15系以前）を使っている可能性があるので、まずClusterのMaster versionをアップグレードしましょう。

`networking.gke.io/v1`はMaster version 1.17系以降存在しているようです。

> 1.15系にでも `networking.k8s.io/v1` というものが存在しているのですが、これではなくて `networking.gke.io/v1`を使うのでご注意ください。


そして正しいネームスペースを指定し、`mycert.yaml`をデプロイしてみると:

```bash
$ kubens the-correct-ns && kubectl apply -f mycert.yaml
managedcertificate.networking.gke.io/what-a-cool-cert created
```

普通のGKEリソースとして確認できます(`mcrt`とは、kubectlリソースの`managedcertificates`の略になります）:

```bash
$ kubectl get mcrt
NAME                AGE   STATUS
an-older-cert       20d   Active
what-a-cool-cert    3m    Provisioning
```


## 注意点

#### domain名は63文字まで

GCPのcloud endpoints APIで、63文字より長いドメイン名を普通に作れますが、ManagedCertificateの中でそういうドメイン名を指定しようとするとこういう怒られ方をします:

```yaml:mycert.yaml

# ...(略)...
spec:
  domains:
  - this-domain-name-is-ok.endpoints.myproject.cloud.goog
  - this-domain-name-is-too-long-and-gke-will-hate-you-if-you-even-try.endpoints.myproject.cloud.goog
```

```bash
$ kubectl apply -f mycert.yaml
The ManagedCertificate "what-a-cool-cert" is invalid: spec.domains: Invalid value: "": spec.domains in body should be at most 63 chars long
```


#### WildCardは使えない

ManagedCertificateはwildcardを使ったdomain指定はダメっぽいので気を付ける必要があるようです。self-managed証明書なら使えます。
LT会で学んだリーダブルコード

## はじめに
先日ラクスさんが運営するオンライン勉強会「リーダブルコード LT会」が開催され、そこで多くの素晴らしい登壇者の方が良いコードの書き方をご教授してくださりました。
自身の学習メモとしてや、LT会に参加できなかった人へ共有できればと思いQiitaにて記事を書こうと思いました。
※ もし登壇者の方で載せて欲しくない！などの苦情ございましたらご連絡ください。すぐ削除対応致します。

## 命名規則

### 接頭辞を使う
- isXXX
- hasXXX
- canXXX

### 明確な単語を選ぶ
**size()**は大きさ？長さ？個数？などいろいろ想像できるため、この場合**height()**や**weight()**など明確な単語を設定する。

### 汎用的な名前は避ける
- **change()**や**tap()**といった汎用的なワードは、変わった・押したという情報しか伝わってこないため、明確にどんなアクションが行われるかを明記する。
- 特にtmp,retval,result,hogeなども汎用的すぎるため使わないほうがいい(らしい)。

### 誤解されやすい名前は避ける
例えば値の有無確認に**valueRead()**はややこしい。
なぜならreadとはこれから読むのか既に読み取ったのかわからない、**isValue()**などの方がわかりやすい。

### ループ変数の名前など、狭いスコープでの名前の省略をしない
- 変数に型のプレフィックスを避ける(str, i , obj)
- work,hoge,とかijkxyzはつかわない

```
for(let i = 0; i < 5; i++) {
  console.log(str[i].length);
}
```

チームメンバーによって狭いスコープの定義が違う場合があったり、後から改修した場合にスコープを広げると他の名前にも影響してくるので初めから省略しすぎないほうがいい(らしい)。


### 一般的な英単語を使う
changeAcquisitionQualificationDate()などの難しい単語を利用した名前をつけない。
誰もが読みやすく認識している英単語を使うべき。

### 適切な命名
オブジェクトや変数は**形容詞 + 名詞**か、**名詞 + 名詞**で。
メソッドは**動詞・目的語**で書く

### 変数に単位や属性をつける
- size → **size_MB**
- speed → **speed_bps**
- password → **plaintext_password**
- html → **html_utf8**

### 状況に応じた具体的な名前を設定する
- **Get()**よりも状況によっては**Download()**などのほうが伝わりやすい


## コメントの付け方

### 短いコードにコメントをつけない
当たり前だが、読めばわかるコードには基本的にコメントは付けない

### 最初からコードを追わせない
全体像理解してなくても途中からでもコードをかけるようにする為のコメントを書く

### 複雑な処理をしているコードにはコメントをつける
特に試行錯誤してやっとできたコードほど、読みにくくないかを確認する
できたーで放置しがちなので注意。

## リファクタリング

### 読みにくいコード
- あちこちにロジックが散らばっているコード
- 大量の「if」のネストがあるコード
- 早期リターンせず、最後まで読まないと処理が確定しないコード
- 変数や関数名の命名が悪く、ソースを読むだけでは処理が理解できないアンリーダブるなコード
- 引数や戻り値に型を宣言せず、I/O(入出力)が理解しづらいコード
- テストがしづらいコード
- 適切なコメントがないコード
- viewファイルにロジックが記載されてある
- 複数のviewファイルや、違うControllerに同じ処理が記載されてある
    - ロジックに変更があった時に修正が大変&バグの可能性が高まる

### 読みにくいコードを対策する
ifの中にfor文、そしてその中にif文...など読みにくいコードの場合、対策としてできるのは

- 関数として切り分ける
- 複数の処理を関数内で持たせるのは避ける
- 早めにreturnする
- 複雑にせざるを得ない場合はコメントを残す
- 引数や戻り値に型を指定しておく
- ロジックを細かく分ける


## 学んだLT会
以上がLT会にて学ばさせていただいた内容でした。
もし興味のある方はまた開催される時にご覧になると大変勉強になると思います。
読んでくださりありがとうございました。

リーダブルコード LT会【登壇初心者の方大歓迎】
https://rakus.connpass.com/event/199845/
[Microsoft] Edge（Chromium版ではない）のブックマークを別のユーザへ移動する

普通であれば、エクスポート/インポートしたり、MSAに紐づければよいのですが、それをできなかったとき（例えば、ドメインアカウントからAADアカウントへ移行とか）のときの方法です。

こちらに解説がありました。
https://gorazy.com/blog/edge-bookmarks-location.html

下記にあるフォルダを新しいユーザへコピー上書きすればよさそうです。

```dosbatch
%LOCALAPPDATA%\Packages\Microsoft.MicrosoftEdge_8wekyb3d8bbwe\AC\MicrosoftEdge\User\Default\DataStore
```
AWSにデプロイすると、いつも起こるエラー

#はじめに
現在作成中のアプリケーションはAWSにデプロイしているが、毎回、CSSがうまくいかず、`rails assets:precompile RAILS_ENV=production`をすると、
`"webpack" not found`と出て、挫けます。
きっとwebpackが見つからないとエラーを吐いているのだが、適切な解決方法が見つからず、
テキトーに操作してやり過ごしてしまってします。

##今のところの解決方法
```bash
% yarn install --check-files
% bundle install
```
- **Unicornの再起動**

この3つを試すと、どこかしらでうまくCSSのスタイルが適用されているみたいです。

##最後に
読んだ人へ
なんの参考にもならなくてすみません。
自分が次、同じような目に遭った時、見返す用です。
Fakerについて

#目次
<b>①Fakcerとは
<b>②Fakerの使い方

##①Fakcerとは
ダミーデータを自動で作成してくれるもの。

##②Fakerの使い方
<b>1.Gemfileにfakerを記述

```php:Gemfile
 gem 'faker'
```

```php:ターミナル
 bundle install
```

<b>2.seeds.rbにダミーデータを作成できるように記述する([こちらを参考に](https://github.com/faker-ruby/faker#note))

```php:seeds.rb

 50.times do |n|
  email = Faker::Internet.email
  password = "password"
  User.create!(name: name,email: email, password: password,password_confirmation: password)
end
```

<b>3.ターミナルにてデータを生成する

```php:ターミナル
 rails db:seed
```
以上

◯補足
seeds.rbとは、初期データを生成してくれるファイルのこと。このファイルにデータを生成するコードを書いておくだけで、アプリにデータを備えさせることができる。
GitHub Flowモデルとは

#GitHub Flowモデル
メインブランチはmainの１つだけ、常にデプロイ可能な状態に維持するというシンプルなブランチモデルです。プルリクエストを作って、レビューしてもらって、マージします。
これは頻繁にリリース（デプロイ）する開発に適しています。

１　新しい作業を開始するときは、わかりやすい名前のブランチをmainから分岐します。
２　ローカルで小さい単位でこまめにコミットし、同じ名前でリモートにもpushします。
３　フィードバックやヘルプが必要なとき、
　　またはマージの準備ができたらPull Requestを作成します。
４　他のメンバーがレビューして確認したら、mainへマージできます。
５　mainにマージしたらデプロイできます。

**mainブランチ**

旧 masterブランチ （2020年に変更されました）
既存のメインブランチです。常にデプロイ可能な状態です。

**作業用ブランチ名**
機能追加：feature-機能を表す名称
　例）　　feature-user-notice
バグフィックス：fix-修正を表す名称
　例）　　　　　fix-login-validation

など


#featureブランチ命名
featureブランチはスラッシュで区切ることができるため、ここに複数の情報を入れます。
具体的には

feature/201902/yait/fix-admin-panel
といった形で作成しています。
feature/(yearmonth)/(username)/content
となっています。
その理由について述べます。


**年月を入れる**

featureの下に年月を入れています。
これはSourceTreeを使った場合のグルーピングやブランチ名でソートした場合、時間順でグルーピング、ソートすることができるからです。
開発が長くなってくるとブランチの数がそれなりに増えてきます。だいたい100個を超えたあたりから探すことが大変になってきます。
そこでこのようにスラッシュで区切ることで見通しを良くします。


GitHubのブランチはGitHub上で削除することができますが、Gitの実際の削除ではなく、GitHub上のソフトデリートです。
そのためGitコマンドなどで確認すると生きているブランチとして見えるため、「ちょっとこのブランチをチェックアウトして確認してほしい」とレビュー依頼を出す際など、探すことが困難になります。
こうしてグルーピングしておけば、少なくとも最新の月で絞り込めるため便利です。

**ユーザ名を入れる**

ブランチ名にユーザ名（GitHubやSlackのユーザ名と揃えています）を入れます。
こちらも上記の理由と同じく、見通しを良くするということがあります。
またその他にもブランチの持ち主を特定するために入れています。「このブランチって使われてないけど、消して良いのかな…。誰に聞けば良いんだ…」ということを防ぐことが出来ます。

またプルリクエストと同様に責任者を明らかにする、ということがあります。
「このブランチは俺のブランチだから、テストが通らなければ俺が直す責任がある」ということで、責任の所在をはっきりさせることができます。
Mongoでよく使うコマンド

すぐ忘れちゃうのでメモ。一般的なsqlとの比較。

# select文

and条件、 is not 、betweenとか

```sql
select 
  user_id 
from 
  tabel_name
where 
  hoge = 'aaa'
  and fuga <> 'bbb'
  and time between '2021-01-01' and '2021-01-31'
;
```
↓
`'user_id':1`の`1` は0以外ならなんでも良いらしい。
`_id:0` はmongo独自で持ってるidを表示しないために。
tabel_nameはコレクション名に置き換わっています。

```sql
db.{コレクション名}.find(
    {
        'hoge': 'aaa'
        'fuga':{$ne:'bbb'},
        'time':{$gte:ISODate('2021-01-01T00:00:00Z')},
        'time':{$lte:ISODate('2021-01-31T00:00:00Z')}
    },
    { 'user_id':1, _id:0}
);
```

# その他いろいろ

## count

```
db.{コレクション名}.find({条件}, {対象フィールド: 1}).count();
```

## limit 

```
db.{コレクション名}.find({条件}, {対象フィールド: 1}).limit({数字});
```
Raspberry Pi Pico用にThonnyを使ってみる

##公式ページ
https://thonny.org/

##使ってみる
Micropythonよくわからない勢なので、なんか使いやすいIDEないかなと
探していたら、Raspberry Pi Picoのドキュメント内にて紹介されていたので
サクッと入れてみることにしてみたのです。

まずは公式ページからダウンロードして、インストールしてみる
![RPP_2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/481194/08d7ce82-3017-95aa-7283-658ddbbc83cb.png)

★Tool->Options->Generalタブ
起動後、言語を日本語へ
![RPP_2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/481194/efd305a6-68b6-52db-5a59-77f4bc392d69.png)

★Tool->Options->インタプリタタブ
デバイスのところでRaspberry Pi Picoに設定
PortはRaspberry Pi Picoが認識されているUSB-COMポートを指定(下記例だとCOM7)
![RPP_2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/481194/bee9583b-c415-8da1-7268-c107c4e6a912.png)

##コードを実行してみる
他にシリアル接続していないか(Teratermなどで開きっぱなしだとエラー)を
確認して、コードを書いて実行するとShellに結果表示される。

下記は内部温度センサーの値をとって表示するサンプルコードを実行してみたところです。
![RPP_2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/481194/c2445768-4c84-6ba7-cef4-6b916ee42d44.png)
Docker + Symfonyで環境構築する

# はじめに
仕事でSymfonyを扱うことになりそうなので、勉強用にDocker環境を構築しました。
SymfonyはPHPのメジャーフレームワークだけど、Laravelと比べると少し日本語の情報が少ないですね。
Laravelを使っているとSymfonyの日本語の情報の少なさに狼狽える自分ががｇ

# 対象者
Symfonyが動く環境をdockerですぐに作りたい方

# 前提
* Docker
* Git  

少し前のアプデでWindows10 HomeでもDocker for Windowsが使えるようになったんですね。
とりあえず、DockerとGitが使えればOKです。

# 環境構築
`docker symfony`とかでググると以下のリポジトリが出てきました。

https://github.com/eko/docker-symfony
https://github.com/dunglas/symfony-docker
https://github.com/joeymasip/docker-symfony4

一番最初の[リポジトリ](https://github.com/eko/docker-symfony)がスター数が多かったのでそちらで進めます。

## リポジトリをclone

```
$ cd 好きなディレクトリ
$ git clone https://github.com/eko/docker-symfony.git
```

## コンテナ作成
```
$ cd docker-symfony
$ docker-compose up -d
```

## hostsの書き換え
[リポジトリ](https://github.com/eko/docker-symfony)のREADMEに書いてある通り進めていきます。
ローカルのhostsファイルに以下を追記。

```
127.0.0.1 symfony.localhost
```

### hostsの場所
Windowsの場合

```
C:\Windows\System32\drivers\etc
```

macの場合

```
/private/etc/hosts
```

※違ってたらご指摘お願いします。

## コンテナへ入る
```
$ docker exec -it php-fpm sh
```

## symfonyプロジェクトのインストール
```
# composer create-project symfony/website-skeleton . 4.2.x
```

バージョンを変えたい方は末尾の数字を変えてください。
今回は4.2.xを指定しています。

## 確認
http://symfony.localhost/

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/261977/76288cc3-be13-49c0-9af9-a3f5a68e8703.png)

終わりです！

これで環境構築は終わりです。
多分これが一番早いと思います。
kibanaとかxdebugはREADME読めばすぐにわかるハズ。

# さいごに
チュートリアルでサンプルを作成しましたが、Symfony4の参考書も購入してみました。
とても読みやすいので最初はおすすめです。

https://www.amazon.co.jp/dp/B07NQ5WH6R/ref=dp-kindle-redirect?_encoding=UTF8&btkr=1
Matlabのhistcounts/histcounts2をPythonで


Matlabで個人的によく使うhistcoutsとその2変数版のhistcounts2のやりかたメモ。

#ヒストグラムをプロットするやり方
”python　ヒストグラム”　とかでググると
matplotlibのhistやhist2dの情報が見つかって、その返り値からcountをとってくる方法が色々と出てくる。

たとえばこんな感じ。

```python
import numpy as np
import matplotlib.pyplot as plt

x = np.random.normal(loc=0, scale=1, size=1000)
y = np.random.normal(loc=0, scale=2, size=1000)
 
xEdge = np.arange(-3, 3, 0.1)
yEdge = np.arange(-6, 6, 0.2)

fig = plt.figure()
ax = fig.add_subplot(111)
(cnt, xBin, yBin, img) = ax.hist2d(x, y, bins=[xEdge, yEdge])
```

これはこれで良いのだけれど(ちなみにax.hist2dの４つめの返り値が何なのかは知らない）
いちいちプロットするのがまどろっこしい…と思っていたのだが、普通にnumpyにあった。

#1変数の場合

```python
import numpy as np

x=np.random.normal(loc=0, scale=1, size=1000)
xEdge=np.arange(-3, 3, 0.1)
(cnt, xBin) = np.histogram(x, bins=xEdge)
```

#２変数の場合

```python
import numpy as np

x = np.random.normal(loc=0, scale=1, size=1000)
y = np.random.normal(loc=0, scale=2, size=1000)
xEdge = np.arange(-3,3,0.1)
yEdge = np.arange(-6,6,0.2)
(cnt, xBin, yBin) = np.histogram2d(x, y, bins=[xEdge,yEdge])
```

これで簡単にcntをz-scoreにしてプロットとかできて捗る。
AWS　(VPC)についての全体像

# はじめに
AWSのVPCについての概念や用語を簡単にアウトプットしていきたいと思います。

### リージョン
・リージョンとは、AWSの各サービスが提供されている地域のこと
・世界中に21のリージョンがある。
・AWSのサービスを利用するとき、まずリージョンを選択する。
(リージョンによって使えるサービスは異なる。自分が使いたいサービスと照らし合わせてリージョンを決める。日本でサービスを展開する場合は東京リージョンが良い。AWSのサーバーを設置するときはアメリカに設置するよりも日本に設置したほうが応答時間が早くなります。)

###アベイラビリティゾーン
・アベイラビリティゾーンとは、独立したデータセンターのこと
AWSは世界各国にデータセンターをもっていて複数のデータセンターを束ねたのがアベイラビリティゾーンとなります。
・どのリージョンにもアベイラビリティゾーンは2つ以上存在していて、それぞれ物理的に離れて存在しています。なぜ複数あるかというと、トラブルがおきて１つのアベイラビリティゾーンが利用できなくなっても、ほかのアベイラビリティゾーンでカバーできるからです。
・実際にEC2のサーバーをたてる際は、まずリージョンを選んで、次にその中のどのアベイラビリティゾーンにたてるかを選択することになります。複数のアベイラビリティゾーンを設置すれば、何かあったときのリカバリーができます。

### リージョンとアベイラビリティゾーンは色々なサービスの基礎の概念となります。

## VPC(Virtual Private Cloud)

・VPCは、AWS上に仮想ネットワークを作成できるサービス
・VPCを使うことでほかとは分離されたネットワーク環境を自由に作ることができます。
・AWSで作業するときは、まずVPCを作りサブネットで分け、そのサブネットの中にサーバーを設置していく流れになります。

##VPCを作ったら、その中をネットワークでさらに区切ります。それをするのがサブネットとなります。

###サブネット
・サブネットとは、VPCをさらに細かく区切ったネットワーク
・アベイラビリティゾーンの中に作る
・AWSでサーバーを作るときは、このサブネットの中で設置するようにします。
###パブリックサブネット
インターネットから接続できる
###プライベートサブネット
インターネットから接続できない

#おわりに
VPCについて簡単な全体像でした。また勉強してアウトプットしたいと思います。
mypy + numpy で静的型チェックするメモ

## 背景

機械学習とか画像処理とか, numpy を使う場合型はだいたい既知(e.g. 画像データだと dtype `np.uint8` とか)なので, 静的型チェックしたい.

Python3.5 以降の型アノテーション + mypy + `nptyping`(完全ではない) を使います.
(numpy v1.12 かそれ以降では `numpy.typing` が使えるようだが現状 2021/01/28 時点では v1.12 はベータリリース段階で stable release は v1.19)

Python 3.8 以降あたりを使うのがよさそうです.

ただ, 現状(2021/01/28 時点), 完全にうまく行く方法はありません.

(追記) 2021/01/30 に `numpy.typing` 対応した numpy v1.20 がリリースされました.

https://numpy.org/doc/stable/release/1.20.0-notes.html#numpy-is-now-typed

今後はこちらを mypy と共に使うのが主流になっていくことでしょう.

## 静的型チェック

* 型アノテーションと実行時型チェックをコードに記述
* mypy でチェック
* OK になったら普通に python で実行

のステップになります.

mypy とは...?

Pythonではじまる、型のある世界
https://qiita.com/icoxfog417/items/c17eb042f4735b7924a3

ありがとうございます.

ただ, そのまま mypy 実行だと `numpy` module の型情報取得できないっぽいので,
 
Type hint for NumPy ndarray dtype?
https://stackoverflow.com/questions/54503964/type-hint-for-numpy-ndarray-dtype

にあるように, `data-science-types` を入れておきます(ついでに `pandas` とかでも使えてよい)

他に使っている module があり型ヒントがなくてエラーになる場合は, 適当に `--ignore-missing-imports` をつけるなりしてひとまず suppress しておきます.

## nptyping で型アノテーション

numpyでも型ヒントチェックしたいと思った
https://qiita.com/qython/items/1f7416bbb29f48a153bb

ありがとうございます.

nptyping なしで文字列指定もできますが, dtype のチェックはうまくしてくれないようで

```python
import numpy as np


def proc_numpy(a: "np.ndarray[np.float64]"):
    print(a)


a = "bora"
proc_numpy(a) # error

b = np.random.rand(4, 5).astype(np.int32)
proc_numpy(b) # ok :thinking: 
```

文字列渡す場合は

```
error: Argument 1 to "proc_numpy" has incompatible type "str"; expected "ndarray[float64]"
```

とエラーレポートしてくれますが,

と int 配列を渡す場合は mypy は OK をレポートしてしまいます.


nptyping を使って型アノテーションを書くと, size や dtype もチェックできまます.

### nptyping は mypy でチェックできない

しかし, 現状 `nptyping` は残念ながら mypy でサポートしていないため,

```py
def proc_numpy(a: NDArray[(typing.Any, ...), Float[64]]) -> None:
    print(a)
```

のように書いても mypy チェックでは無視されます :cry:

関数の引数の型指定の場合, ひとまずは文字列指定などで最低限のチェックを mpypy で行い,
残りは `isinstance` で実行時型チェックするかありません.

## 実行時型チェック

上記のようなケースや, コードの書き方によっては実行時にチェックする必要も出てくるかと思います.

実行時に型チェックしたい場合は今までどおり `assert isinstance(...)` あたりを記載することになるかと思います.

## (将来) numpy.typing で型アノテーション

https://numpy.org/devdocs/reference/typing.html

v1.12 では numpy 自体に取り込まれるっぽい.

## まとめ

`numpy.typing` にいずれは統合されて mypy でよろしく型チェックできると思われますが, python 自体の型サポートとあいまり, 現状は過渡期という感じです.

python 3.10+ + numpy v1.12+ あたりでいい感じになるかもしれません.
【Python】絶対パスと相対パス

pythonを使用してExcelファイルの操作を勉強しています。
本日の気づき(復習)は、絶対パスと相対パスに関してです。

# 複数ブックのセルを取得して一覧を作る
先ずは前提として
デスクトップ上にtestフォルダーを作成し、その中に
スタッフのチェックシートを纏めて保存したbooksフォルダーと
以下のようなプログラムを作ってみました。

```python:User/Desktop/test/read_books.py
from pathlib import Path

from openpyxl import load_workbook, Workbook

wb_new = Workbook()
ws_new = wb_new.active
ws_new.title = '社員一覧表'

ws_new['B2'] = '部署名'
ws_new['C2'] = '氏名'

path = Path('./books')
for i, file in enumerate(path.glob('*.xlsx')):
    wb = load_workbook(file, read_only=True)
    ws = wb['チェックシート']

    row_no = i + 3
    ws_new[f'B{row_no}'] = ws['C2'].value
    ws_new[f'C{row_no}'] = ws['C3'].value

wb_new.save('社員一覧表.xlsx')

```
こちらで問題なく社員一覧表は作成出来たのですが
ふと、booksフォルダーは、デスクトップ上で保管したいなと思い至り
booksフォルダーをデスクトップ上へ移動させます。
後は記述を変更するだけです。が、どこを変えるのかな？？
# 相対パスを使用する
答えは簡単でした。相対パスを使用します。

```python:User/Desktop/test/read_books.py
# 記述を変更
path = Path('../books')
```
こちらで問題なく作成できました。
思いがけずスクールの復習もでき
言語が変わっても記述方法が変わるだけで、意外と考え方は変わらないことも再発見できました。
Pythonの標準ライブラリであるpathlibを使うと相対パスを絶対パスに変換のできるみたいですし
色々と勉強が楽しみです。
XAMPPのphpだけアップデートする -2021年版-

# XAMPPのphpだけアップデートする -2021年版-

## XAMPPのアップデートは面倒

まず全部アンインストールしてからインストールしないといけないのでバックアップが大変。俺はめんどくさがりなのでググって色々調べてできるだけ今の設定を維持したまま楽ちんにアップデートしたいわけです。

## XAMPP 8.0.0 から 8.0.1

ああ、めんどうだ。めんどうだよこれ。ということでphpだけアップデートしようと思って調べたら、なんか「XAMPPのphpは32bit」という情報が。でも怪しいな？と思って調べました。いや、8.0.1にアップデートした後なんですけどね。

### phpinfo

``` php:hoge.php
<?php
phpinfo();
```

実行結果：
![phpinfo.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/569616/983122b0-cc85-c81d-4cab-42f091f1179d.png)
あれ、これx64じゃない？

### タスクマネージャーでもわかる

タスクマネージャーでは、32bitアプリはこのように(32 ビット)と表示されます。親切ですね。
![タスク.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/569616/2a14c804-2765-e975-61bf-1144adc0f6dc.png)
なので、XAMPPのphp.exeを実行してタスクマネージャーで見てみました。php.exeをダブルクリックすればphpのコンソールが立ち上がります。この状態でタスクマネージャーを見ます。で、php.exeを探すと…
![php8t.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/569616/0a3045a5-1385-b541-2cc2-009bcbaff8c8.png)
**64bitだー！**

## 結論

確認できたのは7.3.26からですが、XAMPP for Windowsのphpも64bitです。なので、windowsだと [https://windows.php.net/download#php-8.0](https://windows.php.net/download#php-8.0) あたりから VS16 x64 Thread Safeのzipを落としてきてphp.ini以外を上書きすれば良い。

## 参考

[EXE、DLLが32bitなのか64ビットなのか確認する方法](https://qiita.com/towtow/items/a5c92482cca797456b86)
RailsでjQueryを利用する方法  (Webpacker使用)

## 環境
Rails 6.0.3
Ruby 2.6.6

## 導入
WebpackのProvidePluginを利用することでreqireを明示することなくどこでもjQueryを使用することが可能になります。

###jQueryをインストール
`$ yarn add jquery`

###plugin用のファイルの作成

```config/webpack/plugins/provide.js
const webpack = require('webpack')
module.exports = new webpack.ProvidePlugin({
    $: 'jquery',
    jquery: 'jquery'
});
```

###webpackの設定リストに先ほどのプラグインを追加する
特定の環境でしか使用しないのであればenviroment.jsではなくtest.js,development.jsなどに記述する。

```config/webpack/environment.js
const { environment } = require('@rails/webpacker')
// 編集開始
const provide = require('./plugins/provide')
environment.plugins.prepend('provide', provide)
// ここまで編集
module.exports = environment
```
これでrequireを記述せずともjsファイル内でjQueryが使用可能となります。
試しに、

```app/javascript/packs/hello.js
$(function() {
  console.log("hello");
});
```

```app/views/layouts/application.html.erb
<!DOCTYPE html>
<html>
  <head>
    .
    .
    .
    <%= javascript_pack_tag 'hello', 'data-turbolinks-track': 'reload' %>
    .
    .
  </head>
</html>
```
これでjQueryが使用できていることがわかります。
git レポジトリにあるパッケージを pip install (setup.py-style, pyproject.toml)

# setup.py-style

setuptools(デフォルト)を使う場合、以下の形式で install ができます。

`pip install "git+protocol://git.example.com/MyProject.git#egg=<project name>&subdirectory=<setup.pyがある階層までのパス>"`


### パラメータ の egg に関して

> egg=<project name> is used by pip in its dependency logic to identify the project prior to pip downloading and analyzing the metadata.

[pypaのドキュメント](https://pip.pypa.io/en/stable/reference/pip_install/#vcs-support)の上記説明だと具体的にどのように、何を指定すれば良いか分かりませんでしたが、以下の記事が役立ちました。


> egg=(パッケージ名)は setup.py の中にある関数 setup(name=○○○, ...) の引数 name に渡される名称です。

https://qiita.com/tshimura/items/64603dfb8f0d6eb35992#pip-install-%E3%81%AE%E6%9B%B8%E3%81%8D%E6%96%B9


### パラメータ の subdirectory に関して
setup.pyがプロジェクトのルートにない場合に使います。

subdirectory を追加して、プロジェクトルートからのsetup.pyがある階層までのパスを指定する必要があります。
> The value of the “subdirectory” component should be a path starting from the root of the project to where setup.py is located.

# pyproject.toml にビルドツールを指定している場合 (PEP 517)

pyproject.toml にビルドツールを指定して install する場合のドキュメントを見つけられませんでした。しかし、suffix に egg を指定しない記法で install ができました。pipはpyproject.tomlを確認した際は指定のビルドツールを使ってくれるみたいです。

>  if a project specifies a different build system using a pyproject.toml file, as per PEP 517, pip will use that instead. 

by https://pip.pypa.io/en/stable/reference/pip/

> If a user wants to explicitly request PEP 517 handling even though a project doesn’t have a pyproject.toml file, this can be done using the --use-pep517 command line option. 

by https://pip.pypa.io/en/stable/reference/pip/

## pyproject.toml がプロジェクトルートにある場合
install に成功した自作サンプル↓

`pip install git+https://github.com/nnashiki/wordcloud-cli`

なお、build ツールには poetryを指定しています。

## pyproject.toml がプロジェクトルートにない場合
install に成功した自作サンプル↓

`pip install git+https://git@github.com/nnashiki/wordcloud_cli_training#subdirectory=wordcloud-cli-for-japanese`

なお、build ツールには poetryを指定しています。


# 参考にしたドキュメント類
- https://pip.pypa.io/en/stable/reference/pip_install/#vcs-support
- https://pip.pypa.io/en/stable/reference/pip_install/#examples
- https://qiita.com/tshimura/items/64603dfb8f0d6eb35992#pip-install-%E3%81%AE%E6%9B%B8%E3%81%8D%E6%96%B9
- http://orolog.hatenablog.jp/entry/2019/03/24/223531

# pep517 について知りたい場合のリンク
- https://www.python.org/dev/peps/pep-0517/
- https://pip.pypa.io/en/stable/reference/pip/
後々めっちゃ便利になる。firebase-functionsでCloudFirestoreの変更を検知する方法！

今回はタイトルの通り、firebase-functionsでCloudFirestoreの変更を検知します。

どういうことかと言うと、まずは下記のコードを見て下さい。！

```index.js
exports.addAdminClaim = functions.firestore.document('admin_users/{docID}').onCreate((snap) => {
    const newAdminUser = snap.data();
    if (newAdminUser === undefined) {
        return;
    }
    modifyAdmin(newAdminUser.uid, true);
    //true: 管理者
});
```

firebaseでこのような関数を定義したとき、どういった時にこの関数が実行されるか分かりますか？

注目すべきは``onCreate``です。

まず、``functions.firestore.document('admin_users/{docID}').onCreate``これ自体初めて見る方も多いと思います。

ただ、これをそのままコピペして使えるくらい簡単なので、そんなに焦らなくてもいいです。

まず、``onCreate``から紹介します。

[https://firebase.google.com/docs/functions/firestore-events?hl=ja](https://firebase.google.com/docs/functions/firestore-events?hl=ja)

こちらにも書いてあるのですが、今一度整理します。

``onCreate``：（ドキュメントが）**最初**に書き込まれたとき
``unUpdate``：（ドキュメントが）更新されたとき
``onDelete``：（ドキュメントが）消去されたとき
``onWirte``：上の３つのどれかが発動したとき

感覚としてはJavascriptの``addEventListener``的な感じ。

例に挙げた``functions.firestore.document('admin_users/{docID}').onCreate``は、ドキュメントが最初に書き込まれたときに発火する。

また、``document('admin_users/{docID}')``は``admin_users``というテーブルになんかしらの値（docID）の変更を監視している。

こうやってFirestoreの変更を検知することができる。

とても便利なので、ぜひ使ってください！！！

また、今回はこちらの記事[さぁ、firebaseでユーザーが管理者かどうかの判別を行おう！](https://qiita.com/akki-memo/items/508c6922ec989486ab94)をベースにして書いたので、ぜひ時間がある方は見て下さい！

以上、「後々めっちゃ便利になる。firebase-functionsでCloudFirestoreの変更を検知する方法！」でした！

良ければ、LGTM、コメントお待ちしております。

また、何か間違っていることがあればご指摘頂けると幸いです。

他にも初心者さん向けに記事を投稿しているので、時間があれば他の記事も見て下さい！！

Thank you for reading
[jQuery] ページのトップに戻るボタンを作成する

#js形式のファイルを用意する
CDNを利用してjQueryを読み込み、js形式のファイルにコードを書いていきます。詳しくは以下で説明しています。
[jQueryを使う準備をする](https://qiita.com/momo1010/items/256628708056a8c22415)

#トップに戻るボタンをHTML、cssで作る
自分で好きなようにボタンを作ってください。Bootstrapやアイコンフォントなどを使ってもいいですね。
今回はトップに戻るボタンのクラス名を `top-btn` にしています。

#js形式のファイルにコードを書く

```:js
$(function(){

  $('.top-btn').hide();
  
  $(window).scroll(function(){
    if($(this).scrollTop()>200){
      $('.top-btn').fadeIn();
    }else{
      $('.top-btn').fadeOut();
    }
  });

  $('.top-btn').click(function(){
    $('body,html').animate({scrollTop: 0},500);
    return false;
  });

});
```

上記のコードの説明です。↓

初めは、ボタンを表示させないようにします。

スクロール量が `200` になったらボタンを表示させます。
今回はスクロール量を `200` に設定しましたが好きな量に変更してください。

ボタンをクリックしたらスクロール量を `0` にします。（ページのトップに戻る）
戻る速度は `500` の速度に設定しましたが好きな速度に変更してください。