OmniAICreator/Qiita-1.07M huggingface dataset:
Prism.jsがサポートする言語一覧(バージョン別)

JavaScript製のシンタックスハイライトライブラリの[Prism.js](https://prismjs.com/index.html)がサポートするプログラミング言語一覧です。

Gatsbyなど、Prismを使っている静的サイトジェネレーターで対応言語を調べるときにご活用ください。

全画面に広げて見るには[こちらのページ](https://codepen.io/suin/full/XWmYZXz)を開いて下さい。

<p class="codepen" data-height="505" data-theme-id="light" data-default-tab="result" data-user="suin" data-slug-hash="XWmYZXz" style="height: 1000px; box-sizing: border-box; display: flex; align-items: center; justify-content: center; border: 2px solid; margin: 1em 0; padding: 1em;" data-pen-title="List of supported languages by Prism">
  <span>See the Pen <a href="https://codepen.io/suin/pen/XWmYZXz">
  List of supported languages by Prism</a> by suin (<a href="https://codepen.io/suin">@suin</a>)
  on <a href="https://codepen.io">CodePen</a>.</span>
</p>
<script async src="https://static.codepen.io/assets/embed/ei.js"></script>
Automatorでmovをgifに変換するスクリプトを作成する

会社の人に教えてもらったAutomatorでmovをgifに変換するスクリプトを作成する方法を、忘れないように記事にしておく
教えていただいた方の言葉とキャプチャ、非常にわかりやすかったので、ほぼ、そのまま流用させていただきました:bow:

# ffmpeg をインストール
```shell
brew install ffmpeg
```

# Automator の設定
## 1. brew install ffmpegしたあと、以下の設定でAutomatorを保存します。
保存したファイル名で、クイックアクションに登録されるので、以降は、そこから一発変換できます。

```shell
DIRNAME=`dirname $@`
BASENAME=`basename $@`
/opt/homebrew/bin/ffmpeg -i $@ -r 10 -vf scale=300:-1 ${DIRNAME}/${BASENAME}.gif
```
※Intel　Macを使っている場合は、`/usr/local/bin/ffmpeg` になります

## 2. 以下のキャプチャのように設定する
![スクリーンショット 2019-10-29 18.21.52.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/35613/9d2d45dc-2bea-d28b-2ead-23dde798aa65.png)
![スクリーンショット 2019-10-29 18.22.20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/35613/187eb9b6-88b4-49fb-0d4a-3b7544c92075.png)
<img width="554" alt="スクリーンショット_2019-10-29_18_23_21.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/35613/2df38d48-41f1-ae2d-87ab-1d499ca052b4.png">


Automatorの「ワークフローが受け取る現在の項目」を「ファイルまたはフォルダ」もしくは、「ムービーファイル」にしておきます。
![スクリーンショット 2019-10-29 18.31.43.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/35613/47177f9f-3771-9d9b-1ffc-e20390fb010c.png)

拡張子を mp4 に変えたバージョンも作っておくと便利です。

```shell
DIRNAME=`dirname $@`
BASENAME=`basename $@`
/opt/homebrew/bin/ffmpeg -i $@ -crf 28 -vf scale=300:-1 ${DIRNAME}/${BASENAME}.gif
```

参考
https://syobochim.hatenablog.com/entry/2021/01/07/004600
https://tech.ckme.co.jp/ffmpeg_h264.shtml
https://qiita.com/riversun/items/d09d8e596a20ec1798f3
Kony Visualizerでボックスに影をつける

#目次
1. はじめに
2. 作成方法
3. まとめ

#はじめに
Konyでレイアウトを作成する場合、影がついたデザインを作成することがあると思います。
はじめてKonyでモックアプリを作成する際に、この影をつける方法について手こずったため、
ここでは影の作成方法を説明したいと思います。

#作成方法
[完成図]
ボタンを4つ配置し、各ボタンに影が表示されるように作成します。
<img width="272" alt="スクリーンショット 2020-05-12 11.32.10.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/e28d4cc3-cc71-3655-6bcb-2fee866254e0.png">

それでは早速作成していきましょう！
以下のようにflexcontainerを使いボタンを作成します。

[レイアウト]　　　 [widget構成]
<img width="108" alt="スクリーンショット 2020-05-12 11.36.52.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/7a7d68e1-3ca0-85ad-ae70-1528a96b3820.png"><img width="174" alt="スクリーンショット 2020-05-12 11.35.04.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/494b1cc4-21e4-1379-4343-d3cffec07ae4.png">
ボックスに影を付けたいため、
`flxGotoCheckIn`のSkinタブからShadowを探して、
以下のように設定します。
透明度や、ぼかし度、色はお好みで設定してください。
<img width="352" alt="スクリーンショット 2020-05-12 11.39.11.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/cca2dbdd-9b42-bdf9-c96a-8dbd992cfa28.png">

この状態でレイアウトをみてみると、↓
<img width="108" alt="スクリーンショット 2020-05-12 11.41.18.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/2e7a863e-8b58-a0fb-f4cb-e0bfc20fd4e6.png">
・・・影が反映されていません:sob:


影を設定しても、反映されていない場合、
影を設定しているFlexContainerのFlexContainerタブのClip Boundsの設定を確認してください。

Clip BoundsがONになっている場合は、
ボックスの境界から漏れている範囲を切り取る設定となっているため、
影を作成したとしてもその部分が切り取られてしまい、反映することができません。
<img width="381" alt="スクリーンショット 2020-05-12 11.42.46.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/983096cf-b3d0-8768-ba2c-fe42da4ec260.png">

そのため、Clip BoundsをOffにすると・・
<img width="365" alt="スクリーンショット 2020-05-12 13.03.02.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/662c737b-c1f8-35b2-f182-2ce40f6cfffd.png">

影が反映されました！:clap_tone1:
<img width="104" alt="スクリーンショット 2020-05-12 12.50.38.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/088855df-0cfd-a7b9-99eb-b2420abc35f8.png">

Clip BoundsはデフォルトでOnになっているため、
ボックスに影を付けたい場合などは、Offにして作成するようにしてくださいね！

[補足]
Widgetを複数重ねて影を作成したい場合、zindexが大きい数値のwidgetが上に来るようになっているため、
zindexの数値は、上に配置したいWidgetほど数字が大きくなるように設定してください。

↓の画像は、以下の設定になっていますが、
[before]
flxGotoCheckInのwidgetのzindex: 1
flxShadowのwidgetのindex:　2


<img width="741" alt="スクリーンショット 2020-05-14 10.22.51.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/347b8e27-683a-2373-cb06-9ded44034e20.png">

以下の設定にすると、flxShadowが下に配置されるようになります。
[after]
flxGotoCheckInのwidgetのzindex: 2
flxShadowのwidgetのindex:　1


<img width="334" alt="スクリーンショット 2020-05-14 10.26.41.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/592264/33035dad-3dbb-90c6-cc8b-a52d00c44026.png">


#まとめ
影をつける方法は基本的な内容に見えますが、
初めてKonyでモックアプリを作成する際に検索してもヒットするものがなく、
なかなか解決することができなかったため、今回Qiitaにアップすることにしました。

同じところでつまづいている人がいたら、お役に立てれば嬉しいです:v:

#参考
https://docs.kony.com/konylibrary/visualizer/visualizer_user_guide/Content/Flex_Container.htm
Pythonでアルゴリズム（ベルマンフォード法,Bellman-Ford）

# 目的
　ある頂点から他の頂点への最短距離を求める。(単一始点最短経路)**負のコスト**を持つ辺があっても利用可能。
# 原理
　グラフの頂点数を$V$,辺の数を$E$とする。各頂点への最小コストを記録するリスト$d$を作成する。ここで、自身の点への距離は0で確定、他の点への距離はINFとする。
　ここから、辺をすべて見て最短距離を更新していく。具体的に、辺$e$が頂点$from$から頂点$to$に向けてコスト$cost$という情報を持つとすると、
$$d[from] + cost < d[to]$$
となるとき、$d[to]$の値が$d[from] + cost$に更新される。
　すべての辺を見るという操作を合計$V - 1$回行えば、負閉路がない場合にはすべての最小コストが確定する。つまり、$V$回目においてまだ最小コストの更新が行われた場合には負閉路を持つということで、正しい最小コストは求められない。
　では、なぜ$V - 1$回のループで操作を完了させていいのか。自分の理解の仕方を説明する。ある頂点への最小コストとなる経路の中に、同じ頂点は2度と含まれない。含まれるとしたら負閉路があるということでそもそも正しい経路は求まらない。以上より、ある頂点への最短経路に含まれる辺の数は最大でも$V - 1$本である。この後のコードを確認すれば分かるのだが、辺の並びは入力順である。(幅優先探索のように近い順に調べるわけではない)つまり、$V - 1$本の最短経路を求める過程を考える。うまくいけば1回のループで前から順に辺が辿られ、この最短経路が求まるかもしれない。しかし、調べる辺の順がきれいに後ろから並んでしまっているとする。この時、前の辺が調べられていないとそれより後ろの辺を最短経路の一部とは考えられない。($from$までの距離がINFもしくは最小コストではないため)つまり、このケースでは1回のループにつきこの最短経路のうち前から1つずつしか求まらない。よって、これが最悪のケースで、$V - 1$回のループを必要とする。
※なら、幅優先探索的に近い順に調べればと思い実装しましたが、負閉路があると無限に値が更新され続けてしまうのでそこの工夫が必要な気がしました。正のコストのみのときについては会津オンラインのダイクストラの問題に投げたところ正解となったのでなんかこれにも名前付いているのかなあ。
#計算量解析
　最悪、すべての辺を見る操作を$V - 1$回行うので計算量は$O(EV)$。
#実装
```py
# O(EV)
def bellman_ford(s):
    d = [float('inf')]*n # 各頂点への最小コスト
    d[s] = 0 # 自身への距離は0
    for i in range(n):
        update = False # 更新が行われたか
        for x, y, z in g:
            if d[y] > d[x] + z:
                d[y] = d[x] + z
                update = True
        if not update:
            break
        # 負閉路が存在
        if i == n - 1:
            return -1
    return d

n, w = [int(x) for x in input().split()] # n:頂点数, w:辺の数
g = []
for _ in range(w):
    x, y, z = [int(x) for x in input().split()] # 始点,終点,コスト
    g.append([x, y, z])
    g.append([y, x, z]) # 有向グラフでは削除
print(bellman_ford(0))
```
#おわりに
　コードについてもですが今回は考え方が結構不安なのでもしよければアドバイスください!
#参考文献
[プログラミングコンテストチャレンジブック](https://www.amazon.co.jp/dp/B00CY9256C/ref=dp-kindle-redirect?_encoding=UTF8&btkr=1)
EclipseでGithubからリポジトリをクローンする方法

## この記事では以下を前提としております。

- Githubにリポジトリが既にある
- EclipseにeGitというものが入っている(古いEclipseには入っていません)

### ウィンドウ→ビューの表示→その他からビューの表示ウィンドウでGit→Gitリポジトリーを選択する

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/c278636e-9446-b170-3e26-da5d0c77e1d8.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/2d638845-d8d8-aa4f-de57-b49a7fb934d8.png)

### Gitリポジトリ―のペーンから「Gitリポジトリをクローンしこのビューへ追加」をクリックする

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/1fc44ec1-f9c5-f365-ccc5-d679dcbe918d.png)

###　Gitリポジトリーのクローンの画面でURI,ユーザー、パスワードを入力する、ユーザーとパスワードはリポジトリの持ち主、もしくはコラボレーターのアカウントを設定する
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/7f7f953a-d0aa-e355-dd21-df51d8ef570d.png)

