OmniAICreator/Qiita-1.07M huggingface dataset:
いまさら「令和何年？」って調べない

# ちょこっと業務を簡略化したい

　この記事では、ちょこっと効率化させたいことをプログラミングやツールをつかって解決していきます
ちょこっと削減した時間を、もっと人生楽しくなることに使いましょう！

# 今年令和何年？　何どし？
「今年令和何年？」と検索していないでしょうか
わからなくなりますよね
こんな時はこれで解決です！






# python(tkinter)で解決してみた

<環境>
🖥 Mac
🐍 python 3.12.5
🏆 VSCode


※YouTube動画です。音量に気をつけてください

[![YouTube動画](https://img.youtube.com/vi/1rZV5SbAVVM/hqdefault.jpg)](https://youtube.com/shorts/1rZV5SbAVVM?feature=share)


<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3636287/c97dcbb5-8765-fb32-58d8-8df0ce716b8f.png" width=50%>


# 全体コード

<details><summary>全体コードはこちら</summary>

```python:python
import tkinter as tk
from tkinter import ttk
from datetime import datetime

# 干支リスト
eto_list = ["🐭子", "🐮丑", "🐯寅", "🐰卯", "🐲辰", "🐍巳", "🐴午", "🐑未", "🐒申", "🐓酉", "🐕戌", "🐖亥"]

# 情報計算関数
def calculate_info():
    try:
        year = int(year_entry.get())
        eto = eto_list[(year - 4) % 12]
        if year >= 2019:
            era = f"令和{year - 2018}年"
        elif year >= 1989:
            era = f"平成{year - 1988}年"
        elif year >= 1926:
            era = f"昭和{year - 1925}年"
        else:
            era = "大正以前"
        today = datetime.now()
        weekday = today.strftime("%A")
        today_str = today.strftime("%Y年%m月%d日")
        result_label.config(
            text=f"🌸 {year}年は 🌸\n\n"
                 f"① {eto}どし\n"
                 f"② {era}\n"
                 f"③ 今日は {today_str}（{weekday}）"
        )
    except ValueError:
        result_label.config(text="⚠️ 正しい年を入力してください！ ⚠️")

# アプリウィンドウの設定
root = tk.Tk()
root.title("🌸 年情報アプリ 🌸")
root.geometry("400x450")
root.config(bg="#fffbf0")

# タイトルラベル
title_label = tk.Label(
    root,
    text="✨ 知りたい年を入力してください ✨",
    font=("Helvetica", 16, "bold"),
    bg="#fffbf0",
    fg="#d35d6e"
)
title_label.pack(pady=20)

# フレームで中央整列
frame = ttk.Frame(root)
frame.pack(pady=10)

# 入力ボックス
year_entry = ttk.Entry(frame, font=("Helvetica", 14), width=15)
year_entry.grid(row=0, column=0, padx=5)

# 実行ボタン
calc_button = ttk.Button(
    frame,
    text="調べる",
    command=calculate_info,
    style="Custom.TButton"
)
calc_button.grid(row=0, column=1)

# 結果表示ラベル
result_label = tk.Label(
    root,
    text="",
    font=("Helvetica", 14),
    bg="#fffbf0",
    fg="#5d6e7d",
    wraplength=350,
    justify="center"
)
result_label.pack(pady=20)

# スタイルの設定
style = ttk.Style()
style.configure(
    "Custom.TButton",
    font=("Helvetica", 14),
    padding=5,
    foreground="#ffffff",
    background="#d35d6e",
    borderwidth=0,
)
style.map(
    "Custom.TButton",
    background=[("active", "#c14a5c")]
)

# アプリ起動
root.mainloop()


 ```
 </details>


## 💙最後に豆知識

令和の場合、「2025」→ 2＋5＝7　令和7年とのことです
ぜひ活用して見てください

見ていただき、ありがとうございます😍
【AWS SAP】AppSyncとは

# AppSyncとは
GraphQL API構築・管理サービスです。

## もう少し具体的に
**AWS AppSync**とは、GraphQL APIの構築・管理を支援するフルマネージドサービスです。GraphQLを用いることで、クライアントは単一のエンドポイントから必要なデータのみを効率的に取得・操作できます。AppSyncは、AWSのデータソース（DynamoDB、RDS、Lambda、OpenSearchなど）や外部APIと統合し、柔軟でスケーラブルなデータ操作を可能にします。また、リアルタイム機能やオフライン同期もサポートしており、接続状況に依存しないアプリケーションの構築が容易です。セキュリティ面では、CognitoやIAM、APIキーを使った認証が統合されており、安全なデータアクセスを提供します。これにより、効率的なAPI設計と運用が実現します。

## AppSyncがあると何が便利か
**GraphQL API**を簡単に構築ができます。

## AppSyncがないと？
**GraphQL API**を手動で構築（GraphQLサーバーの構築、データソースとの連携、認証機能やリアルタイム更新の実装など）をする必要があります。

## 何が実装できる？
- **リアルタイムチャット:**
    - メッセージをGraphQLで送受信、全クライアントへ通知
- **スコアボード更新:**
    - DynamoDB連携でスコア保存、リアルタイム反映
- **プレイヤーマッチメイキング:**
    - クエリで条件検索、サブスクリプションで結果配信
- **ゲーム進行状態同期:**
    - セッション状態をGraphQLで管理、全プレイヤーに即時共有
- **通知システム:**
    - DynamoDBトリガーでイベント生成、リアルタイム通知

:::note info
ゲームのセッションデータ管理は、リアルタイム性ならAmazon ElastiCache、永続化が必要ならAmazon DynamoDBが適切です。
:::

## 「AppSync」の名前の由来は？
アプリケーション（App）とデータの同期（Sync）を効率的に行う機能に由来しています。

## そもそも、GraphQLとは
GraphQLとは、クライアントが必要なデータをクエリで指定して取得・操作できるAPI設計仕様および言語です。
Facebookが2012年に開発し、2015年にオープンソース化され、**効率的なAPI設計として普及**しました。

### 何が効率的なのか
GraphQLは、必要なデータのみ取得できる柔軟なクエリ構造と、単一エンドポイントで複雑なデータ操作が可能な点が効率的です。

#### もう少し具体的に
GraphQLは、クライアントがクエリで必要なデータやフィールドを正確に指定できるため、REST APIのように過剰なデータ取得や不足取得が発生しません。また、**単一エンドポイントで異なるデータ操作が可能**で、ネスト構造のデータも一度のリクエストで取得できます。さらに、型定義によってデータ構造が明確化され、クライアントとサーバー間の整合性が保たれるため、APIの設計・運用が効率化します。

#### GraphQLはエンドポイントが単一！
```mermaid
flowchart LR
    subgraph GraphQL
        direction TB
        Client2[クライアント] --> GAPI[単一GraphQLエンドポイント]
        GAPI --> DB4[データベース1]
        GAPI --> DB5[データベース2]
        GAPI --> DB6[データベース3]
    end
```
#### REST APIはデータベース毎に必要...
```mermaid
flowchart LR
    subgraph REST
        direction TB
        Client1[クライアント] --> API1[APIエンドポイント1]
        Client1 --> API2[APIエンドポイント2]
        Client1 --> API3[APIエンドポイント3]
        API1 --> DB1[データベース1]
        API2 --> DB2[データベース2]
        API3 --> DB3[データベース3]
    end
```

## REST APIを使うくらいならGraphQL？
用途によりますが、複雑なデータ取得や操作が必要ならGraphQLが効率的です。単純な操作ならREST APIも有効です。

## バックエンドで対応しているデータソースは？
- AWS Lambda
- Amazon DynamoDB
- Amazon Elasticsearch
- Amazon Aurora Serverless
- HTTPエンドポイント
など

## GraphQLはオワコン？
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2746730/190433b2-114d-dcb1-28d0-97f3ca7420c8.png)
GraphQLが「オワコン」と言われる理由は、導入や運用が複雑で、用途によってはRESTの方が適している場合があるためです。
AndroidからMacにUSBテザリングするまで

# 筆者について

- もうすぐ卒業の高校３年生（誰を参考にしようかな）

# 本編

最近の僕の携帯は訳ありで検証用のAndroidがモバイルデータ通信をしているのですfが、ふとMacbookからそちらの方にUSBテザリングを使いたいなと思いまして、今回それをやってみることにします。今回、これをするにあたり、以下の記事を参考にさせていただきました。

https://zenn.dev/ddd3h/articles/eade04d329fb99

## セキュリティの設定

先にセキュリティレベルを避けなければいけません。とりあえず、リカバリーモードでMacを再起動し、ターミナルで以下のコマンドを入力します。

csrutil enable --without kext

あとは、GUIでも設定をする必要があります。。以下のURLの通りにしてください。
Nucleo-F446RE端子について

# はじめに

　NHK高専ロボコンが終わり、一関高専機械技術部1,2年生は交流ロボコン2025に参加することとなりました。
そこで使用する制御基板を作成したときの備忘録です。

# F446REについて
　STM32-Nucleoボードの一つであるF446RE。STマイクロエレクトロニクスが販売しているArm社のCortexという32bitのマイコンです。

　ロボット制御で使用するにあたってserialや、PWMとして使うピンを決めます。
まずはユーザーマニュアル「6.9 Solder bridges」などを踏まえて、使用する際に操作が必要なピンをまとめました。

ユーザーマニュアル↓
> https://www.st.com/resource/en/user_manual/um1724-stm32-nucleo64-boards-mb1136-stmicroelectronics.pdf

参考にさせていただいたサイト↓
> https://keiorogiken.wordpress.com/2018/12/08/nucleo-f446re/

| Pin | デフォルト | GPIOとして使うときの操作 |
| :--: | :--: | :--- |
| PC14, PC15 | 外部素子と接続 | SB48, SB49をON. R34, R36をOFF |
| PC13 | B1 push buttonと接続 | SB17をOFF<br>(B1 push buttonが使えなくなる). |
| PA5 | Green user LED LD2と接続 | SB21をOFF. <br>(OFFにしなくてもGPIOとしては使用できるがLチカする) |
| PA2, PA3 | STM32F103CBとUSARTで接続 | SB13, SB14をoff. SB32, SB63をON.<br>(Mbedで開発するなら使わないほうが良いらしい) |
| PB3 | TRACESWO機能,<br>その他機能に接続 | GPIOやPWM出力に使えるが、混乱を避けるため使わないほうが良い |
| PH0, PH1 | クロック入力に使用 | PH_1はGPIOとして使用可。<br>両方使うにはSB54, SB55をON. SB16, SB50をOFF |
| PA13, PA14 | morphoコネクタ, <br>SWDに接続 | デバッグで使用されるため、使用は避けるべき |

　ざっと書きましたがここにあるものを注意して作り、実験したところ、筆者は問題なく動作しました。

# おわりに
　今回は、Nucleo-F446REを使用する際のピンについてまとめました。
このように他のマイコンでも注意点があるので面倒くさがらず、調べたり、ユーザーマニュアルを読んだりして、しっかり動く基板作成を頑張っていきましょう。

<br>

　一関高専機械技術部ではJLCPCBのスポンサーシップに参加させて頂きました。
JLCPCBは、基盤制作、部品実装、３Dプリントなどのサービスを提供している会社です。

![jlcpcb.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3969931/101928b5-7664-f009-bc95-e5d44ad7982c.png)

JLCPCBホームページ
https://jlcpcb.com/jp

スポンサーシップ
https://jlcpcb.com/help/article/152-how-to-apply-for-free-pcb

　JLCPCBさんには毎度、作成した基板の代金を割り引いていただいております。この場を借りてお礼申し上げます。

　最後まで読んでいただきありがとうございます。
[感想]自走プログラマー ～Pythonの先輩が教えるプロジェクト開発のベストプラクティス120

エンジニア転職をした私が、本書のコード実装を読みもう少し早く知っておきたかったことや実際に言われた事等を記載し今後の糧にする。

## 1つのテストメソッドでは1つの項目のみ確認する
1つのテストメソッドに複数のテスト項目を詰め込んでしまっていたため、実際に「1つのメソッドには1つの項目にしてください」と指摘されました。

## テストケースは準備、実行、検証に分割しよう
(自分で書いた)テストコードがどこまでテストの準備で、どこからテスト対象の実行か区別ができない事がありました。なので、準備、実行、検証に分けてコメントを入れるのはとても分かりやすい。まぁ、自分で書いたのに区別できないのはどうかと思いますが...

## 公式ドキュメントを読む
これが一番重要です！調べる時に公式ドキュメンを読む事の重要性を痛感しました。英語が読めないから公式ドキュメントを避けていた自分にとって、大きな教訓でした。[私たちはどうして公式ドキュメントが読めないのか？](https://qiita.com/hiraike32/items/f0a211cceb0ecc516b6c)という記事が参考になりました。

## 実装方針を相談しよう
コードレビューを依頼した際に、実装方法が間違っている事がありました。仕様の確認漏れ等で起きてしまいました。実装を始める前に方針を相談する事で認識のずれに気づく事ができるため、言語化して相談する事は大切です。

## まとめ
以上が、本書のコード実装を読んでもう少し早く知っておきたかったことや実際に言われた事です。
Gitコマンドまとめ

gitコマンドの備忘録です。
※オプションはgit ~ -h で確認ができるので省略しています。

### 最重要コマンド
|コマンド名             | オプション         | 用途                                     |
|:---------------------|:------------------|:--------|
| git add              |[スペース.]全量選択 | ステージされていないファイルをステージングへ |
| git commit           |                   | ステージされているものをコミット           |
| git push [ブランチ名] |                   | コミットしたものをgit上に送信              |
| git checkout         |                   | ブランチ切り替え                          |
| git pull [ブランチ名] |                   | リモートのブランチを今のブランチに取り込む  |

### 覚えておくと便利
|コマンド名| オプション | 用途 |
|:-|:-|:-|
| git status |  | 変更されたファイル名の確認(赤→notステージ, 緑→onステージ) |
| git diff [ファイル名] |  | 変更されたファイル名の内容の確認 |
| git remove |  | ステージされたものを元に戻す |
| git branch |  | ブランチ名を表示|

### 今後覚えていきたいね
|コマンド名| オプション | 用途 |
|:-|:-|:-|
| git stash |  | ステージングされていないファイルを消す |
| git pop |  | stashの処理を元に戻す |
| git soft [commit id]|  | [commit id]を復元する。(現在の変更内容は保持)  |
| git head [commit id]|  | [commit id]まで戻る。(現在の変更内容は保持しない) |
| git log |  | 現在のブランチの履歴確認 |
| git history |  | 全ブランチの履歴確認 |
IDA Freeのインストール方法

# 最初に

逆アセンブラツールであるIDAは基本機能であれば、無料で使うことができます。

そのインストールをした際の手順を備忘録として整理しました。



# インストール手順


おおまかな流れは以下です。

1. インストーラとLicense Keyのダウンロード
2. インストールとLicense Keyの配置



## 1. インストーラとLicense Keyのダウンロード

Hex-Rayのダウンロードページにアクセス

https://hex-rays.com/ida-free


Download IDA Freeをクリック

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2152468/d6c6f2ef-ac12-6b39-ade7-dd72156af8d1.png)


サインインを求められるので、アカウントを作ってサインインするか、GoogleかGitHubのアカウントでサインイン

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2152468/6c40ba17-ae3c-0851-3df8-ce49af05f4ff.png)


