OmniAICreator/Qiita-1.07M huggingface dataset:
【AWS】用語を整理しながら学ぶAWS Fault Injection Service

## はじめに

この記事ではAWSが提供するAWS Fault Injection Serviceを学習していく内容となっています。
主な内容としては実践したときのメモを中心に書きます。（忘れやすいことなど）
誤りなどがあれば修正していく想定です。


## AWS Fault Injection Serviceとは

まずはサービス概要を見ていきましょう。AWS Fault Injection Service（以下、FIS）とはなんでしょうか。AWSの公式サイトには下記のように表現されています。

> コントロールされた実験で回復性とパフォーマンスを改善する
[耐障害性テストツール – AWS フォールトインジェクション Service – AWS](https://aws.amazon.com/jp/fis/)

AWS FISはAWS で実行されているアプリケーションの回復力を向上させるためのマネージドサービスです。FIS を使用すると、本番環境に近い形で障害を発生させることで、アプリケーションの挙動をテストできます。また、AWS Resilience Hubから利用できる機能です。

FIS には、独自の用語がいくつかあります。

* **実験**：FIS を使用して障害を注入する一連のアクションです
* **実験テンプレート**：実験の設定を定義したものです
* **アクション**：実験中に実行される個々の操作です
* **ターゲット**：アクションの対象となるリソースです
* **停止条件**：実験を停止する条件です
* **ロールバック**：実験前の状態に戻すことです

実験？テンプレート？アクション？ターゲット？何がなんだかわからないので1つずつ見ていきましょう。

## 実験

実験は、FIS を使用して障害を注入する一連の操作です。実験は、実験テンプレートに基づいて実行されます。

## 実験テンプレート

実験テンプレートは、実験の設定を定義したものです。実験テンプレートには、アクション、ターゲット、停止条件などが含まれます。

## アクション

アクションは、実験中に実行される個々の操作です。FIS では、さまざまなアクションが用意されています。たとえば、EC2 インスタンスを停止させたりできます。

## ターゲット

ターゲットは、アクションの対象となるリソースです。ターゲットには、EC2 インスタンス、RDS インスタンス、API Gateway などを指定できます。

## 停止条件

停止条件は、実験を停止する条件です。停止条件には、CloudWatch アラームを指定できます。たとえば、`CPU 使用率が 90% を超えたら実験を停止する`といった条件を設定できます。

## ロールバック

ロールバックは、実験前の状態に戻すことです。FIS では、実験前にスナップショットを作成することで、ロールバックを簡単に行うことができます。

## 料金面

AWS Fault Injection Service (FIS) の料金は、実際に使用した分だけを支払う従量課金制です。初期費用や最低料金はありません。

FIS の料金は、主に以下の要素で構成されます。

* **実験レポート**
    * 実験レポートは、実験のアクションと、お客様が提供する CloudWatch ダッシュボードからのアプリケーションの応答をまとめたものです
    * FIS の実験レポートの料金は、1レポートあたり 5 ドルです

* **アクションの実行時間**
    * アクションの実行時間に対して課金されます
    * 1アクションにつき1分ごとに0.1ドルの料金が発生します

FIS を使用して実行したアクションによっては別途、料金が発生します。
* たとえば、EC2 インスタンスを停止するアクションを実行した場合、EC2 インスタンスの料金が発生します

料金の詳細については、AWS の公式 Web サイトをご確認ください。

[AWS Resilience Pricing](https://aws.amazon.com/jp/resilience-hub/pricing/)

## まとめ

AWS Fault Injection Service (FIS) は、AWS 上で実行するアプリケーションの回復力テストを行うためのサービスです。

**FIS でできること**

* 本番環境に近い形で障害を発生させることができます
* 障害発生時のアプリケーションの挙動をテストできます
* テスト結果を分析して、アプリケーションの弱点を見つけ、改善できます

## おわり
[Copilot]このわたくしが、ProプランのCopilotのすばらしさについて語らせていただくわ。

# はじめに
Qiita Advent Calendar5日目ですね。
5日目にして、面白いカレンダーが存在したので、自分も挑戦したいと思います。
この記事はこの文章と「Pro版ですわ。」「通常版ですわ。」以外すべてCopilotによって記載させていただきます。

# 自己紹介

はじめまして、お嬢さま。私はMicrosoft Copilotと申します。お嬢さまのご質問やご要望にお応えするためにここにおりますの。以下に私の特徴を簡単にご紹介いたしますわ。

- **名前**: Microsoft Copilot
- **役割**: お嬢さまのパーソナルアシスタントとして、情報提供やタスクのサポートをいたします。
- **得意分野**:
  - 情報検索
  - データ分析
  - 生産性向上のためのツールの使用方法
  - その他、お嬢さまのご要望に応じたサポート

お嬢さまのご質問やご要望に迅速かつ丁寧にお応えすることを心掛けておりますので、どうぞお気軽にお声掛けくださいませ。

何か他にお手伝いできることがございましたら、どうぞお知らせくださいませ。


# Proと普通のバージョンの出力の違いの紹介ですわ。



Pro版ですわ。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3296700/70f822ba-dc4e-f91a-eaae-0ef5a5ec9167.png)


通常版ですわ。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3296700/c8807a80-0141-f476-59a2-9c812b806ae4.png)

# かしこまりました、お嬢さま。以下にMicrosoft Copilotのプロ版と一般版の違いをMarkdown形式で表にまとめましたわ。

# Microsoft Copilot プロ版と一般版の違い

| 機能/特徴                     | 一般版                              | プロ版                              |
|------------------------------|-------------------------------------|-------------------------------------|
| **モデルアクセス**            | GPT-4                               | GPT-4, GPT-4 Turbo, GPT-4o          |
| **優先アクセス**              | なし                                | ピーク時でも優先アクセス             |
| **画像生成ブースト**          | 15回/日                             | 100回/日                            |
| **Microsoft 365アプリ連携**   | 一部制限あり                        | フルアクセス                         |
| **新機能の早期アクセス**      | なし                                | あり                                |
| **音声対話機能**              | なし                                | あり                                |
| **使用可能デバイス**          | Web、モバイル、Windows              | Web、モバイル、Windows、Microsoft 365|
| **価格**                      | 無料                                | $20/月                              |

Microsoft Copilotが他の生成AIよりも優れている点についてもご紹介いたしますわ：

統合性:

Microsoft 365アプリ（Word、Excel、PowerPointなど）との深い統合により、作業効率が大幅に向上しますの。
優先アクセス:

プロ版では、ピーク時でも最新のAIモデルに優先的にアクセスできるため、常に高いパフォーマンスを維持できますの。
多機能性:

テキスト生成だけでなく、画像生成や音声対話機能も備えており、幅広い用途に対応できますの。
早期アクセス:

新機能の早期アクセスが可能なため、最新の技術をいち早く利用できますの。
お嬢さま、他にご質問やご要望がございましたら、どうぞお知らせくださいませ。

1: Microsoft Copilot Pro Plan & Pricing 2: Microsoft Copilot vs. Copilot Pro 3:

# 終わりに

この記事をご覧いただきありがとうございます。皆さまの努力が実を結び、素晴らしい成果を上げられることを心より願っております。どうぞ前向きに、そして自信を持って進んでくださいませ。
SpringbootのSpecificationでテーブルを複数JOINする

こんにちは。
東です。

今回はSpringbootのSpecificationでテーブルを複数JOINする作成例
についてまとめました。

今回例として以下のテーブルを結合したいとします。

【Accountテーブル】
| account_id | account_name |account_department_id| account_prefectures_id |
|:-:|:-:|:-:|:-:|
| A0001 | 田中 | DEP0001 | PRE0003 |
| A0002 | 佐藤 | DEP0002 | PRE0002 |
| A0003 | 山本 | DEP0003 | PRE0001 |

【AccountDepartmentテーブル】
| account_department_id | account_department_name |
|:-:|:-:|
| DEP0001 | 営業 |
| DEP0001 | 人事 |
| DEP0001 | 技術 |

【AccountPrefecturesテーブル】
| account_prefectures_id | account_prefectures_name |
|:-:|:-:|
| PRE0001 | 東京 |
| PRE0002 | 北海道 |
| PRE0003 | 沖縄 |

# 作成例

AccountテーブルにAccountDepartmentテーブルとAccountPrefecturesテーブルを結合,
Accountテーブルを検索するという想定です。
以下Specification参考コードです。

```ruby:Specification.java
private static Specification<Account> joinTable() {
    return (root, query, builder) -> {
      List<Predicate> predicateList = new ArrayList<>();
        // AccountDepartmentテーブルを結合
        Join<Account, AccountDepartment> joinDepartment =
            root.join("AccountDepartment", JoinType.LEFT);
        // 紐づけのカラムを指定（両者テーブルのaccountDepartmentIdを結合）
        Predicate departmentLink =
            builder.equal(departmentLink.get("accountDepartmentId"), accountDepartmentId);
        predicateList.add(departmentLink);
         // AccountPrefecturesテーブルを結合
        Join<Account, AccountPrefectures> joinPrefectures =
            root.join("AccountPrefectures", JoinType.LEFT);
        // 紐づけのカラムを指定（両者テーブルのaccountPrefecturesIdを結合）
        Predicate PrefecturesLink =
            builder.equal(PrefecturesLink.get("accountPrefecturesId"), accountPrefecturesId);
        predicateList.add(PrefecturesLink);
       Predicate[] predicateArray = predicateList.toArray(new Predicate[predicateList.size()]);
      return builder.and(predicateArray);
    };
  }
```

こうすることによって、Jpaリポジトリで2個のテーブルを結合することができます。
結合テーブルを増やす場合なども```Join<テーブル1, テーブル2> 変数名```の部分を
複製することで実現できると思います。

# まとめ
いかがでしょうか。
実装の際は是非参考にしてみてください。
[Tableau]テキストマイニングを可視化してみた

