OmniAICreator/Qiita-1.07M huggingface dataset:
2025/1/12 学習記録

## 現状：
エンジニアへの未経験転職。
就職先も決まり、2月からひよこエンジニアに。

2025年は頑張ろうということで、2025年学習記録11日目。

内容は常に書き散らしのメモです、あしからず。

当面の目標：LPIC101,102合格


# Linux

## `npm`コマンド

Node.jsのパッケージ管理システムを操作するためのコマンドラインツール。
JavaScript開発のプロジェクトの依存関係を効率的に管理し、必要なライブラリやツールを簡単に導入・更新・削除することができる。

### 主な機能

1. `npm install` または `npm i` ：パッケージのインストール。パッケージをプロジェクトにインストールします[1][3]。
2. `npm update` または `npm up` ：パッケージの更新。インストールされたパッケージを最新版に更新します[1][3]。
3. `npm uninstall` または `npm rm` ：パッケージの削除。パッケージをプロジェクトから削除します[1][3]。
4. `npm list` または `npm ls`：パッケージ情報の表示。インストールされたパッケージの一覧を表示します[1][3]。
5. `npm run`：スクリプトの実行。`package.json` に定義されたスクリプトを実行します[1]。
6. 依存関係の管理: `package.json` ファイルを使用して、プロジェクトの依存関係を管理します[2][3]。

### Citations:

[1] [https://npm.command-ref.com](https://npm.command-ref.com/)
[2] https://www.sejuku.net/blog/96866
[3] https://qiita.com/akkey2475/items/4c1eb3e3f36f705c7a1c
[4] https://qiita.com/y-suzu/items/26a79305123766999445


# Ruby
- 配列だけではなく、ただの文字列にもindexは適用できる。
- 文字列を順に取り出したい場合
```
str = 'string'
len = str.length

i = 0
len.times do
  beeline = str[i]
  puts beeline
  i += 1
end
```
`index`って配列にしか無い概念かと思っていた・・・

## `delete`メソッド

特定の要素や文字を削除するためのメソッド。
主に配列、文字列、ハッシュで利用される。

### **文字列におけるdeleteメソッド**

文字列に対して使用する場合、deleteメソッドは指定した文字を削除した新しい文字列を返します。元の文字列は変更されません。

**使用例**:

```ruby
str = "hello-world"
result = str.delete("-")
puts result  # => "helloworld"

```

ここでは、「-」が削除され、新しい文字列が生成されています[2][6].

### **配列におけるdeleteメソッド**

配列に対して使用する場合、deleteメソッドは指定した要素を削除します。このメソッドは、削除された要素を返し、指定された要素が存在しない場合は`nil`を返します。

**使用例**:

```ruby
fruits = ["apple", "banana", "orange", "banana"]
removed = fruits.delete("banana")
puts fruits.inspect  # => ["apple", "orange"]
puts removed         # => "banana"

```

この例では、"banana"がすべて削除され、残りの要素が表示されます[1][4].

### **ハッシュにおけるdeleteメソッド**

ハッシュに対して使用する場合、指定したキーを持つ要素を削除し、その値を返します。指定したキーが存在しない場合は`nil`を返します。

**使用例**:

```ruby
hash = { a: 100, b: 200 }
value = hash.delete(:b)
puts hash.inspect  # => {:a=>100}
puts value         # => 200

```

この例では、キー`:b`が削除され、その値が返されています[3][4].

### Citations:

[1] https://magazine.techacademy.jp/magazine/21219
[2] https://www.javadrive.jp/ruby/string_class/index9.html
[3] https://hasyrails.hatenablog.com/entry/2021/05/17/001014
[4] https://style.potepan.com/articles/27656.html
[5] https://qiita.com/hapiblog2020/items/6bdc2f6f2a0a0388ab89
[6] https://zenn.dev/keyproducts/articles/2224ef9f79fc5b
[7] https://qiita.com/jackie0922youhei/items/588cd6f62cb1ff9e9809




# React
拡張機能
`ES7+ React/Redux/React-Native snippets`
https://github.com/r5n-labs/vscode-react-javascript-snippets/blob/HEAD/docs/Snippets.md


# javascript
- `module`について
`default` を用いる場合、`export`できるのは一つのファイルにつき一つだけになる。

### 分割代入
- 配列の場合：順番が重要
- オプジェクトの場合：プロパティ名と一致させることが重要

















### 今日はここまで！
読書感想文「SOFT SKILLS ソフトウェア開発者の人生マニュアル 第1版」

# 書籍名「SOFT SKILLS ソフトウェア開発者の人生マニュアル 第1版」
ジョン・ソンメズ (著), まつもとゆきひろ (その他),
日経BP

中古本を買ったので古い一版の方です。

# 読もうと思った動機
知り合いが推奨してくれたから


# 印象に残った部分

## p76 私の成功のための本のリスト
・CodeComplete
・CAREER SKILL
・権力に翻弄されたいための４８の法則
・夜と霧
・苦境を好機に変える法則


## p96 ダメな履歴書をよくする方法
・履歴書ライターを雇う
　雇うには金が必要だが、２，３％高い給料が高い仕事を得られれば一年目から元を取れる。
・自分で履歴書を書いてから、誰かを雇って改良してもらえば良い

## p151 独学の方法
・教育の大きな目的は知識ではなく行動である　ハーバード・スペンサー
・行動を起こした時にもっともよく学べる。そして学んだことを誰か他の人に教えると知識が補強され、
　理解が深まる。独学する時に重点をおくべきことは、できる限り早く実際に試せるポイントに到達して、行動を起こすことだ。


## p117　気持ちと無償労働である
自分にとっていいメンターになりそうな人をリストアップする

メンターに助けてもらう代わりに差し出せるもの

## p181 弟子を取る
・本気で学びたいという思いのない人を手助けして、あなたの貴重な時間が無駄になってしまうようなことは簡単に起こる。
そのために弟子は慎重に選ぶことが大切だ。豚に真珠に投げるようなことはしてはならない。

・本当に学びたいという気持ちを持ち、そのためには真剣にがんばる気持ちになっている人間を探そう。


## p192 知識の中の隙間を探す
・私達は皆、知識の中に隙間を抱えており、そのために効率を最大限に引き上げて仕事をすることができないでいる。
そういった隙間をたくさんみつけるほど長期的に良くなる。

・知識の隙間チェック項目
　１．もっとも時間を使っているのはどこか
　２．改善できるはずの繰り返し作業
　３，完全に理解しているとは言えない事柄


# 実践できること or 感想

## 感想
・独学のところは耳が痛かったですね。知識だけもっていても実務で使えなきゃもったいないと感じました。
今時間外で勉強している部分が業務で使えるかと考える癖を持とうと思います。

読んだ直後に感想とか自分の主観をしっかり書いとくべきですね。
でないと忘れてしまう。


## 実践できること
履歴の下書きを書く。書いた履歴書を専門の業者にチェックしてもらう。
この場合転職エージェント？？


### 自分にとっていいメンターになりそうな人をリストアップする
自分の場合は以下のとおりです。

SQL→ミックさん
データモデル→渡辺幸三さん
セキュリティ→徳丸浩さん、イプシロンさん
その他周辺知識→増井 敏克さん
プログラミング→Udemy

ブログとか、本で見ればある程度までは知識を継承できると思います。


### 知識の隙間チェック項目
自分の場合は以下のとおりです。

インフラのセキュリティ
ネットワーク
プロジェクトの管理
STM32F767と温度センサーMCP9700で温度をシリアル出力 (Arduino)


参考

![o_coq777.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/a198bc58-b236-3551-27f0-5cb8e36b8c41.jpeg)


https://akizukidenshi.com/catalog/g/g130012/

https://akizukidenshi.com/catalog/default.aspx

x 過去ログを見ょ!!!
x 負の数は、かんがえない!!!
x 例題の為に完全性は、求めない!!!
x MCP9700は、MCP9700T-E/TTのこと

目的
MCP9700の電圧を測って500引いた値の温度を
シリアルからの値をパソコンで表示する。
printfは、stm32 arduinoでは、使えるが?
ここは、あえて、

無意味に
●軽量
●高速化
●見やすさ重視
(f767にハードウェア除算ある為?積極的に割り算を使う)

MCP9700は、温度のアナログ出力ICで内部にオペアンプと
基準電圧?を持ち、多少、補正された値が出力される
リニアティー(値の直線性は、良い)
2Vぐらいから5Vぐらいの電源で使える
mVに対して1℃当たり10mVで10で割った値で温度(整数)になる
オフセット(0℃の中心点)は、500mVで単に500を引けばよい



![Screenshot from 2025-01-13 06-46-37.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/1919934d-49a4-f31d-d857-5cd9123d10c4.jpeg)

![image_original.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/4c703cab-ee1c-cdba-88a2-d7d24f6c5e9e.jpeg)


プログラム


```c++


//ser_mcp9700_stm32f767_1


//インクルド
#include <Arduino.h>


//初期化
void setup() {

  //シリアルポートの初期化
  Serial.begin(9600);

}  //setup


//メインループ
void loop() {

  //温度センサーから電圧を入力する(3.3Vを4096に分解した値)
  analogReadResolution(12);  //センサーの分解度4096
  int s = analogRead(A0);    //センサーの値


  //電圧を温度に変換 ex 20.0 -> 200 温度の十倍を出力
  s = (s * 3300) >> 12;       // s = s * 3300 / 4096 電圧こと
  int temperature = s - 500;  //0℃にするため500引く


  //温度を文字列に変換する
  char data[16];                     //出力用文字列
  data[4] = 0;                       //終端記号
  data[3] = '0' + temperature % 10;  //小数点の値
  temperature = temperature / 10;
  data[2] = '.';                     //小数点の区切り
  data[1] = '0' + temperature % 10;  //整数1桁目(1の位)
  temperature = temperature / 10;
  data[0] = '0' + temperature;  //整数2桁目(10の位)


  //MCP9700の温度を小数点1桁で表示 ex 23.4
  Serial.println(data);


  //1秒の待ち
  delay(1000);

}  //loop


```
IT エンジニアが 自分の小さな「箱」から脱出する方法 を考えると顧客との会話が少し楽になるかもしれない

## 自分の小さな「箱」から脱出する方法

本のタイトルです。読書感想文です。

![](https://m.media-amazon.com/images/I/41odNFVEpHL._SY445_SX342_.jpg)


> Google、Apple、Microsoft などなど、数々の有名企業が研修に採用!
ラグビー日本代表、五郎丸選手も推薦!

> 身の周りの人間関係はすべて自分が原因で引き起こしている。
それこそが、本書のいう「箱に入っている状態」である。

との本で、大雑把には人間関係の悩みへの心理的なアプローチに関するヒントをストーリー仕立てで説く本、だと思います。



## 「箱」とは

この本のタイトルから「箱」とは、何の比喩と想像するでしょうか。

- 「箱入り娘」の「箱」
- 箱 というより訳の問題で「枠」
- バイアスのようなもの

などと私は考えてしまいましたが、ちょっとそれだけだと言葉不足のようでした。曰く:

- 自分への裏切りは「箱」へつながる。
- 「箱」の中に居ると集中できない。
- 自分は「箱」の外に出ているか。
- 抵抗するのをやめたとき「箱」の外に出ることができる。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/93824/10d660ee-6796-6d7d-43f9-496b3c57bbfe.png)


## 「箱」とは「自己欺瞞」

> - 箱 というより訳の問題で「枠」

読み進めると、そうでもないようだ、というようなことが分かります。
「自己欺瞞」なのだそうです。
この段階では、自己欺瞞とはなんなのかがとかく解釈にむずかしいです。

自分の深く信じていたもの (自分の思考の枠組み) が「箱」でもあるのだとしたら、自分の信念 も 自己欺瞞 になってしまいそう... それはちがうだろう！

というのは私の心の声で、しかしその「固執」こそが自己欺瞞という 2 重 (?) のトリックなのだろうかなどなど。以下のように話は展開します。

- 自分がどう考えるかが重要。
- 自分は正しくもあり間違ってもいる。
- 「箱」の中と外では違う結果を招く。


## 「箱」とは: 私の理解

1. 「ソフトウェア開発者としてお客様に貢献したい！」、まず、この気持ちを否定して現状の仕事をしている方はあまりいないはずです。
2. だから、「良いソフトウェアを作りたい！」と考えます。
3. 一方で、実務として仕様を検討したりを進める中で、顧客やプロジェクト チーム内で意見の食い違いが起こることがあります。
4. そうしたときに「あの顧客は分かってない！」とか「あのリーダーが仕様を駄目にした！」などと考えてしまいます。プロジェクトに対する意欲も無くなってしまいます。 

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/93824/042d551e-c95b-9645-04ac-c91ce2fe416e.png)