Download centerで、IDA Freeとあるところから利用するOSに合わせてインストーラをダウンロード

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2152468/ef32af16-0257-135e-5af2-27abb254fc31.png)


キャプチャを取り損ねましたが、インストーラのダウンロード後にLicense Keyの取得画面があるので、画面の指示に従い取得して、左上のLicensesのタブからダウンロードしておきます


## 2. インストールとLicense Keyの配置

ダウンロードしたインストーラを実行して、基本的にデフォルト値でインストールする。

インストールの最後にLicense Keyを入れてください、という画面がでてきます。
このLicense Keyを格納しないとIDAが使えないしくみになっています。

![IDA_スクリーンショット 2025-01-05 080409.jpeg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2152468/095aab09-9595-c225-2d80-664f9bbca9d3.jpeg)

私は
`C:\Program Files\IDA Free 9.0`
に、IDAをインストールしていましたが、以下にダウンロードしたLicense Keyを格納したら、動作しました
`C:\Users\********\AppData\Roaming\Hex-Rays\IDA Pro`





# 最後に

CTFの問題で使うためにインストールはしましたが、細かい使い方はこれから整理してきます！
【GitHubActions】matrix と workflow_dispathの合わせ技

## 概要

GitHubActionsを使用して、実行するコンポーネントを動的に選択できるワークフローの作成方法を紹介します。`workflow_dispatch`イベントと`matrix`戦略を組み合わせることで、柔軟で効率的なCI/CDパイプラインを構築できます。

## ワークフロー例

```yaml
name: exec matrix component

on:
  workflow_dispatch:
    inputs:
      components:
        description: '実行するコンポーネントを選択（カンマ区切りで複数可）'
        required: true
        type: choice
        options:
          - action1
          - action2
          - action3
          - action1,action2
          - action1,action3
          - action2,action3
          - action1,action2,action3
      environment:
        description: '実行環境を選択'
        required: true
        type: choice
        options: [development, staging, production]
      debug_mode:
        description: 'デバッグモードを有効化'
        required: true
        type: boolean
        default: false
      version:
        description: 'バージョン番号（例: 1.2.3）'
        required: true
        type: string

jobs:
  run-component-actions:
    runs-on: ubuntu-latest
    strategy:
      matrix:
        component: ${{ fromJson(format('[{0}]', github.event.inputs.components)) }}

    steps:
    - uses: actions/checkout@v4.1.7

    - name: ${{ matrix.component }} アクション実行
      uses: ./component/${{ matrix.component }}
      with:
        environment: ${{ github.event.inputs.environment }}
        debug_mode: ${{ github.event.inputs.debug_mode }}
        version: ${{ github.event.inputs.version }}
        component_param1: value1
        component_param2: value2
```

## ワークフローの詳細説明

1. **`workflow_dispatch`イベント**: GitHubのUI上でワークフローを手動実行できるようにします。

2. **動的な入力パラメータ**:
   - `components`: 実行するコンポーネントを選択（複数選択可能）
   - `environment`: 実行環境の選択（開発/ステージング/本番）
   - `debug_mode`: デバッグモードの有効/無効(ワークフローの詳細なログが見ることができます)
   - `version`: バージョン番号の指定