### ブランチ選択ウィンドウで「次へ」を選択する
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/10e14e67-da7f-5122-496f-57f768419530.png)

### ローカル宛先で各設定値を確認し問題がないようなら完了ボタンを押下する
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/453c111b-ab24-bab7-1832-d5ba4c31ee94.png)

### Gitリポジトリ―のペーンにリポジトリが追加されていることを確認する
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/3bae62e6-19db-1e17-849c-3c7797f0da0d.png)

### 改訂履歴
- 2020/5/12 新規作成
誰でも簡単にコマンドプロンプト画面を開く手順

# まえおき

コマンドプロンプトの起動を簡単におこなう手順です。

# 手順

1. キーボードのショートカット[Winボタン + r]を押下
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/249974/18b4b4e8-b5c9-4385-4e80-b1e4acad18b6.png)
       
1. 名前(O)に「cmd」と入力して[Enter]キーを押下します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/249974/7ac9b194-1f5e-1e77-f28c-a1031ce11e2a.png)

1. コマンドプロンプトのウィンドウが開きます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/249974/7a51f6a0-a2b1-6f29-0af7-5d7840e455eb.png)

# ピン留めすればもっと簡単に開けます

よく使う人はコマンドプロンプトをタスクバーにピン留めすればワンクリックでコマンドプロンプトが開けます。

1. コマンドプロンプト画面が開いている状態で下部タスクバーにあるコマンドプロンプトを右クリックします

    ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/249974/e5a5cdf9-6e7a-7c67-f750-1f0374669d88.png)

1. タスクバーにピン留めするをクリックします。
    
     ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/249974/a06e3eaf-f998-71c3-997c-9d13881a41e8.png)
Railsで開発中に増えすぎたRubyのプロセスを全部殺す

```
% killall fsevent_watch
```

`bin/spring stop` してもこういう状態になって、PCのファンがうおーんと言い出したときに使う。

```
% ps aux | grep ruby
kazuto           36486   0.0  0.0  4350160   2056 s006  S+   10:32AM   0:00.48 /Users/kazuto/.rbenv/versions/2.4.2/lib/ruby/gems/2.4.0/gems/rb-fsevent-0.10.2/bin/fsevent_watch --format=otnetstring --latency 0.1 /Users/kazuto/projects/xxx
kazuto           36467   0.0  0.0  4324560   1268 s006  S+   10:32AM   0:00.31 /Users/kazuto/.rbenv/versions/2.4.2/lib/ruby/gems/2.4.0/gems/rb-fsevent-0.10.2/bin/fsevent_watch --format=otnetstring --latency 0.1 /Users/kazuto/projects/xxx/config/locales
kazuto           36452   0.0  0.0  4350160   2104 s006  S+   10:31AM   0:00.50 /Users/kazuto/.rbenv/versions/2.4.2/lib/ruby/gems/2.4.0/gems/rb-fsevent-0.10.2/bin/fsevent_watch --format=otnetstring --latency 0.1 /Users/kazuto/projects/xxx
kazuto           36447   0.0  0.0  4324560   1264 s006  S+   10:31AM   0:00.30 /Users/kazuto/.rbenv/versions/2.4.2/lib/ruby/gems/2.4.0/gems/rb-fsevent-0.10.2/bin/fsevent_watch --format=otnetstring --latency 0.1 /Users/kazuto/projects/xxx/config/locales
kazuto           36407   0.0  0.0  4350160   2100 s006  S+   10:30AM   0:00.50 /Users/kazuto/.rbenv/versions/2.4.2/lib/ruby/gems/2.4.0/gems/rb-fsevent-0.10.2/bin/fsevent_watch --format=otnetstring --latency 0.1 /Users/kazuto/projects/xxxx
kazuto           36406   0.0  0.0  4295888   1264 s006  S+   10:30AM   0:00.30 /Users/kazuto/.rbenv/versions/2.4.2/lib/ruby/gems/2.4.0/gems/rb-fsevent-0.10.2/bin/fsevent_watch --format=otnetstring --latency 0.1 /Users/kazuto/projects/xxx/config/locales
```
【Golang】配列

#【Golang】配列
Golangの基礎学習〜Webアプリケーション作成までの学習を終えたので、復習を兼ねてまとめていく。 基礎〜応用まで。

```
package main
//配列
//サイズを変更できない。拡張性がない
//後から追加する場合は、スライスを使う

//関数では値渡しされるので、コピーが作成されて引数に取られる

import "fmt"


func main() {
	//2つの配列を作る宣言
	//[2]int が型になるため、サイズを変更できない
	var a [2]int
	fmt.Println(a)
	//>>[0, 0]

	//宣言
	b := [3]int{1,2,3}
	fmt.Println(b)
	//>>[1 2 3]

	//宣言
	var arr[2] string = [2]string {"A", "B"}
	fmt.Println(arr[0], arr[1]) 
	//>>A, B
	fmt.Println(arr)
	//>>[A B]


	//宣言 要素数省略ver
	//要素の数を自動でカウントしてくれる
	arr2 := [...] string{"A", "B"}
	fmt.Println(arr2[0], arr2[1]) 
	//>>A, B
	fmt.Println(arr)
	//>>[A B]



	//0に100,1に200を代入
	a[0] = 100
	a[1] = 200
	//aを表示
	fmt.Println(a)
	//>>[100, 200]


	//配列に追加できない
	/*
	    //初期で値を入れる
		var b [2]int = [2]int{100, 200}
		//追加
		b = append(b, 300)
		fmt.Println(b)
	*/
	


	//その他の宣言

    


}

```
【VScode】上下スクロールを速くする方法

#はじめに
ショートカットでVScodeで上下スクロールするときにもう少し速く移動したいと思い、探すと見つかったので、その記録。
<blockquote class="twitter-tweet"><p lang="ja" dir="ltr"> <a href="https://t.co/N3vQbMGGcf">pic.twitter.com/N3vQbMGGcf</a></p>&mdash; わにわにのワニ@駆け出しエンジニア (@4PMnju90BzmWLJb) <a href="https://twitter.com/4PMnju90BzmWLJb/status/1259815626572394496?ref_src=twsrc%5Etfw">May 11, 2020</a></blockquote> <script async src="https://platform.twitter.com/widgets.js" charset="utf-8"></script>

