OmniAICreator/Qiita-1.07M huggingface dataset:
How to "%" (mod, Modulo) in ASH shell (Alpine Linux) (Bash compatible)

[「how to "%" modulo in alpine linux or in ash shell」でググって](https://www.google.com/search?q=how+to+%22%25%22+modulo+in+alpine+linux+or+in+ash+shell)もピンポイントでヒットしなかったので、自分の<ruby>ググラビリティ<rt>Google-ability</rt></ruby>として。

## TL; DR

> Quote with `$((` `))` instead of `$[` `]`

```shell:ash/bash_compatible
#!/bin/sh

echo $(( $RANDOM % 10 ))

```
```shell-session
/app/tests # # Tested Alpine version (via Docker)
/app/tests # cat /etc/os-release | grep PRETTY
PRETTY_NAME="Alpine Linux v3.10"

/app/tests # # View sample script
/app/tests # cat sample.sh
#!/bin/sh

tmp_rand=$RANDOM
echo $tmp_rand
echo $(( $tmp_rand % 10 ))
echo $(($tmp_rand % 10))
echo $(( $tmp_rand % 10 + 1 ))

/app/tests # # Run in Ash shell
/app/tests # /bin/sh ./sample.sh
23095
5
5
6

/app/tests # # Run in Bash shell
/app/tests # /bin/bash ./sample.sh
9465
5
5
6
/app/tests # 
```

:::note info
If you get an error of "`arithmetic expression: expecting primary: " ... "`", you are probably using a shell that does not support `$RANDOM`. In that case consider using `:-` substitution.

```bash:Example
# 12345 will be used if $RANDOM is empty or not defined. Thus, not random.
RANDOM=${RANDOM:-12345}
```
:::

## TS; DR

Ordinary way. **Runs in Bash but not in ASH**. (Not compatible)

```shell:sample1.sh
#!/bin/bash

time_sleep=$[ ( $RANDOM % 10 )  + 1 ]
echo "Sleeping ${time_sleep} seconds ..."
sleep "${time_sleep}"s
```
```shell-session
/app/tests # # Run in Ash shell (Fails)
/app/tests # /bin/sh ./sample1.sh
./sample.sh: line 3: syntax error: unexpected "("

/app/tests # # Run in Bash shell
/app/tests # /bin/bash ./sample1.sh
Sleeping 3 seconds ...
```

- [View it online](https://paiza.io/projects/O_Jh1uyWRBzsxcwOA1X7mg) @ paiza.IO

Now, let's make it compatible between Bash and Ash.

```bash:sample2.sh
#!/bin/sh

time_sleep=$(( $RANDOM % 10 + 1 ))
echo "Sleeping ${time_sleep} seconds ..."
sleep "${time_sleep}"s
```

```shell-session
/app/tests # # Run in Bash
/app/tests # /bin/bash ./sample2.sh
Sleeping 8 seconds ...

/app/tests # # Run in Ash
/app/tests # /bin/sh ./sample2.sh
Sleeping 8 seconds ...
```

- [View it online](https://paiza.io/projects/9ztWRhAg3X4sIuLLVbEwpA) @ paiza.IO

---

```shell-session:VersionInfo
/app/tests # # Alpine Linux default shell
/app/tests # /bin/sh --help
/bin/sh --help
BusyBox v1.30.1 (2019-06-12 17:51:55 UTC) multi-call binary.

Usage: sh [-/+OPTIONS] [-/+o OPT]... [-c 'SCRIPT' [ARG0 [ARGS]] / FILE [ARGS] / -s [ARGS]]

Unix shell interpreter

/app/tests # # Install bash shell
/app/tests # apk --no-cache add bash
...
/app/tests # /bin/bash --version | grep version
GNU bash, version 5.0.0(1)-release (x86_64-alpine-linux-musl)
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
```

## Reference（参考文献）

- [Newbie question: modulo operator with negative operand, bug or feature?](https://www.unix.com/shell-programming-and-scripting/260045-newbie-question-modulo-operator-negative-operand-bug-feature.html) @ The UNIX and Linux Forums
【SQL】Error Code: 1241. Operand should contain 1 column(s)のエラーの対処方法について

```
Error Code: 1241. Operand should contain 1 column(s)
```
このエラーは自分がサブクエリを走らせたときにでてきました。
どういうパターンのときにでてきて、どのように対処すればいいのか紹介していこうと思います。

1. オペランドとは
2. サブクエリのオペランド
3. 対処
オペランドとは

##オペランドとは何か？

[オペランド (operand)とは｜「分かりそう」で「分からない」でも「分かった」気になれるIT用語辞典](https://wa3.i-3-i.info/word13306.html)

このサイトによると、式を構成する要素、演算子ではなく数字や変数のことというわけです。
直訳すると被演算子という意味になります。

SQLの場合だと、、？

```sql

select * from tableA
```

この*のところです。

オペランドと聞いて僕はオペラント条件づけのことを思い出しましたが、関係なかったです。
`operand`と`operant`ですｗ 
operantだと「事象によって変化する行動」みたいな意味になります。全然違います

##サブクエリのオペランドと対処方法

今回のエラーは

```sql

select * from tableA where (select * from tableB where columnA = "A") is not null
```
みたいな感じでサブクエリを書いたときに発生しました。

エラー文によると、「オペランドが一つのカラムを持っている必要がある」ということを行っていますね。
今回の文だとサブクエリのオペランドが*になっていて、複数カラムを指定していますね。
これに対して、「is null」を適用することはできません。tableAの中からカラムをひとつだけえらんで対象に設定できるようにすればいいかと思います。

以上でなおる簡単なエラーでした。
もしこのエラーがでたら、オペランドの意味を確認してselectでとってきているものに問題がないかなどを確認してあげて下さい。

以上です。
PyStan 自分用メモ

初期値設定

```
fit = sm.sampling(data = stan_data, iter=2000, warmup=500, chains=1, seed=123, init=[dict(a=0.5, mu=[0,5], sigma=[1,1])])
```

各サンプル抽出時にwarmupを加える

```
fit.extract(permuted=False, inc_warmup=True)
```
Phoenix1.5 の開発環境でSSLの設定方法

久々の投稿

どうもこんにちは、東京なのにfukuoka.exのYOSUKENAKAO.meです。

さて、本日は開発環境でHTTPS接続する必要があったので、その設定方法を調べて見た所、めちゃくちゃ簡単だったのですがQiitaには古い方法しか見当たらなかったので情報を更新しておこうと思います。

# Phoenix 開発中のSSL化

開発中SSL化はずばり次の２STEPで終了です。

## STEP1 Mixコマンドで自己署名証明書を生成

```console
$ mix phx.gen.cert
```

## STEP2 config/dev.exsに下記を追加

```elixir
config :my_app, 自分のアプリ.Endpoint,
  ...
  https: [
    port: 4001,
    cipher_suite: :strong,
    keyfile: "priv/cert/selfsigned_key.pem",
    certfile: "priv/cert/selfsigned.pem"
  ]
```

終了。

はい便利
【SQL】join・group by・sum・countを用いた発展的な使い方

データベースは以下の通り。

カラムは省略。


|   id |   user_id     |    utem_id    |  purchased_at |  
|:-----------------|------------------:|:------------------:|:----:|
|              |            |            |   |
|            |            |           |   |
|              |            |            |   |
|                |            |            |   |
|              |            |          |   |
|          |            |          |   |




##例題

販売記録を日付ごとにグループ化し、
・日付
・日付ごとの販売個数
を日付順で取得する。

考えるポイント

・日付ごとにデータを取得する必要があるのでgroup byを使う。
・日付ごとの販売個数を出すので販売個数に対してcountを使う。

```
select purchased_at, count(item_id),  
from sales_records
group by purchased_at;
```





##例題
販売記録を日付ごとにグループ化し、
・日付
・日付ごとの販売個数
を日付順で取得する。


テーブルは以下の通り。

|   id |   user_id     |    item_id    |  purchased_at |  
|:-----------------|------------------:|:------------------:|:----:|
|              |            |            |   |
|            |            |           |   |
|              |            |            |   |
|                |            |            |   |
|              |            |          |   |
|          |            |          |   |



|   id |   name     |    gender    |  price | cost  |  
|:-----------------|------------------:|:------------------:|:----:|:----:|
|              |            |            |   | |  
|            |            |           |   | |  
|              |            |            |   | |  
|                |            |            |   | |  
|              |            |          |   |


ポイント
・テーブルが2こあるのでjoin〜onを使う。
・日付カラムに対してgroup byを使う。
・売上カラム（つまり値段）に対してsumを使う。



```
select purchased_at, SUM(items.price) AS "売上額"
from items
join sales_records
on items.id = sales_records.item_id
group by purchased_at;
```


##countの使い方
カラムの数を計算する。select count(*)とgroup by```カラム名```を一緒に使うことによって、そのカラムごとの合計を別で計算して表示してくれる。
【Docker】docker loginをするときにError saving credentials: error storing credentialsがでてログインできないときの話


職場でUbuntu 18.10をつかっていたのですが、docker loginをしようとしたところcredentialに関するエラーが出続けて悩みまくっておりましたが、なんとか解決できたのでそのメモ。gitlab registryにもdocker hubにもログインできず死んでおりました。

エラーは

```
Error saving credentials: error storing credentials - err: exit status 1, out: `The connection is closed`
```

こんな感じです。
正直connection is closedっていうのが？？？っていう感じでした。

とりあえずdockerの公式ドキュメントのloginのところをみてみると


[Docker公式ドキュメント(英語版)](https://docs.docker.com/engine/reference/commandline/login/#credentials-store)

`$HOME/.docker/config.json`

ここにdockerはcredentialに関する情報を溜め込んでいるようです。
中身をみてみると、、

```json
"credsStore": "secretservice"
```
このcredsStoreでは証明書を外部保存する先を指定することができるようです。

公式ドキュメントによると、、、



>DEFAULT BEHAVIOR
By default, Docker looks for the native binary on each of the platforms, i.e. “osxkeychain” on macOS, “wincred” on windows, and “pass” on Linux. A special case is that on Linux, Docker will fall back to the “secretservice” binary if it cannot find the “pass” binary. If none of these binaries are present, it stores the credentials (i.e. password) in base64 encoding in the config files described above.


Linux上でのみ"pass"がない場合は自動でsecretserviceが指定されるようになっているみたいです。
ここが悪さをしていたようで、↑を消して証明書が外部に保存する機能をなくしてから再度loginすると見事ログインできるようになりました！！


>WARNING! Your password will be stored unencrypted in /root/.docker/config.json.
Configure a credential helper to remove this warning. See
https://docs.docker.com/engine/reference/commandline/login/#credentials-store

>Login Succeeded



>root/.docker/config.json.

ここに証明書情報がセーブされちゃっていて、あまりよろしくないかもですが、、
ひとまず安心です。
Macだったらすごくあっさりとできたので、ubuntuとの違いを感じました、、
SQLとPower Query 用語の違い

Power Queryを触り始めたころ、「SQLでいうところの〇〇をするにはどうすればいいんだろう？」ってことがよくあったので、**SQLの〇〇 → Power Queryでは✖✖** という形式で軽くまとめてみました。

他にも思い出したら追記する...かも

## JOIN → マージ
SQLでMERGE(UPSERT)といえば、更新と挿入を同時にできるやつのことなので、いきなり意味が違いすぎて面食らいました。
M言語の関数名は```Table.Join```なのに何故...

## UNION → 追加
こちらはアイコンの形状から想像がつきやすかったです。
![PowerQueryUnion.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/239258/4e50a091-114b-0210-ab56-fd127288e977.png)
標準的なSQLのUNIONと違い、互いの列に差があっても、統合した結果を返すようです。
![UnionSample.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/239258/85f7b40c-142a-5d06-3ed2-2386cd31ecbf.png)
Windows+VScodeでTerraformフォーマッタを実行する

VScodeでTerraformフォーマッタ (terraform fmt) を実行する手順メモ

## ゴール

VScodeのフォーマッタのショートカットキー「Ctrl + Alt + F」にて、`terraform fmt` を実行できるようになる。
![terraform_fmt.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/420612/0725d0f5-dad2-9d7e-cb63-3f63c67bca2f.gif)

## 環境

- Windows 10 pro 64bit version 1909
- VScode version 1.44.2

## 手順

### 1. Terraform インストール

1-1. [公式サイト](https://www.terraform.io/downloads.html) からWindows 64-bit版をダウンロード
1-2. ```C:\Users\my_user\terraform``` に解凍する
1-3. パスを通す  
管理者権限でPowershellを実行し、以下のコマンドを実行する  

```
>$env:Path += ";C:\Users\my_user\terraform"
>[Environment]::SetEnvironmentVariable('PATH', $Env:Path, 'Machine')
```

1-4. 実行確認  
以下のコマンドにてバージョンが表示されればOK  

```
> terraform -v
Terraform v0.12.24
```

### 2. VScode TerraformExtensionをインストール

[これ (mauve.terraform)](https://marketplace.visualstudio.com/items?itemName=mauve.terraform) をインストールする  

以上.

### 補足: ファイル保存時に自動でフォーマット実行する設定

1. VScode > ファイル > 基本設計 > 設定 で「editor.formatOnSave」で検索
2. `Editor: Format On Save` にチェックを入れる  
※settings.jsonに `"editor.formatOnSave": true` を追加でもOK
![formatonsave.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/420612/6ab0d8dd-1fe1-871b-91f1-8192b2f5f64f.png)



※ 留意点 ※
自動保存をON ("files.autoSave": "off"以外)にしている場合、自動フォーマットは実行されないようです。
その場合は、「Ctrl + Alt + F」にて任意タイミングでフォーマットしましょう。

## 参考

- [VSCodeでのTerraformはじめ](https://qiita.com/garakutayama/items/0cdf43816bde2378f4f)
- [VSCodeでTerraformを書くときの設定(2019/11/07追記: HCL2対応)](https://qiita.com/pypypyo14/items/5520f3defa55119f3a1a)
SPRESENSE LTE拡張ボードからTwitterを利用する

SPRESENSEデバイスからLTE越しにツイートするライブラリを作成しました。

## Twitterアカウントの作成

既存のアカウントを使用することもできますが、ここでは~~いつ凍結されても良いように~~専用のTwitterアカウントを作成します。
Twitterアカウントを作成するのに別のメールアドレスを用意するのが面倒だな～と思っていたのですが、こんな方法がありました。
[Twitterアカウントの複数作成をひとつのメールアドレスで!?](https://yamashitamasahiro.com/archives/1570)

## Twitterトークンの取得

[StewGate U](http://stewgate-u.appspot.com/u/
) のサイトへさきほど作成した Twitter アカウントでログインし、連携アプリとして認証します。
この作業により、Twitter トークンを入手することができます。OAuth という仕組みを使っています。

<!--
> 認証の仕組みは [一番分かりやすい OAuth の説明](https://qiita.com/TakahikoKawasaki/items/e37caf50776e00e733be) が参考になります。
-->

> ちなみに認証解除したいときは、Twitter->もっと見る->アカウント->アプリとセッション->StewGate U->アクセス権を取り消す、から解除可能です。

## Twitterライブラリ

[Stewitter](https://github.com/arms22/Stewitter) をベースにして、Spresense LTE 用の Twitter ライブラリを作成しました。
https://github.com/baggio63446333/SpresenseLteTwitter

Arduino の libraries 以下にインストールして使ってください。

## SimplePost サンプルスケッチ

`SpresenseLteTwitter`->`SimplePost` のサンプルスケッチを用意しました。

使用している SIM 環境に合わせて APN 情報を変更してください。

```c++:SimplePost.ino
// APN data
#define LTE_APN       "apn"      // replace your APN
#define LTE_USER_NAME "user"     // replace with your username
#define LTE_PASSWORD  "password" // replace with your password
```

"YourToken" を先ほど取得した Twitter トークンに置き換えてください。

```c++:SimplePost.ino
SpresenseLteTwitter twitter("YourToken");
```

"msg" はツイートの本文です。自由に書き換えてください。

```c++:SimplePost.ino
char msg[] = "Hello, World! I'm Spresense!";
```

繰り返し同一のツイートが禁止されていたり、時間あたりのツイート回数に制限等があったりするのでつぶやきすぎにはご注意ください。
ValueError at set_wakeup_fd only works in main thread の対処法

#背景
DjangoでSSOするためにRemoteUserMiddlewareを使おうとしたら、下記のエラーが出る。

```
ValueError at set_wakeup_fd only works in main thread
```

しかもリロードするたびに出たり出なかったりする奇怪な現象。

#環境
- Windows Server 2016 64bit
- Python 3.8.2
- Django 3.0
- Apache 2.4 + mod_wsgi + mod_shib
- Shibboleth2（今回、直接の関係はない）

#原因
どうやらmod_wsgiのバグ。技術力不足により、理屈は追わない。
[ValueError: set_wakeup_fd only works in main thread #143](https://github.com/django/asgiref/issues/143)
[set_wakeup_fd only works in main thread #156](https://github.com/django/asgiref/issues/156)

#対処
2020/5/4時点で根本的には未解決。
仕方なく、[この人がやったように](https://github.com/django/asgiref/issues/156)Python3.8.2をPython3.7.7に下げる。

##1. Python3.7.7をインストール
https://www.python.org/downloads/windows/
このへんから持ってきてインストール。
PATHに設定するというチェックボックスは外しておいたほうがよい。

##2. 上記に対応するmod_wsgiをインストール
[Python Windows で mod_wsgi を Apache に組み込む方法](https://qiita.com/hatai/items/279ec1dfd28cb9693a1f)
いつもお世話になっている記事↑と、それをもとに書いた記事↓。
[Django + Apache with mod_wsgi on Windows Server 2016]()

##3. DjangoのPython Interpreterを変更
環境によって異なるが、PyCharmでは次の通り。
SettingsのProject InterpreterでAddを選択（右端、切れてしまった…）
![ss02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/117020/c4d2b19a-819a-e7c1-88c1-fa02fda92cbc.png)

Python3.7のInterpreterを選択して、Locationフォルダを適当に変更（今回、安直に"venv2"とした）
![ss01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/117020/605780a4-eac0-333b-7f0b-21b14295b66f.png)

あとはPackageの「＋」ボタンを押してDjangoをインストール。
（しないと、Django関係の識別子がすべてUnresolved referenceになって動かない）

##4. Apacheのhttpd.confにある関係項目を変更  

```conf:httpd.conf
##python3.8.2
#LoadFile "c:/program files/python38/python38.dll"
#LoadModule wsgi_module "c:/program files/python38/lib/site-packages/mod_wsgi/server/mod_wsgi.cp38-win_amd64.pyd"
#WSGIPythonHome "c:/program files/python38"

#python3.7.7
LoadFile "c:/users/administrator/appdata/local/programs/python/python37/python37.dll"
LoadModule wsgi_module "c:/users/administrator/appdata/local/programs/python/python37/lib/site-packages/mod_wsgi/server/mod_wsgi.cp37-win_amd64.pyd"
WSGIPythonHome "c:/users/administrator/appdata/local/programs/python/python37"
```
なお、フォルダ構成は各自の環境に従う。
ちなみにこれらは、

```shell
> mod_wsgi-express module-config
```
コマンドで出力される内容をコピペすると楽。
WSGIPythonPathの変更も忘れずに。

```conf:httpd.conf
##python3.8.2
#WSGIPythonPath d:/apps/shib_test/venv/Lib/site-packages

#python3.7.7
WSGIPythonPath d:/apps/shib_test/venv2/Lib/site-packages
```

あとはApacheを再起動して完了。
Excel×Pythonで作業フローを効率化する方法を調べてみた③

#今回の目的
PythonでExcelファイルを出力するときに、書式を設定する。
※例のごとく、説明はプログラムのコメントで記載しています。

###プログラムの流れ
①sample.xlsxファイルを取り込む
②書式を多数設定する
③sample2.xlsxファイルに出力する

###前回参考
Excel×Pythonで作業フローを効率化する方法を調べてみた②
https://qiita.com/t20190127/items/023e5dd0128252f46378

#プログラム実行結果確認
※プログラムは一番下
###取り込むエクセル（sample.xlsx）
![キャプチャ.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/350277/dc1c4b87-fdc6-3315-e962-f08d0e73f43d.jpeg)

###出力ファイル（sample2.xlsx）
![キャプチャ.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/350277/4e56937f-222d-b423-a883-eb7ad28055a3.jpeg)

#プログラム
```python:file_edit.py
import pathlib
import openpyxl
from openpyxl.styles import Alignment, PatternFill, Font, Border, Side
import csv

#エクセルファイルを取得
wb = openpyxl.load_workbook("./data/sample.xlsx")

#sheet「名：Sheet1」を取得
ws = wb["Sheet1"]

#セルA1のデータを出力　※パターン１
print(ws["A1"].value)  #A1セルを指定して取得

#セルA1のデータを出力　※パターン２
row1 = ws[1]           #sheet「名：Sheet1」の1行目を取得
print(row1[0].value)   #1行目の1列目を取得⇒結果、A1のセル

#全データを出力
print("全データ>")
for row in ws.rows:
	for cell in row:
	    print(cell.value)

#セルA1のデータを書き換え
ws["A1"].value = "★A1です"

#セルA1のフォント変更（ゴシック、12サイズ、太、青）
font_header = Font(name="ゴシック", size=12,bold=True,color="0000FF")
ws["A1"].font = font_header

#セルA1塗りつぶし（灰色）
ws["A1"].fill = PatternFill(patternType="solid", fgColor="808080")

#複数セルA5～D6の塗りつぶし（緑色）
for rows in ws["A5":"D6"]:
    for cell in rows:
        cell.fill = PatternFill(patternType="solid", fgColor="99FFCC")

#メモ
#条件で色を変える（CellIsRule / conditional_formatting.add）
#カラースケール（ColorScaleRule / conditional_formatting.add）

#セルA1の値位置（中央寄せ、下）
ws["A1"].alignment = Alignment(horizontal="center", vertical="bottom")

#A列の書式変更（列幅）
ws.column_dimensions["A"].width= 30

#セルB2のフォーマット変更（ 3桁カンマ区切り）
ws["B2"].number_format = "#,##0"![キャプチャ.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/350277/64e2c4b3-8faa-fd1e-4dac-0054fffa42a7.jpeg)


#セルB2の枠を設定（細い、黒）
side = Side(style="thin", color="000000")
border = Border(left=side,right=side,top=side,bottom=side)
ws["B2"].border = border

#セルA2,A3のセル結合
ws.merge_cells("A2:A3")

#読み込んだエクセルを別名で保存
#※上書きの場合は読み込みファイルパスを指定
wb.save("./data/sample2.xlsx")
```

#まとめ
どうでしょうか。前回から比べると、仕事でつかえる形になってきている気がします。
また、次回はグラフ・ＰＤＦを試したいなぁと思っています。

以上です(*'▽')
GitHub ActionsでLaravelアプリを本番環境に自動デプロイする 〜Docker準備編〜

Laravelの本番デプロイ手順って複雑じゃないですか？
というわけでGitHub Actionsで自動デプロイしてみます。

今回は、まず必要になるDockerについてです。

# なぜDockerが必要なの？

GitHub Actionsの中で任意バージョンのphpやcomposer、npmコマンドなどを実行するために必要になります。
ローカルでの開発や、コンテナでの本番運用にも転用可能なので、使えるようにしておきましょう。

Docker環境既にあるぜ！って人やLaradockなどのDockerHubにあるImageを使う人には今回の記事は必要ありません。
次回作にご期待ください。


## Dockerfileを作る

- php
- composer
- nodejs

の3つを使えるImageを作成します。

以下ではamazonlinux2とphp-fpm環境を例示していますが、上の3つが使えればphpイメージベースなど、何でも良いです。バージョンも適宜読み替えてください。

```Dockerfile
FROM amazonlinux:latest

RUN amazon-linux-extras enable php7.4 epel

RUN yum install -y \
    epel-release \
    https://rpm.nodesource.com/pub_12.x/el/7/x86_64/nodesource-release-el7-1.noarch.rpm \
  && \
  yum install -y \
    composer \
    libaio \
    nodejs \
    php \
    php-fpm \
    php-gd \
    php-mbstring \
    php-redis \
    php-xml \
    php-xmlrpc \
    unzip \
  && \
  yum clean all

# 以下の設定でconf書き換え
# user = root
# group = root
# listen = 9000
COPY www.conf /etc/php-fpm.d/www.conf

WORKDIR /var/www/app

STOPSIGNAL SIGQUIT

EXPOSE 9000
CMD ["php-fpm", "-F", "--allow-to-run-as-root"]
```

## Docker imageをbuildしてGitHub Packagesにpushする

[Configuring Docker for use with GitHub Packages](https://help.github.com/ja/packages/using-github-packages-with-your-projects-ecosystem/configuring-docker-for-use-with-github-packages) も参照してください

```bash
# イメージのビルド
docker build . -t docker.pkg.github.com/OWNER/REPOSITORY/IMAGE_NAME:VERSION

# Github自アカウントの個人トークンでGithub Packagesの認証
cat ~/TOKEN.txt | docker login docker.pkg.github.com -u USERNAME --password-stdin

# Github PackagesにImageをpush
docker push docker.pkg.github.com/OWNER/REPOSITORY/IMAGE_NAME:VERSION
```

REPOSITORYはどこでも構いませんが、Github Actionsで使うならActionsを実行するrepoにpushするとworkflow内での認証が要らなくなるのでおすすめです。


## docker-compose.ymlを作る

```
version: "3.7"
services:
  app:
    image: docker.pkg.github.com/OWNER/REPOSITORY/IMAGE_NAME:VERSION
    ports:
      - "9000:9000"
    volumes:
      - .:/var/www/app
```

## php, composer, nodejs, npmが動くかテスト

```
docker-compose run app php -v
docker-compose run app composer -v
docker-compose run app node -v
docker-compose run app npm -v
```

これでLaravelをDockerで動かす準備ができました。

次回はこのdocker-composeを使ってGithub Actionsのワークフローを作成したいと思います。
C#の他言語と比較して優位な点不利な点まとめ

###注意###
これは掲載者の主観であります。
場面によってはメリットとなる場合もあります
#C#についてメリット、デメリット#
私はC#をおすすめしています
理由としては以下のメリットがあります
###メリット###
- Microsoftが開発しているためWindowsとの相性がいい
- オブジェクト指向プログラミングができる
- 最新の技術が早く取り入られる
- GUIアプリケーションの開発が簡単にできる
- 人気が高いため情報が多い
- Unityに対応しているためゲーム開発が可能
- VisualStudioといった強力なIDEがある
- マルチプラットフォームに対応している
- これから開発が進められていく
- 実行速度が早い
- .NET Frameworkがある環境であればどこでもコンパイルできる

###デメリット###

- 開発環境の容量が多く低スペックPCにはきつい
- AIには弱い
- 基本的にはハードウェアに干渉できない
- OS開発には使えない
- Linuxでは開発環境を整えにくい
- 構文が長くなってしまう

このようにC#はWindowsで開発実行する際はかなり良い言語です

#C#のプラットフォームについて#
C#のプラットフォームについては.NET Framework、.NET Core Mono
Xamarinが動く環境ではすべての環境で動きます
そのため以下の環境で動きます

- Windows7以降(.NET Framework)
- Linux (.NET Core、Mono)
- Mac (.NET Core、Mono)
- Android (Xamarin)
- ios (Xamarin (Macが必要))

このようにC#はほぼすべてのプラットフォームに対応しております
しかしながら注意点があります。
.NET Frameworkが.NET系で今一番開発がすすんでいます。それに比べ.NET Coreはまだ実装されていない機能などがあります。

しかしながら、Microsoftが.NET Core ベースの**.NET5**を発表し2020年の11月にリリース予定です。これは**マルチプラットフォーム**に対応する予定なので今後期待できます。

#他言語との比較#
ここからは他言語との比較をしていきます。
##Java##
JavaはC#の兄弟言語といっても過言ではないほど構文が似ています。
###C#より優位な点###
- マルチプラットフォームを重視しておりすべてといってもいいくらい多くのプラットフォームに対応しています
- MinecraftのModが作れる
- 求人が多い

###C#より不利な点###
- GUIが遅い
- 機能の追加が遅い
- あまりゲーム開発には向かない
- C#に比べ開発環境を構築しにくい(勝手に思ってるだけ)

C#とJavaは似た言語なのでほとんど同じようになっています

##C/C++##

C#のもとになった一つの言語でもある言語
###C#より優位な点###
- ハードウェアを触ることができる

###C#より不利な点###
- 多くの機能が実装されているので無法地帯と化している(メリットとなることもある)
- 実行ファイルをそのまま別のプラットフォームで実行できない
- 構文が多くなってしまう

##Python##
最近はやりのスクリプト言語
###C#より優位な点###
- サードパーティー製のライブラリが豊富
- 構文が少なく実装できる
- ;が不要

###C#より不利な点###
- 実行速度が遅い
- インデントが強制される

#総評#
C#は今後成長していく言語です
初心者の方はC#を始めていれば基本的にすべてのことができます。
また、サードパーティ製のDLLも多く配布されておりTwitterBotやDiscordBotの開発等も行います。
またC#では、AIのDLLもPythonほどの数のライブラリではないですが、AIを開発することができます。

これから、リリースされる予定の.NET5に期待していきたいと思います
【PHP】Composer installしようとしたら、warning: The lock file is not up to date with the latest changes in composer.json.となった時の対処

デプロイを行う際に毎度composer installを行っていたんですが、

```
warning: The lock file is not up to date with the latest changes in composer.json.You may be getting outdated dependencies. Run update to update them.
```

このエラーがでていました。それも長いことでていました。今回はこのエラーの対処方法を書いておきます

## composer.jsonとcomposer.lockに違いがある


[composer install と composer updateの違い - Qiita](https://qiita.com/YusukeHigaki/items/47dd3ec23544225f7301)




そもそもcomposer.jsonとcomposer.lockの違いについて知らなかったのでそこから



`composer.lock：現在使用しているバンドルのバージョン等が管理されます。`
`composer.json：必要となるバンドルを記述します。`

`composer install：composer.lockに書かれている各ライブラリをインストールする。`
`composer update：composer.jsonをもとに各ファイルを最新版にアップデートする。composer.lockのアップデートも`






はい。またこの記事によると




[composer の「Warning: The lock file is not up to date ～」 - Qiita](https://qiita.com/ngyuki/items/eaec9adb0a946973e6cf)

`composer install` で次の警告が表示されたのでなんなのか調べました。

 ```
 Warning: The lock file is not up to date with the latest changes in ...
```



composer.lockにはcomposer.jsonのハッシュ値が記録されておりこれが少しでもずれているとこのエラーがでてくるようです。

## 解決


`composer update --lock`

このコマンドでcomposer.lockに記録されたハッシュ値のみを更新できるようなので
これを実行するとハッシュ値が合い、エラーが解消されました。
Java MethodUtilでプロパティアクセスの処理をリファクタリング

## Java MethodUtilについて
　Java　spring bootを業務で使っています。データクラスに書いたプロパティを簡単にget setできるのは魅力的ですが
どうも扱うプロパティが多い場合にgetter祭りになってしまいコードの見通しに支障をきたすことがありました。その上、型のダウンキャストもしていたため、この型の場合は。。。あの型の場合は。。。など、、、また大変なことになっていました。なのでMethodUtilを使ってリファクタリングを実施することにしました。

## 使い方
```AccessProperly.java
 @SuppressWarnings("unchecked") // 必要
 private static<T> T getProperty(Object o, String MethodName) {
   Method method = MethodUtils.getAccessibleMethod(o.getClass, methodName);
   if (method == null) {
     return null;
   }

   try {
     return(T) method.invoke(o);
   } catch (Exception e) {
     throw new RuntimeException(e);
   }
} 

// 用途
    String str = getProperty(object, "getPropertyName"); // object.GetPropertyNameと同じ 
   // データクラスのフィールドが取得できる
```
インスタンスごとに条件分岐がたくさん必要な場合に役に立ちます。それ以外にもメソッドへのアクセスをクラス内だけで簡潔させたい場合
とか用途はいろいろあります。オブジェクトのプロパティ取得メソッドの呼び出しは頻繁に行うのでより理解を深めていきたいと思います。
まだ、あまり詳しくないので（詳しい記事があまりない。。。）詳しい方いましたら記事にしていただければ幸い極みです笑
【Rails】transaction 入門

## Rails における transaction とは？
ざっくり言うと、**ActiveRecordの処理（DBのSQL操作であるcreate, update, deleteなど）を保護するもの**。

よくわからないかもしれないので、次のような入力されたパラメーターの商品を登録する際に、送料を商品の価格に応じて割引くような一連の処理があったとします。

```rb
ActiveRecord::Base.transaction do
  product = Product.create!(product_params) # product_params 内のデータをもとに product インスタンスを作成する
  shipping_fee = product.price / DISCOUNT_RATE # 価格を DISCOUNT_RATE で割ったものを送料 shipping_fee とする
  product.update!(shipping_fee: shipping_fee) # 商品インスタンスの送料を登録（更新）する
  end
end
```
ここでのActiveRecordの処理は2つ、

```rb
product = Product.create!(product_params)
```
```rb
product.update!(shipping_fee: shipping_fee)
```
ですね。

これらが、

```rb
ActiveRecord::Base.transaction do

end
```
で囲まれることで、この範囲内のActiverecordの処理は一連の処理として保護されます。

どういうことか？というと、例えば1つ目のActiveRecord処理であるproductインスタンスの作成（`create!`）は成功したとして、次の送料計算でもし`DISCOUNT_RATE`が`0`だった場合、0除算で`ZeroDivisionError`が発生します。

```rb
shipping_fee = product.price / DISCOUNT_RATE # DISCOUNT_RATE = 0 なので 0除算が発生する

ZeroDivisionError: divided by 0
```

このようにエラーが発生すると、直ちにロールバック処理が行れ、**transactionで囲まれた範囲内のActiveRecordの処理は全てもとの状態に戻ります**（処理前のcreateされていない状況）。
また、その次の`update!`の処理でエラーが発生した場合も同様で、その以前のActiveRecord処理である`create!`はもとの状態に戻ります。

この**全てもとに戻ってくれる**ということが非常に大事、つまり**transactionを使う意義**があるのです！

例えばお金のやり取りに関わる一連の支払処理があったとすると、**全ての処理が完璧でないと一連の処理としてOKではなく、どこか1つでも処理に誤りがあればその一連の処理はすべてダメ**という処理が必要な場合が多々あります。
そうでないと、例えばお金を渡す人、お金を受け取る人のどちらかが得する、損することなどになりかねず、サービスとしては致命的な設計となります。

では、なぜ？何を？トリガー（引き金）にロールバックが起こるのでしょうか？
察しが良い方は気づかれていると思いますが、エラー（例外）が発生したからです。
つまりこの**例外が発生すること**がtransactionでのロールバックが起こるトリガーになるのです！**←ここ、とても重要ですよ。**

以上を踏まえると、**transaction内で例外が発生する実装**でなければなりません。
次のセクションでは、例外を起こすために気をつける実装例を紹介いたしますので参考にしていただければと思います。

## 例外を発生させる実装
左側での記述では例外が発生しない（失敗しても`false`や`nil`を返すだけ）ので、**右側の記述へ変更**して下さい。

```rb
save => save!
create => create!
update => update!
destroy => destroy!
find_by => find_by!
```
それ以外に覚えておくものも書いておきます。

```rb
find # findはそのままエラーをはきます
```
MediaPipe の Android のサンプルは簡単に試せます

こんな感じで動かせるサンプルが割と簡単にできます。 

![output.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/506075/ce84f0f8-509b-867c-cf23-013c36811de6.gif)

# こちらの手順がとても参考になりました
[Google MediaPipeのサンプルアプリをビルドしてAndroidにインストールする手順](https://qiita.com/d_forest/items/1b40fba54d7d896acfe6)

# 補足
## 先にこっちをやっておくといいかも
Mac の人は [mediapipe hand trackingお試し](https://qiita.com/3attoC/items/b5bad7b2d54fa0bf013a) を参考に hello_world と Desktop 版を動かしておくと、どこまでできているか問題の切り分けができるかと思います。

* Xcode をダウンロードするのに時間がかかります
* エラーが出ることもあるかと思いますが、検索するとだいたい引っかかるのでなんとかなります

## 注意
MediaPipe の Android のハンドトラッキングはビルドに25分ほどかかりました・・・

### 前提
* MacBook Pro(15-inch, 2017)
* CPU 2.8 GHz Intel Core i7

### Elapsed time: 2568.961
![スクリーンショット 2020-05-04 11.03.10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/506075/b78cb565-e731-d44d-bacd-c664f9c1dd24.png)
Elixirでの三項演算子の書き方

# Elixirでの三項演算子の書き方

Elixirでは三項演算子が用意されていません。
色々書き方がありますが、個人的にはif/elseワンライナーを使うのがベターかと思います


### if/elseのワンライナー

if/elseのワンライナー。
Elixirのif/elseワンライナーのシンタックスはカンマ・コロンがごちゃごちゃしていてパット見たときの視認性はかなり悪いです。つまり、見づらいです。

```elixir
result = if 2 == 2, do: 'ok', else: 'ng'
# カンマ(,)と、コロン(:)の位置に注意です
```


### if/else

三項演算子というか、そのままif/else。複数行の処理や、ワンライナーが見にくいならこちらを。

```elixir
result =
  if 2 ==2 do
    'ok'
  else
    'ng'
  end
```

### unless/else

if/else・if/elseワンライナーと同じシンタックスなので省略です。


### case

caseで分岐。関数型の原理主義的な人はifを使わないでcaseだけで記述するイメージ。個人的には、条件式がboolならif/elseのほうが良い気がします。

```elixir
result = case 2 == 2 do
           true -> 'ok'
           _ -> 'ng'
         end
```

### ハックな書き方（個人的に非推奨）

TwitterからStackoverflowに流れてきた書き方を見つけました。
こなれた書き方ですが、読みにくいです。
なにより、returnする値がbool/nilだと三項演算子として機能しないケースもあり、この書き方はバグの温床になります。

```elixir
result = 2 == 2 && 'ok' || 'ng'
# => ok

result = 2 == 2 && nil || true 
# => nilではなくて、trueが返る
```

### まとめ

「三項演算子ってどうやって書くんだっけ？」を忘れてたのでまとめようとしてたら、ただただ条件分岐を網羅するだけの記事になってしまった。

Elixirの三項演算子ではif/elseワンライナーを使ってください。

## その他

if/elseの中では極力代入（束縛）しないほうがスマートになるはずです。

```elixir
# 良くない書き方
# 'result =' は外に出して上げたほうが良い
  if 2 ==2 do
   result = 'ok'
  else
   result = 'ng'
  end
```
## REF

- [Simulate ternary operator in Elixir - Stack Overflow](https://stackoverflow.com/questions/38029176/simulate-ternary-operator-in-elixir)
SwiftUIでList(TableView)を作る

##リスト(tableList)を作成する
![2020-05-04 11.39のイメージ.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/549093/2b1034cf-4fe8-89f2-70c9-c64920518455.jpeg)


```swift
import SwiftUI

var numberArray = ["いち","に","さん","よん","ご","ろく"]
struct ContentView: View {
    var body: some View {
        List(0..<numberArray.count) {i in
            VStack {
                HStack {
                    Text("\(i + 1)")
                    Text("\(numberArray[i])")
                }
                Text("aa\(i)")
                Text("ss")
            }
        }
    }
}

struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}
```

SwiftUIを使ってリストを作成します。
Text()などがこれまで書かれていたところに、List()を書きます。`VStock`を用いて鉛直方向に書き込んでいます。
セルの内容を水平方向に書くために`HStack`を用いています。
リストの高さは自動で変更されます。
Automation Anywhere A360 Bot間のアクションのコピーのやり方

GW中にリリースされた最新バージョンのA360(当時の名称：A2019)ですが、一部ユーザーが待望していたBot間でのアクションのコピーが可能になっています。
（今までできなかったの？という声もあると思いますが・・・ｗ）

#使い方
（コピー元のBot）と（貼り付け先のBot）を開きます。

**（コピー元のBot)**
矢印の個所を右クリックして「新しいタブで開く」で新しいタブを開いて、貼り付け先のBotを開く/作成すると良いでしょう。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/490870/ba0642d2-48dc-995f-34f3-2a7825120858.png)


**（貼り付け先のBot）**
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/490870/4896a5ea-2a32-de88-17c7-0ecba25aca75.png)

今回のバージョンから以下のボタンが追加されていることにお気づきでしょうか・・・？今からこれらを使ってコピペします。

**コピーボタン**
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/490870/6fec31fe-4c99-cf4c-9e92-fe001bf192fe.png)
**貼り付けボタン**
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/490870/69ba4de9-6992-4837-f64c-5d35eaf74760.png)


（コピー元のBot)でコピーしたい個所を選択し、コピーボタンを押します。 （Shift+クリックなどで選択）
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/490870/74d5a9ab-84fd-d452-efbf-8fc25b196183.png)

（貼り付け先のBot）を開き、貼り付けボタンを押すと、コピーした個所が貼り付けられます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/490870/bbd53418-0563-e775-a28a-faacc3cf1d4c.png)

というわけで、これだけですが、開発がとてもしやすくなる待望の機能が今回のバージョンアップで実装されました。
【jQuery】超簡単　ページごと　scss切り替え

## 目的
jQueryを使って、ページごとに装飾を変えます。

## 前提
jQueryを導入済

##実装例
イメージとしてこんな感じができます。
ホーム画面ではフッターのホームアイコンが緑になり
ユーザー一覧では、ユーザーズアイコンが緑になります。
https://gyazo.com/1209de9920840478ec974d0f4cd33632

##記述例

下記にjqueryの記述を書きます
ポイントは

    var loc = location.pathname;
でそのページのパスを取得することです。
あとはシンプルなif文でページによって、クラスを与えます。

```application.js
$(function(){
  var loc = location.pathname;
  if(loc == "/"){
    $("#HomeIcon").addClass("green")
  } else if (loc == "/users"){
    $("#UsersIcon").addClass("green")
  }

});
```

```stylesheet.css
.green{
        color: green;
      }
```

```index.html.erb
<footer class="Footer">

        <%= link_to  root_path , id: "HomeIcon"  do %>
          <i class="fas fa-home"></i>
        <% end %>

        <%= link_to  users_path , id: "UsersIcon"  do %>
          <i class="fas fa-users"></i>
        <% end %>

      </footer>
```

いかがでしょうか
簡単な理屈で装飾を加えることができるので、非常に便利です。

## 参考文献
https://try-m.co.jp/blog/web-create/2190/
【Java】この事象を説明できますかい

あなたのJava力を試してみてください。

以下のコードを見て下さい。
arrayListのすべての値に"D"を代入しようとしています。

```java:ExtentionForSample.java
ArrayList<String> arrayList = new ArrayList<>();
arrayList.add("A");
arrayList.add("B");
arrayList.add("C");
for(String str : arrayList) {
	str = "D";
	System.out.println(str);
}
System.out.println(arrayList);
```
##結果
```
D
D
D
[A, B, C]
```
#なぜこの結果になったのかを説明できるか。
##答え
ローカル変数の参照先を変更していただけだから。。。

##説明しよう
![ローカル変数代入.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/621352/1eecf3b7-8425-c764-0538-4f9523b9a0fa.png)


ローカル変数に新しい参照先を代入しているだけだった。
参照先の"A"に影響はない

##修正する
```java:ExtentionForSample.java
//中略
for(int i=0; i < arrayList.size(); i++) {
	arrayList.set(i, "D");
}
System.out.println(arrayList);
```
ArrayList.set(int index, E element)を使用する
###結果
```
[D, D, D]
```

##ちなみに

```java:ExtentionForSample.java
Map mapA = new HashMap<String,String>(){{put("1", "A");}};
Map mapB = new HashMap<String,String>(){{put("1", "B");}};
Map mapC = new HashMap<String,String>(){{put("1", "C");}};
arrayListMap.add(mapA);
arrayListMap.add(mapB);
arrayListMap.add(mapC);
for(Map map:arrayListMap) {
	map.put("2", "D");
}
System.out.println(arrayListMap);
```
###結果
```
[{1=A, 2=D}, {1=B, 2=D}, {1=C, 2=D}]
```
![ローカル変数代入_map.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/621352/1ae5806f-512d-f59a-bb2c-05b343310ea3.png)



###まとめ
ローカル変数に代入した参照先に対して、データ操作すると参照先に反映される。
MySQLのバックアップ種類と方法

MySQLではどのようなバックアップ方法があるのか調べてみました。

# バックアップの種類
まずMySQLには「物理バックアップ」と「論理バックアップ」という概念があります。

|種類|説明|
|:---:|:---:|
|物理バックアップ|データベースの内容を保存しているディレクトリやファイル自体をコピーする事でバックアップ|
|論理バックアップ|MySQLサーバに対してクエリをかけた結果をエクスポートする事でバックアップ|

それぞれ特長をみていきましょう。

## 物理バックアップ
メリット

- **論理バックアップに比べて早い**(リストア含む)
    - バイナリファイルをただコピーするだけのため(データの変換が行われない)  
- データベースだけではなく、**関連ファイルもバックアップ**する事ができる
    - 設定ファイルやログファイル等
 
デメリット

- 異なるデータベースやハードへの復元ができない
- バージョンが異なると復元が困難な時がある**(互換性がない)**
- **MEMORYテーブルのバックアップはできない**(Enterprise除く)
    - メモリーにデータが存在しており、物理的に存在しない
- **MySQLが停止中のみ実施可能**
    - 実行中に行う場合は、更新が走らないようにするためのロック制御を行う必要がある
    - Enterpriseだと自動的にロック制御を行ってくれる

## 論理バックアップ
メリット

- **データの柔軟性が高い**(実体はただのテキストデータであるため編集が可能)
- **バックアップデータの粒度を細かく指定できる**
    - サーバレベル or データベース or テーブル 
- バックアップデータはどこでも利用が可能**(ハード依存がない)**
- **MySQLサーバが起動中に実施可能**
- 全てのストレージエンジンでバックアップ可能

デメリット

- **物理バックアップに比べて遅い(リストア含む)**
 - バイナリ -> テキスト への変換が行われる
 - ファイルへの書き出し
- 物理バックアップに比べてファイルサイズが大きくなる
- データベースの関連ファイルはバックアップされない

# バックアップ方法
データをバックアップするたの方法もいくつか存在しています。(種類に該当するかもしれませんが。。。。)

- オンライン/オフラインバックアップ
- ローカル/リモートバックアップ
- スナップショットバックアップ
- 完全/増分バックアップ
- レプリケーションスレーブバックアップ
- (スナップショットバックアップ)

それぞれ簡単にですがまとめたいと思います。

## オンライン/オフライン
MySQLサーバの状態が起動中(オンライン)、もしくは停止中(オフライン)なのかという違いです。
物理/論理バックアップにも記載しましたが、論理バックアップはオンラインで対応可能です。物理バックアップはロック制御をしない限りオフライン対応になります。

## ローカル/リモート
**バックアップの取得元**がMySQLが起動しているサーバ(ローカル)、もしくは別サーバ(リモート)なのかという違いです。

## 完全/増分
**特定次点のMySQLサーバ**において全てのデータが含まれている(完全)、もしくは特定期間(ある点からある点)に行われたデータという違いです。増分バックアップにはMySQLサーバでバイナリログを有効化する必要があります。

## レプリケーションスレーブ
マスター側ではなくスレーブ側でバックアップをする事もできます。

## スナップショット
スナップショットとは、ある次点でのファイルシステムの論理コピー(論理バックアップではない)です。MySQLではこのバックアップからのバックアップ機能は存在していないので、LVM等を用いて行う必要があります。

# まとめ
物理と論理だとどちらが使われているのか気になりました。大規模であればあるほど、停止させる事ができないので論理になるかなーと思ったり、時間短縮のためにメンテナンスとかを設けて定期的に停止して物理バックアップもしてそうだなーと思ったりもする。どっちでしょうかね？

。。。。。うん。。。両方してそうですね。。(どなたか教えてください。。)
GWにAPIを活用して天気予報のLINE Notify通知をつくった話

GWに久しぶりにプログラミングに触れようと、[ProtoOut Studio](https://protoout.studio/)の主催する講座に参加している。

初日の5/2につくったものは、「APIを活用した天気予報のLINE Notify通知」。一定の間隔で、取得したlivedoorの天気予報情報を、自分のLINEアカウントに通知するというもの。

復習として、以下に幾つかポイントをまとめておく。


####APIで取得したデータ構造を理解する
例えば、今回はlivedoorが公開している天気情報のデータを、[APIを経由して取得](http://weather.livedoor.com/weather_hacks/webservice)した。これらのデータを上手く活用するためには、

　・データの階層構造
　・オブジェクト、配列の理解

が欠かせない。逆に言うと取得してきたデータが、どのような性質で、どこに配置されているのかが理解できれば、それらを通して無限の組み合わせでデータ活用が可能になる。

```
response.data.pinpointLocations[0].name
```
上記の.data以降は、データの住所を示すようなものであり、ドットを記述することで、入れ子のように階層をさげていくことができる。[ ]は配列で、何番目に格納されているデータかを示す。

####Cron式によるタスクのスケジューリング
Cron式というのは、タスクのスケジューラーの記述方式とのこと。特定の時間や曜日、トリガーを元にして、タスクを実行する予約を行う。用途としては、例えば以下のようなもの。

|処理内容|記述|
|:--|:--|
|月曜-金曜でAM7:00にタスクを起動する|0 00 7 ? **  MON-FRI|
|5分間隔で、同じ処理を実行する|*/5 * * * *|


記述が独特で、しばらく慣れる必要がありそう。また時間指定する際には、日本時間ではなくUTCタイムゾーンに準拠しているので、基本的に-9時間の調整を行って記述をする。こうしたスケジューラーは、幅広い用途で汎用的に使えそうなので、ぜひマスターしていきたいところ。

__＜参考にした記事＞__
[Cron式へのガイド](https://www.codeflow.site/ja/article/cron-expressions)

####もう少し学びを深めたいところ
・Axiosを利用したのだが、利用前、利用後のメリット/デメリットがいまいち実感できていない
・APIのドキュメントの読み方のポイントを抑えたい。英語&情報量多いので整理できてない
・Cron式の時間設定の記述方法が応用効かないので活用事例を増やしたい
BigDecimalの扱いについて（反省を込めて）

# Java BigDecimalについて
　開発業務でjavaを使う場面は多いと思います。計算ロジックを組む場合はBigDecimalを使うこともあるかと思います。
ふと、通常の整数とは違った型なので戸惑うこともあり記事に残すことにしました。

## BigDecimalとは
　https://docs.oracle.com/javase/jp/8/docs/api/java/math/BigDecimal.html　> oracle.docsより
いや、数学的なこと言われてもあんまりよくわからん。。。なので、つまりは・・・
floatやdoubleでは誤差が生じてしまう計算の場合に、意図しない結果を得てしまうことがあります。
例えば

```double.java
 double result = 10d / 6d;
 System.out.println(result)
 // 出力　1.6666666666666666666666666666666666666666
```
みたいな感じです。
ご存じの型もいるかと思いますが、「銀行丸め」の計算をしたい場合は上記の例では不規則過ぎて困ってしまいます。
そこでBigDecimalが役に立ちます。いわゆる勘定系の計算によく使われます。

※銀行丸め
　N桁で丸める場合
  第N桁が偶数なら 5以下は切り捨て。それ以外は切り上げ。
  第N桁が奇数なら 5未満は切り捨て。それ以外は切り上げ。　というものです。

BigDecimalは通常の数の計算とは違い以下のように計算します。

```BigDecimalCalc.java
// BigDecimal型の1000をint型の100で割る場合
   BigDecimal bigNum = BigDecimal.valueOf(1000);
   BigDecimal result = bigNum.divide(BigDecimal.valueOf(100), 2, RoundingMode.DOWN); 
   System.out.println(result);

```

divideの用に特殊なメソッドを使います。通常の/は使えません。
詳しくはoracle.docsを参照ください。

## 0との比較をする場合
　条件分岐などでBigDecimalの0はどう扱うのか。これも慣れていないとハマります。私も初心者なのでもちろんハマりました。

```ZeroCompare.java
 if(比較する値.compareTo(BigDecimal.ZERO) == 0) {
  // ・・・
 }

```
のようになります。つまり0と比べて差がないから0！という比較になります。
ちなみに0以上や0以下の場合は

```Compare.java
ZeroCompare.java
 if(比較する値.compareTo(BigDecimal.ZERO) > 0) {
  // ・・・
 } 
```
のようにします。

## まとめ
　BigDecimalはプリミティブ型とは使い方が異なる。ということを意識しておくことが必要です。特に私のようなjava初心者は実際の開発業務でうっかり正確な計算をしないといけないのにfloatやdoubleを使ってやっちまったり、BigDecimalを間違った使い方にしてコンパイルエラーを起こしまくったりするのはなんともやってはいけないことです。普段はあんまり気にしないかもしれませんが、仕事の場合はよく心がけて開発する計算ロジックの目的や求める精度などはしっかりとヒアリングしてから開発に当たりたいと思います【反省】
terminalからsshでconohaVPSに接続しようとしたら「Permission denied」された

# エラーコード
```terminal
root@123.45.67.8:  (publickey,gssapi-keyex,gssapi-with-mic).
```

# 参考にしようとしたがうまくいかなかった記事たち


https://note.mokuzine.net/ssh-permission-denied/
https://qiita.com/youcune/items/2f427979403771f2e03a
https://hacknote.jp/archives/2225/

# 結論から言うと

下記の公式のガイドマップを参考にして設定をしたらうまくいきました

https://support.conoha.jp/v/vps_ssh/

# つまづいた部分を記載する

### ①

上記の記事には

`vi`で`/etc/ssh/sshd_config`という設定ファイルを編集し、`PasswordAuthentication`の値を`yes`に、`ChallengeResponseAuthentication`の値を`yes`に変更して保存します。

と書いてあるが、これを「Macのファイルだと勘違いしていた」

=> conohaVPS側のコンソールからrootユーザーでログイン。そちらにて設定を変更した

### ②

conohaのコンソールでviを起動したはいいが、なぜかMacのように`:wq`で終了できない

=> 原因はよくわからないが、上にある「コンソール」ボタんから「シリアル」を選択。ログインして、そちらから`vi`を入力したらできた

# つまり

公式をまず読んで、まず試す。それが一番大事。
【Vue.js】イベントのバブリングを防ぐ方法

## はじめに
この記事ではVue.jsでイベントのバブリングを防ぐ方法についてまとめます。

## 結論
イベント修飾子である`.stop`を使用するとイベントのバブリングを防ぐことができます。

## そもそもイベントのバブリングって何？
**イベントが親要素に順に伝播していくこと**を**イベントのバブリング**と言います。
以下のようなコードで実験してみましょう。
リストの項目(`li`タグ)をクリックすると太字に、ゴミ箱のマーク(`i`タグ)をクリックすると打ち消し線が表示されるコードです。

```html
<div id="app">
  <ul>
    <li v-on:click="select(fruit);" v-for="fruit in fruits" :key="fruit.id">
      <span v-bind:style="{
        fontWeight: (fruit.selected ? 'bold' : 'normal'),
        textDecoration: (fruit.removed ? 'line-through' : 'none')
      }">{{ fruit.name }}</span>
      <i class="fas fa-trash" style="margin-top: 4px;" v-on:click="remove(fruit);"></i>
    </li>
  </ul>
</div>
<script>
  var vm = new Vue({
    el: '#app',
    data: {
      fruits: [
        {id: 1, name: 'リンゴ', selected: false, removed: false},
        {id: 2, name: 'バナナ', selected: false, removed: false},
        {id: 3, name: 'ブドウ', selected: false, removed: false}
      ],
    },
    methods: {
      select: function(fruit) {
        fruit.selected = !fruit.selected;
        console.log("Called select method.");
      },
      remove: function(fruit) {
        fruit.removed = !fruit.removed;
        console.log("Called remove method.");
      }
    }
  });
</script>
```
**実際の画面**
![スクリーンショット 2020-05-04 10.35.50.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/68663/8091d8f2-683b-efea-c950-596a4696ffa6.png)

ここで、ゴミ箱のマーク(`i`タグ)をクリックした場合にどうなるか確認してみます。

**実行結果**
![スクリーンショット 2020-05-04 10.46.38.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/68663/44df7140-4926-3569-9eb9-03a80f0ed9fb.png)

```:コンソール
Called remove method.
Called select method.
```

`i`タグのクリックイベントの後に、`li`タグのクリックイベントも呼ばれていることが分かると思います。
このように**イベントが親要素に順に伝播すること**を**イベントのバブリング**と呼びます。

## Vue.jsでイベントのバブリングを防ぐには？
打ち消し線は表示したいけど、太文字にはしたくないということもあるでしょう。
そんなときは、イベントのバブリングを防ぐ必要があります。
イベントのバブリングをVue.jsで防ぐには、`.stop`というイベント修飾子を使用します。

```html
<i class="fas fa-trash" style="margin-top: 4px;" v-on:click.stop="remove(fruit);"></i>
```

この状態で先ほどと同じように、ゴミ箱のマーク(`i`タグ)をクリックした場合にどうなるか確認してみます。

**実行結果**
![スクリーンショット 2020-05-04 11.13.02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/68663/8b832b3b-d074-85e9-364c-4a596251edcd.png)

```:コンソール
Called remove method.
```

`i`タグのクリックイベントだけが呼ばれ、太文字にはならず、打ち消し線だけ表示されるようになりました。
このように`.stop`を使用することで、イベントのバブリングを防ぐことができます。

## まとめ
- **イベントが親要素に順に伝播していくことをイベントのバブリングという**
- **Vue.jsでイベントのバブリングを防ぐにはイベント修飾子の`.stop`を使用する**

イベントのバブリングという言葉自体知らなかったので、勉強になりました。

それではまた。
TomoProg

## 参考
[イベントのバブリングとキャプチャリング](
https://developer.mozilla.org/ja/docs/Learn/JavaScript/Building_blocks/Events#Event_bubbling_and_capture)
[Vue.js イベント修飾子](https://jp.vuejs.org/v2/guide/events.html#%E3%82%A4%E3%83%99%E3%83%B3%E3%83%88%E4%BF%AE%E9%A3%BE%E5%AD%90)
Djangoのrenderは何をするのか

#環境
Python3.6.2
Django3.0.5

#結論
Function-based viewsにおいて、templateにcontextの値を渡してHTMLを完成させる。レンダリングの一種。

#そもそもレンダリングとは
データ記述言語やデータ構造で記述された抽象的で高次の情報から、コンピュータのプログラムを用いて画像・映像・音声などを生成することをいう。
（出典：Wikipedia ）

#Djangoでのrender（レンダリング）とは
Viewで定義（あるいはmodelから取得）した情報から、renderを用いて（templateにcontext(情報)を渡すことで）HTMLを生成すること。

※Djangoではrender以外もレンダリングのメソッドはありますが、今回は一番ベタで学習しやすかったものにしています。

#renderメソッド
renderメソッドは、request、template_name、contextの主に3つの引数を取ります。

```python:view.py
def test(request):
    context = {{ 'info' :'これを渡す' }}
    render(request, template_name = test.html, context)
```
###request
セッション情報、呼び出しのメソッド（GET、POST）の情報などで構成されています。外部からこの関数が呼び出された（HttpRequest）場合、その呼び出し情報がはいっています。呼び出すView内の関数を指定する場所はurls.pyです。

###template_name
context（今回はinfo）を渡す先(htmlファイル)をtemplateフォルダから指定します。

###context
渡したい情報を指定します。辞書であればcontextという名前ではなくても問題ありません。

#おわりに
理解が浅い部分もありますので、間違いや＋αのことがあればご教授お願い致します。
この記事が参考になった・良かったよと思った方はLGMTを押していただけるとすごくうれしいです。
メニューの開閉を画面全体で行う

## 目次

- [完成形のDemo](#完成形のDemo)
- [解説（図解）](#解説（図解）)
- [リポジトリ](リポジトリ)
- [あとがき](あとがき)

## 完成形のDemo

|Before|After|
|------|-----|
|<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/447754/94ffc93d-1966-3c83-159c-a47880ea7ad6.gif" height="280" width="100%" />|<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/447754/05f3ce5b-7dbe-f326-6688-b15aae97d669.gif" height="280" width="100%" />|
|https://github.com/taiki-fw/Qiita/tree/2ed5117ff03b09ea62b020bf21be5797995fc10d|https://github.com/taiki-fw/Qiita/tree/e9456566515908ffca737ce3c18ee3ab9502684e|


## 解説（図解）

サブメニューを表示する際に、ベース（メニュー）階層とサブメニュー階層の間に画面と同じ大きさを持つオブジェクト（divなど）を挿入し、クリックイベント時にサブメニューをクローズする機能を設定して上げる事で実現する事が出来ます。

手順は以下の通りです。
1. メニューボタンクリック時に、サブメニューの表示とベース（メニュー）階層とサブメニュー階層の間に画面と同じ大きさを持つオブジェクト（divなど）を挿入
2. 1で対象のオブジェクトをクリックした時に、サブメニューを非表示・挿入したオブジェクトの削除を行う

|Before|After|
|------|-----|
|<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/447754/01132254-1551-1f23-0f83-41389e9b063e.png" width="100%">|<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/447754/af9621b1-4660-d9d4-b5d4-65003857dfb7.png" width="100%">|

## リポジトリ

https://github.com/taiki-fw/Qiita/tree/master/sub-menu-toggle

## あとがき

この記事について間違いの箇所、また他の実装方法などありましたら、コメントにてお教え頂けたら幸いですm(_ _)m
scala Function[-S, +T] 共変・反変

共変・反変の理解ができていなかったので、scalaの標準ライブラリであるFunction1で納得したので、メモ。

そもそもFunction1とは

A => Bという関数を書いた時に、Fucntion1[A, B]と展開する。

定義は

```scala

trait Function1[-S, +T] {
  def apply(x: S): T
}
```

以下、具体例を交えて、Function1[-S, +T]を解説

```scala
class Publication(val title: String, val number: Int)
class Book(title: String, number: Int) extends Publication(title, number)

object Library {
  val books: Set[Book] = Set(
    new Book("scala", 1),
    new Book("java", 2),
    new Book("ruby", 3)
  )
  // 関数トレイトは次の定義である。
  // Function1[-S, +T]
  // 以下の関数、printBookListでいうと、-SはBook, +TはAnyである。
  // Bookを受け取って、Anyを返す
  // -Sであるパラメータは、反変なので、Sのスパークラスも受け取る
  // -Tである戻り値は、共変なので、Tのサブクラスも受け取る
  def printBookList(info: Book => Any) = {
    for(book <- books) println(info(book))
  }
}

// getTitleをみると、Publicationを引数として受け取って、戻り値としてStringを返している。
// 上記のような関数を、printBookListに渡している。

// printBookList関数の戻り値はAnyであり、+Tなので、getTitile(String), getNumber(Int)のどちらも引数に取れる
def getTitle(p: Publication): String = p.title
def getNumber(p: Publication): Int = p.number
Library.printBookList(getTitle)
Library.printBookList(getNumber)


```


参照
[コップ本](https://amzn.to/3dbDJcv)
CentOS 7にGit2をインストール

# なぜGit2

普段[Visual Studio Code](https://code.visualstudio.com/) [Remote - SSH](https://code.visualstudio.com/docs/remote/ssh)を使って、CentOS内のファイルを編集します。 
`yum install git`コマンドでgitをインストールし、VSCodeから接続すると、下記のような警告が表示されます。
<img width="781" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/193995/3a82f2e3-3493-6e51-f323-52fb290aa75f.png">

これを解決するのは、Git２をインストールします。

# インストールコマンド

```bash
sudo -E yum -y remove git
sudo -E yum -y install https://centos7.iuscommunity.org/ius-release.rpm
sudo -E yum -y install git2u yum-utils
sudo -E yum-config-manager --disable ius
```

# バージョン確認

```bash
[user@okcoder-k8s-m1 ~]$ git --version
git version 2.16.6
```

# 参考資料

- [CentOS7 Git2系をyumからインストールする。](https://qiita.com/ucan-lab/items/568db1c68dab9d62169c)
- [How To Install Git v2 on CentOS 7](https://medium.com/better-programming/install-git-v2-on-centos-7-49448deede19)
【2020からPythonを学んでも遅くない】第３回 Python言語ベーシック（１）

``` python
learning_times = 2
# 勉強回数によって判定
if learning_times > 0:
    print("おめでとう、あなたのPythonの旅がもう始まりました！")
```

## Pythonの誕生
**Python**(パイソン)が誕生したのは1990年。
オランダのグイド・ヴァンロッサム氏(Guido van Rossum)は教育用言語『ABC』の開発プロジェクトに携わった後、**Python**を開発されました。
ただその**Python**(パイソン)は、1989年12月に「クリスマスの暇つぶし」として開発がスタートしました。現代における超主要プログラミング言語は、実に意外なカタチで開発がスタートしたのです。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/605091/28b244b1-6df1-3ef5-148a-9d062e85a164.png)

## Pythonの特徴
**Python**は汎用の高水準言語で、下記の特徴がある。

- 文法単純化
- 少ないコード行数で書ける
- コードの可読性が高く、読みやすく、また書きやすい
- インターネット上から無料で入手できる
- 本体部分は必要最小限で、標準ライブラリやサードパーティ製のライブラリ、関数など、さまざまな領域に特化した豊富で大規模なツール群が用意されている
- 多くのハードウェアとOS (プラットフォーム) に対応
- オブジェクト指向、命令型、手続き型、関数型などの形式でプログラムを書くことができる
- 動的型付け言語であり、参照カウントベースの自動メモリ管理（ガベージコレクタ）を持つ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/605091/170c4e2b-540f-5786-435b-568188e61826.png)

## Pythonのバージョン
Pythonの主なバージョンは2.xと3.xがある。2.xは最近もうサポート期限きれ、現在使うPython基本は3.xとなる。

### 2.xのサポート期限
| バージョン | リリース日 | サポート期限 |
|--:|:--|:--|
| 2.0 | 2000年10月16日 |  |
| 2.1 | 2001年4月15日 |  |
| 2.2 | 2001年12月21日 |  |
| 2.3 | 2003年7月29日 |  |
| 2.4 | 2004年11月30日 |  |
| 2.5 | 2006年9月19日 |  |
| 2.6 | 2008年10月1日 | 2013年10月29日 |
| 2.7 | 2010年7月4日 | 2020年1月1日 |

### 3.xのサポート期限
| バージョン | リリース日 | サポート期限 |
|--:|:--|:--|
| 3.0 | 2008年12月3日 | 2009年1月13日 |
| 3.1 | 2009年6月27日 | 2012年4月9日 |
| 3.2 | 2011年2月20日 | 2016年2月20日 |
| 3.3 | 2012年9月29日 | 2017年9月29日 |
| 3.4 | 2014年3月16日 | 2019年3月18日 |
| 3.5 | 2015年9月13日 | 2020年9月 |
| 3.6 | 2016年12月23日 | 2021年12月 |
| 3.7 | 2018年6月27日 | 2023年6月 |
| 3.8 | 2019年10月14日 | 2024年10月 |

### Python 2.x と 3.xの文法差異
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/605091/5c5aa1d0-b300-4d42-7241-68e70d8cd8b9.png)

## 文法のハイライト
コードの可読性を上げるために、**Python**キーワードと文法の各部分に対して違う色で表示するのは文法のハイライトである。

``` python
# -*- coding:utf-8 -*-

# １行のコメント

"""
三つダブルクォーテーションの複数行コメント。
"""

'''
三つシングルクォーテーションの複数行コメント。
'''


class Animal:
    """これは動物クラスです。
    """

    # 動物名
    name = ''
    # 足の数
    leg_num = 0

    def __init__(self, name, leg_num):
        self.name = name
        self.leg_num = leg_num

    def tell_name(self):
        """動物名の情報を出力する。
        """

        print("この動物の名称は：{name}".format(name=self.name))

    def tell_leg_num(self):
        """足数の情報を出力する。
        """

        print("この動物の足の数は：{leg_num}".format(leg_num=self.leg_num))
```

下記はVS Codeで書いた効果である。(説明付き)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/605091/459442ed-b5ba-b6ca-05b2-1d1444003023.png)
Ready nas のTransmission NT の保存先をしっかり指定する。

![ready nas.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/311381/b947edb7-4433-ed86-acb2-f19e2c1ef2da.png)

#はじめに
　ReadyNASのアプリであるTransmissionNTを使ってlinuxのイメージファイルをダウンロードした際にデフォルトのDownload to "/apps/nastools-transmission"にアクセス出来なかったので
Download to　の設定方法を備忘録として記載する。
#対処方法
　![nas2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/311381/e1c9179a-7b63-b5ae-cade-8ce7abead1eb.png)
　・ホームフォルダと同一場所に"download"フォルダを作成
　・TransmissionNTのDownload to のパスを"/ボリューム名/共有フォルダ名"に変更
　※Downloadフォルダのパーミッションは、Anonymous のみ
![boryu-mu.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/311381/02dc00b5-a0a8-9d64-5858-ff7d4b75fb57.png)
ボリューム名は、管理画面のドライブマーク上の文字(図では赤枠)
#参考元
Transmission NT のフォルダについて
　https://community.netgear.com/t5/ReadyNAS-%E3%81%8A%E7%9F%A5%E3%82%89%E3%81%9B/Transmission-NT-%E3%81%AE%E3%83%95%E3%82%A9%E3%83%AB%E3%83%80%E3%81%AB%E3%81%A4%E3%81%84%E3%81%A6/td-p/1219277