OmniAICreator/Qiita-1.07M huggingface dataset:
Excelで組み合わせ表を作成するマクロ

## サンプル

### 数値サンプル

0,1,2の5つの組み合わせパターン243通りが出力されます。

![組み合わせパターン.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/584743/da88c72b-f276-e126-2351-8a01885e476e.png)

### 文字サンプル

文字でも作成可能です。

![組み合わせパターン.2PNG.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/584743/d494a64c-4305-85a8-78d2-36f41c3061c3.png)

## 使用法

`CCW`が列数。
`v = Array(0, 1, 2)`が組み合わせる値。

文字バージョン
`v = Array("あり", "なし")`


```vb
Option Explicit

Public Sub Sample1()
    Dim rng As Range
    Dim v As Variant
    Dim i As Long, j As Long, k As Long
    
    Const CCW As Long = 5 ' 列数
    v = Array(0, 1, 2)    ' 組み合わせの値
    
    k = UBound(v) - LBound(v) + 1
    
    Application.ScreenUpdating = False
    Cells.Delete
    With Range("A1").Offset(, CCW - 1).Resize(k)
        .Value = WorksheetFunction.Transpose(v)
        Set rng = .Cells
    End With
    For j = 1 To CCW - 1
        For i = LBound(v) To UBound(v)
            With rng.Offset((i - LBound(v)) * rng.Rows.Count)
                If (i > LBound(v)) Then rng.Copy .Cells
                .Columns(1).Offset(, -1).Value = v(i)
            End With
        Next
        Set rng = rng.CurrentRegion
    Next
    Application.ScreenUpdating = True
End Sub

```
Lintの使い方

rubocopとは慣習的でないRailsのコードを発見し、それを簡単に修正してくれる便利なツール。

rubocopの正誤表を見るには、```EmptyLinesAroundClassBody```でgoogle検索をかける。もしくは下のURL。

```
https://www.rubydoc.info/gems/rubocop/RuboCop/Cop/Layout/EmptyLinesAroundClassBody
```

Rubocopでテストを実行するにはターミナルで
```
bundle exec rubocop
```
を実行する。

rubocopは間違いを自動的に修正してくれるコマンドがある。
```
bundle exec rubocop --auto-correct
```
これでほとんどの間違いは解消してくれる。

上のコマンドでも解消してくれない例もある。例えばif文などである。
その場合は手動で修正する必要がある。
Sheet表示時にインスタンスが複数生成されてしまう時には

# 前書き
なんで何回も呼ばれるんや！！！
initすな！！！
なんのためのStateObjectや！！！と思い調べました。

備忘録としてですがめちゃめちゃ困ったので同じ事象で困っている人のためになれば嬉しいです。

確認OS:iOS14.1~15.4
DeploymentInfo :iOS14.1

# 結論
これを追加するだけ
``` 
//呼び出されるViewの方で使用しなくてもこれを宣言しましょう
@Environment(\.presentationMode) var presentation
```

# 発生するときのサンプル
``` 
import SwiftUI

struct BaseView: View {
    @State var showSheet: Bool = false
    var body: some View {
        Text("テスト!")
            .padding()
        Button("モーダル表示", action: {
            self.showSheet = true
        })
        .sheet(isPresented: $showSheet, content: {
            SheetView()
        })
    }
}

struct SheetView: View {
    init() {
        print("init呼ばれたよ")
    }
    var body: some View {
        Text("シートビューだよ")
            .padding()
            .onAppear(perform: {
                print("View appeared")
            })
    }
}
```
こういう時にBaseViewでボタンをタップするとSheetViewのinitが何度も呼ばれるケースがあります。
サンプルのケースではinitでprintしているだけなのでいいのですが（良くない）、一度しか初期化したくない@StateObjectを使用している時にも何度もインスタンスが作成されることで初期化されてしまいます。

#対応したサンプル
``` 
import SwiftUI

struct BaseView: View {
    @State var showSheet: Bool = false
    var body: some View {
        Text("テスト!")
            .padding()
        Button("モーダル表示", action: {
            self.showSheet = true
        })
        .sheet(isPresented: $showSheet, content: {
            SheetView($showSheet)
        })
    }
}

struct SheetView: View {
　　　　　　　　@Environment(\.presentationMode) var presentation
    @Binding var showSheet:Bool
    init(_ showSheet:Bool) {
        print("init呼ばれたよ")
    }
    var body: some View {
        Text("シートビューだよ")
            .padding()
            .onAppear(perform: {
                print("View appeared")
            })
        Button("モーダル閉じる", action: {
            self.showSheet = false
        })
    }
}
```


これだけです。
どうやらiOS側のバグのようです。
WPScanを使いたい

セキュリティチェックツールWPScanを使いたい
どうも、maruです。
最近サイトの設定をちょこちょこいじってます。メンテナンスってやつですね。
そのメンテナンス中にサイトのセキュリティのことが気になって来ました。
このサイトではWordPressを使っているんですが、WordPressの脆弱性とかWordPressの改ざんってよく聞くキーワードだと思います。
そこで、自分のサイトに脆弱性がないか確認するために何か良いツールはないかなと探しているうちにWPScan（WordPress Security Scanner）というツールに行き着きました。
WPScanは指定したサイトのスキャンを行い、脆弱性の有無についてチェックしてくれるというセキュリティチェックツールです。これで、自分のサイトをチェックして脆弱性を見つけてみようという話です。

Windows環境でWPScanを使う方法
WPScanの使い方を調べていたのですが、どうもLinuxベースで使うツールのようなんですね。
Windows環境のままWPScanを使う方法はないかなーと調べていると、Dockerを利用すれば可能であることが分かりました。最近、よく聞きますよねDockerって。ここでついでにDockerについて学んでみようと思いました。

Dockerについて
Dockerとは、Docker社が提供しているコンテナ技術を利用して仮想環境を構築できるシステムです。
例えば、仮想環境といえば、VMwareがありますが、VMwareではゲストOSを作成した上で仮想環境を構築します。Dockerでは、ゲストOSの構築は不要で、ホストの中で別のマシンが動いているかのように動かすことができます。
今回のように、Linuxで使うツールが必要だけど、Linux環境まで構築するのは面倒だと言う場合に使うことができるという、お手軽さがありますね。

Dockerのダウンロード、インストール
まずはDocker社の公式サイトからWindows用のDockerインストーラをダウンロードします。

Dockerインストーラをダブルクリックだけでインストールが完了します。

さあ、これでWindowsでDockerが使えるぞと思い、Dockerを起動してみましたが、デスクトップ上に何やらエラーメッセージが表示されました。

Docker Desktop – Access denied
You are not allowed to use Docker 
You must be in the “docker-users” group
うーん、どういう意味でしょうか。

ネットで調べたところ、docker-usersグループに使用中のWindowsのユーザアカウントが
追加されていないのが原因のようですね。

管理者権限でDockerを使っていれば、このようなエラーメッセージは出ないかと思います。しかし、管理者以外のアカウントでDockerを利用するのであれば、そのアカウントをdocker-usersグループに追加する必要があるわけですね。

docker-usersグループへのユーザアカウントの追加

まず、Windowsマークを右クリックでコンピュータの管理を開きます。
起動したコンピュータの管理画面からローカルユーザとグループを選びます。
ユーザーとグループという２つのフォルダが表示されるので、グループを選択します。
続いて、グループの一覧の中からdocker-usersを選択します。
docker-usersのプロパティ画面が表示されるので、追加を選択します。
追加画面で追加したいオブジェクト名（ユーザ名）を入力して、OKを押します。
これでプロパティ画面にユーザが追加されます。


改めてDockerをインストール
ユーザを追加した状態で改めてDockerを起動します。
起動した際にDocker Desktop stopping…とのメッセージが画面に表示されているので、まだDockerが動いていないことが分かります。

WSL 2 installation is incompleteというエラーメッセージが出る
Dockerの起動後、WSL 2 installation is incompleteというエラーメッセージが表示されます。
WSLとはWSL（Windows Subsystem for Linux）の略で、Windows上でLinuxを使うことが出来るシステムでのことです。WSL2とはWSLの最新バージョンのことですね。
このエラーメッセージは、このWSL2のインストールが完了していませんという意味ですね。
エラーメッセージ内のリンクhttps://aka.ms/wsl2kernelをクリックすると、Microsoftの公式ページに移動するので、
ここからさらにx64 マシン用 WSL2 Linux カーネル更新プログラムパッケージのリンクをクリックします。
リンクをクリックするとwlsのアップデート用パッケージがダウンロードされるので、このパッケージを実行します。
後は、Linuxのペンギンちゃんの指示に従って、WSLのアップデートを行ってください。

Dockerの起動
ここまでの設定が終わると、Dockerのエラーメッセージが消え、Get Started with Docker in a few easy steps!（あとわずかな手順でDockerを始めることができます）という画面表示となり、設定完了まであと少しです。

このままDockerの設定ウィザードに従い、初期設定を進めていきましょう。

初期設定が終われば、Dockerのメニュー画面が表示されます。これでDockerのインストール作業は完了です。

PowerShellでDockerを動かしてみよう
PowerShellを起動し、コマンドdocker versionを入力します。
Dockerが正しくインストールされていれば、ここでDockerのバージョン情報が表示されます。

ついでに、コマンドdocker run hello-worldと入力し、公式で用意されているhello-worldコンテナを実行してみました。
コンテナとは、アプリやミドルウェアを入れた箱です。１つのOS上で様々なコンテナを自由に手軽に利用できるわけです。物流で使われているコンテナと同じようなイメージですね。