3. **`matrix`戦略**: 選択されたコンポーネントごとに並行ジョブを実行します。`fromJson`と`format`関数を使用して、選択されたコンポーネントをJSON配列に変換します。

4. **コンポーネント実行**: 各ジョブで`./component/`ディレクトリ内の指定されたコンポーネントアクションを実行します。

## パラメータの活用

- `environment`: デプロイ環境や環境固有の設定を選択
- `debug_mode`: 詳細なログ出力や特定のデバッグ機能を有効化
- `version`: 特定バージョンのコードデプロイやバージョン管理に使用
- `component_param1`, `component_param2`: コンポーネント固有のパラメータ設定

## ワークフローの利点

1. **柔軟性**: 必要なコンポーネントのみを選択して実行可能
2. **効率性**: 並行実行による時間短縮
3. **拡張性**: 新コンポーネントの追加が容易
4. **カスタマイズ性**: 実行時にパラメータを調整可能

## 使用シーン

このワークフローは、マイクロサービスアーキテクチャや複数の独立したコンポーネントを持つプロジェクトで特に有効です。

開発者は特定のコンポーネントのみをテストしたり、デプロイしたりすることができ、CI/CDプロセスの効率を大幅に向上させることができます。

## まとめ

GitHubActionsの`workflow_dispatch`と`matrix`戦略を組み合わせることで、柔軟で効率的なCI/CDパイプラインを構築できます。

このアプローチにより、開発チームは必要に応じて特定のコンポーネントを選択的に実行し、開発プロセスを最適化することができます。
Go言語(プログラミング)入門③ｰ2

## for文による繰り返し処理
forのあとに「繰り返しで使う変数の初期化」と「繰り返しを続ける条件」、「繰り返すたびに実行する処理の処理」を;で区切って書く。
以下のコードでは、まず変数iを0で初期化し次に「変数iが10より小さい間」を繰り返しの条件とし、そのあとに「i++」と記載している。これは繰り返すたびにiに1ずつ足していくという意味
~~~
for i := 0; i < 10; i++{
    fmt.Println(i)
}
\\
0
1
2
3
4
5
6
7
8
9
と出力される。
~~~

## continue文で次の繰り返しに進む処理をつくる
continueは、処理の途中で次の繰り返し処理に進むときに使う。例えば、先ほどのfor文の中で、iが3のときに「continue」と表示する処理を書きたいときは以下のように記載する。

~~~
for i := 0; i < 10; i++{
    if i == 3{
        fmt.Println("continue")
        continue                //continue文を書く
    }
    fmt.Println(i)
}
\\
0
1
2
continue
4
5
6
7
8
9
と出力される。
~~~

## break文で繰り返しを途中で抜ける
繰り返しを中断してfor文から抜けたいときはbreak文を用いる。
上記のfor文の中でiが5よりも大きいときに繰り返し処理を抜ける、というふうにしたい場合は以下のように記載する。

~~~
for i:= 0; i < 10; i++{
    if i == 3 {
        fmt.Prinln("continue")
        continue
    }

    if i > 5 {
        fmt.Println("break")
        break 　　　　//break文を書く
    }
    fmt.Prinln(i)
}
\\
0
1
2
continue
4
5
break
と出力される。
~~~
breakが表示されたあとはfor文のループから抜けているのでそのあとの繰り返し処理が実行されることはない。

## for文の省略記法
for文の「変数の初期化」と「繰り返すたびに実行する処理」は省略が可能。
~~~
sum := 1　　　　//変数の初期化
for sum < 10 ;{
    sum += sum　　//繰り返し時の処理
    fmt.Println(sum)
}
fmt.Println(sum)
//
2
4
6
8
16
16
と表示される
~~~
上記のように、変数の初期化をfor文の前で、繰り返し時の処理をfor文の中に書くことで省略記法を行える。

## rangeの使い方
for文と一緒に使うことができ、便利な文法としてrangeがある。
「python」「go」「java」という文字列を要素にもつスライスを変数lに入れて、for文で文字列の中身を取り出していく処理を考える

~~~
l := []string{"python","go","java"}

for i:= 0; i<lemn(l); i++ {
fmt.Println(i, l[i])
}
//
0 python
1 go
2 java
と出力される
~~~
上記の処理はrangeを使用するともっと楽に書くことができる。forのあとに「i, v := range l」と書くと変数iとvにそれぞれlのインデックス番号と中身を代入することができる。

~~~
l := []string{"python","go","java"}
for i, v := range l {
    fmt.Println(i, v)
}
//
0 python
1 go
2 java
と出力される
~~~
for文の中でインデックス番号を処理に使わないときはiを_に置き換えると、スライスの値だけを取り出すことができる。
~~~
l := []string{"python","go","java"}
for _, v := range l {
    fmt.Println(i, v)
}
//
python
go
java
と出力される
~~~

次のようにマップのキーと値をrangeで取り出すこともできる。

~~~
m := map[string]int{"apple":100,"banana":200}

for k,v := range m{
    fmt.Println(k,v)
    }
//
apple 100
banana 200
と出力される
~~~

マップのキーだけを取り出したいときは二個目の引数を記載しない。
~~~
m := map[string]int{"apple":100,"banana":200}

for k,v := range m{
    fmt.Println(k)
    }
//
apple 
banana 
と出力される
~~~

バリューだけ出力したい場合は、kを_にしてvだけ出力させるように指定する。
~~~
m := map[string]int{"apple":100,"banana":200}

for _,v := range m{
    fmt.Println(v)
    }
//
100
200
と出力される
~~~

rangeはスライスや、マップを扱う時にとても便利。

## 学習に使用した教材

・『入門】Golang基礎入門 + 各種ライブラリ + 簡単なTodoWebアプリケーション開発(Go言語)』M.A EduTech
https://www.udemy.com/course/golang-webgosql/?utm_medium=udemyads&utm_source=bene-msa&utm_campaign=responsive&utm_content=top-1&utm_term=general&msclkid=81e2f24a32cc185d275d953d60760226&couponCode=NEWYEARCAREERJP

・『シリコンバレー一流プログラマーが教える Goプロフェッショナル大全』酒井 潤 (著)
https://www.amazon.co.jp/%E3%82%B7%E3%83%AA%E3%82%B3%E3%83%B3%E3%83%90%E3%83%AC%E3%83%BC%E4%B8%80%E6%B5%81%E3%83%97%E3%83%AD%E3%82%B0%E3%83%A9%E3%83%9E%E3%83%BC%E3%81%8C%E6%95%99%E3%81%88%E3%82%8B-Go%E3%83%97%E3%83%AD%E3%83%95%E3%82%A7%E3%83%83%E3%82%B7%E3%83%A7%E3%83%8A%E3%83%AB%E5%A4%A7%E5%85%A8-%E9%85%92%E4%BA%95-%E6%BD%A4/dp/4046070897
browser-use 試してみた


```py
from langchain_openai import ChatOpenAI
from browser_use import Agent, BrowserConfig, Browser
import asyncio


# `playwright install` is required to run this example
# Basic configuration
config = BrowserConfig(headless=False, disable_security=True)


async def main():
    agent = Agent(
        browser=Browser(config=config),
        task="食べログで六本木の焼肉店4つ見つけて",
        llm=ChatOpenAI(model="gpt-4o-mini"),
    )
    result = await agent.run()
    print(result)


asyncio.run(main())
```

これでtabelogの検索してくれる。

![Screenshot 2025-01-05 at 22.06.56.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/7059/5f7785c2-0674-73be-c8ef-d85ff1b15c66.png)


headlessにしたい場合は、 `headless=True`にすればOK


結果がこちら

```
1. 焼肉 冷麺 ユッチャン
2. 焼肉うしごろ 西麻布本店
3. 熟成焼肉 肉源 六本木店
4. 焼肉 乃木坂
```
すごい。
Neo4jのDockerをローカルで稼働させ、Cloudflare Workersのローカル実行からの接続を行ったメモ

# 概要
[前回はRDB(Neon Postgres)をローカルで稼働](https://qiita.com/hibohiboo/items/1827c41ce162431fda3e)させた。
今回はGraphDB(Neo4j)をローカルで動かして接続する。

[ソースコード](https://github.com/hibohiboo/odyssage/blob/9d06d3e09118a836a61349e9618d735fd94b5c1b/infra/local/neo4j/docker-compose.yml)

# GraphDBの準備
[公式がDockerを公開している](https://neo4j.com/docs/operations-manual/current/docker/introduction/)。 ([docker hub](https://hub.docker.com/_/neo4j))

```yaml:infra/local/neo4j/docker-compose.yml
services:
  graphDB:
    image: neo4j
    user: root
    ports:
      - 7474:7474
      - 7687:7687
```
`docker-compose up`で起動。  http://localhost:7474/browser/ にアクセスして初期設定を行う。
ユーザ名と初期パスワードはDockerにデフォルトで設定されているものを使う。
任意のパスワードは8文字以上ならば何でもよい。

項目|値
--|--
ユーザ名|neo4j
初期パスワード|neo4j
任意のパスワード|neo4jpassword

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/99876/c42b0359-4441-0759-6f67-0a12fb01b967.png)
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/99876/25f6b59f-96f2-6e29-8bae-7000b0f887ae.png)

パスワードを変更するとエディタが表示されるので、Cypherを入力できる。([Neo4j ブラウザの各部の基本説明][*1])

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/99876/e819cf92-49aa-4643-b7c4-8a77d8c9e788.png)

