OmniAICreator/Qiita-1.07M huggingface dataset:
【SwiftUI】この世でいちばんわかりやすいビューモディファイアの作り方

#この投稿は何？
SwiftUIフレームワークを使ったアプリ開発では、いくつものビューを組み合わせて画面を構築していきます。そのビューの外観や振る舞いを設定するために使用するのがビューモディファイアです。
ここでは、独自のビューモディファイアを定義して呼び出す方法について、実践・解説します。

###実行環境
macOS 11.4
Xcode 12.5.1
Swift 5.4

#ハンズオン
作成するモディファイアは、「ビューにチェックマークをつける」というものです。

![スクリーンショット 2021-07-04 23.09.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/70476/171b97ed-a03f-64af-183c-e38dc7cd8eaf.png)

###ViewModifierプロトコル
新しいファイルを作成して、そこに`Mark`という名前の構造体を定義します。

```Swift:Mark型
import SwiftUI

struct Mark: ViewModifier {
    func body(content: Content) -> some View {
        // ビューを返す
    }
}
```

「モディファイアとして呼び出せるメソッド」を実装するには、その型を`ViewModifier`プロトコルに適合させる必要があります。`ViewModifier`プロトコルは、型にbody(_:)メソッドの実装を要求します。
このメソッドが受け取る’content’パラメータは、モディファイアの適用対象となるビューを示します。そして、返り値の型として宣言されている`some View`が、モディファイア適用後のビューです。

###body(_:)メソッド
ここでは、適用対象となるビューの左側に「緑色のチェックマーク」を配置します。ビュービルダー形式でコードを記述することができます。

```Swift:Mark型
struct Mark: ViewModifier {
    func body(content: Content) -> some View {
        HStack {
            Image(systemName: "checkmark.circle")
                .foregroundColor(.green)
            content
        }
    }
}
```

以上で、独自のモディファイアを定義することができました。

###モディファイアを呼び出す
作成したモディファイアを適用するには、ビューの`modifier(_:)`メソッドを呼び出します。

```Swift:ContentView
struct ContentView: View {
    var body: some View {
        Text("Hello, world!")
            .modifier(Mark())
    }
}
```

プレビューでは、テキストの左側に「緑色のチェックマーク」が配置されます。
ただし、このコードは「一般的なビューモディファイア」とは呼び出し方が異なっていることがわかります。
`.marked()`のように、「モディファイアらしい方法」で呼び出したいところです。

###モディファイアらしい呼び出し方
`View`型を拡張して、モディファイアの望ましい呼び出し方法を実装します。

```Swift:Mark.swift
struct Mark: ViewModifier {
    func body(content: Content) -> some View {...}
}

extension View {
    func marked() -> some View {
        return self.modifier(Mark())
    }
}
```

理想的なメソッド名を宣言して、`some View`型を返すようにします。メソッドのボディでは、自身のインスタンスに対して「元のモディファイアメソッド」を適用したビューを返すでけです。

これで、モディファイアはよりSwiftUIっぽい形式で呼び出せるようになります。

```Swift:Content.swift
struct ContentView: View {
    var body: some View {
        Text("Hello, world!")
            .marked()
    }
}
```

###パラメータを受け取るモディファイア
マークの種類を変更するために、モディファイアがパラメータを受け取ることもできます。

```Swift:Mark.swift
struct Mark: ViewModifier {
    var isChecked: Bool

    func body(content: Content) -> some View {
        HStack {
            if isChecked {
                Image(systemName: "checkmark.circle")
                    .foregroundColor(.green)
            } else {
                Image(systemName: "xmark.circle")
                    .foregroundColor(.red)
            }
            content
        }
    }
}
extension View {
    func mark(isChecked: Bool) -> some View {
        return self.modifier(Mark(isChecked: isChecked))
    }
}
```

ここでは、「緑のチェック」か「赤のバツ」のいずれかをマークするようにモディファイアを定義しました。

呼び出し側のコードでは、モディファイアに`Bool`値を指定します。

```Swift:Content.swift
struct ContentView: View {
    var body: some View {
        Text("Hello, world!")
            .mark(isChecked: false)
    }
}
```

![スクリーンショット 2021-07-04 23.42.08.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/70476/ec069626-0f01-93cb-c048-8198ba4a540c.png)
elasticsearch+kibana+logstashでcsvファイルを可視化する

#logstash
```/etc/logstash/csv.conf
input {
    file {
        mode => "tail"
        path => ["/home/work/*.csv"]
        sincedb_path => "/home/work/sincedb/*_log.csv"
        start_position => "beginning"
        codec => plain {
            charset => "UTF-8"
        }
    }
}
filter {
    csv {
        columns => ["Date", "ID", "contents"]
        convert => {
            "ID" => "integer"
        }
        skip_header => true
    }
    date {
        match => ["Date", "yyyy-MM-dd HH:mm:ss"]
    }
}
output {
    elasticsearch {
        hosts => "localhost:9200"
        index => "log"
    }
    stdout {
        codec => rubydebug
    }
}
```

###実行
`mkdir /home/work/sincedb`
`/usr/share/logstash/bin/logstash -f /etc/logstash/csv.conf`

###indexが作成されているか確認
`curl -X GET http://localhost:9200/_cat/indices?v`

###kibanaで可視化
・kibanaでインデックスパターンを作成
・logの設定 menu> ログ > 設定　>　ログインデックス > log*を追加


#参考
https://aslead.nri.co.jp/column/how-to-ingest-data-into-elasticsearch.html
https://www.casleyconsulting.co.jp/blog/engineer/253/
EC2でauthorized_keys内の公開鍵を削除してしまい、sshログインできなくなった時の対処法

## 参考記事

https://qiita.com/tamano/items/283de0381a55ae6976a6

https://dev.classmethod.jp/articles/ec2-investigate-detach-attach/

https://dev.classmethod.jp/articles/tsnote-how-to-fix-ebs-filesystem-has-duplicate-uuid/

## 状況

これは私がCircleCIを導入する際に、EC2にログインできなくなった事件が発生したので、その際の対処法についてまとめたものです。

ログインできなくなった原因は、CircleCIの設定を行う際に、EC2内の`.ssh/authorized_keys`配置されている公開鍵を削除してしまった事に由来します。この問題はEC2の場合、少しややこしい手順を踏みますが、復旧可能です（まじで詰んだと思いました。）。

## 解決手順

解決手順は1個目のQiitaの記事を参考にさせて頂きました。

注意点としましては、調査用(新しく作成する)EC2の認証鍵の作成の際に、`既存の鍵を使用する`、を選択する事です。これで自身のパソコン内にあるpemファイルを用いてログイン可能にする為、その為に必要な公開鍵がEC2内に作成されます。

> 1. 該当のEC2インスタンスを止めます。
2. ディスクをデタッチして外します。
3. 自分がrootになれる別のEC2インスタンスに、2のディスクをアタッチします。
4. そのEC2インスタンスにログインして、2のディスクをマウントします。
5. マウントしたディスクの中でauthorized_keysファイルを作ります。
6. ディスクをアンマウントしてログアウトします。
7. そのディスクを元のEC2インスタンスにアタッチして起動します。

1~4の更なる詳細な手順は、2個目の記事を参考にすると進行可能です。

4の作業の際にに新しいEC2に対し、既存の(ログインできなくなった)EC2ディスクをマウントする必要がありますが、警告が出てマウントすることができません。
その対処法は自分の場合、3つ目の記事を参考に、`-o nouuid`オプションを追記する事でマウント可能になりました。

そして5の作業について自分の場合は、`sudo cat authorized_keys`コマンドで中にある公開鍵をコピーし、マウントしたディスク内の`.ssh/authorized_keys`内にペーストする作業を行いました。
新規作成したEC2においても同一の公開鍵を利用する設定にしている為、同一の公開鍵が生成され、その値を`authorized_keys`に戻す事で、データを復旧させることができる、という流れです。

あとは引用記事を参考に、ディスクをアンマウント、新規EC2を停止、ディスクを既存のEC2にアタッチする事で、再ログインが可能になります。

## 最後に

まじで焦りました。認証周りの設定に関しては、勢いで行動するのをやめよう。
CMD（コマンドプロンプト）のデフォルト文字コードを変更する方法

私は新卒で入社した開発者になります。
勉強中なので自分用メモとして残したいです。
もし間違っていたらご指摘していただけると幸いです。


###文字コードの確認方法
`chcp`

私のCMDはこのように返ってきた
`Active code page: 932`

###UTF-8に変更

`chcp 65001`

変更されるが、再起動したら元に戻る


###デフォルトの文字コードを変更する方法


①スタート->実行-> regedit
以下レジストリを開く
②HKEY_LOCAL_MACHINE\Software\Microsoft\Command Processor\Autorun
値を以下に変更
③chcp 65001


####もしAutorunがない場合
①スタート->実行-> regedit
以下レジストリを開く
②HKEY_LOCAL_MACHINE\Software\Microsoft\Command Processor

③Command Processorのフォルダを右クリック　新規 -> 文字列値
④作成したものを右クリックして名前をAutoRunに変更

⑤AutoRunをクリックして修正して以下に変更
chcp 65001
CentOS + Apache + MySQL + PHP + Laravel で環境構築 

# 前置き
ほとんどcentos、apacheでの環境構築が初めてだったので、今回行った手順を公開しておこうと思います
「間違っている」「セキュリティ的にどうなの！？」「もっとこっちがいいよ」などなどご意見いただけると嬉しいです


## 前準備
AWSにてCentOsのインストール