WPScanの実行
さて、WPScanを実行するまでに非常に前置きが長くなりました。
先ほどhello-worldというコンテナを実行したように、WPScanのコンテナを実行すればWPScanを利用することができます。
コマンドは、docker run -it –rm wpscanteam/wpscan –url サイトURLとなります。
無事、WPScanが起動しました。

まとめ
以上がDockerのダウンロードとインストール、WPScanの実行までの手順となります。
WPScanを使ったサイトのセキュリティ検査の状況については、いずれ記事を書きたいと思います。

https://myhobbies-blog.net/
Prometheusが乱立して一見どれかわからない問題に対応する

# Prometheusが乱立とは？

Prometheusはクラウドネイティブ時代のモニタリングツールとしてデファクトスタンダードです。

本番環境の監視はもちろん、ステージング、開発環境にも存在するのはふつうの事です。なんなら本番環境でもデータセンターごと、とかアプリケーションごとに小さなPrometheusを用意することもあります。

さて、これらのPrometeus、Web UIを見てもどれも似通っていて、上記に書いたように複数のPrometheusが存在する環境において、どれを見ているのかわからなくなることがあります。

# そんなあなたに`web.page-title`

解決策は無数にありますが、なるべく簡単なもの・・と思って調べているとPrometheusのコマンドの引数に気になるものを発見しました。

https://github.com/prometheus/prometheus/blob/v2.36.0/cmd/prometheus/main.go#L275-L276

```golang
	a.Flag("web.page-title", "Document title of Prometheus instance.").
		Default("Prometheus Time Series Collection and Processing Server").StringVar(&cfg.web.PageTitle)
```

そう、これを設定するとWebページのTitleタグの内容を指定できるのです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/100375/16817336-8747-b2b7-b5f0-7e5cc748d18a.png)

ということで、無事表示させることができました。

これでもう「どのPrometheus?!」と悩むことはなくなりましたね！

（まぁここまで書いてから、普通はURLに環境名とか入ってるから気づくよね、と思いました。まぁやり方の一つということで）
nuxt3のプロジェクトを作るには？？

## どんなコマンド？？

```
npx nuxi init [プロジェクト名]
```
```
Ok to proceed? (y)
```
と聞かれるので、「y」で送信。

nuxt2と違って、質問攻めには合わずこれだけで、
簡単にプロジェクトが作れます！！

```
package.json

"devDependencies": {
  "nuxt": "3.0.0-rc.3"
}
```
ここでバージョンが3以上にになっていればOK！

```
npm install
```
で、node_modulesを作成しましょう！

追記

```
npm build
```

こちらで、.nuxtファイルの生成も必要です！
【超効率】VSCodeで分割して移動のショートカット


## やりたいこと
`VSCode上で、左右にタブを分割、分割したタブを移動`
これを全てキーボードのショートカットでやりたい

## 結論

- タブを分割
`Ctrl`+`\`

- 左右に分割したタブの移動
左から順に1,2,3...と割り振られ、`Ctrl`+`数値`で移動が可能
(例)
`Ctrl`+`1`、`Ctrl`+`2`、`Ctrl`+`3`
メモ : claspで「Error: Looks like you are offline.」の対処方。

claspでpush、pullなどを行うエラーになって少しハマったのでメモ書き。

```:エラー内容
$ clasp pull
⠙ Pulling files…script.google.com ✖
console.developers.google.com ✖
drive.google.com ✖
console.cloud.google.com ✖
Error: Looks like you are offline.
```

# 実行環境

macOS Big Sur v11.6.6
node v16.5.0
clasp v2.4.1

# 参考リンク

[Clasp commands return offline error 90% of the time](https://github.com/google/clasp/issues/872)

# 対処法

自分の場合はclaspのバージョンが問題でした __v2.3.1__ だと問題なく実行出来きた。

```:バージョン変更コマンド
$npm install @google/clasp@2.3.1 -g
```

# その他

nodeのバージョンv14.17.5で実行できた場合もあるみたい。

## nodeバージョン変更方法

npmパッケージnを使用してバージョンを変更

```:インストール
$sudo npm install -g n
```

```:切り替え可能なバージョンの確認
$n ls-remote --all
# 出力
18.2.0
18.1.0
...
0.8.8
0.8.7
0.8.6
```
```:バージョンの切り替え
$sudo n 14.17.5
```

## 試したバージョンの組み合わせ
:::note alert
エラー
node v16.15.0
clasp v2.4.1
:::

:::note info
実行可
node v16.15.0
clasp v2.3.1
:::

:::note alert
エラー
node v14.17.5
clasp v2.4.1
:::

:::note info
実行可
node v14.17.5
clasp v2.3.1
:::
参照フィールドに表示されている項目を変更する


弊社では取引先オブジェクトの中にを売上時に使う得意先と仕入時に使う仕入先というようにレコードタイプで分けて管理しています。

この取引先を選ぶ時に間違えを無くすために、得意先ならそのお客様の担当者を表示し、仕入れ先なら仕入先コードを表示するようにしたいという話がありました。

参照項目の表示を変えるのは
単に

設定 -->オブジェクトマネージャ --> 取引先 --> 検索レイアウト -->デフォルトのレイアウト

のところで表したいフィールドの順番を変更すれば可能です。上から２つが表示されます。

しかし、得意先と仕入先で表示内容を変えるのは...

そうだ、レコードタイプで表示する中身を変える数式フィールドを作って出せばいいですね。
ということで数式フィールドを作って、２番目の位置で表示すると思った通りに機能しました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/ce061dd1-3208-9e10-2bb5-d8b7e3e7a728.png)


# 以下同じよう質問

+ [Is there a way to show the contact's email address when searching contacts?](https://trailhead.salesforce.com/en/trailblazer-community/feed/0D54S00000HkPS1SAN)

この部分の表示を変えたい
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/f5cef373-0fa4-7530-a02a-9f9fb0515a64.png)

+ [二次フィールドの明確化-連絡先へのルックアップでアカウント名を表示できない](https://trailhead.salesforce.com/en/trailblazer-community/feed/0D54S00000HDooJ)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/33ef23b1-9ff7-669f-70c1-1f3b15ecff05.png)

+ [Display field while searching](https://trailhead.salesforce.com/en/trailblazer-community/feed/0D54S00000J7Zvg)

# この場合はコンパクトレイアウトみたい

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/1a236a12-b9ef-155e-b5df-94680a01399d.png)


[Is there a way to edit the shown fields when hovering over records?](https://trailhead.salesforce.com/en/trailblazer-community/feed/0D54S00000IS8VbSAL)
PythonでCloud Functionにあげる

## ターミナルからFunctionを作成

requirements.txt

    functions-framework==3.0.0

main.py

    import functions_framework

    @functions_framework.http
    def test(request):
        return 'Hello World!'

ターミナルコマンド

    gcloud functions deploy test\
    --timeout=540 \
    --runtime python39 \
    --trigger-http \
    --project プロジェクト名

※サービスアカウントを作成していたら` --service-account サービスアカウント名`も追加
FunctionのトリガーからトリガーURLを叩いて`Hello World`が表示されたらOK！

## 最後に

ターミナルコマンドなど備忘録として作成しました。
たったこれだけで、Functionが作成できてしまうなんて...
自分はFunctionで実行して、タイムアウトエラーが起きましたので延長させました。
最大9分までは延長できるみたいなので、色々カスタマイズしてみるのも面白いです。

## 参考文献

https://cloud.google.com/functions/docs/concepts/exec#timeout
PythonでCloud Tasksを使ってみた

## Tasksを使った理由

データ量が膨大すぎたのでCloud Tasksを使って、分割させるため

## 前提
以前作成した下記記事の環境からスタート

https://qiita.com/sh19982580/items/11a918da6d1a03ddf265

## コンソール

Google Cloud PlatformのCloud Tasksから`push キューの作成`を行う
キュー名：test
リージョン：asia-northeast1(東京)

## コード

requirements.txt

    google-cloud-tasks

上記を追加

app.py

    import json
    import os
    from flask import Flask, request
    from google.cloud import tasks_v2

    app = Flask(__name__)

    values = [1,2,3,4,5,6,7,8,9]

    # tasksにセット
    @app.route('/set_tasks', methods=['POST'])
    def set_tasks():
        
        executions_data = []
        # 3つずつ分割する
        for i in range(0, len(values), 3):
            value = {"data":values[i: i + 3]}
            executions_data.append(value)
            
        for data in executions_data:
            client = tasks_v2.CloudTasksClient()
            project = 'プロジェクト名'
            location = 'asia-northeast1'
            queue = 'コンソールで作成したキュー名：test'
            parent = client.queue_path(project, location, queue)
            task = {
                "http_request": {  
                    "http_method": tasks_v2.HttpMethod.POST,
                    # TODO Runにしたら'RunのURL' + '今後の処理(例：/update)'
                    "url": 'https://localhost:0000',  
                }
            }
            task["http_request"]["headers"] = {"Content-type": "application/json"}
            task["http_request"]["body"] = json.dumps(data).encode()
            client.create_task(request={"parent": parent, "task": task})
        return "ok"

    if __name__ == "__main__":
        app.run(debug=True, host='0.0.0.0', port=int(os.environ.get('PORT', 8080)))

※ 今回はvaluesに適当な値を入れています

## 確認
1. ターミナルで`python3 app.py`を実行
1. 別ターミナルで`curl -X POST http://localhost:8080/set_tasks`を叩く
→ Cloud Tasksのコンソールで、データ3個のタスクが3つあれば良い！
今回では3つのタスク、ペイロードに`{"data": [1, 2, 3]}`らが入っていればOK！