試しに`create (:Scenario {name: 'ゴブリンの洞窟'}) -[:HAVE_SCENE] ->(:Scene {name: 'プロローグ'})`と`match (s:Scenario) return (s)`を実行してみた。下記のようにブラウザから確認できる。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/99876/77bd8b87-081f-321a-7d94-ccd0d117eb8b.png)


# バックエンドからの接続
接続用の環境変数を変更し、動作することを確認した。

```diff:apps/backend/.dev.vars
NEON_CONNECTION_STRING=postgres://postgres:postgres@db.localtest.me:5432/main
- NEO4J_URL=neo4j+s://<NEO4J_INSTANCE_DOMAIN>.databases.neo4j.io
- NEO4J_USER=neo4j
- NEO4J_PASSWORD=<NEO4J_PASSWORD>
+ NEO4J_URL=neo4j://127.0.0.1:7687
+ NEO4J_USER=neo4j
+ NEO4J_PASSWORD=neo4jpassword
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/99876/d8282a27-c948-88e2-d6a0-77492d6577ad.png)


# 参考
[CloudflareWorkers+HonoでグラフDB ( Neo4jAura 無料版 ) にアクセスしてみたメモ](https://qiita.com/hibohiboo/items/00d2509541be583efa37)
[（初めてNeo4jブラウザを使われる方向け）Neo4j ブラウザの各部の基本説明][*1]
[Neo4j Auraとは？AuraDB Freeで無料＆手軽にグラフデータベースを使ってみよう](https://www.creationline.com/tech-blog/data-management/neo4j/53077)
[Neo4j Webインターフェースを使い倒す](https://qiita.com/awk256/items/4448899663a6aa82e88d)
[GraphDBを学ぶ（１）neo4jのコンテナ稼働](https://qiita.com/myoshimi/items/83ff5541518e482c4044)

[*1]:https://uti-inc.com/learning/user-interface-guide/
Kotlin Koans やってみた 3

# Introduction
## Triple-quoted strings
### 問題
Kotlin のさまざまな文字列リテラルおよび文字列テンプレートについて学びます。
便利なライブラリ関数 `trimIndent` と `trimMargin` を使用すると、複数行のトリプルクォート文字列を周囲のコードに従ってフォーマットできます。
`trimIndent` の呼び出しを、`#` をプレフィックス値とする `trimMargin` の呼び出しに置き換えて、結果の文字列にプレフィックス文字が含まれないようにします。

```kotlin
const val question = "life, the universe, and everything"
const val answer = 42

val tripleQuotedString = """
    #question = "$question"
    #answer = $answer""".trimIndent()

fun main() {
    println(tripleQuotedString)
}
```

### 解答
```kotlin
const val question = "life, the universe, and everything"
const val answer = 42

val tripleQuotedString = """
    #question = "$question"
    #answer = $answer""".trimMargin("#")

fun main() {
    println(tripleQuotedString)
}
```

### 解説
[Kotlin 公式ドキュメント > trimMargin](https://kotlinlang.org/api/core/kotlin-stdlib/kotlin.text/trim-margin.html)

#### trimMargin
```kotlin
fun String.trimMargin(marginPrefix: String = "|"): String
```

ソース文字列の各行から `marginPrefix` に続く先頭の空白文字をトリミングし、空白の場合は最初と最後の行を削除する（空白(blank)と空(empty)の違いに注意する）
最初と最後の空白行を除き、`marginPrefix` を含まない行には影響しない
元の文字列は、`\r\n`(CRLF)、`\n`(LF)、`\r`(CR) で区切ることができるが、結果の文字列はすべて、`\n`(LF) 改行文字で区切られる

```kotlin
import java.util.Locale
import kotlin.test.*

fun main() { 

    val withoutMargin1 = """ABC
123
456""".trimMargin()
    println(withoutMargin1) // ABC\n123\n456

    val withoutMargin2 = """
    #XYZ
    #foo
    #bar
""".trimMargin("#")
    println(withoutMargin2) // XYZ\nfoo\nbar 

}
```

# おわりに
解説は Kotlin 公式ドキュメントから翻訳してみました。
だけど、サンプルコード見た方が伝わる気がする・・・。

---

[← 前回の記事](https://qiita.com/b-yuko/items/a3f93b5410be7576c457)　|　[次回の記事 →](https://qiita.com/b-yuko/items/cc2baa1dedc979a0050e)
カロミルで付けた摂取カロリーをデータ収集する

# 目的
健康診断の数値が悪くなってきたので、ダイエットしないとな…と思っていた昨今、とりあえずデータ収集して分析してみるかと思い立ち、体重やら摂取カロリーのデータ収集をやろうと思い立った。

## データ収集の検討
体重はBluetooth接続してスマホアプリに記録するものを持っていたが、アプリを立ち上げるのが面倒で使わなくなっていた。
Wifi経由のものならアプリを開かずとも済むとのことなので買いなおした。
https://amzn.asia/d/2hCMy8m

カロリー計測は、あすけんが有名だがデータ書き出しは出来ないらしい。
カロミルなら書き出せはしないが栄養サマリーとして画像を保存することはできた。
https://www.calomeal.com/about-calomeal/

画像が保存できるなら、それをOCRで読み取ってデータ化すればよい。

# 何でOCRするのか
結論から言うとPowerAutomate Desktopを利用して、WindowsOCRを使えば無料でそれなりの読み取りが可能になった。

## Tesseract
PythonでOCRをするならTesseractが有名なようなので、まず最初にこちらを参考にさせていただきやってみた。
https://qiita.com/ryome/items/16fc42854fe93de78a23
エンジンはBest版を利用した。
https://github.com/tesseract-ocr/tessdata_best

![tempFile366778101924718127.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/428123/1ca48ce7-5d1e-9910-505e-6b47e732fe1c.jpeg)
この画像を実行すると以下の出力が得られた。
```
3( 金 ) 栄養 サマ リー カロ ミル

1535 /1eotkcal
-

た ん ば ぱく 質 脂質

104.0 /72.og 46.1 /48.0g
還 上 |- 人

炭水化物

糖 質
188.9 /220.1g 173.7 /202.1g
和香

食物 繊維 塩分
15.2718.og 10.82 /e.sog
| に 上 上 上 上 上
```
ウワー微妙。
他の日もやってみたが変わらず。

## WindowsOCR
PowerAutomate DesktopにあるOCRフローのWindowsOCRエンジンでやってみた。
画像は先ほどと同じものを使用。
```
1 / 3 ( 金 ) 栄 養 サ マ リ ー 日 ノ 食 事 管 理 ア プ リ
カ ロ ミ ル

カ ロ リ -
1535 / 1601kc 引


た ん ば く 質        脂 質
104. O / 72. og       46.1 / 48. og

炭 水 化 物         糖 質
188.9 / 220. lg     173.7 / 202. lg

食 物 繊 維         塩 分
15.2 / 18. og      10.82 / 6.50g
```
Tesseractより全然いい…。
ということで、PowerAutomate Desktopを利用してOCRすることにした。
ちなみにカロミルから保存された画像はwebpになっていたのだが、PowerAutomate DesktopのOCRはwebpを扱えなかったので事前にPythonのPillowでjpgに変換した。
PowerAutomateでwebpからjpgにする方法が分からなかったのでPythonでやったが、もしPowerAutomateで出来る方法が分かったら変えたい。

# まとめ
ほかにいいOCRあったら教えてください。
やっぱり有料のやつは精度がもっといいのかなあ。
【AWS SAP】AWS Schema Conversion Tool (SCT) を使うケース

# はじめに
AWS Schema Conversion Tool (SCT) を使うケース、使わなくていいケースをまとめました。

## AWS Schema Conversion Tool (SCT) を使うケース

### 1. **データベースエンジンの変更**
- Oracle → Amazon Aurora（PostgreSQL/MySQL互換）
- SQL Server → Amazon RDS for PostgreSQL/MySQL

### 2. **オンプレミスからAWSへの移行**
- オンプレミスのデータベーススキーマをAWSデータベースサービス（RDSやRedshift）に変換。

### 3. **データウェアハウスの移行**
- オンプレミスのデータウェアハウス（Teradata、Netezza）→ Amazon Redshift

### 4. **スキーマの互換性チェック**
- ソースデータベースのスキーマをターゲットデータベースで利用可能か評価。

### 5. **スキーマ変換の自動化**
- 手動で修正が必要な部分を最小限にし、効率的にマイグレーションを実施。

### 6. **移行前の分析レポート作成**
- 変換可能な箇所や非互換部分のレポートを作成して移行計画を立てる。

## AWS Schema Conversion Tool (SCT) を使わなくていいケース

### 1. **同一データベースエンジン間の移行**
- 例えば、Oracle → OracleやMySQL → MySQLなど、スキーマ構造がほぼ変わらない場合。

### 2. **シンプルなデータ移行のみが必要な場合**
- データだけを移行し、スキーマ変換が不要な場合はAWS DMSや手動移行で十分。

### 3. **小規模なデータベース移行**
- 小規模で手動で対応可能な場合、SCTを使うほどのメリットがない。

### 4. **非対応のデータベース間移行**
- SCTがサポートしていないデータベースエンジン間の移行には利用できない。
 （例：Cassandra、MongoDB、DynamoDBなど）

### 5. **スキーマの複雑なカスタマイズが必要な場合**
- SCTでは対応しきれないほど高度なスキーマカスタマイズや、専用のビジネスロジックを実装している場合。

### 6. **リアルタイムのデータレプリケーションが目的の場合**
- SCTはスキーマ変換ツールであり、リアルタイムのデータ同期には適していない（AWS DMSなどを使用）。
Apple Silicon & Sequoia15.2での「利用可能なRosettaが見つかりません」の対処方法

# 経緯

1. 2025/01/04に念願の人生初Mac Book Pro(M4)を購入！
2. 色々アプリをインストールしていた時にどうも`Rosetta`というものをインストールしないといけないっぽい
  <img 
  src="https://cdsassets.apple.com/live/7WUAS350/images/macos/big-sur/locale/ja-jp/macos-big-sur-software-update-rosetta-alert.jpg" width=50%>

3. 出てきたポップアップの「インストール」を押下するも何故かインストールされない
  
4. Appleに問い合わせるもよく分からなそうな雰囲気＆ネットで調べても全く情報が出てこない

# 原因

Seqoia15.2は認知しているだけで2種類存在する。
そのうちの片方であるSeqoia15.2(`24C103`)にはどうもRosettaが存在しないっぽい

設定>一般>ソフトウェアアップデート で確認できる

<img src=https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/405444/7f77c557-cdc7-5f83-92f8-7c6d738caf88.png width=50%>

(最初は画像では`24C101`になっている部分が`24C103`でした)

# 解決方法

Sequoiaの再インストールでSeqoia15.2(`24C101`)になります。
下記の公式サポート手順を確認しながら行う。

https://support.apple.com/ja-jp/102655


# 補足情報

今回購入したMac Book Proはカスタマイズを行なっていました。
そのため発送が上海の工場？から行われていたのですが、そこでプリインストールされるSequoiaが`24C103`でした。
しかし、一般的にSequoiaをアップデートするとSequoia`24C101`が入るため非常に情報が少ないのかと思います。(24C101 --> 24C103へのアップデート？方法が不明な点も情報が少ない原因だと感じました)
C# デスクトップアプリ開発 PostgreSQL接続方法

## まずDB接続のC#プログラム構造
C#は
名前空間という概念
クラスという概念があって、クラスの中にメソッドを書いたり、変数を作ったりだとかで、VBAと考え方が違ってくるところがあって面白い。

DB接続関係の処理はDB接続関係の名前空間

を作って、DBクラスを作り、その中に変数、メソッドを作っていくことにしました。

## 名前空間とは
C#はライブラリが多いので、ライブラリ同士でメソッド名が被っても良いように名前空間という概念が存在します。
例えば、
Databaseのupdate というメソッドと、Listのupdateというメソッドがあるとすると、どちらともupdateというメソッドを使っていてどちらのメソッドを参照していいか機械がわからない。

C#はDatabase,Listを名前空間にして、
Database.update
List.update という記述のさせ方をすることによって、メソッド名を競合することを考えずに簡単に命名できるようになっている。

## クラスについての概念説明はスキップします。

## ポスグレSQL接続に必要なライブラリインストール
これ。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/a40fce1d-37d9-ca23-507a-6698e814c56e.png)



## Database関連のクラス作ってみた。

赤いカッコでかこったのがDatabaseManagerというクラスです。
青いカッコ一番上は、public DatabaseManagerというのがDatabaseManagerクラスをnewしたとき(インスタンスを作成したとき)実行されるものです。
変数connectionStringにDB接続パラメータを入れています。

その下にある青いカッコたちはメソッドです。
どのメソッドも、クラスをnewして、DatabaseManager.ExecuteQueryなどで実行することが可能です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/00dc518f-d419-54cb-7589-8163ac1a6c2d.png)

