OmniAICreator/Qiita-1.07M huggingface dataset:
distって何？

# 新人プログラマーの疑問

### vueでプロジェクト作成中の出来事

・pnpm build実行によってdistフォルダが作成される
・仕事でも当たり前のように作っていたが、詳しくは知らない


## pnpm build とは

pnpm buildは、通常、プロジェクトをビルドするために使用されるコマンドです。このコマンドは、プロジェクト内で定義されたビルドプロセスを実行します。

### どのように動作するか：
ビルドプロセスは、package.json内のscriptsセクションに定義されています。
例えば、"build": "tsc"と定義されている場合、TypeScriptのトランスパイルが実行されます。
フレームワークによっては、vite buildやnext buildなど特定のビルドコマンドが実行される場合もあります。

## distフォルダ　とは

pnpm buildを実行すると、プロジェクトのビルド成果物が生成されるディレクトリのことを指します。通常、このディレクトリの名前はdist（"distribution"の略）となっています。

### 内容：

JavaScriptにトランスパイルされたファイル（もしTypeScriptを使っているなら）。
圧縮されたCSSや画像などの静的ファイル。
本番環境で動作可能な形式に加工されたファイル群。

### 目的：

このフォルダにあるファイルは、実際にデプロイされるものです。
開発環境でのコードやツールなどの余分なものを取り除き、本番環境で効率よく動作する形にまとめたもの。

## ビルドする意味
本番環境向けに最適化：

コードを圧縮し、ファイルサイズを小さくすることで、読み込み速度を改善。
モジュールバンドラー（例：Webpack、Vite）を使用して依存関係を1つのファイルにまとめることも可能。
言語の変換：

TypeScriptやSCSSなど、ブラウザやサーバーが直接実行できない形式をJavaScriptやCSSに変換する。
不要なリソースを除外：

開発環境用の設定やツール、コメント、デバッグコードを削除し、本番向けのクリーンな状態にする。
コードの安全性向上：

トランスパイル時にエラーを検出できるため、事前に問題を見つけやすい。

### 例：TypeScriptのプロジェクトをビルドする場合
1. pnpm buildコマンドが実行される。
2. tsconfig.jsonに基づいて、TypeScriptコードが JavaScriptに変換される。
3. 変換されたJavaScriptファイルがdistフォルダに出力される。
4. distフォルダ内のファイルが本番環境にデプロイされる。


### まとめ

- pnpm buildの役割： プロジェクトを本番向けに最適化された形式に変換する。

 - distフォルダ： ビルド結果が格納されるディレクトリで、本番環境で動作するコードが入っている。

 - ビルドの必要性： 本番環境で効率よく、安全に動作させるために不可欠なプロセス。
自己紹介

元事務屋さんの今「WEBアプリケーションエンジニア※（SE）」です。

※会社のスキルにはそう書いてある。

氷河期だったせいで、
アルバイトなのに最初の職は先輩が英語ペラペラだったり、院卒だったりしました。

大手の間を非正規でさまよい(書けませんがあんな会社やこんな会社、あのお客様も！)
なんとか「非正規地◯」から抜け出し、
某テック企業で上記の職を営んでおります。

好きな言葉は「オンスケ」です。

経験職種：経理、営業事務、サポートセンター、PMO、スクラムマスター

徒然なるままに、体当たりテックな記事を書いてまいりますので、
よろしくお願いいたします。
npmパッケージをビルドなしで読み込めるSkypackにおけるエラー解消

Webページで利用していたSkypackのdebounceパッケージが読み込めずJSエラーになっていた。
``` javascript:main.js
import debounce from "https://cdn.skypack.dev/debounce";
```

```
https://cdn.skypack.dev/new/debounce@v2.2.0/dist=es2019
Failed to load resource: the server responded with a status of 500 ()
```

直接見に行ってみても下記のようなレスポンス。
```
Unexpected Error: Build was successful but could not be found.

gOZKgLNzxG6HPjgn9TCJ
```

パッケージは存在するし問題なさそうに見えるが、下記のような記事を見つけた。
バージョン指定をしないとリンクがうまくいかない問題があるようだ。

https://github.com/hotwired/turbo/issues/1074

Skypackのページからnpmの本体githubをたどり、タグの中から最新の一個前のタグを探した。

https://www.skypack.dev/view/debounce

https://github.com/sindresorhus/debounce/tags

<img width="300" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/80263/dc7760e3-5b3e-f1d9-aa09-78c601b7b104.png">

最新のv2.2.0ではエラーになるので、
```
https://cdn.skypack.dev/debounce@v2.2.0
```

一個前のバージョンを指定。
```
https://cdn.skypack.dev/debounce@v2.1.1
```

読み込めた！
```
/*
 * Skypack CDN - debounce@2.1.1
 *
 * Learn more:
 *   📙 Package Documentation: https://www.skypack.dev/view/debounce
 *   📘 Skypack Documentation: https://www.skypack.dev/docs
 *
 * Pinned URL: (Optimized for Production)
 *   ▶️ Normal: https://cdn.skypack.dev/pin/debounce@v2.1.1-EM68BSwmpRS5T8tbaKya/mode=imports/optimized/debounce.js
 *   ⏩ Minified: https://cdn.skypack.dev/pin/debounce@v2.1.1-EM68BSwmpRS5T8tbaKya/mode=imports,min/optimized/debounce.js
 *
 */

// Browser-Optimized Imports (Don't directly import the URLs below in your application!)
export * from '/-/debounce@v2.1.1-EM68BSwmpRS5T8tbaKya/dist=es2019,mode=imports/optimized/debounce.js';
export {default} from '/-/debounce@v2.1.1-EM68BSwmpRS5T8tbaKya/dist=es2019,mode=imports/optimized/debounce.js';
```

### 参考
https://qiita.com/kanta_matsu/items/b7b2a65f6cdfd328e2e7
Raspberry PiカメラのSWモジュール関係性

# この記事について
Raspberry Pi5でカメラを使ったプログラミングをする際に
・過去の仕様が複数ある
・依存関係
で混乱してしまったので備忘録として残しておく

# 関係図
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/540259/683d4436-065e-bdcd-ad3f-6d7c9f9f0665.png)

