OmniAICreator/Qiita-1.07M huggingface dataset:
optparseの使い方

# optparseとは
`octparse`は標準ライブラリの内の1つで、コマンドラインのオプションを使うためのライブラリです。

## 使い方
1. `OptionParser`オブジェクトoptを生成
2. オプションを取り扱うブロックをoptに登録する
3. opt.parse(ARGV)でコマンドラインを実際にparseする
## 1. `OptionParser`オブジェクトoptを生成
optparseライブラリを読み込んで、OptionParseオブジェクトoptを生成します。
```sample.rb
require 'optparse'
opt = OptionParser.new
```

## 2. オプションを取り扱うブロックをoptに登録する
onメソッドを使用し、引数でオプション`-a`と`-b`を定義し、引数が指定されたときの処理をブロック内に記述する
```sample.rb
opt.on('-a') {|v| p v }
opt.on('-b') {|v| p v }
```

## 3. opt.parse(ARGV)でコマンドラインを実際にparseする
`ARGV`にはコマンドラインで渡されたオプション、引数が配列として渡される。

```sample.rb
opt.parse!(ARGV)
p ARGV
```

結果

``` 
ruby sample.rb -a foo bar -b baz
# => true
     true
     ["foo", "bar", "baz"]
 ```

 ## オプションの引数
`on`メソッドのオプション定義で末尾に何かを書くと、そのオプションは引数を受け付けることの指定となる

 ```sample.rb
 require 'optparse'
opt = OptionParser.new

opt.on('-a VAL') {|v| p v }         # <- " VAL" を追加
opt.on('-b') {|v| p v }

opt.parse!(ARGV)
p ARGV
```
結果

```
ruby sample.rb -a foo bar -b baz

# => "foo"
     true
     ["bar", "baz"]
```

## ロングオプション
ロングオプションは`on`メソッドの引数に`--`ではじまるオプションを指定します

```sample.rb
require 'optparse'
opt = OptionParser.new

opt.on('-a', '--foo') {|v| p v }
opt.on('--bar') {|v| p v }

opt.parse!(ARGV)
p ARGV
```
結果

```
ruby sample.rb -a foo bar --bar baz
# => true
     true
     ["foo", "bar", "baz"]
```