## PostgreSQL側の設定
pg_hba.conf の編集
C:\Program Files\PostgreSQL\17\data\pg_hba.conf
```
# IPv4 local connections:
host    all             all             127.0.0.1/32            scram-sha-256
```

127.0.0.1/32はローカルマシンにポスグレSQLインストールしたのでローカルIPアドレスを指定。


## 学習まとめ
DB関係はDBクラスにまとめる を実践してみました。
クラスを作ってみたけど何をクラスにすればいいのか発想できるようにならなければ、今後のプログラム開発で大変な思いをしそうだなと感じた。
`seed` と `system_fingerprint` を使用して OpenAI API の確定性出力を実現する



OpenAI のテキスト生成モデルを使用する場合、デフォルトではモデルの出力は非確定性です。これは、同じプロンプトを入力しても、リクエストごとに出力が異なる可能性があることを意味します。しかし、特定のシナリオでは、結果の再現性を確保するために確定性のある出力を希望する場合があります。OpenAI はこれを実現するための2つの重要なツールを提供しています：`seed` パラメータと `system_fingerprint` レスポンスフィールドです。

本記事では、`seed` と `system_fingerprint` を使用して OpenAI API の出力を制御し、確定性を確保する方法について詳しく説明します。

---

## 1. 確定性出力とは？

確定性出力とは、同じ入力条件下でモデルが毎回同じ出力を生成することを指します。これは、実験、テスト、デバッグなど、再現性が必要なタスクにおいて非常に重要です。

デフォルトでは、OpenAI のモデル出力は非確定性です。これは、モデルがテキストを生成する際に一定のランダム性を導入するためです。しかし、`seed` パラメータを設定することで、このランダム性を制御し、確定性のある出力を得ることができます。

---

## 2. `seed` パラメータを使用して確定性出力を実現する

`seed` は、モデルがテキストを生成する際のランダム性を制御するための整数パラメータです。同じ `seed` 値を設定することで、同じ入力条件下でモデルの出力を一貫させることができます。

### `seed` パラメータの使用方法：
1. `seed` パラメータを任意の整数（例：`seed=42`）に設定します。
2. 確定性のある出力を必要とするリクエストで、同じ `seed` 値を使用します。
3. 他のパラメータ（`prompt` や `temperature` など）が各リクエストで完全に同じであることを確認します。

### サンプルコード：
```python
import openai

response = openai.ChatCompletion.create(
    model="gpt-3.5-turbo",
    messages=[{"role": "user", "content": "春についての短い文章を書いてください。"}],
    seed=42  # seed パラメータを設定
)

print(response.choices[0].message.content)
```

### 注意点：
- `seed` 値が同じで他のパラメータも一致する場合、モデルの出力は一貫します。
- OpenAI がモデル設定に必要な変更を加えた場合、出力の確定性に影響を与える可能性があります。この場合、`system_fingerprint` フィールドを使用してこれらの変更を検出できます。

---

## 3. `system_fingerprint` を使用してモデル設定の変更を追跡する

`system_fingerprint` は、OpenAI API のレスポンスに含まれるフィールドで、モデル設定の現在の状態を識別するために使用されます。OpenAI がモデルを更新または変更した場合、`system_fingerprint` の値が変わる可能性があります。

### `system_fingerprint` の使用方法：
1. API レスポンスで `system_fingerprint` フィールドを確認します。
2. `system_fingerprint` の値が変わった場合、モデル設定が更新されたことを意味し、出力の確定性に影響を与える可能性があります。
3. 完全な確定性出力が必要な場合は、同じ `system_fingerprint` 値の下でテストとデプロイを行うようにしてください。

### サンプルコード：
```python
import openai

response = openai.ChatCompletion.create(
    model="gpt-3.5-turbo",
    messages=[{"role": "user", "content": "春についての短い文章を書いてください。"}],
    seed=42
)

print("出力内容：", response.choices[0].message.content)
print("system_fingerprint：", response.system_fingerprint)
```

### 注意点：
- `system_fingerprint` の変更は、通常、OpenAI によるモデルの最適化や更新が原因です。
- `system_fingerprint` の変更により出力が一貫しなくなった場合は、`seed` や他のパラメータを調整して再び確定性を確保してください。

---

## 4. まとめ

`seed` パラメータと `system_fingerprint` フィールドを組み合わせて使用することで、OpenAI API の出力を効果的に制御し、確定性を確保することができます。以下は重要なポイントのまとめです：
- **`seed` パラメータ**：固定の整数値を設定することで、モデルがテキストを生成する際のランダム性を制御し、確定性出力を実現します。
- **`system_fingerprint` フィールド**：モデル設定の変更を検出し、出力が一貫しない原因を理解するのに役立ちます。

実際のアプリケーションでは、再現性が必要なタスクでは常に `seed` パラメータを使用し、定期的に `system_fingerprint` をチェックしてモデル設定の一貫性を確保することをお勧めします。

---

本記事が、OpenAI API の確定性出力機能を理解し、使用する上でお役に立てば幸いです！ご質問やご意見がありましたら、コメント欄でお気軽にご相談ください。

--- 

