OmniAICreator/Qiita-1.07M huggingface dataset:
QLabでPJLinkプロジェクターとIDKスイッチャーを制御する〜QLab5編

# はじめに
音響・映像の送出だけにとどまらない、ショーコントロールソフトウェアとして進化を続けている、QLab。
映像の送出現場でもよく使っています。

映像の送出で、同時にプロジェクターを制御したいということもよくあります。
特に、シャッター内蔵プロジェクターであれば、シャッターの開閉動作を同時に行えたらとても楽に本番を行えるのではないでしょうか。

2020年ごろ、QLab4を使用していた頃は、直接PJLinkを扱うことはできず、AppleScriptを介して、ターミナルや別appを制御するという方法で行っていました。

https://qiita.com/hiro_esaki/items/efabc28b5d9b0289fc7f

2022年、QLabがバージョン5へと進化し、この状況が大きく変わりました。

# QLab5でTCP messageが扱える
QLabのネットワークキューで扱える内容が増え、QLab4ではUDPのみだったメッセージが、TCPメッセージが扱えるようになりました。
PJLinkはTCPでやり取りするため、これで直接QLabからPJLinkコマンドが送出できます。


# 実際のセッティング
## ネットワークパッチを作成
ワークスペースセッティング > Networkから新しいNetwork Patchを作成します。
![スクリーンショット 2023-08-24 13.28.07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/601755/88985884-df40-02e0-38ef-c2f4a52e0f6b.png)
- Name
    - キューを作成するときにわかりやすい名前をつけられます。
- Type
    - Plain Textを選択します。
- Network
    - TCPを選択します
- Interface
    - 接続するネットワークが複雑で、明示的に接続先を指定する必要がない限り、基本的にはAutomaticでよいと思います。
- Destination
    - 接続先のプロジェクターのIPアドレスを指定します
    - PJLinkはポート4352を使用するため、4352を指定します。
- Passcode
    - 接続パスワードが必要な場合は設定すると良いのだと思いますが、私の環境ではプロジェクターパスワードを設定していないため、使用していません。

## ネットワークキューを作成
ネットワークキューを作成し、[Patch]で先ほどパッチ画面で設定した送信先を選択します。
下の欄に送信するコマンドを入力します。

PJLinkのコマンドは、[JBMIAのPJLinkのサイト](https://pjlink.jbmia.or.jp)の仕様書を参照してください。

たとえば、AVミュート（シャッター閉じ）コマンドは、次のようなものです。（機種によって受け付けるコマンドが異なる場合があります）
コマンドの最後には\r（キャリッジリターン）をつけるのを忘れないようにしてください。
``` plaintext:PJLink
%1AVMT 31\r
```
![スクリーンショット 2023-08-24 13.39.16.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/601755/62dd8edb-94de-bb84-efef-7c352e420064.png)

これでキューを実行すれば、シャッターが閉じます。

## 実際のキューの流れの例
私が実際に本番で使用したキューを参考までに掲載します。
本番の最後、エンディングが終了し客出しBGMを再生すると同時に、プロジェクターの電源を落とすPJLinkコマンドを送り、プロジェクターを触らずに電源を落としました。
![スクリーンショット 2023-08-24 13.51.17.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/601755/84f7fa26-8c4c-4f69-dd25-7e5b70459ee3.png)

# IDKスイッチャーの制御
プロジェクターの前段で、IDK MSD-5404を使用しており、こちらもTCPメッセージを使用しており、同様のセッティングでスイッチャーが制御できます。

IDKスイッチャーは初期状態ではポート1100で通信を行います。

たとえば、スイッチャーのout 2,3,4をオフにするには、次のコマンドを送信します。
なお、IDKのコマンドのデリミタはCR+LF (\r\n)です。
``` plaintext:IDK MSD-5404
@SSW, 0, 2, 0, 3, 0, 4\r\n
```
![スクリーンショット 2023-08-24 13.57.19.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/601755/78b49499-38e1-c0ff-b220-6d8902682d29.png)

# さいごに
QLab5でTCPメッセージが扱えるようになり、制御の幅が格段に広がりました。
プロジェクターやスイッチャーを触らずに直接制御できるようになることで、本番中の手間を格段に減らし、本番のオペレーションに集中することができ、本番のクオリティをアップさせることにつながるのではないかと思います。
組み込み開発 ~ワード集~

概要は省きます。

## リアルタイムOS
　CPUが複数あるように見せかけるソフトウェア
　実際に複数あるのはマルチコア
## タスク
　リアルタイムOSの仮想的なCPUのひとつ
## システムコール(サービスコール)
　プログラム(タスク)宙に記載されるOSへの命令
## セマフォ
　タスク間の排他制御を実装するための変数
## ICE
　動作中のプロセッサの中をのぞく装置
　イメージとしては、プロセッサ(ハード)の部分をICEで丸ごと肩代わりして、接続したパソコンから様々な情報を得る


※随時更新していきます。
neovimで開いたファイル先のディレクトリツリーを表示する(nvim-tree)

# 概要
neovimでnvim-treeを使用しています。```nvim hoge.txt```をした際に、開いたファイル先のディレクトリツリーを表示してほしかったのでその設定方法をまとめます。

例えばカレントディレクトリが```~/path/to/current```だったとして、nvim ```~/config/nvim/init.lua```を開いた場合、currentをディレクトリツリーに表示するのではなく、nvimの方を表示することができます。

# やったこと

## ```file-explorer.lua```の設定
nvim-treeの設定ファイルを作成し、以下の項目を書きます。

```file-explorer.lua
vim.g.nvim_tree_respect_buf_cwd = 1

require("nvim-tree").setup
{
	update_focused_file = {
		enable = true,
		update_cwd = true,
	},
}

```

なお、一度nvim-treeを開いただけだとカレントディレクトリが開くので、再度開きなおすかコードに移動してもう一度nvim-treeに移動すると、nvim-treeがRefreshされて正しく表示されます。


(補足)私は以下のように```file-explorer.lua```を設定しています。

```file-explorer.lua
-- disable netrw at the very start of your init.lua (strongly advised)
vim.g.loaded_netrw = 1
vim.g.loaded_netrwPlugin = 1

-- set termguicolors to enable highlight groups
vim.opt.termguicolors = true

-- showing the tree of my current buffer from where i open up nvim-tree
vim.g.nvim_tree_respect_buf_cwd = 1

require("nvim-tree").setup
{
	sort_by = 'extension',
	update_focused_file = {
		enable = true,
		update_cwd = true,
	},
	view = {
		width = '20%',
		side = 'right',
		signcolumn = 'no',
	},

	renderer = {
		highlight_git = true,
		highlight_opened_files = 'name',
		icons = {
			glyphs = {
				git = {
					unstaged = '!', renamed = '»',
					untracked = '?', deleted = '✘',
					staged = '✓', unmerged = '', ignored = '◌',
				},
			},
		},
	},

	git = {
		enable = true,
		ignore = false,
	},

	actions = {
		expand_all = {
			max_folder_discovery = 100,
			exclude = { '.git', 'target', 'build' },
		},
	},

	on_attach = 'default'
}
```



# 参考

https://www.reddit.com/r/neovim/comments/qnxf12/cwd_in_nvimtreelua/

https://medium.com/@shaikzahid0713/file-explorer-for-neovim-c324d2c53657
組み込み開発 ～セマフォ周り～ 

# はじめに
 組み込みエンジニアになりたての自分が、アウトプットするため投稿させていただきます(※初投稿)
### セマフォとは
・同期・排他制御に用いる仕組み、または変数のこと
・リアルタイムＯＳ上で多数の時間軸(タスク)が動いており、あるタスクと別のタスク間で動機や排他制御を実装するために使われる。

### 使用方法
P操作:セマフォに対して「許可を待つ」「通知を待つ」
※資源を利用する(資源管理用カウンタを1減らす)

　空くのを待つイメージです。

V操作:セマフォに対して「許可を与える」「通知する」
※資源を与える(資源管理用カウンタを1増やす)

　通知許可のイメージです。

### なぜセマフォが必要か
　リアルタイムOＳ上では、複数の時間軸(タスク)が動作している。あるタスクが他のタスクに動きを合わせる必要がある値時に「待合せ」が必要。
　この待ち合わせることを「同期制御」という。

　イベントフラグがわかりやすい考え方です。例えば「スイッチを押したときLEDが点灯」という同期制御の要求仕様があるとします。
　P操作をスイッチがONされたときにおけるフラグを待つ、V操作をスイッチをONしたときフラグをセットするというコードをイメージしてもらえれば、わかりやすいかと思います。

　また、勉強したことはどんどん追記していこうと思います。
VSCodeでipynbファイルを編集しているとシンタックスハイライトが消えるので、ipynbファイル使わないでjupyterぽくファイル編集する話。

## 問題
VSCodeでipynbファイルを編集している際に、セルをショートカット"X"でカットすると全体のシンタックスハイライトが消えてしまう。

## 解決法
根本的な解決ではありませんがpyファイルを"#%%"で区切ると、区切った範囲をセルライクに実行できます。これで対処しました。
Apex compile failure : パッケージのインストール

+ [Getting error : Apex compile failure Apex class DataGeneration_Tests: line 24, column 21: Method does not exist or incorrect signature: void createAccount(Integer) from the type TestFactory](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V00007F4vNCSAZ)


:::note
Please check this article.

https://unofficialsf.com/troubleshooting-installation-of-unofficialsf-packages/
:::


これらのエラーは、実際には、インストールしようとしているパッケージとは関係ありません。何が起こっているのかというと、Salesforce は新しいパッケージをインストールする前に、既存の Apex クラスをすべて再コンパイルしようとしています。これは基本的に、組織に変更を加える前に組織が「クリーン」であることを確認するためです。

場合によっては、組織のコンパイルを実行するかどうかを選択できます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/3f88c309-2038-b5a2-ffd8-b17c685bb3f2.png)