## Tasksからデータを受け取る

    @app.route("/update", methods=['POST'])
    def update():
        tasks_data = request.json["data"]

先ほど記載した`'RunのURL' + '今後の処理(例：/update)'`で次の処理が上記
routeの`/update`から処理が可能
また、request.json["data"]でペイロードにあった`{"data": [1, 2, 3]}`らを使える

## 最後に
自分はスプレットシートの大量更新(800行以上)を行なっていたのですが、一括で更新するには時間がかかりすぎたので、Tasksを使用しました。
何か大量の処理をする場合、使えるかもしれません。

## 参考文献

https://analytics-note.xyz/programming/python-divide-list/

https://cloud.google.com/python/docs/reference/cloudtasks/latest/google.cloud.tasks_v2.services.cloud_tasks.CloudTasksAsyncClient#google_cloud_tasks_v2_services_cloud_tasks_CloudTasksAsyncClient_create_task

https://cloud.google.com/tasks/docs/creating-http-target-tasks
【Python】iniファイルの読み込み方法（ConfigParser）

簡単な例を用いて紹介。

#### iniファイル

```
[test1]
name = aaa

[test2]
name = bbb
```

#### ソースコード

```python
#!/usr/bin/python3

import configparser

config = configparser.ConfigParser()
config.read('test.config')
print(config.sections())
print(config['test1']['name'])
```

#### 実行結果

```shell
$ ./test_ini.py
['test1', 'test2']
aaa
```

色々組合せばiniファイルの値を操作できるようになる。
Google colaboratoryを用いて遺伝子クラスター比較ソフトclinkerを動かす

Clinkerは遺伝子クラスターの比較図を簡単に出力してくれるバイオインフォマティクス用のツールです。
非常に見やすく、遺伝子比較図を出力することができるので有用なツールです。

https://github.com/gamcil/clinker

一方で、PCが苦手な人には扱いにくいかもしれません。
google colaboratry 利用して比較的簡単に動作させることができるので、初心者も利用してみるといいと思います。

https://colab.research.google.com/notebooks/welcome.ipynb?hl=ja

Google colaboratoryを開きコードセルを追加します。
最初のセルに

```
!pip install clinker
```

と入力し実行します。
するとclinkerのインストールが始まります。

2022年11月21日現在、biopythonをv18.0にアップデートすると動作しないようです。
以下の操作でダウングレードします。

```
!pip install biopython==1.79
```

次に比較に使いたいgenbankファイルをアップロードします。
genbankはNCBIなどのサイトからダウンロードします。

左側のバーのフォルダボタンをクリックしフォルダを開きます。

次にアップロードボタンをクリックし必要なgbファイルをアップロードします。

次に新しいコードセルを追加し、

```
!clinker *.gb -p result.html
```

と入力し実行します。
ファイルの拡張子がgbkの場合はgbをgbkに置き換えます。
解析が終了するとresult.htmlというファイルが保存されますのでダウンロードしてください。

他に色々応用が効くと思います。


<h1>オプションの例</h1>
<h2>matrixの出力</h2>

以下のようにオプションを追加することでmatrixを指定出力することができます。
csv形式で類似度を評価した表が出力されます。

```
!clinker *.gb -p result.html -mo matrix.csv
```

以下は出力例です(タブ形式でここは記述してますが、実際はcsv形式です。)。

```
	seq1	seq2	seq3
seq1	0	0.81522588	0.731927411
seq2	0.81522588	0	0
seq3	0.731927411	0	0
```

<h2>ホモログ判定の閾値を設定</h2>
-iを使うことで、ホモログのくくりの閾値を設定することができる。

```
!clinker *.gb -p result.html -i 0.3
```

デフォルトは0.3である。identityを閾値に用いているようなので、0.2とかに設定するとかなりの遺伝子がホモログとして認定されてしまう。
下げるとしたらせいぜい0.25~0.28程度。
対象遺伝子の性質に合わせて判定すると良い。
Ruby on Railsをお勧めしたい理由

# 初めに
今僕はRailsのエンジニアとして生活しています
どんな感じかというと
Webアプリケーションを作って広告をつけて稼ぐ
といった具合
ちなみに今は独立というのか会社には所属しておらず家でやってます
ブログ等でこういう風に稼ぐ人もいるのですが僕は残念なことに文才がなくすぐにネタ切れになるタイプなのでアプリケーション開発をしようと思いました
その際に選んだのがRailsです

## Railsってなに？
プログラミング言語の1つという認識で大丈夫です
厳密には少々違いますがややこしくなるので割愛しますが
国産プログラミング言語であるRubyのパワーアップアイテムと思ってください
ものすごくざっくり言うと
>Webアプリケーションを簡単に作ってしまおうぜ！

って能力に長けています
Webアプリケーションとは？ってなる方も多いと思いますので例を挙げてみましょう
・Youtube
・ツイッター
・掲示板
・ククパッド
こう言うものです
ホームページではなくWebで何かしらできるものって認識でOK

# Railsって何が便利なの？
上記で僕は
>Webアプリを簡単に作ってしまおうぜ！

と言いましたよね
どう簡単に作れるのかを解説します

### 読んで字の如く
Railsってその名の通りレールの上を走らせる感じです
色々と自動でやってくれるのでそれに沿ってプログラムを書けばいいです
そのレールをどのように走らせるか、は自分で考えながらですがある程度規則に沿うのであまり困ることが少ないです

### gemの存在
ほぼこれがメインで書きたいこと
>gemとはプログラムの集合体

って思ってください
例えばSNSを作りたいと思いログイン機能が必要だと考えたとします
ログイン機能って作るのめっちゃ大変なんですよ
でもログイン機能を持っているgemをRailsにインストールするとあら不思議
ログイン機能が実装されちゃいます
開発効率を一気に上げることができますね
例えるなら
ピザって作るは大変だけどデリバリーすれば簡単だよね？
って感じ

### CRUDアプリが簡単に作れる
ここも結構重要
CRUDとは4つの単語の頭文字です
Create、Read、Update、Delete
メモアプリに例えてみましょう
・Createは新規メモ投稿
・Readはそれを閲覧
・Updateは投稿した質問を編集
・Deleteは削除
こういう一連の流れをもつものを作りやすいです
この流れは大手質問掲示板である「知恵袋」などと同じですね

# Railsをやってみたい！と思ったら
ここまでダラダラ書いた記事に付き合っていただきありがとうございます
もし興味を持っていただけたら嬉しいです

### 何が作りたいかざっくり決めておこう
これは目標があったほうが楽しいからです
例えば動画投稿サイトを作りたい
新たなSNSを作りとかでもOK
>え？すでにあるサービスじゃん

と思うかもしれません
いいじゃないですか
吉野家があるけど松屋もすき家もある
レブンイレブンがあるけどファミマもローソンもある
**大きな括りは一緒ですがその中で自分なりの特徴を出せばいいと思います**
動画投稿サイトなら「動物動画に特化した」とかでもなんでもいいです

### 事前知識
さて、Railsを勉強するのには事前知識が必要です
HTML/CSSは抑えておきたいですね
Web関係をするならこの二つは必須
できればJavaScriptも！と言いたいですが簡単なアプリケーションならなくても大丈夫
そしてRubyも必須
あくまでもRubyのパワーアップアイテムがRailsです
勇者(Ruby)がいないのにアイテム(Rails)を使っても効果ないですもんね

### 学習方法
https://qiita.com/rails_kaname/items/e85f9f3672b0910986af
ここに記載しています
僕はこの方法でやりましたが個人差があるのであくまでも参考程度に

# まとめ
さぁ今回もダラダラと書いてしまいました
申し訳ない
要はRailsはWebアプリ作るのには便利だよ！
と言いたいのです
学びやすいですしね

そして疑問に思われる方のためにちょっと補足
**僕みたいに自分でアプリ作ってそれだけで飯を食えるようになるって言うのははっきりいって稀です**
みんながみんなそう言うわけにはいきません
数でいえば結構な人がいると思いますがそれを目指す母数はかなり多いのでやはり稀でしょう
どうやって作ったアプリを使ってもらうかとか運とかも関係してきます
運を掴むにはまずは開発、運用ですね
その中で少しでも話題になったりすれば一気に軌道に乗ります
どうすれば話題になるかここが重要ですね
月100万！とかそんな大金ではないですが田舎で妻と娘を養える程度は稼げてます
贅沢はできませんけどね・・・。
実力も必要ですが運も必ずついて回ります
僕は運が良かったから今の生活が出来てます
だから初めは趣味のプログラミングでお小遣い稼ぎできたらな〜
という小さな目標から始めて徐々に大きくしていけばいいと思います
何事も初めからうまくいきません
継続することが大事だと思います
IBM Cloud: Watson Discovery APIを叩いてみる

# 概要
本記事では、Watson Discovery APIを**curl**を用いて叩くサンプルをご紹介します。

サンプルは、VPC内のインスタンスよりclient2siteのopenVPN経由でコマンド実行しています。
（さまざま試行錯誤してしまったので、合わせて記載します。。）