**参考資料**：
- [Reproducible outputs](https://platform.openai.com/docs/advanced-usage#reproducible-outputs)
svg2pdf



`input.svg` を `output.pdf` を生成します。

```js
const puppeteer = require('puppeteer');
const fs = require('fs');

(async () => {
    const browser = await puppeteer.launch();
    const page = await browser.newPage();

    // SVGファイルを読み込み
    const svgContent = fs.readFileSync('input.svg', 'utf8');

    // viewBoxを取得してサイズを設定
    const [, , width, height] = svgContent.match(/viewBox="([-.\d\s]+)"/)[1].split(' ').map(Number);

    // HTMLにSVGを埋め込み、余白を削除
    await page.setContent(`<html><body style="margin: 0;">${svgContent}</body></html>`);
    await page.setViewport({ width: Math.ceil(width), height: Math.ceil(height) });

    // PDFを生成
    await page.pdf({
        path: 'output.pdf',
        width: `${width}px`,
        height: `${height}px`,
        margin: { top: 0, right: 0, bottom: 0, left: 0 },
        printBackground: true,
    });

    await browser.close();
    console.log('余白なしPDFを生成したのじゃ！');
})();
```
自作PCのwindows11アップデートに伴うBIOSアプデ方法の記録

## windows11アップデートしようとしたら、
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/bab6b8b1-abdc-9f39-4973-c8ec080a12b0.png)


このとおりアプデができない。

色々調べていたら、TPM2.0 というものを有効にしなければいけないらしくて、BIOSアプデすればTPMを有効にできるらしい。

### BIOSアプデ、BIOS設定を間違えるとPCが起動しなくなるなどトラブルが起きるので注意

## マザーボードのアップデートファイル探す

使ってるマザボはこれ↓
ASUS AMD B450 PRIME B450M-K

このマザボの最新アプデファイルを検索してダウンロードしにいきます。

https://www.asus.com/jp/supportonly/


ダウンロード→解凍後　適当なUSBにいれる

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/f16d2ccd-38d0-7ca5-ace6-1e3415673a0d.png)

## BIOS更新作業します。
PCを再起動して、 del , F10 , F8 など お使いのマザボードによってキーは違いますが、再起動中にキーを連打することでBIOS設定画面入れます。



![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/7635b8c4-d756-21ee-4b94-dcc77f83bda4.png)

たしか、右下のブートメニュー行く。
USBに入れたアプデファイルを選択。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/441482a0-e95e-879a-5c5e-329e45cffdbe.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/9da29cbc-260c-d83f-9c6a-d9ae6baa18de.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/3f0dfb1f-96c9-f855-522e-e279ab55a16f.png)

アプデ成功したらBIOS設定画面からTPM見てみる。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/59eee79d-ceaa-9fad-cd53-4735579fccde.png)

ぼやけてるけどEnabled ※有効にする
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/f9c1a98a-67f6-d9fd-c22c-fece8f87ada2.png)

## BIOSの設定が終わったら設定をSaveしてwindows起動

正常性確認する。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/09249667-ca80-f867-233f-ea4586344838.png)
これでOK

しばらくはこの警告でる。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/bab6b8b1-abdc-9f39-4973-c8ec080a12b0.png)

## 1週間後
↑の警告が消えて、win11アプデしませんか というものが出てきます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/8a498930-1d91-7dcf-d7a0-af30318e02b9.png)



![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3882753/4e6d0e07-2471-9160-876a-c04a18a5a069.png)


あとは待つだけでwin11アプデ完了！
# MapShaper で国土地理院のGeoJsonを編集するときによく使うコマンド

アプリ開発している時に国土地理院のデータをダウンロードしたが、その際にGeoJson編集でよく使うコマンドを備忘として自分のために残しておく。
できること
mapshaperを使って国土地理院からダウンロードしたデータの編集
･ 離島を認識させること
･ 政令指定都市を区単位ではなく、市単位で整備すること


# 国土地理院のリンク
https://nlftp.mlit.go.jp/ksj/gml/datalist/KsjTmplt-N03-2024.html

# MapShaperのリンク
https://mapshaper.org/

## 離島を認識させる
最初、下記例のように市を押しても離島が反応しない。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3846056/e1ca2e99-03b0-3b99-8ff5-9cea231aa101.png)


そこで以下コマンドをコンソールで実行
```
dissolve N03_001,N03_002,N03_003,N03_004,N03_005,N03_007
```
実行すると離島も一生に反応するように変わる。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3846056/8d25281c-2ab0-c98f-3e9e-6fd05c53ca3f.png)

## 政令指定都市を区単位ではなく、市単位で整備する
名古屋市のような政令指定都市は最小単位が市のポリゴンでないため、以下のような表示になる

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3846056/77fd9d86-8220-cdb2-0a95-3078b43f9cc7.png)
そこで下記コマンドを実行する。
```
$ dissolve where='N03_005 != null' N03_004 copy-fields=N03_001,N03_002,N03_003,N03_004 calc='N03_007=null;N03_005=null'
```
すると下記のように市単位で管理される
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3846056/43b02fff-4132-9446-44b2-ec4f6a9a85cb.png)

以上、備忘でした。

めっちゃ参考にしたサイト様
https://note.com/kazukio/n/n974da9bb1ffb
スラッシュ(/)とバックスラッシュ(\)、どっちだったか分からなくなるそこのお前！

パーセント(％)とスラッシュ(/)は同じ向きだぜ！
わからなくなったら％を思い出すといいぜ！


https://dic.pixiv.net/a/%E3%81%9D%E3%81%93%E3%81%AE%E3%81%8A%E5%89%8D!%E2%97%8B%E2%97%8B%E4%B8%80%E5%80%8B%E3%81%AB%E5%90%AB%E3%81%BE%E3%82%8C%E3%82%8B%E2%96%B3%E2%96%B3%E3%81%AF%E2%97%8B%E2%97%8B%E4%B8%80%E5%80%8B%E5%88%86%E3%81%A0%E3%81%9C

元ネタの画像にも左右反転があるっぽいぜ！
Azure SQL Database に対して Microsoft SQL Server CDC Source V2 (Debezium) コネクタを設定する際の CDC schema に接続できないというエラーへの対応方法


## 概要

Azure SQL Database に対して Microsoft SQL Server CDC Source V2 (Debezium) コネクタを設定する際に、下記のエラーへの対応方法を共有します。Azure SQL Database にて CDC を有効にしたテーブルを作成する必要があるようです。エラーの再現方法と対応方法を共有します。

> User debezium does not have access to CDC schema in the following databases: debezium_00. This user can only be used in initial_only snapshot mode

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/4b76b105-b597-cff9-8dad-fecdf15536b6.png)

## エラーの再現方法

### 1. Azure SQL Database にて CDC を有効化

```sql
EXEC sys.sp_cdc_enable_db;
```

```sql
SELECT name, is_cdc_enabled
FROM sys.databases  
WHERE name = 'debezium_00';
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/042f4b20-59eb-c920-f71b-f3d5a4c6fe24.png)

### 2. Add Microsoft SQL Server CDC Source V2 (Debezium) connector

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/0384cf27-6122-85bc-7eec-74bebd40d3ca.png)

### 3. `Add Microsoft SQL Server CDC Source V2 (Debezium) connector`のステップでエラーとなることを確認

> User debezium does not have access to CDC schema in the following databases: debezium_00. This user can only be used in initial_only snapshot mode

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/4b76b105-b597-cff9-8dad-fecdf15536b6.png)

## エラーへの対応方法

### 1. Azure SQL Database にて CDC を有効にしたテーブルを作成

```sql
IF OBJECT_ID(N'dbo.test_01', N'U') IS NOT NULL
    DROP TABLE [dbo].[test_01];
GO
CREATE TABLE [dbo].[test_01] (
    [Id] INT NOT NULL,
    CONSTRAINT [PK_Customers] PRIMARY KEY ([Id])
);
GO
```

```sql
EXEC sys.sp_cdc_enable_table
    @source_schema = N'dbo',
    @source_name = N'test_01',
    @role_name = NULL;
```


![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/d5ace132-a6a0-be22-82f0-b7bad1fcad0a.png)

### 2. Confluent にて`Continue`を選択して次の画面に進むことを確認

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/cd651419-7f79-a88a-0803-42a4b95355a0.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/d0095070-8035-c5f4-866d-e4ec71c0d6bd.png)
PropertyWrapper触りだけでも覚える

# はじめに
最近PropertyWrapperの概念を知り、使いこなせるとボイラープレートを削減できかなり有用と思ったので記事を書きつつキャッチアップしようと思います。

# PropertyWrapperってこんなの

公式ドキュメントでは以下のように説明されています。

>A property wrapper adds a layer of separation between code that manages how a property is stored and the code that defines a property. For example, if you have properties that provide thread-safety checks or store their underlying data in a database, you have to write that code on every property. When you use a property wrapper, you write the management code once when you define the wrapper, and then reuse that management code by applying it to multiple properties.


日本語訳
>プロパティ ラッパーは、プロパティの格納方法を管理するコードとプロパティを定義するコードの間に分離レイヤーを追加します。たとえば、スレッド セーフティ チェックを提供するプロパティや、基になるデータをデータベースに格納するプロパティがある場合、すべてのプロパティにそのコードを記述する必要があります。プロパティ ラッパーを使用する場合は、ラッパーを定義するときに管理コードを 1 回記述し、その管理コードを複数のプロパティに適用して再利用します。

https://docs.swift.org/swift-book/documentation/the-swift-programming-language/properties/#Property-Wrappers

だいぶ小難しく書いていて、個人的にはピンとこないのですが、簡単な例を見ると腑に落ちるかと思います。

```swift
@propertyWrapper
struct NameString {
    