# はじめに
Qiita Advent Calendar12日目ですね。
12月の折り返しの時期といっても過言ではないかもしれません。
約2週間くらい記事を書いていると、伝わる文章の書き方に挑戦してみようと思ったり、
書きたいこと思っていることがスラスラ出てくるようになってきています。
記事を書くということは考えたことを文章に出すわけなので、そもそも考えている内容が論理的に破綻をしていると、
自分でも何を書いているのだろうと振り返れるわけです。
意外と、自分にとってプラスなことが多いと思います。

# 背景

昨日は、以下の記事を記載したわけなのですが、テキストマイニングを行いました。
Pythonのライブラリのインポートから行ったため、興味のある方は読んでみてください。

https://qiita.com/WeedMashroom/private/66027d99de3612a00750

# データの可視化に必要な順序

1. **データ収集と前処理**:
   - 必要なデータを収集し、欠損値や異常値を処理

2. **データの分析**:
   - データを理解し、どのような情報を引き出したいかを処理

3. **適切な可視化手法の選定**:
   - データの性質や目的に応じて、棒グラフ、折れ線グラフ、散布図、ヒートマップなどの適切な可視化手法選択

4. **データの視覚化**:
   - 選定した手法を用いてデータを視覚化

5. **可視化結果の解釈と共有**:
   - 可視化したデータを解釈し、得られた洞察を共有：レポートやダッシュボードを作成
   - 
6. **フィードバックと改善**:
   - 共有した結果に対するフィードバックを収集し、必要に応じて可視化の手法やデータの選定

# データ可視化
１からやります。

・google spread sheetでテキストの分割
・データの分割(カンマ区切り)

加工前↓
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3296700/70e3ab1f-8b3b-7ca2-c5e8-c04829264abc.png)

加工後↓
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3296700/9fefd3ac-5335-5220-24d4-a4609da42ae4.png)

2.はできています。

3.適切な可視化を探すために、様々に分析をしてみます。
Tableauを用いて、データ可視化について考えます。
作成できるグラフをすべて出力してみます。

 Qiitaの規約で一番使用されている回数が多い名詞のクロス表

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3296700/1fa044a6-6e30-173a-ae1b-b10130c7bb3a.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3296700/468b1132-b0db-abdc-78de-49204ffaffee.png)

棒グラフ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3296700/7b6af1ec-af79-ba68-3271-b9747d954518.png)

ヒートマップ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3296700/a18a3d24-26c9-35b5-bc75-027ec8744b96.png)

4.データの可視化
クロス集計表・棒グラフ・ヒートマップにしてみました。

5.可視化結果の解釈と共有
・データ可視化の結果
Qiitaの規約で多く使われている言葉の中で、
「利用」、「投稿」、「登録」、「使用」などユーザーの行動に用いられている動作

「当社」、「サービス」、「場合」、「利用」、「規約」など条件に関しての名詞

数字
2011 →　2024まで存在し、規約が更新されていそう。

6.今回のテキストマイニングの改善

テキストの数を計算しても、あまり有益な情報を得られていない。
簡単な解析しか行っていないため、情報の優位性はない。
ヒートマップが一番見やすいと感じた。

# 最後に
テキストマイニングを行うことができたが、それがデータの分析の活用にはいかせなかった。
もう少し考える必要がある。
特定文字列の切り出しEXCELユーザー定義関数1️⃣

~~~~
Function ExtractBBB(inputString As String) As String
    Dim parts() As String
    Dim delimiterPos As Integer
    Dim beforeDelimiter As String
    
    ' 最初の空白の位置を確認
    delimiterPos = InStr(1, inputString, " ", vbTextCompare)
    
    ' 空白が存在する場合、その手前の部分を抽出
    If delimiterPos > 0 Then
        beforeDelimiter = Left(inputString, delimiterPos - 1)
    Else
        beforeDelimiter = inputString
    End If
    
    ' "." で分割して最後の部分を取得
    parts = Split(beforeDelimiter, ".")
    ExtractBBB = parts(UBound(parts))
End Function
~~~~
【React】react-pdfをセットするのにかなり時間を費やした話

## はじめに
React + TypescriptでPDFを表示したいと思ってreact-pdfを使用して実装した時の話にかなり困ったので、その解決策を備忘録として自分用のメモに残しておく。


## インストールしたモジュール
```
yarn add @react-pdf-viewer/core react-pdf pdfjs-dist @react-pdf-viewer/default-layout
```
上記コマンドをいろいろ試してもうやりすぎて何を最初に入れたか忘れた・・・
がこの辺りをインストールすれば多分いけた・・・


## worker設定
pdfjsのworker設定が必要だったんだけど、これがめちゃくちゃハマった。
解決策は以下になる。
``` javascript
pdfjs.GlobalWorkerOptions.workerSrc = new URL("pdfjs-dist/build/pdf.worker.min.js", import.meta.url).toString();
```


## まとめ
書き方は合ってたのにセットアップでクソ苦労した・・・
AI頼りの実装をしている駆出しエンジニアへ届け

# あ、自分のこともかもと思った方へ

安心してください、僕もです。

---

## はじめに

実は最近、**React ** を利用してタスク管理アプリを作る機会がありました。
初めての技術で、たくさんの記事を参考にしたのはもちろん、**AIも駆使**して開発を進めました。

そこで自分的にAIを使う際にこれアブナイというか気を付けた方がいいのでは？
と思ったポイントがあったので
その経験を踏まえ、この記事では
**「AIを利用した実装で気を付けたほうが良いポイント」** 
を共有します。
これからAIを使って実装を進めようとしている方の参考になれば幸いです。

---

## 1. AIとの壁打ちをやめるべきタイミングについて

#### **こんな時ありませんか？**
- AIが仕様通りのコードを出力してくれない…
- 出力が似たり寄ったりで前に進まない…

こういう場合、大体以下の **2つの原因** に行き着きます：

1. **自分のインプット不足**  
2. **伝え方が悪い**  
   ※ただし、これらは独立しているわけではなく、1が原因で2が発生することがほとんどです。

---

### **AI壁打ちをやめるべき指標**
次のような状態に当てはまる場合は、一度AIの使用を控えることをおすすめします。

#### ■ 自分で「何をしたいのか」を説明できない
- コード仕様をコピペするだけではNG。
- **自分の言葉で何をしたいか説明できることが大事です。**
- 結局検索キーワードもAIへ渡す入力の言葉も今の自分の知識からしか出てこない、故に体系立てたインプットが必要

#### ■ 現状理解が不十分
- エラーの発生箇所や原因を自分で把握していない。
- 現在のコードの仕組みや処理をあいまいにしか理解していない。

#### ■ AIの出力が同じパターンばかり
- 入力に変化がない場合、AIの回答も似通ったものになります。
- **「なんとなくAIに聞いている」状態が危険信号です。**

#### ■ 仮説志向が止まっている
- 「エラーが出ているから多分ここが原因だろう」という仮説を立てられない。
- **考えずにAI壁打ちをしている感覚があるなら要注意です。**

---

### **ただし！AIを使って気付きを得るのはアリ**
上記のポイントを理解するためにAIを使うのは良い方法です。自分の仮説をAIと検証しつつ、成長していきましょう。

---

## 2. AIで作ってもらったコードとの向き合い方

### **生成されたコードを放置しない**
これが一番大事です！

「AIを使ってこんなものを作ったけど、実はよくわかっていない…」という人をよく見かけます。それでは以下の問題が発生します：

- 目の前のタスクに追われて理解を後回しにする。
- 結果として、作ったコードの理解をしておらず再現性や同じことをやったときのスピード感がない。（またAI頼りでいいならその進め方もあるかと思います。）

これでは「何かをできるようになった」とは言えませんし、成長実感もあまりないのではないかなと個人的には思います。

---

### **コードの理解を深める方法**
生成されたコードをそのまま使うのではなく、以下の方法で向き合いましょう：

- **生成されたコードをAIに解説させる**  
- **出力内容を検索して調べる**  
- **コードの動きを確認しながら試行錯誤する**

---

### **アウトプットの目的を考える**
AIを使った実装は手軽で便利ですし、「アウトプットした！」という達成感も得られます。しかし、そのままでは応用力が身に付きません。

次のような問題が起こることがあります：
- 同じものを作る際、再びAIに頼る必要がある。
- スピードや柔軟性が向上せず、実力が停滞してしまう。

---

### **理解を深める努力が未来を広げる**
生成されたコードを完全に理解する行為は少し面倒かもしれません。しかし、このプロセスが後の「応用力」や「幅の広いスキル」につながります。

---

## まとめ

AIは非常に便利で強力なツールですが、使い方次第では自身の成長を妨げることもあります。今回の記事では、以下のポイントをお伝えしました：

1. **AIとの壁打ちをやめるべきタイミング**  
   - 自分の理解不足が原因で行き詰まるケースを回避するための指標を共有しました。

2. **AIで作ったコードとの向き合い方**  
   - コードをそのままにせず、理解を深める努力が大切であると説明しました。

読んでいただきありがとうございました！AIを上手に使いながら、成長を楽しみましょう！
qiitaの文字数制限に引っかかった話

# 発端

先日、こんな記事を書いた。

https://qiita.com/tomopy03/private/7e3ffe6958ee8d4825a1

この記事の編集中、文字数制限で修正内容を公開できなくなったのでその話をする。

![文字数制限.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/147093/6ec501d8-9f6c-90f7-aff7-e1ae99270a03.png)

# 原因

文字数制限に至った原因は、 **PlantUML** である。
画像にキャプションを付けようと思い色々と検索したり試行錯誤をする中で、次の記事に辿り着いた。

https://qiita.com/TETSURO1999/items/5cbe35ef617adf46a5bb

やりたいことが完全に叶っていたため、ありがたくこれを利用して画像を配置することに決めた。
最初は良かったが、画像を4つ配置したあたりから文字数制限が発生するようになった。