通常の上下移動→少し速めの移動


#検証環境
```shell
$ sw_vers
ProductName:	Mac OS X
ProductVersion:	10.15.3
BuildVersion:	19D76
```

#scrollkey
[scrollkey](https://marketplace.visualstudio.com/items?itemName=74th.scrollkey)をインストール

`how to use`通りに進めていく。

#1. add settings
`⇧+⌘+p`の後にsettingと打ち込み、`settings.json`を開く。

<img width="634" alt="スクリーンショット 2020-05-11 23.08.29.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/597926/e2ee2c45-537d-6663-d204-3dd0e50865e8.png">

```json

{
    "scrollkey.line1": 1,
    "scrollkey.line2": 30,
    "scrollkey.line3": 60
}
```

を追加。

#2. add Keyboard Shortcuts
`⇧+⌘+p`の後にkeyboardと打ち込み、
<img width="640" alt="スクリーンショット 2020-05-11 23.14.33.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/597926/e10ae51d-5cd8-be8c-6aae-5cad77e46414.png">


右上のこのマークをクリックして`keybindings.json`を開く。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/597926/ce0a9e4a-cc9f-4479-6c0d-144b4eb67a3f.png)

先に重複がないか確認してから、以下を追加する。
（自分はあって、エラーが出てちょっと焦った。）

```json
[
    {
        "key": "ctrl+y",
        "command": "scrollkey.up1",
        "when": "editorTextFocus"
    },
    {
        "key": "ctrl+u",
        "command": "scrollkey.up2",
        "when": "editorTextFocus"
    },
    {
        "key": "PageUp",
        "command": "scrollkey.up3",
        "when": "editorTextFocus"
    },
    {
        "key": "ctrl+e",
        "command": "scrollkey.down1",
        "when": "editorTextFocus"
    },
    {
        "key": "ctrl+d",
        "command": "scrollkey.down2",
        "when": "editorTextFocus"
    },
    {
        "key": "PageDown",
        "command": "scrollkey.down3",
        "when": "editorTextFocus"
    }
]
```

`"key": "ctrl+y",`の部分をすきなように変更する事ができる。