# 結論
以下のように記載します。
（GET/POSTはコマンドによって異なります。後述のドキュメントに従ってください。）
```
$ curl -X GET -u “apikey”:”[APIキー]"  "https://api.jp-tok.discovery.watson.cloud.ibm.com/instances/xxxxxxxxxxxxxxxxxxxxxx"
※ []はいらないです
```

# 注意
### バージョンが異なる
最終的に解決したのがバージョンミスでした。
Watson Discoveryは、バージョンが2種類あり、それぞれのAPIが微妙に異なります。本記事のWDはバージョン2です。
バージョン1の場合のAPI docsは[こちら](https://cloud.ibm.com/apidocs/discovery)
バージョン2の場合のAPI docsは[こちら](https://cloud.ibm.com/apidocs/discovery-data)

IBM Cloudポータルからは確認できないようで、サポートのチャットにEndpointのURLを共有したら調べてくれました。

### 401が返ってくる
```
{
  "code" : 401,
  "error" : "Invalid credentials"
}
```
以下を参考にしても分からず、、
https://cloud.ibm.com/docs/watson?topic=watson-authorization-error


### 415が返ってくる
試しに`-X POST`を追加して試した例です。
(その後`"Content-Type: Application/json"`形式で試してみましたが、401に逆戻り、、)
```{
  "status_code" : 415,
  "errors" : [ {
    "code" : "discovery_request_failed",
    "message" : "Unsupported Media Type",
    "more_info" : "https://cloud.ibm.com/docs/discovery-data"
  } ],
  "trace" : "xxxxxxxxxxxxxxxxxxxxxxxxx"
}
```

# API サンプル実行
## プロジェクトのリスト
```
$ curl -X GET -u "apikey":"[APIキー]" "https://api.jp-tok.discovery.watson.cloud.ibm.com/instances/xxxxxxxxxxxxxxxxxxxxxx/v2/projects?version=2020-08-30"
{
  "projects" : [ {
    "project_id" : "xxx-xxx-xxx-xxx",
    "type" : "document_retrieval",
    "name" : "test-project",
    "collection_count" : 1
  }, {
.
.
.
}
```

## collectionsのリスト
```
$ curl -X GET -u "apikey":"[APIキー]" "https://api.jp-tok.discovery.watson.cloud.ibm.com/instances/xxxxxxxxxxxxxxxxxxxxxx/v2/projects/[プロジェクト ID]/collections?version=2020-08-30"
{
  "collections" : [ {
    "name" : "Sample Collection",
    "collection_id" : "xxx-xxx-xxx-xxx"
  }
}
```

# 結論
#### **いち早くバージョンを確認しましょう。**
2022年6月現在、IBM Cloudポータルでは確認ができません。
すでに作成しておりバージョンを確認できない場合は、サポートチャットにてエンドポイントURLなどを共有しますと調べてくれます。
【Unity】Slider で SE の音量を変更したときに音を鳴らす



uGUI の Slider で音量調整を実装するときの話です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/9f5a2826-8778-dd69-7d2a-33abd4b48fb6.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/5cfe4a0a-76df-fa3d-fcaf-0559e7f74a61.png)
↑ こんな感じのUI

# 仕様
- マウスクリック時に、音を鳴らします
![SE01.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/811a5ec1-0e76-a3ae-bbf4-38b5c4627685.gif)
- マウスドラッグを離した時に、音を鳴らします
![SE02.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/b6095e32-66b8-2bf5-a183-1ef668ac5cf9.gif)

# 実装
パッと見だと、Slider の `On Value Changed (Single)` に音を鳴らす処理を入れれば良いような気がしますが、「マウスドラッグ中にカーソルの動きが小さいと (?) 音が連続して鳴る」という現象が発生したので、別の方法にします。

下の方法でやりました。

1. Slider コンポーネントがアタッチされているオブジェクトから Add Component をクリック
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/3236f6f1-b029-1fda-8bad-968862b737ef.png)
2. EventTrigger をアタッチ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/a0d66da2-bba9-81bf-5871-101cab05f083.png)
3. EventTrigger の `Add New Event Type` をクリック
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/4b1ebf03-ea4e-3ce3-f0da-7bb59c91e6b8.png)
4. PointerUp をクリック
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/517ba2a7-a417-71f6-c080-de706958c05d.png)
5. `Pointer Up (BaseEventData)` の + ボタンをクリック
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/365e52ca-248b-1cfd-f00d-39535bfdf9a3.png)
6. 音を鳴らす処理を追加して完了 (音を鳴らす処理は、各々実装方法が違っていると思うので割愛します) 
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/5a92b89b-dc8d-036d-648b-8ca5e6198dba.png)

PointerUp にすることで、マウスを離した時にだけ音を鳴らせることができます。

# 実例
↑ の実装を使ったものです。

<!-- [↑ の実装を使ったものです。【カゴ詰め検定】](https://unityroom.com/games/kagodume_kentei)
-->

<TABLE ALIGN=CENTER>
  <TR>
    <TD WIDTH=600px>
      <A HREF="https://unityroom.com/games/kagodume_kentei" TARGET="_blank"><strong>カゴ詰め検定</strong></a><BR>
      <BR>スーパーのレジ係の如く、商品をカゴに詰めましょう！目指せ高時給！
    </TD>
    <TD WIDTH=150px>
      <IMG STYLE="float:left;margin-right:.5em;" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/53e33661-c532-4de9-1da6-e58a79dbed10.gif" ALT="" WIDTH="150" HEIGHT="150" />
    </TD>
  </TR>
</TABLE>

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/246559/ae7c520b-8443-e491-703e-c8d8940a7ea4.png)
【Rails】ブラウザのタブにアイコン(favicon)を設定する