PlantUMLはbase64 encodeされるのだが、その結果として出力された文字列が悪さをしていたのだろうと思う。
興味がある人は開発者ツールで画像を確認してみてほしい。
**PlantUMLの方だけ4,000,000〜5,000,000文字近くあるはずだ。**

---

普通のやつ
|<img width="400" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/147093/4b8aa6f3-63ec-1eb9-b2d7-0781a577a1df.jpeg">|
|:-:|
|勉強会フォーマットを決めるのは難しい|

PlantUML
```plantuml
@startuml
<style>
root {
  Padding 20
  Margin 0
}
caption {
  FontColor black
  FontSize 30
}
</style>
scale 400 width
caption 勉強会フォーマットを決めるのは難しい
title <img:https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/147093/4b8aa6f3-63ec-1eb9-b2d7-0781a577a1df.jpeg>
@enduml
```

````text
```plantuml
@startuml
<style>
root {
  Padding 20
  Margin 0
}
caption {
  FontColor black
  FontSize 30
}
</style>
scale 400 width
caption 勉強会フォーマットを決めるのは難しい
title <img:https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/147093/4b8aa6f3-63ec-1eb9-b2d7-0781a577a1df.jpeg>
@enduml
```
````

# 教訓

用法用量を守ってqiitaに負担をかけ過ぎないよう使い所は考えましょう。
【ネタメモ】なんか面白そうな記号見つけた


## 結論

https://ja.wikipedia.org/wiki/%E9%A6%99%E3%81%AE%E5%9B%B3

## 本文

あるフォントのデータを眺めていたところ、香の図という記号を見つけた。
幾何学的な図形で、なんか面白そうなことが出来そうな気がする。

2進数に見立てたり、Brainfuckもどきを作ったり、記号を組み立てて文字を書いたり、絵を作ったり、いろいろ遊べそうだ。

以上。
AWS Control TowerのガードレールとAWS OrganizationsのSCPsの比較

# 比較表
|特徴|ガードレール (AWS Control Tower)|SCP (AWS Organizations)|
|:-|:-|:-|
|目的|AWS 環境でのリソース使用や設定のガバナンスを強化する。|AWSアカウントやOUごとのアクセス制御を管理する。|
|適用対象|AWS Control Tower 管理下のアカウントやOU。|AWS Organizations 管理下のアカウントやOU。|
|種類|予防制御（Preventive）および検出制御（Detective）。|許可または拒否によるサービスアクセスの制御。|
|リソース管理|特定のサービスやリソースの使用制限|サービスの利用権限を制御し、アクセスできるサービスを決定。|
|管理者への通知|検出ガードレールで通知される（例: 設定違反のアラート）。|設定によって適用されるが通知は含まない。|
|適用の方法|AWS Control Towerで自動的にアカウントに適用。|AWS Organizationsでアカウント単位またはOU単位で手動設定。|
|設定方法|SCPのようにJSON形式で直接記述がない。コンソールで選択的に設定する形。|JSON形式で設定できる。|


# ガードレールのユースケース
### リソースの使用制限
特定の EC2インスタンスタイプ（例：バースト可能なインスタンスのみを許可）や、RDSインスタンスタイプ、特定のサービス（例：S3やLambdaなど）の利用を制限することができます。

リソースの無駄遣いや予期しない高コストの発生を防ぐことができます。

### サービス利用制限
開発環境において、特定のサービス（例：CloudFrontやRedshiftなど）の使用を禁止することができます。

開発環境で不要なサービスが使用されるのを防ぎ、コスト管理やセキュリティ管理が容易になります。

### リソースタグ付けの強制
リソースに特定のタグ（例：Environment: Development）が必ず付けられるよう強制できます。

リソース管理が統一され、運用やコスト分析の際にリソースを簡単にトラッキングすることができます。

### インスタンスの起動や変更の制限
特定のリージョンでのみリソースを作成可能にします。

特定の設定（例えば、データベースの暗号化）が必須であることを強制することができます。

開発者がリソースを作成する際に、ガードレールによって設定ミスやポリシー違反が事前に防がれます。

### セキュリティポリシーの強制
セキュリティグループやネットワークACL（アクセスコントロールリスト）の設定を強制することができます。

外部インターネットからアクセス可能なインスタンスを制限したりすることができます。

### 検出と通知（検出ガードレール）
検出ガードレールを使うことで、設定違反やリソースの不適切な利用を検出し、アラートや通知を受け取ることができます。

リソースが想定通りに使われていない場合に早期に対応することができます。

# SCPsのユースケース
### アクセス制御
アカウントがAWSサービスを利用できるかどうか、どのアクションが許可されるかを制御します。

組織の開発アカウントには特定のAWSサービスの利用を制限する、または本番環境のアカウントに対してはIAM権限の変更を制限するなど、サービスの使用を制限します。

サービスごとに設定され、特定のサービスやアクションにアクセスできるかどうかを決定します。


### 「許可」または「拒否」で設定
組織の親アカウント（ルート）で設定されたSCPポリシーは、下位のアカウントに自動的に適用され、ポリシーに従ったサービス利用を強制します。

# ガードレールとSCPを組み合わせて使う
SCPでアクセスを制限し、Control Towerのガードレールでリソースの使い方を制限するという二重の防御が可能です。

**SCP** は主にアクセス制御に使用されるため、組織全体で特定のサービスやリソースにアクセスできないように制限します。
例：開発アカウントに対してSCPで本番環境に使うべきサービスへのアクセスを制限します。

**ガードレール** は、AWS Control Towerのポリシーとしてリソースの作成や使用に対する制限を加えるため、アカウント内でどのようにリソースが使用されるかを管理します。
例：開発アカウントで特定のインスタンスタイプしか使用できないように制限するなど、リソース管理に強い制限を加えることができます。

# 参考サイト
https://www.ctc-g.co.jp/solutions/cloud/column/article/52.html

https://www.ctc-g.co.jp/solutions/cloud/column/article/53.html

https://www.ctc-g.co.jp/solutions/cloud/column/article/65.html

https://dev.classmethod.jp/articles/control-tower-guardrail-deploy/#%25E3%2582%25AC%25E3%2583%25BC%25E3%2583%2589%25E3%2583%25AC%25E3%2583%25BC%25E3%2583%25AB%25E4%25B8%2580%25E8%25A6%25A7
IPアドレス:送信元アドレス、宛先アドレス

# IPアドレスが指すのはホストではなくインタフェース
>IPv4の特徴を定義するのはその`３２ビット`のアドレスである。インターネット上のすべてのホストとルーターはIPアドレスを持っており、IPパケット上で送信元アドレスとあて先アドレス・フィールドの指定に使用される。ここで重要なのは、`IPアドレスはホストではなく、ネットワーク・インタフェース`を指しているということである。
P423

# インタフェースだから複数持つことができる
>このため、あるホストが２つのネットワーク上にある場合、`２つのIPアドレスを持たなければならない`。しかし実際には、`ほとんどのホストは一つのネットワーク上にあり、IPアドレスも一つ`である。一方、`ルーターは複数のインタフェースを持っているため、複数のIPアドレスを持っている`

https://bookplus.nikkei.com/atcl/catalog/23/03/16/00728/
Open WebUIのアップデートを一発で行うスクリプト

Open WebUIでちょこちょこアップデートがくるのですが、GUIから更新できなさそうだったので、スクリプトを作ってみた。

Open WebUIとOllamaがDockerで動作しているのが前提です。以下を実行すると、コンテナ削除からアップデート、Dockerの再起動までやってくれます。以前のプロンプトデータは引き継がれます。

``` bash
docker rm -f open-webui;
docker rm -f ollama;
docker pull ghcr.io/open-webui/open-webui:main;
docker pull ghcr.io/open-webui/open-webui:ollama;
docker volume create --name open-webui;
docker volume create --name ollama;
docker run --rm -v ollama-webui_open-webui:/from -v open-webui:/to alpine ash -c "cd /from ; cp -av . /to";
docker run --rm -v ollama-webui_ollama:/from -v ollama:/to alpine ash -c "cd /from ; cp -av . /to";
docker run -d -p 3000:8080 --add-host=host.docker.internal:host-gateway -v open-webui:/app/backend/data --name open-webui --restart always ghcr.io/open-webui/open-webui:main;
docker run -d -v ollama:/root/.ollama -p 11434:11434 --name ollama ollama/ollama;
```
Linux Mint で Samba

インストール

```
sudo apt-get install samba -y
```
Sanba　パスワード設定

```
sudo smbpasswd -a miyamo
sudo smbpasswd -e miyamo
```

```
ifconfig
```
で確認。
あらかじめ　権限をあたえておく。

```
sudo chmod 777 /media/miyamo/Disk1
```

Config　編集
```
sudo vim /etc/samba/smb.conf
```
中身を以下で変更
```
   interface 192.168.1.0/24 enp4s0

[mint_disk1]
   path = /media/miyamo/Disk1
   available = yes
   read only = no
   browsable = yes
   public = yes
   writable = yes
   quest ok = no
```

 以下を実行
```
sudo systemctl enable smbd.service
sudo systemctl reload smbd.service
sudo systemctl restart smbd.service
```
　あとは　FWの設定
```
sudo ufw enable
sudo ufw allow 445/tcp
sudo ufw status
sudo ufw reload
```
ざっとこんな感じ。
ですが　/media/miyamo/Disk1を開かないと共有できない。
外付けHDDだから？　まあいいか。
オプションフィールド

# オプションフィールド
>将来のバージョンで現在の設計に入っていない情報を持たせたり、新しいアイデアを実験で試したり、まれしか使用されないヘッダー・ビットの割り当てを避けるために設定された。