[パッケージ内の Apex のみをコンパイル] が選択されている場合に問題が発生したという話は聞いたことがありません。

あるいは、テスト失敗を生成している apex クラスを削除または修正することもできます。削除の危険性は状況によって異なります。場合によっては、エラーを生成しているクラスが明らかに古い、時代遅れ、または不要である場合があります。Salesforce は他の Salesforce メタデータによって参照されるクラスの削除を防ぐため、ある程度の保護が得られます。再作成する必要がある場合に備えて、削除する前にいつでも apex コードを別のドキュメントにコピーしてみてください。
高コスパ自作PC 2023年版

去年から続く半導体の価格下落がついに底を着いたようだ。内臓SSD、DDR4 DRAMメモリが大暴落しており、40%も下落している。CPUはほぼ横ばい推移なので、自作PCを作るなら今がいいのではと思い、高コスパのデスクトップPCの部品を選定してみた。

#### 内臓SSD価格推移
https://www.bcnretail.com/research/detail/20230815_352256.html

![202308041212_1.gif_1691118761.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/483556/2d2c1b0a-49d8-a7de-607d-99964bfdc309.jpeg)

#### DDR4 DRAM メモリ価格推移
https://www2s.biglobe.ne.jp/~sakharov/research/graph.html

![mem4a.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/483556/a841a56c-6f5b-184d-d3d5-519652314b8f.png)

### 高コスパPCの部品

仕入れ先は購入のしやすさから、Amazon.co.jpで確認して、見繕った。

|部品 |製品名 |値段|
|---|---|---|
|CPU|AMD Ryzen 7 5700X, without cooler 3.4GHz 8コア/16スレッド 100-100000926WOF/EW-1Y|29000円|
Mother Board|B550 Steel Legend|19800円|
RAM	|DDR4-3200 PC4-25600 32GB 288pin DIMM CL22(16GB×2枚)|8500円|
ROM	|Crucial P3plus 1TB 3D NAND NVMe PCIe4.0 M.2 SSD CT1000P3PSSSD8JP|6200円|
GPU	|NVIDIA GeForce RTX3060 GDDR6 12GB GALAKURO GAMINGシリーズ|40000円|
電源 |玄人志向 KRPW-BK750W/85+ Power Supply 80 Plus 750 W ATX|9600円|
OS	|Windows 11 Home 日本語版|13600円|
Monitor	|Acer Nitro QG241YEbmiix 23.8インチ IPS フルHD 100Hz|12000円|
Total||138700円|

※ セカンダリストレージとして、SSDを追加する場合は、NVMeは一つしかスロットがないため、SATAを買うか、PCieスロットを一つ使用して、変換基盤でNVMeを接続するかしないといけないことに注意。

CPUのベンチマーク
https://www.cpubenchmark.net/cpu.php?id=4814&cpu=AMD+Ryzen+7+5700X

![CPUbenchimark.PNG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/483556/e44f708b-ab83-d329-701e-11b720f7a04b.png)

ちなみにmouseコンピューターなどのハイスペックPC販売サイトで購入すると、GPU以外1ランク型落ちのデスクトップPCが込みこみで16万円程度なので、自作の方が数万円くらい安いかなくらい。3年保証を考えると、販売サイトへ頼んでもいいかな。
https://www.mouse-jp.co.jp/store/g/ggtune-dga5g60b5aabw102decal/
wslにNerdFontsをインストールし、設定する(nvim-treeアイコン)

# 概要
nvim-treeを使っていたときにファイルアイコンが表示されませんでした。
そこで、wslにNerdFontsを入れる必要があったのでその設定をしました。

# やったこと
### fontsがあるファイルの場所を開く

1. windows key + r を押す
2. ```shell:fonts```を押す
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2261812/4e0aee34-196c-4432-1d1e-14d7d09b88aa.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2261812/200fa918-495b-13c2-6833-76f35ccf627f.png)

### NerdFontsのインストール
https://www.nerdfonts.com/font-downloads

ここから好きなフォントをダウンロードします。私はHack Nerd Fontを入れました。
ダウンロードフォルダで解答します。

### Fontsへの移動

ttfでフォントが定義されています。HackNerdFont-RegularをコピーしてFontにペーストします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2261812/32711e0c-04f4-aee9-6ef5-0e47446537d9.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2261812/a060aafb-4994-2c86-faeb-74812592de67.png)



### powershell上での設定
まだ終わりません。fontなので、**wslではなく、powershellの設定が必要になります**

1. タブの隣の空白を右クリックし、settingsを押します
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2261812/8f77d66f-5b0b-c29f-4460-3956f0a1e953.png)

2. 左のバーから、windows powershellを押します
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2261812/69c7d83d-e301-c5ac-582a-71883731a4ac.png)

3. Appearanceを押し、Font face から　Hack　Nerd　Fontを選択します
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2261812/a12b803a-4422-5d34-14d9-927a9ca84aa5.png)

4. 保存してpowershellを開くとフォントが変わっているはずです


### 補足
nvim-treeの場合、アイコンが表示されます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2261812/d9d2c97a-d337-0d57-66e0-9a57d584719a.png)
【Rails】Railsチュートリアルの追加機能～フォロワー通知 Vol.1～