はい。この「〇〇は分かってない！」が「自己欺瞞」ということなのです。
1 の理想に背いているからです。

「あいつの言うこんな仕様でソフトウェアを作っても意味無いよ！」とか「顧客の言うことはすぐ変わるから信用できない」とかいう気持ちになるのを抑えつつ、でも所詮それは 自分の小さな「箱」なのですね。箱の外から見ると、「あいつの言う仕様」と自分の思っている仕様って圧倒的な違いはあるでしょうか。本当に違いがあるケースもあると感じつつ、意外と大差ない気もする？ その視点をずらすことがまず大事なのかななどと感じます。


## 「箱」 まとめ

すべきことは分かっているのに時としてその感情に背く、それが自己欺瞞、自分への裏切りなのだと考えています。箱は自分の癖のようなもの？箱の中は居心地が良いのだそうです。

> 自分の中の嘘に気づくことで箱から出られる

「バイアス」とか表現するのではなく「自己欺瞞 (嘘)」というのが良いのかもしれません。「3 日坊主は自分に対する裏切りだ」という意味での「自己欺瞞 (嘘)」です。他の人々に抵抗することをやめると、箱の外に出ることができるのです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/93824/ebf4ddd0-2215-1560-d2f5-c5d4f66c3211.png)

一般的な技術書と異なるふわふわ感で好みが分かれるところがあるかもしれませんが、私はかえって変なテクニックを解説したアプローチではない点に面白味を感じました。人の心理に目を向けている本なのではなどなど。

素直な人の心にすっとはまる本。笑
先にほかの方の書評を読んでから読むのが私には合っていました。以下など参考。



### 参考

https://bookmeter.com/books/105078

https://note.aiken-to-osanpo.dev/n/nc402f9f4af04

以上です～
circuitjsの作法 その40

# 概要
circuitjsを調査してみた。
練習問題やってみた。

# 練習問題
リレーで、Dフリップフロップ回路を作れ。
ワイヤーループ対策せよ。

# 写真

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/18104/6d361585-8cbe-4f9a-ac2a-21cfa87bb2d1.png)


# ネットリスト

```
$ 1 0.000005 10.20027730826997 50 5 50 5e-11
178 448 336 448 432 6 2 0.2 0 0.05 1000000 0.02 20 0.015 0.005 0
178 672 336 672 432 6 2 0.2 0.0000018812468029037255 0.05 1000000 0.02 20 0.015 0.005 0
178 848 336 848 432 6 2 0.2 0.09359636117711292 0.05 1000000 0.02 20 0.015 0.005 1
R 304 96 240 96 0 0 40 5 0 0 0.5
g 416 432 416 448 0 0
g 640 432 640 448 0 0
g 816 432 816 448 0 0
w 304 96 320 96 0
w 320 96 320 160 0
w 320 160 320 192 0
w 320 192 352 192 0
w 432 192 432 240 0
w 432 240 416 240 0
w 416 240 416 336 0
w 320 96 448 96 0
w 640 272 640 336 0
w 816 304 816 336 0
s 352 192 432 192 0 1 false
178 176 336 176 432 6 4 0.2 0 0.05 1000000 0.02 20 0.015 0.005 0
g 144 432 144 448 0 0
w 288 192 320 192 0
w 224 192 208 192 0
x 253 155 284 158 4 24 clk
x 356 157 373 160 4 24 D
w 1280 96 1280 128 0
w 1072 96 1072 128 0
162 1280 128 1280 176 2 default-led 1 0 0 0.01
162 1072 128 1072 176 2 default-led 1 0 0 0.01
g 1264 432 1264 448 0 0
g 1056 432 1056 448 0 0
w 1200 304 1200 336 0
w 992 272 992 336 0
g 1200 432 1200 448 0 0
g 992 432 992 448 0 0
178 1232 336 1232 432 6 3 0.2 0.0000022931211354680617 0.05 1000000 0.02 20 0.015 0.005 0
178 1024 336 1024 432 6 3 0.2 0.041632843888228056 0.05 1000000 0.02 20 0.015 0.005 1
w 144 336 144 192 0
w 144 192 208 192 0
w 320 336 320 304 0
w 176 304 176 336 0
w 224 336 224 304 0
w 272 336 272 304 0
w 176 304 224 304 0
w 224 304 272 304 0
w 272 304 320 304 0
w 560 96 672 96 0
w 672 96 848 96 0
w 848 96 1024 96 0
w 1024 96 1072 96 0
w 1072 96 1232 96 0
w 1232 96 1280 96 0
w 720 336 720 304 0
w 896 272 896 336 0
w 1120 304 1120 336 0
w 1328 272 1328 336 0
w 640 272 896 272 0
w 720 304 816 304 0
w 992 272 1328 272 0
w 1120 304 1200 304 0
w 912 432 912 480 0
w 192 432 192 480 0
w 464 480 912 480 0
w 1248 432 1248 480 0
w 912 480 1248 480 0
w 240 432 240 512 0
w 1040 432 1040 512 0
w 736 432 736 512 0
w 576 512 736 512 0
w 736 512 1040 512 0
w 256 432 256 544 0
w 688 432 688 544 0
w 256 544 688 544 0
w 304 432 304 576 0
w 864 432 864 576 0
w 304 576 864 576 0
w 1344 432 1344 544 0
w 688 544 1344 544 0
w 1136 432 1136 560 0
w 1136 560 1136 576 0
w 864 576 1136 576 0
w 448 96 496 96 0
w 496 96 560 96 0
w 240 512 480 512 0
w 432 432 432 480 0
w 512 432 512 512 0
w 480 512 512 512 0
w 512 512 576 512 0
w 432 480 464 480 0
w 192 480 432 480 0
s 224 192 288 192 0 1 true
w 1072 176 1072 224 0
w 1072 224 1072 336 0
w 1280 176 1280 336 0
r 320 192 320 272 0 100
r 448 96 448 208 0 100
r 496 96 496 208 0 100
r 672 96 672 208 0 100
r 848 96 848 208 0 100
r 1024 96 1024 208 0 100
r 1232 96 1232 208 0 100
w 320 272 320 304 0
w 448 208 448 320 0
w 496 208 496 336 0
w 448 320 448 336 0
w 672 208 672 336 0
w 848 208 848 336 0
w 1024 208 1024 336 0
w 1232 208 1232 336 0

```