## 参考文献
[library optparse (Ruby 3.2 リファレンスマニュアル)](https://docs.ruby-lang.org/ja/latest/library/optparse.html)
初めてのJavaアプリ製作から3週間の今

## あらすじ
IT業界未経験のおじさんが9月からJavaを学んで最近アプリを作り始めました。

## 現在の状況
<img width="800" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3569128/19ce6a83-e80c-5ed7-2144-7edfd7127b1e.png">

思った以上にアプリ製作楽しめています。
記事を書くより製作に時間を使いたいと思う程に。

現在の完成度は、最低限の機能の実装は完了したという状況です。
### ログイン画面
<img width="400" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3569128/32cd2a8c-5d21-28be-e9fe-d32ceb3dd03e.png">

### メイン画面
<img width="600" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3569128/93481ce4-c3f7-f0df-eef5-9f655d50cc87.png">

## 苦労した点
大きな問題はなく小さな疑問を潰して行くといつの間にかメイン画面が完成したので、
少し色気づいてログイン画面を作ろうとしたが故にパスワードの取り扱いという難しい問題に直面しました。

暗号化とハッシュ化の違いすら知らないセキュリティ音痴だったので、
パスワードの取り扱いの基本の記事をいくつか読むことにしました。
## 浅瀬で撤退の判断
セキュリティの記事を深掘りすると永遠に抜け出せないと早々に撤退。
とりあえず自分に必要な情報だけを抜き取ることにしました。

その結果私が選んだ管理方法は、
1. アルゴリズムはSHA-256
1. パスワードにランダムなsaltを追加
1. ストレッチング1000回以上のハッシュ化

ただ、この辺は調べ方が甘かったようで、計算負荷が低いのでセキュリティ面では危うい模様。
PBKDF2かGradleを入れてArgon2idなどに変更をする必要がありそうです。要調査。

## MySQLのWorkbench上でsaltが文字化け。
想定したコードは完成したものの、varbinaryで保存したsaltが文字化け。
コマンドラインでは問題なく表示されるものの少しモヤっとする感覚。
設定の変更やいくつかのコマンドを試しても治らなかったので、
ひとまずJavaでStringに変換してvarcharで保存することで解決としました。
恥ずかしながらこれに関しては半日ほど検索しても直せず、
「varbinaryで保存することとvarcharで保存することに違いはないだろう」と自分に言い聞かせたとも言えます。
つまり最も苦労した点はセキュリティではなく文字コードでした。
**文字コード憎し。**

## 今後の課題
#### ユーザーごとに進捗を管理できるようにDBの作り直し
雰囲気でログイン画面を作ったことにより生まれてしまった作業。
ER図などの知識も入れてみるきっかけになったので結果的にプラスでした。
 

#### メイン画面のコードを分割
メイン画面のJFrame関連を一つのクラスにまとめた結果コードが400行を超えたので分けたい。
ButtonやLabelでクラスを分ける予定ではあるものの、
GridBagLayoutの挙動次第では混乱する可能性を秘めているのが怖い所。

とりあえずこの2つが今後の大きなタスクになりそうです。

## アプリ初製作の感想
まだ完成したとは言えないので時期尚早ですが、もう少しボコボコにされて苦しむかなと思っていました。
もちろん先人の方々が足跡を残してくれていたお陰で製作できたというのが9割以上でしたが。
それでも3週間で形にはできたので、自分に甘い私にとっては十分満足できるものとなりました。

次はWEBアプリを作りたいと思っているので、必要な知識が増え今回のように簡単に行くとは思えませんがそれもまた楽しめたらなと思います。

次の記事を書く時に何を製作中であるかはわかりませんが、またお付き合いいただければ幸いです。
駄文失礼いたしました。
Accessでまれに『3270プロパティが見つかりませんでした』の例外になる件の対応

:::note warn
根本の原因調査までは行っていません。
『これやったら再発しなくなった』という内容なので参考情報として見て下さい。
:::

# 状況

2023年09月20日ごろ。
Windows10 Pro OSビルド19045.3448にインストールしたMicrosoft365 for business 32bit。
（Microsoft365のバージョンについては後述）

特定のAccessファイル起動時、まれに『3270プロパティが見つかりませんでした』の例外になりました。
断言はできませんが、 ```CurrentProject.Path``` で起きてる可能性が高い状況でした。
同じAccessファイルを開いた時、『例外が起きるPC』もあれば『起きないPC』もありました。

# 対応

例外が起きるPCは下記のように、Office更新プログラムの自動インストールが止まっていました。

![68747470733a2f2f71696974612d696d6167652d73746f72652e73332e61702d6e6f727468656173742d312e616d617a6f6e6177732e636f6d2f302f3637353836302f38626162333931662d663835332d393739652d303235372d6432383430386663346235622e706e.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/706116/66288b31-77cc-800e-3c29-186cebd2102e.png)

下記のように自動インストールを有効にし、バージョンも最新にしました。

![68747470733a2f2f71696974612d696d6167652d73746f72652e73332e61702d6e6f727468656173742d312e616d617a6f6e6177732e636f6d2f302f3637353836302f36356661383762302d613764382d356138302d363134392d6237626465376131386236332e706e.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/706116/dfa00d10-e91a-a30d-b4bf-275027626680.png)

そのまま2ヶ月ほど経ちましたが、「3270の例外が再発した」といったことは無かったです。

# 蛇足

下記のような理由からMicrosoft365の自動更新を止めることはあります。

1. Microsoft365のアップデートによってAccessのシステム障害が起きた。
1. Accessを修正している暇はないので、いったんMicrosoft365のバージョンを戻した。
1. 障害が再発しないように、Microsoft365更新プログラムの自動インストールを止めた。

そのあと放置するとこの記事のような問題が起きやすくなると思います。
あと古いバージョンのまま動き続けるので、セキュリティも下がります。

クライアントにインストールするタイプのソフトは、忘れたころに『バージョン管理』が足を引っ張ることがあります。

そういったソフトは『クライアント1台1台まわらずにバージョン管理できる仕組み』を整えた上で展開できるとよいと思います。

# 参考サイトさん

https://tsware.jp/tips/tips_437.htm
初期アプリをriverpodで状態管理してみる

こんにちは。
今日は初期アプリの状態管理をriverpodに置き換え、
その使い方やメリットを理解しようと思います。

前回は初期アプリをproviderに置き換えました。
その記事は[こちら](https://qiita.com/output_tarou/items/8ba18ba26ca95a05828b)

また初期アプリの解説記事は[こちら](https://qiita.com/output_tarou/items/a0257ba0699a05f0425a)になります！

今回もpackageの導入から始めます。
```
$ flutter pub add flutter_riverpod
```

そしてmain.dartファイル内で下記インポートと
counterProviderの定義を行います。
```
import 'package:flutter_riverpod/flutter_riverpod.dart';

final counterProvider = StateProvider((ref) => 0);
```

ここでStateProviderというクラスが出てきました。
これはriverpod特有のクラスで、こちらを使い状態管理を行います。

StateProvider((ref) => 0);
こう書くことでStateProviderのコンストラクタを呼び出し、
引数として無名関数（refを引数として渡し、0を返す）を渡しています。
そしてこのrefはStateProviderのコンテキスト（ProviderReference）にアクセスするためのものです。

要するにこれまでの文脈を渡し、初期値として0を返しています。


そして、ProviderScopeでアプリ全体をラップします。
これはriverpodを使うための儀式で、こうすることで全てのproviderへグローバルにアクセスできるようになります。

```
void main() {
  runApp(
    ProviderScope(
      child: MyApp(),
    ),
  );
}
```

最後にMyHomePageをConsumerWidgetを継承する形で書き換えます。

```
class MyHomePage extends ConsumerWidget {
  const MyHomePage({super.key, required this.title});

  final String title;

  @override
  Widget build(BuildContext context, WidgetRef ref) {
    final counter = ref.watch(counterProvider);

    return Scaffold(
      appBar: AppBar(
        title: Text(title),
      ),
      body: Center(
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: <Widget>[
            const Text('You have pushed the button this many times:'),
            Text(
              '$counter',
              style: Theme.of(context).textTheme.headlineMedium,
            ),
          ],
        ),
      ),
      floatingActionButton: FloatingActionButton(
        onPressed: () => ref.read(counterProvider.notifier).state++,
        tooltip: 'Increment',
        child: const Icon(Icons.add),
      ),
    );
  }
}
```

まず、ConsumerWidgetとはなんぞやという話からですが、
こちらもriverpodから提供されるWidgetクラスです。

ConsumerWidgetはproviderから提供される状態をサブスクライブ（購読）し、状態が変更された時に自動的に再構築され、UIが更新されます。

```
final counter = ref.watch(counterProvider);
```

またConsumerWidgetはbuildメソッドの際、WidgetRefオブジェクトをパラメータとして受け取り、このWidgetRefを使用して、providerから状態を読み取ります。

そしてcounter変数を用いて、body内で値を表示し、
onPressedイベントが発火した際には
ref.read(counterProvider.notufier)によって、現在の値を１度だけ取得し、
.state++にて1加算しています。


以上がriverpodを使用した状態管理への移行方法になります。


ここまで
StatefulWidgetとsetState
provider
riverpodと試してきましたが、
やはり最近よく使われているだけあって、riverpodが書くソース量も少なく、使いやすそうだなという印象です。ただグローバルに状態にアクセスできることはメリットの反面、非常に多くの箇所からアクセスされるようになると、結合度が高くなるようなデメリットも少なからずあると感じました。

実際に使っていく中で設計など意識していきたいと思いました。
Neovim環境の構築

neovim開発環境構築の備忘録。
ちょっとずつ更新していきます。

# vimのショートカットを勉強するのに使ったサイト
https://www.openvim.com/

一回これのチュートリアルやるとなんとなく使いやすいショートカットの全体像がわかる。
こんなのあるのかー便利だなーということがわかる。

# neovimのインストール
管理者権限がなかったため、一旦x86_64環境にインストールする。

```
$ uname -m
x86_64
```
```
brew install neovim
```


# lazyvimのインストール
公式の手順に沿って進める。めっちゃ簡単！

https://www.lazyvim.org/installation

まずはバックアップを取る
```
# required
mv ~/.config/nvim{,.bak}

# optional but recommended
mv ~/.local/share/nvim{,.bak}
mv ~/.local/state/nvim{,.bak}
mv ~/.cache/nvim{,.bak}
```

starterのclone
```
git clone https://github.com/LazyVim/starter ~/.config/nvim
```

.gitフォルダの削除（後程自分のリポジトリのを追加できるようにするため）
```
rm -rf ~/.config/nvim/.git
```

以下のコマンドを叩いてNeovimを起動！
```
nvim
```

# アイコンが文字化けしていたので、フォントをダウンロード
https://www.nerdfonts.com/font-downloads

Symbols Nerd Fontをダウンロードし、`~/Library/Fonts/`に.tffファイルを移動。
iTerm2の設定画面で、`use ligatures`で検索。
Non-ASCII Fontで先ほどダウンロードしたフォントを選択し、nvimコマンドを叩くとアイコンが表示された。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1045261/6263cd16-5b07-8836-da79-8fbcc1f9b335.png)



# lazyvimのkeymaps

https://www.lazyvim.org/keymaps


# toggletermのインストール

https://github.com/akinsho/toggleterm.nvim#custom-terminal-usage

`~/.config/nvim/lua/plugins`に`toggleterm.lua`というファイルを作成。
`~/.config/nvim/init.lua`に以下を追加。
```init.lua
require("toggleterm").setup{
  open_mapping = [[<c-\>]],
}
```
これでctrl+\でterminalが開くようになる。

# lazy.nvimのインストール
https://zenn.dev/stafes_blog/articles/524e4c8c80db24

ここのブログの手順で実行。
「toggletermの設定」の箇所は、`~/.config/nvim/init.lua`に記載すればOK。


# normal modeでgccでコメントアウト
https://github.com/numToStr/Comment.nvim

# golangのimportの自動補完
goplsの機能を用いることで、vscodeのようにgolangのimportを自動補完することができます。
下記の公式ドキュメントを参考にしてインストールを行いました。
[tools/gopls/doc/vim.md at master · golang/tools](https://github.com/golang/tools/blob/master/gopls/doc/vim.md#neovim-omnifunc)

```terminalでこれを実行.sh
dir="${HOME}/.local/share/nvim/site/pack/nvim-lspconfig/opt/nvim-lspconfig/"
mkdir -p "$dir"
cd "$dir"
git clone 'https://github.com/neovim/nvim-lspconfig.git' .
```

これを実行してからnvimを起動し、golangのソースコードを保存することで自動的にimoprtが補完されるようになります。


# 任意の隠しファイルをneo-treeで表示させる設定
下記のように、never_showにて
```~/.config/nvim/lua/plugins/neo-tree.lua
return {
  "nvim-neo-tree/neo-tree.nvim",
  opts = {
    filesystem = {
      filtered_items = {
        hide_dotfiles = false,
        hide_gitignored = false,
        hide_hidden = false,
      },
    },
  },
}
```


# Copilotのpluginが動作しなかった際の対応
```
:Copilot status
<Tab> map has been disabled or is claimed by another plugin
```
となってしまった場合、copilotの設定ファイルを下記のようにすることでエラーを解消できました。
`Tab`ではなく`ctrl + j`でcopilotの提案を受け入れるような設定です。
``` .config/nvim/lua/plugins/copilot.lua
return {
  "github/copilot.vim",
  lazy = false,
  config = function()
    vim.keymap.set("i", "<C-J>", 'copilot#Accept("\\<CR>")', {
      expr = true,
      replace_keycodes = false,
    })
    vim.g.copilot_no_tab_map = true
  end,
}
```

nvimにて`:Copilot help`を叩くと、公式のlua設定が出てきます。
今回はその内容をそのまま追加することでエラーを解消できました。
「現代数理統計学の基礎」演習問題解法メモ　第2章問1～問6

ページ数が多いので3分割程度にして掲載します。
緑ペンは根拠をメモしています。
![第2章問1　P1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/e614de31-265e-45f6-6306-adaca9869402.jpeg)
![第2章問1　P2.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/31fe1ef8-aaab-1f03-ac8d-1bbe239fb23f.jpeg)
![第2章問1　P3.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/5d8bdb87-47d6-b0fc-feb2-b54899f10271.jpeg)
![第2章問2　P1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/cff063f0-00f5-cdc0-9a73-1c3103ae91d8.jpeg)
![第2章問2　P2.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/38393063-81c9-4b10-c161-6e8272a2c12f.jpeg)
![第2章問3.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/f4871eb8-93ba-0362-6fb1-2d9fbd389744.jpeg)
![第2章問4　P1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/aa2a4e8a-9204-c37d-3b4e-a690e480a3b2.jpeg)
![第2章問４P2.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/af3f2bc0-87b7-6d0c-57b2-67c773472804.jpeg)
![第2章問４P3.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/4548dcab-0403-f82a-e78a-2afb19842862.jpeg)
![第2章問5.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/9738d3f6-befa-acd9-6a7f-4d6e4ed07b31.jpeg)
![第2章問6.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3576811/a3a8058b-1529-0b0e-83e8-aa9ac32d7643.jpeg)
【業務に役立】めっちゃ紹介したいツール個人まとめ

## 一覧

- PowerToys
	- Fancyzone
	- PowerToys Run
	- Preview
	- Mouse Utility
- VSCode
- CubePDF 
    - Utilities
- Snipaste
    - 商用可能なのはSnipaste 1
- autohotkey
- Quickswitch
    - Libraryの機能を持ち出し
- Everything
  - 1.5aのalpha版
- magick
- CopyQ


## 簡単紹介
[PowerToys](https://github.com/microsoft/PowerToys)（MS社が開発したツール集）

- Fancyzone：自分が設定したレイアウトで画面の配置が可能
- PowerToys Run：Alt+spaceで入力バーを起動し
    ○ 電卓、単位変換、日付時間コピー
    ○ ファイル・フォルダー・ソフトの起動
    ○ PCのシャットダウン・スリープ
- Preview：ファイル開かずに、覗き見ができる
- Mouse Utility：マウス位置の特定、クリック蛍光ペン
- Text Extractor：画像にあるテキストをコピー
- Awake：ずっと電源オン状態で保持可能
- Power Rename：ファイル名を正規表現で一括変更
- Text Extrator：画面文字OCR
- Borderless Mouse：複数のパソコンを一つのマウスでコントロール

[VSCode](https://code.visualstudio.com/)：多分いう必要のない、すべてのコーディングと文字ファイル処理に向いている
[CubePDF](https://www.cube-soft.jp/cubepdf/)：無料ソフト、PDFの編集、画像からPDFの変換
[Snipaste](https://www.snipaste.com/download.html)：スクリーンショットと編集
	無料で商用可能なのはバージョン1
[autohotkey](https://www.autohotkey.com/)：いくつかの動作をスクリプトとして作成、ショートキーより呼び出し可能、プログラミング能力必要
[Quickswitch](https://github.com/gepruts/QuickSwitch/tree/main)：Libraryの機能で、ポップアップ画面で素早くフォルダー間移動
[Everything](https://www.voidtools.com/forum/viewtopic.php?t=9787)：一瞬でファイル特定ができる
- 1.5aのalpha版があり、新しい機能が追加されている
[magick](https://imagemagick.org/script/download.php)：コマンドラインで画像の変換ができる
[CopyQ](https://github.com/hluk/CopyQ)：コピーした内容の履歴が残る、アイテムを固定してダブルクリック入力ができる
携帯電話だけで実現するCRMの方式検討

Webフォームを使った店舗予約などはよくあるが、まだまだ店舗側やユーザ側も通話を使った予約行為はよくある。

電話予約の場合はほとんどの場合は「お電話番号をお願いします」との案内を元に口頭で電話番号を伝えている。

そもそも発信者番号は伝わっているのだから電話番号をキーに顧客DBと結びついてもよいのでは？と思った。

### 案1. SIP電話を導入する → 見送り

コールセンターなどで使われる仕組み。昔から存在はするがその辺の店舗が導入してないことを思うと大掛かりすぎる。

### 案2. 050の専用サービスを導入 → まぁまぁ

みんなに電話転送
https://minderu.com/
みたいな、050の電話転送サービスがある。主目的は転送だけどどこから電話がかかってきたかはPC上で確認できる。ブラウザでアクセスできればあとは、画面上に機能を足して（本当はAPIがあればいいんだけどなくてもHTMLを直接みればいい）、顧客DBをLOOKUPできる。

こんな便利なのにいまいち普及してない。月額料金も高くない。そもそものニーズ設定が間違ってるのか？

### 案３. そういうスマホアプリを作る → 完全無料

店舗の電話を受け取るのはスマホの番号にしちゃう。着信履歴にアクセスするスマホアプリは作ることが可能なので（あとAdnroidなら勝手アプリもインストールできる）、そのアプリをインストールして、着信があればスプシに着信履歴を書き込んでスプシ上で簡易顧客DBとVLOOKUPすればいい。

ださいけど、完全無料でできる。

### 案4. Googleマイアクティビティを使う → ボツ

Googleマイアクティビティはスマホ上のアプリの使用履歴を保存、閲覧できる。PC上からも確認できる。ただし電話の着信はアクティビティとして保存されてなかった。したがってボツ。

### 案5. MSの「スマホと同期」を使う

MSが提供している「スマホと同期」のアプリを入れれば、電話機能を全てPCからも操作できるらしい（まだ試してない）。これなら、PC上で顧客DBと接続できる。しかしながらブラウザじゃなくてアプリなので機能拡張が足せない。

## まとめ

- 案３がギリギリ無料でできちゃう。テンプレートとなるスプシも用意してあげるといいかも
- MSの「スマホと同期」はそのアプリの機能やUIに依存してしまった仕組みだとちとつらい（AndoridOSの機能に依存するのはまだゆるせるが）
- そもそも「そういうソリューション」が求められてるのかどうかというところから要調査
- やるとなったらWordPressなみにロックインされない仕組みで提供したい

## 理想のシナリオ

こんなフローがオープンソースでできると嬉しい

- 顧客が店舗に電話をかける
- 店員がスマホで受電する
- PC上には発信者番号から顧客情報が表示される
- 顧客と店員が口頭で予約を調整
- 店員がPC上で予約を確定
- 予約確定後にSMSで予約日時が顧客に届く

以下がキーとなりそう

- 発信者番号がPC上で管理できる
- PCからSMSに送信できる

PCからSMSに送信するのは、Googleが提供するPC版メッセージ
https://messages.google.com/web/
で実現可能。ブラウザだから機能は拡張できる。
Railsで画像を保存する際のassets配下とpublic配下の違い

# Railsで画像を保存する際のassets配下とpublic配下の違い

Railsアプリケーションにおけるアセット管理は、画像、スタイルシート、JavaScriptなどの静的ファイルを効率的に扱うための重要な部分です。特に画像ファイルの配置には、`assets`ディレクトリと`public`ディレクトリの2つの主要な選択肢があります。これらの違いを理解することは、Rails開発において重要です。この記事では、`assets`ディレクトリと`public`ディレクトリの特徴と使い分けについて詳しく解説します。

## assets配下に画像を保存する

### assetsディレクトリの役割

#### 概要

`assets`ディレクトリは、Railsアセットパイプラインの一部として機能します。アセットパイプラインは、JavaScriptファイル、スタイルシート、画像などのアセットを効率的に管理し、配信するための仕組みです。

#### 特徴

- **プリコンパイル**: `assets`ディレクトリに置かれた画像は、本番環境へのデプロイ時にプリコンパイルされます。これにより、ファイル名にユニークなフィンガープリントが付与され、キャッシュ管理が容易になります。
- **圧縮・最適化**: 画像ファイルは、パフォーマンス向上のために自動的に圧縮されます。

#### 使用例

```ruby
image_tag 'example.png'
```

このコードは、`assets/images`ディレクトリ内の`example.png`を参照します。

## public配下に画像を保存する

### publicディレクトリの役割

#### 概要

`public`ディレクトリは、Railsアプリケーションのルートに直接アクセス可能な静的ファイルを配置する場所です。アセットパイプラインを経由せずに直接参照されます。

#### 特徴

- **直接アクセス**: ブラウザから直接URLを指定してアクセスできます。
- **プリコンパイル不要**: プリコンパイルのプロセスを経ずに、そのままの形で配信されます。
- **エラーページなどの配置**: カスタムエラーページなど、アプリケーション外部からのアクセスに必要なファイルを配置するのに適しています。

#### 使用例

```html
<img src="/example.png" alt="Example">
```

このHTMLは、`public`ディレクトリ内の`example.png`を参照します。

## どちらを使うべきか

### シナリオに応じた選択

- **アセットパイプラインの恩恵を受けたい場合**: JavaScriptやCSSと一緒に画像も管理し、圧縮やフィンガープリントなどの機能を活用したい場合は、`assets`ディレクトリを利用します。
- **直接アクセスが必要な場合**: エラーページやメールテンプレートなど、アプリケーションの外部から直接参照される画像は`public`ディレクトリに配置します。

## 

まとめ

Railsにおける`assets`ディレクトリと`public`ディレクトリは、それぞれ異なる目的と機能を持っています。`assets`ディレクトリはアセットパイプラインを通じた管理と最適化のために、`public`ディレクトリは直接アクセスが必要な静的ファイルのために使用します。適切なディレクトリを選択することで、Railsアプリケーションの効率的なアセット管理とパフォーマンス向上が可能になります。
配列の基本

# 初学者の備忘録
初学者の備忘録です。今回は配列の基本編です。

## 配列
値がたくさん入る箱。変数がたくさん入る箱みたいなイメージでOK。
配列を作成するには決まり事があります。

・配列は[]で定義する
・,（カンマ）で区切ること

上記の二つの定義は大切なのでしっかり覚えておきましょう。


## 配列の基本
```
let 変数名 = [値, 値１, 値２, 値3, ・・・]
console.log(変数名);
```

上記のコードが基本形になります。変数名を定義してあげてから、今度は配列を定義してあげて[]と,（カンマ）を使用してあげることで配列ができます。値と書いてあるところに変数を入れることも可能です。

```
let 変数１　= 値１
let 変数１　= 値2
let 変数１　= 値3

let 変数名 = [値, 変数１, 変数２, 変数3, ・・・]
console.log(変数名);
```

上記のコードのような配列も可能。つまり基本さえ守れば変数でも値でも入ることができるということです。
ここに四則演算もつけることが可能です。


### 配列の要素を一つずつ取り出す

配列の中に入っているデータには番号が自動的に割り振られています。左からスタートし０から順番に割り振られます。この番号のことをインデックスと呼びます。
基本編では配列の要素をまとめて呼び出していましたが、１つずつ呼び出すことも可能です。そのためにインデックスが重要になってきます。
```
let 変数名 = [値, 値１, 値２, 値3, ・・・]
console.log(変数名[0]);
console.log(変数名[1]);
console.log(変数名[2]);
```
上記のコードで対応する要素が１つずつ抜き出され、出力されます。
ここに四則演算もつけることが可能です。


### 上書き
配列に入っている要素の上書きすることも可能です。
```
let 変数名 = [値, 値１, 値２, 値3, ・・・]

let 変数名[２] = 要素２

console.log(変数名[0]);
console.log(変数名[1]);
console.log(変数名[2]);
```

上書きしたい変数名[インデックス]を指定してあげて、上書きするデータ内容を記述するだけで可能です。

<details><summary>末尾に追加</summary>
上書きとは少し違いますが、`変数名[変数名.length] = "配列末尾に追加";`lengthを使用することで最後の配列の番号を知ることができたり、また配列の最後の要素に付け加えたいなどできます。
lengtの省略バージョンでpushもあります。

```
let 変数名 = [値, 値１, 値２, 値3, ・・・]

// 配列の末尾に追加
team[team.length] = "配列末尾;
//　pushは配列の末尾に追加（length)よりも省略できるという理解度でOK
team.push("配列末尾");


console.log(変数名[0]);
console.log(変数名[1]);
console.log(変数名[2]);
```

</details>

このように配列は様々な応用ができて、可能性大なのです。

## 最後に
今回は配列の基本について学びばした。配列は変数と同じくらい様々な場面で使う上、応用も効く便利な存在です。
なのでたくさん使ってみて色々なことにチャレンジしていきたいですね。
それでは以上で終了したいと思います。お疲れ様でした。
udemyで学ぶ：スキル習得のための10の教材

<!--
    title: udemyで学ぶ：スキル習得のための10の教材
    tags:  udemy
-->

# 始めに

udemyでは今年も「ブラックフライデー」セールが開催されています。

セール時には多くの学習教材を低価格で購入できるため、私は「NestJS」と「GraphQL」に関するコースを選びました。既存のスキルを深める中で、常に新しいスキルの開拓を行ってきました。技術を学ぶ際には公式サイトからの学習も行いますが、Udemyでのノウハウ習得も取り入れており、使い分けています。

今回の記事では、最近購入した教材の整理と共に、過去に学んだコースの内容を振り返り、その経験を共有します。この内容が皆さんの学びの機会になればと思います。

# udemyとは

udemyとは、オンラインで様々なコースを提供する学習プラットフォームです。プロの教師や業界の専門家が作成したコースを通じて、ユーザーは様々な分野の知識やスキルを学ぶことができます。udemyのコースは、プログラミング、データサイエンス、ビジネス、芸術、言語学習など多岐にわたり、個人や企業のニーズに応じた学習が可能です。

https://www.udemy.com/

# ① Git： もう怖くないGit！チーム開発で必要なGitを完全マスター

この教材は、Gitを基礎から学ぶ際に選びました。図解が豊富で、視覚的なイメージを持ちながら学べる点が特に役立ちました。各概念を図で示すことで、Gitの理解が深まり、学習過程がとても充実していたと感じます。

https://www.udemy.com/course/unscared_git/

# ② AWS：ゼロから実践するAmazon Web Services。手を動かしながらインフラの基礎を習得

AWSに関する学習リソースは公式サイトや様々なウェブサイトで豊富にありますが、この教材の教師による解説のわかりやすさが購入の決め手となりました。AWSの無料枠を活用することで、追加費用なしに実践的な学習が可能である点も大きな魅力です。

https://www.udemy.com/course/aws-and-infra/

# ③ REST WebAPI サービス 設計

RESTおよびRESTfulなAPIの概念を根本から理解するために、この教材を選びました。RESTful APIの設計と実装に関する具体的なガイダンスが提供されており、API構築する場合に非常に役立っています。

https://www.udemy.com/course/rest-webapi-development/

# ④【2023日本語版】FigmaでレスポンシブWEBデザイン作り方！Figmaの基礎からWEBデザイン実践まで完全サポート

Webサイトの画面設計においてFigmaの使用したかった為、この教材を購入しました。レスポンシブデザインの指導が含まれており、PCやスマートフォンなど異なるデバイスでの表示を容易に想像できます。また、学習した内容の振り返りにも大変役立っています。

https://www.udemy.com/course/figmaresponsive/

# ⑤【22日間で学ぶ】SQL文、分析関数、テーブル設計、SQLチューニングまでMySQLで覚えるSQL実践講座

データベース設計の学習を目的に、この教材を選びました。SQLの基本からテーブル設計、さらにはSQLチューニングまで、幅広い内容を網羅しています。内容はボリュームがありますが、必要な部分を選んで振り返ることが容易です。

https://www.udemy.com/course/3sqlmysql/


# ⑥ 2時間で学ぶ！ソフトウェアテスト設計講座（機能テスト編）～効率的に”もれ”の無いテスト設計手法を習得～

業務上のテスト設計において自己のスキルを振り返り、拡張する目的でこの教材を選びました。様々な企業のテスト設計方法を学ぶことができ、自分のテスト設計プロセスを再整理するのに役立ちました。また、テスト設計未経験者でも基本的なノウハウを習得できる内容となっています。

https://www.udemy.com/course/shift-designfunctionaltest/


# ⑦ 正規表現入門　作業効率アップに役立つ38個の方法

業務で頻繁に正規表現を使用しているものの、これまで正式な学習をしていなかったため、この教材を購入しました。正規表現は多様なプログラミング言語において汎用性が高く、実務での利用に大きな助けとなっています。

https://www.udemy.com/course/38-bgtqc/

# ⑧　現役シリコンバレーエンジニアが教えるアルゴリズム・データ構造・コーディングテスト入門

アルゴリズムとデータ構造の基礎を深く理解するため、この教材を選びました。図解を用いた解説があり、視覚的な理解を助けています。動画は繰り返し視聴することで、忘れた際にも参照しやすく、学習効果を高めるのに役立っています。内容の難易度は高いため、繰り返し学習することをお勧めします。

https://www.udemy.com/course/python-algo/

# ⑨【Reactアプリ開発】3種類のReactアプリケーションを構築して、Reactの理解をさらに深めるステップアップ講座

Reactのスキルを拡張する目的でこの教材を購入しました。3種類の異なるReactアプリケーションを実装することにより、理論と実践のバランスを取りながらReactの理解を深めることができました。特に、Reactの基礎を学んだ後、実践的なスキルを伸ばすのに非常に有効だと感じています。

https://www.udemy.com/course/react-3project-app-udemy/

# ⑩ 【Redux完全入門】絶対に理解させるReduxアルゴリズム徹底解説入門パック

Reduxの学習のためにこの教材を購入しました。図を用いた丁寧な解説があり、内容の理解が非常に容易でした。Redux Toolkitの有り無しに応じた2つの異なるパターンも提供されており、理論を実際のイメージに結びつけるのに役立ちます。学んだ内容の振り返りにも頻繁に利用しています。

https://www.udemy.com/course/react-redux-beginner-course/

# 終わりに

今回は10種類の学習教材をご紹介しました。今後もさまざまな学習教材を探求し、新たな知識を身につけることに期待しています。また、他の投稿者の記事も参考にしながら、学びの幅を広げていきたいと思います。

最後までお読みいただきありがとうございました！
カンガルー・マジック2のCSVがEC-CUBEにアップロードできない

# 基本環境

EC-CUBE4.2.2

# 西濃運輸カンガルー・マジック2との連携

運送会社連携プラグインを入れて、
```
１）EC-CUBE →　`受注CSVファイル`　→ カンガルー・マジック2
```
をして、出荷手続きをする

出荷されたら、
```
２）カンガルー・マジック2 →　`出荷済みCSVファイル`　→ EC-CUBE
```
をして、お問い合わせ番号など出荷された時のデータをEC-CUBEに取り込む

# 出荷済みCSVがアップロードできない

`１）受注CSVファイル`
のダウンロード　＆　アップロードは成功

`２）出荷済みCSVファイル`
のダウンロードは成功したもののアップロードをすると、

```
フォーマットが一致しません
```
とエラーになってしまう

# 「見出し行」が必須

カンガルー・マジック2からの出荷済みCSVダウンロード時に、

![スクリーンショット 2023-11-23 11.16.00のコピー.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1653133/08538f34-af34-2811-fca2-3d457c1066a5.png)

「見出し行を出力する」
にチェックを入れてダウンロード

![スクリーンショット 2023-11-23 11.17.37のコピー.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1653133/8e985c33-3b53-ec8c-b41d-7043924dd99d.png)

1行目に見出し行が入った状態のCSV

これをEC-CUBEにアップロードすると成功した

https://www.ec-cube.net/products/detail.php?product_id=2493っせ
標準入力

# 初学者の備忘録
初学者の備忘録です。今回は標準入力からデータを受け取れるコードを書いていきます。
ただ、機能はしますが理解はまだまだ及んでいないので未完成の記事となっています。ご了承ください。

## 標準入力
プログラムでデータが特に指定されていない場合に、標準的に利用するデータの入力元。つまりユーザがキーボードで入力した値を受け取ってなんらかの処理をプログラミングが実行するということ。


## 標準入力を受け取るコード
```ruby:標準入力

process.stdin.resume();
process.stdin.setEncoding('utf8');

var lines = [];
var reader = require('readline').createInterface({
    input: process.stdin,
    output: process.stdout
});
reader.on('line', (line) => {
    // push=最後に出力
    lines.push(line);
});
reader.on('close', () => {
    console.log("hello " + lines[0]);
    console.log("hello " + lines[1]);
    console.log("hello " + lines[2]);
});
```

上記のコードが標準入力されたデータを受け取るコードになります。今回は標準入力から受け取ったデータを変数に格納して、console.logで出力するだけの基本コードになりますが、このconsole.logのところにfor文やif文を使用することで少し複雑な処理もできます。

## 複数のデータ受け取り

```ruby:複数標準入力
// 標準入力からのデータの受け取りを再開
process.stdin.resume();
process.stdin.setEncoding('utf8');

var lines = []; // 入力された各行を保存する配列
var reader = require('readline').createInterface({
    input: process.stdin,
    output: process.stdout
});

reader.on('line', (line) => {
    // 各行のデータを配列 lines の末尾に追加する
    lines.push(line);
});

reader.on('close', () => {
    // lines 配列に保存されたデータを出力する
    console.log("hello " + lines[0]); // lines 配列の最初の要素を出力
    console.log("hello " + lines[1]); // lines 配列の2番目の要素を出力
    console.log("hello " + lines[2]); // lines 配列の3番目の要素を出力
});
```

ここからどうやって発展していけばいいのかや一つひとつのコードの意味はまだまだ理解できていないのでコメントアウトもあまりできていません。

## 最後に
ここから色々発展していけそうだな、と思いつつJavaScriptを勉強初めてから１週間くらいしか経っていない自分にはまだまだ理解できていないところです。ですが、理解はしていけるように頑張っていかないとですね。
それでは以上で終了したいと思います。お疲れ様でした。
【Salesforce認定アドミニストレータ試験】公式模擬試験の英日翻訳と図解解説 (1)

この試験を受けるための勉強をした際に思わぬ苦戦をしたので、英語公式模擬問題を翻訳しながら図解解説として整理しました。

以下は、Salesforceの重要な機能(仕組み)である「レコードタイプ」に関する問題の翻訳と図解解説です。

Aung

![Q2-1_1.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3626902/e1c0c1fc-56fb-dce7-a0cd-3d7e50af7319.jpeg)
![Q2-1_2.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3626902/2cba0945-fd27-7cb2-0be5-3b52b67702b1.jpeg)
![Q2-1_3.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3626902/13a04b59-d64a-ef82-af6a-738b19fe6bd5.jpeg)
![Q2-1_4.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3626902/b28380ce-b60c-5c33-032d-d2f7553d3092.jpeg)
![Q2-1_5.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3626902/c0a5f688-8dea-7513-7e77-fe9b513425d4.jpeg)
EC-CUBEからCSVダウンロードしたらhtmlソースコードがオマケされた

# 基本環境

EC-CUBE4.2.2

# CSVの下にソースコードが…

CSVダウンロードし、Excelで確認したら

![スクリーンショット 2023-11-23 14.55.05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1653133/083bc68b-cd60-f712-008e-35542b55d00e.png)

正常なデータの下に不要なオマケ、何やらおかしなデータが…

どうもHTMLコードのようだ

# デバッグモードが原因

もしや開発中のためデバッグモードにしているから？…と思い、

```:root/.env
APP_ENV=dev
APP_DEBUG=1

↓

APP_ENV=prod
APP_DEBUG=0

```

書き換えたらソースコードのオマケが消えた

知りませんでした…
GoogleのSMTPサーバーを利用してメールを送信する

## 概要
メール送信機能を実装する際に、GoogleのSMTPサーバーを利用してLaravelからメール送信を行う方法について紹介します。これにより、メールサーバーを独自に構築せずに、手軽にメール送信機能を組み込むことができます。

初めはSendGridを検討しましたが、個人利用者が契約できないといった制約があったため、代わりにGoogleのSMTPサーバーを選択しました。

## 2段階認証を有効にする
まずGoogleアカウントを管理から下記のページまで移動します。
https://myaccount.google.com/security

![スクリーンショット 2023-11-23 13.53.56.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2851087/b225f37c-107d-13e9-39a2-6f8e94053f05.png)

2段階認証プロセスをクリックして画面に従って有効にしてください。

注意: 2段階認証を有効にしないと、メール送信ができないので注意が必要です。

## アプリのパスワードを設定する
設定できない場合は、2段階認証を有効にしていない可能性があります。

[アプリパスワード] 設定ページから、アプリの名前（ここではLaravel）を入力します。
https://myaccount.google.com/apppasswords

![スクリーンショット 2023-11-23 14.36.48.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2851087/c25f1b6e-09dc-7bfd-f276-fb3462529440.png)

すると下記のように16文字のパスワードが表示されます。

![スクリーンショット 2023-11-23 14.37.07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2851087/5944d619-6858-86ce-2a68-afc999b6be74.png)

注意: アプリのパスワードは.envファイルに記述するため、慎重に管理してください。

## .envに記述する
上記で設定した値で``.env``を編集していきます。

```.env
MAIL_MAILER=smtp
MAIL_HOST=smtp.gmail.com
MAIL_PORT=587
MAIL_USERNAME=自身のメールアドレス
MAIL_PASSWORD=16文字のパスワード
MAIL_ENCRYPTION=tls
MAIL_FROM_ADDRESS="${MAIL_USERNAME}"
```

**MAIL_ENCRYPTIO**は、Laravelのメール機能がSMTPサーバーとの通信時に使用するセキュリティプロトコルを指定するための設定です。TLSを使用します。

**MAIL_PORT**には、GmailのSMTP(TLS)のポートである587を指定してください。

注意: **MAIL_PASSWORD**には、先程生成したアプリパスワードを貼り付けます。コピペ時に半角スペースが入らないように注意してください。

## キャッシュをクリアする
``.env``を編集したので古いキャッシュ(編集前の環境変数情報)をクリアして編集後の値を適用します。

```
$ php artisan cache:clear
```

これで、LaravelからGoogleのSMTPサーバーを利用してメール送信が可能になります。

## 参考
https://kinsta.com/jp/blog/gmail-smtp-server/
RockyLinux 9にOpenJDK 21をインストール（AppStream）

# はじめに

Application Stream(AppStream)を利用してRockyLinux 9にOpenJDK21をインストール
親記事：[OpenJDKの各種インストール方法とEOLまとめ](https://qiita.com/witchcraze/items/b179202216aab50b7090)
参考：[Product Documentation for Red Hat build of OpenJDK 21 \| Red Hat Customer Portal](https://access.redhat.com/documentation/ja-jp/red_hat_build_of_openjdk/21)

## サポート

本手法で導入した場合、[Red Hat Enterprise Linux Application Streams Life Cycle \- Red Hat Customer Portal](https://access.redhat.com/support/policy/updates/rhel-app-streams-life-cycle) より、2029-12がEOLだと思われる。
それ以降に報告された脆弱性や不具合への対応は実施されない可能性がある。

## LOG

### インストール

```shell-session
# cat /etc/redhat-release
Rocky Linux release 9.3 (Blue Onyx)

# yum install java-21-openjdk
... 略
```

### 各種確認

```shell-session
# which java
/usr/bin/java

# /usr/bin/java -version
openjdk version "21.0.1" 2023-10-17 LTS
OpenJDK Runtime Environment (Red_Hat-21.0.1.0.12-2) (build 21.0.1+12-LTS)
OpenJDK 64-Bit Server VM (Red_Hat-21.0.1.0.12-2) (build 21.0.1+12-LTS, mixed mode, sharing)
```
ループ処理：for文基本

# 初学者の備忘録
初学者の備忘録です。今回はループ処理：for文基本編です。


## for文
決まった回数繰り返し処理するための構文。ループ処理。


## for文の基本
for文の基本コード
```ruby:for文
for (条件式に使う変数の初期化処理; 条件式; 条件式に使う変数の値の更新) {
　　//繰り返し処理
}
```

文章で表すとこれで終了です。()の中に１行で処理を記述できるので、while文よりもすっきりとしたコードになります。
具体例もこのまま記述していきます

```ruby:具体例
let count = 0;

for (var count = 0; count < 6; count++) {
    console.log(count);
}
```

上記のコードは変数に０のデータを入れる。０〜５までの間繰り返し出力するという処理になります。count++は＋１つづ足していくという意味で、省略できるので省略した状態です。
繰り返し処理して出力するという基礎ならこれだけで終了です。


## 最後に
while文もfor文も繰り返し処理という点では一緒ですが、どちらも基礎くらいは覚えていきたいです。
必要に応じて両方使いこなせて方がいいですからね。現状だとfor文の方がよく使うんですけど。
それでは以上で終わりにしたいと思います。お疲れ様でした。
LambdaとRDSのセキュアな接続 ~SSL/TLS証明書の選択と実装~

最近、アーキテクチャにRDSのリードレプリカを組み込む作業を行ったのですが、Lambda(NestJS)からRDS(リードレプリカ)へのSSL/TLS接続を設定する際、以下のエラーメッセージが表示されました。

```objectivec
Error: self-signed certificate in certificate chain
```
この問題の原因と解決方法を備忘録として残します。

# 原因
単純に、使用する証明書が不適切だったのが原因でした。

## RDS Proxyを介する場合の証明書
元々の構成では、Lambda(NestJS)からRDS Proxyを経由してRDS(プライマリ)に接続しており、この場合には[`AmazonRootCA1.pem`](https://www.amazontrust.com/repository/AmazonRootCA1.pem)証明書を使用していました。

RDS Proxyを使用する際には、AWSが提供する`AmazonRootCA1.pem`というルート証明書が重要です。この証明書は、RDS Proxyの身元確認と通信の暗号化を保証するために用いられます。

```
Lambda(NestJS) → RDS Proxy → RDS（プライマリ）
```
https://repost.aws/ja/knowledge-center/rds-aurora-mysql-connect-proxy

## RDS(リードレプリカ)への直接接続
今回新たに追加したRDS(リードレプリカ)への接続では、RDS Proxyを介さず直接Lambdaから接続する必要がありました(RDS Proxyは主に書き込み操作の負荷を軽減し、接続管理を効率化するために使用されますが、読み取り専用のリードレプリカではこれが必要ないため、直接接続を選択しました)。

この直接接続では、リージョンに特化した`ap-northeast-1-bundle.pem(~-bundle.pem)`証明書が必要でした。

```
Lambda(NestJS) → RDS（リードレプリカ）
```

# 解決方法
この問題を解決するために、RDS(リードレプリカ)への接続で適切なSSL/TLS証明書を使用しました。

AWSの公式ページに証明書のバンドル`ap-northeast-1-bundle.pem`があったので、それを参照し直すことでエラーが解消されました。

https://docs.aws.amazon.com/ja_jp/AmazonRDS/latest/UserGuide/UsingWithRDS.SSL.html

# 補足：証明書の読み込み方法(NestJS)
アプリケーション(NestJS)でのSSL/TLS証明書の読み込みは、AWS S3から証明書を取得する形で実装しました。

## S3からの証明書取得処理
`S3CertificatesService`クラスを定義し、AWS SDKを使用してS3にアクセスします。このクラスでは、指定されたバケットとキーから証明書を取得する`getCertificateFromS3`メソッドを提供します。

```ts
import { Injectable } from '@nestjs/common'
import * as AWS from 'aws-sdk'

@Injectable()
export class S3CertificatesService {
  private s3: AWS.S3

  constructor() {
    this.s3 = new AWS.S3()
  }

  async getCertificateFromS3(bucket: string, key: string): Promise<string> {
    const params = {
      Bucket: bucket,
      Key: key
    }

    const data = await this.s3.getObject(params).promise()

    if (data.Body) {
      return data.Body.toString()
    }

    throw new Error('Failed to retrieve certificate from S3. Body is undefined.')
  }
}
```
## DB接続設定
DBへの接続設定では、上記サービスを利用してS3から証明書を取得し、DB接続の設定に適用します。ここでは`ap-northeast-1-bundle.pem`証明書を取得し、DB(MySQL)へのSSL接続に使用しています。

```ts
    const certificate = await s3CertificatesService.getCertificateFromS3('rds-certificates', 'ap-northeast-1-bundle.pem')
    const dbConfig = {
      type: 'mysql',
      host: '',
      port: 3306,
      username: '',
      database: '',
      password: '',
      ssl: {
        ca: certificate,
        rejectUnauthorized: true
      }
    }
```
AlmaLinux 9にOpenJDK 21をインストール（AppStream）

# はじめに

Application Stream(AppStream)を利用してAlmaLinux 9にOpenJDK21をインストール
親記事：[OpenJDKの各種インストール方法とEOLまとめ](https://qiita.com/witchcraze/items/b179202216aab50b7090)
参考：[Product Documentation for Red Hat build of OpenJDK 21 \| Red Hat Customer Portal](https://access.redhat.com/documentation/ja-jp/red_hat_build_of_openjdk/21)

## サポート

本手法で導入した場合、[Red Hat Enterprise Linux Application Streams Life Cycle \- Red Hat Customer Portal](https://access.redhat.com/support/policy/updates/rhel-app-streams-life-cycle) より、2029-12がEOLだと思われる。
それ以降に報告された脆弱性や不具合への対応は実施されない可能性がある。

## LOG

### インストール

```shell-session
# cat /etc/redhat-release
AlmaLinux release 9.3 (Shamrock Pampas Cat)

# yum install java-21-openjdk
... 略
```

### 各種確認

```shell-session
# which java
/usr/bin/java

# /usr/bin/java -version
openjdk version "21.0.1" 2023-10-17 LTS
OpenJDK Runtime Environment (Red_Hat-21.0.1.0.12-2) (build 21.0.1+12-LTS)
OpenJDK 64-Bit Server VM (Red_Hat-21.0.1.0.12-2) (build 21.0.1+12-LTS, mixed mode, sharing)
```
個人的よく使うC#とTypescriptで配列操作

# はじめに
C#とTypeScriptを並行してかいているとごっちゃになるため、配列操作比較。
C#の配列操作はLINQです。

今回はとりあえず特に使う4つ。

## 配列に要素が含まれているか、条件を満たす要素をチェック

### C# ⇒ Any()

```c#
string[] words = new string[] { "Hoge", "Fuga", "てすと" };
bool result = words.Any(x => x == "てすと");
```

よく使うのは配列が空じゃないか調べたいとき

```c#
string[] words = new string[] {};
bool result = words.Any();
```

### TypeScript ⇒ some()

```typescript
const words = ['Hoge', 'Fuga', 'てすと'];
words.some(x => x === 'てすと');
```

## 配列の要素が全て条件を満たしているかどうかをチェック

条件を満たさない要素が見つかった時点でfalseを返す

### C# ⇒ All()

```c#
int[] numbers = new int[] {1,2,3};
bool result = numbers.All(x => x > 0);
```

### TypeScript ⇒ every()

```typescript
const numbers = [1,2,3];
numbers.every(x => x > 0);
```

## 別の配列をつくる

息をするように使う

### C# ⇒ Select()

```c#
var test = testModel.Select(x => x.Test);
```

### TypeScript ⇒ map()

```typescript
const test = testModel.map(x => x.Test);
```

## 条件に一致する要素だけを含む新しい配列をつくる

息をするように使うパート2

### C# ⇒ FindAll or Where

`FindAll`はListでないと使えない。
FindAllはLINQではなく、List<T>クラス。
(のであまり使ってない…)
例はWhere。

```c#
string[] words = new string[] { "Hoge", "Fuga", "てすと" };
var result = words.Where(x => x == "てすと");
```

### TypeScript ⇒ filter()

```typescript
const words = ['Hoge', 'Fuga', 'てすと'];
const result = words.filter(x => x === 'てすと');
```

# おわりに
最近ぜんぜん覚えられない😢
MSYS2?GitBash?

__#１．事象__
　2023.9頃より、C++をGitを同時並行で学習している。
　ターミナルとしてC++ではMSYS2を、GitではGitBashを使用していた。
　ある時、ファイルをcommitするとエディターのPATHが通らなくなっていた。
```
(…)code --wait: line 1: code: command not found(…)
```

__#２．解決__
　誤ってMSYS2でGitのコマンドを入力しており、一部のコマンドでPATHが通らなかった。
　GitBashでコマンド実行するとPATHが通り、コミットにも成功した。

__#３．原因__
* MSYS2とGitBashを混同した
　GitBashは、MSYS2をベースにGit実行のため機能に絞って制作されたプログラム群である。※1
 ベースが同じなので、操作画面は当然似たような緑や紫色のカラフルな画面となる。（写真1・2参照）

![gitbash.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3560043/13eb7561-27f7-dbe7-532c-d0b3d5faf7f7.png)
写真1 GitBashの操作画面
![msys2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3560043/826e686a-8039-15f9-7547-2e7f587d1937.png)
写真2 MSYS2の操作画面

* ソフトに特有のPATHがある
　GitBashとMSYS2に通っているPATHを調べてみると（*echo $PATH*）、GitとGitBashで異なるディレクトリが表示される。
　~~これがイマイチ確信できていないが、__PATHは一度設定するとすべてのソフトを扱う際に同じPATHが適用されるわけではなく、ソフト特有のPATHを通す方法があるようだ。__~~
　~~自分の環境ではMSYS2が環境PATHを継承していないためこのような症状が出ていたようで、ユーザー変数に「変数→MSYS2_PATH_TYPE」「値→inherit」登録すると解決した。~~
　MSYS2の場合、以下のように、.bash_profileにVSCodeのPATHを追加することで解決した。
①バッシュで```export PATH='ディレクトリ':PATH```を実行。
![スクリーンショット 2023-11-25 144743.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3560043/e3eef29a-0b3d-6371-1232-7e47095dba24.png)
②.bash_profileにVSCodeのPATHが追加される。
![スクリーンショット 2023-11-25 144821.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3560043/6529d7dd-917b-0ee9-1f36-09a514b48ffb.png)

　今回はこれが直接的な原因となり、PATHが通らない不具合に悩まされた。

* 同じような悩みを持つ人がネットで調べても見つからなかった。
　そもそも初歩的過ぎてすぐ解決できてしまうのかもしれない。

__#４．まとめ__
・MSYS2とGitBashは混同しないようにする。
・パスはソフトごとに通す。
　（msys2の場合、exportコマンドでできる）

参照
※1　MSYS2とGitBashのルーツについて
https://qiita.com/Yuki-Inoue/items/58d3bb564cf2c20fde97
※2　PATH設定方法
https://qiita.com/n_otsuka/items/bfba784f37a98a930629
Python3で画像をリサイズする方法

## 要　旨
Python3を使用して、画像を1個リサイズする方法について記述します。
## 実行環境等
コンピューター：iMac 21.5インチ　2017年モデル
mac OS:Ventura 13.6.1
python: 3.8.3
## 実施要領
インプット画像: input.png (1280,720)
アウトプット画像: output.png (896,504)
とします。
Python3インタープリターの起動
```python:インタープリターの起動
username%python3
```
必要なライブラリの読み込み
```python:ライブラリの読み込み
>>>from PIL import Image
```
インプット画像を読み込む
```python:インプット画像の読み込み
>>>img = Image.open('input.png')
```
サイズの確認
```python:サイズの確認
>>>img.size
(1280,720)
```
リサイズする
```python:リサイズ
>>>img_resized = img.resize((896,504))
```
正しくリサイズされたか確認する。
```python:サイズ確認
>>>img_resized.size
(896,504)
```
リサイズした画像をファイル保存する。
```python:ファイル保存
>>>img_resized.save('output.png')
```
Pythonインタープリターを抜ける。
```python:インタープリターを抜ける
>>>quit() または　Ctrl+D
```
## 結　言
今回はPython3を使用して、画像を1個リサイズする方法について記述しました。
RockyLinux 8にOpenJDK 21をインストール（AppStream）

# はじめに

Application Stream(AppStream)を利用してRockyLinux 8にOpenJDK21をインストール
親記事：[OpenJDKの各種インストール方法とEOLまとめ](https://qiita.com/witchcraze/items/b179202216aab50b7090)
参考：[Product Documentation for Red Hat build of OpenJDK 21 \| Red Hat Customer Portal](https://access.redhat.com/documentation/ja-jp/red_hat_build_of_openjdk/21)

## サポート

本手法で導入した場合、[Red Hat Enterprise Linux Application Streams Life Cycle \- Red Hat Customer Portal](https://access.redhat.com/support/policy/updates/rhel-app-streams-life-cycle) より、2029-12がEOLだと思われる。
なお、RockyLinux 8自体のEOLが2029-05。
それ以降に報告された脆弱性や不具合への対応は実施されない可能性がある。

## LOG

### インストール

```shell-session
# cat /etc/redhat-release
Rocky Linux release 8.9 (Green Obsidian)

# yum install java-21-openjdk
... 略
```

### 各種確認

```shell-session
# which java
/usr/bin/java

# /usr/bin/java -version
openjdk version "21.0.1" 2023-10-17 LTS
OpenJDK Runtime Environment (Red_Hat-21.0.1.0.12-2) (build 21.0.1+12-LTS)
OpenJDK 64-Bit Server VM (Red_Hat-21.0.1.0.12-2) (build 21.0.1+12-LTS, mixed mode, sharing)
```
EC-CUBEで特定ページのみCSSを反映したい

# 基本環境

EC-CUBE4.2.2

# EC-CUBEでのCSSカスタマイズ

### デフォルト仕様

```
root/html/twmplate/default/assets/css/style.css
```
### カスタマイズ仕様
```
root/html/twmplate/default/assets/css/style.css
↓
root/html/user_data/assets/css/customize.css
```
customize.cssが後から読み込まれ優先される

# 特定ページだけカスタマイズしたい場合
そのページのtwigの`{% block main %}`より上に`{% block stylesheet %}`を設置してCSSコードを記述

```
{% block stylesheet %}
    <style>
        セレクタ {
            プロパティ: 値;
        }
        .ec-layoutRole__main {
            background: #c0c0c0 !important;
        }
    </style>
{% endblock %}

{% block main %}

{% endblock %}
```


### twig内`<style>`が反映されない

同じセレクタ指定が

`style.css`
`customize.css`
`twig内<style>`

に存在する場合、

`twig内<style>`（最優先）
　　　↓
`style.css`（優先）
　　　↓
`customize.css`

の順で読み込まれるようだ

### twig内`<style>`を反映させるには


```
<style>
        セレクタ {
            プロパティ: 値 !important;
        }
</style>
```

値に`!important`を追加する
TS評価基準にある "成人発達段階"とは？

# はじめに

株式会社OMJテクノソリューションズ Advent Calendar 2023
24日目の記事です🎄🎁

皆さん、こんにちは！
株式会社OMJテクノソリューションズ
代表取締役社長 石川祐也です。

[前回の記事](https://qiita.com/yuya-ishikawa-qa/private/6f04bc4a2212df6e85cf) で
「すべてのメンバーにとってティール組織が適して
　いるわけではなく、一部の人々にとっては馴染み
　にくいことがある。」と記載しましたが、

今回は、ティール組織を実現するためには
『構成員の"成人発達段階"の向上が必要』
という話をしていきたいと思います。

ティール組織は、どんなコミュニティでも
実現できる訳ではありません。

構成員の多くのが、ロバート・キーガン氏が提唱した
 "成人発達理論"の発達段階4, 発達段階5 に到達している
必要があります。

以下に、ロバート氏が提唱した成人発達理論の
各段階を簡単に紹介します。

注意点として、ここで述べている発達段階は優劣がある訳
ではなく、それぞれの強みと弱みがあり、次の段階には
前段階の要素を持ちながら、"含んで超える"必要がある"
ということを明記しておきます。

# 発達段階① 具体的志向段階

この段階では、具体的思考はできるが
抽象的な概念を扱うことが出来ません。

→ただ、言葉を獲得したての子供に見られるもので
　全ての成人はこの段階を超えていると言われます。
　そのためこちらの段階の具体例は割愛します。

# 発達段階② 道具主義的段階（利己的段階）

利己的段階では、個体は自己中心的で、他者との関係や
社会的な規範を理解することは難しいとされています。
個体は欲望や感覚に基づいて行動します。

→他者（会社を含む）を道具のように扱うことがあり
　自身の考えと異なる方針に直面すると、他者の考え
　に思考を巡らせずに、感情的になってしまう。

# 発達段階③ 他者依存段階（慣習的段階）

慣習的段階では、個体は社会的な規範やルールを理解し、
それに基づいて行動します。自らの役割や立場を認識し、
社会的な地位や権力を決まりごとに基づき運用できる。

→会社の方針に従って、意思決定を一部行うことが出来るが、
　会社の決まり、上司の発言に従順に従うため、それを超える
　ブレイクスルー的な意思決定や成果を出すことが出来ない。

# 発達段階④ 自己主導的段階

自己主導的段階では、他者の視点や感情を理解する能力が発達します。
個体は他者との関係を重視し、共感や協力が重要な価値となります。

→会社や他社の価値観を理解することが出来る上で、
　自分なりの価値観や、意思決定基準を儲けることができ
　自らの行動基準によって主定的に行動出来る。
　しかし自分の価値基準が絶対で融通が効かない場合がある。

# 発達段階⑤ 自己需要・相互発達段階

自己主観的段階では、個体は抽象的な概念や価値にアクセスし、
自らの役割や視点を超越して、より包括的な社会や組織の視点から
物事を捉えることが可能になります。

→この段階になると自分の価値観や意見に囚われることがなく、
　多様な価値観・意見などを汲み取り的確に意思決定ができる。
　異なる社会的な視点や価値観の相手に対しても尊重し合い、
　他者の成長により自らが成長するという共育視点を持つ。

# さいごに

今回は、ティール組織を実現するためには、
『構成員の"成人発達段階"の向上が必要』
という、お話をしました。

この記事で"成人発達理論"に興味を持ったら、
以下の文庫本がストーリー調で楽しくわかりやすく
読みことが出来るので購入して貰えればと思います！

① [なぜ部下とうまくいかないのか](https://amzn.asia/d/3ToNVXr) (男性リーダー向け)
② [リーダーシップに出会う瞬間に](https://amzn.asia/d/9z9Cq7V) (女性リーダー向け)

またロバート・キーガン氏の "成人発達段階"
こちらを、なぜOMJテクノソリューションズ
の評価基準で採択しているかというと

僕自身が、設立時からTSのメンバーは、
『エンジニアとしてだけではなく、
 　1人の人間として成長して欲しい』
という想いを込めたものであるためです。

どんな地域や環境に育ったとしても、
想いがあれば、学び育ち働ける環境を！

これからもOMJテクノソリューションズは
作り続けていきたいと心から願っています。
[GCP]Cloud Pub/Sub概要

Pub/Subの概要を思い出すための自分用メモ。

# 概要
Cloud Pub/SubはGCPが提供するメッセージングサービスである。

**メッセージングサービス**

- システムから別システムへのデータの送受信を、プログラミング言語、プラットフォームを超えて実現する仕組み
- システム間を疎結合にして、1システムで問題が発生したとき、全体に波及するのを防ぐ
- 非同期処理を実現できる
  - 送信側は受信側の処理を待たなくていい
  - 受信側は処理可能なタイミングで処理できる


**Pub/Subでのデータ送信・処理イメージ**
(システムAからシステムBへpush型でデータを配信する場合)

![CloudPubSub (1).jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59542/c4f6c4a2-7ea4-a0fd-e849-7bc531987442.jpeg)


**Publisher**
データ送信側のシステム

**Subscriber**
データ受信側のシステム

**Topic**
Pub/Subの機能。
publisherがデータを送信する窓口。
データの保存期間はここで設定。

**Subscription**
Pub/Subの機能。
Subscriptionに対する設定(以下のようなもの)に基づいて、Topicに届いたデータをSubscriberに送信する。
- 紐づけるTopic
- Subscription自体の有効期間
- データの再送信間隔
- データの送信順
- データ送信失敗時の試行回数
- データ送信失敗の記録間隔(試行回数)
- Subscriberのエンドポイント


参考

https://www.sunnycloud.jp/column/20210525-01/

https://cloud-ace.jp/column/detail417/

https://future-architect.github.io/articles/20230613a/

https://cloud.google.com/pubsub/docs/subscription-properties?hl=ja


https://registry.terraform.io/providers/hashicorp/google/latest/docs/resources/pubsub_subscription#nested_push_config

https://registry.terraform.io/providers/hashicorp/google/latest/docs/resources/pubsub_topic#message_storage_policy
AlmaLinux 8にOpenJDK 21をインストール（AppStream）

# はじめに

Application Stream(AppStream)を利用してAlmaLinux 8にOpenJDK21をインストール
親記事：[OpenJDKの各種インストール方法とEOLまとめ](https://qiita.com/witchcraze/items/b179202216aab50b7090)
参考：[Product Documentation for Red Hat build of OpenJDK 21 \| Red Hat Customer Portal](https://access.redhat.com/documentation/ja-jp/red_hat_build_of_openjdk/21)

## サポート

本手法で導入した場合、[Red Hat Enterprise Linux Application Streams Life Cycle \- Red Hat Customer Portal](https://access.redhat.com/support/policy/updates/rhel-app-streams-life-cycle) より、2029-12がEOLだと思われる。
なお、AlmaLinux 8自体のEOLが2029-05。
それ以降に報告された脆弱性や不具合への対応は実施されない可能性がある。

## LOG

### インストール

```shell-session
# cat /etc/redhat-release
AlmaLinux release 8.9 (Midnight Oncilla)

# yum install java-21-openjdk
... 略
```

### 各種確認

```shell-session
# which java
/usr/bin/java

# /usr/bin/java -version
openjdk version "21.0.1" 2023-10-17 LTS
OpenJDK Runtime Environment (Red_Hat-21.0.1.0.12-2) (build 21.0.1+12-LTS)
OpenJDK 64-Bit Server VM (Red_Hat-21.0.1.0.12-2) (build 21.0.1+12-LTS, mixed mode, sharing)
```
共創と共育を実現するティール組織とは？

# はじめに

株式会社OMJテクノソリューションズ Advent Calendar 2023 
23日目の記事です🎉

初めまして、もしくはお久しぶりです。
株式会社OMJテクノソリューションズ（以下TS）
代表取締役社長 石川祐也です。

弊社は2022年12月28日に以下の2社の合弁会社
という形で設立された会社になります。
・株式会社オーダーメイドジャパン
・株式会社クエストアカデミア

私がこの会社（システム開発事業）の設立に携わったのは、
①私自身が地方と都市での教育格差を感じていた
②地方在住のままでも学び成長できる環境を作りたい
③経験が浅いメンバーでも開発経験を積める環境を作りたい
このような想いからでした。

合弁会社ということで私一人の創業ではなく、
想いを共にする創設メンバーが複数名いたこと、

また設立時の想いである成長できる環境を作りたいという考えから、
・自主性と目的思考を大切にした共創文化
・組織の目的に向かって個人も共育文化
を実現できる "ティール組織"として、会社経営することにしました。

## ティール組織とはなんだろう？

ティール組織（Teal Organization）は、フレデリック・ラルー氏
によって提唱された組織モデルです。ティール（青緑色）組織は、
組織の進化段階として「ティール」と呼ばれる次の段階を指します。

### ①赤（Red）
進化段階: 赤（Red）
特徴: 力や力のバランスが中心。絶対的な権威と服従が支配的。
組織モデル: 軍隊や一部のトラディショナルな組織。

### ②アンバー（Amber）
特徴: ヒエラルキーと規律が重要。組織内の役割や責任が厳格に決まる。
組織モデル: 大規模な企業や機構。

### ③オレンジ（Orange）
特徴: 成果と競争が重要。イノベーションや個人の成功が強調される。
組織モデル: 多国籍企業や市場主義的な組織。

### ④グリーン（Green）
特徴: 共感と協力が重視され、組織内のコミュニケーションが強化。
組織モデル: チームワークやコミュニティ志向の組織。

### ⑤ティール（Teal）
特徴: 自己管理と目的志向が中心。柔軟で分散された組織構造。
組織モデル: ラルーの提唱したティール組織。


## ティール組織の特徴とメリット

ティール組織は、
・自己管理や目的思考を大切にし、
・役割や責任の分散を行うため、

現場の必要性に応じた、柔軟で創造性やイノベーション
が発揮された意思決定をすることが可能になっています。

ディール組織が実現によるメリットは、
自己主導型で目的志向であることで、
個人のモチベーション向上に繋がり
成果に対する責任と熱意が生まれることです。

実際に導入した場合も、会社の方向性と
メンバーの志向性が上手くマッチした場合は
・エンゲージメントシステムの導入
・社内ポータルサイトの構築&運用
・社員ニーズに沿ったAWS勉強会
など

自主的で革新的アイディアが提案され、
ボトムアップ型で、数多く採択されました。
＊私からの提案がなく発案&実行されています。

## ティール組織のデメリットと実例紹介

しかしもちろんデメリットがあり、
①ティール組織の原則や価値観は従来の組織文化
　とは異なるため、浸透には時間がかかることがある。

→"カウンシル"という実行プロジェクトが
　軌道に載るまでに10ヶ月ほどかかりました。

②従来の指令命令型のリーダーシップから、
　協力とサポートを重視するサーバント型
　リーダーシップの形成が必要。

→最初は意思決定をするというプロセスに慣れておらず
　会社目的を理解した上で、自主的に思考するまでには
　メンバーとリーダーの意識改革の時間が必要。

③すべてのメンバーにとってティール組織が適して
　いるわけではなく、一部の人々にとっては馴染み
　にくいことがある。

→構成員に成人発達段階が低いメンバーが多い場合には、
　会社目的（MVV）に沿わない意思決定が発生して、
　社内で混乱や不和が生じることがある。

④決定権や責任の分散が進むため、
　一部で意思決定が遅れる可能性がある。

→上位下達ではないため、急激な成長を望む場合には適さない。
　経営陣は、責任領域を犯さないような配慮が必要である。

# さいごに

ティール組織は、実現することで
・自主性と目的思考を大切にした共創文化
・組織の目的に向かって個人も共育文化
を築き上げることができ、

現場の必要性に応じた、柔軟で創造性やイノベーション
が発揮された意思決定をすることが可能になっています。

導入に際しては、多くの不安や混乱に直面することが
あるかと思いますが、どのような組織を作り上げたいか、
という "目的志向"から逆算し、進んでいきましょう。

[次回の記事](https://qiita.com/yuya-ishikawa-qa/private/98a7d2b45d197c8eab9b) では
「すべてのメンバーにとってティール組織が適して
　いるわけではなく、一部の人々にとっては馴染み
　にくいことがある。」という項目を深堀して、

ティール組織を実現するために、構成員がどのような
素質を持つべきかについて話したいと思います。

ではまた次回にお会いしましょう！
【Unity初歩】~オブジェクトを動かす~

# はじめに
前回オブジェクトの配置までが完了しました。
今回は配置したオブジェクトを動かしてみます。

前回の記事

https://qiita.com/usomaru/items/f81e46dd8246fe61e112

# 配置したオブジェクトを動かすスクリプトをかく
前回配置した🦀のオブジェクトを矢印キー入力によって動くようにしたいと思います。

## スクリプト起動の流れ
スクリプトを起動すると最初にStartメソッドが1度だけ走ります。
その後、Updateメソッドがフレームごとに繰り返し走ります。

## スクリプト作成

プロジェクトウィンドウの＋ボタンをクリックします。
(プロジェクトウィンドウ内で右クリ→Create選択でも可能です。)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201826/f8dac859-2aff-5ba6-8bca-7eb02f8f9663.png)

C# Scriptを選択します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201826/1e082117-556e-89b4-6de1-19b2cef09983.png)

C#スクリプトが作成されました。
名前は「PlayerController」とします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201826/94c35d6f-9b1a-8d17-24c1-8b22be141406.png)

追加したスクリプトをダブルクリックをするとソースコードが開きます。
※エディタをVisual Studioに設定しているために、Visual Studioが立ち上がっています。エディタの設定方法は下の[スクリプトをVisual Studioでかきたい](#スクリプトをvisual-studioでかきたい)で紹介しています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201826/1f18d49b-a59e-7c76-e944-23bb70ce40b2.png)

矢印キーでオブジェクトが動くようなソースコードをかいていきます。

```c#
using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class PlayerController: MonoBehaviour
{
    void Start()
    {
    
    }

    void Update()
    {
        // 左矢印が押されたとき、左に3移動
        if (Input.GetKeyDown(KeyCode.LeftArrow))
        {
            transform.Translate(-3, 0, 0);
        }

        // 右矢印が押されたとき、右に3移動
        if (Input.GetKeyDown(KeyCode.RightArrow))
        {
            transform.Translate(3, 0, 0);
        }
    }
}
```

ここで登場する`Translate`メソッドはオブジェクトを今の座標から引数に与えた分だけ移動するメソッドです。

かいている内容はjavascriptでゲームを作成したときと同じ感じだなという印象を持ちました。

## スクリプトをVisual Studioでかきたい
Edit -> Preferencesをクリックします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201826/378a89c9-6cc4-bdf0-1a7b-850fac0b2a80.png)

開いた画面でExternal Toolsを選択すると、一番上の「External Script Editor」で自分の好きなエディタを選択することができます。
私はVisual Studioを選びましたが、Visual Studio Codeも選択できます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201826/d58cf91a-aaea-d1b7-0bce-6d9cba2d090a.png)


# かいたスクリプトをオブジェクトにアタッチする
アタッチをすると、オブジェクトはスクリプトでかいた指示通りに動くようになります。

PlayerControllerをヒエラルキーウィンドウの「kani_enemy」にドラックアンドドロップします。
これでアタッチ完了です。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201826/82d7d3d6-ae62-aa4c-a183-d578b5703347.png)



ゲームを実行してみます。

初期値
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201826/a4a40bef-ed05-06ed-4b45-75d5c03446f7.png)

右矢印クリック
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/201826/937a1c77-6237-f5a6-0d3b-2edbf11f63ac.png)


動いた！けど、ちょっと動かす距離を取りすぎたかもしれません🤣
あと、今回KeyDownでかいてるので、長押しで🦀が動かないため連打が必要でした。
IAM に関するメモ

# はじめに

AWSのアカウント・ユーザー・権限の関係性が複雑に感じていたので、一から IAM について調べたことをまとめます。

# 概要

- IAM とは
- IAM ユーザー
- IAM ポリシー
- IAM ロール

# IAM とは

IAM は「Identity and Access Management」の略で、IDとアクセス権を管理するサービスになります。

複数のAWSアカウントが存在する際、誰がどのアカウントにアクセスできるか、どのサービスを利用できるのかといった権限を管理するためのサービスです。

<br>

※複数のAWSアカウントを持つメリットとデメリット

https://dev.classmethod.jp/articles/account-and-vpc-dividing-pattern/

# IAM ユーザー

IAM ユーザーは **人に与えられるID** で、AWSアカウントにログインする際に必要となるユーザー名とパスワードが付与されます。

下記のように１つのAWSアカウントに複数のユーザーを作成することが可能で、従業員１人ずつ個別のIAMユーザーを作成することが推奨されます。

```
├── AWS アカウントA
│   ├── IAM ユーザーA1
│   └── IAM ユーザーA2
│
└── AWS アカウントB
    ├── IAM ユーザーB1
    └── IAM ユーザーB2
```

新規作成したIAMユーザーには権限が存在しないため、後述する IAMポリシーを割り当てることでアクセス権を付与します。

ユーザーを複数まとめる「IAMユーザーグループ」という機能もあり、後述するIAMポリシー（アクセス権限）をグループに対して付与することも可能です。

<br>

別途として、AWSアカウントにログインするとき以外にも、プログラムに権限を渡したい場合にもIAMユーザーを作成することがあります。

# IAM ポリシー

IAM ポリシーは

- 何に対して
- どんな操作を
- できる（できない）

ということを定義した認可用のドキュメントで、AWSリソース（EC2やRDSなど）にアクセスするための権限設定になります。

IAMユーザーや後述のIAMロールに割り当てることで、これらの認可情報を付与します。

<br>

AWSがデフォルトで用意してくれているポリシーもありますが、自作することも可能です。

| ポリシー | 作成者 | 説明 |
| ---- | ---- | ---- |
| AWS管理ポリシー | AWS | AWSによって事前に作成されているポリシー |
| カスタマー管理ポリシー | 利用者 | 複数のIAMユーザーやIAMグループ、IAMロール間で共有可能 |
| インラインポリシー | 利用者 | 1:1で特定のIAMユーザーやIAMグループ、IAMロールに対して適用する |

<br>

またIAMポリシーにはいくつかのアタッチ先が存在します。

| ポリシー | アタッチ先 |
| ---- | ---- |
| ユーザーベースのポリシー | IAMユーザー |
| リソースベースのポリシー | AWSリソース |
| IAMロールの信頼ポリシー | IAMロール |


# IAM ロール

IAM ロールは IAMポリシーをグループ化したようなもので、IAMユーザー、IAMグループ、AWSリソース（EC2、RDSといったAWSサービス）に対して付与するものになります。

前述したIAMポリシーをまとめてグループ化したものに名前を付けて管理することができます。

例えるなら、

```
├── 人事部権限（IAM ロール）
│   ├── 人員管理表のアクセス権（IAM ポリシー）
│
└── 開発部権限（IAM ロール）
    ├── ソースコードへのアクセス権（IAM ポリシー）
    └── 本番用AWS環境へのアクセス権（IAM ポリシー）
```

のようなイメージです。

AWSリソースへのアタッチですが、AWSリソースにはIAMポリシーを直接アタッチできるもの（S3、Lambdaなど）とできないもの（EC2、RDSなど）があります。
直接IAMポリシーをアタッチできればそれでよいのですが、できないリソースに対してはIAMロールとしてグループ化したものをアタッチすることで、リソースごとの権限を割り当てることができます。

また、IAMロールはアカウント間で共有して使用することが可能です。

<br>

ここでの詳しい説明は割愛させていただきますが、IAMロールを使うことでユーザーに対して**一時的な**権限を付与することもできます。

管理者が一時的に操作権限を割り当てて、完了したら権限を外して...といった面倒な作業も、STS（AWS Security Token Service）＋IAMロール の組み合わせにより、認証後の一定期間が過ぎると操作権限を無効にする、といったように自動化できるようになります。

https://zenn.dev/fdnsy/articles/31105a37126d66

# 最後に

他のAWSサービスにも言えることですが、実際に使ってみた方が覚えるのが早そうです。

<br>

【参考記事】

https://dev.classmethod.jp/articles/aws-iam-beginner/

https://www.idaten.ne.jp/portal/page/out/secolumn/multicloud/column005.html

https://qiita.com/montama/items/90bb8a3973d101be4690

https://qiita.com/ninoko1995/items/79ab8c7c40825c9b68f5

https://zenn.dev/fdnsy/articles/31105a37126d66