# SWモジュール
## libcamera
[libcamera](https://libcamera.org/)
Linux, Android用のオープンソースカメラライブラリ
複雑なカメラの制御を吸収してくれるAPIを提供している
カーネルではなく、ユーザースペースのAPI

## Picamera2
[picamera2 manual](https://datasheets.raspberrypi.com/camera/picamera2-manual.pdf)
Raspberry PiのカメラシステムにアクセスするためのPythonライブラリで、libcameraプロジェクトの上に構築されている。libcameraカメラスタックが必要。
Raspberry Pi OS（Bullseye以降）で動作する。

## rpicam-apps
[Camera software](https://www.raspberrypi.com/documentation/computers/camera_software.html)
libcameraを使ったCLIアプリケーション
カメラの接続確認でよく使われる `rpicam-hello` はこれ

古い資料だとlibcamera-*というコマンドが出てくるが、これがrpicam-*に置き換えられた
シンボリックしてあるのでlibcamera-*もまだ使えるが、非推奨
少なくとも新しく何か作るのであれば使わない方が良い

<font color="red">**このlibcameraとライブラリの方のlibcamera(このページで最初に紹介した)が同じ名前なのが混乱するの注意**</font>
019 AI屋さんの　LLMに２００万トークン全文入力　グーグルラボ　超簡単編


019 AI屋さんの　LLMに２００万トークン全文入力　グーグルラボ　超簡単編


グーグルラボの　サンプルプログラムの解説です。
https://www.cloudskillsboost.google

サーバーレスで　streamlitを　デプロイする公式サンプルです。
streamlit, cloudrun, gemini　とてんこ盛りです。


![スクリーンショット 2024-11-23 18.01.23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/237930/b0aa53f8-6a0a-8e2e-a2fe-9a2e171116e0.png)


一通り終わると　下記のようなLLMの　webアプリが　cloudrunで完成します。




Gemini Pro と統合された Streamlit アプリの Cloud Run へのデプロイ





https://www.cloudskillsboost.google/focuses/85991?locale=ja&parent=catalog





GitHub


![スクリーンショット 2024-11-23 17.15.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/237930/bb6a664f-b899-a6c3-26b8-ca3e14c5c1ec.png)




サーバーレスwebアプリ



![スクリーンショット 2024-11-23 9.43.14.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/237930/3fa54d66-b6ab-89f0-bc8d-dbc22e98713b.png)





取説の通りに実行すれば完成するのですが、折角なので少しアレンジして
超簡単バージョンで作ります。

手順

　１、サンプルコードをダウンロード
　２、ローカルでdockerイメージ作成
　３、docker Hubへプッシュ
　４、cloudrun　でデプロイ

です。
特に難しいことはないです。
ほぼボタン　ポチポチで完成です。
若干、サンプル毎にアプリ内の権限設定が必要な場合もあります。

目次

https://qiita.com/bono0/items/dc1d000c98af7e07c9a7


今回も　streamlitを簡単に開発できましたね。全文入力は出来そうです。

　019 AI屋さんの　LLMに２００万トークン全文入力　グーグルラボ　超簡単編

完成です。おめでとうございます。




ー続くー
[初期設定]htmlファイルののtemplate記入方法

HTMLファイルを作成してすぐ下記を実施することで簡単にコーディングを開始できる。

1. ! を入力する。
1. return で雛形が表示される。

```
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
        
</body>
</html>
```
window.location.href に return が必要な理由

JavaScriptのリダイレクト処理でやりがちなミスについて、同じ過ちを繰り返さないよう記事に残します。

## 誤ったイメージ
```javascript
// googleへのリダイレクト処理が実行されれば後続のYahooへのリダイレクトは実行されないはず
if (true) {
    window.location.href = 'https://www.google.co.jp/';
}
window.location.href = 'https://www.yahoo.co.jp/';
```

googleにリダイレクトされるはず。リダイレクト処理が実行中なので後続のYahooへのリダイレクトは実行されないはず。
しかし、実際にはgooleではなくYahooにリダイレクトされてしまう。

## 実際の挙動
googleにリダイレクトされるはずが、Yahooにリダイレクトされてしまう

## なぜか？
googleへのリダイレクト処理が実行されている間、後続のyahooへの処理が実行されるため。
言い換えれば、`return`がないので後続の処理が続けて実行されている。
```javascript
if (true) {
    window.location.href = 'https://www.google.co.jp/';
    // 'return'がないので後続の処理が続けて実行される
}
window.location.href = 'https://www.yahoo.co.jp/';
```

## `return`を記述
```javascript
// googleにリダイレクトされるので問題ない
if (true) {
    return window.location.href = 'https://www.google.co.jp/';
} else {
    return window.location.href = 'https://www.yahoo.co.jp/';
}
```
`return`を記述することで、想定通りGoogleへのリダイレクトが実行され、後続の処理が止まる

## なぜ`return`を書かなくて良いと考えてしまったのか？
あるコードで`return`を書かずに`window.location.href`を実行している箇所がありました。
そのコードは関数の最後に記述されており、後続の処理がないため`return`を書かずとも問題なく動作していました。

恥ずかしながら、「JavaScriptのリダイレクト処理には`return`が不要なんだな」という先入観が生まれ、リダイレクト処理がうまくいかない事態に陥り、解決に時間を費やすことになりました・・・

## 最後に
「他のコードがこうだから」
「たぶんこうなるだろう」
「とりあえずこれ書いておけばいいよね」
少し考えればわかることでも、こうした先入観や思い込みでエラーにハマってしまうことがあります。
思考停止せず、一旦立ち止まって理解を深める姿勢を大切にしていきたいものです。
初心者向け：AレコードやCNAMEレコードなど主要DNSレコードの役割と設定方法

## はじめに
DNS（Domain Name System）は、インターネット上でドメイン名をIPアドレスに変換する仕組みを提供するシステムです。

:::note
**この仕組みの中で、DNSレコードが重要な役割を果たしています。**
:::

この記事では、DNSレコードの基本的な役割と代表的なレコードの種類について解説します。

## DNSレコードとは？
DNSレコードは、特定のドメイン名に関連する情報を記録したデータです。

この情報はDNSサーバーに保存されており、ユーザーがドメイン名にアクセスする際に参照されます。

![スクリーンショット 2024-11-23 17.05.17.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3662571/1a1d86a8-5f35-4a3c-29b0-0ea98a539726.png)
引用画像：https://www.value-domain.com/media/a-record/

:::note warn
**たとえば、「example.com」を入力した際に、そのドメインのIPアドレスがDNSレコードを通じて取得され、ウェブサイトが表示されます。**
:::

## 主なDNSレコードの種類
DNSレコードには複数の種類があり、それぞれ役割が異なります。以下に主要なものをまとめました。

### 1. Aレコード（Address Record）
概要: ドメイン名をIPv4アドレスに紐付けるレコードです。

```bash
example.com.  IN  A  192.0.2.1
```

ウェブサーバーやメールサーバーなどのホストを特定するために使用されます。

### 2. AAAAレコード（IPv6 Address Record）

ドメイン名をIPv6アドレスに紐付けるレコードです。

```bash
example.com.  IN  AAAA  2001:0db8::1
```

IPv6対応が必要な場合に使用されます。

### 3. CNAMEレコード（Canonical Name Record）

ドメイン名を別のドメイン名に紐付けるレコードです。

```bash
www.example.com.  IN  CNAME  example.com.
```

ドメイン名のエイリアス（別名）を作成する際に使用されます。

### 4. MXレコード（Mail Exchange Record）

メールサーバーの情報を指定するレコードです。

```bash
example.com.  IN  MX  10 mail.example.com.
```

:::note warn
**※「10」は優先度を表します。**
:::

メールの配送先を指定します。

### 5. TXTレコード（Text Record）

任意のテキストデータを記録するレコードです。

```bash
example.com.  IN  TXT  "v=spf1 include:_spf.example.com ~all"
```

SPF（Sender Policy Framework）やDKIM（DomainKeys Identified Mail）など、メール認証に利用されることが多いです。

### 6. NSレコード（Name Server Record）

ドメイン名に対応するDNSサーバーを指定するレコードです。

```bash
example.com.  IN  NS  ns1.example.com.
```

ドメインの管理を行うDNSサーバーを指定します。

### 7. PTRレコード（Pointer Record）

IPアドレスをドメイン名に変換するための逆引きレコードです。

```bash
1.2.0.192.in-addr.arpa.  IN  PTR  example.com.
```

主にリモートサーバーの認証に利用されます。

### 8. SRVレコード（Service Record）

特定のサービスを提供するサーバーの情報を記録するレコードです。

```bash
_sip._tcp.example.com.  IN  SRV  10 5 5060 sipserver.example.com.
```

:::note warn
**※「10」は優先度、「5」は重み、「5060」はポート番号です。**
:::

VoIPやチャットサービスなどに利用されます。

### 9. SOAレコード（Start of Authority Record）

ゾーン情報の開始を示すレコードです。

```bash
example.com.  IN  SOA  ns1.example.com. admin.example.com. (
                2024010101 ; Serial
                3600       ; Refresh
                900        ; Retry
                604800     ; Expire
                86400 )    ; Minimum TTL
```

ドメインの管理情報を提供します。


## まとめ

DNSレコードはインターネットを支える重要な要素であり、それぞれが特定の用途に応じた役割を持っています。

:::note
**適切なDNS設定を行うことで、ウェブサイトやメールサービスを正しく機能させることができます。**
:::

DNSの仕組みや設定方法を理解し、必要に応じて活用してみてください！

## 関連記事

https://help.onamae.com/answer/7883

https://wa3.i-3-i.info/word12284.html

https://remacre.jp/column/homepage/8786/
TypeScript基礎 学習記録 #1


JavaScriptを用いたReactの学習が一通り終わったところでTypeScriptを学ぼうと思い、都度メモを残しつつ学習することにした。なお、こちらはTypeScriptの基礎を抑えることを目的としているため、発展的な学習は極力控えて学習を進めていく。

## 私について
24卒、現在はフリーター。実務未経験者です。
情報系の大学を卒業後、キャリアステップをいち早く実現したいという思いから、仕事と通院をしながら勉強をしています。
受託開発or自社開発企業への就職を目指し、Reactを中心にフロントエンドを学習中です。

## 現在のTypeScriptに対しての理解度
現状JavaScriptとの違いがある程度理解できている程度。
TypeScriptを用いた実践講座をUdemyで購入するが何も理解できず敗走したため、具体的な記述方法などは知識ゼロに近いレベル。

## 学習期間
1ヶ月以内。

## 目標
何を以って学習終了とするか、インプット・アウトプットそれぞれで目標を決めておく。

#### :inbox_tray: インプット
・[超TypeScript 完全ガイド 2024
](https://www.udemy.com/share/102AoG3@DhuKDW0rbN5P-0zMhE-AVcJhh0mL7pHhgSIr8e1mxKPtVikUxBGweCpMDYOzy3yKMw==/)

こちらのUdemy講座はTSの知識が体系的に学ぶことができ、最終的にはReactとの連携方法も学習することができるとのことなので、こちらの講義修了を目標とする。先ずはなんとなくな理解が出来れば上出来。しっかりとした理解はアウトプットフェーズで行う。

#### :outbox_tray: アウトプット
こちらはReact中心で個人開発したブログサイトを、TSに置き換えて作り直すことを目標とする。インプットフェーズで使用した教材を見直しながら進めていくことで理解を深めていく。

...エラーは極力自力で解消する。（生成AIに頼るのは最終手段）
FluentBitをDockerで入門する



## 内容
  - localのlogファイルをfluentbitで標準ログ出力
  - PARSERを使った ltsvをjson形式へ変換
  - MULTILINE_PARSERを使って stacktrace を連結する

## 検証

凄い充実している docs
https://docs.fluentbit.io/manual/pipeline/parsers/ltsv

- リポジトリをクローンする
  - https://github.com/GitEngHar/fluentbit 
- 動いているDockerの停止/削除 イメージの削除

```bash
export imagename=customfluentbit:0.1
export containername=fluentbid-01

docker stop $containername
docker rm $containername
docker rmi $imagename
```

- DockerImageを作成

```bash
docker build .  -t $imagename
```

- Dockerを起動する ローカルのtmpディレクトリをマウントする

```bash
docker run --name $containername -v ./tmp:/tmp  $imagename
```

- それぞれに紐づいたログファイルの中身を編集して結果を確認する
  - すでに記載してあるログが検証ログなので、コピーしてペーストする 

## 備忘録

### エラー : pasaerは外部ファイルとして定義せよ

```text
Sections 'multiline_parser' and 'parser' are not valid in the main configuration file. It belongs to 
the 'parsers_file' configuration files.
[2024/11/23 00:55:10] [error] configuration file contains errors, aborting.
```

### Parser
- Parser設定は 以下を合わせる必要がある (設定しないと適用されない)
  - [PARSER] の Name
  - [INPUT] の parser
- MultiLineParserの時は `Multiline.parser` を使う 

## FluentBitについて

fluentbit は TresureData社が公開した fluentdの派生
fluentd は 多機能で複雑なログ処理とか データセンターやら大規模なサーバシステムでは重宝された  
しかし!! Iotシステム や k8s コンテナサービス で 利用したいという要望から 軽量化が求められた
(fluentd は 大分重い)
そこで軽量化 と 機能を絞った fluentbitの爆誕!!
AWS Chatbot で Slack チャットチャネルから Amazon Bedrock とやり取りする

# 概要

概要はタイトル通りなので省略します。アップデート記事は以下の通りです。

https://aws.amazon.com/jp/about-aws/whats-new/2024/09/aws-chatbot-amazon-bedrock-agent-microsoft-teams-slack/


# 設定

ざっくりと、
① Bedrock エージェントを呼び出す権限を Chatbot に付与する
② Bedrock エージェントをチャットチャネルに接続する
③ エージェントとの会話する
です。

## ① Bedrock エージェントを呼び出す権限を Chatbot に付与する

`chatbot.amazonaws.com` に Bedrock エージェントを呼び出す権限 `bedrock:InvokeAgent` が必要です。

```json
{
  "Sid": "AllowInvokeBedrockAgent",
  "Effect": "Allow",
  "Action": "bedrock:InvokeAgent",
  "Resource": [
    "arn:aws:bedrock:aws-region:111122223333:agent-alias/AGENT12345/ALIAS12345"
  ]
}
```

## ② Bedrock エージェントをチャットチャネルに接続する

Bedrock エージェントをチャットチャネルに接続するには、Chatbot コネクタを設定する必要があります。

チャットチャネルで `@aws connector` を入力します。

`@aws connector add connector_name arn:aws:bedrock:aws-region:111122223333:agent/AgentID AliasID` を実行して Amazon Bedrock エージェントを追加します。

## ③ エージェントと会話する

エージェントとの会話を開始するには、次のコマンドを実行します。

`@aws ask connector_name your message` を実行し会話します。


# やってみる

## 必要なリソースのデプロイ

ちょっと時間がなかったので、こちらの記事で紹介してくれている CloudFormation を利用させてもらいました。

https://dev.classmethod.jp/articles/bedrock-agents-chatbot-slack-for-cloudformaiton/

CloudFormation をデプロイすると次のようなリソースがデプロイされます。

![スクリーンショット 2024-11-23 16.05.26.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/c92ee7a7-a776-2dcb-cdff-92c88b70905d.png)

次に、Slack のチャネルで`@aws connector`コマンドを入力し、Bedrock エージェントをチャットチャネルに接続します。

![スクリーンショット 2024-11-23 16.29.10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/fdc29bdf-618c-a75e-c17b-fcc34e10eac7.png)

必要な設定は完了したので、質問してみます。

![スクリーンショット 2024-11-23 16.41.21.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/280929/be0863b9-5261-f561-f601-13a1a22e41df.png)

回答が返ってきました。

まあ、11/23 なんですがね。。。
ReactのRouteとLinkの違い

Reactの`Route`と`Link`は、React Routerライブラリで使用されるコンポーネントですが、それぞれの役割は異なります。

### Route
- `Route`は、特定のパスに対してどのコンポーネントを表示するかを定義します。
- URLとマッチするパスを指定し、そのパスに一致する場合に描画するコンポーネントを指定します。
- 例:
  ```jsx
  <Route path="/about" component={About} />
  ```

### Link
- `Link`は、ユーザーが他のページにナビゲートするためのリンクを作成します。
- HTMLの`<a>`タグのように機能し、クリックすると指定したパスに遷移しますが、ページを再読み込みすることなく遷移します。
- 例:
  ```jsx
  <Link to="/about">About</Link>
  ```
Ubuntu Linux 24.04 LTSのbento/ubuntu-24.04を使う時は、bash-completionをインストールしよう

# What's？

Ubuntu Linux 24.04 LTSからは、UbuntuからVagrantのイメージが提供されなくなりました。

> Starting in Ubuntu 24.04, Ubuntu no longer produces Vagrant images. 

[Ubuntu 24.04 LTS (Noble Numbat) Release Notes / New features in 24.04 LTS / Platforms / Public Cloud / Cloud images / Vagrant](https://discourse.ubuntu.com/t/ubuntu-24-04-lts-noble-numbat-release-notes/39890#p-99950-vagrant)

`ubuntu/noble64`みたいなものがないことになるので、なにか探してこないといけません。

# bento/ubuntu-24.04

VagrantのProviderがVirtualBoxの場合、`bento/ubuntu-24.04`になりそうです。

[bento/ubuntu-24.04](https://portal.cloud.hashicorp.com/vagrant/discover/bento/ubuntu-24.04)

で、このBoxを使う時は立ち上げたらとりあえずbash-completionをインストールしておきましょうという話です。

# 環境

今回の環境です。

```shell
$ vagrant version
Installed Version: 2.4.3
Latest Version: 2.4.3

You're running an up-to-date version of Vagrant!


$ VBoxManage --version
7.1.4r165100
```

使用するVagrant Boxのバージョン。

```shell
$ vagrant box list | grep ubuntu-24.04
bento/ubuntu-24.04            (virtualbox, 202404.26.0, (amd64))
```

# 立ち上げてみる

`vagrant init`してから仮想マシンを立ち上げて、SSHログインするまで。

```shell
$ vagrant init bento/ubuntu-24.04
$ vagrant up
$ vagrant ssh
```

OSのコマンドに補完が効かないので、bash-completionをインストールしておきましょう。

```shell
$ sudo apt install bash-completion
```

今まで使っていた他のUbuntu LinuxのBoxだと入っていることが多かったので、最初は少し驚きました。

bashの補完だけだと物足りないかと思うので、あった方がよいでしょうね。

`Vagrantfile`で起動時にインストールしてもいいでしょう。

```ruby
  config.vm.provision "shell", inline: <<-SHELL
    apt-get update
    apt-get install -y bash-completion
  SHELL
```
Raspberry Piで、Lチカ（LEDチカチカ）してみた！~ with PyConjp2024~

## こんにちは あるいは こんばんは
PyConjp2024に行ってきました！:feet:
![83ACD2EF-5FD1-40EB-BC8C-06C2DFDC24D5-q14my1pnj3nbxfjnmrhd5yswdc.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3190323/d113827f-11c2-6d2c-9ca5-80a192134b5b.jpeg)

そこで知ったRaspberry Piの"Hello world"にあたる「Lチカ」を、初心者がスライドを見ながら、ハンズオンをした記録です。
![F0D9CE4C-ADE0-482E-B2B3-F83CD6BB6071-d8ms8p5a8jgjjgwh41w9685x8r.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3190323/02c7fd5e-a01c-270e-3255-3eb05674db09.jpeg)

私自身、「Raspberry Piは興味あるけど・・・動かすのは難しいんじゃないかな？」と認識しておりました。
が、セッションにて、スピーカーの皆さんが **「語るにはあまりに時間が足りない！！！」** とおっしゃるほどの熱量で話してくださりました。

**その熱に当てられて、
やってみたくなるのが世の常・・・！**

下記セッションのスライドの始めを参考にさせていただきました！(WiFiはちょっとまだ早かった・・・)
[PyConJP2024公式HP](https://2024.pycon.jp/ja/talk/MJ7GA9)
[該当スライド](https://nkm3.org/raspberry_pi_pico_w_network_slide/1)

実際にやってみて感想と、詰まったところについて書きました。

※なお、PyConjp2024に関する内容が中心ではないため、ご注意ください。

### この記事の対象者
Pythonを少しでも書いたがことある方
Raspberry Piが興味がある方
Raspberry Piを知っているがハードルが高いと感じている方


## Lチカとは
その名の通り、LEDをチカチカさせるという言葉の略称です。
LEDライトを「点灯させるコード」と「消灯させるコード」を交互に書いて実行することを指します。
プログラミング言語を学び始めたとき、画面に「Hello World」を表示させるのと同じ役割を持ちます。

# 環境
**使用機材**
- Raspberry Pi Pico W
- ケーブル（USB Type-A → USB Type-B）情報を渡せるもの

**入れたアプリ**
- [uf2ファイル](https://micropython.org/download/RPI_PICO_W/)
- Thonny

# Lチカ完成!
![8C204A42-7581-4BCD-8661-AA2F75735B7C-6okzjxijhpd4mftkidi5h7gfyc.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3190323/23a21edf-bc61-6e9d-0146-198749006f76.jpeg)

上記写真のように、付属のLEDライトが点滅することができました。
初めて触るレベルの初心者ですが、次に記載する内容以外は、スライドを参考に進めることができました。
点滅レベルでは、かなり簡単に行うことができます。
また、ケーブルを直接つなげることによって、Raspberry Pi内部のファイルを直接実行することができるため、お手軽に動かせることがわかりました。
今回使ったRaspberry Pi Pico Wは、温度センサーが内蔵されているため、温度を測ることもできました！
![スクリーンショット 2024-10-03 17.44.10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3190323/24dbd085-1c56-fc83-c05f-2a4193fb6a78.png)
時間にすると、半日程度で環境構築や調査をしながら進めることができるという印象です。

# 個人的にハマったところ
## Raspberry PiのファイルをThonnyで開けない！
Thonnyを初めて触った際、使用中のPCからRaspberry Piに変更する方法がわからず、「ファイルがない！」となってしまいました。

![スクリーンショット 2024-10-03 17.49.36.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3190323/a6c5bd2e-93e8-1f37-9989-a7244b90c1f8.png)

写真の右下の部分をクリックすると、接続したいRaspberry Piを選択できます。
選択した後に、「ファイルを開く」ボタンを押すことで、接続が可能になります。

## uf2ファイルをドラッグ&ドロップしたら、「不正なディスクの取り外し」エラー警告が出た！
調べたところ、これは正常な動きのようです。
入れられなかったのかと焦り、何回も試してしまいましたw
正常に入れられてよかったです。
[調べた際の参考URL](https://ameblo.jp/pta55/entry-12657731791.html)

## ケーブルの種類について
ケーブルには、
- 電気を通すだけのもの
- 電気と情報の両方通すもの

があります。ここを間違えると、コードや環境が合っていても光らないということが起こります。
百均のケーブルではなく、ちゃんとデータ送信ができるケーブルを入手してから作業を行ってください。

# まとめ
私個人のRaspberry Piへの第一印象は、機械工学がわからないと何もできない・低レイヤーの物理層について理解しないと話が成立しない印象でした。
今回、「Lチカ」を行い、Pythonで電気をつけることができました。
Pythonが少しわかれば、面白ことが簡単にできると感じました。
しかし、低レイヤーに関してもっと理解があれば
今回は時間の関係上、Wi-Fiなどの接続までは行いませんでしたが、面白そうなので機会があれば試してみたいと思います。
【標準入力・標準出力】【PHP】paizaスキルチェックのサンプルコードを理解するのに必要な知識

## はじめに
久しぶりにpaizaのスキルチェックをPHPで受けようと思い立ったんですが、忘れている事が多々あったので備忘録を兼ねてPHPのサンプルコードを元にチートシートを作成しました。

## 標準入力・標準出力
ここの概念はスキルテストを行う上で重要ではありません。
スキルテストで求められていることは、後述する**STDINからfgetsメソッドで値を取得して、問題（テスト）を解いて、答えをechoで出力**することです。
厳密な定義を調べるのに時間を割くのはやめましょう。
~~タイトル詐欺かと言われれば返す言葉がありません。~~

## サンプルコード
```:入力される値
2
2 5
3 4
```

```:期待する出力
hello = 2 , world = 5
hello = 3 , world = 4
```

```php:PaizaSampleCode
<?php
$input_line = trim(fgets(STDIN));
for ($i = 0; $i < $input_line; $i++) {
    $s = trim(fgets(STDIN));
    $s = str_replace(array("\r\n","\r","\n"), '', $s);
    $s = explode(" ", $s);
    echo "hello = ".$s[0]." , world = ".$s[1]."\n";
}
?>
```

## fgets
引数に指定したファイルポインタから1行取得する。
※サンプルコードでは「STDIN=ファイルポインタ」です。
※読みこむデータが無くなった場合はfalseを返します。
```php
fgets(STDIN)
// 2
fgets(STDIN)
// 2 5
fgets(STDIN)
// 3 4
fgets(STDIN)
// false
```
https://www.php.net/manual/ja/function.fgets.php

## trim
文字列の先頭および末尾にあるホワイトスペースを取り除く

:::note warn
下記のように文字列の間に存在するホワイトスペースは削除されません
:::

```php
trim("   2 5   ")
// 2 5
// ※2と5の半角スペースは削除されていない
```

https://www.php.net/manual/ja/function.trim.php

## str_replace
第三匹数の文字列に存在する、第一引数を第二引数に変換する。
第一引数を配列にすることで複数指定も可能。
```php
str_replace(array("\r\n","\r","\n"), '', '2 5')
// 文字列'2 5'の中に改行コードが存在すれば空文字に変換する（つまり改行コードの削除）
```

https://www.php.net/manual/ja/function.str-replace.php
## explode
第二引数を第一引数で区切った文字列を配列に格納して返却する
```php
explode(" ", '2 5')
// 空文字で区切って格納するので'2'と'5'
// [2,5]
```
https://www.php.net/manual/ja/function.explode.php


## 文字列連結
文字列をドットで連結出来ます。
変数も連結させることが出来ます。
当然、変数はダブルクウォートで囲む必要はありません。

:::note warn
最後に"\n"が無ければ、改行されずに一行で下記のようになってしまいます。
hello = 2 , world = 5hello = 3 , world = 4
サンプルコードで期待する出力は下記なので"\n"が必要です。
hello = 2 , world = 5
hello = 3 , world = 4
:::
```php
$s = [2,5]
"hello = ".$s[0]." , world = ".$s[1]."\n"
// hello = 2 , world = 5
```
## 最後に
どれも基礎的な内容ですが、スキルテストは実務では意外と使用頻度の低いメソッドや、意識することのない標準入力・標準出力といった概念が出てきます。
久々にスキルテストをやろうと思ったけど、ド忘れしたな〜って時に使っていただければ幸いです。
【Kotlin】合計値を丸めた結果を変えずに、リストの各要素を丸める

```Kotlin
import kotlin.math.absoluteValue
import kotlin.math.ceil
import kotlin.math.floor
import kotlin.math.round

/**
 * 合計値を「偶数に丸め」た値を保ったまま、各要素の値を丸めた、新しいリストを返す。
 *
 * レシーバーであるリストの各要素の値を丸めた新しいリストを返す。
 * レシーバーであるリストの全要素の合計値を「偶数に丸め」た値と、返値であるリストの全要素の合計値は、一致する。
 *
 * 「偶数に丸める」とは次のような処理である。
 * - 端数が 0.5 より小さければ切り下げる。
 * - 端数が 0.5 なら偶数側に丸める。（0.5 加えた値が偶数なら 0.5 加える。0.5 減じた値が偶数なら 0.5 減じる。）
 * - 端数が 0.5 より大きければ切り上げる。
 *
 * 各要素については、端数を「0 から合計値への方向に丸め」た場合の変化量が小さいものを優先して「0 から合計値への方向に丸め」、
 * 残りを「合計値から 0 への方向に丸め」る。
 * 合計値が 0 の場合は、合計値が正であると考える。
 * レシーバーに同じ値の要素が複数含まれていたとき、それぞれを丸めた結果が同じ値になるとは限らない。
 *
 * 例えばレシーバーが [0.8, 0.1] の場合、全要素の合計値は 0.9、合計値を偶数に丸めると 1.0。
 * 各要素の端数を 0 から合計値 0.9 への方向（正の方向）に丸める（つまり切り上げる）と [1.0, 1.0]。
 * その変化量は [0.2, 0.9]。
 * そのため、変化量が小さいインデックス 0 の要素を切り上げ、変化量が大きいインデックス 1 の要素を切り下げて、
 * 返値は [1.0, 0.0] となる。
 * この合計値は 1.0 で、レシーバーの合計値を偶数に丸めた値と一致する。
 *
 * 元のリストの全要素の合計値が有限でない（すなわち [Double.NaN], [Double.POSITIVE_INFINITY], [Double.NEGATIVE_INFINITY] のいずれかである）場合は、
 * 各要素を偶数に丸める。
 * この場合も合計値を偶数に丸めた値は保たれる。
 */
fun Iterable<Double>.roundedElementsToPreserveSum(): List<Double> {
    val numberList = this.toList()

    // 合計値を偶数に丸めた値
    val roundedSum = round(numberList.sum())

    // 合計値が有限でない場合
    if (roundedSum.isFinite().not()) {
        // 全ての要素を偶数に丸めたリストを返す。
        return numberList.map { round(it) }
    }

    // roundUp: 端数を 0 から合計値への方向に丸める関数
    // roundDown: 端数を合計値から 0 への方向に丸める関数
    val (roundUp, roundDown) =
        if (roundedSum >= 0) {
            ::ceil to ::floor
        } else {
            ::floor to ::ceil
        }

    // 各要素を roundDown した値の合計値
    val sumOfRoundedDown = numberList.sumOf { roundDown(it) }

    // 「合計値を偶数に丸めた値」と「各要素を roundDown した値の合計値」の差。
    // 端数がある要素について、この数の要素を roundUp し、残りの要素を roundDown すれば、
    // 合計値を丸めた値が変わらないように各要素を丸められる。
    val roundingUpCount = (roundedSum - sumOfRoundedDown).absoluteValue.toInt()

    return numberList
        .asSequence()
        // 後で元の順番に並べ直せるようにするため、インデックス付きにしておく。
        .withIndex()
        // roundDown した場合の変化量が大きい（roundUp したときの変化量が小さいが 0 ではない）順にソートする。
        .sortedByDescending { (_, number) ->
            (number - roundDown(number)).absoluteValue
        }
        // roundDown した場合の変化量が大きい順に roundingUpCount 個を roundUp し、残りを roundDown する。
        .let { sorted ->
            val roundedUp = sorted.take(roundingUpCount).map { it.copy(value = roundUp(it.value)) }
            val roundedDown = sorted.drop(roundingUpCount).map { it.copy(value = roundDown(it.value)) }
            roundedUp + roundedDown
        }
        // 元の順番に並べ直す。
        .sortedBy { (index, _) -> index }
        // インデックスを除く。
        .map { (_, roundedNumber) -> roundedNumber }
        .toList()
}
```

／以上
LILYGO T-Deck Plus GPSを試す

LILYGO T-Deck(無印)とLILYGO T-Deck Plusの大きな違いはGPSが標準搭載になったこと。
ただ曲者なのが、中華らしいというかなんというか届くまでどのGPSモジュールが搭載されていないかわからない。
(今の所 __u-blox__  か __l76k__ のどっちからしい。)

# ライブラリのインストール

examplesのプロジェクトは定番のTinyGPS++を利用するので、PlatformIOでインストール

# 動作確認
サンプルプロジェクトを動作させると

ターミナルに受信状態が表示される
未受信状態だと、INVALID
Location: INVALID  Date/Time: 1/1/2024 00:00:0.00

データを受信すると
Location: xx.yyyyyyyy,zzz.zzzzz  Date/Time: 1/1/2024 00:00:00.00
のような表記になって受信できていることがわかる。

特に問題なく動いた

# 自作系GPSでのハマりどころ
M5Stackの時にハマったんだけど、スマホ等のGPS機器と違って受信に時間がかかる。
というかスマホは位置情報を常時更新しているからGPSが受信できていなくても位置情報が
なんとなく表示される。
だから、スマホで位置でるのにモジュールでは表示されない．．．不良かも！！
ってなる。

<font color="red">__空の見える所にいって1分ほど待ちましょう__　</font>
rails7.0のdelete効かない

JavaScriptが動かずにdeleteアクションが起こらないのは、rails7.0になってからujsが廃止された。turboを使って書く必要がある。

rails7.0公式
https://guides.rubyonrails.org/v7.0/working_with_javascript_in_rails.html#replacements-for-rails-ujs-functionality

rails7.0ではujsが廃止された。turboを使う。

rails 7.0 turboの正しい書き方
https://www.hotrails.dev/turbo-rails
[React] 画面要素を関数で出力する

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

# Reactで画面要素を関数で出力する理由
Reactはコンポーネントベースのアーキテクチャを推奨しているから

# なぜ`コンポーネントベースのアーキテクチャを推奨`しているのか??
1. 再利用性の向上
1. 状態やプロパティに応じた動的レンダリング
1. 宣言的UIの実現
1. コンポーネントの分割によるモジュール化

# HTML
~~~html:index.html
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <title>React App</title>
  </head>

  <body>
    <noscript> You need to enable JavaScript to run this app. </noscript>
    <div id="root"></div>
  </body>
</html>
~~~

# JavaScript
## 関数を使用**しない**場合
~~~jsx:index.js
import { StrictMode } from "react";
import { createRoot } from "react-dom/client";

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

root.render(
  <StrictMode>
    <h1>こんにちは!</h1>
  </StrictMode>
);
~~~

## 関数を使用**する**場合
~~~diff_jsx:index.js
import { StrictMode } from "react";
import { createRoot } from "react-dom/client";

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

+const App = () => {
+  return (
+    <>
+      <h1>こんにちは!</h1>
+    </>
+  );
+};

root.render(
  <StrictMode>
+    <App />
  </StrictMode>
);
~~~

# 参考リンク
- [Reactのコンポーネント・ベース・アーキテクチャ：ケーススタディ](https://appmaster.io/ja/blog/riakutokonponentobesuakitekuchiya)
- [Mastering Component-Based Architecture with React](https://samuellawrentz.com/hacks/react/mastering-component-based-architecture/)
初心者向け：Webサーバーとクライアントの違いを完全解説

# 初心者向け：Webサーバーとクライアントの違いを完全解説

Webシステムを理解するために欠かせないのが、Webサーバーとクライアントの役割です。この記事では、Webサーバーとクライアントの違いを初心者にも分かりやすく解説し、よく混乱する技術用語や呼び名についても整理していきます。これからWeb開発やシステム運用を学ぼうとする方に向けた内容です。

## 概念図で理解する Webシステムの基本

Webシステムの全体像を理解するために、まずは以下のような概念図をイメージしてみましょう。

[クライアント] ← → インターネット ← → [Webサーバー]


- **クライアント**：ユーザーが操作する側。ブラウザやアプリケーションなど。
- **インターネット**：クライアントとWebサーバーを繋ぐ通信網。
- **Webサーバー**：リクエストを受けてデータ（HTMLや画像など）を返す。

この関係を頭に入れた上で、各役割の詳細を見ていきましょう。

---

## Webサーバーとクライアントの役割

### Webサーバーとは？
Webサーバーは、インターネット上でリクエストを受け取り、そのリクエストに対して適切なレスポンス（例えば、HTMLファイルや画像など）を返す役割を持っています。一般的には、Webアプリケーションのコードや静的ファイルを保存して、クライアント（主にブラウザ）からのアクセスに応じて処理を行います。

例えば、ユーザーがWebページを開く際に、クライアント（ブラウザ）がWebサーバーにリクエストを送信し、そのレスポンスとしてHTMLや画像が返されます。

### クライアントとは？
クライアントは、ユーザーが操作する側、つまりブラウザやアプリケーションなどがこれに該当します。ユーザーがWebページを開く際、クライアントがWebサーバーにリクエストを送信し、サーバーから返されたデータを表示します。クライアントは、ユーザーと直接的にやりとりをする部分です。

例えば、ブラウザを通じてGoogleを検索したり、SNSを操作する際の操作がクライアント側の役割です。

---

## 技術用語の違いを整理

### マネージャー vs エージェント
初心者が混乱しやすい用語の一つに「マネージャー」と「エージェント」があります。これらは、Webシステムの内部構造や他のシステムでよく登場しますが、Webサーバーとクライアントの話とは少し異なる概念です。

- **マネージャー**：システム全体を監視・管理し、複数のエージェントを制御する役割を持つプログラム。例えば、サーバー管理ツールや、システム全体を調整する役割を担います。
- **エージェント**：マネージャーから指示を受けて、特定のタスクを実行するプログラム。例えば、システムの一部として動作するアプリケーションやサーバープログラムなどです。

これらの用語が登場するのは、Webシステムの運用や管理の分野で、複数のサーバーやサービスが協力して動作する場合に重要になります。初心者の段階では、あまり深く考える必要はありませんが、システム全体の理解が進んでいくと重要になります。

---

## Webサーバーとクライアントの整理

### 役割の整理
Webサーバーとクライアントについて、改めて役割を整理してみましょう。

- **Webサーバー**：データを提供する役割。クライアントからのリクエストを受け取り、必要なデータ（HTML、画像、CSSなど）を返します。Webサーバーは、リクエストが来るまで待機しており、処理が必要なときにのみ動作します。
- **クライアント**：リクエストを送信する役割。ユーザーがWebページを表示するために、クライアントがWebサーバーにリクエストを送り、そのレスポンスを受け取って画面に表示します。

このように、**Webサーバー**は「サーバー側」、**クライアント**は「ユーザー側」という形で、役割が分かれています。

---

### Webサーバーとクライアントの関係

- **Webサーバー**と**クライアント**は、リクエストとレスポンスを通じてやり取りを行います。クライアントは情報をリクエストし、サーバーはその情報をレスポンスとして返します。
- **Webサーバー**と**クライアント**は、物理的には異なる場所に存在することが多いですが、インターネットというネットワークを通じて繋がっています。

これらのやり取りがWebシステムの基本的な通信となり、サーバーとクライアントの間でデータのやり取りを行うことにより、ユーザーはインタラクティブにWebアプリケーションを利用できます。

---

## まとめ

Webサーバーとクライアントは、インターネット上で通信を行うための非常に重要な役割を担っています。混乱しやすい技術用語や呼び名についても整理して、基本的な役割をしっかり理解することが大切です。

- **Webサーバー**は、リクエストを受けてレスポンスを返す。
- **クライアント**は、リクエストを送ってレスポンスを受け取る。

これらを理解することで、Webシステム全体の流れを把握でき、より深い理解が得られます。理解が進んだら、次はサーバーレスアーキテクチャやクラウドサービスについても学んでいきましょう！

---

### 注意
Webシステムにおける**サーバーレスアーキテクチャ**（例：AWS LambdaやFirebase Cloud Functions）では、従来のWebサーバーの概念とは異なるアプローチが取られています。サーバーレスでは、サーバーが完全に隠蔽され、リクエストに対して処理が自動で行われます。これは、サーバーの管理が不要なため、従来の「Webサーバー」という概念にとらわれず、柔軟なシステム設計が可能になります。

---

:::note info
もしこの記事が役に立ったと思ったら、ぜひ「いいね」やコメントをお願いします！
:::
Python ファイルの改行コードを一括でLFへ変換する


本記事では、テキストファイルの改行コードをLF（ラインフィード）に変換する方法をまとめます。

Windows環境で作成・編集したファイルや、Windowsサーバー経由でコピーしたファイルは、改行コードがCRLF（キャリッジリターン＋ラインフィード）になります。これをLinux環境で使用すると、ファイル中に`^M`と表示されたり、`SyntaxError`が発生したりすることがあります。  
これを防ぐため、改行コードをLFに変換する方法を紹介します。


## 方法 1: エディタでの手動変換

### VSCodeの場合
1. ファイルを開く。
2. 右下の「CRLF」をクリックして「LF」に変更。
3. 上書き保存。

### 他のエディタ
ほとんどのエディタに改行コードの変更機能が備わっています。

---


## 方法 2: `replace()` を使ったバイナリモードでの変換

Pythonで改行コードをバイナリモードで置換する例です。

```python
def convert_file_to_lf(file_path):
    with open(file_path, 'rb') as f:
        content = f.read()

    # 改行コードを LF に統一
    new_content = content.replace(b'\r\n', b'\n').replace(b'\r', b'\n')

    with open(file_path, 'wb') as f:
        f.write(new_content)

    print(f"Converted: {file_path}")

# 対象ファイルを指定
target_file = "path/to/your/file.py"
convert_file_to_lf(target_file)
```

---

## 方法 3: `open()` を使ったテキストモードでの変換

改行コードをテキストモードで統一する方法です。

```python
def convert_file_to_lf_text_mode(file_path):
    with open(file_path, 'r', newline='') as f:
        content = f.read()

    with open(file_path, 'w', newline='\n') as f:
        f.write(content)

    print(f"Converted to LF: {file_path}")

# 対象ファイルを指定
target_file = "path/to/your/file.py"
convert_file_to_lf_text_mode(target_file)
```

`newline=''` を指定して開くことで、Pythonが改行コードを正しく解釈します。書き込み時に `newline='\n'` を指定してLFに変換します。

---

## 方法 4: `subprocess` で dos2unix コマンドを利用

`dos2unix` ツールを使う方法です。ツールがインストールされていれば簡単に利用できます。

```python
import subprocess

def convert_file_to_lf_dos2unix(file_path):
    try:
        subprocess.run(['dos2unix', file_path], check=True)
        print(f"Converted using dos2unix: {file_path}")
    except FileNotFoundError:
        print("dos2unix コマンドが見つかりません。インストールしてください。")
    except subprocess.CalledProcessError:
        print("変換中にエラーが発生しました。")

# 対象ファイルを指定
target_file = "path/to/your/file.py"
convert_file_to_lf_dos2unix(target_file)
```

`dos2unix` はWindowsでもWSLを利用して動作させることができます。

---

## 方法 5: sed コマンドを利用

LinuxやmacOSなどで、`sed` コマンドを利用する方法です。

```python
import subprocess

def convert_file_to_lf_sed(file_path):
    try:
        subprocess.run(['sed', '-i', 's/\r$//', file_path], check=True)
        print(f"Converted using sed: {file_path}")
    except subprocess.CalledProcessError:
        print("変換中にエラーが発生しました。")

# 対象ファイルを指定
target_file = "path/to/your/file.py"
convert_file_to_lf_sed(target_file)
```

`sed -i 's/\r$//'` は、行末のCRを削除して改行をLFに統一します。

---

## 方法 6: `pathlib` を使った簡潔な方法

Pythonの`pathlib`を利用したシンプルな方法です。

```python
from pathlib import Path

def convert_file_to_lf_pathlib(file_path):
    file = Path(file_path)
    content = file.read_text(encoding='utf-8').replace('\r\n', '\n').replace('\r', '\n')
    file.write_text(content, encoding='utf-8')
    print(f"Converted using pathlib: {file_path}")

# 対象ファイルを指定
target_file = "path/to/your/file.py"
convert_file_to_lf_pathlib(target_file)
```

---

以上の方法を活用することで、環境や用途に応じた柔軟な改行コードの変換が可能です。


# 参考

1. [Python ファイルの改行コードを一括でLFへ変換する](https://hk29.hatenablog.jp/entry/2022/01/21/223611)
1. [【備忘録】dos2unix 改行コード変換](https://qiita.com/kabosu-s/items/d46a98b067114f0d927c)
1. ChatGPT
nvidia gpuをつんだPCにインストールしたubuntuの初期設定

# はじめに
前回、NVIDIA GPUを搭載したPCにubuntu 24.04 Desktopをインストールしたので、引き続き初期設定をしていく。gpuに関係ない設定も一部ある。

# ssh
ローカルネットワーク内からSSHできるようにするためにopen-sshをインストールする。

```sh
sudo apt install openssh-server
sudo systemctl status ssh # 確認
```

参考: [SSH接続のための設定まとめ](https://qiita.com/010Ri/items/0a09356633655b5613ee)
# avahi-daemon（mDNS）
IPアドレスではなくホストネームでsshできたほうが便利なため、mDNSを有効化する。このためにavahi-daemonをインストールする。

```sh
sudo apt update
sudo apt install avahi-daemon
sudo systemctl start avahi-daemon
sudo systemctl enable avahi-daemon
```

`ssh USERNAME@HOSTNAME.local`みたいなコマンドでsshできればOK

参考: [UbuntuでmDNSを有効化する](https://qiita.com/Galvalume29/items/80a9ba42012a80e86bca)
# uvのインストール
uvをメインに使っているのでインストールする。
uvのインストールコマンドを実行したらcurlがないといわれたのでcurlのインストールから。

```sh
sudo apt install curl
```

uvのインストール

```sh
# On macOS and Linux.
curl -LsSf https://astral.sh/uv/install.sh | sh
```

確認（.bashrcへの追記は自動でされるので不要なはず）

```sh
source ~/.bashrc
uv --version
```


# cudaのインストール
- nvidia-smiの出力から、推奨のcudaバージョンを確認（上の方に書いてある）。12.6だった。
- 「cuda 12.6 install」などで検索しNVIDIAのダウンロードページに遷移、適切なOSを選択し、インストールコマンドを表示させる。cuda-toolkitのコマンドをターミナルで実行していく。
- nvidia-driversのinstallコマンドも下の方にあるが、すでにインストール済みなのでスキップ。nvidia-smiの結果が表示される状態であれば、スキップで問題ない。
- パスを通す
  ```sh
  export PATH="/usr/local/cuda/bin:$PATH"
  export LD_LIBRARY_PATH="/usr/local/cuda/lib64:$LD_LIBRARY_PATH"
  ```
- 確認
  ```sh
  nvcc --version
  ```

# torchからのcuda呼び出し確認
cudaのインストールが完了したら、torchから呼び出せるか確認する。

uvでテスト用の仮想環境を作成

```sh
mkdir torchtest
cd torchtest
uv venv
uv pip install torch
uv pip install "numpy<2"
```

torchtestディレクトリにチェック用のスクリプトを作成。

```python:cudatest.py
import torch

# CUDA が利用可能か確認
if torch.cuda.is_available():
    print("CUDA is available!")
    print("Device Name:", torch.cuda.get_device_name(0))
else:
    print("CUDA is not available.")
```

uvから実行。

```sh
uv run cudatest.py
```

```
CUDA is available!
Device Name: NVIDIA GeForce RTX 4060 Ti
```

# dockerのインストール
[Install Docker Engine on Ubuntu](https://docs.docker.com/engine/install/ubuntu/)に従う。
インストール後のサービス起動コマンド`sudo service docker start`は`sudo systemctl start docker`でもよさげ。enableは自動でされているはず。

## sudoなしでdockerを使えるようにする設定
dockerをインストールすると自動でdockerというユーザが追加されているはず。確認方法は以下。

```sh
grep docker /etc/group
```

追加されていれば、以下のコマンドを実行する。

```sh
sudo usermod -aG docker $USER
```

sshで操作している場合はexitして再度ログインすると、dockerコマンドがsudoなしで使えるはず。

# dockerからGPUを使えるようにする
[Installing the NVIDIA Container Toolkit](https://docs.nvidia.com/datacenter/cloud-native/container-toolkit/latest/install-guide.html)に従う。
optinalの実験的な機能を使うための設定はやらなかった。
configuring dockerも実施する。

## 確認
以下のコマンドを実行

```sh
docker info | grep -i nvidia
```

```
WARNING: bridge-nf-call-iptables is disabled
WARNING: bridge-nf-call-ip6tables is disabled
 Runtimes: io.containerd.runc.v2 nvidia runc
```

最終行の表示により正しくインストールできていそうだが、warningも同時に出ていた。dockerからホストネットワークへのアクセスに関係する警告らしい。無くす方法も調べればありそうだったが、一旦無視する。

[Running a Sample Workload](https://docs.nvidia.com/datacenter/cloud-native/container-toolkit/latest/sample-workload.html)も試してみる。

```sh
docker run --rm --runtime=nvidia --gpus all ubuntu nvidia-smi
```

コンテナ経由でnvidia-smiを実行していると思われる。nvidia-smiの出力が表示されればOK。

# おわりに
他にもやりたくなることはありそうだが、一旦区切りにしておく。
【備忘録】VSCodeでC++デバッガの設定をする

# 環境
元のOS win11 or mac Monterey 12.7.6
docker desktop
ubuntu24.04.1(noble numbat)
VSCode

# 前提
dockerでubuntuを動かしてVScodeでリモート接続をしてその中で作業をする
C++,gccは既にインストール済み

:::note info
gccはC言語のコンパイラ、g++はgccに含まれているC++のコンパイラ
gdb(gnu debugger)はデバッガーのこと
:::


# 必要なファイルを作成する
launch.json

:::note info
目的: デバッグ構成を定義する。
場所: .vscode ディレクトリ内。
内容: デバッガの種類、実行ファイルのパス、引数、作業ディレクトリ、環境変数など。
:::

tasks.json

:::note info
launch.jsonから指定したlavelを呼び出される
目的: ビルドやその他のタスクを定義する。
場所: .vscode ディレクトリ内。
内容: コンパイル、テスト、デプロイなどのタスクを自動化するための設定。
各タスクについて補足
ビルドタスク: プログラムをコンパイルするためのタスクを定義。
テストタスク: 単体テストや統合テストを実行するタスクを定義。
デプロイタスク: アプリケーションをデプロイするためのタスクを定義。
:::

# 作業概要
launch.jsonでデバッグの設定を記述してtasks.jsonに記述してあるビルドタスクを呼び出す

# 躓いたところ
### gdbが入っていない
下記コマンドを使用してubuntuにインストールする
~~~shell
sudo apt-get install gdb
~~~

### ルートディレクトリのinput.txtに記載したものを入力として渡せない
launch.jsonのargsに下記を追加する
~~~shell
"args": ["<","${workspaceFolder}/input.txt"]
~~~
:::note info
${workspaceFolder}は現在作業中フォルダのルートディレクトリという意味
:::

# 設定ファイル
~~~json:lauch.json
{
    "version": "0.2.0",
    "configurations": [
        {
            "name": "C++ Debug",
            "type": "cppdbg",
            "request": "launch",
            "program": "${workspaceFolder}/a.out",
            "args": ["<","${workspaceFolder}/input.txt"],//rootディレクトリのinput.txtを標準入力として受け取る記述
            "stopAtEntry": false,
            "cwd": "${workspaceFolder}",
            "environment": [],
            "externalConsole": false,
            "MIMode": "gdb",
            "setupCommands": [
                {
                    "description": "Enable pretty-printing for gdb",
                    "text": "-enable-pretty-printing",
                    "ignoreFailures": true
                }
            ],
            "preLaunchTask": "build",//task.jsonで呼び出したい機能
            "miDebuggerPath": "/usr/bin/gdb",//デバッガの場所を指定する
            "logging": {
                "trace": true,
                "traceResponse": true,
                "engineLogging": true
            }
        }
    ]
}
~~~

~~~json:tasks.json
{
    "version": "2.0.0",
    "tasks": [
        {
            "label": "build",//launch.jsonに呼び出されるときの名前
            "type": "shell",
            "command": "g++",
            "args": [
                "-g",
                "${file}",
                "-o",
                "${workspaceFolder}/a.out"
            ],//ターミナルで実行されるコマンド
            "group": {
                "kind": "build",
                "isDefault": true
            },
            "problemMatcher": ["$gcc"]
        }
    ]
}
~~~
LILYGO T-Deck Plusで遊ぶ

Lilygo からリリースされているT-Deck Plusが手元に届いたから遊んで行きたいと思います

LILYGO T-Deck Plus
![スクリーンショット-2024-08-14-22.53.47.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1039628/bcc43628-b142-ba64-ff73-21c50839c251.jpeg)
https://lilygo.cc/products/t-deck-plus

　中国のLILYGOブランドから発売されていたT-DeckにGPSが標準搭載されて
その結果Groveが使えなくなっています。（端子は残ってる）

　m5stackはボード設定とかPlatformIOに標準であったけど、T-DECK Proは無いので
ボード設定から始める必要がある。

液晶解像度：320 x 240

# ボード設定を追加
C:\Users\(ユーザ名)\.platformio\platforms\espressif32\boards
等にボード設定の.jsonが置かれているので、LILYGOのGitHubからT-Deck-Pro.jsonを
持ってきてフォルダにコピーする。（というかGitHubから全部クローンしておこう）

# プロジェクトの作成
・VSCordのPlatformIOからNew Project
・platformio.iniの内容をGitGubの内容に変更。
・libとexamplesの内容をプロジェクトフォルダにコピー。

# Hello World
とりあえず定番の<font color="red">**Hello World**</font>をやってみる。
\examples\HelloWorld\ フォルダのHelloWorld.inoとutilities.hを \srcにコピー
してコンパイルして転送。

# なんで？？
サンプルのplatformio.ini の記載が
platform = espressif32@6.3.0
となっている。
本稿作成時のespressif32の最新版は6.9.0
最初何も考えずに最新版でコンパイルしたら
 tft.begin();
 でリブートループに。
6.3.0でコンパイルしたら問題なく作動。

こういうの気になるなぁ．．．
【ChatGPT】論理的に分析するPrompt。


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

　今回は、論理的に分析するPromptです。

:::note info
本記事は、ChatGPT（有料版）
で行なっております。画像は
ありません。　あしからず。
:::
　ChatGPT等の動作状況を知らせる
　　OpenAIのステータスページ。
　　　[OpenAIステータス](https://status.openai.com/)

***
　まずは、ニュース。

　一昨日（2024/11/21）の
　　シンガポールで行なわれた
　　　OpenAIのDevDayに
　　　　参加された方が、
　　　　　レポートをあげて
　　　　　　くれました。
　[Albertus Angga Raharjaさんポスト](https://x.com/albertusdev/status/1859897398073717091?t=uws-Fe_LicNSDaeKg6ihWg&s=19)

　ここに載せるには
　　非常に細かいので
　　　割愛させてください。

　主に、API絡みの話てした。
　　o1についての言及は
　　　なかった模様です。
***
　さて、本題です。

　今回は、論理的に分析するPromptです。

　Taiyoさんという方が
　　ポストしてくれました。
　　　[Taiyoさんポスト](https://x.com/taiyo_ai_gakuse/status/1859549924230324463?t=jNWWh_LeybPGDQam_jSnnQ&s=19)

　ここでは、
　　ほぼそのまま、
　　　使います。
```Text:論理的に分析するPrompt
「＊＊＊」

以下の3ステップで論理的に分析してください。

1. 論理抽出：与えられた情報から重要な前提条件と論理関係を抽出してください。

2. 論理拡張：抽出した条件に基づいて、追加の可能性や関連する推論を展開してください。

3. 論理翻訳：分析結果を自然な表現で分かりやすく説明してください。

4. 結論を導き出してください。
```

　書き加えたのは
　　・「＊＊＊」
　　・番号（ChatGPTが加えました）
　　・4の結論
　です。

　最後の“論理翻訳”は
　　自然な表現での説明です。
　　　他言語からの翻訳とは違います。

　なお、
　　このPromptは
　　　ウェブ検索のON/OFFは
　　　　関係なく動きます。

　　設定で、
　　　ウェブ検索OFFしている場合は
　　　　内部知識のみでの出力に
　　　　　なります。
　　　　　　そこは意識しておいて
　　　　　　　くださいね。

　みなさんの
　　作品制作の糧に
　　　なれば、幸いです。

　今回は、ここまで。
VS Code - .d.tsファイル(型定義ファイル)の効用

# はじめに
MH ソフトウェア & サービスが開発・公開しているアプリケーションは、Microsoft社のVisual Studio Code(以後、VS Code)でコーディングされています。  
***
「そもそも.d.tsファイルって、TypeScriptだろ!」と言う声もあると思います。  
VS CodeでJavaScript編集する時、.d.tsファイルは有効になります。そもそもTypeScriptって、JavaScriptの拡張ですし。

JavaScryptでinputと言うクラスを使用して、入力タグを作成する場合、input.d.tsファイルが無い場合はlet input;の上にマウスカーソルを移動すると  
![no_d_ts.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/569469/73ecd3e9-e130-b622-c9a0-33f8334e12b8.jpeg)  
inputはanyとなります。  

また、input.まで入力しても、入力補助は出ません。  
![no_d_ts1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/569469/0f8e12fb-e7b9-51f6-e7bf-a8ce11b54be7.jpeg)  

JavaScriptソースに下記の行を追加します。  
```Javascript
/// <reference path='../html/input.d.ts'/>
```
input.d.tsはRun on Saveで作成したファイルです。  
let input;の上にマウスカーソルを移動すると  
![at_d_ts.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/569469/9da613fd-ef91-1ebe-656c-542c1cbd0bf7.jpeg)  
inputはIInputとなります。  

また、input.まで入力すると  
![at_d_ts1.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/569469/4e3ad36a-be75-003a-cbfa-fd4f50e4dc4d.jpeg)  
入力補助一覧が表示されます。キーストロークが減らせます。  

***
[Webアプリケーションサーバ AiR](https://qiita.com/MH-SS/items/7a99e799e4988fdad2cc)
***
[弊社webページ: AiR](https://mhss.server-on.net/?f401c=Index&ae504=air)
MuleSoft Composer 接続に関するまとめ

[MuleSoft Composerまとめに戻る](https://qiita.com/Keiji_otsubo/items/ef2fdd213551168c360b)

-----------------------
+ [MuleSoft サポート チケットをオープンできるように、Salesforce アカウントを MuleSoft アカウントに接続しようとしています。接続されているアカウントを確認しましたが、組織を選択できません。](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V00007W8LNa)

:::note
Please check this article. 

https://help.salesforce.com/s/articleView?id=000395906&type=1
:::

+ [これは、Azure AD Enterprise アプリにユーザーを追加し、その方法で Anypoint にログインした場合、そのユーザーは新しい Mule ユーザーとして自動的に追加され、事後的にアクセス許可を管理することになるということでしょうか? ](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V00007YvmNK)

:::note
はい、そのとおりです。彼らは新しい Mule ユーザーとして表示されます。ユーザーを Anypoint に割り当てることなく Anypoint Teams に参加させる場合は、アプリ登録でアプリ ロールを作成し、Azure AD グループをそれらのロールに結び付けることもできます。
:::

+ [SalesforceとMulesoft(Anypoint Platform)のSAML連携について](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V00007YwgFy)

:::note
Mulesoftの設定はよく理解できていなのですが、以下のヘルプが関連してそうな感じです。

Map Single Sign-On Users to Roles or Teams
https://docs.mulesoft.com/access-management/map-users-roles-teams
:::

+ [Mule 4.5.0 コミュニティ エディション用の OAuth2?](https://trailhead.salesforce.com/trailblazer-community/feed/0D54V00007ifeLq)

:::note
Please add the below dependency in POM.XML or add the OAuth Module from the pallet. 

```
	<dependency>
			<groupId>org.mule.modules</groupId>
			<artifactId>mule-oauth-module</artifactId>
			<version>1.1.21</version>
			<classifier>mule-plugin</classifier>
	</dependency>
 ```
 :::
GitHub Actionsの仕組み

## はじめに
この記事ではGitHub Actioins(以下Actions)の仕組みやについて書いていき、簡単なハンズオンも実施してみます。
普段何気なく使っていたActionsの裏側で何が行われているかや、概念的な部分を特に詳しく書いていこうと思います。

## 仕組み
Actionsの実行環境としては主に、以下の2パターンがあります。
1. GitHubが用意してくれる仮想マシン上で行う"GitHub仮想ホストマシン型"
1. 自分で実行マシンを用意する"セルフホスト型"

それぞれメリット、デメリットありますが、”GitHub仮想ホストマシン型”は自分で実行環境を用意する必要がない分すぐに始められ、actions実行用のサーバー運用も必要ありません。
その分Actionsの実行時間に制限等はあります。

”セルフホスト型”は自分でActionsの実行環境を用意する必要がありますが、Actionsの時間制限がなかったり、クレデンシャル等の機密情報を自社で管理できるといったメリットがあります。
今回は"GitHub仮想ホストマシン型"の仕組みで解説していきます。

そして、Actionsの中身を見ていくといくつかの要素があります。
- on
    - Actionsが実行されるトリガーを指定
- job
    - actionsの一番大きな単位。job単位ごとに別々の仮想マシンのホスト上で実行
- runs-on
    - 仮想マシン上で動くOSを指定
- steps
    - jobの中で順番に実行するコマンドを含める
- run
    - Steps内で順番に実行するコマンドを記載する

以下に図解します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3492874/e5ad903b-189e-abd3-c91c-148af2237b03.png)
注意点として、Stepsは上から順番に実行されますが、jobは並列で処理されます。
またjopbはそれぞれ別の仮想マシンホスト上で実行されるので、"run"で設定したコマンドを実行するのにパッケージのインストール等が必要な場合には、job毎に実施する必要があります。

上記画像のActionsが実行される順序は以下のようになります。
1. onで指定したトリガーを条件にActionsが起動
1. job1,job2が同時に実行
1. job1,job2それぞれで、runs-onで指定したOSでStep内のコマンドが順番に実行される

イメージとしては、Actions実行の度に環境構築からコマンドの実施までその都度実施しているイメージです。
Actionsを使用してAWS等のクラウドサービスにアクセスすることも可能で、その際に使用するクレデンシャルの情報もGitHub Secret等に設定しておき参照することも可能です。
制限時間があるとはいえ、無償で使わせてくれるGitHubさん凄すぎます。。

## ハンズオン
実際に簡単なActionsを動かしてみます！
```yml
name: GitHub Actioins Test

on: [push]

jobs:
  job_1:
    name: greetings
    runs-on: ubuntu-latest
    steps:
      - name: "気持ちのいい挨拶"
        run: echo "hello world"
      - name: "気持ちのいい別れ"
        run: echo "good bye"
  jopb_2:
    name: like foods
    runs-on: ubuntu-latest
    steps:
      - name: "食べ物1"
        run: echo "sushi"
      - name: "食べ物2"
        run: echo "egg"
```
上記では２つのjobの中で、挨拶と好きな食べ物を出力する、Actionsを記載していて,pushをトリガーに起動します。
実際にpushしてみます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3492874/a016d2e6-ea26-42db-4ae1-a88ee6a878af.png)
jobが２つ起動しています。
一つ中身を見てみます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3492874/9c27abc0-0d73-6618-9e12-8fad3bf06745.png)

"setups"内のrunが２つ実行されているのが確認できます。
また、"setup"の部分でimageを指定しているので、内部的にはDockerを使用してActionsを動かしていると思われます。

## 終わりに
今回はGitHubActionsの仕組みについて記載しました。
次回はもう少し業務で使用しているようなActionsを作ってみて、どんなメリットがあるのかやっていこうと思います！
誰かの参考になれば幸いです。
atcoder練習(2024.11.23)

# キーワード

# 問題
https://atcoder.jp/contests/abc381/tasks/abc381_b

文字列 T が以下の 3 つの条件をすべて満たすとき、かつそのときに限り、T を 1122 文字列と呼びます。

|T| は偶数である。ここで、|T| は T の長さを表す。

1 ≤ i ≤ |T|/2 を満たす整数 i について、T の (2i-1) 文字目と 2i 文字目は等しい。

各文字は T にちょうど 0 個または 2 個現れる。すなわち、T に含まれる文字は T にちょうど 2 回ずつ登場する。

英小文字のみからなる文字列 S が与えられるので、S が 1122 文字列であるならば Yes を、そうでないならば No を出力してください。

制約

S は英小文字のみからなる長さ 1 以上 100 以下の文字列

入力

入力は以下の形式で標準入力から与えられます。

S

出力

S が 1122 文字列ならば Yes を、そうでないならば No を出力せよ。

入力例 1

aabbcc

出力例 1

Yes

S = aabbcc は 1122 文字列の条件をすべて満たしているため、Yes を出力します。

入力例 2

aab

出力例 2

No

S = aab は長さが奇数であり、1 つ目の条件を満たしていないため、No を出力します。

入力例 3

zzzzzz

出力例 3

No

S = zzzzzz は z が 6 個含まれており、3 つ目の条件を満たしていないため、No を出力します。
# 回答
```Python
S = input()

if len(S) % 2 != 0:
  print("No")
  exit()

list =[]

for i in range(len(S)):
  if i % 2 == 0:
    if S[i] == S[i+1]:
      list += S[i]
    else:
      print("No")
      exit()
  else:
    pass
  
if len(list) != len(set(list)):
  print('No')
else:
  print('Yes')
```

# 参考
https://magazine.techacademy.jp/magazine/36304

https://note.nkmk.me/python-list-duplicate-check/#_1
# 備考
- 初めて一発で成功した。頭の中でできていたとしても、頭の中で想定してないことは山ほどある。せめてでも例題だけでも全部確認するようにしよう。
- 動いたとはいえ、確実に汚いコードの部類には入るはず。もう少し綺麗なコードを書いてください。
- 他の人のコードを見る限り、なんとなく同じような気がする。forでi-1番目とi番目をチェックするのは同じ。あとの部分は色んな人のコード見たけど、よくわからない。
GitHub Actionsで日報用のIssueを自動生成する

## はじめに

『達人プログラマー』を読み、その中で言及されていた「エンジニアリング日誌を書く」習慣を確立しようと考えました。
<br>
以下のブログを見て良さそうだったので、自分もGitHubのIssueを活用し作成を自動化することにしました。
<br>

https://soudai.hatenablog.com/entry/2020/12/31/165940

<br>
そのためのGitHub Actionsのワークフローファイルを備忘録としてまとめます。

## GitHub ActionsのワークフローでIssueを自動作成する

以下のワークフローファイルを使えばIssueを自動生成できます。
<br>

```.github/workflows/daily-report.yml
name: Today I Learned Issue Creator

permissions:
  issues: write  # Issue作成のみの権限を付与
  contents: read # リポジトリの読み取り権限

on:
  schedule:
    - cron: '0 22 * * *'  # 毎日22:00 UTCに実行（日本時間翌朝7:00 JST）
  workflow_dispatch:      # 手動トリガーを追加

jobs:
  create-daily-issue:
    runs-on: ubuntu-latest

    steps:
      - name: リポジトリのチェックアウト
        uses: actions/checkout@v4

      - name: 変数の設定
        run: |
          echo "TODAY=$(TZ=Asia/Tokyo date +'%Y-%m-%d')" >> $GITHUB_ENV

      - name: Issue の作成
        run: |
          cat << 'EOF' | gh issue create --label "Today I Learned" --title "TIL - ${{ env.TODAY }}" --body-file -
          ## 今日やること
          - [ ] 今日やることを書く

          ## 学んだこと
          - 

          ## ネクストアクション
          - 
          EOF
        env:
          GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
```
<br>

このワークフローファイルでは`--label "Today I Learned"`の部分でラベルを付与していますが、この`Today I Learned`というラベルは事前にGitHub上で作成が必要です（もちろんなんでもいいし、やらなくても良い）
<br>

リポジトリのmainブランチにpushすると翌朝7時に以下のIssueが作成されます。
<br>

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2325281/6c9c1f00-0448-5f30-1f64-8856a4a783d3.png)

<br>
TIL（＝ Today I Learned）というフレーズを知ったため、これを採用しています（もちろんなんでもいい）
<br>

テンプレートもなんでもいいのですが、単なるTODOリストではなく毎日のフィードバックサイクルを確立したいため、「学んだこと」「ネクストアクション」など、次の行動へ落とし込むための項目を設けています。

### マークダウンが狙い通りに反映されずハマった

マークダウン形式のテンプレートが正しく反映されず手こずりました。
<br>

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2325281/e3218a0c-3b32-130f-6128-4937d7bd590b.png)

<br>

試行錯誤したのですが、最終的に`--body-file`を使ったこの形に落ち着きました。
<br>

自分の知識不足なだけで本来は難しいポイントではなさそうに思います。
<br>

また、テンプレートの`- [ ] 今日やることを書く`の部分で`今日やることを書く`と文言を初期設定しているのは、これを書かないとチェックボックスとしてではなく`- [ ]`という文字列として表示されてしまうからです↓
<br>

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2325281/e4ee1d99-10df-9442-453d-946e7165aa1b.png)

## おわりに

せっかく作ったからには習慣化してフィードバックサイクルを確立したいと思います。
<br>

今後は、前日のIssueを自動的にクローズするフローも追加する予定です。