###参考にさせて頂いた記事
- [ Visual Studio|   Marketplace scrollkey](https://marketplace.visualstudio.com/items?itemName=74th.scrollkey)


###終わりに。
最後まで読んで頂きありがとうございます:bow_tone1:
転職の為、未経験の状態からRailsを学習しております。正しい知識を着実に身に着け、実力のあるエンジニアになりたいと考えています。継続して投稿していく中で、その為のインプットも必然的に増え、成長に繋がるかと考えています。
今現在、初心者だからといって言い訳はできないですが、投稿の内容に間違っているところや、付け加えるべきところが多々あるかと思いますので、ご指摘頂けると幸いです。この記事を読んで下さりありがとうございました。
知らないと恥ずかしい「Chrome DeveloperTool」の ショートカット一覧（Windows版）

ショートカットの備忘録。

###F12
DeveloperToolを開くだけ。

###Ctrl＋Shift＋C
「要素の検証」と同じ状態で開く。
「C=Choice」で覚えると◎
「Esc」で選択モードをオフにできる。

###Ctrl＋Shift＋M
「Device Mode」で開く。
「M＝Mobile」で覚えると◎

###Ctrl＋Shift＋D
dockの位置を右寄せor下寄せに変更。
「D=Dock」で覚えると◎
本当にあったやらかしDB設計⑥【見えない削除フラグ】

どうも、最近コンビニ飯に飽きてきた人です

今日は[「本当にあったやらかしDB設計⑤【第三正規化病】」](https://qiita.com/bouitengineer12/items/6cf86923bbe8d3815390)に続いてびっくりしたことを紹介します

#見えない削除フラグ
そもそも削除フラグとは何でしょうか
レコードに専用のカラムを用意し、その値が0であれば未削除、1であれば論理削除、とする手法のことです

しかし、**削除フラグは良い方法ではありません**
下記でかなり詳細にわかりやすく説明されているので是非見てください
[SQLアンチパターン 幻の第26章「とりあえず削除フラグ」](https://www.slideshare.net/t_wada/ronsakucasual)

削除フラグは手間を増やしたりバグになる可能性を持ってはいますが、注意していれば取り扱うこともできます

**見えない削除フラグはとりあえず削除フラグを凌駕する問題です**
どういうことかと言うと、<font color ="red">削除フラグを立て忘れる</font>、ということです

###何が悪いの？？
生きているデータと死んでいるデータが混ざります
これは通常の削除フラグにも言えますが、**見えない削除フラグでは死んでいるデータを死んでいるデータと判別することができなくなります**

###問題
見えない削除フラグはいくつかの問題を引き起こします

- **本当は死んでいるデータなのに生きているデータのように見えます**

途中で処理をキャンセルされたデータが、処理途中のデータに見えます
タイムスタンプを使って怪しいデータを炙り出すことができますが、本当に処理途中のデータなのか、途中で処理をキャンセルされたデータなのかのを削除フラグを使って見分けることはできません

- **死んでいるデータを捨てられなくなります**

本来であれば削除フラグが立っているレコードは定期的に削除、または他のテーブルに移動するなどの処理が行われます
結局処理をするのであればそもそも削除フラグが存在している意味は更に薄くなりますが…
それはともかく、<font color ="red">削除フラグが立っていないためデータベースに永遠に残り続けます</font>

**これは明らかな負債です**
長く運用していると見えない削除フラグが立っているレコードの量が馬鹿にできなくなってきます
それを永遠に保存するために一体いくらかかるのでしょうか…

ゴミを保存するのにお金使いたくないですよね


###原因
なぜこんなことが起こってしまうのかは単純です

<font color="red">**削除フラグを正しく取り扱えていません**</font>


###解決方法

######削除フラグを適切なタイミングで立てよう！
削除フラグを立てるタイミングを少なく見積もっていると見えない削除フラグを生み出します
データを削除する時だけではなく、処理が途中でキャンセルされた時にも削除フラグを立ててください

######ログをあさろう！
既存の見えない削除フラグに対応するにはアプリケーションを変更することはもちろん、今までのログをあさって死んでいるデータを見つけ出す必要があります
お金と時間がかかる作業だと思いますが、何もしないよりかは安くて済みます




#まとめ
- 削除フラグに頼るな
- 削除フラグを使うなら正しく使え

削除フラグに頼っていると、古いデータを削除するのではなく削除フラグが立っているデータを削除しようとする、というような問題も出てきます

生きているデータと死んでいるデータを分けることは、データを正しく取り扱うためには非常に重要です
データを「おまけ」ではなく「主役」として考えることで良いシステム設計ができるようになります


- [本当にあったやらかしDB設計シリーズ一覧](https://qiita.com/bouitengineer12/items/e63e5f7d6f628da11362)
AtCoder Problems の新機能

# はじめに
*[AtCoder Problems](https://kenkoooo.com/atcoder/#/)* の Recommendation を利用して、過去の問題を解いています。
AtCoder さん、AtCoder Problems さん、ありがとうございます。
# AtCoder Problems の新機能
<img width="960" alt="20200512.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/538241/3c1fa4a4-96c9-4524-c512-6a1388ca2c87.png">
Recommendation に新しいプルダウンメニューが追加されました。

従来、一度解いた問題はそれ以降表示されなかったのですが、新機能として、表示させない期間を設定できるようになりました。

これで、~~忘れた頃に~~何度でも問題に取り組むことができ、学習効果が高まります。

# まとめ
+ AtCoder Problems の Recommendation で期間を設定できるようになった
+ AtCoder さん　ありがとう
+ AtCoder Problems さん　ありがとう
TypeScriptのUnion Typeをプロパティの値によってフィルタする (Redux)

意味のわからないタイトルになってしまいましたがReduxなどでは意外とやりたくなるパターンかと思います。

```typescript
type FooAction = {
  type: 'Foo',
  payload: string
};
type BarAction = {
  type: 'Bar',
  payload: number
};
type Action = FooAction | BarAction;
```

みたいなのがあったときに

```typescript
type SomeAction = FilterActionByType<Action, 'Foo'>; // FooAction
```

のようなことがしたい。

# 結論
以下のようにします。

```typescript
type FilterUnionByProperty<
  Union,
  Property extends string | number | symbol,
  Condition
> = Union extends Record<Property, Condition> ? Union : never;
```

冒頭の`FilterActionByType`は

```typescript
type FilterActionByType<Action, Type> =
  FilterUnionByProperty<Action, 'type', Type>
```

のようにできます。

# 仕組み
最初は以下のようなコードを書きました。

```typescript
type FilterActionByType<Action extends { type: any }, Type> =
  Action['type'] extends Type ? Action : never;
```

しかしながら、これではなぜか皆`never`になってしまいます。

調べたところ、この方法では`Action['type']`が[distributive conditional types](https://www.typescriptlang.org/docs/handbook/advanced-types.html#distributive-conditional-types)として扱われないためだとのこと[（参考）](https://stackoverflow.com/questions/58584071/how-to-filter-union-of-object-type-by-property-in-typescript)。

distributive conditional typesの説明を見ると

> Conditional types in which the checked type is a **naked** type parameter are called distributive conditional types.

となっています。`Action['type']`は裸（naked）ではない型引数のため、distributive conditional typesとならないのです。

先ほどの[Stack Overflow](https://stackoverflow.com/a/58584234)の回答を見ると、以下のようなコードも載っていました。

```typescript
export type FilterActionByType<
  A extends AnyAction,
  ActionType extends string
> = A extends any ? A['type'] extends ActionType ? A : never : never;

type ActionUnion = Action<'count/get'> | Action<'count/set'>;

type CountGetAction = FilterActionByType<ActionUnion, 'count/get'>;
// type CountGetAction = Action<"count/get">
```

`A extends any ? ～ : never`によりラップすることで問題を回避していますね。なんてトリッキーな...。

いやはや、TypeScriptは奥が深い。そして設計者に改めて敬意を示したくなりますね！
Next.js 9.4 Fast RefreshとIncremental Static Regeneration等のアップデート

本日Next.js 9.4がリリースされました。簡単にまとめたので、[公式ブログ](https://nextjs.org/blog/next-9-4)と合わせて確認してください。

## Fast Refresh
Hot ReloadがReact Refreshを用いたFast Refreshに置き換えられました。
これで編集したファイル内のコードのみが更新され、コンポーネントの状態を失うことなく再レンダリングを行ってくれます。
これに伴いエラーのオーバーレイも再設計され、ページ上ですぐにエラーを確認できるようになっています。

## Incremental Static Regeneration (beta)
段階的な静的ページ再生成がサポートされました。
[Next.js 9.3でサポートされたStatic Generation](https://qiita.com/mottox2/items/5f01015e74c55c4df1be)では、ビルド時に生成したページでなくても`fallback: true`オプションを利用することで実行時に新しいページを追加することが出来ました。[Tweetを表示する事例が話題になりましたね。](https://static-tweet.now.sh/)

Next.js 9.4では過去に生成したページであっても、一定期間を経た後に再生成することができるようになります。
getStaticPropsでrevalidate期間を返すことで期間を設定し、ページが生成されてから設定した期間を超えると再生成されます。

## CMS examples
Contentful、DatoCMS、Prismic、Sanity、TakeShapeなどのCMSを利用したExampleが用意されています。
[Examples](https://github.com/zeit/next.js/tree/canary/examples)のうち`cms-`から始まるものがCMSのexampleです。
DatoCMSは画像の最適化、TinaCMSはページ内編集にも対応しているとのこと。

Headless CMSが更に便利に使えそうです。

## New Environment Variables Support
Next.jsはNode.jsとブラウザの両方で動くことから、環境変数を設定した場合、どっちで動作するのかが分かりづらいものでした。（Node.jsでしか見たくない環境変数がブラウザで見れたら事故ですよね）
そこで下位互換性のある2つの変更が行われました。

1. NEXT_PUBLICから始まる環境変数はブラウザに公開される。
2. `.env`のサポートが行われます。[Basic Features: Environment Variables](https://nextjs.org/docs/basic-features/environment-variables)

環境変数はデフォルトでNode.js環境でのみ利用可能で、NEXT_PUBLICで始まるものだけがブラウザで利用可能になります。


## Improved Built-in Fetch Support
今までブラウザ環境でのfetchポリフィルは提供されていましたが、サーバー環境では独自にポリフィルライブラリを導入する必要がありました。今回のBuild-in Fetch Supportではサーバー環境でもfetchポリフィルが用意されました。

## Integrated Web Vitals Reporting
Googleがウェブで優れたユーザー エクスペリエンスを実現するために重要と思われる品質シグナルの統合ガイドを提供する取り組みである[Web Vitals（日本語記事）](https://developers-jp.googleblog.com/2020/05/web-vitals.html)
Largest Contentful Paint, First Input Deley, Cumulative Layout Shiftをすべてのサイトで共通な指標ととらえCore Web Vitalsと呼んでいます。
これらの指標を追跡するために_app.jsにreportWebVitalsというメソッドが導入されました。（[ドキュメント](https://nextjs.org/docs/advanced-features/measuring-performance#sending-results-to-analytics)）

## Absolute Imports and Aliases
jsconfig.js, tsconfig.jsonを使って絶対パスでのインポートが可能になります。

## Configurable Sass Support
[Next.js 9.3でサポートされたBuild-in Sass Support](https://qiita.com/mottox2/items/5f01015e74c55c4df1be)。コンパイラーの設定をnext.config.jsでいじれるようになります。

## Improved Log Output
ログが重複して出力されるケースが改善されます。

---

## 感想
今回の目玉はIncremental Static Regeneration (beta)だと思います。これでメディアサイトであってもrevalidateの期間を短くすればstaticなページとして提供できるのではないかと考えています。
ガチャのデータ設計-基本的構造２-

#内容
[前回](https://qiita.com/saib-ryo/private/771b5839e9e34d9872ff)のデータ構造を拡張して、複雑なガチャ設定ができるようにしてみます

1. ガチャの引き方の設定追加
2. 複数の確率を保持する仕組みの追加

>[ガチャのデータ設計-基本的構造１-](https://qiita.com/saib-ryo/private/771b5839e9e34d9872ff)
>[Pythonで書くガチャ-データ設計-](https://qiita.com/saib-ryo/items/1309c4c94d9f6629ba6d)

##1. ガチャの引き方の設定追加
gacha_lotteryを拡張して、設定可能なガチャ条件を増やしてみます

- 属性の絞り込み（item_type）
- 通常抽選のレアリティ以上絞り込み（rarity）
- おまけの抽選回数指定（omake_times）

**gacha_lottery**

|  id | item_type | times | rarity | omake_times | omake_rarity | cost |
|:---:|:----:|:----:|:----:|:----:|:------:|:------:|
|  1  |  0  | 1  |  0   |  0    |  0    | 10 |
|  2  |  0  | 10 |  0   |  1    |  3    | 100|
|  3  |  2  | 2  |  0   |  0    |  0    | 30 |
|  4  |  0  | 10 |  2   |  2    |  3    | 200|
|  5  |  2  | 10 |  0   |  1    |  3    | 100|

各項目の設定条件を以下のように追加、変更します。
（これらの設定に対応するためにプログラムの改修が必要になります）

- item_type：0の場合は全て対象
- rariy：0の場合は全て対象
- omake_times：0の場合は、おまけなし
- omake_rarity：0の場合は全て対象（おまけの有無は、omake_times）

##2. 複数の確率を保持する仕組みの追加
ガチャアイテム確率情報は、ID毎の確率（重み）を管理しています。
あるIDについて確率（重み）は一つしか設定できません。

**「このガチャの場合は、確率（重み）を変更したい」**
ということに対応できるように、ガチャアイテム確率情報にグルーピングを行うための**グループ（gacha_group）**を持たせます。

**gacha_items**

|  id | gacha_group | weight | item_id |
|:---:|:----:|:----:|:------:|
|  1  |A |  1   |  5101    |
|  2  |A |  9   |  4201    |
|  3  |A |  9   |  4301    |
|  4  |A |  9   |  4301    |
|  5  |A |  20  |  3201    |
|  6  |A |  20  |  3301    |
|  7  |A |  20  |  3401    |
|  8  |A |  40  |  2201    |
|  9  |A |  40  |  2301    |
|  10 |A |  40  |  2401    |
|  11  |B |  15 |  4201   |
|  12  |B |  30 |  3201   |
|  13  |B |  55 |  2201   |

####gacha_lotteryの修正
gacha_itemsと紐付けるためのgacha_groupを追加します
**gacha_lottery**

|  id | gacha_group | item_type | times | rarity | omake_times | omake_rarity | cost |
|:---:|:----:|:----:|:----:|:----:|:----:|:------:|:------:|
|  1  |  A  |0  | 1  |  0   |  0    |  0    | 10 |
|  2  |  A  |  0  | 10 |  0   |  1    |  3    | 100|
|  3  |  B  |  0  | 2  |  0   |  0    |  0    | 30 |
|  4  |  A  |  0  | 10 |  2   |  2    |  3    | 200|
|  5  |  A  |  2  | 10 |  0   |  1    |  3    | 100|

##考察
###・データ構造と出来ること
|  id | gacha_group | weight | item_id |
|:---:|:----:|:----:|:------:|
|  11  |B |  15 |  4201   |
|  12  |B |  30 |  3201   |
|  13  |B |  55 |  2201   |

|  id | gacha_group | item_type | times | rarity | omake_times | omake_rarity | cost |
|:---:|:----:|:----:|:----:|:----:|:----:|:------:|:------:|
|  3  |  B  |  0  | 2  |  0   |  0    |  0    | 30 |

グループがBのガチャを抜き出してみました。
このガチャは、「属性がFighterのみ引けるガチャ」になります。

属性が**Fighter（item_type=2）**のみということであれば、**属性（item_type）**の絞り込みで可能ですが、確率の設定も変更したいので、敢えて別グループを作成しました。

拡張により、**このガチャの仕組み**にて出来ることをまとめると以下のようになります

- ガチャ対象アイテムをグループ（母集団）として複数設定
- ガチャ実行時に属性の絞り込み（item_type）
- ガチャ実行時に通常抽選のレアリティ以上絞り込み（rarity）
- ガチャ実行時に通常抽選の回数指定（times）
- ガチャ実行時におまけのレアリティ以上絞り込み（omake_rarity）
- ガチャ実行時におまけの抽選回数指定（omake_times）

###・開発の現場において
通常はガチャの企画と、運用の設定されるのは**プランナーさん（非エンジニア）**です。企画に応じて、データ設計とプログラム開発を**エンジニア**が行うことになります。
そのため、**エンジニア**として開発をする際に抑えておきたいことは、以下の2点になります

- ガチャとしての基本的データ構成
- 機能の拡張性

また、**運用データの設定のしやすさ**も求められることです。
複雑すぎてエンジニアでなければデータの設定ができないというのは、自分の首を絞めることになりかねないので気をつけておきたいことです。
Ansible Playbook タグの継承

Ansible Playbook のタグについて、混乱する挙動があったので調べてみました。
タグの継承についてです。
https://docs.ansible.com/ansible/latest/user_guide/playbooks_tags.html#tag-inheritance


```yaml:tagtest.yml
- name: Test Tag
  hosts: localhost
  connection: local
  tasks:
    - name: "step_1"
      debug:
        msg: "こんにちは"
    - name: "step_2"
      debug:
        msg: "hello"
      tags:
        - hello
```

この Playbook を `hello` タグを指定して実行すると、タグが付いていない `step_1` タスクは無視され、`step_2` タスクのみが実行されます。

ここまでは想定通りです。

では、この Play 自身にも次のように `hello` タグが付与されている場合、`hello` タグを指定して実行するとどのタスクが実行されるでしょう。

```yaml:tagtest.yml
- name: Test Tag
  hosts: localhost
  connection: local
  tasks:
    - name: "step_1"
      debug:
        msg: "こんにちは"
    - name: "step_2"
      debug:
        msg: "hello"
      tags:
        - hello
  tags:
    - hello
```

実行結果は次の通りです。

```text
$ ansible-playbook tagtest.yml -t "hello"

PLAY [Test Tag] ************************************************************************************************************************************************************************************************************************

TASK [Gathering Facts] *****************************************************************************************************************************************************************************************************************
ok: [localhost]

TASK [step_1] **************************************************************************************************************************************************************************************************************************
ok: [localhost] => {
    "msg": "こんにちは"
}

TASK [step_2] **************************************************************************************************************************************************************************************************************************
ok: [localhost] => {
    "msg": "hello"
}

PLAY RECAP *****************************************************************************************************************************************************************************************************************************
localhost                  : ok=3    changed=0    unreachable=0    failed=0    skipped=0    rescued=0    ignored=0   
```

タグの付いていない `step_1` も含め、すべてのタスクが実行されています。

この挙動に最初は混乱していたのですが、タスクはその親に当たる Play からタグを継承していて、`step_1` タスクにも `hello` タグが付いているのだと分かりました。

一つの Playbook に複数の Play が含まれている場合。以下の Playbook を、`hello` タグを指定して実行すると、「こんにちは」「hello」「Ciao」が出力されます。

```yaml:tagtest.yml
- name: "Test Tag 1"
  hosts: localhost
  connection: local
  tasks:
    - name: "step_1"
      debug:
        msg: "こんにちは"
    - name: "step_2"
      debug:
        msg: "hello"
      tags:
        - hello
  tags:
    - hello

- name: "Test Tag 2"
  hosts: localhost
  connection: local
  tasks:
    - name: "step_1"
      debug:
        msg: "Hola"
    - name: "step_2"
      debug:
        msg: "Ciao"
      tags:
        - hello
```
Reactのrender()内で、コンポーネントの引数に数値を渡す方法

# 盲点でした。
react-railsの環境では、以下のようなコマンドで簡単にコンポーネントの雛形が作れます。
```bundle exec rails g react:component sampleComponent id:number name:string ```

こうして作られたファイルの中身は以下のようになります。

```javascript:SampleComponent.js

import React from "react"
import PropTypes from "prop-types"
class SampleComponent extends React.Component {
  render () {
    return (
      <React.Fragment>
        Id: {this.props.id}
        Name: {this.props.name}
      </React.Fragment>
    );
  }
}

SampleComponent.propTypes = {
  id: PropTypes.number,
  name: PropTypes.string
};
export default SampleComponent

```

ここで、idの型をnumberとしてみたはいいものの、render()内で実際にSampleComponentを使う際はどうやって値を渡すのでしょう？

# ダメな方法
stringさんは、以下の方法で渡せます。
```<SampleComponent name="hoge" />```

が、numberさんを以下のように書いてしまうと、エラーになります。
```<SampleComponent id="10" />```

# 解決方法
中かっこ("{}")で囲みます。
そうか、数値リテラルを渡すのだから、こうなるんですね。
思いつかなかった。。
```<SampleComponent id={10} />```
シェルスクリプト内でディレクトリ階層移動して呼び出し元で反映する方法

# シェルスクリプト内でディレクトリ階層移動して呼び出し元で反映する方法

簡単なシェルスクリプト書いたので後世に残しておく。
特にシェルに詳しいわけではないので何か問題あったら気軽に編集リクエストとかコメントください！

## やりたいこと

- 毎日サーバー上で日付いりのフォルダを掘ってそこで作業している人向けのスクリプト `mkdir 190512 && cd 190512`
- 現シェルのコンテキストで別シェルを呼び出す `source ~/start.sh`

## データ

> ~/ops/startTodaysOps.sh

```bash
#!/bin/bash

dir1='ops/'
dir2=`date "+%y%m%d"`

dir=$dir1$dir2

if [[ ! -e $dir ]]; then
    mkdir $dir
    chmod g+w $dir
fi

echo $dir
cd $dir
```

> ~/.bashrc

```.bashrc
alias start='source ~/ops/startTodaysOps.sh'
```

> 実行する

```bash
hirao $ start
ops/200512

hirao $ ~/ops/200512$ 
```

## ちょっとだけ解説


```
# 存在確認
if [[ ! -e $dir ]]; then

fi
```

```bash
# -p オプションで存在確認してもよし
    mkdir $dir

# とりあえずグループに書き込み権限あたえる
    chmod g+w $dir
```

```bash
cd $dir

# このCDは source で呼び出さないと別シェルでディレクトリ移動するっぽい
```

実行シェルのプロセスIDを書き出す


> test.sh

```bash
#!/bin/bash

echo $$
```


```bash
~/workspace/shell-sample hirao$ echo $$
42143

~/workspace/shell-sample hirao$ ./test1.sh       
42366

~/workspace/shell-sample hirao$ source ./test1.sh
42143

```

こんな感じ。sourceで実行すればもとのシェル内での移動になるので実行後に移動されています。

## 終わりに

結構雑に書きましたが、スクリプト書くのには時間かかった（ `cd` されずにハマった）ので同じ感じでハマるかたがいないように :pray:
「新型コロナ」で株価急落？Webスクレイピングで日経平均株価を取得してみた

元記事：https://www.octoparse.jp/blog/scraping-stock-prices/

2020年1月に中国で感染が報告された新型コロナウィルス（COVID-19）は、世界に蔓延し、3月中旬には他国の感染者数が中国の感染者数を追い抜きました。各国で外出制限等が行われ、金融市場は大きく動き、実体経済も多くの国で大きく落ち込みました。新型コロナウイルスのパンデミックを受けて、株式市場の大幅な下落も生じています。

この記事では、１月から4月までの日経平均株価をスクレイピングしようと思います。今回はYahoo!ファイナンスのWebサイトの公開しているデータを利用します。以下URLで、日経平均株価データ過去4ヶ月分を参照できます。

https://info.finance.yahoo.co.jp/history/?code=998407.O&sy=2020&sm=1&sd=1&ey=2020&em=4&ed=30&tm=d

 

それでは、始めましょう！

 

#データ収集

PythonやAPIなどで株価データをスクレイピングすることがよくありますが、Pythonだと作業が複雑になり、無料API情報も持ってないので、今回はスクレイピングツールである[Octoparse](https://www.octoparse.jp/)を使います。

最新[バージョンの8.1版](https://helpcenter.octoparse.jp/hc/ja/articles/360013048720)はWebページの自動認識機能が備え、先のURLを入力するだけで、肝心なデータが検出され、実行すると、すばやく抽出できます。
![7.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/262932/f262c134-c9ea-5677-e9a4-5ccabe2f4872.gif)


 

Pythonなどは割と高速ですが、過去1年以上の時系列データをスクレイピングしようとするとやはり時間がかかります。株価分析したい時、大量のデータを解析したい場合は、やはりOctoparseなどの[スクレイピングツール](https://www.octoparse.jp/blog/10-best-open-source-web-crawler/)でデータ収集するのが最も効率的だと思います。しかもハンズフリーでデータをスクレイピングできるのは素人にもやさしいですね。

以下は取得したデータです。整理することもなく、完璧なデータフォーマットです。

![sample data.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/262932/d9fe97e8-bbbf-d247-53c1-d1a306a1374c.png)


 

#データ分析

今回はデータも取得したので、公式のものほど完璧ではありませんが、Excelで株価のグラフを作ってみました。
![日経平均株価.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/262932/9d79c118-5feb-14fa-81a5-ee19df34b2f9.png)


グラフに見れば、日経平均株価は2/21の23,386.74円から暴落が続いて、3/19に目先の底値16,552.83円を付けました。日銀による買い支えもあって目先戻り基調となり、3/25には戻り高値19,546.63円まで戻しました。4/1には18,065.41円まで下げたが、今では、暴落はいったん下げ止まり、しかも徐々に上げています。

新型コロナウイルス感染症の流行拡大による混乱により、日本だけでなく、世界各国の株式市場も下落が続いています。アメリカ株式市場でも、3月9日、12日、16日の取引で寄り付き直後にS&P500種株価指数が7％を超える下落となり、取引が15分間停止されるサーキットブレーカーが発動されました。この措置が発動されたのは1997年以来です。

<img width="250" alt="img_f340657b5c7a14f030b33b232a9949bf73254.jpg" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/262932/7e482151-0ba6-df04-ddf0-513e2ff88e6f.jpeg">

[出所：ピクテ投信投資顧問株式会社](https://gentosha-go.com/articles/-/26144)

 

#まとめ

過去、株式市場は何度も、様々な理由で急落を繰り返してきましたが、今回の新型コロナウイルスの世界的な感染拡大については、工場の生産能力の低下、サプライチェーンや交通網の遮断など供給面での影響（供給ショック）への懸念が株価の下落に繋がりました。グローバル化が進んだから、どこかの国で新型コロナウィルスの影響が続けば、それが他国の経済活動に影響し、それだけに厳しい局面が続きそうと思います。

いずれにしても、一刻も早く事態が収束し、新型コロナウィルス危機を乗り越えられるよう望んでいます。
InteliJを更新時ににlombokプラグインでエラーが起きる。

#事象
InteliJを2018.3 -> 2020.1 にアップデートしたときに、
プラグインとして入っていた「lombok」が互換性がない旨のエラーが出る。

エラー内容：「intellij plugin is incompatible with this installation」


#解決
「lombok」プラグインを一度アンインストールして、再度インストールし直す。
アンインストールは下記のようにドロップダウンから可能。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/338998/a42f4d27-23cf-b234-96f2-ab383e92fc70.png)
Symfony のテストで private なサービスを取得する

Symfony 3.4 以降では、すべてのサービスは private となりました。それにより container の `get` メソッドでインスタンスを取得することができません。

それ自体は良いことですが、テストの時に困ることがあります。

テストで、あるクラスのインスタンスを作りたい。それがテスト対象のクラスの場合もありますし、テスト対象のクラスを作るために必要な依存するクラスの場合もあるでしょう。
完全な単体テストでしたらモックを作って、となるところですが、実際のインスタンスを注入してテストしたいこともあります。

そんな時には、container の `get` メソッドで取得したいのですが、前述の規則により取得することができません。しかし、そのための抜け道を Symfony は用意してくれています。

`KernelTestCase` などの中で次のようにコンテナを取得すると、`get` で private なサービスを取得できませんが、

```php
self::bootKernel();
// returns the real and unchanged service container
$container = self::$kernel->getContainer();
// error will occur
$container->get(SomeClass:class);
```

次の手順で取得すれば、private なサービスを取得することができるようになります。

```php
self::bootKernel();
// gets the special container that allows fetching private services
$container = self::$container;
// will succeed
$container->get(SomeClass:class);
```

参考:
[New in Symfony 4.1: Simpler service testing](https://symfony.com/blog/new-in-symfony-4-1-simpler-service-testing)
Githubで新規にリポジトリを作成する方法

## この記事では以下の前提条件を満たしていることを想定しています。

- Githubのアカウントの作成が完了している
- Githubのアカウントに登録しているメールのGithub側の確認が済んでいる。
- Githubにログインしている

### Githubにログインした状態で赤枠の部分をクリックする

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/3f5ca1b5-7994-144c-7908-10bd79ef94d8.png)

### 「New repository」をクリックする

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/80dc8ea7-91c5-454b-2a0e-99861d5b80c3.png)

### 「Create a new repository」画面で「Repository name」などを入力し「Create repository」ボタンを押下する(この記事ではプライベートのリポジトリでREADMEを追加する設定にしています)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/44cba250-3362-6fbb-0e24-4acd9dd7e605.png)

### リポジトリが作成されていることを確認する

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/f7cd0aa5-4f17-1795-a82a-16b8385edf14.png)

## 改訂履歴

- 2020/5/12 新規作成
SSR、SSG、Client Side Renderingの違いをまとめた

SSR、SSG、ClientSideRenderingの違いについて言語化。Next.jsチュートリアルの説明が個人的に一番わかりやすい。[Pre-rendering and Data Fetching](https://nextjs.org/learn/basics/data-fetching/pre-rendering)

## Client Side Rendering

「Client Side Rendering = SPA」の文脈で使われることが多い気がする。

ブラウザ上でJavaScriptを実行してDOMを生成、マウントし、コンテンツを表示させる。SPAアプリの場合、以下のような中身が空のHTMLファイルを使うことが多い。

```index.html
<html>
<head>
<title>sample</title>
</head>
<body>
<div id="app"></div>
<script src="/js/bundle.js"></script>
</body>
</html>
```

上記のHTMLファイルはルートディレクトリ直下に置くのが普通なため、```/```以外にリクエストが送られると404となる。開発時はwebpack-dev-serverがよしなに面倒を見てくれるが、ホスティング先ではそうではないので、初めてSPAでアプリを作ってホスティングしたときに戸惑うやつ。

なので、どのルートにリクエストが送信されても、上記のHTMLファイルがダウンロードされるように設定が必要。

「Vue.jsやReactを使っている = SPA」ではない。LaravelやRailsなどのテンプレートファイルにVueやReactコンポーネントを埋め込んで使う例もある。

### メリット

- ページ遷移が非常に高速（非同期で必要なデータを取得する場合は、そのコンテンツが表示されるまではラグがある）
- 最低限必要なものはHTMLファイル、JSファイルのみであり構成がシンプル。この2つをホスティング先に置いておけばとりあえずページは表示される

### デメリット
- JSファイルが実行、評価されてDOMがマウントされるまでコンテンツが何も表示されない
- JSファイルのサイズが大きくなると、ファイルダウンロードの時間が無視できないレベルになる
- SEOで不利（クローラーがJavaScriptを実行できるようになったとのことなので、この問題は解決されつつある。ただ、即時的に評価されるのではなく、評価までにラグがあるらしい）
- TwitterやFacebookのクローラーはJavaScriptを実行しないため、プレーンなSPAアプリだと動的なOGP対応ができない

## SSR

「Server Side Rendering」の略。Vue.jsやReactコンポーネントをサーバー側で評価、実行し、その結果を配信する。

オリジンサーバーにリクエストがあるたびに上記の処理を行い、HTMLファイルを生成する。そのため、サーバーの負荷は他の2つより高くなる傾向があり、TTFB（Time To First Byte）の時間も長くなる。

JSファイルを配信しないというわけではない。インタラクティブな表現のためのJSファイルは必要。

Nuxt.jsやNext.jsを使って実装するのが楽。

### メリット

- レンダリング後のファイルを返却するためコンテンツ表示までの時間を短縮できる
- SEOで不利を背負わない
- 動的なOGP対応が可能

### デメリット
- キャッシュ設定が複雑になりがち
- SSRするためのWebサーバーが必要になる

## SSG

「Static Site Generator」の略。「SSRする」は意味が通じるが、「SSGする」は元の言葉の意味を考えるとおかしい気がする。

アプリのビルド時にあらかじめページ表示に必要なデータを取得し、各ページごとに静的なHTMLファイルを出力しておく。そしてサーバーへのリクエスト時にはこのHTMLファイルを返却する。

たとえばヘルプページなんかはユーザーごとに表示するコンテンツが変わるわけではない。それなら最初から静的なファイルとして用意しておけばよくね？的な発想。

ブラウザが静的なHTMLファイルを取得するのはサイトへの初回リクエスト時のみで、ページ遷移時には代わりにJSONファイルを取得し、動的に変化する部分はこのJSONファイル内のデータを使ってレンダリングする。

上記はイメージがつきにくいが、実際に自分で試してみるとわかりやすい。

Nuxt.js、Next.js、Gatsby.jsなどが対応。Next.jsではSSRとSSGを混在させることもできる。

## メリット

- ページ表示までに必要な時間はClient Side Rendering、SSRより高速
- SEOで不利を背負わない
- 動的なOGP対応が可能

## デメリット

- 外部からデータを取得している場合、外部データが更新されたタイミングで再ビルドを行わないと変更は反映されない
- 上記の仕様から動的なデータが頻繁に変更される場合は採用しにくい。その場合はSSRのほうがマッチする


## まとめ
要件的にSSGを選択できるなら、そちらのほうが良さそう。SSRとSSGのメリットはよく似ているが、メンテナンス性などを考えると基本的にSSGのほうが楽になるはず。というより、SSRは消極的に選択される手法な気がする。。。
jquery女学院

自分の作成してるサービスはスクレイピングに関するものが多いので、その要素の取得のテストのためにgoogle chromeのコンソールでよく使ってるjqueryのコードなどをまとめておくことにしました。

amazonの価格取得
$('#priceblock_saleprice').outerText
$('#priceblock_ourprice').outerText
ページによって微妙にタグが違うみたいですね。

amazonの商品名のタグ
$('#productTitle').outerText
rails tutorial 【第二章】herokuプッシュ後に「Heroku | Welcome to your new app!」と表示されてしまう。

タイトル通りです。herokuにプッシュ後に「hell,world」が表示されずに「Heroku | Welcome to your new app!」と表示されてしまう問題の解決方法です。

<h2>原因</h2>
「git remote -v」で表示されたリモートリポジトリと実際にデプロイしているリポジトリが異なっていたため

<h2>解決方法</h2>
リポジトリ変更コマンド「git remote set-url heroku 新しいherokuのgitリポジトリURL」を実行して再度プッシュすると「hell,world!」が表示されました。

参考記事→https://teratail.com/questions/166277
【Laravel】フォームリクエストでバリデーションする

##`やりたいこと`##
- バリデーションする
- フォームリクエストを使い汎用性をあげる

##`前提`##
データベースは作成済み
モデルは作成済み
##`進め方`##
- フォームリクエストを作成する
- コントローラーを作成する
- viewを作成する
- ルートを設定する

フォームリクエストを作成する
-
コマンドプロンプトで作成するプロジェクトのディレクトリに移動してから

```php
$ php artisan make:request TestRequest
```
今回はTestRequestという名前のフォームリクエストクラスを作成。
※クラス名はキャメルケースにする。

```php:TestRequest.php
<?php
namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;
use Illuminate\Validation\Rule;

class TestRequest extends FormRequest
{
    public function authorize()
    {
        return true;
    }
　　//バリデーションしたい項目のルールを書く
    public function rules()
    {
        return [
          'name' => 'required',
          'prof' => 'required',
          'age'  => 'numeric|between:0,100',
          'mail' => 'email',
        ];
    }
　　//バリデーションしたい項目のエラーメッセージを書く
    public function messages()
    {
        return [
                'name.required' => '名前を入力してください',
                'prof.required' => 'プロフィールを入力してください',
                'age.numeric'   => '年齢を整数で入力してください',
                'age.between'   => '年齢は0歳～100歳の間で記入してください'
                'mail.email'    => '正確なメールアドレスを入力してください',
        ];
    }
}
```
コントローラーを作成する
-
コマンドプロンプトで作成するプロジェクトのディレクトリに移動してから

```php
$ php artisan make:controller TestController
```

今回はTestControllerという名前のコントローラークラスを作成。
※クラス名はキャメルケースにする。

```php:TestController.php
<?php
namespace App\Http\Controllers;

use Illuminate\Http\Request;
use User;
use App\Http\Requests\TestRequest;//TestRequestをuseするのを忘れずに

class TestController extends Controller
{
    public function index()
    {
        return view('user.index',['msg'=>'フォームを入力してください']);
    }

   //userメソッドの引数を先程作成したTestRequestにすることで自動的にバリデーションしてくれる
    public function user(TestRequest $request)
    {
        $user = new User;
        //フォームから送られてきたプロパティをすべて取得し$formに代入
        $form = $request->all();
        //全てのプロパティを取得すると必要のない_tokenプロパティまで取得してしまうのでunsetメソッドで削除
        unset($form['_token']);
        //Userモデルをインスタンス化した$userにfill($form)でデータベースに保存
        $user -> fill($form) -> save();
      
        return redirect('user.index',['msg'=>'正しく入力されました']);
    }
```

Viewを作成する
-

```php:index.blade.php
<p>{{$msg}}</p>
//$errorsはバリデーションするとlaravelで自動的に組み込まれるオブジェクト。
//エラーが一つでもあるなら@foreachで順に取り出して表示する。
@if (count($errors) >0)
    <div>
        <ul>
            @foreach ($errors -> all() as $error)
                <li>{{ $error }}</li>
            @endforeach
        </ul>
    </div>
@endif
<table>
<form action="/user" method="post">
    {{ csrf_fierd() }}
    <tr><th>name:</th><td><input type="text" name="name"></td></tr>
    <tr><th>Prof:</th><td><input type="text" name="prof"></td></tr>
    <tr><th>Age:</th><td><input type="text" name="age"></td></tr>
    <tr><th>Email:</th><td><input type="email" name="email"></td></tr>
    <tr><th></th><td><input type="submit" value="登録"></td></tr>
</form>
</table>
```

ルートを設定する
-
```php:routes/web.php
Route::get('/user', 'TestController@index');
Route::post('/user', 'TestController@user');
```

以上です。
SQLSeverのIN句でバインド変数を使う

# 要件
* べた書きのSQLしか作れません
* ORマッパーは利用できません
* プログラムで動的に条件句を編集することもできません
    *  文字列をカンマ区切りで繋げることくらいは可能

という~~絶望的な~~制約の中でIN句を動的に設定する必要が出てきました。
なお当方にストアドプロシージャの知識はありません。

# 解決策
SQLServerなら`STRING_SPLIT`に文字列と区切り文字を渡せばサブクエリとしてIN句の条件に使えます。([参考](https://qiita.com/Tachy_Pochy/items/27fafdce116d94132f66))

# サンプル
```sql
select
  id,
  name
from
  employee
where
  id in (
    select
      value
    from
      STRING_SPLIT('001,002,003', ',')
  )  
```

# おわりに
ORマッパー使えないのはキツいけど製品の制約なのでどうしようもないのですが、この場合は正直言って素直にストアドプロシージャ使った方が良いような気がします。
Githubのアカウントを作成する方法

## Githubのアカウントを作成する方法を解説します。

### Githubとは何か

[GithubのWikipedia](https://ja.wikipedia.org/wiki/GitHub)より
>GitHub（ギットハブ）は、ソフトウェア開発のプラットフォームであり、ソースコードをホスティングする。コードのバージョン管理システムにはGitを使用する。

### アカウント作成方法

#### **[Githubのページ](https://github.com/)にアクセスする、ユーザー名、メールアドレス、パスワードを入力し「Sign up for Github」ボタンを押下する**

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/9bb2b414-e19c-aef2-0140-027915920c2c.png)

####　検証開始をクリックする 

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/3fd55f36-0e76-ad6d-1a07-0c9a3749057a.png)

#### パズルを解く、終了リンクを押下する 

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/e712d804-f52d-1d93-9b6b-400c7a508d38.png)

#### 「Join a Free plan」ボタンを押下する 

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/bf6f11cf-5d91-b14a-975c-3a7c0f65b2ae.png)

#### 職業を選択する場面が表示される、こちらの入力は任意

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/3d6eac21-21a1-20fe-2f06-da5d9d7ab179.png)


#### 登録したメールアドレスのメールボックスを確認する。「[GitHub] Please verify your email address.」のメールの「verify email address」ボタンを押下し、メールアドレスの確認を完了させる

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/d6c2127d-f576-9bfc-a0b9-b4cf6d302441.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280363/e2e5485b-8318-86d3-b589-794aecd5cdb5.png)

以上になります。

##　改訂履歴
- 2020/5/12 新規作成
[備忘録]Shinyの日本語ファイル文字化け回避

#はじめに
shinyアプリを作成する際、日本語があると文字化けによりエラーが発生してアプリが実行できなくなることが多々あった。
回避方法がわかったので、備忘録として記す

また、文字化けは２種類ある。
1. コード上に日本語がある場合によるエラー
2. 読み込んだファイル内に日本語がある場合のエラー

###1.コード上に日本語がある場合によるエラー
https://qiita.com/testmemo/items/b145bcc6ee6296daf8a1
こちらの方の記事にある通りで、UTF-8として読み直し、UTF-8として読み込むことをすると、エラーが回避できた。
なお、当該ファイルをサクラエディタで開きなおし、UTF-8として保存したファイルの場合、エラーが発生した。

###2.読み込んだファイル内に日本語がある場合のエラー
自分の使い方としては、緯度経度が含まれているCSVファイルを読み込み、leafletによって作成した地図上に投影することをよくつかう。その場合、用意するCSVファイルはUTF-8ではなく、SHIFT-JISにしておく必要がある。
読み込むときは下記のようにする。

```
df <- read.csv(paste0(path,"sample.csv"))
```
とくにオプションはつける必要なし！

#おわりに
これで日本語が使えるようになりました！
Jupyter Notebookで!sudoマジックコマンドを実行する方法の備忘録メモ

Jupyter NotebookはPythonの手軽な実行環境として大変便利であり、愛用しています。Python意外の言語が追加出来る上にノートブック上でLinuxコマンド(マジックコマンド)も実行可能です。

# 実行例
以下の様に`ls`コマンドや`cd`コマンドが実行出来ます。

## lsコマンド

```bash
!ls
```

## cdコマンド

```bash
%cd
```

## pipコマンド
pipコマンドもマジックコマンドとして実行可能です。pandasをインストールする場合は以下のコマンドで実行可能です。Jupyter Notebookを使っている時に追加で必要なライブラリを追加する場合以下のコマンドを記載しておけばNotebookの共有時にも安心です。

```bash
!pip install pandas
```

# sudoが必要なコマンドも実行
ここから本題です。管理者権限(sudo)で実行が必要なコマンドを実行してみます。ここでは`apt`を実行してみます。Pythonのライブラリでは時々別途OSのパッケージマネージャーでアプリケーションをインストールを求められる物[^app]が有ります。Notebook上で実行出来ればインストール忘れを防げます。

## ステップ1: そのまま実行
そのまま試しに`!sudo apt update`を実行してみます。

```bash
!sudo apt update
```

以下の様な結果となりました。この状態ではパスワードは入力出来ません。

<img width="416" alt="sudo.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/469079/479611a0-6266-e6d1-9890-9cf2942b7ce9.png">

## ステップ2: echoコマンドを使って文字列渡し
echoコマンドを使って文字列としてパスワードを渡してみます。sudoコマンドには`-S`オプションを渡します。これでコマンドライン引数としてパスワードを渡せます。(実際は標準入力からパスワードを入力する方式)

```bash
!echo "passwd" | sudo -S apt udate
```

<img width="730" alt="sudopw.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/469079/dd6711fb-22f3-dfe1-c5b0-b34c5c04d240.png">

無事動きました。しかし、Notebook共有時に文字列を書き換える必要が有り煩雑になります。加えてこのままではパスワードが丸分かりであり、セキュリティー上好ましく有りません。パスワードが漏れてしまったりしてはパスワードの意味を成しません。。。

# パスワードを外部ファイル渡しとする
パスワードを`passwd.txt`というファイルに記載し、そのファイルの中身を読み込んで渡す方式に変更します。こうすればパスワードが誤って漏洩する心配も有りません。ファイルの読み込みには`xargs`コマンドを用います。コマンドライン引数を作るコマンドです。ここでは`-a`オプション(--arg-file=)を渡すことでファイルを指定しています。

```bash
!xargs -a passwd.txt | sudo apt update
```

<img width="632" alt="sudopwarg.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/469079/69e6eced-5f8a-ed1b-b4de-1031751d4309.png">

無事実行出来ました。パスワードが漏れる心配が無くなった上にNotebookの共有時にパスワード部分を書き換える必要が無くなり煩雑な作業が無くなりました[^passwd]。これで安心です。

# Reference
* [逆引きUNIXコマンド/sudoコマンドのパスワードを自動的に入力する方法](https://linux.just4fun.biz/?%E9%80%86%E5%BC%95%E3%81%8DUNIX%E3%82%B3%E3%83%9E%E3%83%B3%E3%83%89/sudo%E3%82%B3%E3%83%9E%E3%83%B3%E3%83%89%E3%81%AE%E3%83%91%E3%82%B9%E3%83%AF%E3%83%BC%E3%83%89%E3%82%92%E8%87%AA%E5%8B%95%E7%9A%84%E3%81%AB%E5%85%A5%E5%8A%9B%E3%81%99%E3%82%8B%E6%96%B9%E6%B3%95)
* [【 xargs 】コマンド――コマンドラインを作成して実行する](https://www.atmarkit.co.jp/ait/articles/1801/19/news014.html)
* [Jupyter Notebookでマジックコマンド一覧を確認する%lsmagic](https://note.nkmk.me/jupyter-notebook-ipython-lsmagic/)

[^app]: MecabやGraphVizはPython版とは別に本体のインストールも必要です。

[^passwd]: passwd.txtに相当するファイルを用意する必要は有りますが。。。
plex - Media Server

* [linuxserver/plex - Docker Hub](https://hub.docker.com/r/linuxserver/plex/)

```yaml:docker-compose.yaml
---
version: "2.1"
services:
  plex:
    image: linuxserver/plex
    container_name: plex
    network_mode: host
    environment:
      - PUID=1000
      - PGID=1000
      - VERSION=docker
    ports:
      - 32400:32400
    volumes:
      - ./library:/config
      - ./tvseries:/tv
      - ./movies:/movies
    restart: unless-stopped
```

* http://localhost:32400/web

にアクセスして応答があることを確認。
EC2上のterraformからawsのprofile指定して使いたい

EC2上でterraformを使う場合```--backend-config="profile=プロファイル名"```を指定しても、
インスタンスにアタッチされているIAMロールが優先されてしまいました。

```shell
$ TF_LOG=DEBUG terraform init --backend-config="profile=terraform_profile"

# - 省略 -

[DEBUG] [aws-sdk-go] <GetCallerIdentityResponse xmlns="https://sts.amazonaws.com/doc/2011-06-15/">
  <GetCallerIdentityResult>
    <Arn>arn:aws:sts::xxxxxxxxxx:assumed-role/ec2-sample-instance-role/i-0bb01f7be2c61dc01</Arn>
    <UserId> …
```

access_key等をvarで渡したり、.tfvarsを使う方法もありますが、
既にprofileが作成されている場合はAWS_PROFILEが使えます。

```shell
$ aws configure list --profile terraform_profile
      Name                    Value             Type    Location
      ----                    -----             ----    --------
   profile                  terraform_profile           manual    --profile
access_key     ****************UOJ5 shared-credentials-file    
secret_key     ****************eNBm shared-credentials-file    
    region           ap-northeast-1      config-file    ~/.aws/config

# これから作成する場合は--profileオプションで指定
$ aws configure --profile terraform_profile
AWS Access Key ID [None]: xxxxxxxxxxxxx
AWS Secret Access Key [None]: xxxxxxxxxxxxxxxxxxxxxxxxxxxxx
Default region name [None]: ap-northeast-1
Default output format [None]:
```

terraform init実行（version 0.12で確認）

```shell
$ AWS_PROFILE=terraform_profile terraform init
```

こんな感じでうまくいきました。
IQ Bot：エクスポートしたCSVの日本語が文字化けしている場合の対処

[IQ Bot](https://qiita.com/IQ_Bocchi/items/fab5f59230ff38a98bbd)の[抽出結果を表示](https://qiita.com/IQ_Bocchi/items/13720aee5ddc1770afe1)画面からエクスポートしたCSVをExcelで開くと、日本語の項目が文字化けしていることがあります。

![CSVが文字化けする.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587845/1544c623-fe60-1b7d-be7a-e2b438bfc1ed.jpeg)

一瞬びっくりしますが、該当のファイルを右クリックしてメモ帳で開くと文字化けせずに表示できているはず。

![メモ帳で開くと大丈夫.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587845/f95de87e-a539-c580-b900-18bcff8124fd.jpeg)

これはUTF-8のBOMあり・BOMなしという文字コードの問題によるものです。

詳細は[こちらのサイト（外部リンク）](http://blog.webscraping.ninja/?p=69)の説明がわかりやすかったです。

対処のしかたも、上記サイトに載っています。「3) Windowsの「メモ帳」を使う」が簡単かなと思います。
**メモ帳のコードがもともとUTF-8・BOM付きになっている場合は、その状態で上書き保存をするだけで大丈夫**です。

一度保存をしなおしてしまえば、以下のとおり、Excelで開いても文字化けしなくなります。
![一度保存しなおすと大丈夫.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/587845/57c94861-a18d-900f-cd4c-d78c10a7eaa3.jpeg)


#補足

この問題は、RPAで出力したCSVには起こらないのですが、マッピング設定の「抽出結果を確認」画面で「CSVにエクスポート」を選択した場合に、バージョンによって起こる場合があるようです。

V11.3.4以降では起こらないことを確認済みで、A2019.12では起こります。