以前AmazonLinuxで作成した際にはホストユーザー名がEC2-userだったが、CentOS時にはcentosとなる


## 実行コマンド(行った順で記載)
Apacheのインストール

```
sudo yum update -y
sudo yum install httpd
```

Apacheの起動と、自動起動設定

```
//Apacheの起動
sudo systemctl start httpd
//自動起動の設定
sudo systemctl enable httpd
```
自身のサイトへアクセスし、Apacheの初期画面が表示されていればOK!

PHPとLaravel導入用のComposerのインストール

```
sudo yum install epel-release
sudo yum install http://rpms.famillecollet.com/enterprise/remi-release-7.rpm
sudo yum install --enablerepo=remi-php74 php74 php 
sudo yum install --enablerepo=remi-php74 php-fpm
sudo yum install --enablerepo=remi-php74 php-mbstring
sudo yum install --enablerepo=remi-php74 php-mysqlnd
sudo yum install --enablerepo=remi-php74 php-pecl-zip
sudo yum install --enablerepo=remi-php74 php-xml
sudo yum install -y  php74-php-bcmath php74-php-ctype php74-php-json php74-php-openssl php74-php-PDO php74-php-tokenizer gcc
sudo yum install --enablerepo=remi,remi-php74 php-pecl-zip composer
```

Vimのインストール

```
sudo yum -y install vim-enhanced
```
laravelのインストール

```
composer global require laravel/installer
cd /var/www/html
sudo composer create-project --prefer-dist laravel/laravel app "7.*"

```

権限設定

```

sudo chmod -R 777 /var/www/html/app
sudo chown -R apache.apache /var/www/html/app
sudo chown -R apache:apache /etc/httpd
```

初期で入っているmariadebを削除

```
sudo yum remove mariadb-libs
```
MySQLインストール

```
sudo yum localinstall http://dev.mysql.com/get/mysql80-community-release-el7-3.noarch.rpm
sudo yum install -y mysql-community-server
sudo touch /var/lib/mysql/mysql.sock
sudo chown mysql:mysql /var/lib/mysql/mysql.sock
chmod g+w /var/lib/mysql/mysql.sock
//mysqlのグループへ追加し、参照できるようにする
//usermod -aG [追加したいグループ] [追加するユーザー]
usermod -aG mysql user
```


Laravel設定

```
cd /var/www/html/app
php artisan key:generate
```
centosのタイムゾーン変更

```
sudo timedatectl set-timezone Asia/Tokyo
```
mysqlのタイムゾーン変更

```
/usr/bin/mysql_tzinfo_to_sql /usr/share/zoneinfo > ~/timezone.sql
mysql -u root -p -Dmysql < ~/timezone.sql
```

sudo vi /etc/my.cnfに以下追加

```
default-time-zone = 'Asia/Tokyo'
```

MySQLの文字コードをutf-8へ変更
my.confに以下を追加

```
character_set_server=utf8
skip-character-set-client-handshake
```

再起動させて変更を反映させる

```
systemctl restart mysqld
```
UnityとVisual Studioの連携方法(組み込みライブラリの参照)

## はじめに
この記事は、Visual Studioを使ってUnityのC#スクリプトを実装し始めた初心者の方を対象としたものです。
本記事で登場するVisual StudioとUnityのバージョンは以下の通りとなります。

- Visual Studio Community 2019 : 16.9.4
- Unity : 2020.3.4f1

## 導入・設定手順

### 1. Unity support for Visual Studioのインストール

