OmniAICreator/Qiita-1.07M huggingface dataset:
Fatal error: read tcp 127.0.0.1:xxxx->127.0.0.1:yyyy: read: connection reset by peer

#事象
サーバ・クライアント間でTCP/IPコネクションを確立している状態でクラアントからサーバにデータを送信すると以下のエラーが出てきた。

```
connection reset by peer 
``` 

#原因
サーバからクライアントにRST(Reset TCP)パケットが送信されてコネクションがブチ切られている。
電話に例えると、発信者(クライアント)から受信者(サーバ)に電話した時に相手側が即効電話を切っていると同じ。

RSTとは

>When an unexpected TCP packet arrives at a host, that host usually responds by sending a reset packet back on the same connection. A reset packet is simply one with no payload and with the RST bit set in the TCP header flags. 
 

①データ送信(クライアント→サーバ)
![スクリーンショット 2021-04-17 0.50.13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/317296/3e4d97c4-c5b0-a066-1178-505a7689fa48.png)

②RSTパケット送信(サーバ→クライアント)
![スクリーンショット 2021-04-17 0.50.19.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/317296/98a9678b-eef0-c221-9259-21568a02ca3e.png)


③コネクション終了
![スクリーンショット 2021-04-17 0.50.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/317296/e9497a40-6b98-bf17-f8ce-4cc5815fe581.png)