# はじめに
ポートフォリオを作成しましたが、ブラウザのタブのアイコンがないのは寂しい！！と思い、
設定方法を調べたところ、favicon(ファビコン)を設定すれば実装できることが分かり、簡単に設定できたのでアウトプットとして記録します。
今回下の画像の赤枠のアイコンを変更していきます。
![favicon](https://i.gyazo.com/ea1273055473e527dff3c0396709fac6.png)

# 環境
- Ruby 2.6.3
- Rails 6.1.5.1


# タブのアイコン用の画像を用意する
favicon用に設定するファイルを[**こちら**](https://ao-system.net/favicon/ "ファビコン作成")で変換し作成してください。無料で半透過マルチアイコンを作成できます。
ファイルを指定し、作成ボタンを押した後、ファイルが作成されますので、ダウンロードボタンを押します。
ダウンロードしたfavicon.icoを、railsのimageフォルダに保存します。
自分は16×16用画像ファイルで変換し作成しましたが問題無く反映されました。

# コードを追加する

`app/views/layouts/application.html.erb`内に、以下のコードを追加します。
```diff_php:application.html.erb
<html>
  <head>
    <!--(省略) -->
+   <%= favicon_link_tag('favicon.ico') %>　　←　#追記
  </head>
  <body>
    <!--(省略) -->
  </body>
</html>
```

# サーバーを再起動して確認
`rails s`でサーバーを再起動すると、faviconが適用されていることが確認できます。

# 参考記事
https://qiita.com/mihooo24/items/380cc2b9c6980bfd0bfa

# 最後に
記事の感想や意見、ご指摘等いただけると助かります。
最後までご覧いただき、ありがとうございました。
rbenvでrubyのバージョンを指定する方法

## OSレベルでの指定
```
$ rbenv global [バージョン]
```

## ディレクトリレベルでの指定
```
$ rbenv local [バージョン]
```
上記コマンドを実行すると、実行フォルダに.ruby-versionというファイルが作成される。
その中にRubyのバージョンが記述されている。 
RailsのPJなどの場合、プロジェクトのルートフォルダにこのファイルを作成し、共有しておくことでプロジェクト毎にRubyのバージョンを共有することが可能。

## シェルレベルでの指定
```
$ rbenv shell [バージョン]
```

## 環境変数でのバージョン指定
```
RBENV_VERSION=[バージョン]
```
初心者用：まずはどの言語を選べばいいの？

# どの言語を選べばいいの？

実際に僕の周りでこの質問を投げかけられることが多々あります　　
よく回答で見るのが
>やりたいことによる　　

って言われますよね　　
確かにそうなのですが今回は
**特にまだやりたいことがわからない人向け**　　
に書いていきたいと思います　　


## 筆者おすすめはJavaScript
まずはこれです
Web開発には欠かせない言語です
開発環境の用意が非常に単純
テキストエディタとブラウザがあればできます
テキストエディタとはプログラムを書くノートみたいなものです
実はWindowsに入っている「メモ帳」でもできます
筆者のおすすめのエディタは「VScode」か「Atom」ですね

### JavaScriptで何ができるの？？
ざっくりといえばWeb開発です
ホームページを作ったりできます
フロントエンジニア、サーバーエンジニアという言葉がありまして
・前者は人の目に見える部分
・後者は裏方の仕事
といった認識でいいでしょう
JavaScriptは基本的にフロントエンジニアの仕事になります
ブラウザアプリケーションの見た目を作っているという感じですね
**ちょっと地味に思えますがプログラミング自体地味ですから気にしないでください**
ただJavaScriptは奥が深く極めると大抵のことは出来てしまいます
JavaScriptにはパワーアップアイテムが用意されており、装備(学習)することで開発は無限大です

さてここまでだらだらと説明してきましたが具体例をあげていきましょう
・Webのフロント開発
・簡易的ゲーム
・スマホアプリ
・チャットシステム
・掲示板
なども作れたりします
ちなみにパワーアップアイテムで「Node.js」というものがありこれはサーバーエンジニアの仕事もJavaScriptでできちゃうぜ！というチートアイテム
確かスマホゲームの「グラブル」にも採用されていたような？

### 事前知識
JavaScriptを学ぶ前にHTMLとCSSは押さえておきたいですね
HTMLは表示したいものの配置を、CSSは文字とかボタンやレイアウトデザイン
といった具合です
ぶっちゃHTMLは
>このタグはこういう役割なんだ　　

程度の認識でいいです
書き方は忘れていても使いたいタグがわかってたら調べれますから
CSSについては凝ったデザインなどはコピペで対応できます
はじめのうちは流す感じで
使ってたら重要な部分は自然と覚えます
1日休憩込みで2時間勉強するとして3日前後で終わると思います
もし楽しいと思えたらガッツリ理解できるまでやるのもいいですね
とりあえずお試し期間ということであっさりやってもOK

### 学習方法
おすすめの学習方法はこちらにまとめています
https://qiita.com/rails_kaname/items/e85f9f3672b0910986af
HTML、CSSはある程度今は流して大丈夫ですが、JSはしっかりやっておきましょう

# まとめ
というわけでまとめると
JavaScriptは
・Webのフロント開発ができる！
・Node.jsでサーバーもさわれちゃう
・開発環境が桁違いに用意しやすい

といった感じですね
ちなみにですがJavaScriptって<font color="red">かなり求人多い</font>んですよ
これさえ書けたら飯食べるのには困らんだろ
って思えるくらいです
フリーランスとしてホームページ制作をして生活してた時期があったのですが企業のページ、個人のページ等はHTML、CSS、JavaScriptで完結できますしね
とりあえずプログラミングを学びたいんだ！という人は僕はここから始めるのをお勧めします
mydns触ってみる

## mydnsとは
ddnsなどのIPを無料ドメインで解決してくれるサービス

## 設定方法

アカウントを作りIDとパスワードを控えておく

https://www.mydns.jp/

## cron

[cronとは](https://qiita.com/katsukii/items/d5f90a6e4592d1414f99)

```mydns.sh
#!/bin/bash
MID="自分のmydnsID"
PASS="自分のパスワード"
wget -O -  https://$MID:$PASS@ipv4.mydns.jp/login.html
wget -O -  https://$MID:$PASS@ipv6.mydns.jp/login.html
```

### mydns.shを30分度に実行

systemctl status cron.service
crontab -l

```
*/30 * * * * /mydns.sh
```
PHPのバージョンをプロジェクトごとに切り替える方法

## はじめに
今回は**phpenvの導入～使用方法**までを紹介します。

- **導入の発端**
Jenkinsの**ビルド時にジョブごとにPHPのバージョンの切り替えを可能**にして
**依存関係エラーの解消**をするために使用。

:::note warn
Jenkinsのシェルからコマンドを打つ場合は、
最初にsource ~/.bash_profileを実行しないと`.bash_profile`は反映されない。
:::

## インストール

#### phpenv
```
$ git clone https://github.com/phpenv/phpenv.git ~/.phpenv
```

#### 環境変数へ追記
```
$ echo 'export PATH="$HOME/.phpenv/bin:$PATH"' >> ~/.bash_profile
$ echo 'eval "$(phpenv init -)"' >> ~/.bash_profile
$ exec $SHELL -l
```

#### シェルの再起動
```
$ exec $SHELL -l
```

#### php-build
```
$ git clone https://github.com/php-build/php-build $(phpenv root)/plugins/php-build
```

#### phpenvからダウンロード可能なバージョンを確認
```
$ phpenv install -l
```

#### PHPをインストール
```
$ phpenv install {version} 
```
:::note warn
**パッケージエラーが多発**する可能性があるため
**yumで追加、更新**する必要がある。
:::

:::note warn
PHPでlibzipを動作させるためには、**libzip0.11以上**のバージョンが必要だが
yumで入れる場合は、**0.10.1**までなので公式サイトからダウンロードが必要。
:::

## コマンド
#### 切り替え可能なバージョン一覧を表示
```
$ phpenv versions 
```

#### カレントディレクトリでPHPを切り替え
```
$ phpenv local {version} 
```

#### システム全体のPHPを切り替え
```
$ phpenv global {version} 
```

#### hashの更新
```
$ phpenv rehash
```

## アップグレード
```
$ cd ~/.phpenv
$ git pull
```

## 参考
https://github.com/phpenv/phpenv

https://github.com/php-build/php-build
100日後くらいに個人開発するぞ！day037

## 今日はRubyを動かしてみた！

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2632394/af79e29a-696c-7524-648e-6a5bfcd239a4.png)



## 今日の学び

### Rubyとは
* RubyはWEBアプリケーションシステムをつくるためのプログラミング言語
* PHPやPythonと類似

### Rubyで文字を出力する方法
* `puts "テキスト"`というコードを書くと"テキスト"がコンソールに出力される

### コメントを書く方法
* `# テキスト`と書くとその行はコメントになりコンソールには出力されない

### 四則演算の結果を出力する方法
* `puts 計算式`で四則演算の結果を出力できる
    * 例：「4+2」の結果を出力したい場合
        * `puts 4+2`
* 「％」を用いると割り算の余りを計算できる
    * 例：「9÷2」の余りを出力したい場合
        * `puts 9%2`


### 文字列を連結させたい場合
*`puts "テキスト１"+"テキスト2"`というように文字列同士を「＋」記号を用いると連結することができる
JUnit:例外が発生しないことを確認するテストの書き方

# 何もしないメソッドのテスト

弊社ではJUnit5でJUnitを書いているのだが、次のような既存メソッドのテストをどうしようか迷った。（ググレカスと言われかねない）


```java
public class HogeCheck{

  /**
   * Api経由で何かしらの値をチェックし、trueの場合、専用Exceptionを投げる
   * @param url
   */
  public void hogeCheck(url){
    
    boolean checkResult = new FugaApi(url).check();
  
    if(checkResult){
       throw new HogeHugaException();
    }

  }

}
```

個人的にvoidはあんまり好みじゃないというか、テストしにくいからできるだけ敬遠している。
返り値を作れるならそうなるようコードReviewでも指摘を入れることがよくある。

しかし今回のコードはレガシーコード。つまりテストのないコード。
ここについてはまずテストを書くことを優先した。

前出のメソッドの正解のテストを以下に記載していく。

**プロダクションコード**

```java

public class HogeCheck{

  /**
   * Api経由で何かしらの値をチェックし、trueの場合、専用Exceptionを投げる
   * @param url
   */
  public void hogeCheck(url){
    
    boolean checkResult = new FugaApi(url).check();
  
    if(checkResult){
       throw new HogeHugaException();
    }

  }

}


```

**テストコード**

```java

public class HogeCheckTest{

  @DisplayName("APIで取得した結果がtrueの場合、例外が発生")
  public void testHogeCheck_exception(){
     String errorUrl = "https://xxxx.yyyy";//trueが返ってくるurl
     HogeCheck it = new HogeCheck();
     assertThrows(HogeHugaException.class, () -> it.hogeCheck(errorUrl));
  }

}

```

Exceptionが発生することのテストは↑のように書くことができる。

FYI

https://qiita.com/flyaway/items/858fe506c85d7bdc48b3

一方、Exceptionが発生しない場合は、**assertDoesNotThrow**を利用できる。

```java

public class HogeCheckTest{

  @DisplayName("APIで取得した結果がfalseの場合、例外が発生しない")
  public void testHogeCheck_no_exception(){
     String url = "https://xxxx.zzzz";//falesが返ってくるurl
     HogeCheck it = new HogeCheck();
     assertDoesNotThrow(() -> it.hogeCheck(url));
  }

}

```
記法はassertThrowsと似ているので書きやすいし忘れにくい。
- assertThrowsの第一引数はExceptionのクラスを定義、assertDoesNotThrowはそれがない
- それ以外の記法は差異なし。


FYI
https://junit.org/junit5/docs/current/api/org.junit.jupiter.api/org/junit/jupiter/api/Assertions.html#assertDoesNotThrow(org.junit.jupiter.api.function.Executable)

# 最後に

ポイントとしてはreturnがvoidのメソッドで、
条件付きでExceptionを発生させるメソッド（つまり外から見ると何も起きないこともある）場合は前出の記法で分岐網羅が可能である。（Exception発生可否基準で）

一方Exceptionもくそもないreturnがvoidのメソッドの場合（DTOのsetterとか）は、
- 素直にgettterで検証する
- [Mockito verify](https://qiita.com/fumu238/items/64c910bc36b051c6b976#%E3%83%A2%E3%83%83%E3%82%AF%E5%8C%96%E3%81%97%E3%81%9F%E3%83%A1%E3%82%BD%E3%83%83%E3%83%89%E3%81%AE%E5%91%BC%E3%81%B3%E5%87%BA%E3%81%97%E5%9B%9E%E6%95%B0%E3%82%92%E6%A4%9C%E8%A8%BC%E3%81%99%E3%82%8Bverify)を使う

などによって、検証は可能である。
2022年06月何故かベストアンサーをつけてくれない質問

+ [新しい発見へのチャートの追加](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HjoPQ)
+ [レコードトリガーフローの構築-価値に関する質問](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HjlLH)
+ [#COMPACTLAYOUTS](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HDZgcSAH)

+ [i am getting an error message like "Line: 1, Column: 16 Method does not exist or incorrect signature: void viewAnnualRevenue() from the type AccountUtility"](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HkG3s)
+ [「注文商品にツインフィールドを作成する」を検証すると、このエラーが発生しますか？-無効なIDフィールド：null](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HDaqs)
+「Creating new user](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000H2k84SAB)
+ [Community stuck in limbo](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000Hl3uW)
+ [Trying to complete trailhead and getting "Success" but not getting challenge 500 points and showing completed.](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HlCeTSAV)
+ [旅行承認アプリでステップがまだ完了していません関連リストのプロパティが見つかりませんでした-経費項目=経費項目番号、経費タイプ、および金額。](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HkvdA)
+ [Build a simple flow and getting following : **We recommend using a new Developer Edition (DE) to check this challenge.**](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HlKQM)
+ [I am facing a problem regarding the section of Approval process of Recruiting App that I have created the section named "Approvers" and completed the task successfully but its not verifying .The Screenshot is attached below.](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HDaQg)
+ [problemas creando la aplicación My Trailblazer Journey](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HDhpH)
+ [連絡先チャレンジにカスタムボタンを追加する](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HDkgG)
+ [How to apply State and Country Picklist on a Contact Object after enabling the feature](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HmRTb)
+ [Convert Picklist value to a Time field](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HDmI1SAL)
+ [Problemas em completar o Desafio no módulo "Control Access to the Org", embora eu segui cada passo](https://trailhead.salesforce.com/ja/trailblazer-community/feed/0D54S00000HmkIf)
scriptコマンドの使い方

## scriptコマンドとは
端末での操作内容を記録するコマンドです。
scriptコマンドからexitを入力するまで記録します。

## 使い方
以下のように記述します。
```:ターミナル
$ script オプション 保存先ファイルのパス
```
保存先ファイルのパスを指定しない場合は`typescript`というファイルが作成され記録されます。
また何のオプションを指定しないと既存のファイルに上書きされます。
記録が保存されるのはexitを実行したタイミングです。

## オプション
オプションには以下のようなものがあります。
<table class="cmd_option" border="1">
  <tbody>
    <tr>
      <th class="opt">オプション</th>
      <th class="note">説明</th>
    </tr>
    <tr>
      <td>-a</td>
      <td>内容を上書きせず既存のファイルに追記する</td>
    </tr>
    <tr>
      <td>-c コマンド</td>
      <td>コマンドの実行結果を記録する</td>
    </tr>
    <tr>
      <td>-f</td>
      <td>リアルタイムに記録する</td>
    </tr>
    <tr>
      <td>-q</td>
      <td>開始、終了時のメッセージを表示しない＆終了時のメッセージを表示しない</td>
    </tr>
    <tr>
      <td>-t</td>
      <td>タイミングデータを標準エラー出力に出力する。/td>
    </tr>
  </tbody>
</table>
【Docker 環境構築】PyTorch・Deep Graph Library・Cuda・mxnetのバージョン互換性【Cuda:11.2.0】

## 1. 背景
UbuntuのGPUマシンのDockerコンテナ内で[Deep Graph LibraryのサンプルであるGraph Convolutional Networks (GCN)のコード](https://github.com/dmlc/dgl/tree/master/examples/mxnet/gcn)を実行するための環境構築のための備忘録です．

もともとcuda11.3用の環境しか用意しておらず，今回のコードの実行に必要なmxnetがcuda11.3に対応していなかったためコンテナをカスタマイズしてDockerイメージ化することにしました．

[以前書いた記事](https://qiita.com/greentiger/items/7c71708cc108f73707df)でDocker回りの基本的な使い方などをまとめています．

## 2. 前提
### PC環境
- GPUマシン（サーバー側）
    - Ubuntu 20.04 LTS
    - AMD EPYC 7402P 24-Core Processor
    - RTX 3090 ×2
    - メモリ128GB
    - openssh-serverインストール済み
    - Dockerインストール済み

## 3. 環境構築
### 入れたいもの
- cuda11.2.0
- python3
- jupyter lab（jupyter labを使いやすくするための拡張機能もいくつか）
- nodejs
- torch==1.10.1+cu111 torchvision==0.11.2+cu111 torchaudio==0.10.1（cu111版を入れているが，cu112が存在しないのと，cuda11.2でもcu111が動かせるため）
- mxnet-cu112（全てはこれのバージョンに合わせるため…）
- dgl-cu111

### セットアップ

```bash:terminal
docker pull nvidia/cuda:11.2.0-cudnn8-devel-ubuntu20.04
docker run -it --gpus all --name cuda11.2 -v ~/Desktop/user1:/container/user1 nvidia/cuda:11.2.0-cudnn8-devel-ubuntu20.04
apt update
apt -y upgrade
apt install -y python3-pip
pip install torch==1.10.1+cu111 torchvision==0.11.2+cu111 torchaudio==0.10.1 -f https://download.pytorch.org/whl/torch_stable.html
pip install jupyterlab
apt install curl vim wget ffmpeg imagemagick nodejs npm
npm install -g n
n stable
apt purge nodejs npm
exec $SHELL -l
source ~/.bashrc
```

jupyter labの拡張機能をpipで入れる．
```bash:terminal
pip install jupyterlab-language-pack-ja-JP lckr-jupyterlab-variableinspector jupyterlab_nvdashboard ipywidgets black yapf isort jupyterlab_code_formatter jupyterlab_tabnine jupyterlab-lsp 'python-lsp-server[all]' pprintpp jupyterlab-spreadsheet-editor ipympl opencv-python
```
Deep Graph Libraryを動かすために以下を実行．
```bash:terminal
pip install mxnet-cu112
pip install dgl-cu111 dglgo -f https://data.dgl.ai/wheels/repo.html
```

```bash:terminal
exit
docker commit cuda11.2 cuda11.2lab
```

`cuda11.2lab`という名前のDockerイメージが使えるようになった．

## 4. まとめ
備忘録のため，簡素なものになってしまいましたが，以上のコマンドでDGLのサンプルが実行できるDockerコンテナを作れるようになります．
ミスなどありましたら，コメントでご指摘の程よろしくお願いします．

ここまで読んでくださり，ありがとうございました．
Macで(VS Codeなどの)ウインドウを切り替えるショートカットは"コマンドキー＋@"

# 概要

メモしておきたい内容、タイトル通りです。

## 方法

Macで、Visual Studio Codeなどで複数ウインドウを開いていてウインドウの切り替えをしたいとき、"コマンドキー+@"で次のウインドウに切り替えられます。

## 前提

このショートカットキーは、（個別アプリのものでなく、）Mac側のものです。

「設定」→「キーボード」の「ショートカット」タブの「キーボード」項目で、「次のウインドウを操作対象にする」のショートカットにチェックが入っていること、他のショートカットと競合していないこと、が必要です。

![スクリーンショット 2022-06-02 6.52.46.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/65002/6fb491d1-eb2a-5e23-d469-a317e4b1e727.png)

## 確認した環境

- macOS Mongerey 12.3.1
- Visual Studio Code 1.67.2 (April 2022)

## 補足

VS Codeのウインドウ切り替えをどうやるのか、VS Code側の設定で探していたのですが、ウインドウの制御なので、OS側のショートカットで実現されるのでした。
Raspberry Pi 4B のモバイルバッテリー駆動の目安は10時間前後

Raspberry Pi 4B をモバイルバッテリーで駆動させ、バッテリーの性能をある程度出し切ったところで安全にシャットダウンしたいと思っています。

そのために、まずは無負荷でどのくらい稼働するか実験をしたところ、その結果を次のように理解しているところです。

- モバイルバッテリー駆動の目安はざっくり10時間前後
- 電圧降下を捉えるのはおそらく難しく、タイマーをかけてシャットダウンするのが現実的

# コンテキスト
## yata
国連ベクトルタイルツールキットでは、その Raspberry Pi 運用である UNVT Portable をソーラーパネルとモバイルバッテリーで稼働させるノウハウを蓄積・共有し、能力構築のコンテキストを広げるとともに、将来的な現場配備の選択肢を増やしたいと思っています。

https://github.com/unvt/yata

## kagero
実際に、バッテリー駆動させてみる実験を進めてみました。

https://github.com/unvt/kagero/issues/1

# 結果の分析
出揃った結果を見て、私は次の通りとらえたいと思います。

バッテリー | 無負荷稼働時間 | 稼働目安 | 稼働目安の長さのイメージ
---|---|---|---
PowerCore 20100 | 26時間 | 18時間 | 人間が起きている時間
PowerCore 10000 | 15時間 | 10時間 | 人間の稼働時間
PowerCore 5000 | 7時間30分 | 4時間 | 人間の稼働時間で言う半日

なお、これらのバッテリーが切れる直前に、Raspberry Pi 4B 側で電圧降下（under-voltage) が観測されるか実験してみましたが、5分間隔の観測では、電圧降下は検知されませんでした。

バッテリーが切れる前にシャットダウンをするためには、電圧降下をとらえてシャットダウンをすることを考えるのではなく、稼働目安時間になったらシャットダウンするようにするのが現実的だと思います。

# 追伸：ソーラーパネルの出力との関係
yata で調達されたソーラーパネルは、晴天時の日光直射時には安定して 5V2A または 5V1A の入力を作ってくれます。つまり、10W または 5W のパワーソースとして動いてくれます。

PowerCore 20100 はつまり 20Wh のリチウムイオン電池であると捉えることができますが、このソーラーパネルを使えば、数時間程度で充電が進むことになります。

他方で、実際には日本の関東地方の5月、6月の場合、日光直射が数時間にわたって連続的に続くと言うことはなく、また、ソーラーパネルに日光が直射するようにソーラーパネルの角度を調整することはそれほど簡単ではありません。

体感としては、次のような感じの運用イメージになります。

- PowerCore 20100 を充電したければ、晴天の1日が必要。運が良ければお釣りがくる。
- PowerCore 10000 や 5000 は、確かに数時間で充電できると言うイメージ。ちょっとした晴天時に置いておくと、電力が貯められると言う感覚がある。
レンタルサーバーをFreeBSDのファイルシステムにマウントする

## 結論、できます。

この記事は FreeBSD 13.x を前提に記述しています。
他のバージョンでは多少異なるかもしれません

## やりたいこと

画像超圧縮としてavifも導入したいが、
avifencはとても重いのでレンタルサーバーに入れるにはふさわしくない
動的に対応するにしても、scpだと非効率なため

### パスフレーズなしのssh鍵を作る

セキュリティーは悪くなりますが便利です

### fusefs-sshfsの導入

```
pkg install fusefs-sshfs

or

cd /usr/ports/sysutils/fusefs-sshfs && make install clean
```

### 以下のファイルを記載する

```/boot/loader.conf
fusefs_load="YES"
```

```/etc/sysctl.conf
vfs.usermount=1
```

### groupファイルのoperetorに自分のユーザーを追加する

### 再起動する

### 接続
```mount.sh
mkdir /mnt/sshfs
sshfs -p 22(portnumber) username@example.com:/home/username/path/to /mnt/sshfs -o IdentityFile=/home/username/id_rsa_keyfile
```

### 切断
```unmount.sh
unmount /mnt/sshfs
```
2022/6/2主にITとかセキュリティの記事

「MSDT」にゼロデイ脆弱性「Follina」 - MSが回避策をアナウンス
https://www.security-next.com/136947

交通関連サービスのフィッシングサイトが増加 - BBSS調査
https://www.security-next.com/136955

フィッシング攻撃で150万ドル相当のムーンバードNFTが遮断される(5/31)
https://nextmoney.jp/?p=50738

九州カードを偽装したフィッシング確認、注意を(5/31)
https://gunosy.com/articles/ajQfS

ウェブサイト閲覧で勝手にマルウェアをダウンロードする「ドライブバイダウンロード攻撃」への対策(5/31)
https://ascii.jp/elem/000/004/093/4093004/?rss

IEC 62443とは何か、工場のサイバーセキュリティ対策のカギを握る国際標準を解説(5/31)
https://monoist.itmedia.co.jp/mn/articles/2205/31/news006.html

月桂冠にランサムウェア攻撃、顧客情報等が流出の可能性(5/31)
https://scan.netsecurity.ne.jp/article/2022/05/31/47663.html

金銭の代わりに善行を要求するランサムウェア『GoodWill』(5/30)
https://www.nichepcgamer.com/archives/goodwill-ransomware.html

目標完遂する金融機関の共通項、「極めてアジャイル」になるための4ステップ(5/31)
https://active.nikkeibp.co.jp/atcl/wp/b/22/05/24/02647/?i_cid=nbpnxta_sied_newarticles

AndroidスマホでOneDriveを使う（2）(5/31)
https://swri.jp/article/1064

違法漫画サイトへの月間アクセス数、半年で半減　ただし後継サイトは急成長中(5/31)
https://news.nicovideo.jp/watch/nw10990500

Logitechの旧キーボード/マウス用ユーティリティ「Logi Option」がApple M1 Macに対応。(5/31)
https://applech2.com/archives/20220531-logi-options-support-apple-silicon.html

Microsoftの診断ツールにリモートコード実行の脆弱性(5/31)
https://pc.watch.impress.co.jp/docs/news/1413507.html

Microsoft Officeにゼロデイの脆弱性、マクロ無効にしても悪用可能(5/31)
https://news.infoseek.co.jp/article/mynavi_2422869/?tpgnr=it

青森市ホームページの偽サイトにご注意ください(5/31)
https://www.city.aomori.aomori.jp/jyuuyou.html

大規模なハードウェアのオフロードを実現する PSP の暗号化がオープンソースで登場(5/31)
https://cloud.google.com/blog/ja/products/identity-security/announcing-psp-security-protocol-is-now-open-source

iOSアプリのためのログインフレームワークを１から作り直した話(5/31)
https://blog.cybozu.io/entry/2022/05/31/170000

Web版Googleドライブでキーボードショートカットを使ったファイルのコピー／ペーストなどが可能に(5/31)
https://news.infoseek.co.jp/article/itmedia_pcuser_20220531181/?tpgnr=it

サポート期限は大丈夫ですか？　Windows、Windows Server、SQL Server、Office、IEの最新ライフサイクル情報を確認せよ(5/31)
https://atmarkit.itmedia.co.jp/ait/articles/2205/31/news010.html

【匠の部屋】vProでBitLockerのパスワードは遠隔解除できる？　vPro PCをNASにする場合、遠隔操作にモニターは必要？(5/31)
https://internet.watch.impress.co.jp/docs/column/vpro_takumi/1412232.html

iPhoneは電源オフにしても「眠らない」、居場所は分かるしマルウエアも動き続ける(6/1)
https://xtech.nikkei.com/atcl/nxt/column/18/00676/052600107/

10通に1通が「盗聴」されるリスク、メールの危険な現状が明らかに(6/1)
https://xtech.nikkei.com/atcl/nxt/column/18/02079/052000001/

アカウント漏洩の原因はいろいろ、すぐ実行したいセキュリティー対策(6/1)
https://xtech.nikkei.com/atcl/nxt/column/18/02050/042800001/

「立ち上げて終わり」ではない　D2Cがうまくいかない4つの理由(6/1)
https://xtech.nikkei.com/atcl/nxt/mag/nc/18/101400256/052600011/

接客DXで新サービス　DevOpsやAPI化を実践(6/1)
https://xtech.nikkei.com/atcl/nxt/mag/nc/18/052700295/052700001/

ネットワークの至る所が高速化Part 1　総論(6/1)
https://xtech.nikkei.com/atcl/nxt/mag/nnw/18/051800136/051800001/

10Gビット/秒の接続サービスが続々登場Part 2　アクセス回線(6/1)
https://xtech.nikkei.com/atcl/nxt/mag/nnw/18/051800136/051800002/

2.5Gビット/秒対応スイッチが店頭にPart 3　イーサネット(6/1)
https://xtech.nikkei.com/atcl/nxt/mag/nnw/18/051800136/051800003/

最大9.6Gビット/秒のWi-Fi 6が普及間近 Part 4　無線LAN(6/1)
https://xtech.nikkei.com/atcl/nxt/mag/nnw/18/051800136/051800004/
GCP Terminalで繰り返し使うコマンドや資料をメモ

## Common

### Machine Typeの選択

[GCPinstances.info](https://gcpinstances.doit-intl.com/)

### Project, Region, Zoneを設定

環境変数を設定

```
export PROJECT_ID=<value>
```

環境変数を設定

```
gcloud config set project $PROJECT_ID
gcloud config set container/cluster cluster-1
gcloud config set compute/zone us-central1-c
```

## Kubernetes Engine

### GKEクラスターを作成

環境変数を設定

```
export CLUSTER_NAME=<value>
export MACHINE_TYPE=<value>
```

クラスターを作成

```
gcloud services enable container
gcloud container clusters create $CLUSTER_NAME --cluster-version latest --machine-type=$MACHINE_TYPE --num-nodes=3
gcloud container clusters get-credentials $CLUSTER_NAME
kubectl config current-context
```

### GKEクラスターのノードプールを操作

環境変数を設定

```
export CLUSTER_NAME=<value>
export MACHINE_TYPE=<value>
```

ノードプールを追加

```
gcloud container node-pools create new-pool --cluster=$CLUSTER_NAME --machine-type=$MACHINE_TYPE --num-nodes=3
```

ノード数を変更

```
gcloud container clusters resize $CLUSTER_NAME --node-pool default-pool --num-nodes 4
```

## Cloud Run

### コンテナイメージをデプロイ

```
docker pull wordpress
docker tag wordpress gcr.io/$PROJECT_ID/wordpress
docker push gcr.io/$PROJECT_ID/wordpress
gcloud run deploy wordpress --region us-central1 --platform managed --image gcr.io/$PROJECT_ID/wordpress --port 80
```

### Cloud Runで実行中のサービス一覧を表示

```
gcloud run services list
```
[PHP入門]　テキストデータへの、送信、書き込み、読み込み　

# 初めに
PHPの学習を始め、よく使うけど、始めのうちは忘れて何度も見直すだろう。
という点を、メモ代わりにまとめていきます。

## 基本的な書き方
**[開始タグ]**  ```<?php```
**[終了タグ]**  ``?>``

**[HTMLへ表示]** ``echo``  　　
```
echo "Hello"; //文字列
echo $hensu;  //変数
```
※jsのconsole.logのように()は不要だが、`` ; ``を忘れるとエラーが出るので注意。

**変数定義**　 
```
$num = 1;          //数列
$name = "hoge";　　　  //文字列
```
## HTMLフォームのデータをPHPファイルへ送信
PHPを使う事で、HTMLとCSSだけでは見た目だけだったお問い合わせフォームを実際に活用できるようになります。

```
<form method=”get" action=“get_confirm.php">
<p>お名前:<input type="text" name="name"></p> 
<p>MAIL:<input type="text" name="mail"></p> 
<p><input type="submit" value="送信"></p>
</form>
```
### **[method]**
**formタグ**の``method``の部分には、``get``か``post``を入力。

どちらも同じような使い方ができるのですが、僕の現段階の理解では、
**ログインIDや個人情報など**は``post``
**その他**は``get``

**formの場合は``post``を使う**
※``get``の場合は取り扱うデータがURLに表示されてしまう為、個人情報等に使うのは適していないという理由。

### **[action]**
**formタグ**の``action``の部分には、**データの送信先URL**を記入する。

## PHPファイルでデータの受け取り
データの受け取り方はすごくシンプルです。
<INS>postでデータを送信した場合</INS>と、<INS>getでデータを送信した場合</INS>で、受け取り方が変わりますで、注意しましょう。

**[postの場合]**
```
<?php
//$_POST["input名"];
$name = $_POST["name"];  //$_POSTの部分は大文字で
$mail = $_POST["mail"];  
?>
```

**[getの場合]**
```
<?php
//$_GET["input名"];
$name = $_GET["name"];　　//$_GETの部分は大文字で
$mail = $_GET["mail"];
?>
```

## PHPファイルから、textファイルへの書き込み
データベースを使わない場合はtextファイルへ情報を残しておくことができます。
基本的には、下記の3行で書き込みが可能です。

```
<?php
$file = fopen(“./data/data.txt”, “a” ); //ファイルOPEN 
fwrite( $file, “**書き込み文字列**” );     //ファイルへの書込み
fclose( $file );                        //ファイルを閉じる
?>
```

``$file = fopen(“◯◯”, “△△” );``
◯◯の部分には、**書き込むtextファイルのpath**を記述。
△△の部分には、**ファイルの開き方**を指定します。

**[開き方一覧]**
```
r    ：読み込みのみ でオープン。
r+   ：読み込み/書込み用 にオープン。
w    ：書込みのみ でオープン。           内容をまず削除、ファイルがなければ作成
w+   ：読み込み/書込み用 でオープン。     内容をまず削除、ファイルがなければ作成
a    ：追加書込み用のみ でオープン。      ファイルがなければ作成
a+   ：読み込み/追加書込み用 でオープン。  ファイルがなければ作成
```

**[form内容の書き込み記述例]**
```
<?php
//データの受け取り
$name = $_POST["name"];
$mail = $_POST["mail"];

//データを区切る為の、カンマ
$c = ",";

//受け取ったデータ2つを1つの文字列にまとめる
$str = $name.$c.$mail;

//データを書き込む為のファイルを開く
$file = fopen("data/data2.txt", "a");

//データの書き込み作業 　　           ※"\n"は改行です
fwrite($file, $str."\n");

//ファイルを閉じる
fclose($file);

//ページの遷移
header("Location:http://localhost/php_kadai/output.php")
?>
```

## textファイルに書き込まれたデータを、PHPファイルで取得
書き込み同様、シンプルな記述で取得が可能です。

```
<?php

//読み込みたいファイルのpathを記述し、変数に代入
$filename = 'data/data2.txt';

//読み込んだファイル内の全てのデータを取得し、変数に代入
$content = file_get_contents($filename);

//取得したデータをHTMLで表示
echo $content;

?>
```
ファイル内のデータの取得方法はたくさんありますが、とりあえずデータを取得する為に、一番簡単かな。という方法で記述いたしました。

## まとめ
HTMLとCSSで外観を作れるようになり、JavaScriptで動きを作れるようになり、PHPを使えるようになる事で、データの取り扱いやログイン処理等の本格的な機能を作れるようになります。

まだまだ学び始めたばかりなので、どんどん追記していきたいと思います。
僕と同じ、初学者の方のお役に少しでも立てれば幸いです。
@AppStorage変数をバインディングできるのか。。。

# 背景

現在、計算を用いたごく簡単なアプリの作成過程でエラー？というかわからない点が浮上したので記事にまとめていきたいと思います。


その疑問点とは@AppStorage変数を@Bindingして他のViewに反映をさせることができるかということです。


ちなみに僕はドがつくほどのアプリ開発初心者ですので間違っていたら教えてくださると嬉しいです。

# ＠AppStorageを他のファイルに＠Bindingしたら

＠AppStorageを他のファイルに＠Bindingしたら下記のようなエラーが発生しました。

>Return from initializer without initializing all stored properties

どうやら初期値を入力してくれ！！的なことらしい

ということで

```
init(){
    self.result = 0.0 ←Dobule型なので0.0を初期値に入れてみます
}
```
というふうにやってみました。

そしたらなんとまたエラーが発生してしまいました、、、、


# Cannot assign value of type 'Double' to type 'Binding<Double>' というエラー発生

訳すと、Double型のデータをBinding型に割り当てることができないということらしい。

色々ネットを探ってみると、

```
init(result:Binding<Double>){
    self._result = result ← 0.0からresultへと変化させました
}
```

のように変化させるといいらしい。

初期化処理を自動でお任せしていたから、init()の引数にはDouble型が入るって勘違いしていたけれど実際に入ってきたのはBinding型（Double）だったからXcode君が焦ってエラーを出したって感じなのかな？笑

焦っているXCode君に手動でinit()の中に（result：Binding<Double>）と引数の方の情報を教えてあげることでエラーが解消してくれました。

あともう一つ変わったところで言うと

```
self._result = result
```

ですね。ここはなぜ変化したかと言うとプロパティーラッパーを定義したプロパティに(_)をつけるとプロパティラッパー内部変数にアクセスができるから！


# 最後に

今回Qiitaで記事書くのはもちろん初めてだし、もしかしたら僕の理解が間違っている可能性もあリます。

もし間違えていたら教えてください！！お手数をおかけします。

初めて書いた感想としてはいつもの数倍理解が深まりました！書いてよかった！これからも書いていきたいと思いますのでお願いします。
TypeScriptにおけるimport/requireの使い方【TypeScript Deep Dive全部読む】

TypeScript Deep Diveを読みながら、学んだことを軽くまとめていく。

https://typescript-jp.gitbook.io/deep-dive/project/modules/external-modules

```import```の使い方について見てみる。

## まずCommonJSとES Modulesって何？

JavaScriptをモジュールとして扱うために、定められたモジュールの仕様のこと。

* ```CommonJS```はNode.jsで用いられていて、サーバーサイドなどブラウザ外を中心に扱われる仕様。




* ```ES Modules```は主なブラウザで対応している。最近の主流になっていくらしい。

TypeScriptにおいては```module```オプションに応じて異なるJavaScriptが生成される。

どちらも使える環境が異なるため、CommonJSをブラウザで使う場合やES ModulesをNodeで使う場合などはひと手間挟む必要がある。

### importとrequireって何が違う？
```CommonJS```の仕様か、```ES Modules```の仕様かの違い。
* ```CommonJS```においてはrequire()を用いてモジュールを読み込む。
```ts
const a = require("./testModule");
```
* ```ES Modules```においてはimportを用いてモジュールを読み込む。
```ts
// importを用いてモジュールを読み込む。
import {b} from "./testModule";
```

この際、```import```では何らかの型情報を持って読み込むが、```require()```では```any```型の変数を定義することになるため、VScodeの補完などが効きづらくなる。TypeScriptを扱う上ではできるだけ```import```を使うべき。

### ESモジュールの書き方
エクスポートを行う際は変数、型の定義をexportを前において行う。
```ts: module.ts
export let a = 1;

export let b = 2;

export let testfunc = () => {
    console.log("hello world!");
}
```
こう書いても同じ。
```ts: module.ts
let a = 1;

let b = 2;

let testfunc = () => {
    console.log("hello world!");
}
export{
    a,
    b,
    testfunc
}
```
名前を指定してexportもできる。
```ts
export{
    a as a_,
    b as b_,
    testfunc as testfunc_
}
```

インポートを行う際は```import```を使用する。

```ts: app.ts
import {a, b, testfunc} from "./module";
console.log(a); // 1
console.log(b); // 2
testfunc(); // hello world!
```
名前を変更してimportすることもできる。

```ts: app.ts
import {a as a_, b as b_, testfunc as testfunc_} from "./module";
```

```*```を用いて全てのモジュールを```import```することもできる。
```ts: app.ts
import * as m from "./module";
console.log(m.a);
m.testfunc();
```
ちなみに```require```でも同じような使い方ができる。

```ts: app.ts
const m = require("./module");
console.log(m.a);
m.testfunc();
```
ここから再度エクスポートなどもできる。
```ts: app.ts
export * from './foo';
```

### デフォルトエクスポート
defaultを指定してエクスポートができる。
```ts: module.ts
let a;
export default a = 1
```

```ts: app.ts
import a from "./module";
console.log(a); // 1
```
ただしdeep dive内では```export default```は有害、使うなと様々な理由で言われている。

https://typescript-jp.gitbook.io/deep-dive/main-1/defaultisbad#dynamic-imports

## 残り
https://typescript-jp.gitbook.io/deep-dive/project/modules/external-modules

↑記事内では、指定するパスの解決方法についての記述や、```import foo = require('foo');```といった型だけをimportする手法も紹介されているが、ここに書くのは省略する。