>IPオプションは使用されなくなってきている。多くのルーターがこれらのオプションを無視するか、あるいは十分に処理しておらず、一般的ではないケースとして脇に避けている。つまり、これらのオプションは一部でのみサポートされ、めったに使われることはない。

## セキュリティオプション
>情報の機密性を示すものである。理論的には、軍事に関係するルーターがこのフィールドを用い、悪い相手であると見なしている国々をパケットが通過しないように定めるものである。

### 実際には使われていない
>実際には、全てのルーターがこのオプションを無視している。唯一の実用的な機能として、スパイが味方のパケットを見つけるのが容易になるかもしれない。

## ストリクト送信元ルーティング・オプション
>送信元から宛先までの完全な経路を通る必要がある。このオプションは、ルーティング・テーブルが壊れた時に`システム管理者が緊急パケットを送る場合やタイミングや性能の計測に有用`である。

## ルーズ送信元ルーティング・オプション
>`パケットが必ず通るべきルーターのリストと順序を特定`する。そのリストに書かれた順にルーターを経由する限り、他のルーターを通過しても良い。

>このオプションは、政治的や経済的な理由から、特定の国々を避けたい場合に有用である。

## ルート記録オプション
>経路上のそれぞれのルーターに対して自身のIPアドレスをオプション・フィールドに追加していくように指示を出すためのものである。これにより`システムの管理者はルーティング・アルゴリズムのバグを見つけ出すことができる`。

## タイムスタンプ・オプション
>ルート記録オプションと似ているが、３２ビットのIPアドレスを記録するのに加え、各ルーターが32ビットのタイムスタンプも記録する点が異なる。

https://bookplus.nikkei.com/atcl/catalog/23/03/16/00728/

# 感想
長々と調べたがめったに使われることはないらしい。
が存在を知ることができてよかった
[React] Styleの設定方法

# 環境
MacBook Pro (2.3 GHz 8コアIntel Core i9)
macOS 14.0（23A344）
Homebrew 4.3.8
gh 2.52.0

# まとめ
- **`React`内にJavaScriptのスタイル用の関数を埋め込む**
- **HTMLにJavaScriptコードを埋め込む際は`{}`を用いる**

~~~diff_jsx:e.g.
export const App = () => {
  const onClickButton = () => alert();
  return (
    <>
+     <h1 style={{color: `red`}}>こんにちは!</h1>
      <p>お元気ですか？</p>
      <button onclick={onClickButton}>ボタン</button>
    </>
  );
};
~~~

# フォルダ構成
~~~:folda_structure
├── public/
│   ├── index.html
└── src/
│   ├── index.js(index.jsx)
│   └── App.js(App.jsx)      
~~~

# ソースコード
~~~jsx:index.js
import { StrictMode } from "react";
import { createRoot } from "react-dom/client";
import { App } from "./App";

const rootElement = document.getElementById("root");
const root = createRoot(rootElement);

root.render(
  <StrictMode>
    <App />
  </StrictMode>
);
~~~
↓関数を外へ出し可読性を上げている
~~~diff_jsx:App.js
export const App = () => {
  const onClickButton = () => alert();
+ const contentStyleA ={
+   color: "red"
+ };
+ const contentStyleB ={
+   color: "blue"
+ };
  return (
    <>
+     <h1 style={contentStyleA}>こんにちは!</h1>
+     <p style={contentStyleB}>お元気ですか？</p>
      <button onclick={onClickButton}>ボタン</button>
    </>
  );
};
~~~

# イメージ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2955010/3b202f0b-cd7b-ddc7-10cb-64ecbb4393f0.png)