「Visual Studio インストーラー」を起動します。Unityと一緒にVisual Studioをインストールしている場合は、既にお使いのPCに入っていると思います。
![VisualStudioInstaller_Search.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/682277/941a1961-4136-9fc8-e026-ea39913955f4.png)
もし、お使いのPCに入っていない場合、[ここ](https://docs.microsoft.com/ja-jp/visualstudio/install/install-visual-studio?view=vs-2019)からインストールできます。

「Visual Studio インストーラー」を起動したら、「変更(M)」を押して、ダウンロードする拡張機能を選択します。
![VisualStudioInstaller.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/682277/bd5ea4b3-db18-1387-9ada-fccf9fd63b1a.png)
拡張機能の一覧が表示されたら、「Unity によるゲーム開発」にチェックを付けて、「変更(M)」を選択しましょう。
![VisualStudioInstaller_UnityDev.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/682277/5c07f145-2b40-1323-1eb4-eac293217d99.png)
ダウンロード、インストールにはしばらく時間がかかると思うので、気長に待ちましょう。

### 2. Unityの設定変更

拡張機能のインストールが終わったら、次はUnityの設定を変更しましょう。

「編集」から「環境設定...」を選択し、設定画面を開きましょう。（UIが英語版の場合は、「Edit」から「Preferences...」を選択しましょう）
![Preferences.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/682277/b879a35f-a684-7d32-5b45-8f193f4b7db7.png)
「外部ツール」の項目を選択すると、一番上に「外部のスクリプトエディター」と書かれたプルダウンがあると思いますので、そこを「Visual Studio Community 2019 [16.9.4]」に変更しましょう。

以上でUnity側の設定は終わりです。これでVisualStudio上からUnityの組み込みクラスを参照できるようになっていると思います。
![VS_suggest.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/682277/887f6d6b-dfd2-52ea-f6f0-8b00c12d49b4.png)
試しに、VisualStudioでC#のソースコードを開いて、文字を打ってみましょう。`ga`と打ったら、`gameObject`が出てきていますね！ヤッタ！

以上、VisualStudioとUnityの連携方法(組み込みライブラリの参照)でした。皆様のゲーム制作のお役に立てていればうれしいです。
ActiveRecordの基本メソッドとSQL

##初めに
railsにはActiveRecordと呼ばれる機能が存在します。
ActiveRecordを使用することでデータベースに簡単にアクセスできます。
しかしActiveRecordでは対応できないデータの取り出しや、そもそもSQLの理解が深まらないため、今回はActiveRecordのメソッドで発行されるSQLについてまとめます。

##ORMとは
オブジェクトリレーショナルマッピングのことで、rubyなどのオブジェクト指向言語では直接扱う事のできないRDBMS上のデータを、マッピングすることで扱えるようにします。開発者はSQLを意識することなく、オブジェクト指向的にデータを扱うことが可能になります。

##ActiveRecordとは
ActiveRecordとはMVCのM(mdel)を担う階層です。上記のORMシステムを利用するための機能。railsで作成されたmodelはActiveRecordが継承されるため、ActiveRecordが提供するメソッドを使用することができます。


##ActiveRecordの基本メソッドによって発行されるSQL
|カラム|データ型|
|---|---|
|id|integer|
|name|string|

```practice.rb

user.save(name: "ジョン")
#userが新規登録の場合。
#INSERT INTO users name values ('ジョン')
#userが既に登録されている場合。
#UPDATE users SET name = 'ジョン';

user.update(name: "たかし")
#UPDATE users SET name = 'たかし';
#既に登録されている場合はsaveメソッドとupdateメソッドは同じSQLが発行される。

user.create(name: 'ジョン')
#INSERT INTO users (name) values ('ジョン');

User.find(1)
#SELECT * FROM users WEHERE id = 1 limit = 1;

User.find_by(name: "ジョン")
#SELECT * FROM users where name = 'ジョン' limit = 1;

User.all
#SELECT * FROM users;

user.destoroy
#DELETE FROM users WHERE users.id = 1;

User.find(1).articles
# SELECT * FROM users WHERE id = 1 LIMIT 1;
# SELECT * FROM articles WHERE user_id = 1;
```

##終わりに
ActiveRecordは便利ですが、どうしても発行されるSQLを意識しないまま実装してしまいがちです。実務においてSQLは使用機会が多いそうなので意識して実装する方が良さそうですね〜
Google Colaboratoryで指定フォルダ配下のデータをGitHub連携

Google Colaboratory(Colab)で指定フォルダをGitHub連携させる方法は3つありそうです。

1. Gitコマンドを使った連携
2. Private tokenを発行した連携
3. GitコマンドとSSHを使った連携
4. APIを使用した連携

1, 2はうまく実行できています。


## 1.Gitコマンドを使った連携

このColabにコードは載っているのでコピーして活用ください。
https://colab.research.google.com/drive/1hAKJOrjdw09uf_i-zAdUgEj38fvj6ibk

このコードの中
- user_name
- email
- passwprd
- repo
を変更したら動きます。

ただ、パスワードが見れる状態になってしまうので、
SSHで指定したいなと思っています。

この動画を参考にさせていただきました。
https://www.youtube.com/watch?v=zPx-nZF7890

cloneから実施する場合はこれでいけます。

```bash
# ドライブをマウント
from google.colab import drive
drive.mount('/gdrive')

# ディレクトリの変更
%cd /gdrive/MyDrive/{フォルダ名}

!git clone https://{user_name}:{password}@github.com/{user_name}/{repo}.git
```

## 2.Private tokenを発行した連携
こちらの記事を参考に実行できました。
https://qiita.com/shikumiya_hata/items/fa89126e13c57a997d59

tokenを発行して`git_token`を発行したtokenに変更したら実行できました。

```
!git clone https://git_token@github.com/username/repository.git
```

private tokenの発行方法はこちら
https://docs.github.com/en/authentication/keeping-your-account-and-data-secure/creating-a-personal-access-token

実行後はcontentは以下にレポジトリが作成されているので、
下記でディレクトリを変更してimportしていきます。

```py
%cd /content/repository
from モジュール名 import クラス名 or 関数名
```

## 3.GitコマンドとSSGを使った連携

わかりやすくまとめていただいている記事があったのですが、
動かず断念しました。
https://qiita.com/SeeLog/items/100e64e2decd0c0efb7d


## 4.APIを使用した連携

これはフォルダごとGitHubに連携できるのかはまだ分かっていないです。
まだ試していないですが、この記事とかを参考にコードを変えたら、
フォルダ毎GitHubにあげられないかなと思っています。
https://qiita.com/calderarie/items/fc867e67232daea01983



## 備考

指定フォルダではなくて、今開いているファイルのみGitHubへ上げる場合は
ファイルの`GitHubにコピーを保存`で可能です。

GitHubのprivateのレポジトリを指定したい場合は、
下記のURLから`GitHub` > `非公開レポジトリを含める` にチェックをつける必要があります。

https://colab.research.google.com/notebooks/intro.ipynb?hl=ja#recent=true
高レイヤのアプリ開発者にも役立つ strace の実践例(1)


## 概要

Linux システムコールトレーサである strace の実行例である.


## 詳細

リモート Git リポジトリに Push しようとしたところ、次のエラーが出た.
現象としては全く別のアカウント (ここでは `oldname`) を使って GitHub にアクセスしようとしている.

恐らく何かしらの設定ファイルに記したアカウント情報を見て GitHub に接続しているのだろうが、ファイルに見当が付かない.
この場合、Linux のシステムコールである open 関数を使っていると想像できるので、システムコールトレーサである strace コマンドを使って調査することが可能である.

```
$ git push -u origin master
remote: Permission to <GitHub の URL>/tutorial.git denied to oldname.
fatal: unable to access 'https://github.com/<GitHub の URL>/tutorial.git/': The requested URL returned error: 403
```
　

## 補足

strace の詳細は [Binary Hacks ―ハッカー秘伝のテクニック100選 (オライリ)](https://www.amazon.co.jp/Binary-Hacks-%E2%80%95%E3%83%8F%E3%83%83%E3%82%AB%E3%83%BC%E7%A7%98%E4%BC%9D%E3%81%AE%E3%83%86%E3%82%AF%E3%83%8B%E3%83%83%E3%82%AF100%E9%81%B8-%E9%AB%98%E6%9E%97-%E5%93%B2/dp/4873112885) を見ても良い.

// 15年も前の本なので、流れが緩やかな低レイヤといえども使用不可になった技がいくつかある.
// 例: statifier


## 実践

### 1. strace を使って調査したいコマンドを実行する

次のように「strace -f -o ログ出力先 本来のコマンド」という使い方をする

```
$ strace -f -o /tmp/log-git git push -u origin master
```

するとログ「`/tmp/log-git`」が生成されるので見てみる.
ログは末尾から辿ると、原因特定が早いことが多い.

### 2. strace の実行ログを見て原因を調べる

疑義箇所として 🛑 が見つかった.

```
略
4226  openat(AT_FDCWD, "/home/foo/.netrc", O_RDONLY) = 3 🛑
4226  fstat(3, {st_mode=S_IFREG|0600, st_size=55, ...}) = 0
4226  read(3, "machine github.com\nlogin jofrnpn"..., 4096) = 55
4226  read(3, "", 4096)                 = 0
4226  close(3)                          = 0
略
```

### 3. /home/foo/.netrc を見てみる

github.com に接続する場合に使用してほしいアカウントとパスワードをベタ書きしていましたとさ.

```
$ cat /home/foo/.netrc
machine github.com
login oldname
password p@ssw0rd
```

ということでこのファイルを消せば問題解決である.


以上
Rails 用語　まとめ（メモ用）

#この記事を書こうと思った理由
エンジニアとして仕事をしていくためにはコードを書くことも大事ですが、他の人と共同作業をしていくためには押さえておくべき用語や知識が必要と考えました。
###ルーティングとは
ルーティングとは送信されたURLに対して、どのコントローラーの、どのアクションで処理するかを決める「対応表」みたいなものです。ルーターでは受け取ったリクエストを見て、どのコントローラーのなんの処理を行うのかを決定してくれます。
###アクションとは
ブラウザに返すビューをviewsフォルダの中から見つけ出す役割を担っています。
アクションは、コントローラーと同じ名前のビューフォルダから、アクションと同じ名前のHTMLファイルを探してブラウザに返します。
###コントローラとは
パソコン・ブラウザからのリクエストを受け取り、結果をブラウザに送る役割を担っています。
ルーティングによって振り分けられた情報を処理して、クライアントに返します。
###ビューとは
レスポンスとして返す見た目を設定します。
###モデルとは
データベースとのやり取りを行うクラスのことで、共通した記述やルールを記述します。
###HTTPとは
webサイトを表示する際に使用するプロトコルのことです。クライアントとwebサーバー間でhtmlで記述されたwebページの送受信で使用します。
##参考になった記事
[コントローラーについて](https://udemy.benesse.co.jp/development/system/rails-controller.html#:~:)
[2021/06]今月の俺のエラー

# はじめに
自分がどんなエラーに遭遇したのかをまとめておくことで、エラーの早期解決につなげることを目標とします。
もちろん、みなさんのお役にも立てれば幸いです。

## Avoid mutating a prop directly since the value will be overwritten whenever the parent component re-renders
- カテゴリー
    - Vue.js
- 場面
    - propsで取得した値にメソッドで空のオブジェクトを代入した
- 解決法
    - propsの値を別のプロパティに代入し、そのプロパティを操作する

## 1822 Failed to add the foreign key constraint. Missing index for constraint 'admins_authority_id_foreign' in the referenced table 'authorities'
- カテゴリー
    - Laravel
- 場面
    - マイグレーション
- 解決法
    - 主キーを設定するの忘れていた

## Failed asserting that two strings are equal.
- カテゴリー
    - Laravel
- 場面
    - 「保存が完了したらリダイレクトさせる」という処理のテスト
- 解決法
    - 下記のように、assertRedirectを書かない。
    - HTTPステータスコードで確認してあげれば良い。

```php:修正前.php
$response = $this->post(route('admin.management.store'), $data);
$response->assertRedirect(route('admin.management.home',['company' => $admin->company_id]));
```

```php:修正後.php
$response = $this->post(route('admin.management.store'), $data);
$response->assertStatus(302);
```

# さいごに
エラーって遭遇した時は、精神的ダメージが大きいですが、解決できたら本当嬉しいですよね。
7月にはどんなエラーが待ってるのか、みなさんお楽しみに〜。
住所一覧の各目的地までの所要時間を取得する GAS スクリプト

大したスクリプトではないのですが、同じことをしようと思っている方がいるかもしれないので記事にしました。

# 背景
新型コロナウイルスのワクチン接種がスタートしてしばらく経ちますが、自治体によっては接種券が配布されて予約ができるようなところも増えていると思います。国や自治体が実施している大規模接種もありますが、近隣の病院で予約を取ることも可能です。
私の住む板橋区では、ありがたいことにウェブページにて予約を受け付けている病院の一覧を公開してくれています [^1] 。しかし、住所を見ただけでは家から近いのか、ワクチンを打って帰ってこれる距離なのかがわからず、かといって全部の病院を地図で調べるのも手間です。なので、スクリプトで所要時間を計算して近い病院を探すことにしました。
[^1]: https://www.city.itabashi.tokyo.jp/kenko/kenshin/yobou/1030911/1032756.html

# 使い方
実際のスクリプトはこちらです。
https://github.com/hako017/gasGetRequiredTime/blob/main/%E3%82%B3%E3%83%BC%E3%83%89.gs

1. スプレッドシートを作成します。
1. スプレッドシートに機関一覧の情報をコピーします[^3]。
1. GAS のエディタを開き[^2]、コードをコピペしてください。
1. コードの必要な部分を修正します。（詳細は次のセクションを参照）
1. 実行する関数を`myFunction`に変更して実行します。
1. 権限を求められたら許可してください。
1. 実行結果がスプレッドシートの指定された場所に書き込まれます。

あとは結果をもとにソートするなりしてあげてください。

[^3]: スプレッドシートの関数`importHTML`を使うとhtmlファイルから表をインポートすることもできます。
[^2]: GAS の詳しい使い方は説明しませんが、Qiita に記事があると思うのでそちらを探してみてください。

## 実行する前に修正する部分
```js
  /** 出発地 */
  const origin = "" // ここに出発地を入力
```
上記の変数には出発地（住所など）を記載してください。

```js
  /** 住所一覧が記載されている行のはじめ */
  var destRow = 2
  /** 住所一覧が記載されている列 */
  var destCol = 2
```
この箇所でデータを取ってくる開始行と列を指定しています。実際のスプレッドシートに合わせて変更してください。
上のコードでは、開始行は2行目、読み取る列は2列目となっています。

```js
  // スプレッドシートへと書き込む
  range = sheet.getRange(2, 4, list.length, list[0].length)
```
この箇所でスプレッドシートに結果を書き込んでいます。`getRange(2, 4, ...)`の2, 4がそれぞれ開始行と書き込む列を指定していますので、実際のスプレッドシートに合わせて変更してください。

# 参照
https://qiita.com/luc_yhi/items/7fe167f6ab49298ab9dd

こちらに掲載されているコードを参考にさせていただきました。ありがとうございます。
変更点としては以下の通りです。

- 移動手段を自動車から[徒歩もしくは公共交通機関]へと変更
- 移動経路が取得できなかった場合の処理を追加[^4]

[^4]: 移動経路が取得できない場合のほかに時間が極端に長くなる場合もありました。Google Map で手動で検索すると検索できる場合が多いので、変な結果があった場合は手動で検索してみてください。

車での経路を探したい方は参照元のコードを参考にしていただければ幸いです。
SharePoint サイトの通知設定をPower Queryで一覧化

# 概要
SharePointの通知設定、個人の設定は見ること可能なんですが、サイト一覧を見る方法が見つからなかったので、Power Queryで一覧化してみたメモ

# 結果の例
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/120072/55ad138f-078b-a4d8-7b2e-85b0412afc46.png)

# やり方
1. Urlを替えやすいように、Excel内でTable定義
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/120072/8289a548-5019-3a8b-b07c-67f720358fd8.png)

1. Alertsの取得<br>
<code>**= OData.Feed("{サイトURL}/_api/web/alerts", null, [Implementation="2.0"])**</code>
>     <code>= OData.Feed((Excel.CurrentWorkbook(){[Name="ShareSettings"]}[Content]){0}[対象URL] & "/_api/web/alerts", null, [Implementation="2.0"])</code>
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/120072/314d5352-57b0-c566-fd41-3580a19557c2.png)
1. Usersの取得<br>
<code>**= OData.Feed("{サイトURL}/_api/web/siteusers", null, [Implementation="2.0"])**</code>
>     <code>= OData.Feed((Excel.CurrentWorkbook(){[Name="ShareSettings"]}[Content]){0}[対象URL] & "/_api/web/siteusers", null, [Implementation="2.0"])</code>
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/120072/fa65c0e1-4aed-6dfa-5c43-6f350b3f1b08.png)
1. 上二つをマージして終わり
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/120072/55ad138f-078b-a4d8-7b2e-85b0412afc46.png)
Enumのままだとわかりにくいので、Table でEnum定義して、変換かけると少しわかりやすくなります。