以上。
circuitjsの作法 その39

# 概要
circuitjsを調査してみた。
ワイヤーループ対策する。

# ワイヤーループとは
電気的に、無意味な、２重のワイヤー接続。
circuitjsは、ワイヤーループを検出するとシュミレーションを止めてしまう。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/18104/6b393dcf-e1e2-bfb5-d5d2-ddc7f8253e6f.png)

# 対策
抵抗を入れる。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/18104/deb628e0-31cd-edb1-e734-f8a97b57ad47.png)


以上。
App Storeのローカリゼーションを日本語のみにする

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/393560/893126cd-1a48-9751-5c79-d8bbaf46e8fd.png)

デフォルトだと、添付の画像のようにENとなってしまいます。

## Xcodeで日本語をサポートする設定を追加
1. プロジェクト設定を開く:
    * Xcodeでプロジェクトを開き、左上のプロジェクト名をクリック。
2. ローカリゼーション設定を開く:
    *「Info」タブを選択。
    *「Localizations」セクションで、+ ボタンをクリック。
    *「Japanese（日本語）」 を追加。

## Info.plist ファイルで対応言語を確認
Info.plist に対応する言語を指定する必要があります。

1. CFBundleLocalizationsキーを確認:
    * プロジェクト内の Info.plist を開きます。
    * CFBundleLocalizations キーがない場合は追加してください。
    * 以下のように、日本語（ja）を含めます：
    ```xml
    <key>CFBundleLocalizations</key>
    <array>
        <string>ja</string>
    </array>
    ```
Awtrix の Tips（カスタムアプリ削除）

## 空メッセージを送れない MQTT アプリからカスタムアプリを削除する
MQTT を使って Awtrix を制御することができるが、コマンド一覧は API のページに列挙されている。

https://blueforcer.github.io/awtrix3/#/api

この中で、カスタムアプリを削除するには空のペイロード・本文をトピックに送ればよいと書かれている（To remove a custom app, dispatch an empty payload/body to the associated topic or URL.）。

ところが、 MQTT アプリの中には空のメッセージを送れないものがある（Android の MyMQTT や MQTT Clientなど）。
かといって "" などを送っても空と解釈はされない。
Awtrix の JSON の解釈はわりと厳密で、末尾に余分な改行があっても動作しない。

試行錯誤してみたが、
```
{}
```
のように空のオブジェクトを送ったところ、無事アプリの削除ができた。

## カスタムアプリの削除は前方一致
MQTT によるカスタムアプリの送信では、複数のオブジェクトを配列化することで複数のカスタムアプリを一度に作ることができる。この時、各アプリ名はトピック名の末尾に0からの連番が付加される。

このような管理をすることで、連番を除いたトピック名に空の本文を送ることにより配列全部のカスタムアプリを削除することができる。
この一括削除は配列による複数自動生成に限った仕様ではないため、他のカスタムアプリの先頭部分に同じ文字列が入っていた場合、それらも削除されてしまう。

例えば、 tokyotemp というアプリ名でアメダス気温を表示させつつ、 tokyo というトピック名で予報の配列を送った場合（それぞれ tokyo0・tokyo1 のようになる）を考える。
予報のみを削除しようとして tokyo に空の本文を送ると、 tokyo0・tokyo1だけでなく、 tokyotemp も消えてしまう。
tokyotemp を削除しないためには、面倒でも tokyo0・tokyo1 それぞれに空の本文を送る必要がある（もちろんトピック名を tokyoforecast のように指定すればよい話なのだが）。

他のアプリ削除時に意図せぬ削除が生じないよう、アプリ名（トピック名）を設定する時は注意が必要である。
Hugging Face モデルをONNX形式で使いたい。あとNSC2で文字起こしがしたい

大学の講義でICT実践なるものがあり、RaspberryPi5 8GBモデルを使ってスマートスピーカーを作ることに挑戦している。

この記事をベースにして制作しているのだが……

https://qiita.com/nijigen_plot/items/5f5299af6aebc54b42d3

自分の場合、学生で金もないためお高いGPUをサーバーとして使うこともできない。
この記事でも多くの処理をRaspberryPi上ではなく、
外部サーバに任せることでスムーズな実行を行っている。
（割と取り返しのつかない時期に気づいた。）

このままでは、一回の応答にn時間かかるスマートじゃないスピーカーが出来上がってしまう。
さて、どうしたものか……

あれなんだこれ

https://www.switch-science.com/products/4104?srsltid=AfmBOoqWVTCNkVlg7k3U_pGoPS-XJm7Pvd9gHi3H_iiu8zI9dCdL_E8z

先輩が残していった遺物です。（販売終了済み）
希望の光が見えてきた。

そしていろいろ調べて何とかうまくいきそうなとこまできました。
ONNX形式やIR形式についていろいろ調べてぶつかりまくったので、備忘録として残しておきます。

以降のコマンドは、wslかつpyenv上で実行したコマンドです
pythonのバージョンは3.8.20です。
openVINOなどの互換性を調べたらこのあたりが無難そうだったからです。

# Hugging FaceモデルをONNX形式に変換するには
ChatGPT君が出すコードどれもエラーでした。
結局自分でググって、自分で解決しました😢

僕が全然知らなかっただけでみんな知ってるかもしれませんが……
`kotoba-whisper-v2.0`なら、こんな感じで

```
optimum-cli export onnx --model kotoba-tech/kotoba-whisper-v2.0 ./kotoba-v2_onnx/
```

簡単に変換できます。
リポジトリ名のところを見れば規則性が明らかですね。

```
pip install optimum
``` 

としてやれば簡単に使えるコマンドです。

コードでも変換できるのかもしれませんが、
エラーが消えなくて諦めました。

一行で変換できちゃうのは楽でいいですね！

参考

https://huggingface.co/docs/optimum/exporters/onnx/usage_guides/export_a_model


# ONNX形式からIR形式に変換
こちら、ChatGPTが使い物にならず。
`mo`はもう使えないらしい。

結局公式ドキュメントのコードをそのままパクりました。

こんな感じ

```
ovc model/encoder_model.onnx --output_model model/encoder_model.xml --compress_to_fp16=False
```

ちなみに、`compress_to_fp16=False`というのは、重み行列などを16bit float型に圧縮させませんよーという意味です。（デフォルトでfp16に圧縮するよう設定されている）

わかりやすいですね。
このコマンドはデフォルトで圧縮されるので、
`=False`
としてやることで、32bit float型のままIR形式に変換しろという意味です。

オプションとかも書いてあるのでここが一番わかりやすいです。

https://www.isus.jp/wp-content/uploads/openvino/2024/docs/notebooks/121-convert-to-openvino-with-output.html

# 謎のonnx_data形式が出現？！
こいつ、まじクソ。
公式サイトでこの拡張子を書いてないから調べるのに手間取った。

どうやら、onnxファイルのサイズが2GBを超える場合、
別途外部にファイルを作成するとかなんとか。
わかるけどさー。
せめて拡張子くらい書いてくれ。

一応、onnxをIRに変換するときは
自動で結合して変換してくれるので気にしなくて大丈夫です。

onnx_data形式の正体について気づくきっかけになった公式ドキュメント

https://onnx.ai/onnx/api/external_data_helper.html

あとはNCS2とラズパイがまともに動作するか……
わからねぇ……
FiveMのプラグイン開発　メモ

# 使いそうなの
個人的に使いそうだなと思ったやつを一部まとめます。
スニペットともいいます。

## コマンド
```client.lua
RegisterCommand('test', function(args)
    print("test command.")
)
-- ゲーム内チャットで /test で呼べる
```

## Config（設定ファイル）

```config.lua
Config = {}
Config.Value   = 10.0
Config.Locale  = "ja"
```

必ずfxmanifestに記述してください。

```fxmanifest.lua
...

shared_scripts {
    'config.lua'
}

...
```

```client.lua
-- fxmanifestに書いてあれば require とかはいらないです。
local value = Config.Value
local locale = Config.Locale
```



## print
```client.lua
print("test") -- testと出力される。
print("テスト") -- 文字化けする。
```

## スレッド
- 非同期で実行したいときに便利。

```client.lua
Citizen.CreateThread(function()
    while true do
        print("Hello world!")
        Citizen.Wait(1000) -- 待機時間（ミリ秒）
    end
end)
```
:::note warn 
Wait を入れ忘れると、負荷が高まりクラッシュする可能性があります。
:::


## 描画関係
スクリーンへの描画。
```client.lua
-- 線を描画
DrawLine_2d(x1, y1, x2, y2, lineWidth, r, g, b, a)

-- 四角形を描画
DrawRect(x, y, width, height, r, g, b, a)
```
四角形は必ず塗りつぶされます。枠線のみが必要な場合は `DrawLine_2d` を使用してください。

## 座標系
```client.lua
-- Entityの座標
local playerCoords = GetEntityCoords(PlayerPedId())
print(playerCoords) -- vector3で返される。

-- ワールド座標をスクリーン座標へ変換する。
local isOnScreen, screenX, screenY = GetScreenCoordFromWorldCoord(boolean, screenX, screenY)

```
:::note warn 
・`GetScreenCoordFromWorldCoord`について
最初の返り値は「スクリーン内に映っているかどうか」を示すboolean。

``GetWorldCoordFromScreenCoord``というワールド座標へ変更する方もあります。
:::