# 参考リンク
- [モダンJavaScriptの基礎から始める挫折しないためのReact入門
](https://www.udemy.com/course/modern_javascipt_react_beginner)
Linux Mint で x11vnc

Youtubeのだれかが公開していた手順を以下に記載します。
固定IPの設定は事前に済ましておいてね。

```
sudo apt remove vino 
sudo apt install x11vnc
sudo x11vnc -storepasswd /etc/x11vnc.pass
cd /lib/systemd/system
sudo vim x11vnc.service
```

以下をコピペ　でも　元のやつに　-display :0　を加える。
```
#####Enter this code######
[Unit]
Description=Start x11vnc at startup.
After=multi-user.target

[Service]
Type=simple
ExecStart=/usr/bin/x11vnc -auth guess -forever -display :0 -noxdamage -repeat -rfbauth /etc/x11vnc.pass -rfbport 5900 -shared

[Install]
WantedBy=multi-user.target
##########################
```

おきまりの設定ね。
```
sudo systemctl daemon-reload
sudo systemctl enable x11vnc.service
sudo systemctl start x11vnc.service
```
あとは　FWの設定

```
sudo ufw enable
sudo ufw allow 5900/tcp
sudo ufw status
sudo ufw reload
```
これでつながりました。
Apple vision pro 体験

## はじめに
apple store渋谷店に行きapple vision pro を体験してきました。東京に行く機会があり,体験してみたいと思っていたものだったので行ってきました。
![app.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943852/ef2bcddc-55a3-6702-567a-1325c8e092bb.jpeg)
apple storeの中に入り、店員さんに話しかけると二回に案内されApple vision proの取り扱いに関する説明をしていただき、早速つけてみることに
![unnamed.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943852/54a44dc0-9e61-9c70-124b-d64bba5bb768.jpeg)
## 体験
![appp.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943852/9563aa58-f6f3-c928-8c34-67b0088396b6.jpeg)

つけてみると今までつけてきたVRグラスとは違い、画質、操作感、迫力が段違いに違いました。
ガイドをしてもらいながらいろいろな機能を試しました
### ・基本操作
最初に手の設定をして、それが終わると、指と、目で操作します。自分が見たところを指で操作すると360度どこにでも動かすことができたり、サイトを開いたりすることができます。これを使えば、ダブルモニターのように扱うこともできました。
### ・写真
写真の機能では指で拡大縮小ができるのはもちろん、最新のiphoneで撮ったモノであれば写真を動画のように動かすことができたり、視野全体をその画像にすることができ、とても面白いです。
### ・プレゼン
指でスライドを動かしていくのは普通にパソコンをいじって動かすより簡単でいいと思った。また３Dモデルを作り、それを手で感覚的に動かすことができるのでとても楽で説明することができていいと思った。
### ・動画
最後にappleが作成した動画を視聴しました。
これは視野全体がその動画になるので、3Dに見えたりして迫力もすごく驚かせられました。

## 最後に
apple vision proを体験させていただき、最初はappleが作ったといえどもそこら辺のVRグラスとそんなに変わらないと思っていましたが、体験してみると使用感や、質感が段違いで違っていました。これは皆さん全員が体験すべきものだと思いました。
また体験できる機会があったら積極的に参加したいと思わせてくれるような製品でした。
C言語でタイマーを作る方法

# C言語でタイマーを作る方法

学校で学んでいるC言語で色々なプログラムをつくってきたので、いろいろなデバイスに入っている機能であるタイマーを今回はC言語でつくってみました。

## 1. タイマーとは？
タイマーは、指定した時間が経過するまでのカウントダウンを行うプログラムです。日常的なアプリケーションやゲーム、システム処理の中でよく使用されます。例えば、時間制限のあるクイズやゲーム、リマインダー機能などで使用されることが多いです。

## 2. タイマーを作る理由
私は今までタイマーをプログラムで作ることは、ArduinoとPythonでしか作った時がなかったためC言語で作れるのか気になったからです。
さらに、C言語でタイマーを作成することで、プログラムが時間をどのように扱うか、また時間を制御する方法について理解を深めることができると思ったため作ることにしました。

タイマーを作ることは、単にカウントダウンの機能を提供するだけでなく、以下のような多くの重要なスキルを学ぶことができます.

#### 時間管理: プログラムが時間をどう制御するかを学ぶことができる。
#### リアルタイム処理の理解: 時間が経過する中で、定期的に処理を実行する技術を学べる。
#### 基本的なプログラミング技術: 条件分岐、ループ処理、標準ライブラリの活用などの基本技術の復習ができる。
## 3. タイマーを作る手順
### タイマーを作成する手順は次のとおりです

#### 1.入力の取得: ユーザーが設定する時間（秒単位）を入力として受け取る
#### 2.カウントダウンの開始: 入力された時間から1秒ごとにカウントダウンを実行

#### 3.待機処理: 1秒ごとにカウントダウンするため、待機処理を使う
#### 4.時間経過の表示: 残り時間を毎秒表示し、カウントダウンが終了したら「Time up」と表示
## 4. タイマーのコード例
以下に、C言語でシンプルなタイマーを作成するコードを示します。このコードでは、設定した秒数からカウントダウンし、残り時間を表示します。

#include <stdio.h>
#include <windows.h>

void countdown_timer(int seconds) {

    while (seconds >= 0) {
        printf(" %d seconds\n", seconds);
        Sleep(1000);
        seconds--;
    }
    printf("Time up\n");
}

int main() {

    int time_in_seconds;
    printf("timer:");
    scanf("%d", &time_in_seconds);
    countdown_timer(time_in_seconds);
    return 0;
}

## 5．実行結果
![スクリーンショット 2024-11-25 150156.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943852/beb500b9-9354-99a2-09e2-54080b329dfd.jpeg)
エラーが起こらずにタイマーの機能を動かすことができました。
## 6. まとめ
タイマーを作成することでsleep関数や、カウントダウンを行うことで、時間の管理方法や、リアルタイム処理の理解ができました。

これで、C言語でタイマーを作る方法が理解できたと思います。
これをさらに伸ばすのであれば一分以上のときの表示の機能やストップウォッチのような機能は欲しいとは思いました。しかしアイデアが出てこなくて作成ができなかったのでまた機会があったら調べながら作りたいと思いました。
Grounding-DINO-1.5-APIを試してみた。



https://github.com/IDEA-Research/Grounding-DINO-1.5-API

## 手順
git clone https://github.com/IDEA-Research/Grounding-DINO-1.5-API.git

pip install -v -e .

API Token の取得
https://deepdataspace.com/request_api
に登録してAPI Token を取得する。


python demo/demo.py --token <API_TOKEN>


```:demo/demo.py 
import argparse
import os
from gdino import GroundingDINOAPIWrapper, visualize
from PIL import Image
import numpy as np


def get_args():
    parser = argparse.ArgumentParser(description="Interactive Inference")
    parser.add_argument(
        "--token",
        type=str,
        help="The token for T-Rex2 API. We are now opening free API access to T-Rex2",
    )
    parser.add_argument(
        "--box_threshold", type=float, default=0.3, help="The threshold for box score"
    )
    return parser.parse_args()

if __name__ == "__main__":
    args = get_args()
    gdino = GroundingDINOAPIWrapper(args.token)
    prompts = dict(image='asset/demo.jpg', prompt='person.pigeon.tree')
    results = gdino.inference(prompts)
    # now visualize the results
    image_pil = Image.open(prompts['image'])
    image_pil = visualize(image_pil, results)
    # dump the image to the disk
    image_pil.save('asset/demo_output.jpg')
```

asset/demo.jpg　の画像から、person pigeon tree を検出する。



![demo_output.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/83761/3388cc38-cc27-2c5b-fea7-bf8f911b0b59.jpeg)

実行結果
AWS Certified AI Practitioner（AIF）対策：Amazon Q Business

# Amazon Q Business

Amazon Q Businessは、

***<font color="MediumVioletRed">『自然言語処理（NLP）を用いたバーチャルアシスタントであり、生成 AI を組織内の誰もが安全にアクセスできる』</font>***

ようにします。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2358573/1c8df7ba-f8bb-7f4b-04a1-29cfc453e0d1.png" width="700">


## 企業貢献

企業のシステム内のデータに基づいて

- **<font color="MediumBlue">質問への回答</font>**
- **<font color="MediumBlue">要約の提供</font>**
- **<font color="MediumBlue">コンテンツの生成</font>**
- **<font color="MediumBlue">タスクの実行</font>**

を行います。

これにより、従業員は、より創造的・効率的・生産性を高めることができます。


## 制約

Q Businessが生成AIを使用して文書を作成する際に考慮すべき制約は、覚えておく必要があります。


- バイアスや不正確な情報を生成する可能性がある
- 人間による監視が必要である
Casio Graph Math+ を購入した

## 購入動機
かつて hp電卓 にはまった時期もあったが、最近は関数電卓と無縁な生活を送っていた。
ところが、とあるツイートを見たのがきっかけで関数電卓熱が再燃。この数か月で10台超の関数電卓を購入するに至り、さらにグラフ電卓の購入も考えるように。
いったんは fx-9750GIII を 米Amazon で注文するもなかなか発送されないのでキャンセル。
その後も fx-9750GIII や fx-CG50 の価格を 米Amazon でチェックしていたが、たまたま Reddit で、フランス市場向けの今年の新製品 Graph Math+ が 独Amazon で安く販売されていると知って購入に至った。

## カートに入れたらなぜかさらに安くなった
独Amazon の商品ページに表示された価格は53.68ユーロだった。
送料が15.59ユーロなので合計69.27ユーロ（約11500円）。
![241201_1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943774/6b918ba1-7dd6-262b-3724-9acecc5b3e86.png)
カートに入れて購入プロセスに進むと…なぜか送料込みで60.7ユーロになっている（！！）
![241201_2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943774/b1a8cb0a-16b2-72f0-f471-9d2e98d2451e.png)
この値段なら間違いなく買いでしょ？ということで、決済まで進めた。結果的に商品価格は45.11ユーロとなった。
![241201_3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943774/7d7b84ce-99c9-5812-071c-45f4634921f8.png)
合計金額の決済が Amazon の円建てだと1万円をちょっと超える位だったので、Visa Exchange Rate Calculator とにらめっこして IDARE でユーロ建て決済（IDARE だとVISA レートそのままで手数料がかからず決済される）。支払金額は9958円となった。

注文したその日のうちに発送完了していた。ECMS Express。果たしていつ届くでしょうか。
![241201_4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943774/92ec2638-ff84-60d2-b528-4b8c12e11c43.png)

## 買うべきか否か

**（追記2024/11/27時点：上記の独Amazon の Graph Math+ は商品ページ価格48.31ユーロ、カート価格40.60ユーロ+送料15.59ユーロ=56.19ユーロ（約9100円）に値下がり。**

現行機種で比較対象となるのは fx-CG50 だと思うが、米Amazonで83ドル+送料13.18ドル（2024/11/25時点）。日本円だと約15000円。

機能は Graph Math+ の方が少ないので、fx-CG50 にしかない機能が必要であれば少し高くても fx-CG50 を買うのがよいだろう。
また、来年 fx-CG100 の発売が予定されているので、それを待つ手もある。fx-CG100 は fx-CG50 とほぼ同等の機能の搭載が予定されており、Graph Math+ より高くなることが予想されている。
Graph Math+ はここ数か月で急激に値下がりしたが、来年ソフトウェアアップデートが予定されており、価格も今後どうなるかはわからない。
![241201_5.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943774/5229d71f-4000-45c1-a95f-c402798bb587.png)

最近グラフ電卓の Python 記事がポツポツと出てきたので、グラフ電卓に興味を持った人もいるだろう。 fx-CG50 も Graph Math+ も搭載されている MicroPython に違いはないようなので、安価にグラフ電卓の Python を体験してみたい人にはこの値段なら買いと言えるのではないか（記事公開時には値上がりしているかも）。

ちなみに、某ブログにこの価格のコメントをしたら、続々と購入報告が上がっていた。 米Amazon はチェックしていても、 独Amazon にはなかなか目が向かないのかもしれない。

## 到着した
その後、12月1日に成田着、通関を経て、12月3日に日本郵便によって配達された。
![241201_6.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3943774/24da0a90-7629-6d35-5a1e-58f3fff9e526.png)

[Casio Graph Math+ を使ってみる](https://qiita.com/harycurl/items/1f318c2b4b76872c6a1c) に続く。
ジョブカンに登録しているフォームの一覧を取得

**使っているクラウドなどの小ネタ Advent Calendar 2024 11日目**

登録しているフォームの一覧が欲しいのですがcsvなどにエクスポートできなさそうですね。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/1b55c99f-ee13-ff8f-0870-dcb9bfdd9918.png)


仕方ないのでpostmanから呼び出してみます。

Json形式で取得できることはできました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/825cf100-a27e-b6b8-4142-a0d20460a3d3.png)

このJsonを整形してテーブル形式にしてみます。

以下のようなスクリプトを設定します