# description
how to display sharepoint alert settings by power query

# 参考情報
- Enumの定義

https://docs.microsoft.com/ja-jp/dotnet/api/microsoft.sharepoint.spalert?view=sharepoint-server
Flask操作メモ： Hello World 出力

#概要
Pythonの軽量フレームワーク、FLASK。
自身の知識振り返り・メモもかねて作成


##項目
1.myapp ディレクトリの作成
2.myappディレクトリ内に、hello.py ファイルを作成
3.hello.py　の記述
4.FLASKサーバーを起動して、表示確認

***
###1. myapp ディレクトリの作成
コマンド操作で実行。作成場所はどこでもOK
※初めての場合、pip install Flask でインストールが必要

```
  $ mkdir myapp
  $ cd myapp 
```
mkdir でmyappディレクトリを作成
cd で作成したmyapp フォルダに移動しています
***


###2. myappディレクトリ内に、hello.py ファイルを作成

以下のように、新規ファイルを作成
myapp/hello.py

***
###3. hello.py　の記述
```php:(hello.py)
from flask import Flask
app = Flask(__name__)

@app.route("/")
def hello_world():
    return "Hello World!" 
```

1行目で、Flaskモジュールを読み込み
2行目で、Flaskクラスのインスタンスを作成。app変数に代入

3行目以降は、「/」というURLにアクセスされた際の処理を記述。
ここでは、return 'Hello, World!' で、 'Hello, World!' という文字列を返すように設定。
***
###4.FLASKサーバーを起動して、表示確認
```
$ FLASK_APP=hello.py FLASK_ENV=development flask run
```
FLASK_APP= で起動させる.pyファイルを指定。

FLASK_ENV=development を記載すれば、デバックモードが有効になる。
（変更点の反映が確認しやすいので、主に記載して起動）

ブラウザで、以下のローカル環境にアクセス。
Hello World と表示されていれば完了。
>http://localhost:5000/


以上、必要に合わせて内容追記します。
機械学習の2値分類における評価実装

#はじめに
正解率、損失、再現率、適合率、F値の可視化の方法をまとめています。
tensorflowを使って学習をし、モデルを保存した状態での方法を書いています。

# 評価方法
## 正解率, 損失
```python
#モデルを作成し評価する
score = model.evaluate(x_test, y_test)
print('Test loss:', score[0])
print('Test accuracy:', score[1])
```

```
Test loss: 0.2857113599777221
Test accuracy: 0.96397587776184
```

## 混同行列(再現率、適合率、F値)
```python
predict = model.predict(x_test)
cm = confusion_matrix(y_test, predict>0.75)
print("confusion_matrix")
print(cm)

recall =cm[0][0] / (cm[0][0] +cm[0][1])
precision = cm[0][0] / (cm[0][0] +cm[1][0])
print("recall:" +str(recall))
print("precision:" +str(precision))

F1_score = 2* (recall * precision)/(recall + precision)
print("F値:" + str(F1_score))
```


```:out
confusion_matrix
[[ 4567  40]
 [12 3456]]
recall:0.94117647058824
precision:0.7607361963190186
F値:0.82290322580645157
```

## 再現率（Recall）,適合率(Precision)

- 再現率
正解が0のデータのうち、AIくんが0と答えられた割合のこと

- 適合率
AIくんが０と答えたデータのうち、正解していた割合のこと

```python
import matplotlib.pyplot as plt
from sklearn import metrics

precision, recall, thresholds = metrics.precision_recall_curve(y_test, test_predict)

plt.plot(np.append(thresholds, 1), recall, label = 'Recall')
plt.plot(np.append(thresholds, 1), precision, label = 'Precision')
plt.legend()
plt.xlabel('Thresholds')
plt.ylabel('Rate')
plt.grid(True)
```
##F値
再現率と適合率を合わせて評価する指標
再現率と適合率の確率の平均

```python
recall =cm[0][0] / (cm[0][0] +cm[0][1])
precision = cm[0][0] / (cm[0][0] +cm[1][0])
print(recall)
print(precision)

f1_score = 2* (recall * precision)/(recall + precision)
print(f1_score)
```

#終わりに
これは自分用のメモで作成しました。雑ですみません。
printの出力の数値は適当です。

ご意見、指摘等ありましたら、びしばし教えていただけると嬉しいです。
Get class method parameter name from .class file at runtime

#In the beginning

In the beginning class method parameter name is ignored by complier and only parameter type is recored into .class file. For example

```java
float totalSalary(float hours, float hourlySalary) {
	...
}
```