## イベント関連

- クライアント側からサーバーイベントのトリガー
```client.lua
TriggerServerEvent('custom_event')
```

```server.lua
-- カスタムイベントは必ずRegisterNetEventをしないとフックできません。
RegisterNetEvent('custom_event')
AddEventHandler('custom_event', function()
    print("Server event has")
end)
```

- サーバー側からクライアントイベントのトリガー
```client.lua
-- カスタムイベントは必ずRegisterNetEventをしないとフックできません。
RegisterNetEvent('custom_event')
AddEventHandler('custom_event', function()
    print("Client")
end)
```

```server.lua
TriggerClientEvent('custom_event')
```

:::note warn
TriggerClientEvent(クライアントをトリガー）、TriggerServerEvent(サーバーをトリガー）の混同に注意。
:::

:::note info
https://docs.fivem.net/docs/scripting-reference/events/list/
に乗っているやつはRegisterNetEventしなくても大丈夫っぽい？
:::

## プレイヤー関連
```client.lua
local health = GetEntityHealth(PlayerPedId())
local armor = GetPedArmour(PlayerPedId())

print("player health : " .. health)
print("player armor  : " .. armor)
```
プレイヤーのヘルスとかアーマーとか他にも色々取得できます。

## 車両
```client.lua

-- Ped（何らかのキャラクター）が乗り物に乗っているかどうか
if IsPedInAnyVehicle(PlayerPedId(), false) then
    print('Local player is in a vehicle')
end

local playerPed = PlayerPedId()

-- Pedが乗っている車両を取得
local vehicle = GetVehiclePedIsIn(playerPed, false)
print("Vehicle ID: " .. vehicle)

-- 組み合わせると便利
```

## QBCore 編

## アイテムの使用

```client.lua
-- アイテムを使えるようにする
function QBCore.Functions.CreateUseableItem(item, cb)
    QBCore.UseableItems[item] = cb
end

-- アイテムが使えるかのチェックを推奨
function QBCore.Functions.CanUseItem(item)
    return QBCore.UseableItems[item]
end

-- アイテムを所持しているかどうか
local hasItem = QBCore.Functions.HasItem('my_cool_item')
print(hasItem)
```

## 通知

```client.lua
-- 文字化けせず日本語が使える
QBCore.Functions.Notify("通知が呼び出されました", "success")

-- 前者と違い、赤くエラー表記になる
QBCore.Functions.Notify("通知が呼び出されました", "error") 
```

## まとめ
使えそうなのがあればまた追記していきます。
【rails】Docker環境にデバッグの導入

# はじめに
現在、Youtube apiを導入しており、そこでデバッグをするための`binding.pry`を環境に取り入れようとして、結局`debug`を取り入れた内容を備忘録として記載しておきます。

# 現状
これまでrailsを勉強してきて、`binding.pry`も利用してきました。ですので、今回も以下の流れで進めておりました。
　①Gemfileに必要なものを追加
　②bundle installを実行
　③binding.pryを記述して実行
しかし、うまく機能しなかったので、原因を調べて解決するまでの流れをこちらに記載したいと思います。

# 流れ
#### 原因
そもそも`binding.pry`は、プログラムの実行を一時停止して、ターミナル上で対話的に操作できるデバッグツールです。なので通常の環境では、ターミナルとプロセスが直接接続されているため、簡単に機能します。
しかし、Dockerを使用している場合、作成されたコンテナ内のプロセスはローカルのターミナルから隔離されているため、機能しないとのことでした。
ですので、そちらの解決する方法を今回は紹介します。

#### 解決
###### Gemの追加
```diff:Gemfile
- gem 'pry-rails'
+ gem 'debug' #これを追加
```
> 'debug Gem'は、Ruby公式の最新デバッガとして、標準的なデバッグツールとなりました。
特に Rails 7.0以降では、デフォルトで導入されているため、デバッグ環境のセットアップがより簡単になったそうです。

これから新しいプロジェクトを始める際は、binding.break を使って効率的にデバッグしましょう！

###### compose.yamlの追加
```php:compose.yaml
    tty: true
    stdin_open: true
```
これらのコードを追記してください。
`tty`は「擬似端末」を割り当てる設定とのこと。つまり、Dockerコンテナ内のターミナル操作を有効にするための記述です。
`stdin_open`は「標準入力」を開いたままにする設定です。
trueに設定することで、コンテナが実行中に標準入力を受け付けるようになります。ターミナルの`-it`コマンドと同じ役割を持つ。

###### コンテナの起動
デタッチモードでコンテナを起動させる。
```php:ターミナル
docker-compose up -d
```
そこから、コンテナにアタッチすることで、デバッグを活用することができます。
```php:ターミナル
docker attach Webサーバーのコンテナ名(docker psで取得)
```
これで準備は完了です。あとは、`binding.break`などを入れて必要に応じてデバッグを実行して下さい。
デバッグのコマンドなどは[こちら](https://qiita.com/yuskubo/items/111a87e2402de8e12914)のサイトを確認してみると、とても分かりやすいです！

# さいごに
初めは`binding.pry`を導入しようと色々調べたが、docker環境だと標準的に導入されたデバッグツールを使用することで、デバッグすることができました。これからもポートフォリオ完成に向けて進めていきたいと思います。
vosk を利用して音声ファイルから文字起こしファイル（テキストファイル、字幕ファイル `srt`）を生成する


# 概要

音声ファイル(.wav)に対して、文字起こしした結果をテキストファイル(.txt)に出力する。

vosk のサンプルコードである [vosk-api](https://github.com/alphacep/vosk-api/) リポジトリの Python コードが目的を果たすのに十分だったので、その動作方法記載です。

# 準備

## 動作確認

- Python 3.12.6
- macOS 14.4

## モデルをダウンロードする

https://alphacephei.com/vosk/models からモデルをダウンロードする。

vosk-model-ja-0.22 をダウンロードし、任意のディレクトリに展開する。ほかのモデルを使う場合は、後述の -m オプションを調整する。

## スクリプト用意

```bash
git clone git@github.com:alphacep/vosk-api.git
cd vosk-api
cd python

pip install vosk
# 動作確認時 vosk==0.3.44 だった
```

# 使い方

## 実行例

テスト用の英語音声ファイル example/test.wav がリポジトリに含まれている。

音声ファイル example/test.wav の字幕ファイル test.srt を出力する。

```bash
# モデルの指定がない場合は英語のモデルを自動でダウンロードして英語で文字起こしする。
python vosk/transcriber/cli.py -i example/test.wav -t srt -o test.srt

# 日本語で文字起こしする場合は `-m` オプションでモデルを指定する。展開後のディレクトリを相対パスで指定した。
python vosk/transcriber/cli.py -m vosk-model-ja-0.22 -i test.wav -t srt -o test.srt

# `-t` オプションを指定しなければ出力はテキストファイルになる。
python vosk/transcriber/cli.py -m vosk-model-ja-0.22 -i test.wav -o test.txt
```

### 結果

英語で文字起こしした srt ファイルの結果は以下です。きちんと時間ごとに字幕が別れていることを確認できます。短く単純な音声のため文字起こしに間違いもなさそうです。

```
1
00:00:00,840 --> 00:00:02,610
one zero zero zero one

2
00:00:03,930 --> 00:00:04,980
nah no to i know

3
00:00:06,240 --> 00:00:07,980
zero one eight zero three
```

音声ファイル（2025/1/13確認）: https://github.com/alphacep/vosk-api/blob/master/python/example/test.wav

### 日本語での結果

日本語のテスト音声ファイルはないため、日本語は試した範囲の結果の感想を記載します。

日本語の YouTuber の雑談会話（1名、1時間、BGMあり）に対して利用してみたところ、元の音声を知っていれば理解できるぐらいの精度はありました。

自分の元々の期待は単語が2,3割ぐらい分かって検索可能になれば十分ぐらいに思っていましたが、単語5割/文章5割ぐらいは分かるので期待以上という感触でした。とくにBGMがあってこの精度なのは驚きました。

精度への期待は色々あると思うので、まずは試していただくのがいいと思います。

別途実行時間について計測したところ、10分の動画で2分程度でした。

## オプションについて

```
usage: cli.py [-h] [--model MODEL] [--server SERVER] [--list-models] [--list-languages] [--model-name MODEL_NAME] [--lang LANG] [--input INPUT] [--output OUTPUT] [--output-type OUTPUT_TYPE] [--tasks TASKS]
              [--log-level LOG_LEVEL]

Transcribe audio file and save result in selected format

options:
  -h, --help            show this help message and exit
  --model MODEL, -m MODEL
                        model path
  --server SERVER, -s SERVER
                        use server for recognition. For example ws://localhost:2700
  --list-models         list available models
  --list-languages      list available languages
  --model-name MODEL_NAME, -n MODEL_NAME
                        select model by name
  --lang LANG, -l LANG  select model by language
  --input INPUT, -i INPUT
                        audiofile
  --output OUTPUT, -o OUTPUT
                        optional output filename path
  --output-type OUTPUT_TYPE, -t OUTPUT_TYPE
                        optional arg output data type
  --tasks TASKS, -ts TASKS
                        number of parallel recognition tasks
  --log-level LOG_LEVEL
                        logging level
```

- `--model` はモデルのパスを指定します。
- `--output-type` は出力形式を指定します。デフォルトは `txt` です。`txt`, `srt`, `json` が利用可能です。
- `--input` は入力ファイルを指定します。ディレクトリも指定できます。
- `--output` は出力ファイルを指定します。ディレクトリも指定できます。
- `--model-name` はモデル名でモデルを指定します。`--list-models` で利用可能なモデル名を確認できます。モデルは自動でダウンロードします。
EC2 の料金タイプについて


この記事は[AWS CloudTech カレンダー](https://qiita.com/advent-calendar/2021/awscloudtech)の 24 日目です。

EC2 の料金タイプについて書いてみました。

## オンデマンドインスタンス

何も設定しない場合は、EC2 インスタンスを起動するとデフォルトでオンデマンドインスタンスになります。
秒単位で使ったら使った分だけ料金が請求されます。
必要なときに必要なインスタンスを起動できます。

## リザーブドインスタンス(RI)

1 年または 3 年の期間で使用量を契約するかわりにオンデマンドより安く利用できるプランです。
24 時間 365 日(またはそのうちの 75%以上)稼働することが決まっている場合はリザーブドインスタンスを使うと安くなります。
リザーブドインスタンスには、期間中に属性を変更できるコンパーティブルとスタンダードと呼ばれるものがあります。
3 年間、全額前払い、スタンダードタイプが最も値段を安く抑えることができます。

## スポットインスタンス

EC2 には、ユーザの利用頻度によって料金が変わるスポット料金というのがあります。
スポット料金は AZ によって異なります。
ユーザが利用したい料金(=リクエスト料金)を設定してその料金をスポット料金が下回ったときにスポットインスタンスが稼働します。
リクエスト料金がスポット料金を上回ったときはスポットインスタンスが停止します。
なので、急に停止しても問題ないようなユースケースに向いています。
たとえば、厳密なリアルタイム性を必要としないバッチ処理などに向いています。

## Dedicated Hosts

EC2 が起動するホストを占有するオプションです。
インスタンスではなくホストに対しての従量課金です。

## Savings Plans(SP)

1 年または 3 年の期間で一定量の使用量を契約するかわりに安く使用することができるプランです。
[公式の説明](https://aws.amazon.com/jp/savingsplans/)によると、オンデマンドインスタンスを使うより最大で 72%もコストカットができるようです。
RI との違いは購入のしかたです。RI では、リージョンやインスタンスタイプなどオンデマンドタイプと同様の指定をするのに対して SP では、コミットメント額と呼ばれる 1 時間あたりの金額の指定をする必要があるため、自分で金額を計算する必要があります。

## 参考

https://aws.amazon.com/jp/ec2/pricing/
https://dev.classmethod.jp/articles/ec2-reserved-instances-savings-plans-comparison/
https://www.sbcr.jp/product/4797397406/
【AWS】Amazon Bedrockを使ってブラウザをプロンプトだけで操作してみた（bedrock_browser_agentの開発）

## この記事のポイント

- Amazon BedrockのConverse APIを使ってChromeブラウザを開いたよ
- どういう仕組みか解説しているよ

## はじめに

この記事ではAmazon Bedrockを使ったブラウザ操作について書いています。

## 動作環境

- chromedriver
- anthropic.claude-3-haiku-20240307-v1:0
- macOS 15.2
- boto3 1.35.97

## AIエージェントの流行りに乗って

巷ではAIエージェントて何かを自動化するのが流行っていると聞いたので今回はブラウザを操作してみることにしました。

## 実際にやったこと

Amazon BedrockのConverse APIでWebDriverのエンドポイントにリクエストを送り、お手元のChromeブラウザを起動するということをやってみました。

[実演動画](https://youtu.be/fcCPRoWejWA)

検証の目的としては「プロンプトだけでE2Eテストできたらいいな」というのがありました。

既製品ですでにできることではありますが、やっぱ自分で作ってワクワクしたいってのもありますし、
既製品ではできないことを実現してみたいというモチベーションもありました。

## 実際のソースコード

今回はWebDriverを操作するモジュールとAmazon Bedrockの基盤モデルを操作するモジュールの2つを自作しました。

2つのモジュールを使ってブラウザをプロンプトだけで操作してみました。

```py
import webdriver.tool as wd_tool
import bedrock.core.const as const
import bedrock.tool as bdr_tool

if __name__ == "__main__":
    print(wd_tool.help())
    print(bdr_tool.boto3_version())
    print(const.region_name["apne1"])

    agent = bdr_tool.agent_action()
    agent.set_query("https://www.google.com/ をGoogle Chromeのウィンドウで開く")
    res = agent.execute(const.claude_model_ids["claude-3-haiku"])

    print(res)
    if res:
        session_id = wd_tool.open_window(
            res[1].get("url"), res[1].get("browser"))
        print(session_id)
```

- [webdriver](https://github.com/ymd65536/bedrock_for_webdriver/tree/main/bedrock_browser_agent/webdriver)
- [bedrock](https://github.com/ymd65536/bedrock_for_webdriver/tree/main/bedrock_browser_agent/bedrock)

仕組みとしてはAmazon BedrockのConverse APIでTool UseしてWebDriverの機能を呼び出しています。

## まとめ

今回はブラウザを起動するだけに留まりましたが、作り方次第でUIのクリックやファイル出力もできるのでもう少し拡張できたら良いなと思いました。

なお、WebDriverで作っていますが、Playwrightで作るのもいいなと思ったので後々考えていきたいと思います。

## ちなみに

Google DeepMindさんが[Project Mariner](https://deepmind.google/technologies/project-mariner/)というプロジェクトをスタートさせており、簡単に説明するとブラウザを操作するAIエージェントを研究・開発するプロジェクトみたいです。もっと簡単に言うと、プロンプトひとつでAIがブラウザを操作できるようにするプロジェクトなので今回の記事でやっていることに近いのかなと思いました。
commitlintとCommitizenの導入（huskyもあるよ）

# はじめに

GitCommitのコミットコメントを統一化する手法として、commitlintとCommitizenの導入が考えられる。
commitlintとCommitizenは特に問題ないが、huskyで詰まったのでメモとして残す。

## 使用するパッケージ
- commitlint
コミットメッセージが規約に沿っているかをチェックするツール。

- Commitizen
フォーマットされたコミットメッセージを簡単に作成できるCLIツール。

- husky
Gitフックを簡単に管理・設定し、自動化スクリプトを実行できるツール。


## 大まかな手順

1. commitlintの導入と設定
1. huskyの導入と初期設定
1. Commitizenの導入と設定
1. huskyのフック設定

## commitlintの導入と設定

### commitlintのインストール
npmを利用してライブラリをインストールする。（yarnでも良い）

```bash
npm install --save-dev @commitlint/cli @commitlint/config-conventional
```
package.jsonにも追加されている


### commitlintの設定ファイルを追加

```commitlint.config.js
module.exports = {extends: ['@commitlint/config-conventional']}
```

:::note warn
Cursorをなどを使用しているとJSをESモジュールに変換するように促してくるが、変換はせずこのまま（CommonJSのまま）にしておくこと
:::

### 動作確認
以下のコマンドでcommitlintの動作確認を行う。　設定に失敗していればエラーメッセージが表示される。
なお、コミットしてまだプッシュしていないものがあれば、Conventional Commitsに沿っていない場合はその旨のメッセージが表示される。

```bash
npx commitlint -l
```

## huskyの導入と設定

### huskyのインストール
npmを利用してライブラリをインストールする。（yarnでも良い）

```bash
npm install husky --save-dev
```

### huskyの初期設定
initオプションを使用して初期設定を行う。
以前は`npx husky install`や`npx husky add 〜`を使用していたが、v9になってから非推奨のオプションになった。

```bash
npx husky init
```

これでGitフックの準備ができている。
以下のように`.husky/pre-commit`ファイルにtestコマンドが登録されているため、不要であればコメントアウトしておく。
```.husky/pre-commit
#npm test
```

## Commitizenの導入と設定
### Commitizenのインストール
npmを利用してライブラリをインストールする。（yarnでも良い）
```bash
npm install --save-dev commitizen
```

### Commitizenの初期設定
以下のコマンドで設定を行う。`package.json`にも設定が追加される。
```bash
npx commitizen init cz-conventional-changelog --save-dev --save-exact
```

### Commitizenの設定追加
package.jsonにscriptsを追加する。　※huskyがあると思うのでその下に`"commit": "cz"`を追加する。
```package.json
{
  〜
  "scripts": {
    "prepare": "husky",
    "commit": "cz"
  },
  〜
}
```

### Commitizenの動作確認
`npm run commit`を実行してエラーがないことを確認する。
なお、ファイルがGitのステージングに無いときは↓のようなエラーになるが、これは問題ない。
```
% npm run commit
Debugger attached.

> commit
> cz

Debugger attached.
No files added to staging! Did you forget to run git add?
Waiting for the debugger to disconnect...
Waiting for the debugger to disconnect...
```

## huskyのフック設定
huskyのフック設定を行い、`git commit`でCommitizenの実行とcommitlintを実行するようにする。

### prepare-commit-msgフックの設定
prepare-commit-msgフックで、`git commit`時にCommitizenを実行する。
`.husky/prepare-commit-msg`ファイルを作成し以下の内容を記述する。

```.husky/prepare-commit-msg
exec < /dev/tty && git cz --hook || true
```
もし上記で上手くいかないようであれば↓のようにしてみる。
```.husky/prepare-commit-msg
exec < /dev/tty && node_modules/.bin/cz --hook || true
```




### commit-msgフックの設定
commit-msgフックでコミットメッセージを入力した時にcommitlintを実行する。
`.husky/commit-msg`ファイルを作成し以下の内容を記述する。

```.husky/commit-msg
npx --no -- commitlint --edit ${1}
```

`.husky`以下のファイルは↓のようになっていると思う。
![スクリーンショット 2025-01-13 0.51.35.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2964854/66e4b0bb-2c53-13c3-5f3a-e49167833911.png)

以上で設定完了。
変更ファイルを`git add`でステージングに配置し、`git commit`で動作するはず。
Chrome拡張機能「WA Number Checker」を使用してWhatsApp番号を確認する方法

私たちは最近、WhatsApp番号のステータスをオンラインで無料で確認できるChrome拡張機能「WA Number Checker」を発表しました。

## Chrome拡張機能「[WA Number Checker](https://CheckNumber.AI)」を使用してWhatsApp番号を確認する手順

![WA-number-checker-chrome-extension.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3963003/1bee1b7b-7047-5ce6-335d-6cb93b58dad0.png)


1. まず、Chromeウェブストアのウェブサイトにアクセスします: https://chromewebstore.google.com/detail/wa-number-checker-checknu/ancoloifckoalgpijpnmpolbdgegdogo をクリックし、「Chromeに追加」ボタンをクリックします。

2. インストール後、Chromeツールバーの拡張機能アイコンをクリックします（赤い点1で示されています）。

3. 確認したいWhatsApp番号を入力します（赤い点2で示されています）。

4. 「番号を確認」ボタンをクリックします（赤い点3で示されています）。

5. ネットワークが正常であれば、待つことなく下部にWhatsApp番号の確認結果が表示されます（赤い点4で示されています）。

## WhatsApp番号確認結果の説明:

1. 「number」フィールドは確認されているWhatsApp番号です。

2. 「whatsapp」フィールドは、その番号がWhatsAppで利用可能かどうかを示します（利用可能な場合は「はい」、利用できない場合は「いいえ」、番号が確認中の場合は「確認中」と表示されます）。

3. 「status_update」フィールドは、現在のWhatsAppアカウントのステータス更新の時間情報を表示します。

4. 「signature」フィールドは、それが企業アカウントであるかどうかを示します。

5. 「avatar」フィールドは、WhatsAppのアバターがあるかどうかを示します。

6. 「region」フィールドは、WhatsApp番号が所在する国/地域を示します。

7. 「carrier」フィールドは、WhatsApp番号のキャリアを示します。

現在、このWhatsApp番号確認サービスは無料で提供されており、1日に約10〜30番号を確認できます（無料ユーザー）。

より多くのWhatsApp番号を一括で確認する必要がある場合は、[ウェブサイトのスタッフに連絡](https://wa.me/17253100591)して、一括確認サービスを購入することができます。これは非常に手頃な価格です。

English Version: [How to check WhatsApp number using Chrome Extension WA Number Checker](https://checknumber.ai/blog/chrome-extension-wa-number-checker)
[WA Number Checker Chrome extension](https://wa-number-checker.blogspot.com/)
FreeBSD 小ネタ /etc/dma/dma.conf

# dma.conf は基本的に
" " を区切り文字と考えてないので、トラブルになることがる


```
MASQUERADE   root-hoge@

```
普通に考えると "root-hoge@" と解釈されることが想定されるのだが、dmaはこれを

"   root-hoge@.."

と解釈してしまうので、トラブルになる。
【Next.js】App Routerを使ってみた！

## はじめに
今回なぜNext.jsのApp Routerについて記事にしたかというとver.12まではPage Routerが主流でしてたがver.13以降はApp Routerがデフォルトのルーティング機能であるため簡単に使用方法をまとめてみました

### App Routerとは
App Routerはディレクトリ構造に基づいたルーティング機能であり、以下のような特徴がある
1. ファイルベースのルーティングでありディレクトリ構造そのものがルートである
2. サーバーコンポーネントでありデフォルトはサーバー側でレンダリングされる
3. ページごとにことなるレイアウトを簡単に適応できる 

**ディレクトリ構造**
```plaintext
app/
├── layout.jsx        // アプリ全体のレイアウト
├── page.jsx          // ルートページ (/)
├── about/
│   ├── page.jsx      // /about ページ
│   ├── layout.jsx    // /about専用レイアウト
├── blog/
│   ├── [slug]/
│   │   ├── page.jsx  // 動的ルート: /blog/:slug
│   ├── page.jsx      // /blog ページ
├── globals.css
```

**静的ルートの作成**
各ディレクトリのpage.jsxをページに対応させる
URL
* app/page.jsx → /
* app/about/page.jsx → /about
```jsx:app/page.jsx
export default function HomePage() {
  return (
    <main>
      <h1>Welcome to the Home Page</h1>
    </main>
  );
}
```

**レイアウトの設定**
layout.jsxを使用してページ間で共有される要素を設定できる
* childrenは各ページのコンテンツが挿入される場所である
```jsx:app/layout.jsx
export default function RootLayout({ children }) {
  return (
    <html lang="en">
      <body>
        <header>
          <nav>
            <a href="/">Home</a>
            <a href="/about">About</a>
          </nav>
        </header>
        <main>{children}</main>
        <footer>© 2025 My App</footer>
      </body>
    </html>
  );
}
```

**動的ルートの作成**
動的ルートは[param]を使って設定する
* params.slugにはURLの値が渡される
* 例:/blog/post
```jsx:app/blog/[slug]/page.jsx
export default function BlogPost({ params }) {
  return (
    <main>
      <h1>Blog Post: {params.slug}</h1>
    </main>
  );
}
```

**データフェッチの方法**
サーバーコンポーネントを活用してデータを取得する
```jsx:app/blog/page.jsx
async function fetchPosts() {
  const res = await fetch('https://jsonplaceholder.typicode.com/posts');
  return res.json();
}

export default async function Blog() {
  const posts = await fetchPosts();

  return (
    <main>
      <h1>Blog Posts</h1>
      <ul>
        {posts.map((post) => (
          <li key={post.id}>{post.title}</li>
        ))}
      </ul>
    </main>
  );
}
```

**クライアントコンポーネントの利用**
クライアントサイドで動作するコンポーネントを作成するにはファイルの先頭に`"use client"`を追加する
App Routerでは、デフォルトがサーバーコンポーネントのため明示的にクライアントで指定する必要がある
```jsx
"use client";

import { useState } from "react";

export default function Counter() {
  const [count, setCount] = useState(0);

  return (
    <button onClick={() => setCount(count + 1)}>
      Count: {count}
    </button>
  );
}
```

**ネストしたレイアウト**
特定のページやグループに専用のレイアウトを追加することが可能
/about以下のページでこのレイアウトが適用
```jsx:app/about/layout.jsx
export default function AboutLayout({ children }) {
  return (
    <section>
      <h1>About Section</h1>
      {children}
    </section>
  );
}
```

## まとめ
App Routerの簡単な使用方法について学習しました。App Routerの大枠な部分を理解し`use Router`、`use params`などのフックスを利用したルーティング方法やAPI通信を実現したいと思います
JavaScriptでパスワード生成

### やりたいこと
記号大文字小文字数字を含むパスワード生成
```mkpass.html
<form name="makepass">
	<input type="button" value="exec" onclick="makePass()">
	<input type="text" size="1" id="passcount" style="text-align:center" value="10">
	<input type="checkbox" id="kigou" checked>記号あり
	<input type="text" size="15"  name="pass" readonly="readonly">
</form>

<script type="text/javascript">

window.onload = function () {
	makePass();
}

function makePass() {
	const passLen = document.makepass.passcount.value;
	let pass = "";
	const lower = "abcdefghijklmnopqrstuvwxyz";
	const upper = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
	const num = "0123456789";
	const kigou = "!#$%&=/*-+^{}()";
	let kigoucount,lowercount,uppercount;
	let aryIndex = [];
	let aryKigouNum = [];
	let aryLowerNum = [];
	let aryUpperNum = [];
	
	const checkKigou = document.makepass.kigou.checked;
	if (checkKigou == true) {
		kigoucount = Math.floor(Math.random() * ( passLen - 3 ) + 1); //kigoucountにパスワード長から他文字最低1引いた数ランダムな数値(1以上)を格納する
	}else {
		kigoucount = 0;
	}
	aryIndex = [...Array(Number(passLen))].map((_, i) => i); //aryIndexにパスワード長のインデックス(0~)を格納する
	lowercount = Math.floor(Math.random() * ( passLen - kigoucount -2 ) + 1);
	uppercount = Math.floor(Math.random() * ( passLen - kigoucount - lowercount -1 ) + 1);
	for(let i=0; i < kigoucount; i++){
		aryKigouNum.push(aryIndex.splice(Math.floor(Math.random() * aryIndex.length), 1)); //aryIndexからkigoucount個のランダム番目のインデックス数値を取り出す
	}
	for(let i=0; i < lowercount; i++){
		aryLowerNum.push(aryIndex.splice(Math.floor(Math.random() * aryIndex.length), 1));
	}
	for(let i=0; i < uppercount; i++){
		aryUpperNum.push(aryIndex.splice(Math.floor(Math.random() * aryIndex.length), 1));
	}
	for(let i=0;i<passLen;i++){
		if (aryKigouNum.find(element => element == i)) { //passのaryKigouNum番目の位置に記号を入れる
			pass += kigou.charAt(Math.floor(Math.random() * kigou.length));
		}else if (aryLowerNum.find(element => element == i)) {
			pass += lower.charAt(Math.floor(Math.random() * lower.length));
		}else if (aryUpperNum.find(element => element == i)) {
			pass += upper.charAt(Math.floor(Math.random() * upper.length));
		}else {
			pass += num.charAt(Math.floor(Math.random() * num.length));
		}
	}
	console.log("aryKigouNum:" + aryKigouNum);	//aryKigouNum:3,9
	console.log("aryLowerNum:" + aryLowerNum);	//aryLowerNum:2,1
	console.log("aryUpperNum:" + aryUpperNum);	//aryUpperNum:8,6,0
	console.log("aryIndex:" + aryIndex);		//aryIndex:4,5,7
												//     0123456789
	console.log("pass:" + pass);				//pass:Usf)00N8S*
	document.makepass.pass.value = pass;
}

</script>
```

### 参考にさせていただいた
https://qiita.com/suin/items/1b39ce57dd660f12f34b
Chrome拡張機能「WA Number Checker」を使用してWhatsApp番号を確認する方法

私たちは最近、WhatsApp番号のステータスをオンラインで無料で確認できるChrome拡張機能「WA Number Checker」を発表しました。

## Chrome拡張機能「[WA Number Checker](https://CheckNumber.AI)」を使用してWhatsApp番号を確認する手順

1. まず、Chromeウェブストアのウェブサイトにアクセスします: https://chromewebstore.google.com/detail/wa-number-checker-checknu/ancoloifckoalgpijpnmpolbdgegdogo をクリックし、「Chromeに追加」ボタンをクリックします。

English Version: [How to check WhatsApp number using Chrome Extension WA Number Checker](https://checknumber.ai/blog/chrome-extension-wa-number-checker)
Line Messaging APIで簡単なグループへの通知アプリを雑に作ってみた

## 環境
- Rails8
- Ruby 3.3.6

## 読んで欲しい人
- Line Messaging APIの概要をざっと知りたい人
- 過去の自分
  
## 作ったもの
Line Messaging APIを使用して、簡単な通知アプリを作りました

使い方

- Rails側で表示されているボタンを押す
- 任意のグループに通知が飛ぶ

以上です

## 具体的な手順

### Messaging APIの準備

#### LINEビジネスIDに登録する

前提としてLine Messaging APIを利用するには、公式アカウントが必要です
ここではフォームを作成して公式アカウントを作成するところまで行います

https://developers.line.biz/ja/docs/messaging-api/getting-started/#create-oa-line-business-id

#### 作成した公式アカウントのMessaging APIの利用を有効化する

公式アカウントが作成された次は、そのアカウントでMessaging APIの利用を許可する必要があります

https://developers.line.biz/ja/docs/messaging-api/getting-started/#step-one-enable-use-of-messaging-api


#### Developersコンソールにログイン、チャネルを確認する

チャネルとは、LINEプラットフォームが提供する機能を利用するための通信路のことです
今回は、Messaging APIの利用を許可した公式アカウントのチャネルが確認できるはずです

https://developers.line.biz/ja/docs/messaging-api/getting-started/#step-one-enable-use-of-messaging-apiLINE

#### チャネルアクセストークンの発行

チャネルを選択して、ログインしたらチャネルアクセストークンを発行してください
チャネルアクセストークンとは、Messaging APIを呼び出すときに使用するアクセストークンのことを指します、これがないとAPI通信が行えなえません

https://developers.line.biz/ja/docs/messaging-api/building-bot/#issue-a-channel-access-token

#### チャネルシークレットの確認

チャネルアクセストークン同様に、チャネルシークレットの確認を行います
アプリからアクセスする際の秘密鍵です

#### チャネルシークレット、チャネルアクセストークンをRails側で管理

Rails側でチャネルシークレット、チャネルアクセストークンを保存しておきます
今回はcredentialsを使用します

```
$ EDITOR="vi" bin/rails credentials:edit
```

```
line:
  line_channel_secret: チャネルシークレット
  line_channel_token: チャネルアクセストークン
```

#### Webhook URLを設定する

Webhook URLを設定します

httpだとWebhookを設定することができないので[ngrok](https://ngrok.com/)などを使用してhttpsのURLを生成して設定します

https://developers.line.biz/ja/docs/messaging-api/building-bot/#setting-webhook-url

#### 公式アカウントを友達追加、テスト用のグループに入れる

ここで作成した公式アカウントを自分のアカウントで友達追加して、テスト用（なんでも良いですが）グループに招待をしておきます

### Rails側の処理をする

#### line-bot-api gemをインストール

```gemfile
gem 'line-bot-api'
```

https://github.com/line/line-bot-sdk-ruby

#### Rails側でMessaging APIにリクエストを送る準備

今回はこんな感じで準備をしてみました

```routes.rb
Rails.application.routes.draw do
  root 'homes#show'
  resources :notifications, only: %i[create]
end
```

```notifications=controller.rb
class NotificationsController < ApplicationController
  def create
    client.push_message('※グループID', 
        {
            "type":"text",
            "text":"通知だよ"
        })
  end
end
```

```erb
<% #homes/show.html.erb %>
<h1>通知アプリ</h1>

<%= form_with url: notifications_path do |form| %>
  <%= form.text_field :name, class: "item-text-field" %>
  <%= form.submit "通知を送る", class: "submit-btn" %>
<% end %>
```

#### グループIDはどこで入手するのか？

ローカルのサーバーとngrokでhttpsのサーバーを構築した後で、公式ラインを追加したグループ内で実際にメッセージを飛ばしてみてください。

そうすると下記のようなレスポンスが帰ってくると思います

```
"source": {
  "groupId": "group_id",
  "type": "group"
},
```

こいつを※グループIDに指定したあげる感じです

## 感想

- そもそもlineにgroup_idがあるんだと思いました
- lineはいろんなアプリとコラボレートできると思うのでやっておいてよかった

## 参考

https://developers.line.biz/ja/reference/messaging-api/

https://qiita.com/prg_mt/items/b3238ebfae1a3df67cab
【React】 #7 年齢計算機アプリを作成

# はじめに
現在、Reactを習得するために、23種類のReactアプリ開発に取り組んでいます。
今回はその第7弾として、Reactで年齢計算機アプリを作成しました。

https://qiita.com/xYasi/items/0e223b8be80006ef9933

# 要件
一般的な年齢計算機アプリの仕様を満たすことを目標にしました。
具体的には、以下の要件を満たすことを目指しています：

- ユーザが「西暦」「和暦」及び「誕生月」「誕生日」を入力して年齢を算出
- 「小学校」「中学校」「高校」「4年生大学」卒業年を表示

# 作成したアプリのイメージ
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3947973/1f10fb00-c582-3ec3-536d-6846990e67be.jpeg" width=100%>

# アプリ紹介動画
<iframe width="200" height="450" src="https://www.youtube.com/embed/fOjRxEuPAQQ" title="React Age Calculator" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" referrerpolicy="strict-origin-when-cross-origin" allowfullscreen></iframe>

# 利用技術
- React
- Vite
- TypeScript
- Tailwind CSS
- date-fns

# 意識したポイント
## 日付計算はdate-fnsを利用
年齢計算はdate-fnsのライブラリを採用しました。
日付の比較、計算などが直感的にわかりやすいので、使いやすかったです。

```typescript:ageUtils.ts
import { differenceInCalendarYears, isBefore } from "date-fns";

export const calculateAge =  (today: Date ,birthDate: Date): { age: number; countAge: number } => {
   const countAge = differenceInCalendarYears(today, birthDate);

   const birthDateThisYear = new Date(today.getFullYear(), birthDate.getMonth(), birthDate.getDate());
   const age = countAge - (isBefore(today, birthDateThisYear) ? 1 : 0);

   return {age, countAge};
}
```

# useActionStateを使用
前回同様にstateの保持をReact19のuseActionStateを利用しました。
アクション実行時に自動的にステートと実行状態を更新してくれるので、
非常に便利です。

```tsx:AgeCalc.tsx
  const [state, formAction, pending] = useActionState(
    calcurateAge,
    initialState
  );

  return (
    <main className="flex flex-col justify-start items-center constainer mx-auto px-8 md:px-16 lg:px-24 my-24 gap-4">
      <AgeCalcForm formAction={formAction} pending={pending} error={state.error} />
```
```typescript:actions.ts
export async function calcurateAge(
  prevState: State,
  formData: FormData
): Promise<State> {
   const era = formData.get("era") as string;
   const year = formData.get("year");
   const month = formData.get("month") as string;
   const day = formData.get("day") as string;

   ...
}
```

# Github
GitHubにコードをアップロードしていますので、よかったら確認してみてください。
https://github.com/yasi1989/react-age-calc
【Fish】viモードでヤンクしたテキストをクリップボードに保存する

## 設定方法

`~/.config/fish/config.fish`に以下のように記述するとviモードでヤンクしたテキストがクリップボードに保存されるようになります。

```shell:config.fish
bind yy fish_clipboard_copy
bind Y fish_clipboard_copy
bind p fish_clipboard_paste
```

## 参考

https://github.com/fish-shell/fish-shell/issues/4028#issuecomment-1791599167

https://fishshell.com/docs/current/cmds/fish_clipboard_copy.html
【Ruby 3.3.5 インストール失敗時の解決法】BUILD FAILEDエラーと xcode-select --install での修正

# はじめに
Ruby環境の構築中に rbenv install 3.3.5 を実行したとき、以下のようなエラーが表示されることがあります。
```
(base) -zsh ~ % rbenv install 3.3.5
ruby-build: using openssl@3 from homebrew
==> Downloading ruby-3.3.5.tar.gz...
-> curl -q -fL -o ruby-3.3.5.tar.gz https://cache.ruby-lang.org/pub/ruby/3.3/ruby-3.3.5.tar.gz
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100 21.1M  100 21.1M    0     0  10.4M      0  0:00:02  0:00:02 --:--:-- 10.4M
==> Installing ruby-3.3.5...
ruby-build: using libyaml from homebrew
ruby-build: using gmp from homebrew
-> ./configure "--prefix=$HOME/.rbenv/versions/3.3.5" --with-openssl-dir=/opt/homebrew/opt/openssl@3 --enable-shared --with-libyaml-dir=/opt/homebrew/opt/libyaml --with-gmp-dir=/opt/homebrew/opt/gmp --with-ext=openssl,psych,+

BUILD FAILED (macOS 15.1.1 on arm64 using ruby-build 20241225.2-3-g068c4047)

You can inspect the build directory at /var/folders/t_/1z86vw2d6dn88v7lrc76_7pc0000gn/T/ruby-build.20250112232158.7164.VkLYpv
See the full build log at /var/folders/t_/1z86vw2d6dn88v7lrc76_7pc0000gn/T/ruby-build.20250112232158.7164.log
```
このエラーの原因として頻繁に挙げられるのが、Command Line Tools (CLT) for Xcodeの未インストール または 設定の破損です。このツールが不足していると、ruby-build に必要なCコンパイラが使用できなくなり、Rubyのインストールに失敗します。本記事では、「このエラーが出たときになぜ xcode-select --install が必要なのか」 を詳しく説明します。

## 1. エラーの原因
ruby-build は、Rubyのインストール時にCコンパイラや関連するビルドツールを利用します。これらのツールは Command Line Tools (CLT) に含まれており、特に以下のような状況で問題が発生します。

よくあるエラーの例
```
checking whether the C compiler works... no
configure: error: C compiler cannot create executables
```

このエラーの原因は、clang や xcrun などのコンパイラツールのパスが無効か、ツールそのものが不足しているためです。

## 2. なぜ xcode-select --install が必要か
xcode-select --install は、Command Line Tools をインストールし、以下の重要なコンパイラツールを提供します。

| ツール | 説明 |
|:-|:-|
| clang  |C言語コンパイラ。Rubyや他のライブラリをビルドする際に必要   |
| make  |ビルドのプロセス管理ツール   |
| xcrun  |macOSの開発者ツールを管理   |

xcode-select --install を実行しないと、Rubyをビルドするために必要なこれらのツールが使えないため、インストールが失敗します。

## 3. 解決手順
以下の手順で問題を解決できます。

### 1. Command Line Tools のインストール
```
xcode-select --install
```
インストールが始まり、完了するまで待ちます。

### 2. Rubyの再インストール
```
rbenv install 3.3.5
```

### 3. インストールが成功することを確認
```
ruby -v
```

### 4. 追加のトラブルシューティング
エラーが続く場合は、パスのリセットを行います。
```
sudo xcode-select --reset
```

# まとめ
このエラーは コンパイラツール不足 に起因するものであり、xcode-select --install で解決できます。エラーメッセージが直接 xcrun と言及していなくても、内部でこのツールが使用されている点に注意してください。これでRuby 3.3.5のインストールがスムーズに進むはずです！
A10 Thunder ロードバランサ設計構築ガイド

# 本ガイドについて

本ガイドは、A10 ネットワークス社の Thunder シリーズの設計構築を行うエンジニアのためのガイドです。

A10 Thunder シリーズは F5 ネットワークス社の BIG-IP と並んで良く利用されるロードバランサ製品です。BIG-IP と比較してコンフィグがシンプルであり、CLI が Cisco のネットワーク機器と似たような仕組みのため設定しやすいという点で今後も多く利用されることが予想されます。

本記事では Thunder シリーズの設計・構築に役立つ情報をまとめています。
情報は随時更新していきます。

# 基礎知識

https://kagechiku.com/a10-thunder-manual/

https://kagechiku.com/a10-thunder-upgrade/

# ネットワーク系設定

https://kagechiku.com/a10-thunder-interface/

# 冗長化設定(VRRP-A)

https://note.com/shadowgarden_org/n/neaf1fe384ecf

# ロードバランサ

https://kagechiku.com/a10-thunder-lb/

# ヘルスチェック

https://kagechiku.com/a10-thunder-healthcheck/

# aFleX

https://kagechiku.com/a10-thuder-accesslog/
Chrome で「画面をキャスト」をすると真っ暗になる現象を解決する方法 (Mac)

# Chromeで「画面をキャスト」すると真っ暗になる現象を解決する方法 (Mac)

## はじめに

こんにちは。

**「Chromeのキャスト機能でタブのキャストはできるけど、画面全体をキャストすると真っ暗になって映らない…！」**  
こんな症状にお困りではありませんか？

筆者の環境（**macOS Sequoia 15.1.1 + Chrome（現時点の最新版）**）でも同様の現象が起き、  
**「ハードウェア アクセラレーションをオフにする」** ことで、問題なく表示できるようになりました。

ググっても解決方法が日本語では見つからなかったので備忘録として記事化しました。
なお本記事はChatGPT o1を使って執筆しました。

---

## 症状の詳細

- **「タブをキャスト」** は正常に動作する
  - YouTubeやブラウザ上のサイトは問題なくテレビやディスプレイに映せる
- **「画面をキャスト」** を選択すると、キャスト先デバイス（Chromecastなど）に接続はされるものの、  
  **キャスト先の画面が真っ暗のまま表示されない**
- キャストを一度解除しても改善せず、Chromeを再起動しても症状が続く

この状態だと、プレゼンなどでMacの画面をそのまま映したい時に非常に困ってしまいますよね。

---

## 環境

- **OS**: macOS Sequoia 15.1.1  
- **ブラウザ**: Google Chrome（現時点での最新版）  

他のmacOSバージョンやChromeのバージョンでも同様の現象が起こる可能性があります。

---

## 対処法：ハードウェア アクセラレーションをオフにする

実際に筆者の環境では、以下の手順で **「ハードウェア アクセラレーションをオフ」** にしたところ、  
**「画面をキャスト」** も正常に表示されるようになりました。

1. **Chromeの設定を開く**  
   - 右上の「…」(縦の点が3つ) → 「設定(Settings)」  
   - またはアドレスバーに `chrome://settings/` と入力して直接アクセス

2. **「システム(System)」を表示**  
   - サイドメニューや画面下の「詳細設定(Advanced)」などから「システム」を探します

3. **「ハードウェア アクセラレーションが使用可能な場合は使用する」をオフにする**  
   - デフォルトではオンになっているため、オフに切り替えます
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/37048/7231c9e8-cd7d-07d0-8033-7cc46a9eaba7.png)

4. **Chromeを再起動**  
   - 設定を反映させるため、必ずChromeを再起動しましょう

これで再度 **「画面をキャスト」** を試すと、真っ暗にならずにきちんと表示されるようになるはずです。

---

## なぜこれで解決するのか？

「ハードウェア アクセラレーション（HA）」とは、**CPUではなくGPUのパワーを使ってブラウザの描画などを高速化する技術**です。通常は有効にしておくとパフォーマンスが向上しますが、OS・ブラウザ・GPUドライバの組み合わせによっては不具合の原因になるケースがあります。

キャスト機能は、**映像・音声の処理やエンコード**を行う際にGPUアクセラレーションの恩恵を受ける部分があります。しかし、特定の環境下ではこの部分が正しく動作せず、結果として **画面キャストがうまく描画されず「真っ暗」になる** 現象に繋がることがあるようです。

---

## 他に試してみると良いこと

ハードウェア アクセラレーションをオフにしても改善しない場合は、以下の方法も検討してみてください。

1. **Chromeの再インストール**  
   - バージョンが壊れている、あるいは更新の過程で何かおかしくなっている可能性があります。  
   - アプリを一旦削除（設定ファイルごと） → 再インストールを行います

2. **OSを最新バージョンにアップデート**  
   - Mac側のアップデートで、ドライバやグラフィックス周りの不具合が修正される場合があります

3. **拡張機能やプラグインの無効化**  
   - Chromeの拡張機能がキャスト機能と干渉しているケースもあるため、一旦全てオフにして試します

4. **他のブラウザで試す**  
   - 一時的にMicrosoft EdgeなどのChromium系ブラウザでキャストをテストしてみると、Chrome特有の問題なのかどうかを切り分けられます

---

## まとめ

- Mac + Chromeで **「タブはキャストできる」のに「画面全体をキャストすると真っ暗」** になる場合は、  
  **「ハードウェア アクセラレーションをオフにする」** ことで解決できる可能性が高いです
- HAをオフにするだけであっさり直る場合も多いので、まずは気軽に試してみましょう
- それでもダメな時は、Chrome/OSの再インストール・アップデートや拡張機能の無効化など、他の手段で原因を切り分けます

キャスト機能は便利な反面、OS・ブラウザ・ネットワーク・ハードウェアが複雑に絡み合うため、トラブルの原因の切り分けが難しいですよね。この記事が同じ問題にお悩みの方のヒントになれば幸いです。

もし他にも有効な対処法があれば、ぜひコメントや編集リクエストで教えてください！

以上、**Mac（macOS Sequoia 15.1.1） + Chrome最新版環境**で、**「画面をキャスト」が真っ暗になる問題**を解決したときのメモでした。

---

ご覧いただきありがとうございました。