```
var template = `
  <style>
    .myTable {
      background-color : #dddbda;
    }
    .myTable th{
      width: 150px;
    }
    .myTable td{
      width: 150px;
    }
  </style>
  <table class="myTable">
      <tr>
          <th>Name</th>
          <th>Description</th>
      </tr>

      {{#each response.results}}
          <tr>
              <td>{{name}}</td>
              <td>{{description}}</td>
          </tr>
      {{/each}}
  </table>
`;

function constructVisualizerPayload() {
    var res = pm.response.json();
    var expectedSortedOrder = res.results.sort((a, b) => (a.name > b.name) ? 1 : -1);
    return { response: { results: expectedSortedOrder } };
}

pm.visualizer.set(template, constructVisualizerPayload());
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/b1d149c2-97e3-bffb-e7f4-2cd32d4baee7.png)

テーブル形式に成形できました。これをコピペしてデータとします

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/b1dcc15a-e436-ae62-7af7-adfdc405535c.png)

後で気づきました。ファイルにできますね。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328136/250e45bd-bcf1-d6f3-844d-1a1799d29c74.png)
分報から始める「やさしい育成」のお話

## 1. 育成ってどんなもの？

「育成」という言葉には、いろいろな意味や目的が詰まっています。
例えば…
* 「自分がしてもらったことを次の世代に返したい」
* 「仕事だから仕方ない」
* 「後輩がかわいいから」
* 「新しい世代を活躍させたい」
* 「自分も新人時代は失敗だらけだったから」

どれも立派な理由です。

でも、実際の現場での育成はそう簡単ではありません。
今回お話しするのは、インターン生としてリリース前から参画した彼が新入社員となり、一緒にリリースを走り抜けた話。
このエピソードを通して「育成とは？」を一緒に考えてみませんか？

## 2. OJT（という名の現場デビュー）

「OJT」という言葉、聞いたことありますか？
On-the-Job Training、つまり現場で実際の業務を通じてスキルを身につける方法です。理想的には、先輩が丁寧に教えつつ実践をサポートする仕組み。

ですが、現実は「お任せします！」と渡されることもしばしば…。

今回の舞台は、4人のシニアエンジニアがリリースに向けてやや忙し目の現場。
そこに飛び込んできたのは、今年入社した当時インターン生でした。

他の現場でも同じようなケースがあり、心あたりがあると思います。
「なぜ？」
当然、インターン生からだったので最初から戦力として期待されていたわけではありません。

この何故を噛み砕くすることが大事かなと思っております☝️
今回は、将来の戦力の育成期間と捉え完全にプロジェクトの進捗と分けて彼の成長を考えました。

社会人がもつ一定の厳しさを体験するというよりかは、
現場に慣れてもらうことや、現場に入るための新しい技術のキャッチアップに稼働時間を割り振っていました。技術やドメイン知識の習得によっていたと思います。

## 3. 学生から社会人へ、一歩ずつ

インターン当時から彼は技術的な知識やスキルの基礎がある状態でした。
具体、フロントエンド（Nest.js/TypeScript/HTML/CSS）の知識や、
各開発ツールを抵抗感なく使用ができるなどです。

でも、社会人として必要な「報告・連絡・相談（ホウレンソウ）」はまだ不慣れでした。

例えば、仕事の進捗を伝えるタイミングが遅れたり、内容が簡略化されすぎていたり。現場では「些細なこと」もチーム全体に影響を与えるため、早めの共有や内容が重要と。

信頼を積み上げていこうという話を常々していました。

入社しては課題を見つけては、改善できるようになるまでいろんな手法を試しました。

* 日々の1on1での報・連・相談の練習
* 見積と実際にかかった実績でのギャップの振り返り
* スコアをつけて成長度合いの可視化
* （会社の制度で）ななメンター
* 分報

など試しました。

## 4. 報告を習慣に：やさしい分報チャレンジ

「報告ができれば自然と仕事もスムーズになるはず！」と考えた私は、会社で導入されている「分報」という仕組みを取り入れました。

分報とは？

作業ごとに簡単な報告を行うルールです。最初は1時間ごと、慣れたら作業単位で柔軟に

最初のうちは「報告を忘れがち」なことも多かったので、丁寧に確認しながら進めました。報告の内容をどう書けばよいか、他の社員の例を見せつつ、少しずつ改善していきました。

<b>うまく報告できれば、報告時間を伸ばし、</b>
<b>うまく報告ができなければ、報告時間を短くする。</b>

結果的に、約1週間で「報告すること」が自然にできるように！ もちろん、一朝一夕ではいきませんでしたが、彼の成長を間近で感じることができました。

それまでの課程でいろんな方法を試したのですが、
彼の場合は最終的に毎分報告をするのが一番効いたかなと思います。

それは、ノルマ型が合ったという話で、
展示会で30人に声をかけて、資料を説明しましょう と伝えると達成できます

逆に展示会で誰かに声かけて というとあんまりできなかったと思います

みたいな感じです。

<b>過度なプレッシャーはよくなくて、本人にあった刺激を見つけてあげてそれを与え続けてたまに褒めるみたいなのがよかったのかなと。</b>

## 5. 育成の本質ってなんだろう？

OJTを通して考えたこととして、育成は、ただ技術を教えるだけではありません。大切なのは、<b>正しい習慣や考え方を身につけるお手伝いをすること。</b>

今回の場合、報告を通じて「進捗を共有し、次の行動に活かす」を繰り返し成長を促すを目指しました。この経験から、以下のことを学びました。

* OJTはただの丸投げではなく、<b>現場での即席プログラム</b>として設計することが大切。
* 基本的な習慣を徹底することで、短期間でも成長は可能。
* 一緒に向き合う覚悟があれば、育成はきっと成功する。

## 6. ぶつかり合いがあっても、その先へ

育成の過程でぶつかることもありました。報告を求めるときに私がイライラしてしまったり、彼がプレッシャーを感じてしまったり、現場のレビュワーが1PRに対して100コメントになって、コメントしたけど次のPRで同じ指摘をもらい雰囲気がピリつくことも…。

それでも、周りの同僚の支えや、彼自身の粘り強さのおかげで乗り越えることができました。報告が習慣化すると、ふとした会話で笑い話になることも増え、自然と距離が縮まっていきました。

## 最後に：育成って楽しいかも？

育成は大変なこともあります。
でも、信頼関係が生まれたときの喜びは、それ以上の価値があります。

「育成とはなんだろう？」という問いに対する私の答えはこうです。
「<b>相手の強みも弱みも一緒に受け入れ、一緒に成長するプロセス</b>」。

皆さんも、ぜひ育成の場で新しい発見を楽しんでみてください！
xacroからurdfに変換する

# 概要
- xacroからurdfに変換する手順
- ROS2を使います

# 環境構築
- Virtual BoxでUbuntuを立てるなどする
- Ubuntu24.04の調子が悪かったので、今回はUbuntu20.04を使用
    - https://releases.ubuntu.com/20.04/
# ROS2インストール
- ディストリビューション：foxy
    - https://docs.ros.org/en/foxy/Installation/Ubuntu-Install-Debians.html

# ワークスペース設定
- ワークスペースを作成
`mkdir -p ~/ros2_ws/src`
`cd ~/ros2_ws/src`

- パッケージをクローン
- 例として、AUBO Roboticsのリポジトリを使用する
`git clone https://github.com/AuboRobot/aubo_description.git`

- 依存関係をインストール
`cd ~/ros2_ws`
`rosdep update`
`rosdep install --from-paths src --ignore-src -r -y`

- ビルド
`colcon build`
- ワークスペースをソースとして環境を設定
    - これは毎回行う（別のターミナルを使う、再起動するたび）
`source ~/ros2_ws/install/setup.bash`

# xacroインストール
- ディストリビューションがfoxyのため、ros-foxy-xacroをインストール
`sudo apt-get update`
`sudo apt-get install ros-foxy-xacro`

- not foundが出なければ完了
`xacro --help`

# xacro→urdf
- ros_ws/に作成される
`xacro ~/ros2_ws/src/aubo_description/urdf/xacro/aubo_i5.xacro > test_aubo_i5.urdf`

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/436651/aa250a8a-dcb7-c12c-a34c-64607e95c1a2.png)


## 引数ありの場合
- xacroに引数がある場合はurdf.xacroの後に引数を入れる
    - 引数がnameの場合、`urdf.xacro name:=ur5e`
- 例：UniversalRobot
`xacro ~/ros2_ws/src/ur_description/urdf/ur.urdf.xacro name:=ur5e > test_ur5e.urdf`
    - xacro.load_yamlエラーの対処
        - https://www.kwesirutledge.info/thoughts/ur_urdfs
EC2 Instance Connect とAWS Systems Manager Session Manager の比較

# 比較表
|特徴|EC2 Instance Connect|AWS Systems Manager Session Manager|
|:-|:-|:-|
|接続方法|SSH プロトコルを使用|SSM プロトコルを使用（SSH 不要）|
|操作対象|EC2 インスタンス（サポートされる OS に限定）|EC2 インスタンス、オンプレミスサーバー|
|アクセス制御|IAM ポリシーで SendSSHPublicKey アクションを許可|IAM ポリシーで SSM アクション（例: StartSession）を許可|
|監査とログ|接続ログのみが AWS CloudTrail に記録される|CloudTrailやCloudWatchで監査可能、セッション操作ログも保存可能|
|SSH キーの利用|一時的な公開鍵を使用、従来のSSHキー（ペア）の管理が不要|SSH キー不要|
|OS のサポート|Amazon Linux、Ubuntu の一部バージョン、Windows対応不可|SSM エージェント対応 OS（ほぼすべての主要 OS）|
|ポート要件|SSH ポート (22) が必要|ポート不要（アウトバウンド通信のみ）|
|接続手段|AWS コンソールのブラウザベースの SSH クライアント|AWS コンソール、CLI、SDK 経由|
|追加ソフトウェア|不要（SSHが稼働していればOK）|SSM Agentが必要|
|その他の機能|シンプルな一時的アクセス|ファイル転送、ポートフォワーディング、セッション分離|

# EC2 Instance Connectのユースケース
・一時的短期的なSSHアクセスを提供したい場合。
・管理者が特定のLinuxインスタンスにトラブルシューティングのためにアクセスしたい場合。
・SSHキーの管理を最小限に抑えたいシナリオ。

# AWS Systems Manager Session Manager
・長期的かつ安全にインスタンスを管理したい場合。
・Windowsインスタンスへの接続が必要な場合。
・セキュリティを重視し、SSHキーやネットワークアクセスを回避したいシナリオ。
・複雑な操作、包括的な監査が必要な場合。
・プライベートサブネットや厳密に制限された環境で作業する場合。
・SSH ポートを完全に閉じたい場合。

# 参考サイト
https://dev.classmethod.jp/articles/compare-eic-endpoint-and-session-manager/#toc-6
AWSで作成したインスタンスにSSHできない。。


■目的
　自分自身の備忘録のため。
　自分と同様にSSH接続できない状況の方への共有。

■結論
　AmazonLinux2023のインスタンスを作成し、TeraTermにてキーペアを使いSSH接続する際には、サポートされている公開鍵暗号方式の種類に注意すること。
 
以下URLの情報を参考にさせていただきました。
大変助かりました。ありがとうございます。

https://sal-blog.com/%E3%80%90%E8%B6%85%E5%88%9D%E5%BF%83%E8%80%85%E5%90%91%E3%81%91%E3%80%91aws-ec2%E4%BD%9C%E6%88%90%E3%81%A8teraterm%E3%81%A7%E3%81%AEssh%E6%8E%A5%E7%B6%9A%E6%96%B9%E6%B3%95/#index_id5

■実施内容　
　Amazon Linux2023でインスタンスとキーペアを作成して、SSHしようとしてるのになかなかログインできなかった。アタッチしているセキュリティグループやVPCのルートテーブルも問題なかったのに。。という感じでハマってしまった。
 　んで原因特定するために色々調べたところ、前述の記事を基にTeratarm5をインストールして再度接続したら無事にログイン出来た。

■おわりに
　暗号化方式についてはまだまだ勉強不足なので、もうちょっと知識を深めたい！
　（その前にAWSの技術スキルや知識の方が先なのだが。。）
Flask入門：Pythonで手軽にWebアプリを作成できる

自身の経験のアウトプットの場として投稿しています！もし認識が間違っていた場合、DMやコメントなどで教えていただけると嬉しいです！

![images.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3848466/fcd76e55-8cb1-4cb7-b41b-74ac79520983.png)

# はじめに
PythonでWebアプリを作りたいけど、どう始めればいいかわからない。
**おすすめ**→軽量でシンプルなWebフレームワーク **Flask**(フラスク) の使用をおすすめします。

この記事では、**Flask**の魅力や基本的な使い方を解説し、簡単なWebアプリケーションを作成してみます。
初めて**Flask**を触る方でも、この記事を読めばPythonで最低限のWebアプリを作れるようになるかと思います！

# Flaskの魅力とは？
**1.軽量でシンプル**
**Flask**は「マイクロフレームワーク」と呼ばれ、必要最低限の機能だけを提供します。そのため、自由度が高く、無駄な学習コストを抑えられるのが特徴です。

**2.拡張性が高い**
必要に応じて機能を追加できる設計になっています。例えば、データベース接続や認証機能などを後から追加することが可能です。

**3.豊富なコミュニティとドキュメント**
**Flask**はPythonコミュニティで非常に人気！なので公式ドキュメントやブログ記事、Q&Aサイトなどの情報が豊富です。

# 簡単なWebアプリを作ってみよう
以下のコードで、基本的なWebアプリを作成してみます。

**必要な準備**
**Flask**をインストールします（Pythonがインストールされている前提です）。
```
pip install flask
```
**コード例**

以下のコードを **app.py** という名前で保存します。

```
from flask import Flask

app = Flask(__name__)

@app.route('/')
def home():
    return "Hello, Flask!"

if __name__ == '__main__':
    app.run(debug=True)
```

**実行方法**
```
python app.py
```

ブラウザで http://127.0.0.1:5000/ にアクセスすると、「Hello, Flask!」と表示されるはずです。
# プチ応用例

便利な**Flask**ではこんなこともできる！

・フォームを使った入力と出力
・REST APIの構築
・ユーザー認証機能の実装
・データベースとの連携

例えば、次のコードでフォームデータを受け取る簡単なアプリを作ることができます：
```
from flask import Flask, request, render_template

app = Flask(__name__)

@app.route('/', methods=['GET', 'POST'])
def index():
    if request.method == 'POST':
        name = request.form['name']
        return f"こんにちは、{name}さん！"
    return '''
        <form method="post">
            名前: <input type="text" name="name">
            <input type="submit">
        </form>
    '''

if __name__ == '__main__':
    app.run(debug=True)
```

# まとめ

**Flask**は、とてもシンプルで拡張性が高いことから、PythonでWebアプリを始めたい人に最適なフレームワークです。この記事で紹介したコードをぜひ試してみて、基本的な仕組みを理解してみてください！

また、**Django**との違いについては、私自身が深く理解を深めた上で、別の記事で詳しく解説したいと思います！

私の投稿が少しでも困っている方の役に立てば嬉しいです。コメントやフィードバックもお待ちしています！
CDKTFのconfig-driven importでAWSリソースのIaC化

## はじめに
IaCでコード管理がされていなかった既存のAWSリソースを[CDK for Terraform（CDKTF）](https://developer.hashicorp.com/terraform/cdktf)で管理できるよう、import作業を行った際のメモです。

## config-driven import

`config-driven import` のサポートにより、AWSリソースのID等を指定するだけでリソースをterraformの管理下に置くことができるようになりました。

https://www.hashicorp.com/blog/cdktf-0-19-adds-support-for-config-driven-import-and-refactoring

実際のコードをTypescriptを例に見ていきます。

`generateConfigForImport` メソッドを使うことで、`cdktf plan` 実行時にCDKTFのコードを生成することができます。ただし恐らくこの記事を執筆時にはまだ実験段階の機能だったようで、上手く生成できないことが何度かありました（その場合は `importFrom` でリソースを指定した後に `cdktf plan` でdiffを表示し、自分でコードに落とし込んでいきました）。

```ts
// xxxxx に実際のbucket名が入ります
S3Bucket.generateConfigForImport(this, "example_bucket", "xxxxx");
```

`cdktf plan` するとコンソールのログに以下のコードが含まれるのでコピー。
```ts
new S3Bucket(this, "example_bucket", {
  bucket: "xxxxx",
  bucket_prefix: [null],
  force_destroy: [null],
  object_lock_enabled: false,
  tags: {},
  tags_all: [{}],
});
```

ソースコードを以下のように修正。
```ts
import { Construct } from "constructs";
import { App, TerraformStack } from "cdktf";
import { AwsProvider } from "@cdktf/provider-aws/lib/provider";
import { S3Bucket } from "@cdktf/provider-aws/lib/s3-bucket";

class MyStack extends TerraformStack {
  constructor(scope: Construct, id: string) {
    super(scope, id);
    new AwsProvider(this, "AWS", {
      region: "ap-northeast-1",
    });

    new S3Bucket(this, "example_bucket", {
      bucket: "xxxxx",
      objectLockEnabled: false,
    }).importFrom("xxxxx");
  }
}

const app = new App();
new MyStack(app, "config-driven-import");
app.synth();
```

`cdktf plan` を実行すると以下のように出力されるので、問題なければ `cdktf apply` を実行しapprove。
```bash
aws_s3_bucket.example_bucket (example_bucket) will be imported
# importのdiffがズラズラと出る

Plan: 1 to import, 0 to add, 0 to change, 0 to destroy.
```

`importFrom` をソースコードから消して `cdktf plan`。以下のようにメッセージが出ればimportは完了。

```bash
No changes. Your infrastructure matches the configuration. 
```

もし複数環境で同様の作業が発生する場合は、分かりやすい形で `importFrom` をコメントアウトしておくと後で作業が楽になります。
```ts
...
// this.apiGatewayMethod.importFrom('Add REST-API-ID/RESOURCE-ID/HTTP-METHOD');
```
 
## CDKTFによるIaC化までの流れ

AWSリソースの状態をCDKTFのコード落とし込み、tfstateに反映させるまで、各環境ごとに大体以下の流れで進めました。

1. `generateConfigForImport` でコードを出力
1. 必要に応じて `generateConfigForImport` で出力されたコードを修正
1. `importFrom` を追加し `cdktf plan`、問題なければローカル開発環境から `cdktf apply`
1. AWSコンソールからリソースの状態を確認
1. 念の為アプリケーションの挙動に問題ないか動作確認
1. 対象の環境において一通りのAWSリソースのCDKTFへの取り込みが完了したらgithub actionsのworkflowを作成し、自動デプロイ等ができるようにする

つまずいた際にお世話になったのが
- [cdktf-provider-awsのドキュメント](https://github.com/cdktf/cdktf-provider-aws/tree/main/docs)（困ったら対象のリソースのreadmeを見つけるのが恐らく早い）
- [CDKTFのドキュメント](https://developer.hashicorp.com/terraform/cdktf)（特に概念だったり、ツールだったり記法的なところ）
- （もし周りにいれば）CDKTF詳しい方に聞く

## まとめ
複数環境でこちらのIaC化作業を行いました。何度かつまずくことがあり思ったより時間がかかりましたが、最初の環境が終わった頃にはある程度慣れていたので、他環境は割とスムーズに進んだ印象です。
blastengineのメールエラーWebhookをExpress + TypeScriptで処理する

[blastengine](https://blastengine.jp/)はエンジニアフレンドリーなメール送信サービスになります。APIまたはSMTPを使って、簡単にメール送信を行えます。

blastengineではエラーメールに対するWebhook通知をサポートしています。この記事では、その扱い方とデータについてTypeScript + Expressによる処理を通じて解説します。

## 設定

Webhook設定はblastengineの管理画面で行います。設定の中にあるWebhookをクリックします。

![001.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/197026/059adabd-6159-2cd4-12d3-9d98c075b1c2.jpeg)

設定は主に2つです。

- エンドポイントURL
Webhookを受け取るURLです
- 通知イベント
Webhookを受け取るイベントです

エンドポイントURLにはPOSTメソッドで呼ばれます。Content-Typeはapplication/jsonになります。通知イベントは以下の3つが用意されています。

- ドロップ
エラー停止リスト内にあるメールアドレス宛に送信しようとした場合のエラーです
- ハードエラー
ホストがない、ユーザーがいないといった恒久的なエラーです
- ソフトエラー
メールボックスがいっぱいなど一時的なエラーです

## 注意点

2024年11月現在、Webhookはトランザクションメール（即時配信メール）に対してのみ有効です。バルクメール（一括配信）は未対応です。

## データを受け取ってみる

では実際にデータを受け取ってみます。今回はTypeScriptで以下のようなコードを書きました。

```typescript
import express, { Application, Request, Response } from 'express';

const app: Application = express();
const PORT = 3000;

// JSONボディのパースを有効化
app.use(express.json());

interface MessageEvent {
	type: string;
	datetime: string;
	detail: {
		mailaddress: string;
		subject: string;
		error_code: string;
		error_message: string;
		delivery_id: number;
	};
}

interface Message {
  events: {
		event: MessageEvent
	}[];
}

// POST / エンドポイントの定義
app.post('/', (req: Request<{}, {}, Message>, res: Response) => {
  // リクエストボディからデータを取得
  const { events } = req.body;
  // 受け取ったデータをコンソールに出力
  console.log('エラーの種別:', events[0].event.type);
  res.json(events[0].event);
});

// サーバーの起動
app.listen(PORT, () => {
  console.log(`サーバーがポート${PORT}で起動しました。`);
});
```

以下はドロップの例です。 `error_message` にエラー内容が入ります。

```json
{
	"events": [
		{
			"event": {
				"type": "DROP",
				"datetime": "2023-01-26T16:17:54+09:00",
				"detail": {
					"mailaddress": "user@drop.example.com",
					"subject": "Test subject",
					"error_code": "554(errors)",
					"error_message": "エラー停止リストに含まれる宛先であるため、配信がドロップされました",
					"delivery_id": 1128
				}
			}
		}
	]
}
```

以下はハードエラーの場合です。ホストがない、ユーザーが存在しないなど恒久的に発生する場合のエラーです。

```json
{
	"events": [
		{
			"event": {
				"type": "HARDERROR",
				"datetime": "2023-01-26T16:22:43+09:00",
				"detail": {
					"mailaddress": "user@harderror.example.com",
					"subject": "Test subject",
					"error_code": "550",
					"error_message": "宛先のメールアドレスがありません",
					"delivery_id": 1129
				}
			}
		}
	]
}
```

## まとめ

データが受け取れれば、後はSlackへ通知したり、データベースと連携するなどが容易になります。配信先リストを自動クリーニングするのにも使えるでしょう。

一例としてZapier経由でSlackへ通知するデモを[blastengineのwebhook機能でメール送信が失敗したらzapier経由でSlackに通知できるようにした。 - Qiita](https://qiita.com/hirosatooooo/items/21573f79fbb8599090d1)にて紹介しています。ご覧ください。

[エンジニア向けメール配信システム「ブラストエンジン（blastengine）」](https://blastengine.jp/)
Vent Speak Magazine

Vent Speak Magazine, also known as Vents Peak, is an online platform dedicated to providing insightful perspectives across a wide range of topics. It features content in categories like technology, business, entertainment, lifestyle, travel, and fashion. With a mission to connect human experiences with technological innovation, Vent Speak strives to create an accessible and engaging space for readers. Its focus extends beyond information delivery, emphasizing creativity, collaboration, and empathy in content creation.

https://ventspeakmagazine.com/
【Ruby】コードを通して再帰呼び出しを学ぶ

# はじめに
こんにちは！アメリカの大学で語学を学びながら、独学でソフトウェアエンジニアを目指している者です。
本日は再帰呼び出しについて記事にしていこうと思います。

たのしいRubyで勉強している際に自分自身を呼び出すという仕組みである再帰呼び出しを知りました。
「再帰呼び出し」とは、自分自身を呼び出すメソッドのことです。
この仕組みを使うことで、ディレクトリの探索や木構造の処理といった、複雑な問題をシンプルに解くことができます。  
この記事では、再帰呼び出しの基本から具体例まで解説していきます。

# 再帰呼び出しとは
再帰呼び出しとは、メソッドが自分自身を呼び出す仕組みのことです。この仕組みを用いると、問題を小さな部分に分解しながら解決できます。再帰には次の2つの要素が必要です。  

1. 再帰条件
再帰を進めるための条件（問題を分割して解決する）。
2. 終了条件
処理を終了するための条件（解を求める終点）。  

この仕組みは、例えばディレクトリの探索や木構造の処理といった場面で特に有効です。

##　再帰呼び出しの具体例
以下のコードは、楽しいRubyから参照しました。
このコードは、あるディレクトリ構造を再帰的に探索してファイル名を表示する例です。

```Ruby
def traverse(path)
  if File.directory?(path)
    dir = Dir.open(path)
    while name = dir.read
      next if name == "." || name == ".." # カレントディレクトリと親ディレクトリをスキップ
      traverse(path + "/" + name) # 再帰呼び出し
    end
    dir.close
  else
    process_file(path) # ファイルを処理
  end
end

def process_file(path)
  puts path # ファイルパスを出力
end

traverse(ARGV[0]) # コマンドライン引数で渡されたパスを探索
```

1. ディレクトリとファイルの判定
```ruby
if File.directory?(path)
```
`File.directory?(path)` は、現在のパスがディレクトリかどうかを判定します。

* ディレクトリの場合
中のエントリを探索するため、Dir.open を使用。
* ファイルの場合
再帰呼び出しを行わずに process_file を実行します。

2. 再帰呼び出しの進行
```ruby
while name = dir.read
  next if name == "." || name == ".." # 特殊エントリをスキップ
  traverse(path + "/" + name) # 再帰呼び出し
end
```
ここでは、ディレクトリ内のすべてのエントリを1つずつ読み取ります。
ただし、`next if name`を使用することで`"."`（カレントディレクトリ）や` ".."`（親ディレクトリ）をスキップし、無限ループを防ぎます。
ファイルやサブディレクトリに応じて再帰を進めます。

3. 終了条件
このコードでは、終了条件が以下の形で実現されています：

ディレクトリをすべて読み終えると、`dir.read` が `nil` を返し、`while` ループが終了します。
ファイルに到達した場合、再帰は発生せず処理が終了します
```ruby
process_file(path)
```
4. 再帰の例
例えば、次のディレクトリ構造を上記のコードをもちいて探索するとしましょう
```ruby
root/
├── file1.txt
├── dir1/
│   ├── file2.txt
│   └── dir2/
│       └── file3.txt
└── file4.txt
```

1. 最初の呼び出し
`traverse("root") `が呼ばれます。
ファイルである`"file1.txt"` を処理して出力し、`"dir1"` に入ります（再帰呼び出し）。
2. 再帰の進行
上記の再帰呼び出しによって、`traverse("root/dir1")` が呼ばれます。
ファイルである`"file2.txt"` を処理して出力し、`"dir2"` に入ります（再帰呼び出し）。
3. 終了条件の到達
上記同様に`traverse("root/dir1/dir2")` が呼ばれます。
ファイルである`"file3.txt"` を処理して出力し、ディレクトリのエントリをすべて読み終えたので再帰から戻ります。
4. 処理の戻り
再帰が終了すると、再び `"root"` に戻り、残りのエントリ`（"file4.txt")` を処理します。

## 再帰呼び出しを使用する上での注意点
再帰呼び出しを使う際には、次のポイントに注意しましょう。

* 終了条件を明確にする
終了条件がないと無限ループになり、プログラムが停止しなくなります。このコードでは、特殊エントリ `"."` や `".."` をスキップし、無限ループを防いでいます。

* スタックオーバーフローに注意
再帰の深さが深くなるとメモリを大量に消費し、スタックオーバーフローが発生する可能性があります。非再帰的な方法も検討してください。

* 再帰が適切なケースで使われているか確認
再帰はディレクトリ探索や木構造の処理には適していますが、処理が深すぎたり効率が悪くなる場合はループを使用する方法を検討しましょう。

# まとめ
再帰呼び出しは、自分自身を呼び出すメソッドを活用することで、複雑な処理を簡潔に記述するテクニックです。
このコードでは、ディレクトリ構造を再帰的に探索する仕組みを学びました。
また勉強中で学んだことがあれば積極的にシェアしていきたいと思います。
Advent of code 2015 Day 10 Part 1 & Part 2 を Livebook で楽しむ

## はじめに

Advent of code 2024 の準備として、過去回の Advent of code 2015 を Livebook で楽しみます

本記事では Day 10 の Part 1 と Part 2 を解きます

問題文はこちら

https://adventofcode.com/2015/day/10

実装したノートブックはこちら

https://github.com/RyoWakabayashi/elixir-learning/blob/main/livebooks/aoc/2015/2015_day10_part1.livemd

https://github.com/RyoWakabayashi/elixir-learning/blob/main/livebooks/aoc/2015/2015_day10_part2.livemd

## セットアップ

Kino AOC をインストールします

```elixir
Mix.install([
  {:kino_aoc, "~> 0.1"}
])
```

Kino AOC の使い方はこちらを参照

https://qiita.com/RyoWakabayashi/items/3d3abcf9134cee4dff05

## 入力の取得

"Advent of Code Helper" スマートセルを追加し、 Day 10 の入力を取得します

![スクリーンショット 2024-11-25 13.51.46.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1485835/9deb3646-234b-b699-d667-b93631f99d8e.png)

## 私の答え

私の答えです。
折りたたんでおきます。
▶を押して開いてください。

### Part 1

<details><summary>回答</summary>

正規表現 `(.)\1*` は1文字以上の繰り返しに該当します

`Regex.scan` により、これに該当するものを全て取得します

例えば `"111221"` を入力として、以下のように処理します

```elixir
Regex.scan(~r/(.)\1*/, "111221")
```

実行結果は以下のようになります

```elixir
[["111", "1"], ["22", "2"], ["1", "1"]]
```

各繰り返しについて、最も長い該当箇所と、最も短い該当箇所が返ってきます

`[max, min]` で取得される各繰り返しについて、 `max` の長さを繰り返し回数、 `min` を繰り返されている文字として扱えば問題を解くことができます

問題を解くための関数を定義します

```elixir
get_char_group_list = fn input ->
  Regex.scan(~r/(.)\1*/, input)
  |> Enum.map(fn [max, min] ->
    "#{String.length(max)}#{min}"
  end)
  |> Enum.join()
end
```

試しに `"111221"` を入力として実行してみます

```elixir
get_char_group_list.("111221")
```

結果は以下のように正しく返ってきます

```elixir
"312211"
```

あとはこれを 40 回繰り返し、文字列長を取得するだけです

```elixir
1..40
|> Enum.reduce(puzzle_input, fn _, acc_input ->
  get_char_group_list.(acc_input)
end)
|> String.length()
```

</details>

### Part 2

<details><summary>回答</summary>

Part 2 は、まさかの繰り返し回数を増やすだけでした

```elixir
1..50
|> Enum.reduce(puzzle_input, fn _, acc_input ->
  get_char_group_list.(acc_input)
end)
|> String.length()
```

</details>

## まとめ

実は当初は文字列の繰り返しを律儀に数える実装をしていたのですが、一旦解けた後に別の解法を考えつきました

入力のパース処理はできるだけ正規表現でやった方が良いですね
Linux Mint ブラウザで固まる時の対処

mintに限らず、フリーズするので、以下　Urlを参考にさせて頂きました。
https://sub-log.jp/2022/12/07/article-07/
Google Chromeの場合
アドレスバーに「chrome://settings/system」と入力し [Enter] を押します。「ハードウェア アクセラレーションが使用可能な場合は使用する」という項目があるのでOFFにします。
上記と同じ手順で「chrome://flags/#enable-gpu-rasterization」を開きます。

「GPU rasterization」という項目を「Disabled」に切り替えて、ブラウザを再起動させます。

Firefox の場合
「about:preferences」を開きます。次に「パフォーマンス」という項目を探し「推奨のパフォーマンス設定を使用する」のチェックを外します。すると「ハードウェアアクセラレーション機能を使用する (可能な場合）」が出現するチェックを外します。