    private var _value: String
    
    init(wrappedValue: String) {
        
        self._value = wrappedValue
        self.wrappedValue = wrappedValue
    }
    
    var wrappedValue: String {
        get { _value + "さん" }
        set { _value = newValue }
    }
}

struct Human {
    
    @NameString var name: String
    
    init(name: String) {
        
        self.name = name
    }
}
```

上記例では、`NameString`というPropertyWrapperを定義し、`Human`の`name`プロパティに付与しています。
名前なので、必ず末尾に「さん」をつけるようにするという例です。

名前には必ず末尾に「さん」をつけるという仕様があった場合に、いちいち以下の様に名前取得用のコンピューテッドプロパティを用意するといったコードが必要となり、また他のクラスや構造体で名前の表すプロパティを持つことになると、そこでも同じようなコードが必要になります。
こういったコードをボイラープレートといったりしますが、定型的なコードであり毎回同じ様なことを書くのは大変面倒です。


```swift
struct Human {
    
    private var _name: String
    var name: String {
        return _name + "さん"
    }
    
    init(name: String) {
        
        _name = name
    }
}
```

ボイラープレートなコードを再利用可能な状態にできることが、PropertyWrapperの良さと言え、公式のドキュメントからも、その様な使用方法のために存在することが読み取れます。

>プロパティ ラッパーを使用する場合は、ラッパーを定義するときに管理コードを 1 回記述し、その管理コードを複数のプロパティに適用して再利用します。

# おわり
本当に触りだけでしたが、PropertyWrapperの意義を知ることができました。
今回見た限りは簡単な例にとどまっていますが、使い方によっては依存解決のためのコードもPropertyWrapperで省略するなどできたりしそうで実務でもかなり使えるのではと思っています。([swift-dependencies](https://github.com/pointfreeco/swift-dependencies)のライブラリにある`@Dependency`多分PropertyWrapperなんだろうなと思うので)
良い使い方見つけたら、また記事にしてみようと思います！
【AWS SAP】AWS Application Discoveryとは？

# AWS Application Discoveryとは？
オンプレ資産情報を収集するツールです。
AWS Migration Hubに統合されており、収集した情報をAWS Migration Hubで確認でき、そのまま移行管理にも使用できる。追加のオプションでは収集した情報をKinesis Data FirehoseからS3へ送信し、Athenaで分析することも可能。


![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2746730/53b62b21-3a4e-9a5a-d126-149f3c7dbcc6.png)

https://aws.amazon.com/jp/blogs/news/new-aws-application-discovery-service-console/

## 導入するには？
- **ディスカバリーエージェント（エージェント型）**
    - 対象サーバーにエージェントをインストールして、詳細なメタデータやプロセス情報を収集
- **エージェントレスコレクター（エージェントレス型）**
    - ネットワーク経由でVMware環境から情報を収集し、インストール不要

### 何が違うの？

| 項目             | ディスカバリーエージェント                   | エージェントレスコレクター                       |
|------------------|-------------------------------|----------------------------------|
| インストール要否  | 必要                          | 不要                            |
| 対応環境         | オンプレサーバー全般           | VMware環境のみ                  |
| 情報の詳細度     | 詳細な依存関係やプロセス情報   | 環境全体の基本的な情報           |
| 使用ケース       | 詳細な移行計画や依存関係分析   | 初期の環境調査や概要把握         |

### 具体的に何が取得できる？

- **ディスカバリーエージェントで取得可能な情報**
	- OS情報（バージョン、構成）
	- プロセス情報
	- ネットワークトラフィック
	- ディスク使用状況
	- アプリケーション依存関係
	- CPU使用率やメモリ使用量
	- サーバーの稼働状況
　
- **エージェントレスコレクターで取得可能な情報**
	- 仮想マシンの一覧
	- ホスト情報（CPU、メモリ、ストレージ）
	- 仮想ネットワーク構成
	- 仮想マシンの基本属性（OS、IP、名前など）
	- リソース使用状況の概要
	- VMwareハイパーバイザーの情報

## 結局どっちを使うべきか？
- VMware環境のみであれば、基本的に**エージェントレスコレクター**を使用
- より詳細な情報やプロセスレベルのデータが必要な場合はディスカバリーエージェントを併用

:::note info
[【AWS SAP】Application Migration Service エージェント とApplication Discovery Service エージェントは違う？](https://qiita.com/aws-training/items/be1df2b26ba288dbddd6 "【AWS SAP】Application Migration Service エージェント とApplication Discovery Service エージェントは違う？")
:::

## 参考資料

https://pages.awscloud.com/rs/112-TZM-766/images/AWS-Black-Belt_2023_AWS_ADS.pdf
MySQLのbind-addressが無いんですが……？

# 前置き
タイトル通りの問題に直面したので、解決方法を残しておく。
多分忘れた頃にまた出会う。

## 状況
外部端末からサーバのmysqlにアクセスするために調べてると、どの記事も
> `/etc/my.cnf`に書かれてるbind-addressの値を変えたり、コメントアウトすると良い

みたいに書いてある。
でも`/etc/my.cnf`は無いし、`/etc/mysql/my.cnf`はあったけど、`bind-address`なんて記述は無いし、何言ってんだこいつら状態。

# 解決方法
`/etc/mysql/my.cnf`の末尾に下記を追加する
```
[mysqld]
bind-address = <任意のIPアドレス>
```

とりあえずどっからでもアクセスできるようにしたければ、`bind-address = 0.0.0.0`とする。

最後に接続確認で
```sh
mysql -h <サーバのIPアドレス> -u <ユーザー名> -p
```
を実行して、無事ログインできればOK。
2025年の抱負をまとめてみる

# はじめに
明けましておめでとうございます！
あっという間に2025年を迎えましたが、皆様は連休中いかがお過ごしでしたか？
昨年は激動の一年と呼べるくらい色々なことがいっぺんに起きた一年でしたが、今年も引き続きチャレンジングな一年となりそうです。
そこで今回は少し方向性がずれますが、一年の抱負を忘れずにいる為に今年の抱負をまとめておこうと思います。

# 仕事面
仕事面での今年の抱負はズバリ【余裕と情熱を持って変化を楽しむ】です。
今年はこれまでとは違うステージでチャレンジを続けていくのですが、質の高いインスピレーションを生み続ける為にはやはり余裕と情熱、この二つは欠かすことのできない要素です。

また、抱えているものが多くなると何かと疎かになりがちなこの二つの要素を常に高い状態で維持していく、その為には全力で楽しむということも同様に大切にしていきたいと思います。

# プライベート面
プライベート面での抱負はズバリ、【健康】です！
本当にお恥ずかしい話ですが、昨年は不摂生が続いたことで体重も増加・・・
代表たる私が不健康では不安に感じるメンバーも出てくると思うので、今年こそはより一層健康に気を遣っていきたいと思い、プライベートでは健康に全振りで行こうと思います。
その為にまずは以下を実行していこうと思います。

- 毎日30分程度の運動をする
- 子供と毎週一緒に運動をして汗を流す
- テニスを復活させる

健康面に関しては本当に二日坊主になりがちなので、まずは習慣化を目指していきます！

# さいごに
今年も後悔の残らないよう全力で取り組んでいきます！
Microsoft Authenticatorで要求は送信されませんでしたと出るとき

メモです。たまにこれが起きてしまい、毎回解決方法を探すので。

# 要求は送信されませんでした 現時点では通知を送信できませんでした。アプリで保留中の通知を確認してください。

たまにMicrosoft Authenticatorを使っているとこんなメッセージが出るときがある。


原因としては、スマホで一度Authenticatorに確認コードを求める通知が表示されたのに、何もせずにそのまま画面を閉じてしまうとこうなるらしい。裏で通知が保留状態で残ってしまい、再度通知を送れなくなってしまう。

パソコンから認証しても、スマホへ通知が数分単位で送られないときがあって、そういうときは手違いでこうなってしまう。

## 解消

スマホのAuthenticator上で右上の三点ポチから「通知の確認」を行う。
アカウントの一覧が表示されているトップ画面で下にドラッグしても行える。

そうすると最初の通知がもう一度表示されるので、ここでコードの正誤は問わないのでとりあえず何かコードを入れる。これをすることによって通知の保留が解除され、再度通知を送れるようになる。
デザインパターン - その2 (MVP, MVVM, MVC)

# はじめに
MVP, MVVM, MVCのデザインパターンについて記載していく。
なんとなく理解しているが、それぞれの違いを明確に説明はできないな、、と思い改めて学び直してみた。

# それぞれの違い
| 特徴 | MVC | MVVM | MVP |
|:-:|:-:|:-:|:-:|
| データフロー  | View → Controller → Model → View  | View ↔ ViewModel ↔ Model  | View ↔ Presenter ↔ Model  |
| Viewの役割  | UI表示、ユーザー入力の検知  |  UI表示、ユーザー入力の検知、ViewModelの変更を監視 | UI表示、ユーザー入力をPresenterに通知  |
| Modelの役割  | ビジネスロジックとデータ処理  | ビジネスロジックとデータ処理  | ビジネスロジックとデータ処理  |
| 中間層の役割  | Controller: ユーザー入力処理、Modelの更新指示  | ViewModel: ViewとModelの仲介、データバインディングやUI表示ロジック  | Presenter: ViewとModelの全通信を仲介、UI表示ロジック  |
| データ更新の仕組み  | Viewがモデルの変更を監視  | データバインディングによる自動更新  | Presenterが明示的にViewを更新  |
| 学習曲線  | 低い  | 高（データバインディングの概念学習など）  | 中  |

:::note info
Modelで実装するビジネスロジックについて
アプリケーションの中核となる処理や規則をModelで実装します。
例：
　商品の在庫管理ロジック
　ユーザーの認証プロセス
　複雑な計算処理
これらの処理は、他の層から独立（切り離して）して実装する。
:::


# 図で表してみた
３つのデザインパターンについて、同じ図を用いて表現してみた。
同じ図なので、それぞれの差異が分かり易いと思う。

## MVC
一番シンプル
![スクリーンショット 2025-01-05 19.59.11.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3782130/73b4e8be-6dbd-a90c-fbd4-c2fcfddff829.png)

## MVVM
肝はデータバインディング
![スクリーンショット 2025-01-05 19.59.28.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3782130/6239cd21-cec3-ebb7-69bd-961b0b53cd77.png)

## MVP
処理の順番が分からないと辛いので、この図だけ処理の順番を番号で振ってる。
![スクリーンショット 2025-01-05 19.59.37.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3782130/c3a1d5aa-dbac-3d48-b796-562d4141b852.png)

# MVPとMVVMの違い
図的にも似通っているようにも見えるのが、本質は結構違う。
パッと見分かりづらいと思うので、以下に違いを記載する。

## データバインディング
MVVMの最大の特徴は、ViewとViewModelの間で双方向のデータバインディングを使用することです。これにより、ViewModelの状態が変更されると自動的にViewが更新されます。
一方、MVPではPresenterがViewを直接更新します。

## 責任の分離
MVP: Presenterは、ViewとModelの間の仲介役として機能し、Viewの更新を直接制御します。
MVVM: ViewModelは、Viewに必要なデータと操作を提供しますが、Viewの直接的な制御は行いません。

## テスト容易性
MVVMは、ViewModelとViewの疎結合により、ユニットテストがより容易になります。
MVPもテスト容易性が高いですが、PresenterとViewの結合がMVVMよりも強くなる傾向があります。

## 実装の複雑さ
MVP: 比較的シンプルで、既存のMVCプロジェクトからの移行が容易です4。
MVVM: データバインディングの概念や関連ライブラリ（例：RxSwift）の理解が必要で、学習曲線が急な傾向があります。

## 適用シナリオ
MVP: 小規模から中規模のプロジェクトに適しており、既存のコードベースへの導入が容易です。
MVVM: 中規模から大規模のプロジェクトに適しており、特に複雑なUIロジックを持つアプリケーションに効果的です。
AtCoder ABC387 振り返り感想戦(緑コーダーがPythonでA,B,D問題)

## ABC 387感想まとめ

[AtCoder Beginner Contest 387（Promotion of AtCoderJobs） - AtCoder](https://atcoder.jp/contests/abc387)

ABC387はABDの3問回答でした。

今回は何と言ってもC問題が難しかったようです。私もC問題は早々に諦めて、D問題に取り組みました。難易度的にも C >>> D だったようでした。

D問題に着手した判断が結果的には良かったようで、思った以上の成績が出せました。

C問題は桁DPを使って解くようなのですが、公式解説を見てもよくわからないので、今後の復習課題です。

::: note warn
そもそも、桁DPはそんなに自信がない...
:::

## [A - Happy New Year 2025](https://atcoder.jp/contests/abc387/tasks/abc387_a)

問題に書いてあるとおり、(A+B)^2を計算すればokです。

``` python
A, B = map(int, input().split())
print((A+B)**2)
```

## [B - 9x9 Sum](https://atcoder.jp/contests/abc387/tasks/abc387_b)

これも問題に書いてあるとおり、九九の掛け算のうちでX以外の数を全部足せばokです。

``` python
X = int(input())