[Stack Over Flow](https://stackoverflow.com/questions/1434451/what-does-connection-reset-by-peer-mean)での説明がわかりやすい。
GAEにデプロイしていたプロジェクトが消えてた。

Google Cloud Shell Editor のUIが、去年（2020年）の9月10月くらいにアクセスした時と、今（2021年2月）とでだいぶ違っていた。

作成したプロジェクトが見えなくなってしまったし、でも、サーバーはちゃんと動いているし。
どこかにあるはずと思って、探したらこんなところにあった。

まず、下記画像のように「Add Folder to Workspace...」をクリックします。
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/640981/61838e70-7f6d-e5c1-1b31-dd6633a6f181.png" width=500px />

次に、表示された検索ウィンドウの上のプルダウンから「/home」をクリック。
「home > info > cloudshell_open > nodejs-docs-sample」
この中にありました。
AWS Glue とは

## 勉強前イメージ

glueってのり？
何かと何かを繋げる的な・・・？

## 調査

### AWS Glue とは

データの分類、クリーニング、加工を行う、
フルマネージドなETL(Extract(抽出)/Transform(変換)/Load(ロード))サービスです。
分析用のデータ準備やロードを簡単に行うことができ、日々のETL処理を自動化・サーバレス化が可能になります。
データカタログに保存されると、データがすぐ検索でき、クエリ可能にもなるのが特徴です。

### メリット

- 迅速なデータ統合

Glueで抽出、クリーニング、正規化、結合、読み込み、ワークフローの実行など行うことができ、
分析までにかかる時間を数ヶ月から数分に短縮できます

- 大規模なデータ統合を自動化

いくつものETLジョブを実行・管理ができ、
SQLを使用して複数のデータを結合できます。

- サーバー管理が不要

フルマネージドサービスなのでサーバレス環境で実行できます。

### 用語

- データストア
	- s3やDynamoDB,RDS等
- データソース
	- Glueに入力するためのデータストア
- データターゲット
	- Glueに出力するためのデータストア
- データカタログ
	- データを分析するための領域
- クローラー
	- いろんなデータストアからデータカタログにデータを集約する
- ジョブ
	- データカタログ内でデータをELTジョブを実施する


## 勉強後イメージ

分析用のデータを連携して自動的に分析してくれる・・・ってサービス？
触ってみないと実際にはきちんと理解できない。。
一歩がむずかしい

## 参考

- [AWS Glue](https://aws.amazon.com/jp/glue/?whats-new-cards.sort-by=item.additionalFields.postDateTime&whats-new-cards.sort-order=desc)
- [AWS再入門ブログリレー AWS Glue編](https://dev.classmethod.jp/articles/relay_looking_back_aws_glue/)
Mobile Publisher を使用してブランド設定したモバイルアプリケーション ⇒ Mobile Publisher の使用開始

１．Mobile Publisher とは何ですか?
２．ブランド設定された従業員向けアプリケーションを Mobile Publisher を使用して作成する利点は何ですか?
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/634241/2316eb1e-a708-860b-48c2-213568103050.png)
REST APIについて調べてみました

表題にもあります通りREST APIについて調べてみました。
web関係の仕事に携わるために勉強している人は設計モデルについてしっかりと理解することが大切だと感じました。

##そもそもRESTとは
REST(**RE**presentational **S**tate **T**ransfer)はWebサービスの設計モデルです。
RESTは設計に際し以下を設計原則とするよう提言しています。

* アドレス指定可能なURIで公開されていること
 提供する情報がURIを通して表現できること。全ての情報はURIで表現される一意なアドレスを持っていること。

* インターフェース(HTTPメソッドの利用)の統一がされていること
 情報の操作は全てHTTPメソッド(GET、POST、PUT、DELETE)を利用すること。

* ステートレスであること
 ステートとは「状態」を意味します。よってステートレスは「状態がない」という意味になります。ステートレスなやり取りにおいてサーバーはクライアントのセッション情報を保持しません。逆にステートフルなやり取りにおいてはセッション情報が保持される。
※ステートレスについて下記の記事がとても分かりやすかったです。
https://qiita.com/mtakehara21/items/efcbbc3ba58a62c10eb6

* 処理結果がHTTPステータスコードで通知されること
ステータスコードはWebサーバーからのレスポンスを表すコードです。RESTはHTTPメソッドを利用しているのでHTTPステータスコードをその結果として返却します。


###REST APIとは？
上記のRESTの設計原則に則って構築されたWebシステムのHTTPでの呼び出しインターフェースのこと。

```
http://hoge.com/api/post1/getpost
http://hoge.com/api/post1/newpost
http://hoge.com/api/post1/updatpost
http://hoge.com/api/post1/deletepost
```
上の例であれば、RESTの考え方に基づいて考えるとよくない設計です。
正しくは以下のようなURLになります。

```
http://hoge.com/api/post1/postinfo
```
これでは削除なのか投稿なのかが判別出来ません。
そこで登場するのがHTTPメソッド(GET、POST、PUT、DELETE)になります。
先の例ではURLが4つ存在していましたがpost情報を扱うAPIに対して一つにURLで対応することが出来ます。



**参考記事**

https://qiita.com/masato44gm/items/dffb8281536ad321fb08#:~:text=RESTful%20API(REST%20API)%E3%81%A8,%E3%81%AB%E5%BE%93%E3%81%A3%E3%81%A6%E7%AD%96%E5%AE%9A%E3%81%95%E3%82%8C%E3%81%9F%E3%82%82%E3%81%AE%E3%80%82

https://www.subthread.co.jp/blog/20160506/

https://www.slideshare.net/unsolublesugar/res-tful

https://www.subthread.co.jp/blog/20160506/
$GOPATH/go.mod exists but should not


##事象
goファイルを実行する

```
go run xxx.go
```

以下のエラーが出てきた。

```
$GOPATH/go.mod exists but should not
```

##原因
$GOPATHで指定されているディレクトリ配下にxxx.modがあることが原因。
mvコマンドで適当な場所にこのファイルを移動しましょう。
因みにxxx.modファイルはgoモジュールを管理してくれるファイルです。

```shell
#カレントディレクトリにgo.modファイルを移動。
mv $GOPATH/go.mod ./
```
EC2の起動時にPythonのスクリプトを実行

# やりたいこと
- S3へのファイルアップロードをトリガーに、AWS上でかなり重たい処理（動画処理）をさせたい
- しかし、LambdaだとTimeOutやメモリ不足が心配
- そこで、LambdaでEC2を起動させて、起動時にPythonのスクリプトを自動で実行させる

※Pythonに限らず何でも実行できます。

# ファイル構造
```
/home/ec2-user/
└── environment
    ├── main.py
    └── start_function.sh

/etc/init.d/
└── start
```
- （任意）ホームディレクトリ（/home/ec2-user）に```environment```というディレクトリを作る
- 自動実行させたいpythonスクリプト```main.py```
- pythonスクリプトを実行させるためのシェルスクリプト```start_function.sh```
- EC2の起動時にシェルスクリプトを実行させるための```start```

※ファイル名やディレクトリ名は自分で好きに変えてください

# 本編

## pythonスクリプトを実行させるshellスクリプト

```
sudo vim /home/ec2-user/environment/start_function.sh
```
以下をコピペ

```
#!/bin/bash

nohup /usr/local/src/pyenv/shims/python /home/ec2-user/environment/main.py &

exit 0
```
## 起動時にshellスクリプトを実行させるためのファイル

```
sudo vim  /etc/init.d/start
```

以下をコピペ

```
#!/bin/sh
# chkconfig: 345 99 10
# description: start_function shell
case "$1" in
  start)
    su -l ec2-user -c "sh /home/ec2-user/environment/start_function.sh"
       ;;
  stop)
     /usr/bin/kill python
       echo "stop!"
       ;;
  *) break ;;
esac
```
## 権限の変更と自動起動への登録


```
cd /etc/init.d
sudo chmod 775  start
sudo chkconfig --add start
sudo chkconfig start on
sudo chkconfig --list start
```
以下のような出力が出れば完成。

```
start       0:off   1:off   2:on    3:on    4:on    5:on    6:off
```
STM32F767とMCP3425でなんちゃってluxを液晶表示(MCP3425A0T-E/CH 16bitADC)(明るさ)


STM32L010用に軽量コンパクト

構成
STM32G031J6M6
MCP3425A0T-E/CH
NJL7502L
AQM0802A

1.SCLとSDAを接続、プルアップも忘れずに
2.電源の接続
3.下記のソースコードを書き込む
4.コンパイル実行で表示されたら終了
5.おわり

```c++

#include "mbed.h"

#define ADDR        (0xD0)   //  address
#define ADDR_LCD    (0x7C)   //  address

I2C i2c(I2C_SDA, I2C_SCL); //767
//I2C i2c(dp5, dp27); //1114
//I2C i2c(PA_10, PA_9); //010

char    data_read[8];   //i2cバッファー

char INIT_com[]={0x0,0x38,
0x0,0x39,
0x0,0x4,
0x0,0x14,
0x0,0x70,
0x0,0x56,
0x0,0x6C,
0x0,0x38,
0x0,0xC,
0x0,0x1,
0x40,0x41};

char INIT_cls[]={0x0,0x1};

char ch_hex_a_b[5];
char *ch_hex_a(int l_num)
{
    int a,b,c;

    if( l_num >= 400 ) {
        a=4;b=0;c=0;
 
    } else if( l_num >= 300) {
        a=3;b=(l_num-300) / 10;c=l_num % 10;

    } else if( l_num >= 200) {
        a=2;b=(l_num-200) / 10;c=l_num % 10;
        
        
        
    } else if( l_num >= 100) {
        a=1;b=(l_num-100) / 10;c=l_num % 10;
    } else {
        a=0;b= l_num / 10;c=l_num % 10;  
    }

    ch_hex_a_b[0] = '@';
    ch_hex_a_b[1] = '0' + a;
    ch_hex_a_b[2] = '0' + b;
    ch_hex_a_b[3] = '0' + c;
    ch_hex_a_b[4] = 0;

    return(ch_hex_a_b);
}

int ii;     //ループカウンタ

int main()
{
    //液晶の初期化
    for(ii=0;ii<11;ii++){
        i2c.write(ADDR_LCD, &INIT_com[ii*2], 2);wait_ms(2);
    } //for

    i2c.write(ADDR, "\230", 1); //16bit 15sps PGA x1

    int p,s;
    while (1) {
        //液晶のクリア
        i2c.write(ADDR_LCD,INIT_cls,2);wait_ms(2);

        //データの読み込み
        i2c.read(ADDR | 1, data_read, 2);
        
        s = (data_read[0] * 256 ) + data_read[1];
        //s = 32767;
        printf("-s=%d\r\n",s);
        //printf(" h=%d\r\n",data_read[0] * 256 );
        //printf(" l=%d\r\n",data_read[1]);

        // 32768/(163.84/2)=400 luxに変換
        p=( ((s>>5)*6)  + (s>>7)  ) >> 4;
        printf(" p=%d\r\n",p);
        
        i2c.write(ADDR_LCD, ch_hex_a( p ) ,4);

        wait_ms(1000);
    }//while

}//main




```

![mcp3425_767_lux_1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/91a712fd-541c-ab65-c9fb-d7e53b904e3c.jpeg)
【Swift】NotificationCenterのuserInfoで値の受け渡しをする

#はじめに
NotificationCenterで値の受け渡しをする方法を解説します。

#実装

```swift
import UIKit

final class ViewController: UIViewController {

    @IBOutlet private weak var label: UILabel!
    
    override func viewDidLoad() {
        super.viewDidLoad()
        NotificationCenter.default.addObserver(self, selector: #selector(someFunc), name: .someName, object: nil)
    }
    
    @objc private func someFunc(notification: Notification) {
        if let num = notification.userInfo?["someKey"] as? Int {
            label.text = String(num)
        }
        
    }

    @IBAction private func buttonDidTapped(_ sender: Any) {
        NotificationCenter.default.post(name: .someName, object: nil, userInfo: ["someKey": 10])
    }

}

extension Notification.Name {
    static let someName = Notification.Name("someName")
}
```

#解説
まず、Notificationの名前を定義しておきます。

```swift
extension Notification.Name {
    static let someName = Notification.Name("someName")
}
```

次に、NotificationCenterに先ほど定義したNotificationのNameを持つObserverを追加します。
ここで登録したセレクター関数は任意のタイミングでpostした時に呼ばれる関数になります。

```swift
override func viewDidLoad() {
    NotificationCenter.default.addObserver(self, selector: #selector(someFunc), name: .someName, object: nil)
}
```
任意のタイミングでpostして先ほど登録しておいたObserverに処理をするよう通知を発行します。この時、引数のuserInfoに辞書で渡したい値を設定します。

```swift
@IBAction private func buttonDidTapped(_ sender: Any) {
    NotificationCenter.default.post(name: .someName, object: nil, userInfo: ["someKey": 10])
}
```

セレクター関数を定義します。ここで先ほどpostした時に設定した値をNotificationを通して受け取ります。

```swift
@objc private func someFunc(notification: Notification) {
    if let num = notification.userInfo?["someKey"] as? Int {
        label.text = String(num)
    }    
}
```

#おわりに
おわりです。
LeetCode日本語修行3日目- [87-Scramble String]

#Scramble String
参考:https://leetcode.com/problems/scramble-string/
###問題の内容
今日の問題、難しい...
一知半解の状態で、説明がつかない
解答は、他のコードを参考して書きました。
先にコードを記録きます...

```Kotlin
class Solution {
     lateinit var solution: Array<Array<ByteArray>>
        fun isScramble(s1: String, s2: String): Boolean {
            var n = s1.length;
            var m = s2.length;
            if (n != m) {
                return false;
            }
            solution = Array(n, { Array(n, { ByteArray(n) } ) } )
            return myScramble(s1.toByteArray() ,0 ,n - 1 ,s2.toByteArray() ,0,n-1)
        }

       fun myScramble( s1:ByteArray , start1:Int , end1:Int , s2:ByteArray , start2:Int , end2:Int): Boolean {
            if(start1 == end1) return s1[start1] == s2[start2];
            if(solution[start1][start2][end1 - start1].toInt()!=0) return solution[start1][start2][end1 - start1] > 0;
            for (i in 0 until end1 - start1) {
                if( (myScramble(s1 ,start1 ,start1+ i ,s2 ,start2 ,start2 + i) &&
                            myScramble(s1 ,start1 + i + 1,end1 ,s2 ,start2+i+1,end2) ) // x + y
                    ||
                    (myScramble(s1 ,start1 ,start1 + i ,s2,end2 - i,end2) &&
                            myScramble(s1 ,start1 + i + 1,end1 ,s2 ,start2 ,end2 - i -1)) // y + x
                ) {
                    solution[start1][start2][end1 - start1] = 1;
                    return true;
                }
            }
            solution[start1][start2][end1 - start1] = -1;
            return false;
        }
}
```
Ruby/Ruby on Rails 6　環境構築　*Mac OS 編*

#はじめに

今回、progate にてRuby on Rails の学習を一周し終えたので環境構築にチャレンジしてみました。
が、スムーズに行かずつまずいた為その概要を書いていきたいと思います。
同じ駆け出しエンジニアの方の力に少しでもなれれば幸いです。


__＊Mac OSでのRails6環境構築の記事となります＊__


##ターミナルでコマンドを実行
Mac os には標準でターミナル.appが搭載されいるのでそれを使いました。
（アプリケーション/ユーティリティ/ターミナル.app にあります）

##Homebrewのインストール
Mac os専用のパッケージ管理システムです。
[Homebrew](https://brew.sh/index_ja.html)

インストールできたらターミナルにて下記コマンドを入力します。

```
 brew -v
```
インストールできていると、この様にバージョンが表示されます。
＊バージョン名は各自異なります。

```
Homebrew 3.1.2
Homebrew/homebrew-core (git revision e985cb6ba7; last commit 2021-04-16)
```


##rbenvのインストール

ターミナルに下記コマンドを入力します。

```
brew install rbenv
```

インストールができているか確認します。

```
rbenv --version
```
インストールができていれば、この様にバージョンが表示されます。
＊バージョン名は各自異なります。

```
rbenv 1.1.2
```
##rbenvを使用できるようにPATHを通す
ターミナル起動時にrbenvを自動的に起動するようにする為にパスを通します。
下記コマンドを一行ごとに入力します。

```
echo 'export PATH="$HOME/.rbenv/bin:$PATH"' >> ~/.bash_profile
```
```
echo 'if which rbenv > /dev/null; then eval "$(rbenv init -)"; fi' >> ~/.bash_profile
```
```
source ~/.bash_profile
```
正直ここはよく分からなかったため別記事を参考に進めました。

##readlineのインストール
ターミナルのirbで日本語入力ができる様になります。
下記コマンドを入力します。

```
brew install readline
```
日本語入力できる様にパスを通します。

```
brew link readline --force
```

##Rubyのインストール
Rubyのバージョンを確認する為、下記コマンドを入力します。

```
rbenv install -l
```
コマンドを実行すると、バージョン一覧が表示されます。
＊バージョンは各自異なります。

```
2.5.9
2.6.7
2.7.3
3.0.1
jruby-9.2.17.0
mruby-2.1.2
rbx-5.0
truffleruby-21.0.0
truffleruby+graalvm-21.0.0

Only latest stable releases for each Ruby implementation are shown.
Use 'rbenv install --list-all / -L' to show all local versions.
```
インストールするバージョンを指定してコマンドを入力します。
＊バージョンは各自異なります。

```
rbenv install 3.0.1
```
インストール出来ているか確認します。

```
ruby -v
```
インストールができていればこの様にバージョンが表示されます。
＊バージョン名は各自異なります。

```
ruby 3.0.1p64 (2021-04-05 revision 0fb782ee38) [x86_64-darwin20]
```

##Bundlerのインストール
gemに必要な正確なバージョンを追跡してインストールしてくれます。
下記コマンドを入力します。

```
gem install bundler
```
インストール出来ているか確認します。

```
bundler -v
```
インストールができていればこの様にバージョンが表示されます。
＊バージョン名は各自異なります。

```
Bundler version 2.1.4
```
##yarnのインストール
Rails6ではyarnのインストールも必要になりましたので、下記コマンドを入力してインストールします。

```
brew install yarn
```

インストール出来ているか確認します。

```
yarn -v
```
インストールができていればこの様にバージョンが表示されます。
＊バージョン名は各自異なります。

```
1.22.10
```

私はここでつまづきました...。
Rails6ではWebpackerが標準になったことにより、yarnが必要になったそうです。
いくらRailsをコマンドを実行してもインストールできず、ググっても出来ず...。
結果調べて試していたのは、Rails5のインストール手順でyarnのインストールをしていなかったから出来なかっただけでした。
常に最新情報に耳を傾け、調べる力も付けていく必要があること改めて実感しました...。

##Railsのインストール

インストールするバージョンを指定してコマンドを入力します。
今回は-v 6.0.3.4を指定します。

```
gem install rails -v 6.0.3.4
```

インストール出来ているか確認します。

```
rails -v
```
インストールができていればこの様にバージョンが表示されます。
バージョン名は各自違います。

```
Rails 6.0.3.4
```

以上 Ruby / Rails の環境構築となります。
Linuxで手っ取り早くBGPを使うためのBIRDセットアップ

# BIRDとは
BIRDはLinux等で動作するBGPやRIPなどのルーティングプロトコルを実装したプログラムです。2021年4月時点で2.0系と1.6系の両系列がメンテナンスされています。
フリーで利用可能な選択肢としてOSレベルで動作するVyOSなどがありますが、そちらと比較してパフォーマンスは劣る一方で、既存のアプリケションと共存する形でソフトウェアとして導入できる点がメリット。個人的には超簡易にBGPの検証を行う際にも使えるかと思っています。
本記事では、現在主流の2.0系を利用して、Ubuntu20.04上でBGPを動作させ、サーバと直接接続されたセグメントを広告＋網側からの経路を受け取る機能を機能を持った簡易的なルータを動作させるところまで備忘録的にまとめています。

# BIRD2.0導入手順
### apt経由でBIRDをインストール

```bash
$ sudo apt update
$ sudo apt install bird2
```

### BIRD設定
以下の設定例の通りに書き換え

![bird_network.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/661039/96111bf8-ba2b-8262-1ee6-265f0c5df678.png)

- local AS: 65001（Ubuntu側の所属するAS）
- remote AS: 65002（対向側ルータの所属するAS）
- router id: 172.16.1.1（Ubuntu側のIPアドレス）
- neighbor ip: 172.16.1.2（対向側ルータのIPアドレス）
- bgp:
    - (export): すべて（birdで保有する経路 = interface"eth0"のdirect経路のみ）
    - (import): すべて
  
```bash
$ sudo vim /etc/bird/bird.conf
```

```:/etc/bird/bird.conf
log syslog all;
router id 172.16.1.1;
protocol device {
    scan time 10;
}
protocol kernel {
    scan time 10;
    ipv4 {
        export filter {
            if proto = "direct1" then reject;
            accept;
        };
    };
}
protocol direct direct1 {
    ipv4;
    interface "eth0";
}
protocol bgp {
    ipv4 {
        import all;
        export all;
    };
    local as 65001;
    neighbor 172.16.1.2 as 65002;
}
```

```bash
$ sudo systemctl restart bird
# うまく行かない場合再起動
```

### ステータス確認

```bash
$ sudo birdc
```

```
>bird
show protocol all # bgp neighborとの接続がESTABLISHEDになっているか
show route # 経路配信、受領できているか
[ctrl+c]
```

```bash
$ ip route # birdによるbgpの経路がルーティングテーブルに乗っているか
```

### ip_forward設定
Ubuntuではデフォルトでルーティング機能が無効化されているため、
/etc/sysctl.conf 内の `net.ipv4.ip_forward = 0`を`net.ipv4.ip_forward = 1`に変更

# 参考リンク
* [サイボウズエンジニアのブログ ルーティングソフトウェア BIRD の使いかた](https://blog.cybozu.io/entry/bird)
* [BIRD - User's guide 2.0](http://bird.network.cz/?get_doc&f=bird.html&v=20)
* [BIRD - Wiki](https://gitlab.labs.nic.cz/labs/bird/wikis/home)
* [パケット転送をオンにする](https://access.redhat.com/documentation/ja-jp/red_hat_enterprise_linux/6/html/load_balancer_administration/s1-lvs-forwarding-vsa)
requireの使い方

#requireメソッド
送信されたパラメーターの情報を持つparamsが、使用できるメソッド。
requireメソッドは、パラメーターからどの情報を取得するか、選択する。

```ruby
params.require(:モデル名)
```
requireを使うのはパラメーターが二重ハッシュの時のみ。

```ruby
[1] pry(#<OrdersController>)> params
=> <ActionController::Parameters {"authenticity_token"=>"dIFiIxMsjPdq0lATAzwoZgYl/LKtBrD1Zsoo
gqyCDoVhXGqCAQHoVSWIkvkMhuXn+ooywt50eQJiCfcCniJamQ==",
 "hoge"=>"", "post_code"=>"111-1111", "shipping_area_id"=>"3", "municipality"=>"aa",
 "address"=>"aa", "building_name"=>"", 
"phone_number"=>"00000000000", "commit"=>"購入", "controller"=>"orders", 
"action"=>"create", "item_id"=>"2"} permitted: false>
```

この場合だとハッシュは一つなのでrequireは使えない。

```ruby
[1] pry(#<OrdersController>)> params
=> <ActionController::Parameters {"authenticity_token"=>"dIFiIxMsjPdq0lATAzwoZgYl/LKtBrD1Zso
ogqyCDoVhXGqCAQHoVSWIkvkMhuXn+ooywt50e
QJiCfcCniJamQ==","user_purchases"=>{
 "hoge"=>"", "post_code"=>"111-1111", "shipping_area_id"=>"3", 
"municipality"=>"aa", "address"=>"aa", "building_name"=>"", 
"phone_number"=>"00000000000"}, "commit"=>"購入", 
"controller"=>"orders", 
"action"=>"create", "item_id"=>"2"} permitted: false>
```

このような場合だと二重ハッシュなのでrequireを使うことになる。

二重ハッシュになる場合はモデルを指定した時に生成される。
PCの設定で初めにすること

# 概要

最近使ってたPCのSSDが突然読み込まなくなりました．
そこで，新しくSSDを購入，windowsを再インストールしましたが，どんなソフトをダウンロードしていたか忘れたので，覚書としてインストールするソフトウェアを書いていこうと思います．

僕みたいに既にPCの設定を初めからしなくてはいけなくなった人，新しくPCを買って設定したい人に参考になればと思います．僕自身がデータサイエンスの仕事を行ってるので，特にそういった方には共通することが多いと思います．

## スタートメニューで設定できるもの + 

・電源とスリープ : なし
（計算回して放置することもあるので，スリープはしない設定で．）

・Bluetoothとその他のデバイス : ワイヤレスマウス，キーボードの接続
（Logicoolの製品は別でドライバーをインストールする必要があります．）

・PIN サインインの設定

・Microsoft One Drive の設定

## インストールして設定するもの

・ブラウザ : Chrome等

・IME : Google日本語入力 等

・PDF見るやつ : Adobe Acrobat Reader

・アンチウイルスソフトウェア

・コミュニケーションツール : LINE, Zoom, Teams, Slack, Discord 等


## インストールして設定するもの（データサイエンティスト用）

・計算環境 : Spider, Jupyter, MATLAB 等

・エディタ : VScode, Atom 等

・Git


## 必要に応じて

・仮想環境 : Docker Desktop, Virtual Box等

・文章編集ソフト : Tex

・画像編集ソフト : Illustrator, Inkscape等

・GPU周り : Nvidia driver

・Unity

## その他便利なツール

・スクリーンショットアプリ : Rapture

・スクリーン録画 : OBS (Open Broadcaster Software）

・Git Bash, .bashrcの設定


適宜追加していくかもです
Qiitaで自分の投稿記事から検索をする方法

検索ボックスで、以下のように`user:`や`tag:`のクエリをつけて検索する。

`user:tiger-for-fun tag:python イテレータ`

![E4B7ED91-323F-41CA-9677-021FC2C68A49.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1333158/853ffaa2-207f-6597-1513-563bc4113f85.png)

これで「あれどうやるんだったっけ...たしかQiitaに上げたはずだな...」をすぐスマホでも検索できる。

参考:クエリ一覧
![E489153B-3460-4040-98A9-EBCE61C9E192.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1333158/f86eea69-7761-472c-53d5-bbc53cbf5840.png)
ecscheduleでECSクラスタにタスクのスケジューリングを設定する

ECSにサービスをデプロイする場合、[ecspresso](https://github.com/kayac/ecspresso) を含めいろいろなツールがあり情報も多いですが、タスクのスケジューリング（cron的なもの）に関してはあまり情報が見つかりません。みんな定期実行どうしてるんでしょう :thinking: 

探してみると、ecspressoにインスパイアされた __ecschedule__ というツールがありました。

https://github.com/Songmu/ecschedule

実際に使ってみてなかなか良かったので、ecscheduleの使い方と注意点を紹介します。

# インストール

ecscheduleはGo製なので、`go get` か自分の開発環境にあった実行ファイルをパスの通った場所に置けば動きます。また、READMEには書いてありませんが、Macを使っている方はHomebrewでインストールできます。

```sh
$ brew install Songmu/tap/ecschedule
```

# GUIでスケジューリング設定したものをダンプする

ecspressoと同様に、AWSの管理コンソールで設定したものをecscheduleの設定ファイル（YAML）として吐き出せます。GUIでの設定方法は公式サイトを参考にしてください。

https://docs.aws.amazon.com/ja_jp/AmazonECS/latest/developerguide/scheduled_tasks.html

![ap-northeast-1.console.aws.amazon.com_ecs_home_region=ap-northeast-1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/28249/d12b4cc5-5f5b-1954-05a8-58caa8a75385.png)

今回は、このような設定を登録してみました。この設定をダンプしてみます。

```sh
$ ecschedule dump --cluster sample --region ap-northeast-1 > ecschedule.yaml
$ cat ecschedule.yaml
```

```yaml:実行結果
region: ap-northeast-1
cluster: sample
rules:
- name: test
  scheduleExpression: cron(0 3 * * ? *)
  taskDefinition: [TASK_DEFINITION]
  launch_type: FARGATE
  platform_version: LATEST
  network_configuration:
    aws_vpc_configuration:
      subnets:
      - [SUBNET_ID_1]
      - [SUBNET_ID_2]
      - [SUBNET_ID_3]
      security_groups:
      - [SECURITY_GROUP_ID]
      assign_public_ip: ENABLED
```

設定に変更がある場合、ecschedule.yamlを変更して `ecschedule apply` で適用できます。

```sh
$ ecschedule -conf ecschedule.yaml apply -rule test # test という名前のスケジュールルールのみ対象
$ ecschedule -conf ecschedule.yaml apply -all # すべてのスケジュールルールが対象
```

楽ちんですね :sparkles: 

# 注意点

ecspressoと同じような感覚で使えて大変良いのですが、いくつか注意点があります。

## 1. タスク定義を登録する機能はない

ecspressoとは異なり、ecscheduleにはタスク定義を登録する機能はなく、スケジューリングの設定のみ行うことができます。タスク定義は別途行う必要がありますが、ecspressoで作成したタスク定義のJSONファイルを流用し、aws-cliで登録するという方法があります。

```sh
$ aws ecs register-task-definition --cli-input-json file://ecs-task-def.json
```

## 2. 起動タイプを指定しないとEC2になる

ecschedule自体の問題ではないと思いますが、設定ファイルで起動タイプを指定しないとEC2になります。ECSクラスタでFargateのみ使うようにしている場合、起動タイプがEC2だとタスクを起動できず、起動に失敗したログも（おそらく）出ません。

## 3. タスク定義にコンテナが1つしかない場合、1コマンドしか実行できない

ECSでは当たり前な気もしますが、KubernetesのCronJobを使っている方だと勘違いしてしまうかもしれません（私のことです）。CronJobがPodを起動するのとタスク定義からタスクを実行するのとでは概念が違うので、要注意です。

## 4. （v0.9.1まで）設定ファイルからルールを削除してapplyしても、ECSクラスタには適用されない

:::note info
v0.10.0より、[`-prune` オプション](https://github.com/Songmu/ecschedule?tab=readme-ov-file#using-the--prune-option-to-manage-rules) を指定すると、設定ファイルから削除したルールがECSクラスタからも削除されるようになっていました :raised_hands: 
:::

ecscheduleコマンドではルールを削除することができないので、

- GUIで削除する
- aws-cliで削除する
- 設定ファイルに `disabled: true` を追加して無効にする

このような対応を行う必要があります。

## 5. Cron形式で記述する場合、UTCの日時で設定する

https://docs.aws.amazon.com/AmazonCloudWatch/latest/events/ScheduledEvents.html

> All scheduled events use UTC time zone and the minimum precision for schedules is 1 minute.

日本在住だとついついJSTで書きがちですが、UTCで書きましょう。

# 最後に

ECSのデプロイは、ベストプラクティスがイマイチ固まっていないような印象です。運用に応じて適切なツールを選びたいですね。
混同行列のF値を眺めてみる

混同行列の総合評価でF値ってよく出現しますよね。

`p`をprecision(適合率), `r`をrecall(再現率)としたとき、`F`値は、

```math
F = \frac{2pr}{p+r} = \frac{2}{\frac{1}{p} + \frac{1}{r}}
```
で定義されます。`p, r`が動くときどんな挙動を示すのでしょうか？

# 描画

`python`を使って描画してみます：

```py
## set libraries
import numpy as np
import seaborn as sns

## 値の計算
F = np.array([2 / (1/r+1/p) for p in np.arange(0, 1, 0.1) for r in np.arange(0, 1, 0.1)]).reshape(10, 10)

## 描画
sns.heatmap(F)
```

するとこうなります：
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/80539/27dfb7ff-2a19-4236-f589-ce11d624e427.png)

→縦軸、横軸の目盛が0, 1, .., 9なのはご愛嬌。本来は0.0, 0.1, .., 0.9にして欲しいですが、取り敢えず概観みたいだけなので放っておきますw

# 気づくこと

- `p` or `r`が0の時は`F`の定義から値自体が`0`(青枠部分)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/80539/8b50d967-b306-0f4d-83b8-e37d10f2108b.png)


- `p`と`r`の和が一定でも、`p`or`r`のどちらかが高くないとF値は下がる、つまり`p`と`r`のトレードオフを考えた場合、`p`と`r`の両方がバランス良くないとF値は下がりがち
    - 青枠部分は`p+r`が一定のラインですが、端っこにいくと色が黒く、つまり`0`に近く、真ん中辺りは比較的オレンジっぽく値が高いですね。
    - 実務で言えば、適合率、再現率の両者ともに良くないと使い物にならないよね、っていう場合に使ったらいいってことですかね。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/80539/cf0b667f-c1fe-2651-aa26-162a83e87304.png)


## Reference
- [Heatmap in seaborn](https://seaborn.pydata.org/generated/seaborn.heatmap.html)
Herokuでデプロイする手順

#手順
## Heroku CLIをインストール
```
brew tap heroku/brew && brew install heroku
```
その後、完了を確認するため

```
heroku --version
heroku/7.40.0 darwin-x64 node-v12.16.2　#このようにバージョンが表示されていると良い
```
## Herokuにログイン
```
heroku login --interactive
```
## Heroku上にアプリ作成
```
heroku create アプリ名
```
その後、確認のため

```
git config --list | grep heroku
```
## Heroku上でMySQLを使えるようにする
```
heroku addons:add cleardb #ClearDBアドオンを追加
```
その後、ClearDBデータベースのURLを変数heroku_cleardbに格納する

```
heroku_cleardb=`heroku config:get CLEARDB_DATABASE_URL`
```
## Heroku上で環境変数を設定する
```
heroku config:set RAILS_MASTER_KEY=`cat config/master.key`
```
環境変数一覧を表示する

```
heroku config #RAILS_MASTER_KEYが設定されていれば良い
```
## 動作環境を変更する
```
heroku stack:set heroku-18 -a   #Herokuで利用するStackを指定
```
## Herokuへアプリを追加
```
git push heroku master
```

その後、Heroku上でマイグレーションファイルを実行

```
heroku run rails db:migrate
```

##　コマンド一覧
```
heroku apps:info → 公開されたアプリの詳細をみる
heroku logs --tail --app アプリ名　→　ログを表示する
```
##　補足情報
Herokuでは、定期的に画像のデータなどがリセットされるため、出品から一定時間経過した商品画像は適切に表示されなくなる。適切に表示されなくなった画像のデータを消すためには、下記コマンドを用いてデータベースをリセットすることが必要（最後にS3を導入することで、商品画像が適切に表示されなくなる問題は解消される）。
 `% heroku run DISABLE_DATABASE_ENVIRONMENT_CHECK=1 rails db:drop db:create db:migrate`
[PHP] 配列のキーだけを取得する

#概要
配列のキーを一覧を取得する方法をメモします。


#方法
* array_keys()を利用する
* 第一引数にarrayを指定

```.php
<?php
$array1 = [
    'a' => 1,
    'b' => 2,
    'c' => 3
];

$result = array_keys($array1);

print_r($result);
?>
```

結果

```.php
Array
(
    [0] => a
    [1] => b
    [2] => c
)
```
SQL 副問い合わせ(サブクエリ)

SQLの副問い合わせに関して学習したが、忘れそうなので自分用の備忘録。


●副問い合わせとは
　　他のSQL文の一部分として登場するSELECT文。サブクエリとも呼ばれる。丸括弧()で括って記載する。

例：
SELECT 
　　(SELECT [列名] FROM [テーブル名1] WHERE [条件] ) AS 名前
　　FROM [テーブル名2] 
　　WHERE [条件]


●副問い合わせを習得するには
　　・副問い合わせが処理される仕組みを理解する。
　　・副問い合わせの代表的な３パターンを学ぶ。

・副問い合わせが処理される仕組みとは
　　①まず、内側にあるSELECT文が実行され、結果に化ける。
　　②その後、外側のSQLが実行される。

・副問い合わせの代表的な３パターン
　　①単一の値の代わりとして、副問い合わせの検索結果を用いる。
　　②複数の値の変わりとして、副問い合わせの検索結果を用いる。
　　③表の値の代わりとして、服問い合わせの検索結果を用いる。



①単一行服問い合わせ
　　・検索結果が１行１列の１つの値となる副問い合わせ
　　・SELECT文の選択列リスト、FROM句、UPDATEのSET句、また１つの値の判定を行うWHERE句の条件式などに記述できる

SET句での例：
UPDATE　[テーブル名A]
　　SET [列名] = 
　　　　( SELECT AVG([列名]) 
　　　　　FROM [テーブル名B] WHERE [条件] ) 
　　WHERE [条件];


選択列リストで利用する例：
SELECT [列名],
　　(SELECT [列名] 
　　　FROM [テーブル名B] 
　　　WHERE [条件])
　FROM　[テーブル名A]
　WHERE　[条件];

②複数行副問い合わせ
　　・検索結果がn行1列の複数の値となる副問い合わせ
　　・複数の値との判定を行うWHERE句の条件式、SELECT文のFROM句に記述できる。

例：
SELECT　* FROM [テーブル名] WHERE [列名]　IN
　　（SELECT　DISTINCT　[列名] FROM [テーブル名]);

・複数行と比較するときには
　　複数行副問い合わせは複数の値に化けるので、等号や不等号では比較できない。ANY/ALL演算子を組み合わせることで、複数の値との比較を行うことができる。


③表の結果となる副問い合わせ
　　・検索結果がn行m列の表となる副問い合わせ
　　・SELECT文のFROM句やINSERT文などに記述できる

FROM句で利用する例：
SELECT　SUM(SUB.[列名])
　　FROM
　　　　（SELECT [列名]
　　　　　　FROM　[テーブル名A]
　　　　　　UNION
　　　　　SELECT [列名]
　　　　　　FROM　[テーブル名B]
　　　　　　WHERE [条件]
　　　　）　AS　SUB;
[Android Studio]ToolsにSDKマネージャーがない、 build.gradleがない

Android StudioでFile→Openでフォルダを開くとき最初に指定するフォルダを間違えてる可能性があります。
自分の場合、このようなフォルダ構成になっておりました。
ドロイド君のアイコンが下記三つ並んでいるうちの、上二つのフォルダいずれかを指定して「OK」を押してしまうと、掲題の状態になります。
三つ目の青線が入ったところで「OK」を押すと、掲題の事象は解消されました。
目安としては「.gradle」などがあるディレクトリを選択するということのようです。
![ss_and.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/32299/ad57eee0-f73e-e42f-93b4-8f3d2d4f694c.png)
dSYMファイルアップロード方法


firebaseの計測に必要なdSYMファイルが欠落する場合のアップ方法を記載します。
 [dsymファイルとは](https://firebase.google.com/docs/crashlytics/get-deobfuscated-reports?hl=ja "dsymファイルとは")

##方法その１
TestFlightからダウンロードする

①　app store connectでdSYMファイルを取得したいappのTestFlightに移動
②　[ビルドのメタデータ]に移動し、[シンボルを含む]項目にあるdSYMをダウンロードをクリック
③　ダウンロードしたdSYMを解凍
④　dSYMをコマンドでアップロード


ソース内のFirebaseCrashlyticsまで移動

```
$ cd ソースのパス/Pods/FirebaseCrashlytics 
```
FirebaseCrashlyticsディレクトリ内で、以下コマンド実行

```
$ ./upload-symbols -gsp ソースのパス/GoogleService-info.plist -p ios ダウンロードしたdsymフォルダのパス
```

Successfully uploaded Crashlytics symbols
が表示されれば成功！



##方法その2
XcodeのArchivesからdSYMファイルを探す

①　Xcode メニュー → Window → Organizer → Archives
②　dSYMファイルを取得したいビルド版を選択
③　右クリックでshow in foler 選択
④　フォルダが開くので、xcarchiveファイルを右クリックでパッケージの内容を表示
⑤　dSYMsフォルダがあるのでパスを確認
⑥　dSYMをコマンドでアップロード


ソース内のFirebaseCrashlyticsまで移動

```
$ cd ソースのパス/Pods/FirebaseCrashlytics 
```
FirebaseCrashlyticsディレクトリ内で、以下コマンド実行

```
$ ./upload-symbols -gsp ソースのパス/GoogleService-info.plist -p ios ⑤で確認したdsymフォルダのパス
```

Successfully uploaded Crashlytics symbols
が表示されれば成功！
[python] 二次元リストの平坦化

二次元リストなどイテレータの二重構造になっているものの平坦イテレータを取得するには、itertoolsのchain.from_iterableを使う。

```python
import itertools

l_2d = [[0, 1], [2, 3]]

print(list(itertools.chain.from_iterable(l_2d)))
# [0, 1, 2, 3]
```

ちなみに、itertools.chain()は、イテレータの結合につかうもの。

```python
from itertools import  chain
import numpy as np

nums = np.array([[0, 1, 2], [10, 11, 12], [20, 21, 22]])
zeros = np.zeros((2, 3))
print(list(chain(nums, zeros)))
# [array([0, 1, 2]), array([10, 11, 12]), array([20, 21, 22]), array([0., 0., 0.]), array([0., 0., 0.])]
```
[python] sorted()やsort()でソート条件を指定する

lambda式を使う

```python
l_2d = [[2, 10], [1, -30], [-3, 20]]
print(sorted(l_2d, key=lambda x: x[1], reverse=True))
# [[-3, 20], [2, 10], [1, -30]]
```

max()などの関数でも使える。
PandasのDataFrameを二重リストから作成する＆CSVに書きだす

## 二重リストからDataFrameを作成する(カラム名を指定)

```python
import pandas as pd
import numpy as np

data = np.arange(12).reshape(3, 4)
df_simple = pd.DataFrame(data, columns=['col_0', 'col_1', 'col_2', 'col_3'])

print(df_simple)
#    col_0  col_1  col_2  col_3
#0      0      1      2      3
#1      4      5      6      7
#2      8      9     10     11
```

## DataFrameをCSVに書き出す(indexなしでエンコードを指定して)
```python
df_simple.to_csv("df_simple.csv", encoding="utf-8-sig", index = False)
```
Linuxでのコード読み (vim/GNU global)

# 1. はじめに

比較的軽い環境でのコード読みを実現するためのvim/global環境設定をメモしておく。すでに同じような記事があちこちあるが、自分用のメモである。キーバインドはいろいろあるそうなので、徐々に増やす。

# 2. 環境設定
## 2.1. コマンド実行
以下のコマンドを実行する

```
sudo apt update
sudo apt install global
mkdir -p ~/.vim/plugin
wget -P ~/.vim/plugin https://raw.githubusercontent.com/harai/gnu-global/origin/gtags.vim
```

## 2.2. vim設定
`.vimrc`に以下の設定を追加する。

```
cat >> ~/.vimrc << "EOF"
map <C-g> :Gtags 
map <C-h> :Gtags -f %<CR>
map <C-j> :GtagsCursor<CR>
nmap <C-k> :Gtags -r <C-r><C-w><CR>
map <C-n> :cn<CR>
map <C-p> :cp<CR>
EOF
```

# 3. コード読み
## 3.1. コード作成
以下のコマンドで、該当コードに対してタグを作成する。

```
gtags -v
```

## 3.2. コード検索(vim内で)

- `Ctrl + j` 関数定義に移動する。
- `Ctrl + k` 関数の使用場所を探す。
- `Ctrl + o` カーソルを戻す。
- `Ctrl + n` カーソルを下に動かす。
- `Ctrl + p` カーソルを上に動かす。
- `Ctrl + w k` 上のウィンドウへ移動する。
- `Ctrl + w j` 下のウィンドウへ移動する。



# A. 参考資料

- [GNU GLOBALとvimで巨大なコードでも快適にコードリーディング](http://blog.matsumoto-r.jp/?p=2369)
- [gtags.vimでエラーが出る](https://qiita.com/kktk-KO/items/61d2b48d928f1fc77b0f)
    - Ubuntu 16.04等古い版では、gtags.vimの設定ファイルでエラーが発生する。その時この対応が必要となる。
    - `Error: invalid arguments. please use the latest GLOBAL.`
【MySQL／PostgreSQL】UNIQUE制約（一意制約）の違い

## MySQL

**大文字と小文字を区別しない**

hoge@gmail.com == Hoge@gmail.com -> true

UNIQUE制約に引っかからない。


## PostgreSQL

**大文字と小文字を区別する**

hoge@gmail.com == Hoge@gmail.com -> false

UNIQUE制約に引っかかる。

ポスグレのほうが制約としては正しい気がしていますが、こういう仕様らしいです。
Pythonで設定ファイルなどに環境変数の内容を展開する方法

設定ファイルやちょっとしたファイルで、一部のみ動的に変更したい場合があります。
とくに、Dockerコンテナなんかで使う場合は、環境変数で動作を変えられると便利です。
かっこいいテンプレートエンジンを使ってもいいのですが、それほどでもない場合のやり方です。
いつも忘れてしまうので、ここにメモしておきます。

## 設定ファイルのようなもの

次のようなファイルの${NAME}の部分を環境変数で置き換える方法を考えます。

```ini:something.conf
[Setting]
name=${NAME}
```


## 環境変数設定

次のように環境変数に入れておきます。

```console
# export NAME=hirachan
```

## シェルスクリプトの場合

実は、シェルスクリプトでもできます。[envsubst](https://www.gnu.org/software/gettext/manual/html_node/envsubst-Invocation.html#envsubst-Invocation)というコマンドでできるので、紹介しておきます。入っていない場合は、gettextのパッケージを入れましょう。

```console
# envsubst < something.conf
[Setting]
name=hirachan
```

おーー。置き換わりました。
いい感じです。

## Pythonの場合

さて、Pythonの場合です。
Pythonには、[os.path.expandvars](https://docs.python.org/ja/3/library/os.path.html#os.path.expandvars)という便利な関数があります。
os.pathにあるのでファイルのPATHをごにょごにょするための関数のようですが、問題なく使えます。

```python:expand.py
import os
import sys

with open("something.conf", "r") as fr:
    out = os.path.expandvars(fr.read())
    sys.stdout.write(out)
```

実行してみましょう。

```console
# python3 expand.py
[Setting]
name=hirachan
```

おーー。すばらしいですね。

## まとめ

環境変数の展開は、シェルでは`envsubst`、Pythonでは`os.path.expandvars`が便利です。
【ReactNative】Xcodeでビルドできなくなったときに対処したこと

# 概要

React Nativeを0.64.0にアップグレードしたときにXcodeでビルドもアーカイブもできなくなったので、解消方法を書いています。

###環境
macbook pro / Catalina

# Issue1. `jsbundle: No such file or directory` 

## Error
Xcodeにて以下のエラー
`error: /＊＊＊＊/native/ios/main.jsbundle: No such file or directory (in target 'app-name' from project 'app-name')`

`/****/native/ios/main.jsbundle: No such file or directory`

## Solution
### ①NodeのPathを調べる / Checking the Path of a Node

`$ which node`等でnodeのpathを調べる。

``` e.g.
$ which node
/Users/miguel/.anyenv/envs/nodenv/shims/node
```


### ②XcodeでNodeのPathを編集 / Edit Node's Path in Xcode
Projectファイル > TARGETS > APP Name > Build Phases > Bundel React Native code and imageにて、

```
export NODE_BINARY=node
../node_modules/react-native/packager/react-native-xcode.sh
```

となっているところを、 / It's written...

```
export NODE_BINARY=/Users/miguel/.anyenv/envs/nodenv/shims/node
../node_modules/react-native/scripts/react-native-xcode.sh
```
自分のローカルのNodeのPathに合わせてに編集。 / Edit to fit your local Node Path.

### ③メトロバンドラー / Metro-bandler

バンドルを手動で作成する。
React Nativeを0.64.0にアップグレードしたときは一度手動で作成しないといけないらしい。（普段はXcodeが自動で作成してくれてる。）
※2回目以降は不要。

Create the bundle manually.
When I upgraded React Native to 0.64.0, I heard that I have to create the bundle manually once. (Normally, Xcode automatically creates the bundle for you.
(Normally, Xcode creates it automatically.) You don`t need to do it the second time or later.

```
$ react-native bundle --entry-file index.js --platform ios --dev false --bundle-output ios/main.jsbundle --assets-dest ios
```

### ④Run
```
$ yarn ios
```

これでビルドできた。


# Issue2: `Can’t find ‘node’ binary to build React Native bundle`

## Error
Xcodeにて以下のエラー
`Can’t find ‘node’ binary to build React Native bundle`

## Solution
デフォルトのシェルをzshにしていても、Xcodeがbashで動くことがあるみたい。（まだ何故かは分かってないです。詳しい方いたらご教示ください。）
結果的に、bash_profileでnodeのパスを通さないとビルドできなかった。
nodeのpathをzshrc/bashprofileどちらにも通した後、Issue1の解消方法を実行することで解消した。

It seems that Xcode sometimes runs in bash even if the default shell is set to zsh.
As a result, I could not build without passing the node path in bash_profile.
The problem was solved by passing the path of node to both zshrc/bashprofile and executing the solution of Issue1 .

Bundle React Native code and imagesのShellが `/bin/sh` になっているからか？と思い`/bin/zsh`にもしてみたが、結果は変わらず、やはりbashを見ているようだった。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/538418/bff31317-b517-c7e5-b366-8311f122c752.png)


### 解決した

まだ不明点もありますが、これで無事にビルド・アーカイブができるようになりました。
ただm1やbig surの方は、これでも上手くいかないこともあるみたいです。

間違い・補足等ありましたら、教えていただけたら幸いです。
EC2の起動時に自動でソフトをインストールする

無料枠でEC2を作ったり消したりしていると、新しいEC2を作るたびに必要なソフトをインストールするのが手間なので自動でインストールします。

* コンソールからEC2を作成しますが「3.インスタンスの設定」画面で、ユーザーデータにbash形式でスクリプトを張り付けて起動します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/940466/f32d4baf-0fca-8005-c3a0-f0adec26bf58.png)

* 張り付け用スクリプトを作っておくと便利です。

```bash:ユーザーデータ
#!/bin/bash
#hostnameの変更 talominaに変更しています。
sudo sed -i 's/^HOSTNAME=[a-zA-Z0-9\.\-]*$/HOSTNAME=talomina/g' /etc/sysconfig/network
sudo hostname 'talomina'
#localizeの設定
sudo cp /usr/share/zoneinfo/Japan /etc/localtime
sudo sed -i 's|^ZONE=[a-zA-Z0-9\.\-\"]*$|ZONE="Asia/Tokyo"|g' /etc/sysconfig/clock
sudo echo "LANG=ja_JP.UTF-8" > /etc/sysconfig/i18n
#httpdのインストール
sudo yum update -y
sudo yum install httpd -y
sudo service httpd start
sudo chkconfig httpd on
#pipのインストール
sudo yum install python-pip -y
sudo pip install pip --upgrade
#aws cliの更新とboto3のインストール
sudo pip3 install awscli --upgrade
sudo pip install boto3
#pandasと他もろもろをインストール
sudo pip install pandas
sudo pip install pandas-datareader
sudo pip install matplotlib
sudo pip install seaborn
==
```

* 立ち上がったらいきなりいろいろインストールが終わっているので便利です。

```python:getstock.py
#!/usr/bin/python3
from pandas_datareader import data
start = '2021-04-01'
end = '2021-04-11'
df = data.DataReader('7203.T', 'yahoo', start, end)
df.tail(11)
df_json = df.to_json()
print(df_json)
```
【メモ】create-nuxt-appしたファイルが認識されずコミットできない

とある日のことでした。リポジトリを作ってクローン。さてnuxtのフォルダを生成してコードを書こうとした時、`create-nuxt-app app`をしてプロジェクト直下に作成された`app
`がVSCodeの変更タブのところに表示されません。これじゃpushできないじゃん。。といった状態に陥った時の解決策です。

▼イメージ(create-nuxt-appを終えた直後)
![スクリーンショット 2021-04-16 21.15.23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/488939/d6479873-533a-8e2e-0e5b-fea497c27de4.png)
![スクリーンショット 2021-04-16 21.15.36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/488939/8f4f11bb-311f-4a45-be1b-f7948e5acb08.png)


▼解決策
生成された`app`フォルダの中にも`.git`が生成されていた。これを削除すれば変更を認識してくれました。


▼vscodeで.gitが表示されない時
[こちら](https://mrkmyki.com/visual-studio-code%E3%81%A7-git%E3%83%95%E3%82%A9%E3%83%AB%E3%83%80%E3%83%BC%E3%82%92%E8%A1%A8%E7%A4%BA%E3%81%95%E3%81%9B%E3%82%8B%E6%96%B9%E6%B3%95)
コンポーネント指向について

## はじめに
私は、何かを学ぼうとするとき、ついつい基本的な概念を飛ばして、
真っ先にテクニックなどを学ぼうとしてしまいます。

ゲームの説明書は、お出かけ中とかゲームのできない状況だと
夢中で読みますが、ゲームができる時にわざわざ説明書を読みません。

読まずにゲームを始めます。
なぜかゲームをクリアした後に読んだりはしますw
（今でも本棚にあるFF１２の完全攻略本を見るとあの頃を思い出し胸が高鳴ります）

プログラミングの学習においてもそうです。

Reactを学ぶ際、生まれた経緯、コンセプト等は全く調べず、
とりあえずUdemyとかで何か学習教材を探して勉強をはじめました。

改めて今、それを反省し、Reactの基本概念に立ち返るという意味で、
Reactの重要なコンセプトである「コンポーネント指向」について
自分なりにまとめようと思いました。

## コンポーネントとは
まずコンポーネントの言葉の意味を調べてみると

「構成要素、部品」

と書いてあります。

ホームページやアプリは様々なコンポーネントが集まって成り立っています。

例えばTodoアプリであれば、
①Todoを登録するInputエリア。
②登録したTodoを表示するエリア。
③完了したTodoを表示するエリア。

![スクリーンショット 2021-04-10 22.37.45.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1288651/909ae599-6380-bea8-152f-9ce937b6f7a3.png)

たったこれだけのアプリでも３つのエリアに分類されていますし、
①であればさらに細かく言うとTodoを入力する部分と確定ボタンに
分けることができます。
②と③はよく見ると使い回しすれば簡単に作れそうですよね？

そういった部分を一つのコンポーネントとして作成して、
あらゆる部分でそのまま使ったり、ごく一部を書き換えて再利用する。

そうすることで早く作ることができます。

そして何より修正があった時、元のコンポーネントを修正するだけで
いいので、エラーにも強い。

こういったコンポーネントを意識することが、Reactの大前提であると
天下の公式様もトップページで仰っております。

## コンポーネントの分け方
React公式より引用します。

>単一責任の原則 (single responsibility principle) があり、これはすなわち、
>ひとつのコンポーネントは理想的にはひとつのことだけをするべきだということです。
>将来、コンポーネントが肥大化してしまった場合には、小さなコンポーネントに分割するべきです。

先ほどのTodoアプリの例を用いるならば、①で使用した青色の確定ボタン。
これは後々別の部分で使用しそうだな、と思ったら、
このボタンだけのファイルを作成します。
このファイルには、ボタンの機能しかありません。

なんと贅沢なファイルの使い方！
と思った方もいるかもしれませんが、それが上記の
>ひとつのコンポーネントは理想的にはひとつのことだけをするべき

ということなのです。

ひとつのファイルにいろんな関数などをごちゃごちゃ書いていては後々
どこに何が書いてあるかわからなくなります。

「いっぱい書きすぎて訳分からなくなりそう....」
と思ったらファイルを分けてみましょう。

## Atomic Designについて
「ファイルを分けるといっても、どうやって分けるの？」

そんな時参考になる考え方がAtomic Designです！

Atomic　Designとは、コンポーネントを５段階に分けて
完成品を作っていく手法のことです。

1.　Atom

１段階目はアトムと呼ばれる段階です。

日本語に訳すと「原子」。
つまりこれ以上分解できない最小の単位のことを指します。

またまた先ほどのTodoアプリの例で例えると、①のインプットゾーンや
ボタン、②ならTodoの内容、またはチェックボタン、ゴミ箱ボタンがそうです。
１つの要素しかないファイルがAtomです。

2. Molecure

２段階目はモルキュールです。
先ほど作ったAtomを組み合わせて、さらに使いやすいコンポーネントを
作成していきます！
Todoアプリで例えると
②のTodoの内容＋チェックボタン＋ゴミ箱
のAtomを足し合わせて一つのファイルを作成すれば、
どれだけTodoが増えてもそのファイルを使いまわせばいいだけなので楽ちんですね。

3. Organism

3段階目はオーガニズムです。
AtomやMolecureを足し合わせてファイルを作成します。

Todoアプリで言うところの①や②、③のそれぞれのエリアが当てはまります。

4. Templates

4段階目はテンプレートです。
Atom、Molecule、Organismを組み合わせてファイルを作成します。

Todoアプリで例えると.....あれ、ありませんね。
かなり小規模のアプリなのでそういうこともあるでしょう。うん。
...ちゃんと例えられるアプリを例に出せよ？
はい、仰るとおりです。次は頑張ります。

5. Pages

5段階目はページです！これが最後となります。
Atom、Molecure、Organism、Templatesを組み合わせて作成します。

Todoアプリで例えるならタイトル＋①＋②＋③です。
Todoアプリそのものといってもいいかもしれません。

こういった具合にコンポーネントに分けて、利用できるものは再利用して
作成していきます。

## 注意点
ここまで長々と書いてきましたが、注意点としてはただ闇雲に全ての要素を
コンポーネント化する必要はないということです。

Atomとして作成するのはあくまで何度も再利用しそうなものだけで構いません。
なんでもほどほどが肝心です。

コンポーネント化しすぎて逆に時間がかかるようではいけないので
何度も練習して感覚を磨くのが大事かなと思います。

## さいごに
コンポーネント化は何もReactのみに使える話ではありません。

例えばTwitterのアカウント。

作成当初は１つのアカウントに色んなことを呟くと思います。
ゲーム、漫画、アニメ、グルメ、学校、勉強、ムカつく上司への愚痴etc...

しかし途中で自分のツイートを見返した時、多くの情報が混ざりすぎて
関連する内容だけ見たいのに！ともどかしくなるかもしれません。

そのため私は趣味用と学習用で2つアカウントを所有しています。
こうすれば趣味のアカウントを開くときはのほほんと、
学習用をアカウントを開く時は、身が引き締まります。

これもコンポーネント化じゃないかなと思います。

とりあえず長くなったり見づらくなったら整理！
コンポーネント化とはそんな感じだと捉えてます。

以上。ありがとうございました！

## 参考
[React公式](https://ja.reactjs.org/)
[React初学者が必ず押さえておきたい考え方とは？【コンポーネント指向のフロントエンド】](https://www.i3design.jp/in-pocket/8854)
[アトミックデザインとは？ コンポーネント単位で創るUIデザイン手法
](https://goworkship.com/magazine/atomic_design/)
Databricksのアーキテクチャ

> [Databricksクイックスタートガイド](https://qiita.com/taka_yayoi/items/125231c126a602693610)のコンテンツです。

[Databricks architecture overview \| Databricks on AWS](https://docs.databricks.com/getting-started/overview.html) [2021/4/12時点]の翻訳です。

Apache Sparkの開発者が提供する、Databricksの統合分析プラットフォームは、世界中の困難な問題に取り組むデータチームのコラボレーションを実現します。

以下のようなユースケースにおいて、データサイエンティスト、データエンジニア、データアナリストがコラボレーションする際に、Databricksが効果を発揮します：

- スケーラビリティが求められる高度な機械学習、グラフ処理に取り組む
- ディープラーニングを活用して、非構造化データに対する画像解釈、自動翻訳、自然言語処理などを実現する
- データウェアハウスの高速化、簡素化、高スケーラビリティの確保
- データサイエンスとAIによる脅威の早期検知
- IoTデータのリアルタイム分析
- GDPR対応の円滑化


# ハイレベルのアーキテクチャ

Databricksが大量のバックエンドサービスを管理しつつも、セキュアな機能横断チームのコラボラーションを実現するように構成されているので、あなたはデータサイエンス、データ分析、データエンジニアリングの作業に集中できます。

アーキテクチャは独自の設定に依存しますが、以下の図はAWS環境において最も一般的な構成と、データフローを示したものです。
![](https://docs.databricks.com/_images/databricks-architecture.png)

Databricksはコントロールプレーンとデータプレーンから構成されています。

コントロールプレーンには、DatabricksのAWSアカウント上でDatabricksが管理するバックエンドサービスが含まれます。あなたが実行する全てのコマンド(ノートブックのセル)は、完全に暗号化された状態でコントロールプレーンに存在することになります。保存されたコマンドはデータプレーンに格納されます。

データプレーンはあなたのAWSアカウントで管理され、あなたのデータが格納される場所になります。また、ここでデータが処理されます。この図では、既にデータがDatabricksに登録されていることを仮定していますが、イベントデータ、ストリーミングデータ、IoTデータなど外部のデータソースからデータを取り込むことが可能です。Databricksコネクターを用いることで、あなたのAWSアカウント外の外部データソースにも接続することができます。

あなたのデータは常に、データプレーンのあなたのAWSアカウントに存在します。このため、あなたのデータがロックインされることなく、常にフルコントロール、オーナーシップを維持することができます。

## E2アーキテクチャ

2020年9月にDatabricksはE2バージョンのプラットフォームをリリースしました。E2プラットフォームには、以下の機能が含まれます：

- [マルチワークスペースアカウント](https://docs.databricks.com/administration-guide/account-api/new-workspace.html)： [Account API](https://docs.databricks.com/dev-tools/api/latest/account.html)を用いることで、一つのアカウントに対して複数のワークスペースを作成できます。
- [顧客管理のVPC](https://docs.databricks.com/administration-guide/cloud-configurations/aws/customer-managed-vpc.html)： Databricksが作成するVPCでワークスペースを作成するのではなく、あなたが管理するVPCにワークスペースを作成することができます。
- [セキュアなクラスター接続](https://docs.databricks.com/security/secure-cluster-connectivity.html)： "No Public IP"とも呼ばれる機能です。全てのノードがプライベートIPアドレスのみを持つ状態でクラスターを起動でき、より高いセキュリティを実現できます。
- [ノートブックに対する顧客管理の鍵](https://docs.databricks.com/security/keys/customer-managed-keys-notebook-aws.html): (パブリックプレビュー)Databricksが管理するコントロールプレーンに独自のKMSキーを導入できます。

トークン管理、IPアクセスリスト、クラスターポリシー、IAMクレディンシャルパススルーの機能によって、E2アーキテクチャは、AWS上のDatabricksプラットフォームをよりセキュア、スケーラブルにし、管理を容易にします。

特定のお客様を除いて、新たなDatabricksアカウントはE2プラットフォーム上に作成されます。お持ちのアカウントがE2かどうか分からない場合には、Databricks担当までお問い合わせください。

### Databricks 無料トライアル

[Databricks 無料トライアル](https://databricks.com/jp/try-databricks)
kotlinでFirebaseAuthenticationを使ってみる

#はじめに
現在kotlinでチャットアプリを作成中でアカウント作成機能とログイン機能などをつけるためにFireBaseを使用しています。
本記事ではAndroidプロジェクトにFirebaseを追加する方法について記載しています。（未来の自分のためのメモです）
アプリ開発ほぼ初心者で現在勉強中またはバック側の知識が薄い自分みたいな人はメモ程度ですが何かの参考にしていただければ
#開発環境
・使用言語：kotlin
・AndroidStudio 4.1.2
・Android Emulator (自分はm1 Macでの開発をしているので以下のものをダウンロードして使用)
https://github.com/google/android-emulator-m1-preview
#Firebase側の設定
下記画面のプロジェクトの追加を選択し、手順に沿ってプロジェクトを作成する(自分が使っているFireBaseプロジェクトは右側のmessage app)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1077515/da32b81a-5a78-9baa-2346-467ab49ccdb5.png)

プロジェクトの作成が完了すると下記のような画面に移動する。
自分のチャットアプリではメールアドレスとパスワードで会員登録することを想定して開発を行なっているので 'メール/パスワード' が有効になっていますが、Google認証を使用したい場合などは 'Google' のステータスを有効にすることで使用できるかと思います。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1077515/21e33f47-1c36-dab5-e079-d069ac0546b8.png)

こうして作成したアカウントは下記画像のように 'Users' に追加されます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1077515/d69dc10c-81b6-9dc1-c2a4-06591354c4bf.png)
#Firebaseの追加
プロジェクトの設定からマイアプリ内のgoogle-services.jsonのファイルをダウンロード

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1077515/d71d69e7-c31c-d734-6919-ef490c2b993c.png)

ダウンロードしたjsonファイルをAndroidStudioのapp内に格納し、アプリに Firebase SDK を追加するためgradleファイルで宣言。宣言方法は以下の通り（バージョンにもよる）

>dependencies {
  // ...
  // Import the Firebase BoM
  implementation platform('com.google.firebase:firebase-bom:26.8.0')
  // When using the BoM, you don't specify versions in Firebase library dependencies
  // Declare the dependency for the Firebase SDK for Google Analytics
  implementation 'com.google.firebase:firebase-analytics-ktx'
  // Declare the dependencies for any other desired Firebase products
  // For example, declare the dependencies for Firebase Authentication and Cloud Firestore
  implementation 'com.google.firebase:firebase-auth-ktx'
  implementation 'com.google.firebase:firebase-firestore-ktx'
}


![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1077515/8dd2206e-2cb0-e829-ff0d-d6e5285bd3c6.png)

とここまで説明してきましたが公式のドキュメントにもAndroidプロジェクトにFirebaseを追加する方法が記載されています。
自分もこれを見て頑張って作業していたのですが、なかなか実装できず苦労しました。
これを読めば一撃でわかる人が多数だと思いますので参考にしてください
https://firebase.google.com/docs/android/setup?hl=ja#kotlin+ktx

#まとめ
環境構築って嫌になっちゃっていつの間にか部屋の模様替えとか始めちゃいますよね・・・
【React】jestを使用したテスト

# 書き方
```.tsx
import { unmountComponentAtNode } from "react-dom";
import { act } from 'react-dom/test-utils';

describe('テスト箇所', () => {
  let container = null;

  // セットアップ
  beforeEach(() => {
    // documentにDOM要素を描画する
    container = document.createElement('div');
    document.body.appendChild(container);
  });

  // クリーンアップ
  afterEach(() => {
    // documentからDOM要素を削除する
    unmountComponentAtNode(container);
    container.remove();
    container = null;
  });

  it('テスト内容', () => {
    act(() => {
      // コンポーネントをレンダリングする
    });

    // アサーション
    expect('test').toBe('test'); // コンポーネントのレンダリングが完了していることが保証されている
  });
});
```

## unmountComponentAtNode()
- DOMからマウントされたReactコンポーネントを削除する
- イベントハンドラや `state` をクリーンアップする

## act()
- `react-dom/test-utils` が提供するテストのための関数
- アサーションの前に `act()` 内の処理がすべて完了し、DOM に反映されていることを保証する
ROS Python でService Call するまでの流れ

###はじめに

roscore実行時自動で出てくる```/rosout/get_loggers```と```/rosout/set_logger_level```の２つのサービスを例にROS PythonからServiceを呼ぶ時の手順をまとめました。

###サービスについて調べる
1.まず,```Service名```の確認

```
$ rosservice list
/rosout/get_loggers
/rosout/set_logger_level
```

2.次に,```Serviceの型```と```その型を定義しているパッケージ```の確認
Serviceの型のスラッシュの前部分,今回は```roscpp```であることが判明した。

```
$ rosservice type /rosout/get_loggers
roscpp/GetLoggers

$ rosservice type /rosout/set_logger_level
roscpp/SetLoggerLevel
```


3.最後に,```Serviceの型の構成```を確認

```
$ rossrv show roscpp/GetLoggers
---
roscpp/Logger[] loggers
  string name
  string level

$ rossrv show roscpp/SetLoggerLevel
string logger
string level
---
```

### Pythonからの呼び出し

- サービス名が"/rosout/get_loggers"のサービスを呼び出す

![Screenshot from 2021-04-16 20-02-46.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/589906/e1e8e6f2-046d-abbe-8826-454ace0227af.png)


```python:get_loggers.py
#!/usr/bin/env python

import rospy
from roscpp.srv import GetLoggers 

rospy.wait_for_service('/rosout/get_loggers')

get_loggers = rospy.ServiceProxy('/rosout/get_loggers', GetLoggers)

response = get_loggers()

print(response)
```

- サービス名が"/rosout/set_logger_level"のサービスを呼び出す

![Screenshot from 2021-04-16 20-02-37.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/589906/2fa0c5fb-cecb-aac7-bd62-cc4a10f3ccb7.png)



```python:set_logger_level.py

#!/usr/bin/env python

import rospy
from roscpp.srv import SetLoggerLevel

rospy.wait_for_service('/rosout/set_logger_level')

set_logger_level = rospy.ServiceProxy('/rosout/set_logger_level', SetLoggerLevel)

set_logger_level("rosout","DEBUG")

```

### 参考
- [ROS Tutorial Python Service Clientの書き方](http://wiki.ros.org/ja/ROS/Tutorials/WritingServiceClient%28python%29)
【Hyperledger Fabric v1.4.11】「peer version」サブコマンドを実行する

# 「peer version」サブコマンドの概要

* 以下のピアのバージョン情報を表示します。
    * バージョン
    * コミットハッシュ
    * Goのバージョン
    * OS/アーキテクチャ
    * チェーンコードの情報
 
# 文法

```
Print current version of the fabric peer server.

Usage:
  peer version [flags]

Flags:
  -h, --help   help for version
```


# 実行結果

```
~$ peer version
peer:
 Version: 1.4.11
 Commit SHA: 77facb430
 Go version: go1.14.12
 OS/Arch: linux/amd64
 Chaincode:
  Base Image Version: 0.4.22
  Base Docker Namespace: hyperledger
  Base Docker Label: org.hyperledger.fabric
  Docker Namespace: hyperledger
```

# 参考文献

https://hyperledger-fabric.readthedocs.io/en/release-1.4/commands/peerversion.html