You can get the following only if decompile .clsss file generated. This called [method signature](https://docs.oracle.com/javase/tutorial/java/javaOO/methods.html).

```
float totalSalary(float, float)
```

So this is the reason why you **can't** define two methods like below with same method signature in one class.

```java
float totalSalary(float hours, float hourlySalary) {
	...
}

float totalSalary(float days, float dailySalary) {
	...
}
```

#Start from Java 8

As I remember, new option "-parameters" is introduced into javac which includes class method parameter name into .class file. For example

```java
package test;

public class TestClass {

	public static void main(String[] args) {
		System.out.println("Hello");
	}

}
```

By using javap to decompile generated .class file

```
javap -v -cp <class path> test.TestClass
```

Output is

![01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/232557/3eb42be9-7258-f03d-39c3-b3a9a78ebc6f.png)

Method parameter name is shown on **MethodParameters**. And you may refer to [here](https://stackoverflow.com/a/20594685) for how to read this at runtime.

# Relationsip between Spring Framework

Modern frameworks including Spring Framework are heavy using this feature. If "-parameters" option is not specified when compile source code, for example *org.springframework.web.bind.annotation.PathVariable* annotation of Spring MVC will not work.

If your project is managed by Maven, you can specify **parameters** parameter in [Apache Maven Compiler](https://maven.apache.org/plugins/maven-compiler-plugin/compile-mojo.html#parameters) plugin.

Or if your project is built on the top of *spring-boot-starter-parent* project, you don't need to do anything because complier parameter is included at parent POMs.
REST API リンク集

# はじめに

REST API関連のリンク集です。

# Specification

REST API関連の規格についてのリンク集です。

## OpenAPI Specification

https://swagger.io/specification/

Open API です。

## webconcepts

https://webconcepts.info/

Web Conceptsは、web関連の仕様の概要を説明するサイトです。

# Organizations

## OpenAPI Initiative

https://www.openapis.org/

OpenAPI Initiativeは、Open API の規格を管理している団体です。Linux foundation の下部組織です。

# Tools

## OpenAPI.Tools

https://openapi.tools/

Open API のツールチェーンのまとめサイトです。

ツールチェーンを以下のカテゴリに分類して紹介しています。

- コンバーター

    OpenAPIやその他のAPI記述形式との間で変換する様々なツール。

- データ検証ツール

    APIのリクエストやレスポンスがAPIの説明と一致しているかどうかをチェックします。

- スキーマ検証ツール

    APIのスキーマが有効なOpenAPIであるかどうかをチェックします。

- ドキュメント作成

    APIの説明をHTML(またはPDF)で表示することで、技術者ではない人でもAPIの操作方法を理解できるようにします。

- DSL

    YAMLを手で書くのは面白くないし、GUIもいらないかもしれないので、Domain Specific Languageを使って好きな言語でOpenAPIを書きましょう。

- GUI エディター

    ビジュアルエディタを使えば、OpenAPIの仕様全体を覚える必要なく、APIを設計することができます。

- 学習

    トラフィックに基づいてサードパーティのAPIのドキュメントを取得しようとしている場合でも、OpenAPIが全くない組織でデザインファーストに切り替えようとしている場合でも、学習はAPI仕様を前進させ、最新の状態に保つのに役立ちます。

- その他

    OpenAPIを使って何かをするその他のもの。

- モックサーバー

    スキーマを入力とし、入力されたHTTPリクエストをサンプルレスポンスにルーティングしたり、動的にサンプルを生成したりする模擬サーバーです。

- パーサー

    OpenAPIの記述を読み込み、プログラムで操作できるようにします。

- SDK ジェネレーター

    コンシューマに提供するコードを生成して、HTTPレベルでの対話を回避できるようにします。

- セキュリティ

    OpenAPI記述を詮索することで、気づかなかった攻撃ベクターを探すツールもあります。

- サーバーの実装

    API用のリソースやルートを簡単に作成・実装できます。

- テスト

    コマンドラインやGUIインターフェイスを使って、APIリクエストを素早く実行し、レスポンスをその場で検証することができます。

- テキストエディタ

    テキストエディタでは、OpenAPIの記述中に視覚的なフィードバックが得られるため、ドキュメントがどのように見えるかを確認することができます。

## OpenAPI Map

https://openapi-map.apihandyman.io/

OpenAPI Mapは、Open APIのスキーマを可視化するツールです。

こんな感じに可視化できます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/114392/507c7ae1-5937-de58-b19a-948dd2b1d13d.png)

# API Style

## API Style Book

http://apistylebook.com/

API スタイルガイドを集めたサイトです。
【エラー備忘録】SQLiteでError: SQLITE_ERROR: near ")": syntax error

##状況
SQLのcreate文を書くテスト中、デバッグを行うとエラーが出た。

##エラー内容
実際のエラー文は以下の通り。

```
Error: SQLITE_ERROR: near ")": syntax error
```
閉じ括弧")"のあたりに文法エラーがあるとのこと。

##原因・解決法
複数のcreate文を書いていたので、ひとつずつ確認する。
すると、うち一文の閉じ括弧の前に","を書いていた。
これを削除するとエラーは解消された。
Windows機でiOSアプリの開発から実機インストールまで行ってみる【ReactNative】～開発編～

[前回（環境構築編）](https://qiita.com/NAO1998/items/33f05d368f9bbd0bb741)の続きです！

#今回の作業の流れ
・ReactNativeでの開発の基本
・実際に作ってみる
・テスト及びリリースのための準備

#ReactNativeでの開発
基本的にはJavascriptを使っていきます。ライブラリも豊富で、簡単に使いやすいUIパーツを導入できるのも魅力の一つです。詳しい説明は他の方々が既に素晴らしい記事をアップしているので割愛させていただきます。
個人的に私が参考にした記事を下に貼っておきます。

https://codezine.jp/article/corner/772

Reactの基本から実際のアプリ製作までシリーズで解説しています。

https://docs.expo.io/

Expoのドキュメント。ビルドやリリース準備時にお世話になりました。

↓完成品↓
<img width=300 src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1711764/36729c68-5401-4d24-79d6-676c3ba9a22c.gif"> <img width=300 src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1711764/ea6ec80c-580f-d1d0-a014-322d0c26dc4c.gif">

`react-native-calendars`と`react-native-echarts-wrapper`というライブラリを使用しています。簡素ですがそれっぽいアプリができました。

#テスト及びリリースのための準備
まず、実機にアプリとしてインストールしたり、テスト、リリースするためには**Apple Developer Program($99/年)への登録は避けられません**
ちなみに登録後、審査を受けてアクティベートされるまでは2日～1週間程度かかるようです。私の場合は登録から4日でアクティベートされました！
![6.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1711764/55e9ebef-7a46-b710-a25f-d95077ef92b6.png)
↑アクティベートされるとこのようなメールが来ます↑


さて、本題のリリース準備ですが、App Store Connectにアップロードするためにはipaファイルを作らなければなりません。ipaファイルは`expo build:ios`で作ることができますが、そのためにはまず、**ソースコードの他に設定ファイルと画像ファイル（アイコンやスプラッシュ画像など）が必要になります。**

まずは画像ファイルから作ります。iOS向けの場合はassetsフォルダ内に`icon.png`と`splash.png`を用意する必要があります。アイコンのサイズは1024*1024が推奨されているようです。スプラッシュ画像とは、アプリを開いた瞬間に出てくる画面で、使用する端末の向きによって切り取られ方が変わります。また、いずれもExpo Goでどのように表示されるか確認できるので、ズレが無いように調整しましょう！

画像ファイルを作成したら、次は設定ファイルを作りましょう。
app.jsonを開きます。`expo`の階層に多くのプロパティがあると思いますが、加筆すべきものは`name`、`ios`、`version`、`icon`、`splash`だけでひとまず大丈夫です。詳しくは[こちら](https://docs.expo.io/versions/latest/config/app)を参照してください。

私の場合はこのように設定しました。

```json:app.json
{
  "expo": {
    "name": "My Trainer",
    "slug": "trainig-app",
    "version": "1.0.0",
    "orientation": "portrait",
    "icon": "./assets/icon.png",
    "splash": {
      "image": "./assets/splash.png",
      "resizeMode": "contain",
      "backgroundColor": "#ffffff"
    },
    "updates": {
      "fallbackToCacheTimeout": 0
    },
    "assetBundlePatterns": [
      "**/*"
    ],
    "ios": {
      "bundleIdentifier": "com.XXXXX.YYYYY.TrainingApp",
      "buildNumber": "100",
      "icon": "./assets/icon.png",
      "supportsTablet": true 
    },
    "android": {
      "package": "com.XXXXX.YYYYY.TrainingApp",
      "versionCode": 100,
      "icon": "./assets/icon.png",
      "adaptiveIcon": {
        "foregroundImage": "./assets/adaptive-icon.png",
        "backgroundColor": "#FFFFFF"
      }
    },
    "web": {
      "favicon": "./assets/favicon.png"
    }
  }
}

```
`expo.ios`の`bundleIdentifier`は他人と被らない唯一無二のものを設定する必要があります。また、アンダースコア（_）ではなく、ハイフン（-）を使うという点にも注意してください！

お疲れさまでした！これでipaファイルを出力するための準備ができました！
次回は実際にApp Store Connectへの登録と内部テストとしての実機へのインストール、リリースまでを行いたいと思います！

それでは～！

[次回（実機インストール編）](https://qiita.com/NAO1998/items/890b2cfbbcc170a0a5ec)
[Ruby] 正規表現matchメソッドの応用①

##はじめに
今回はRubyで正規表現を利用するmatchメソッドの応用を紹介します。


##パスワードの文字数に制約を設定する
matchメソッドでを使って、登録するパスワードに「英数字8文字以上かどうか」をチェックしてみます。大文字小文字はどちらも入力可能とします。
まずは例を見てみましょう。

```irb:ターミナル
irb(main):001:0> pass = 'Hoge1234'
=> "Hoge1234"

irb(main):002:0> pass.match(/[a-z\d]{8,}/i)
=> #<MatchData "Hoge1234">
```

パスワードを7文字にするとどうなるでしょうか。

```irb:ターミナル
irb(main):001:0> pass = 'Hoge123'
=> "Hoge123"

irb(main):002:0> pass.match(/[a-z\d]{8,}/i)
=> nil
```

nilが返ってきました。irbの００２の記述で8文字以上かどうかが確かめられているのが分かります。
さて、わからないのはmatchの後ろの記述がどういう意味かですね。
一つずつみてみましょう。

先ほどの表現は下記の4つに分けられます。
それぞれに意味があります。

**・[a-z]**
**・\d**
**・{n, m}**
**・i**


##[a-z]
各括弧[]の中文字のうちのどれか一つがマッチするかどうかを確認できます。ハイフンを使うことで範囲的に設定することもできます。[a-z]はアルファベットでaからzまでのどれかにマッチするかどうか、という意味です。

aからcまでの英数字の抽出をしている例を見てみましょう。

```irb:ターミナル
irb(main):001:0> 'dog'.match(/[a-c]/)
=> nil
```

dogにはa,b,cどれもマッチしていないのでnilが返ってきています。

## /d
dというのは数字を表しています。これは特殊文字と言われるものの一つです。特殊文字を使うときは、直前に/を記述する決まりがあります。

先ほどの[a-z]と組み合わせて。**[a-z/d]**とすると、英数字の何か一つにマッチするかどうか確かめることができます。

/dを単体で使用する（数字だけを抽出する）例です↓

```irb:ターミナル
irb(main):001:0> 'I have 3 pens'.match(/\d/)
=> #<MatchData "3">
```
##{n, m}
n, mに数字を入れて使います。直前の文字が少なくともn回、多くてもm回出現するものにマッチすることを確認します。
これを使えば文字数の制約をかけることができます。

[a-z/d]{,8}という記述は英数字のどれかが少なくとも8回出現するものにマッチという意味です。

数字が少なくとも4回、多くても6回出現するものを確認する例です↓

```irb:ターミナル
irb(main):001:0> '12345678'.match(/\d{4,6}/)
=> #<MatchData "123456">

irb(main):002:0> '123'.match(/\d{4,6}/)
=> nil
```

## i
最後にオプションでiを加えることで、大文字と、小文字を区別せずに検索できます。ちなみに、もしiをつけなければ、[a-z]という記述は小文字なので、大文字にはマッチしません。

大文字と小文字の区別をしている例↓

```irb:ターミナル
irb(main):003:0> 'Cat'.match(/cat/)
=> nil

irb(main):004:0> 'Cat'.match(/cat/i)
=> #<MatchData "Cat">
```

##最後に
これらの組み合わせでいろんな制約をかけられそうですね。
次回もmatchの応用で、メールアドレスからドメイン部分のみを抽出する方法を紹介します。
Windows機でiOSアプリの開発から実機インストールまで行ってみる【ReactNative】～環境構築編～

こんにちは！突然ですが、このページに辿り着いた方は**「iPhone開発したい！でもMacPC持ってない！」**というお悩みをお持ちではないでしょうか？？

そんなお悩みをお持ちの方には、**ReactNativeでの開発をオススメします！！**ExpoというReactNativeの開発ツールを用いることにより、たとえ**MacPCを持っていなくともiPhoneさえあれば実機ビルドもすることが可能です。そしてテスト（実機へのインストール）段階においても徹底的にWindows機だけで行います！**（もちろんVirtualBox上でMacOSを使用することもありません）
今回の記事ではiOSアプリを作るための流れと使用ツールの説明を以下でしたいと思います！

#ReactNativeとは？
iOSやAndroid、webといった複数のプラットフォームに対応した（クロスプラットフォーム）フレームワークで、しばしば他の例としてFlutterやXamarinが挙げられます。クロスプラットフォームのフレームワークを使用して開発することにより、「iPhoneはXcodeとswiftで、AndroidはAndroidStudioとJavaで～」のようにそれぞれ別々のプラットフォームで開発する必要は無く、**JavaScript（またはTypeScript）だけでiPhoneにもAndroidにも対応したアプリが作れちゃうよ～**、っていうのがReactNativeです。

#Expoとは？
ReactNativeには開発ツールとしてExpoとReactNative CLIの二つが用意されています。**Expoでは開発サーバを立ち上げると、画面上にQRコードが出現し、スマホ実機で読み取ることで動作確認をすることができます。** ReactNative CLIはWindowsに導入する際はChocolateyを使ってインストールする必要があります。Bluetoothや音楽再生などを扱う場合はこちらを使用しましょう（カメラや位置情報を扱うのはExpoでも可能）ただ、WindowsPCでは実機デバッグやエミュレータの点でReactNative CLIを使って開発するのは難しそうです…
というわけで今回はExpoを使ってiOSアプリを開発していきたいと思います！（もちろんAndroidでも動作します）

#今回の作業の流れ
・node.jsのインストール
・Expoのインストール
・プロジェクトの作成
・実機での動作確認

#node.jsのインストール
[こちら](https://nodejs.org/ja/)からnode.jsのインストーラをダウンロードして、インストールしてください。

```powershell:node.jsのインストールが完了したか確認
node --version
npm --version
```

#Expoのインストール
npmコマンドからインストールします。

```powershell:Expoのインストール
npm install -g expo-cli
#expoコマンドが使えるか確認
expo --version
```

#プロジェクトの作成
expoを正常にインストールすることができたら、次は任意のディレクトリまで移動してプロジェクトを作成していきます。`expo init プロジェクト名`を実行するとManaged workflowとBare workflowの2種類のテンプレートを選択することができます。今回はJSを使っていきたいと思うのでManaged workflowの`blank`を選択します。

```powershell:プロジェクトの作成
expo init MyApp
#Choose a template: » blank
```
成功するとこのようになります。
![1.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1711764/d94a460e-4ffa-415a-a040-f7f8fff1f50f.png)
雛形が作成されたので、少し中身を覗いて見ましょう！
![2.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1711764/6a1802a4-ec3a-69c2-b444-61d5629819f0.png)
初期状態ではApp.jsが画面に読み込まれています。基本的にはここら辺を使って開発していきます。

次に、これを実際にお手持ちのiPhoneで開いてみたいと思います。

#実機での動作確認
まずはApp storeからExpo Goをダウンロードしておきましょう！

https://apps.apple.com/jp/app/expo-go/id982107779

次に、プロジェクトのあるディレクトリに移動して、`expo start`で開発サーバを立てます。

```powershell:開発サーバを立てる
cd MyApp
expo start
```
すると、ブラウザとターミナルにこのようなQRコード付きの画面が出現すると思います。
CONNECTIONで「LAN」を選択している場合は、**お使いのPCとスマホが同じネットワークに繋がっている（共通のwi-fiを使っている）必要があります。**また、Expoが誤ったIPアドレスを認識している可能性があるのでよく確認してください（私の場合はHAMACHIがオンラインになっていたので間違ったネットワークに繋がっていました）
ちなみに、どうしても別々のネットワークじゃなきゃダメ！という場合は、「Tunnel」を選択してビルドしてください。ただし、ビルドも更新も時間がかかるので使い勝手が悪いです…
![3.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1711764/6f8de603-0eaf-a3ef-6650-652d60740f53.png)
これをiPhoneのカメラで読み取り、現れたリンクからExpo Goへと飛びましょう！
ビルドが完了し、App.jsにあるテキストが表示されれば成功です！
<img width=400 src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1711764/67fc03bd-e8f5-f47e-2bce-d61c4e440a07.png">
お疲れさまでした！次回は実際にアプリを作っていきたいと思います！
それでは～～！:wave::wave:

[次回(開発編)](https://qiita.com/NAO1998/items/ef37009849917e3e56ff)
PHP 可変関数を体験してみた

# 目的

- PHPの可変関数を体験してみたのでメモを残す

# 情報

- 下記のリンク先を用いて本記事に記載の内容の動作確認を行った。
    - [https://paiza.io/ja](https://paiza.io/ja)

# 方法

- まず通常の関数をもちいて簡単な動作を定義してみる。
- 下記に引数1と引数2の数字を足して返す関数`add()`を定義する。

    ```php
    <?php

    function add(int $num_1, int $num_2){
        return $num_1 + $num_2;
    }

    $returnInt = add(1, 4);

    printf($returnInt);
    ```

- 上記を実行すると「5」が出力される。
- 先に記載した処理を可変関数の振る舞いに習って呼び出し部分を修正してみる。

    ```php
    <?php

    function add(int $num_1, int $num_2){
        return $num_1 + $num_2;
    }

    $funcName = 'add';
    $returnInt = $funcName(1, 4);

    printf($returnInt);
    ```

- 上記を実行すると結果は変わらず「5」と出力される。
- 可変関数とは関数名を予め変数に格納しておき`$関数名を格納した変数名(引数)`を実行することで関数を実行しているのと同じようにすることである。
Power Query で 空のテーブルを出力する

row type と table type の扱いを忘れてしまうのである。まぁ、詳しい説明もないですしね。
ソースになるテーブルが存在するのであれば、Value.Type( *table* ) で取得できるからよいのだけど、うーん使うかもということがたまにあるので。

**列名とそのデータ型を用意して Table.AddColumn で 列を追加する**

```text
let
    _Fields = {
        [ Name = "Column1", Type = Text.Type ],
        [ Name = "Column2", Type = Int64.Type ]
    },
    InitialTable = #table( null, {} ),
    EmptyTable = List.Accumulate(
        _Fields,
        InitialTable,
        ( state, current ) => Table.AddColumn(
            state,
            current[Name],
            () => null,
            current[Type]
        )
    )
in
    EmptyTable
```

**row type と table type を 定義する1**

```text
let
    _Fields = [
        Column1 = [ Type = Text.Type, Optional = false ],
        Column2 = [ Type = Int64.Type, Optional = false ]
    ],
    _RowType = Type.ForRecord( _Fields, false ),
    _TableType = type table _RowType,
    EmptyTable = #table( _TableType, {} )
in
    EmptyTable
```

**row type と table type を 定義する2**

```text
let
    _RowType = type [
        Column1 = Text.Type,
        Column2 = Int64.Type
    ],
    _TableType = type table _RowType,
    EmptyTable = #table( _TableType, {} )
in
    EmptyTable
```

# 思ったこと🙄
https://docs.microsoft.com/en-us/powerquery-m/type-forrecord

ぶっちゃけ、なんなん？この関数よね。

# その他
https://powerbi.connpass.com/

http://qiita.com/PowerBIxyz/items/6c4735cb5b5712e70981

http://qiita.com/PowerBIxyz/items/52e563037b855a099ca9

- [Power BI 勉強会 - connpass](https://powerbi.connpass.com/)
- [Power BI Desktop を使い始めるには](http://qiita.com/PowerBIxyz/items/6c4735cb5b5712e70981)
- [Excel で Power Query を使い始めるには](http://qiita.com/PowerBIxyz/items/52e563037b855a099ca9)
Webアプリ開発勉強日記１

#Webアプリの基本的な仕組み
###Webアプリとは
ユーザーごとに表示を変えるなどの動的なHTMLも返すWebサイトのこと。
Webブラウザからリクエスト情報を送り、
WEBアプリがデータベースなどと連携をして、リクエスト情報を元にレスポンス情報を返す。

###リクエスト情報の構造
１行目にリクエストライン
２行目以降はヘッダーが記述されている。

リクエストラインには
リクエストメソッドと要求しているリソースのパスとHTTPのバージョンが記述されている。

＝＞リクエストメソッドとは
Webプラウザなどから「url」の形式で、
データのやり取りなどの動きの「指令」を役割ごとにわかりやすく定義したもの。

リクエストメソッドには「GET」、「POST」、「PUT」、「DELETE」がある。
他にもあるが今回は割愛。

＝＞要求しているリソースのパスとは
Webブラウザが「このページ頂戴」言った場合の「このページ」のパス。
説明下手ですみません。

ヘッダーは「フィールド名：値」という形で記述される。

##レスポンス情報の構造
レスポンス情報の構成は１行目にステータスライン
２行目にヘッダーが記述される。

ステータスラインには
HTTPバージョンとステータスコードと説明フレーズが記述されている。

＝＞ステータスコード説明フレーズとは
レスポンス情報を取得しに行った結果
成功したのか、アクセス権限がなくて失敗したのかなどの状況を意味する。

「２００（ステータスコード）　OK（説明フレーズ）」
は成功していることを意味する。


#Webアプリの処理の流れ
Webアプリはさまざまなサーバーと連携しながら構成される。

＝＞サーバーとは
外部からの要求に対して処理結果などを返す働きをするコンピューターやソフトウェアのこと。

１例としてWebサーバー、APサーバー、データベースの3つで構成されたWebアプリがあるとして、
Webブラウザからリクエスト情報を受け取った場合の流れはこうなる。

①Webサーバーはリクエストの窓口のような役割をして、
　必要に応じてAPサーバーに処理を依頼する。

②APサーバーはデータベースと連携をして、Webサーバーに処理を返す。

③Webサーバーは受け取った処理をレスポンス情報として、Webブラウザに返す。
AWS LambdaでAWS Systems Manager(SSM)のAWS-RunShellScriptを実行する(Node.js)

## 行おうとしたこと
LambdaのTest実行から、EC2インスタンス上のシェルスクリプト(/home/ec2-user/hoge.sh)を実行する。
## 前提
Lambdaのランタイム設定 Node.js 12.x、ハンドラindex.handler。
SSM 高速セットアップ実行をして、EC2にSSMから操作されるロールが設定済み。
## ポイント
Lambdaのhandlerはasyncにしない、asyncだとLambdaでエラーがでていないのにindex.jsのssm.sendCommandが実行されていないような状態になる。

Lambdaの実行ロールにAmazonSSMMaintenanceWindowRoleを設定する、AmazonSSMFullAccessではindex.jsのssm.sendCommandで権限エラーがでました。

## Lambdaのindex.js
```
const AWS = require('aws-sdk')
 
exports.handler = (event) => {
    console.log('始まってます');
    const ssm = new AWS.SSM();
    ssm.sendCommand({
        InstanceIds: ["{インスタンスID}"],
        DocumentName: "AWS-RunShellScript",
        Parameters: {
            commands: ["/home/ec2-user/hoge.sh"]
        }
    }, (err, data) => {
          if (err) {
              console.log('エラーです');
              console.log(err, err.stack);
              return err
          } else {
              console.log('成功です');
              console.log(data);
              return data.CommandId;
          }
    });
    console.log('終了');
};
```

## Execution results
```
Test Event Name
hoge

Response
null

Function Logs
START RequestId: 9a3d4c84-7fba-4dc3-9310-4f9025632940 Version: 1
2021-07-04T12:05:10.289Z	9a3d4c84-7fba-4dc3-9310-4f9025632940	INFO	始まってます
2021-07-04T12:05:10.570Z	9a3d4c84-7fba-4dc3-9310-4f9025632940	INFO	終了
2021-07-04T12:05:10.820Z	9a3d4c84-7fba-4dc3-9310-4f9025632940	INFO	成功です
2021-07-04T12:05:10.820Z	9a3d4c84-7fba-4dc3-9310-4f9025632940	INFO	{
  Command: {
    CommandId: '51e98cb1-7a46-4cac-92c2-39468407a837',
    DocumentName: 'AWS-RunShellScript',
    DocumentVersion: '$DEFAULT',
    Comment: '',
    ExpiresAfter: 2021-07-04T14:05:10.791Z,
    Parameters: { commands: [Array] },
    InstanceIds: [ 'i-0e7108f51709dc4c0' ],
    Targets: [],
    RequestedDateTime: 2021-07-04T12:05:10.791Z,
    Status: 'Pending',
    StatusDetails: 'Pending',
    OutputS3BucketName: '',
    OutputS3KeyPrefix: '',
    MaxConcurrency: '50',
    MaxErrors: '0',
    TargetCount: 1,
    CompletedCount: 0,
    ErrorCount: 0,
    DeliveryTimedOutCount: 0,
    ServiceRole: '',
    NotificationConfig: {
      NotificationArn: '',
      NotificationEvents: [],
      NotificationType: ''
    },
    CloudWatchOutputConfig: { CloudWatchLogGroupName: '', CloudWatchOutputEnabled: false },
    TimeoutSeconds: 3600
  }
}
END RequestId: 9a3d4c84-7fba-4dc3-9310-4f9025632940
REPORT RequestId: 9a3d4c84-7fba-4dc3-9310-4f9025632940	Duration: 694.41 ms	Billed Duration: 695 ms	Memory Size: 128 MB	Max Memory Used: 92 MB

Request ID
9a3d4c84-7fba-4dc3-9310-4f9025632940
```
【個人開発】Node.jsを使用したWebサイトの構築

# はじめに
半年間かけNode.jsを使用したWebサイトの構築を行いました。おすすめの飲食店の紹介サイトみたいなものです。この記事ではWebサイトの進め方や使用した技術について紹介していきます。
環境の構築方法は以下の記事にて紹介しています。

https://qiita.com/nacho0707/items/94a181663a14def11e5b

前回作成した占いサイトよりは機能は縮小しております。

https://qiita.com/nacho0707/items/3ef87f412be7b92b9d33

# 設計
![pasted-2021.03.31-13.26.49.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/700107/e7bdb6f1-49bd-07b0-9fe0-b0d2f24d372d.png)

今回はXDを使用し画面イメージを作成しました。XDにも慣れていなかったので勉強しつつ進めていきました。また、Node.jsにも慣れていなかったため簡易的なサイトとしました。


# トップ画面
![スクリーンショット 2021-07-04 18.34.28.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/700107/56c42003-693a-c36c-8c65-d043dd26df0d.png)

設計の時とはちょっと違う雰囲気のトップ画面となりました。また、メニューはハンバーガーメニューを想定していたのですが、意外と難しそうであったというのと「ハンバーガーメニューは古い？」というような記事をいくつか見たので変更しました。
メニューは常に画面上部に表示するようcssの「positon:fixed;」を使用しました:point_up_tone1:
また、今回は１ページに収めたので、メニューの項目を押下後にページ内スクロールするように設定しました。設定方法は以下です。

**遷移先の設定**
idを付与します。

```html
<div id="newPost"></div>
```

**遷移元の設定**
aタグのhref属性に「#」 + 「遷移先に設定したid」を設定します。

```html
<li>
  <a href="#newPost">NEW POST</a>
</li>
```

# NEW POST画面

![スクリーンショット 2021-07-04 20.49.24.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/700107/65ff061f-2a7d-155a-760b-6276774900bb.png)

一番新しく投稿されたお店の紹介画面です。更新日時はhtmlに直書きです:ghost:。。
画像を押下するとお店の詳細が記載されているSHOP LIST画面に遷移します。

# SHOP LIST画面
![スクリーンショット 2021-07-04 20.50.12.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/700107/a2be8fbc-43e8-e17c-7358-8cc538d1e87f.png)

お店の一覧が表示されます。画像を押下するとホットペッパーグルメのお店のページに遷移します。
次に、GoogleMapの画面への表示方法を紹介します。
①GoogleMapにて表示したいお店の住所を入力。
②共有ボタンを押下する。
③地図を埋め込むタブを押下し、HTMLをコピーと書いてある文字を押下する。
![スクリーンショット 2021-07-04 21.17.34.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/700107/fa4d24e0-236c-d740-d955-62cb776537ed.png)

簡単にできました:relaxed:！

# その他
![スクリーンショット 2021-07-04 20.59.34.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/700107/c7da3d85-9036-f5bf-6c38-5b0d53c733f2.png)

今回はファビコンを作成してみました！より本物のwebサイトチックになったと思います。簡単に作成できましたが、マウスで絵を書くところだけは苦戦しました。。

# さいごに
NetlifyにNode.jsの環境を構築するところでだいぶ苦戦し、Webサイトは出来ないかと思いましたが、なんとか形にすることができてよかったです。しかし、環境の設定はほとんどweb上のものをコピーしただけだったので、あまりNode.jsに触れることがなかったことが少し心残りです:disappointed_relieved:今後はこのサイトに機能を少しづつ追加していき、Node.jsの理解を深めていきたいと思います！
CloudFrontでLambda@Edgeを使ってURLを書き換える

## 説明
- CloudFrontだけでは、URL書き換え、リダイレクト、ヘッダー追加、Basic認証などの細かいところはできない
    - そのため、CloudFrontからLambda@edgeへリクエストをバトンタッチすることで、リクエストの細かい内容をごちゃごちゃいじることができる

## CloudFront

### behevier設定
- `https://vamdemic/test/`にきたら、こちらの設定が適用される
- `lambda@edge`設定部分を`Viewer Request`にして、Lambda@edgeのバージョン含めたARNを設定をする
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/293481/7ef8edd1-22ca-ca08-b0b5-db88524c8d52.png)


## lambda
- CloudFrontからlambda@edgeを利用する場合、バージニアリージョンに配置する必要がある
- とりあえず、バージニアリージョンに配置しておけばOKかも

### スクリプト

- `https://vamdemic/test/3333` だったら`https://vamdemic/test/1` へリダイレクト
- Nodejs12

```js
'use strict';

exports.handler = (event, context, callback) => {
	const request = event.Records[0].cf.request;
	request.uri = request.uri.replace(/\/[0-9]+/, '\/1');
	callback(null, request);
};
```

### 設定

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/293481/df420e17-97ec-c2e0-702b-43e78b5702f3.png)

## 参考
https://techblog.zozo.com/entry/lambda-edge
https://oji-cloud.net/2021/01/06/post-5915/
【LPIC】LPIC-2 202を受ける方へ

# はじめに
2021年6月にLPIC202(v4.5)に合格したので、私の勉強方法についてまとめます。
私自身、他の方の合格体験記を励みに勉強していたので、これから受験する方の一つのサンプルになれば幸いです。

201に関してはこちらの記事にまとめています。


https://qiita.com/rocketboy555/items/6ebb62ada16031d9ef90

# LPIC202とは
ここに訪れている方には説明不要かと思いますが、簡単に説明します。
LPICとは、LINUX OSに対する知識を問うLPI認定資格です。
LPICにはLevel1〜3まであり、Level3までいくためには、Level1から順次取得していく必要があります。
Level2の認定を受けるために当記事の試験である202および、201の二つの試験に合格する必要があります。

# 筆者スペック
個人的に、合格体験記に筆者スペックが書いてあると自分と照らし合わせて考えられるので、なかなか好きな欄です。
このくらいのバックグラウンドの人が、このくらい勉強して合格したんだな、といった指標にもなると思うので、一つのサンプルとしてご査収ください。

|項目|内容|
|:---|:---|
|職業|地方の独立系SIer勤務4年目。|
|Linux経験|業務で一年ほど。Linuxベースシステムのミドルウェア開発。|
|他経験|制御系システム開発（C言語）。最近はパブリッククラウドでのインフラ設計・構築。|
|学歴|地方国立理系卒（非情報分野）|
|年齢|28歳|
|保有資格|基本情報技術者 / LPIC1 / LPIC201 / AWS系 / Azure系|
|家族構成|配偶者有り。1歳の娘持ち。|


# 勉強期間
大体2ヶ月です。
１日の勉強量は測定していませんが、1〜3時間くらいだったと思います。
勉強しない日もままありましたね。
時間ではなく、今日はここまで、と目標を区切って勉強を進めました。
娘がまだ1歳ということもあり、本格的に勉強に充てられる時間は22時〜24時でした。
計画大事。

# 使用教材
|#|教材|概要|
|:---|:---|:---|
|1| Linux教科書 LPICレベル2 Version 4.5対応 |その見た目から小豆本と呼ばれている。LPICという試験において、教科書という位置付けで根強い人気がある。試験の中身をざっと理解するために使用した。|
|2|Ping-t|有料のWeb問題集。LPIC201まではこれと小豆本のみでいけるほど、私の中では実績がある。ただし202試験は他試験と若干毛色が異なるため、Ping-tの他に白本を使用した。|
|3|Linux教科書 LPICレベル2 スピードマスター問題集 Version4.5対応|その見た目から白本と呼ばれている。LPIC201までは白本は使用してこなかったが、202試験の他の合格体験記を読むと、この本のおすすめ度が非常に高かったため、試験10日前から実施した。**これが本当に優れもので、巻末の模擬試験から同様の問題が本番試験で多数出題された。**LPIC202に関しては、自らの実感として**この教材は非常におすすめできる。**|

# 勉強方法
### サマリー
|#|内容|期間|
|:---|:---|:---|
|1|小豆本 一周|10日|
|2|Ping-t 一周目(全てヒット)|7日|
|3|Ping-t 二周目(全てコンボ）|7日|
|4|Ping-t コマ問一周|2日|
|5|白本 一周目|7日|
|6|白本 二周目|3日|



### 1.小豆本を読む（約10日）
まずはLPICお馴染みの小豆本で、内容をさらっと理解します。
正直内容は全然頭に入ってこなかったです。
**ここでは、内容の完璧な理解は意識していなくて、こんなものがあるんだなーくらいで全体像を掴むことを意識しました。**
試験範囲を理解することが重要です。

### 2.Ping-t 一周目(全てヒット)(約7日)
LPICお馴染みのPing-t。
各章の単元ごとに、10問ずつを1セットとして解いていきました。**最初は全然解けないかもしれませんが、心配はいりません。**
ここで重要なのは、解説までしっかりと目を通すことです。202は暗記だけで合格することは難しいと思います。

### 3.Ping-t 二周目(全てコンボ)(約7日)
一周目は各章ごとに行いましたが、今回は全章をランダムに10問を1セットとして解いていきました。前半の章などは結構忘れてしまったりするので、解説もそれなりに目を通します。
大体1日100問をコンボにすることを目標にしていました。

### 4.Ping-t コマ問一周(約2日)
**意外とやらない方も多いようですが、私としてはこれに毎度助けられている気がします。**
コマ問は、各章ごとに一周で良いのでやった方がいいと思います。
選択式の問題だと、コマンドやパスなどが曖昧な記憶になってしっている状態かと思います。
コマ問を一周するだけで頭の整理と記憶の定着が出来た感がありました。
もちろん最初は全然解けないかもしれませんが、それだけ記憶が曖昧だったと自覚して、頑張って一周はしましょう。

### 5.白本一周目 (約7日)
Ping-tで単語の意味は理解できている状態かと思います。
白本を読み、点と点を線にしていきました。
Ping-tで全部コンボにしたからといって白本でも余裕で問題が解けるかというと、意外とそういうわけではなく、結構解けない問題があったりしました。
一つ一つの問題の解説に目を通しながら、ざっと一周しました。
巻末の模擬試験も実施しました。
本試験はPing-tよりも白本に近いような問題が出るような気がします。

### 6.白本二周目 (約3日)
試験直前の追い込みとして、白本の二周目を行いました。
試験範囲が広いため、正直ここまでやってきても自信はなかったですね。

# 結果
https://twitter.com/rocketboy555/status/1403889989855760386?s=20

700/800点で合格でした。
試験前はあまり自信なかったですが、なかなか高得点を叩き出せました。
白本で見たことあるような問題が多かったので、白本すげー、と思って解いていました。
コマンドの問題は5問くらいだったと思います。Ping-tのコマ問よりは圧倒的に簡単でした。
オプションは問われることはなく、コマンド単体を答えるだけのものが多かった印象です。


# おわりに
無事201と202に合格できたのでLPIC Level2認定となりました。
今後202試験を受ける人の参考になればと思います。
年内にLevel3まで取得する予定です。
マイコーディングルール

# 概要
typescriptを想定した自分の中でのコーディング規約をのせておきます。


# ルール

- マジックナンバーを使用しない
    - 定数として宣言しておく

```
// ×
switch(shirtColor) {
  case 1:
    function1()
  csse 2:
    function2()
}
// ○
const BLUE = 1;
const BLACK = 2;
switch(shirtColor) {
  case BLUE:
    function1()
  csse BLACK:
    function2()
}
```

- フラグは否定を使用しない
    - `isNotPlaying`: ×
    - `isPlaying`: 〇
- if/else文のif(・・・)の中の条件式は否定文を使用しない
    - ×：`if(a !== b){}else{}`
    - ○：`if(a === b){}else{}`

- メソッド名関数名の接頭語は動詞
    - function changeName(oldName, newName){...};
  
- サイズ、時間はアンダースコアの後に単位をつける
    - `const startTime_ms = 1000;`
 
- クラスのプライベート変数はアンダースコアから始めない
    - `private userId = ''`

- if文のネストは原則禁止
    - 早期リターンを使用し、ネストを回避

```
// ×
if(os === 'windows') {
  if(browser === 'chrome') {
    function1();
  }
}

// ○
if(os !== 'windolws') {
  return;
}
if(brower === 'chrome') {
  fucntion1();
}

```

- 名前は省略しない
```
// ×
let userinfo;
// ○
let userInformation;
```

- 三項演算子は原則使用しない
    - if文を使用

- 後でやるべきことは不具合などあるときは以下のコメントで残す

```
// TODO; 後でやるべきこと
// FIXME; 不具合がある
// HACK; 良い方法ではない
```

# 参考
オライリージャパン 「リーダブルコード-よりよいコードを書くためのシンプルで実践的なテクニック」 Dustin Boswell 他
タスクマネージャ [パフォーマンス] タブのグラフ更新が止まる件について

~~ポエムの時間だオラァ！~~


####状況の整理
　・タスクマネージャーの更新頻度の設定が いつの間にか [一時停止] に変更されている
　・比較的多くの人が同じ問題を抱えており、ウィルスやシステムファイル破損とは考えにくい
　・おそらくICCMon.exeのやつとは別件


####世界で初めて映像で捉えることに成功
うちの自作PCにOCを頑張ってもらいましたｗ

![新しいビットマップ イメージ2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1698056/b9ff6f91-8af7-2f5d-db97-8b6b5297cb0d.png)

左はWindows Sandbox　右はホストのタスクマネージャーです
CPUのクロック周波数に注目
「あっ！ 何か懐かしい誤取得してるな。」とか思って貰えたら投稿した甲斐がありますｗ


####参考資料

クロック周波数の測定手法 - Crystal Dew World
https://crystalmark.info/special/clock.html

　動的可変するCPUのクロック周波数を正確に取得するのは難しいようです
　当時、この手のアプリで 可変CPUのクロック周波数を安定して表示させるのに苦労したので…
　　（ありえない値を取得して測定が止まるとか日常茶飯事）


####タスクマネージャーの挙動について考察
　・取得した周波数を元にCPU使用率などのグラフ描画データを生成してるのは確定的に明らか
　・何かのタイミングで異常な周波数を取得した時に、処理が停止するのでは？
　・周波数測定の手法にも改善の余地があるかと…

　　これ「Microsoftの中の人」じゃないと直せないやつだ…