answer = 0
for i in range(1, 10):
    for j in range(1, 10):
        if i * j != X:
            answer += i * j
print(answer)
```

## [C - Snake Numbers](https://atcoder.jp/contests/abc387/tasks/abc387_c) [未回答]

これが今回の難問でした。私も結構悩んだのですが、どうにも解けず...。行き詰まってD問題を見てみたら「CよりDのほうが典型的なアルゴリズムで解けそう...」ということで、D問題に着手しました。

結果的に、これは好判断だったようです。

## [D - Snaky Walk](https://atcoder.jp/contests/abc387/tasks/abc387_d)

これは迷路の最低移動距離探索なので、幅優先探索で実装しました。

注意点は、水平方向移動→垂直方向移動→水平→垂直...と交互にしか移動できない制限です。

これは、queue に突っ込む tuple に (座標i, 座標j, 移動方向(水平or垂直)) と移動方向を含めることで対応しました。

該当のマスに 水平移動/垂直移動 どちらで来たかがわかれば、次に進める方向はどちらなのかがわかる仕組みです。

``` python
INF = 10 ** 18

H, W = map(int, input().split())

# 地図の四方を # で囲む
S = []
S.append("#" * (W + 2))
for i in range(H):
    s = "#" + input() + "#"
    S.append(s)
S.append("#" * (W + 2))

# スタート地点を探す
START = (0,0)
for i in range(1, H + 1):
    for j in range(1, W + 1):
        if S[i][j] == "S":
            start = (i, j)
            break

# 水平方向の移動と垂直方向の移動
MOVES_H = [(0, 1), (0, -1)]
MOVES_V = [(1, 0), (-1, 0)]

# 水平・垂直方向移動時の、スタートからの距離
dist_h = [[INF] * (W + 2) for _ in range(H + 2)]
dist_v = [[INF] * (W + 2) for _ in range(H + 2)]

# スタート地点は移動距離0、
dist_h[start[0]][start[1]] = 0
dist_v[start[0]][start[1]] = 0


# 幅優先探索
que = deque()

# スタート地点には、水平方向と垂直方向両方入れとく
que.append((start[0], start[1], "V"))
que.append((start[0], start[1], "H"))

while que:
    i, j, direction = que.popleft()
    if direction == "H":
        # Hで来た場合(前のマスはV)
        for di, dj in MOVES_V:
            # 次はV方向に移動
            ni, nj = i + di, j + dj
            if S[ni][nj] == "#":
                continue
            if S[ni][nj] == "G":
                print(dist_v[i][j] + 1)
                exit()
            if dist_h[ni][nj] > dist_v[i][j] + 1:
                dist_h[ni][nj] = dist_v[i][j] + 1
                que.append((ni, nj, "V"))
    else:
        # Vで来た場合(前のマスはH)
        for di, dj in MOVES_H:
            # 次はH方向に移動
            ni, nj = i + di, j + dj
            if S[ni][nj] == "#":
                continue
            if S[ni][nj] == "G":
                print(dist_h[i][j] + 1)
                exit()
            if dist_v[ni][nj] > dist_h[i][j] + 1:
                dist_v[ni][nj] = dist_h[i][j] + 1
                que.append((ni, nj, "H"))

print(-1)
```
curl で gRPC の疎通確認をしたい

## 実行コマンド

```sh
printf '\x00\x00\x00\x00\x00' |
  curl \
    -v -s --http2 \
    --data-binary @- \
    --output - \
    -H "Content-Type: application/grpc" \
    -H "TE: trailers" \
    "${GRPC_ENDPOINT:?}/grpc.health.v1.Health/Check" |
  hexdump -C 
```

空のメッセージを `/grpc.health.v1.Health/Check` 宛に送ってあげれば良い。

## 実行例

- リクエスト: `00 00 00 00 00`
  - 最初の 1 バイト `00` は圧縮フラグ（0 = 非圧縮）
  - 次の 4 バイト `00 00 00 00` はメッセージ長（0バイト）

```bash
$ printf '\x00\x00\x00\x00\x00' | curl -v -s --http2 -H "Content-Type: application/grpc" -H "TE: trailers" --data-binary @- --output - "${GRPC_ENDPOINT:?}/grpc.health.v1.Health/Check" | hexdump -C 
... 略 ...
00000000  00 00 00 00 02 08 01                              |.......|
00000007
```

- レスポンス `00 00 00 00 02 08 01`
  - 最初の5バイト `00 00 00 00 02`
    - 最初の 1 バイト `00` は圧縮フラグ（0 = 非圧縮）
    - 次の 4 バイト `00 00 00 02` はメッセージ長（2バイト）
  - 残りの2バイト `08 01`
    - これは Protocol Buffers でエンコードされたメッセージ
    - `08` は [`HealthCheckResponse`](https://github.com/grpc/grpc/blob/4a72b8844de3515f8a58058714de54d1c22a0f16/src/proto/grpc/health/v1/health.proto#L39) の field number `1` のメッセージであることを示している
      - `(field_number << 3) | wire_type` == `(status << 3) | VARINT` == `(1 << 3) | 0` == `08`
      - ref: [Message Structure | Encoding | Protocol Buffers Documentation](https://protobuf.dev/programming-guides/encoding/#structure)
    - `01` は [`ServingStatus`](https://github.com/grpc/grpc/blob/4a72b8844de3515f8a58058714de54d1c22a0f16/src/proto/grpc/health/v1/health.proto#L35) が `SERVING` であることを示している