railsチュートリアル第7版を始めて1か月の初心者です。
今回はRailsチュートリアルで作成したアプリにフォロワー通知機能を追加するための方法を説明していきたいと思います。
フォロワー通知編は今回のメーラー作成、次回の通知機能のON/OFF切替実装の全2回を予定しています。
# 目次
- [実装した機能詳細](#実装した機能詳細)
- [メール送信のためのメソッドを作成](#メール送信のためのメソッドを作成)
- [メール本文の作成](#メール本文の作成)
- [テスト用ビューの追加](#テスト用ビューの追加)
- [メーラーのテストの作成](#メーラーのテストの作成)
- [メール送信用メソッドを使う場所に追加](#メール送信用メソッドを使う場所に追加)


# 実装した機能詳細
- フォローされたらメールで通知がくる
- フォロー外された場合は通知は特になし
- メールにフォロワーを見るページのリンクなどは一切つけない
※今回は新たにrails generateすることなく実装を進める

私は以上のような最低限の機能を実装しました。

# メール送信のためのメソッドを作成
```ruby:/app/mailers/user_mailer.rb
def follow_notification(user, follower)
  @user = user
  @follower = follower
  mail to: user.email, subject: "#{@follower.name} started following you"
end
```
上記のコードをもともとあったメーラーのファイルに追加しました。

# メール本文の作成
HTMLとテキストのメール本文を作成するために
`/app/views/user_mailer/follow_notification.html.erb`と`/app/views/user_mailer/follow_notification.text.erb`を新たに作成し、以下のコードを追加します。
###### メール本文（HTML）
```html:/app/views/user_mailer/follow_notification.html.erb
<h1>You are followed</h1>

<p>Hi <%= @user.name %>,</p>

<p>
 <%= @follower.name %> started following you!
</p>
```
###### メール本文（text）
```ruby:/app/views/user_mailer/follow_notification.text.erb
You are followed

Hi <%= @user.name %>,

<%= @follower.name %> started following you!

```

# テスト用ビューの追加
```ruby:/test/mailers/previews/user_mailer_preview.rb
# Preview this email at
# http://localhost:3000/rails/mailers/user_mailer/follow_notification
def follow_notification
  user = User.first
  follower = User.second
  UserMailer.follow_notification(user, follower)
end
```

# メーラーのテストの作成
```ruby:/test/mailers/user_mailer_test.rb
test "follow_notification" do
  user = users(:michael)
  follower = users(:inactive)
  mail = UserMailer.follow_notification(user, follower)
  assert_equal "#{follower.name} started following you", mail.subject
  assert_equal [user.email], mail.to
  assert_equal ["from@example.com"], mail.from
  assert_match user.name, mail.body.encoded
  assert_match follower.name, mail.body.encoded
end
```
`from@example.com`の部分は自分で設定した送信用メールアドレスにすることを忘れないようにしてください。

# メール送信用メソッドを使う場所に追加
先程作成したメソッドを使用するためのコードを記載します。
```ruby:/app/models/user.rb
...

# ユーザーをフォローする
  def follow(other_user)
    following << other_user unless self == other_user
    if other_user.follow_notification
      UserMailer.follow_notification(other_user, self).deliver_now
    end
  end

...
```

以上のコードを追加することによって最低限フォロワー通知をすることができるようになります。

次回の記事では、フォロワー通知のON/OFFができるように実装していきます。


#### 参考

https://railstutorial.jp/

https://qiita.com/sconeman/items/6187670f7412d387f632
JavaScript：asyncとawait 簡単なサンプル

# asyncとawaitのサンプル

#### 下記のサンプルはMDNからコピーし、自分の理解をメモ
＊方法：**Promise** を利用し、同期処理を非同期になる。
＊戻り値：**resolve('resolved');** で実現する。

```javascript:async&await.js
function resolveAfter2Seconds() {
  return new Promise((resolve) => {
    setTimeout(() => {
      resolve('resolved');
    }, 2000);
  });
}

async function asyncCall() {
  console.log('calling');
  const result = await resolveAfter2Seconds();
  console.log(result);
  // Expected output: "resolved"
}

asyncCall();
```
Railsのスコープとは？ヘルパーとの違いも解説！

Railsを使って開発をしていると、よく使うクエリを簡潔に書きたいと思うことが多いですよね。そんな時に役立つのが「スコープ」です。この記事では、スコープの使い方と、よく比較される「ヘルパー」との違いについて解説します。

## スコープの基本
スコープは、モデルに定義するクラスメソッドの一種で、特定のクエリを簡潔に書くためのものです。以下は、スコープの基本的な使い方の例です。

```ruby
class Article < ApplicationRecord
  scope :published, -> { where(published: true) }
end
```

このスコープを使うと、以下のように簡潔にクエリを書くことができます。

```ruby
@articles = Article.published
```

## スコープの特徴
チェーン可能: スコープは他のクエリメソッドやスコープと組み合わせて使用することができます。
条件付きスコープ: 引数を取ることができ、動的にクエリを生成することが可能です。
デフォルトスコープ: 全てのクエリに適用されるスコープを定義することができますが、使用する際は注意が必要です。
ヘルパーとの違い
スコープとヘルパーは、役割や使用場所が異なります。

#### 使用場所

**スコープ:** モデル内で使用されます。
**ヘルパー:** ビュー内で使用されます。

#### 目的

**スコープ:** クエリを簡潔に書くためのもの。
**ヘルパー:** ビューのロジックを整理し、ビューのコードを簡潔に保つためのもの。

#### 定義場所

**スコープ:** モデルファイル内で定義されます。
**ヘルパー:** app/helpersディレクトリ内のファイルで定義されます。


## まとめ
スコープは、よく使うクエリを簡潔に書くための強力なツールです。一方、ヘルパーはビューのロジックを整理するためのものです。それぞれの特性を理解し、適切な場所で使用することで、Railsアプリケーションの開発がより効率的になりますね！
運用上の優位性（ Operational Excellence）

それは、業務を効率的に実行していくことでサービスの価値を高め、開発のプロセスや手順を継続的に改善していくことです。

🍀運用をコードとして実行する
クラウドではインフラ構成をコードとして定義し、コードを変更することでインフラ構成を更新できます。
コードとして自動化することで作業効率を向上させたり、人為的なミスを防止できます。

🍀小規模かつ可逆的な変更を頻繁に行う
大きな変更を一気に行うと問題が発生したときの切り分けができず、対応が遅れる可能性があります。
小さな変更を繰り返しながら、徐々に最終目標に近づけていくことが重要です。
小さな変更であれば失敗した場合にもとに戻すことも行いやすく、失敗によるリスクを下げられます。

🍀運用手順を定期的に改善する
システムの運用を行う手順は定期的に改善することが重要です。
手順の中で効率のよくない箇所を見直したり、新しい仕組みを導入するなど、様々な改善ポイントがあります。
実際に作業を行う人の意見を取り入れたり、手順のロールプレイングを行うなどの方法で改善点を見つけることができます。

🍀障害を予想する
障害を予想し、それに耐えられるようにシステムを構成することが重要です。
障害は必ず発生します。
障害から目を背けるのではなく、事前に障害を予測して回避策を取ったり、障害が発生してもシステムが異常な動作を行わないようにすることが重要です。

🍀運用上のすべての障害から学ぶ
システムの運用を行う上で発生する障害は、改善のための大きなインプットとなります。
障害が発生したら、今後その障害が発生しないようにシステム構成や手順を改善していくことで、サービスの価値を高めることができます。
障害が発生したら担当者を攻め立てるのではなく、どのように改善していくかに注目してポジティブに対応していくことが重要です。

■カジュアル面談受付中
下記からスケジュール設定可能となります。
https://t.co/91lhm0x2JE
～・～・～・～・～・～・～・～・～・～・～
LinkedIn
https://www.linkedin.com/in/akkodis-okada/
Twitter(X)
https://twitter.com/edamamecook
nvim-treeを起動時に常に開くようにする

# 概要
[nvim-tree](https://github.com/nvim-tree/nvim-tree.lua)を使用しています。
```nvim hoge.txt```をしたときに、常にファイルツリーが表示されてほしいと思いました。その際の設定をまとめます。

# やったこと

この設定を```init.lua```に追加して動きました。

```lua:init.lua
-- automated settings
local function open_nvim_tree()
    require("nvim-tree.api").tree.open()
end

vim.api.nvim_create_autocmd({ "VimEnter" }, { callback = open_nvim_tree })

```

# 公式ドキュメント

https://github.com/nvim-tree/nvim-tree.lua/wiki/Open-At-Startup#always-open-nvim-tree
【ChatGPT無】深津式→7Rに書き直す

:::note info
本記事は、ChatGPT（無料版）で
行なっております。GPT4での確認
はできておりません。あしからず。
:::

　どうも、カーブミラーです。

　今回は、
　　深津式汎用プロンプトを
　　　野口竜司氏の7Rプロンプトに
　　　　沿って、書き直してみます。
***
　前回の記事。
[【ChatGPT】野口竜司氏提示、7Rプロンプト](https://qiita.com/kabumira/items/77bcfeac699673d99c09)
***
　プロンプトの
　　フレームワークと言えば、
　　　深津式汎用プロンプトですね。
```Text:深津式汎用プロンプト
# 命令書:
あなたは{プロの編集者}です。
以下の制約条件と入力文をもとに{最高の要約}を出力してください。

# 制約条件:
・文字数は300文字程度。
・小学生にもわかりやすく。
・重要なキーワードを取り残さない。
・文章を簡潔に。

# 入力文:
{入力文章}

# 出力文:
```
　この深津式汎用プロンプトを
　　7Rプロンプトに当てはめると、
　　　こんな感じでしょうか。
```Text:7Rプロンプト
# Request（依頼）
{入力文章}の{最高の要約}を出力してください。

# Role（役割）
あなたは{プロの編集者}です。

# Regulation（形式）
・{最高の要約}。

# Rule（ルール）
・文字数は300文字程度。
・小学生にもわかりやすく。
・重要なキーワードを取り残さない。
・文章を簡潔に。

# Reference（参照知識・例）
{入力文章}
```
　# Review & Refine（評価・改善）
　# Run Scenario（実行シナリオ）
　　がありませんけど、
　　　深津式汎用プロンプトには
　　　　該当する部分が
　　　　　ありません。
***
　とりあえず、
　　こんなところですね。

　実際のプロンプトに
　　するのは、次回です。　　

　まだ、勉強中なので。
　
***
　続けて、
　　記事を書きました。
　　　参考にしてください。

『7Rプロンプトに
　　関して、書いた記事』

　最初の記事。
[【ChatGPT】野口竜司氏提示、7Rプロンプト](https://qiita.com/kabumira/items/77bcfeac699673d99c09)

　次の記事。
[【ChatGPT無】深津式→7Rに書き直す](https://qiita.com/kabumira/items/83a6999b21e9484016ea)

　次の記事。
[【ChatGPT無】7R（簡易プロンプト）を簡単な指示と比較した](https://qiita.com/kabumira/items/a4cd4ec25a7cefbb95c7)

　次の記事。
[【ChatGPT無】7Rプロンプトで、ワードミキサーPrompt。](https://qiita.com/kabumira/items/67928a476c259de7701a)

　次の記事。
[【ChatGPT無】7R（簡易）で、長話を短くするには、と聞いてみた](https://qiita.com/kabumira/items/8d807cda0ca5ff1dea25)
***
【統計学】集計表

# ０.はじめに
大学で統計学の講義を受講している者です。
用語や概念をまとめて以下の項目に分類しています。

##### 統計学学習全体像
[【統計学】概要](https://qiita.com/AkihideKato/items/084ace871bb867635f1d)
[【統計学】度数・偏差・分散](https://qiita.com/AkihideKato/items/dd06906886521a27bb39)
[【統計学】係数・回帰](https://qiita.com/AkihideKato/items/ea4b64a8a69b21ff25ac)
[【統計学】集計表](https://qiita.com/AkihideKato/items/3c139087ec6f5462e2b4)
[【統計学】集団・標本](https://qiita.com/AkihideKato/items/dae23d8d09a764e158aa)
[【統計学】分布](https://qiita.com/AkihideKato/items/6daf349eef4e98b38a91)
[【統計学】期待値・推定・信頼度](https://qiita.com/AkihideKato/items/43672f6d69af9cebc5e6)
[【統計学】統計的検定](https://qiita.com/AkihideKato/items/6b8eff70b66ee3513141)
# １．集計
### 集計例
- **``レディーメード集計``**：あらかじめ既成された集計
- **``オーダーメード集計``**：要望に基づいて加工された集計
- **``プリコード``**：事前に割り当てた番号、そのままデータ値となる
- **``アフターコード``**：自由回答で得られた回答に対して実査後にコードを割り当てるコード


## クロス集計表
2つ以上の質的変数を組み合わせたもの
**変数間の関連を表す手法**
1次元で表示することも可能だが煩雑になる表となる
度数分布表2つを組み合わせた2次元状にしたような表

### 変数の表現
行側の変数から表現する
度数``frequency``よりある``行（i）``ある``列（j）``のセル表現をfijと表現
よって1行目2列目の度数はn12と表現する

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/581998/a1f00e3f-cebb-7ff0-a4f7-17bafa1e2fa9.png)

### 割合の表現
クロス集計だとそれぞれ値の重みは（）カッコ内で割合で表される場合がある
``23``や``34``など相対度数で表しても理解しにくい場合に便利
図は行間で相対度数を表しているが列関係を主張したい場合は列による相対度数を表記する

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/581998/36ae7428-46fd-d209-4a47-9363810bdc9b.png)

### 連関とは
相関係数を表示した場合の関連性の強さを知りたい		
そこで新たに連関係数という指標を用いる		
連関があるとは **``変数同士異なる関連性があるということ``**	
互いに関係性があること
- **``ＡとＢの指標が同じようなものであれば、連関が無い``**
- **``ＡとＢの指標が互いに反発しているのであれば、連関がある``**
係数としてオッズ・ファイ係数を学ぶ	

## 多重クロス集計表
質的変数x yに加え第三変数zとしたとき、zを取り扱う分析を行う	
zをカテゴリーごとに集計してxとyの関係を導き出すのが目的	
- **``zがAのときの集計表A``**
- **``zがBのときの集計表B``**

### 例			
クロス集計「性別ごとにケーキを好んで食べる割合」がある		
ここでは「性別」「ケーキ」が変数x,yとなっている		
新たに「年齢層」ごとに集計したい：変数zを利用する		
多重クロス集計により		
- **``"10代"年齢層(変数z)が性別ごとにケーキを好んで食べる割合``**
- **``"20代"年齢層(変数z)が性別ごとにケーキを好んで食べる割合``**
- このパターンの集計表が必要になる

3変数を主に使う	
4変数を扱うのは極めて把握しにくく難しい	

### 多重クロス集計により本来比べてた変数同士が媒介関係となる
性別と事故歴の関係より		
男性は女性より事故歴が多い	
果たして男性だからか？	
走行距離という第三変数を用いてクロス集計及びファイ係数を確かめる	
走行距離が長いほど事故歴が多く男性が走行距離が長い	
よって本来仮説を立てた性別と事故歴の関係は媒介関係	
間に走行距離という変数を挟んだ関係性である
【react-fook-form】 Form内でEnterキーを押した際にSubmitをさせない方法

react-hook-formで作成したForm内でEnterキーを押すと、Submitが走り、勝手に次の未入力のinputにカーソルが移動したり、画面がリロードされます。

それを防ぐようにするには以下のようにすればOKです。

```typescript
const Hoge:FC<Props> = ({props}) ={
  const checkKeyDown = (e: any) => {
    if (e.key === 'Enter') e.preventDefault();
  };
return (
   ...
   <input 
     type="number"
     onKeyDown={(e) => checkKeyDown(e)}
   />
   ...
 );
};
```
https://github.com/orgs/react-hook-form/discussions/2549

# .preventDefault()
https://javascript.programmer-reference.com/js-key-preventdefault/
【Laravel】ログイン後に別のページに遷移する方法

## ログイン後、トップページに遷移させたい場合
app\Providers\RouteServiceProvider.php
以下のように修正する。
```RouteServiceProvider.php
public const HOME = '/';
```
HOME定数の値を変更する。

RouteServiceProviderクラス：Laravelのルーティングを管理するクラス
【Laravel】セッションタイムアウト時にログインページ遷移する方法

## セッションタイムアウトが起きる条件
・ログインした後、しばらく放置したあと操作を行う。
・formタグ内に`@csrf`を記述し忘れる。

## セッションタイムアウト時にログインページに遷移させる
app\Exceptions\Hander.php に以下のように記述する。
```Hander.php
// 以下のuse文を追加する。
use Illuminate\session\TolenMismatchException;

// 省略

public function register()
    {
        $this->reportable(function (Throwable $e) {
            //
        });
    }

	// ※ここから記述する※
    // セッションタイムアウト時はログインページにリダイレクトさせる
	public function render($request, Throwable $exception) {
		if ($exception instanceof TokenMismatchException) {
			return redirect()->route('login');
		}

		return parent::render($request, $exception);
	}
}
```
↑if文を使用して、セッションタイムアウト時にログインページにリダイレクトさせる処理


## 参考サイト
セッション切断時にPOST通信をし419エラーになるのを防ぐ方法
https://zenn.dev/yuzuyuzu0830/articles/3952e36dc91705
Sorry to interrupt

[まとめページに戻る](https://qiita.com/Keiji_otsubo/items/60afc2a8d211b6f7d89f)
[まとめN～Z](https://qiita.com/Keiji_otsubo/items/92f92bb9f668ca9688be)



質問の仕方

Can you cook the Technical Stuff and post details of the error?
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/9fa3ba81-d778-b833-b90a-b7735b8fcd35.png)



# ヘルプにあるもの

+ [Error "Sorry to interrupt. This page has an error. You might just need to refresh it" in Outlook Integration](https://help.salesforce.com/s/articleView?id=000382444&type=1)

# Knowledge articles

+ [Anyone else getting this dialog box when editing Knowledge articles? I've rebooted my computer and the problem still persists.](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V00007F1sHq)

:::note alert
Failed to execute 'setItem' on 'Storage': Setting the value of 'tinymce-autosave-/lightning/r/Knowledge__kav/ka0Hu000000NxjTIAS/view?ws=%2Flightning%2Fr%2FKnowledge__kav%2Fka0Hu000000NxVnIAK%2Fview-mce_34-draft' exceeded the quota.
:::

:::note
Please check this article.

https://trailhead.salesforce.com/trailblazer-community/feed/0D54V000077Cxh6SAC
:::
【Laravel】ユーザーがログイン済みか認証する方法

ログイン機能を実装した場合、ログインせずにトップページにアクセスすると、
以下のエラーが発生する。
http://localhost/laravel-todo-app/public/
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3323019/43aad3ad-fa60-4d0b-2637-65ba7fc43ef4.png)

## ルーティングでmiddleware('auth')メソッドを使用する。
routes/web.php でルーティングの末尾に`middleware('auth')`メソッドを追加する。
```web.php
// トップページでログイン済みか認証を行う
Route::get('/', [GoalController::class, 'index'])->middleware(auth);
```
<br>

トップページにアクセスすると、ログインページにリダイレクトする。
http://localhost/laravel-todo-app/public/
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3323019/f9c02e0f-a2e3-8192-8c22-65ab2a31503a.png)
Github CopolitをVS Codeで試してみた

Githubの公式のcopilotを使ったVS Codeのページを参考にしました
https://docs.github.com/ja/copilot/getting-started-with-github-copilot?tool=vscode



# copilotの導入
copilot試してみました
まず無料トライアルがあるので課金しなくて試すことはできます

![スクリーンショット 2023-08-24 9.36.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/574173/a8ca554c-9c36-cc31-4a64-b99619506107.png)

# VS Codeで拡張機能をインストール
拡張機能の検索窓にcopilotと入れると一番上にきます

![スクリーンショット 2023-08-24 10.44.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/574173/4f33bda3-24d7-1c65-e516-d112234e4430.png)



# 早速試してみた
コードの補完してくれるくらいでそれっぽいコードを提案してくれるんですが
アーキテクチャ理解せずに頼るとひどいコードで出すことになります。
すでにコードがいくつか書かれているところにコードを書いていくと途中でコードの提案が灰色でされて
タブキーを押すとまるっと追加してくれる感じですね。
わかってる人にとっては結構便利な印象です。ちょっと直せばいいわけなので

![スクリーンショット 2023-08-24 10.18.45.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/574173/444a89b3-f96a-32ca-e88d-bbbce8899b40.png)


# 明確な命名をすると効果的
function名を明確に命名できているとより欲しい関数を提案してくれますね

![スクリーンショット 2023-08-24 10.20.36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/574173/78c1cab7-49f8-9c3d-5b44-4e05d6042149.png)

# 注意点
copilotの注意点はこのチェックをいれてしまうとクレデンシャル情報を載せてる時に流出しかねないのでこれはチェック入れない方が良さそうです
公開コードに一致するコードを使うかどうかもライセンス侵害になりかねないのでブロックにしておいた方が無難です

![スクリーンショット 2023-08-24 10.37.10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/574173/c56604ff-fd0a-83ab-d06b-517f5be826da.png)

調査されてる方の記事もあるので参考に
https://zenn.dev/miyajan/scraps/3567cee380280c

チェックを入れてなくてもcopilot自体には送信しちゃうのでそこはユーザーの判断になりますね


# 参考
・https://docs.github.com/ja/copilot/getting-started-with-github-copilot?tool=vscode
・https://zenn.dev/miyajan/scraps/3567cee380280c
[備忘録]Python YAML　ログ　書き方

# pyファイル
```
import logging

class Common:
    config: dict
    logger: logging.Logger

    def __init__(self):
        config_file = load_yaml('./basic.yaml')
        self.config = load_yaml(config_file['configuration_file'])
        filename = "xxx"
        create_dir(os.path.dirname(filename))
        logging.basicConfig(
            filename=filename,
            level=get_log_level(self.config['log']['level']),
            format=self.config['log']['format']
        )
        self.logger = logging.getLogger()

    
    # 設定ファイルのパスを取得する
    def get_filepath(dirname: str, filename: str) -> os.path:
        return os.path.abspath(os.path.join(os.path.dirname(__file__), f'./{dirname}/{filename}'))
    
    # yaml を読み込む
    def load_yaml(filename: str) -> dict:
        file_path: str = get_filepath(dirname='configures', filename=filename)
        try:
            with Path(file_path).open('r', encoding='utf-8') as stream:
                return yaml.full_load(stream)
        except FileNotFoundError:
            print(f'{file_path} が見つかりません。')
            raise
    
    # ディレクトリを作成する
    def create_dir(dirname: str) -> None:
        os.makedirs(dirname, exist_ok=True)

    # ログレベルを返す
    #   指定が非対応の場合は DEBUG
    def get_log_level(level: str) -> int:
        if level == 'info':
            return logging.INFO
        elif level == 'warn':
            return logging.WARN
        elif level == 'error':
            return logging.ERROR
        return logging.DEBUG
```

# yamlファイル
```
# ログ出力に関連する設定
log:
  # ログ出力先ディレクトリ
  #   app からの相対パスまたは絶対パスで記述すること
  dir: './log'
  # ログ・ファイル名
  #   datetime の書式に従うこと
  filename: '%Y-%m-%d.log'
  # ログ書式
  #   logging の書式に従うこと
  format: '%(asctime)s:%(levelname)s:%(message)s'
  # ログレベル
  #   'debug', 'info', 'warn', 'error' に対応
  level: 'debug'
```
Windows11のMicrosoft IMEのキーアサインを変更する

WindowsのIME切り替えキー[半/全]はその時の入力モードによってふるまいが変わるので、変換キーをIME ONに, 無変換キーをIME OFFに割り当てる。
1. 通知領域のIMEアイコンを右クリックし、設定を選択する。
1. 設定 > 時刻と言語 > 言語と地域 > Microsoft IMEページが表示されるので、キーとタッチのカスタマイズを選択する。
1. 設定 > 時刻と言語 > 言語と地域 > Microsoft IME > キーとタッチのカスタマイズページが表示されるので、キーの割り当てを以下のように変更する。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/87548/f9a3b81f-4753-c313-3cf6-cb6ece5da094.png)

古いバージョンのMicrosoft IMEを使用している場合は、以下の通り。
1. 設定 > 時刻と言語 > 言語と地域 > Microsoft IME > 全般ページを開き、詳細設定を開く。
1. Microsoft IMEの詳細設定ダイアログが開くので、全般タブの編集操作 > 変更を選択する。
1. 設定ダイアログが開くので、キー設定タブのユーザー定義で、キー割り当てを以下のように変更する。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/87548/11cd6232-483c-c343-4bc6-0f389b50853a.png)
[Swift漫談]ホワイト課長が退陣したのでswiftで今の気持ちをコーディングしてみた

[1.どういうことか？](#1-どういうことか？)
[2.今の気持ちをコーディングしてみた](#2-今の気持ちをコーディングしてみた)
[3.おわりに](#3-おわりに)

# 1.　ホワイト課長退陣？
どういうことか？
- 経緯
    - 今のホワイト課長とは転職の面接(本田技研->iOS開発)の時に初めてお会いしました。
    - 課長の人柄の良さ、部下からの慕われ具合、なにより定時で社員が帰れる職場環境作りをしていることろに、かなりの魅力を感じて、現職に決めました。

    **そんな課長がなんと部長に昇進してしまった**のです。
    課長の「職場環境づくりへの想い」に魅力を感じて入社したのに、、、

# 2. 今の気持ちをコーディングしてみた
- 今の気持ちは以下のコードです。
    ~~~swift: nowFeeling.swift
        var isHappy = false
        var status = "会社員"
        var boss = "ホワイト課長退陣"

        
        while true {
            print("課長ーーーーT_T")

            if boss == "新ホワイト課長" {
                isHappy = true
                break
            }　else if status == "フリーランス" {
                isHappy = true
                break
            }
        }
    ~~~

# 3. おわりに
入社した時に課長に魅力を感じていることを告げると、「私がいなくなってもどこでも居心地が良いことろに行けるように今のうちに技術を盗んでください。」と言われたことを思い出しました。
本当に良い課長さんだった。。
昇進おめでとうございます！と同時に悲しい気持ちでいっぱいです。
私もそんな部下から慕われる人間になれるように鍛錬いたします。

今回も最後まで本記事を読んでいただきありがとうございました！
MacでCrystalアプリを配布する方法

:::note info
この記事は、[Crystal Forum](https://forum.crystal-lang.org/) の記事をChatGPTを用いて日本語に翻訳した上で注釈をつけたものです。オリジナルの内容を知りたい場合は下記のリンクからソースに当たってください。
:::

https://forum.crystal-lang.org/t/distributing-crystal-apps-on-mac-is-this-correct/5904


# Mac上でCrystalアプリを配布する

静的リンクを用いずにMacOS上でCrystalアプリを配布する場合、必要な共有ライブラリと依存関係をアプリケーションにバンドルする必要があります。また、アプリケーションが実行時にこれらのライブラリを見つけられるようにするスクリプトを作成する必要があります。以下に一般的な手順を示します：

1. **Crystalプログラムのコンパイル**: 必要な共有ライブラリと依存関係を含めて、Crystalアプリケーションを`crystal build` コマンドを使用してビルドします。

2. **依存関係の特定**: バイナリが依存する動的ライブラリを調査するためにotoolのようなツールを使用します。以下のコマンドをコンパイルしたバイナリで実行します：

    ```sh
    otool -L your_executable
    ```

    これにより、実行ファイルがリンクされている共有ライブラリが一覧表示されます。

3. **共有ライブラリのバンドル**: 必要な共有ライブラリをアプリケーションと共に配布するディレクトリにコピーします。これらをアプリのバンドル内の `libs` フォルダに配置する場合があります。

4. **ライブラリパスの更新**: `install_name_tool` コマンドを使用して、バイナリ内の共有ライブラリへのパスを変更します。それをあなたが配布にバンドルしたライブラリの場所を指すようにします。以下のようなコマンドを各共有ライブラリに対して使用します：

    ```sh
    install_name_tool -change old_path new_path your_executable
    ```

    `old_path` はライブラリへの現在のパスであり、`new_path` はアプリのバンドル内のライブラリへの相対パスまたは絶対パスです。

    **kojix2注**：4の手順と、5の環境変数を設定する手順はやや矛盾するようにも見えます。次のサイトなどを参考にすると、うまくいくと5の手順を使わずにすむかもしれません [install_name_tool to update a executable to search for dylib in Mac OS X](https://stackoverflow.com/questions/33991581/install-name-tool-to-update-a-executable-to-search-for-dylib-in-mac-os-x)

    ```sh
    install_name_tool -change libtest.dylib @loader_path/../lib/libtest.dylib myapp 
    install_name_tool -add_rpath "@loader_path/../lib" myapp
    ```

5. **スタートアップスクリプトの作成**: `DYLD_LIBRARY_PATH` 環境変数を設定して、バンドルした共有ライブラリのディレクトリを含めるスタートアップスクリプトを作成します。このスクリプトはその後、あなたのCrystalバイナリを実行します。基本的な例はこちら：

    ```bash
    #!/bin/bash
    export DYLD_LIBRARY_PATH="./libs:$DYLD_LIBRARY_PATH"
    ./your_executable
    ```

6. **アプリケーションのパッケージング**: コンパイルされたバイナリ、共有ライブラリ、スタートアップスクリプトを一緒にバンドルし、.dmgや.tar.gzファイルなどの配布可能な形式にまとめます。

7. **アプリケーションの配布**: パッケージ化されたアプリケーションを、あなたのウェブサイトからの直接ダウンロード、アプリストアなど、適切なチャネルを通じてユーザーと共有します。

この手順に従えば、Crystalアプリが依存する共有ライブラリがアプリに含まれ、実行時に正しく位置付けられることが保証されます。これは、バイナリに静的にリンクされていなくてもです。これは共有ライブラリの慎重な管理を必要としますが、macOS上での配布を可能にします。

### 参考Makefile

```makefile
APP_NAME = your_executable
LIBS_DIR = ./libs
SRC_DIR = ./src
BUNDLE_DIR = ./bundle
STARTUP_SCRIPT = startup.sh

# Build your application
build:
	crystal build $(SRC_DIR)/main.cr -o $(BUNDLE_DIR)/$(APP_NAME)

# Copy and update library paths
libs:
	mkdir -p $(BUNDLE_DIR)/$(LIBS_DIR)
	# Use otool to identify and copy the required libraries, then update their paths
	otool -L $(BUNDLE_DIR)/$(APP_NAME) | awk '/path_to_required_lib/ { system("cp " $$1 " $(BUNDLE_DIR)/$(LIBS_DIR)"); system("install_name_tool -change " $$1 " $(LIBS_DIR)/" $$1 " $(BUNDLE_DIR)/$(APP_NAME)"); }'

# Create startup script
startup-script:
	echo '#!/bin/bash' > $(BUNDLE_DIR)/$(STARTUP_SCRIPT)
	echo 'export DYLD_LIBRARY_PATH="$(LIBS_DIR):$$DYLD_LIBRARY_PATH"' >> $(BUNDLE_DIR)/$(STARTUP_SCRIPT)
	echo './$(APP_NAME)' >> $(BUNDLE_DIR)/$(STARTUP_SCRIPT)
	chmod +x $(BUNDLE_DIR)/$(STARTUP_SCRIPT)
```
AWSのパブリックIPv4利用確認について

# ■概要
2024年2月1日より、従来は無料だったパブリックIPv4アドレスに対して、1IPアドレスあたり 0.005 USD/時間 が課金されるようになりました。
それに伴って現在利用中のIPv4アドレスは一度見直すのが良いでしょう。

新着情報 – パブリック IPv4 アドレスの利用に対する新しい料金体系を発表
https://aws.amazon.com/jp/blogs/news/new-aws-public-ipv4-address-charge-public-ip-insights/

![20230824094419.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/954355/ed238c26-59de-0605-3da1-1f1358218c6d.png)

# ■パブリックIPv4インサイト
普段触れる機会がなかったんですが、IPv4インサイトはVPC IP Address Manager (IPAM) の機能の一部となるようです。
IPv4インサイトのみを利用している場合は特に利用料金は発生しません。

以下さくっと確認方法です。
AWSコンソールよりVPCへ以降し、「VPC IP アドレスマネージャー」を選択しましょう。

![VPC1_20230824085932.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/954355/822b3581-6dc4-6e17-58c7-2d926e76d2df.png)

「パブリック IP に関するインサイト」に進みます。

![インサイト1_20230824090721.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/954355/8ce8784c-a36f-3cad-2764-40da18eb7776.png)

##### 　このページで利用状況を確認できます。
ここで気づいたのが余計なEIPが残ってるみたいですね…特に利用しなければこういうのは解放しておきましょう。

![インサイト2_20230824091131.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/954355/0a89d984-9ce8-ebc2-4c27-1ddeaf82a0f2.png)

##### IPv4の利用状況は下記のような図で表示されます。
「EC2パブリックIP」は主にインスタンスへ自動割り当てしたIPになり、
「Amazon所有EIP」は取得しているEIPになります。
「サービスマネージドIP」については、ELBやCloudFront等の下で動いているIPが表示されるようです。

![インサイト3_20230824091726.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/954355/62af21c2-10df-1415-ca5c-414f378efbf8.png)

##### 更にページ下部にはIP利用の詳細も表示されます。
有料化も始まるので定期的に確認すべき？ですかね。

![インサイト4_20230824092629.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/954355/3b984d12-78bc-1bbf-dd5c-5966a64c5552.png)

# ■IPv4の削減
インスタンス接続に利用しているIPの場合、インスタンスに紐づくIPは撤廃し、
EC2 Instance Connect (EIC) Endpointを利用するようにするのも良いでしょう。
下記も参考までに。

EC2へのSSHでパブリックIP、IGWが不要になりました
https://qiita.com/zenden/items/cc0d4c7a733b40f1a302

以上です！
AWS EBS と EFSの違い　（初学者向け）


 # はじめに
IT業界に入り、知識0からインフラエンジニアになろうとしている者です。
AWSのSAA取得に向け勉強しているのですが、

EBSとEFSの違いがわからない→わかった気がする！

に変わった理由を交えてEBSとEFSについて説明していきます。
## EBSとは
   Amazon Elastic Block Store (Amazon EBS) はAmazon Elastic Compute Cloud (Amazon EC2) 向けに設計された、使いやすく、スケーラブルで、高性能なブロックストレージサービスです。
## EFSとは
Amazon Elastic File System の略で
サーバレスなファイルシステムです。
## 2つの違い
上記の説明を見たとき私も？？？となりました。

ここで理解する上で大切なNASについて紹介します。

###### NAS
NASとは、ネットワーク（LAN）上に接続することができるハードディスクです。

ハードディスクというとUSBみたいなものを想像しますよね。
一般的なハードディスクはパソコンと**1対1**で直接接続して使用します。

しかし！
NASはネットワークに接続しているハードディスクなので、
パソコンと**1対多数**の接続ができ複数のパソコンから同じデータにアクセスができます
＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿＿
### EBSとEFSの違い

**EBS**はEC2インスタンスにアタッチされたサーバと1対1な
ブロックストレージ（USBとかSDカードみたいなやつ！）

**→複数のインスタンスで同時に共有できない**

**EFS**はNAS に似たファイルストレージ

**→最大数千の EC2 インスタンスからの同時アクセスが可能**

また、この説明を聞いたら想像がつくと思いますが
EFSのほうが値段が高いです
### 注意点
EBSのなかのプロビジョンドIOPS SSD (io1またはio2)は
EBSマルチアタッチが可能
→同じアベイラビリティゾーン(AZ)にある複数のインスタンスに共有できるらしい。

ただし、最大アタッチ数が16個だし、R5bインスタンスにはアタッチできないなどいろいろな
制限があるのでEBSマルチアタッチ≠EFSであるのは確か。
## まとめ
知識０のIT業界1年目、AWS勉強開始1か月も満たない人の解釈ではありますが、、、
「ブロックストレージとファイルストレージっていう違いがあるよ」と言われてもわからないので

* EFSは多くのサーバでデータを共有
* EBSはサーバと一対一データのやり取り
* EFSのほうが高い（コスト）

と解釈しました。
自分はわりと理解した気になっていますが
皆さんはどうでしょうか？
サイトをSSL化するためにLet's encryptしてみる

## 背景
現在制作しているサイトがブラウザの検索窓から適当なキーワードを振っても表示されません。
恐らく、サイトがSSL化していないためだと考えられます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3476751/5ee1b438-c665-ec0e-41b4-7a9155cae226.png)

以下は、「サイトがSSL化されていないことに関するGoogleの見解をまとめて下さい。」という質問に対する、perplexityの回答です。

Googleは2014年、2015年、2017年からHTTPS（SSL）の採用を推進してきました[3]。2018年7月24日から、Google ChromeはSSLをサポートしていないすべてのページに警告を表示するようになりました[4]。SSL証明書を持たないウェブサイトは、ユーザーのデータがハッカーによって盗まれるリスクがあるため、ユーザーにとって危険です。また、SSL証明書はSEOにおいても重要な要素となっており、GoogleはSSLの採用がSEOにとって重要であると述べています[6]。Googleのパートナーは、すべての広告スロットにSSL対応のクリエイティブを必要としています[5]。SSL証明書には無料と有料の2種類があります。無料のSSL証明書はLet's Encryptが提供しており、有料のSSL証明書はより高度なセキュリティ機能を提供しています[6]。
> Citations:
[1] https://www.kagoya.jp/howto/rentalserver/webtrend/chrome-ssl/
[2] https://www.non-standardworld.co.jp/20203/
[3] https://ascii.jp/elem/000/004/074/4074894/
[4] https://www.chaco-web.com/blog/chrome68-aossl/
[5] https://www.chaco-web.com/blog/what-is-ssl/
[6] https://lucy.ne.jp/bazubu/ssl-seo-42414.html

ということで、Let's encryptしてみましょうか。

## Let's encrypt

### Let's encryptとは
Let's Encryptは、無料で利用可能なSSL証明書を提供する認証局の一つであり、2016年4月に正式運用を開始しました。Let's Encryptを運営するISRGは、SSLの普及を目的に設立された非営利団体であり、誰もが手軽にSSLを導入できるようにしようという理念の下で運営されています。Let's Encryptは、SSL証明書を無料で提供することができるのは、多くのIT企業がスポンサーとして支援を行っているためです。スポンサードしている企業には世界的な大企業も多く、無料サービスと言っても運営母体は信頼できるものと言えます。Let's Encryptは、Linux webサーバーで2つのコマンドを実行するだけでHTTPS暗号化を設定し、証明書を取得してインストールすることができます[1][3][5]。

>Citations:
[1] https://www.stream.co.jp/blog/blogpost-42894/
[2] https://www.nic.ad.jp/ja/basics/terms/lets-encrypt.html
[3] https://ja.wikipedia.org/wiki/Let%27s_Encrypt
[4] https://letsencrypt.org/ja/
[5] https://faq.wadax.ne.jp/s/article/1706
[6] https://en.wikipedia.org/wiki/Let's_Encrypt

### Let's encryptの手順

Let's Encryptを使用してSSL証明書を取得する手順は以下の通りです。

1. 取得対象のコモンネームを決める。
2. certbotをインストールする。
3. SSL証明書を取得して設置する。
4. Webサーバーの設定でhttpsに対応させる。
5. http⇒httpsのリダイレクト設定を行う。

手順の詳細については、複数のサイトで解説されています[1][3][4][6]。また、手順によっては、コマンドラインでの操作が必要になる場合があります。

> Citations:
[1] https://youtube.com/watch?v=13NTn6WiQvU
[2] https://qiita.com/TsutomuNakamura/items/4166423699061e38d296
[3] https://oji-cloud.net/2020/09/29/post-5570/
[4] https://blog.senseshare.jp/encrypt.html
[5] https://www.nic.ad.jp/ja/basics/terms/lets-encrypt.html
[6] https://webree.jp/article/letsencrypt-install/


===
## SuiteXの仕様
* SuiteXでは、telnetやsshでサーバーに接続することはできない
    * ファイルのアップロード／ダウンロード、パーミッション変更等の作業は、FTPで接続する必要がある
    > サーバーにroot権限でssh接続できるサービスをお探しの場合は、以下のサービスをご検討ください。
・SuitePRO V4
・VPSクラウド
Amazon AppFlow

[まとめページに戻る](https://qiita.com/Keiji_otsubo/items/60afc2a8d211b6f7d89f)
[まとめA～M](https://qiita.com/Keiji_otsubo/items/f3ddedee6793bf1576f8)


+ [Amazon AppFlow received the following error: Encountered authentication error while retrieving metadata. Error details: Status Code: 400 : {"error":"invalid_grant","error_description":"expired access/refresh token"}](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V00007FVuog)

:::note
I fixed the problem by enabling connected app "Amazon AppFlow Embedded Login App" and make sure "Refresh token is valid until revoked" is under  Manage App Policies. I have my AppFlow to newly created sandbox so this has not been configured yet. 

接続アプリ「Amazon AppFlow 埋め込みログインアプリ」を有効にし、「アプリポリシーの管理」で「取り消されるまでリフレッシュトークンが有効である」ことを確認することで問題を修正しました。 AppFlow を新しく作成したサンドボックスに接続しているため、これはまだ構成されていません。
:::
[Swift]多言語経験者からのギャップ！引数の値書き換え

# 目次
[1.Swiftの関数の引数は値を書き換えられない？](#1-Swiftの関数の引数は値を書き換えられない？)
[2.実例](#2-実例)
[3.対処法](#3-対処法)
[4.おわりに](#4-おわりに)

# 1. Swiftの関数の引数は値を書き換えられない？
多言語経験者からのギャップです。
**Swiftの関数は、引数の値を書き換えることができないのです**
引数をごちゃごちゃといじった結果を返したい関数を作ることなんて日常じゃないですか？

# 2. 実例
- どう言うことか？
    → 結論：**引数はlet定義になる**
    ~~~swift: sample.swift
    func rewriteInt(a: Int) -> Int {
        a = 2
        return a
    }
    ~~~
    これだとエラーになってしまうんですねT_T
    内容は「Cannot use mutating member on immutable value: 'a' is a 'let' constant」。
    つまり、**引数はletで定義**されていることになっているみたいです。

# 3. 対処法
- 想いを載せたダメな例
    ~~~swift: sampleNG.swift
    func rewriteInt(var a: Int) -> Int {
        a = 2
        return a
    }
    ~~~
- 正しい対処法
    → 結論：**引数と同名変数をvarで定義しましょっ♪**
    ~~~swift: sampleGood.swift
    func rewriteInt(a: Int) -> Int {
        var a = a   //この代入処理を追加
        a = 2
        return a
    }
    ~~~
    実は、関数の中では引数と同名変数の定義は許容されているんですね。

# 4. おわりに
多言語経験者からすると、引数を書き換えられないとはなんと不便な(怒)
と思ったのですが、きちんと対処法が用意されているんですね(安心)

今回も本記事を最後まで読んでいただきありがとうございました♪
目指せ脱初学者！
minify R8 で GSON でクラス変換をする場合の注意点

# 症状

Android アプリを 1年ぶりぐらいにアップデートしようとしたところ、Release ビルドで実行した時に json 形式のデータが正常にパースされなくなる症状に見舞われました。

# 原因

アプリのビルドタスクに、

```
> Task :app:minifyReleaseWithR8
```

という見慣れないタスクがあり、コレ（R8 での minify）が原因でした。

Android Gradle プラグイン 3.4.0 以上を使用したプロジェクトのビルドでは、ProGuard によるコンパイル時のコード最適化が行われず、R8 コンパイラとの連携により、minifyReleaseWithR8 タスクが実行されるようです。

https://developer.android.com/studio/build/shrink-code?hl=ja

# 必要な対策

Gson や OkHttp など、minifyの影響を受けるライブラリを使用している場合、R8 対応の proguard-rules.pro の記述内容が公開されているので、基本的にそれらを更新すれば大丈夫な筈です。（Webで見つかる大半のローカルフィックスはそれでした）

- [Gson](https://github.com/google/gson/blob/main/examples/android-proguard-example/proguard.cfg)
- [OkHttp](https://square.github.io/okhttp/features/r8_proguard/)

_ただし、私のアプリの場合、その対策だけでは不十分でした。_

# 追加で必要な対策

自前の model クラス (gson で json から変換する data class) の proguard-rules.pro へ記載するルールを修正する必要がありました。

以前の ProGuard では、

```
-keepnames class com.example.model.** { *; }
```

としていれば良かったのですが、R8 の場合、 

```
-keep class com.example.model.** { *; }
```

とする必要があります。

:::note info
つまり、従来の ProGuard では、クラスの名前（names）だけの保持されていれば正常に gson でパースできていたが、R8 だと名前だけでなく属性を含めた全ての情報を保持する必要があるようです。
:::
venvが作成されない場合

## 用途
仮想環境を構築する際に毎回忘れるのでメモ

## venvが作成されない場合
新しい環境を作成する。
下記を打ち込んで、venvフォルダが作成されない場合がある。

```
$ cd [project dir]
$ python3 -m venv [newenvname]
```

venvフォルダが作成されない場合は、pythonが環境変数設定されていない。
解決方法としては以下2つ。

- 環境変数を設定する
- 下記で.exeパスを絶対参照すると行ける。

```
$ C:\Users\abc\AppData\Local\Programs\Python\Python39\python.exe -m venv .venv
```

あとはvenv activateすればOK
git bashで行うなら下記で実行
```
$ source <venv_name>/Scripts/Activate
```

## 参考にさせていただいた記事

https://qiita.com/kimisyo/items/9eba43210a17fd12f749
Databricksでタグを使ってみる

こちらを試してみます。

https://qiita.com/taka_yayoi/items/30ee2c73895f2e56d202

# タグの付与

データエクスプローラにアクセスします。タグを追加できるようになっています。テーブルにタグを付与します。例えば、`更新日`というタグを作成し、値に日付を指定します。

![Screenshot 2023-08-24 at 9.02.20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/1fc9ba67-42e1-0e33-057d-357cd367bef1.png)
![Screenshot 2023-08-24 at 9.02.36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/de74e74c-7a31-d9ef-79ca-743507025f0c.png)

コメント以外にもメタデータを付与できるようになったということですね。
![Screenshot 2023-08-24 at 9.02.48.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/56249921-321f-3a0f-16d1-c14e9c617c7b.png)

カラムにもタグを付与することができます。コメントよりも構造化された情報を取り扱えるようになります。
![Screenshot 2023-08-24 at 9.03.18.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/0b93e36d-ef38-d309-600a-dd0153761632.png)

# タグによる検索

タグ指定での検索も可能です。運用次第ではデータの整理が捗るかと思います。
![Screenshot 2023-08-24 at 9.06.55.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1168882/65bba99c-75fe-9f88-bce5-ba4f87108ff7.png)

### Databricksクイックスタートガイド

[Databricksクイックスタートガイド](https://www.amazon.co.jp/dp/B09V1YXFVQ/)


### Databricks無料トライアル

[Databricks無料トライアル](https://databricks.com/jp/try-databricks)
Chromeの標準機能でWebサイトの一部分だけ印刷

# やり方

印刷したい部分だけ選択。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/706116/f9df1e4c-0bf7-1113-a94c-ba0f363a0dd8.png)

Ctrl + P で印刷プレビュー画面へ。

『詳細』。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/706116/f6f9afc6-eb93-4254-57d5-956f0908dd79.png)

『オプション』の『選択したコンテンツのみ』にチェック入れる。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/706116/922742b5-95e4-5767-bccc-abf313983b40.png)

下記のようにレイアウトが崩れる場合あり。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/706116/5de16db0-d030-2feb-31de-a0b22e389174.png)

# 参考サイトさん

https://tanweb.net/2019/08/23/28409/#:~:text=%E3%81%BE%E3%81%9A%E3%80%81Chrome%20%E3%81%A7%E8%A1%A8%E7%A4%BA%E3%81%97,%E6%A9%9F%E8%83%BD%E3%82%92%E8%B5%B7%E5%8B%95%E3%81%97%E3%81%BE%E3%81%99%E3%80%82

# バージョン

Microsoft Windows [Version 10.0.19045.3324]
Google Chrome 116.0.5845.111（Official Build） （64 ビット）
NetBSD/arm進捗-20230824

FreeBSD/armがくそなので、NetBSD/arm 10に引越し中です。

|SOC|arch|状況|
|:--|:--|:--|
|STR9102|ARMv4(FA526)|USB,ifが使えるようになっています。USB HD(sd0)にINSTALLして起動できました。flashから起動してifが使えるように機種依存コード入ってます|
|IXP422|AEMv5|RedBoot焼きましたがNetBSDでPCIのUSBが動かないのでペンディング中|
|MV88F5181(Orion)|ARMv5|USB外してINSTALL起動できます|
|MV88F6281(Kirkwood)|ARMv5|普通に使えます。クロックが1G以上なのでかなり早いです。mrubyでfib(32)が10秒|
|5VT1310(RT1310)|ARMv5|ifにワークアラウンド入れてINATALLどうにか動きます。なぜかこのSOCはauxctlレジスタの読み込みができません|
|M83261(Comcerto)|ARMv6|普通使いに組み込まれてirssiでircしてます|
|M86291(Comcerto)|ARMv7|USB HDにINSTALLして普通に起動しますが、IFが調子悪いです。|
|A10|ARMv7|普通に使えます|

随時dmesgはNYC*BUG dmesgdにアップしてます。

https://dmesgd.nycbug.org/index.cgi?do=index

ソースはここにあります。

https://github.com/yamori813/netbsd-src

世界に一つだけのBSDは楽しいです。

FreeBSD/armがくそなのは以下の理由です。

* clangでビルドにくそ時間がかかる
* armv4のサポートがいつのまにか動かなくなっていた
* armv4は動かなくなったので消された
* armv5のサポートは起動はできるものの5%くらいのパフォーマンスしか出ない。これはおそらくarmv6対応する時にarmv5を壊してしまったような気がします。
* armv6は1176Fをターゲットにしていて、1136では不安定で使い物にならない
* armv6のサポートはまず1136をサポートして拡張された部分は追加でサポートするのがOS開発のセオリーだがそうなっていない。これはとりあえずラズパイで動くようにしたためにそうなってしまったと思われます。
Databricksにおけるタグの適用

[Apply tags \| Databricks on AWS](https://docs.databricks.com/en/data-governance/unity-catalog/tags.html) [2023/8/22時点]の翻訳です。

:::note warn
本書は抄訳であり内容の正確性を保証するものではありません。正確な内容に関しては原文を参照ください。
:::

本書では、Unity Catalogでどのようにタグを適用するのかを説明します。

タグとは、Unity Catalogにおける様々なセキュリティ保護可能オブジェクトに適用することができる、キーと値(オプション)を含む属性です。メタストア内の様々なセキュリティ保護可能オブジェクトを整理、カテゴリ分けする際にタグ付けは有効です。また、タグを用いることで、ご自身のデータ資産の検索、発見がシンプルなものとなります。

# サポートされるセキュリティ保護可能オブジェクト

現在サポートされているセキュリティ保護可能オブジェクトのタグ付けは、カタログ、スキーマ、テーブルに対するものとなっています。セキュリティ保護可能オブジェクトの詳細については、[Unity Catalog 権限とセキュリティ保護可能なオブジェクト](https://docs.databricks.com/ja/data-governance/unity-catalog/manage-privileges/privileges.html)をご覧ください。

# 要件

Unity Catalogのセキュリティ保護可能オブジェクトにタグを追加するには、セキュリティ保護可能オブジェクトに`APPLY_TAG`権限を含めます。タグ付けの操作を制御するためにこの権限が導入されました。Unity Catalogに登録されているセキュリティ保護可能オブジェクトのみにタグ付けを行うことができます。

# 制約

タグの制約を以下に示します:

- 単一のセキュリティ保護可能オブジェクトには最大20のタグを割り当てることができます。
- タグの最大長は255文字です。
- タグの名前に特殊文字を使うことはできません。
- タグの名前や値を用いたUnity Catalogにおける検索は完全一致のみがサポートされています。

# データエクスプローラにおけるタグの管理

データエクスプローラUIを用いてセキュリティ保護可能オブジェクトのタグを管理するには:

1. サイドバーの![](https://docs.databricks.com/en/_images/data-icon.png)**Data**をクリックします。
1. タグの情報を参照するためにセキュリティ保護可能オブジェクトを選択しまsう。
1. 選択されているセキュリティ保護可能オブジェクトのタグを管理するには、![](https://docs.databricks.com/en/_images/pencil-edit-icon.png)**Add/Edit Tags**をクリックします。タグ管理のモーダルで同時に複数のタグの追加、削除が可能です。

# インフォメーションスキーマテーブルによるタグ情報の取得

Unity Catalogで作成されたそれぞれのカタログには、`INFORMATION_SCHEMA`が存在します。このスキーマには、参照権限を持つスキーマのカタログにあるオブジェクトを説明するテーブルが含まれています。

タグ情報を取得するために以下のテーブルをクエリーすることができます:

- `INFORMATION_SCHEMA.CATALOG_TAGS`
- `INFORMATION_SCHEMA.COLUMN_TAGS`
- `INFORMATION_SCHEMA.SCHEMA_TAGS`
- `INFORMATION_SCHEMA.TABLE_TAGS`

詳細については、[情報スキーマ](https://docs.databricks.com/ja/sql/language-manual/sql-ref-information-schema.html)をご覧ください。

# SQLコマンドによるタグの管理

:::note
**注意**
この機能は、Databricksランタイム13.3以降でのみ利用できます。
:::

現時点では、カタログ、スキーマ、テーブル(ビュー、マテリアライズドビュー、ストリーミングテーブル)、テーブルのカラムに対するタグ付けSQLコマンドがサポートされています。DatabricksのSQLタグコマンドについては、[SQL 言語リファレンス](https://docs.databricks.com/ja/sql/language-manual/index.html)をご覧ください。

# テーブルの検索、フィルタリングでのタグの活用

タグを用いてテーブルを検索、フィルタリングするには:

1. Databricksワークスペースのトップバーの**Search**フィールドをクリックするか、キーボードショートカット`Command-P`を使用します。
1. 検索条件を入力します。割り当てられているタグの名前や値を入力して、Unity Cata logのテーブルを検索します。

また、既存のタグ名を用いて検索結果をフィルタリングするために、**Table**検索タグでタグのフィルターを用いることができます。

### Databricksクイックスタートガイド

[Databricksクイックスタートガイド](https://www.amazon.co.jp/dp/B09V1YXFVQ/)


### Databricks無料トライアル

[Databricks無料トライアル](https://databricks.com/jp/try-databricks)
【備忘録】Postgres再インストール時の残骸について(?)

# 再インストール時の注意

自分のWin環境でのPostgresが調子悪く再インストールしようとしたんですが、いざインストールするときにパスワード設定画面が出ず完了後も認証がうまくいかず・・・

# 対処法
前アンインストールした時の残骸が残っているので、Postgresのフォルダごと削除すれば設定画面が出て、認証もうまくいきました。

良かった💦

そんだけです。
【SSH】パスワード認証から公開鍵認証に移行する

## はじめに
LinuxサーバにOpenSSHサーバとクライアントをインストールし、いざSSH接続しようとしたときの認証方式はパスワード認証です[^1]
今回は公開鍵認証方式に移行する手順を書いていこうと思います。
公開鍵認証方式は、秘密鍵と公開鍵を使ったパスワード入力が必要ない方式で、総当たり攻撃やパスワード流出の対策にもなります。
今回試したLinuxサーバは、クラウド上に用意した`Ubuntu22.04`、ローカルPCはWindowsにWSL2を使用して構築した`Ubuntu22.04`です。
[^1]: PasswordAuthentication yes

## キーペアの作成
では早速、秘密鍵と公開鍵を作成していきます。
ローカルPCで以下を入力します。
```bash:ターミナル
ssh-keygen -t rsa -b 4096
```
RSA暗号を使った4096ビットの鍵を生成します。
途中でパスワードの入力を求められますが、何も入力せずEnterを押しておきます。
[ssh-keygen](https://manpages.ubuntu.com/manpages/jammy/man1/ssh-keygen.1.html)

デフォルトでは、以下の場所に鍵が作成されます。
| 鍵 | 場所 | ファイル名 |
| :-- | :-: | --: |
| 公開鍵 | ~/.ssh | id_rsa.pub |
| 秘密鍵 | ~/.ssh | id_rsa |

## 公開鍵をサーバにコピーする
公開鍵認証に使用するため、生成した公開鍵をサーバにコピーします。[^2]
```bash:ターミナル
ssh-copy-id [アカウント名]@[ホスト名]
```
[^2]: 公開鍵をGithubなどに登録してある場合、`ssh-import-id`コマンドが使えるらしいです。

こうすることでLinuxサーバの`~/.ssh/authorized_keys`に公開鍵が追加されます。
また、`ssh-copy-id`は、ファイルとディレクトリが存在しなければ自動で作成もしてくれる優れものなコマンドです。
念のため、作成されたファイルのパーミッションを確認しておきたいと思います。[^3]

```bash:ターミナル
sudo stat /home/tester1/.ssh/authorized_keys -c '%a'
 -> 600
```
[^3]: パーミッション`600`は所有者のみ読込、書込ができる権限です。

## 公開鍵認証方式でログインできるか試してみる
ここまで終えると、公開鍵認証方式でLinuxサーバへのログインができるようになっているはずです。
実際に試してみたいと思います。
`ssh [ユーザ名]@[ホスト名]`
この結果、パスワードの入力を求められることなく、Linuxサーバにログインできれば成功です。

## 二要素認証を取り入れてみる
ここまでの状態で、秘密鍵が保存されているローカルPCを使ってさえいれば、<font color="Red">誰でも</font>Linuxサーバにログインできるようになりました。
それでは困るといった場合には、第三者がログインできないように、更にセキュリティを強化できます。
それについては、別記事を書きたいと思います。

## パスワード入力を完全に制限する
最後の締めくくりとして、該当のユーザに対してパスワード入力でログインできなくします。

***
注意: これを行うメリット・デメリットを示します。
- メリット
    - 特定のローカルPC、特定のデバイスを持つ者しかログインできないため、セキュリティが高い
- デメリット
    - ハードウェアが故障した場合など、ログイン不可となった際の対応策を用意しておく必要がある
***

まず、他人のローカルPCから該当ユーザでログインを試みるとパスワード入力を求められることを確認しておきます。
例えば、ローカルPCに仮想環境を作っている場合、VMからは公開鍵認証で直接ログインできますが、
ホストPCのPowerShellからはパスワード入力しないとログインできないといった状態です。

以下の編集を行い、パスワード入力を制限してみます。
```bash:/etc/ssh/sshd_config
PasswordAuthentication no
```
sshを再起動（`sudo systemctl restart ssh`）します。
これで、他人のローカルPCからはログインできなくなりました。
(ちなみに、アクセスしてみると`Permission denied (publickey).`となります)

以上で、パスワード認証から公開鍵認証に移行することができました。