OmniAICreator/Qiita-1.07M huggingface dataset:
Goにおけるinterface{}のnilの挙動

[Go Advent Calendar 2023](https://qiita.com/advent-calendar/2023/go)の22日目の記事です。

# はじめに
あるコードをリファクタリングしている際に得たnilの挙動についての記事となります。

# コード

突然ですが、以下のコードがどのような挙動をすると思いますか？
(実際のコードを簡略化したものとなります)

```go
func main() {
	_, err := hoge()
	if err != nil {
		fmt.Println(err)
	}
}

func hoge() (ret *struct{}, err error) {
	defer func() {
		if r := recover(); r != nil {
			err = errors.New("hoge error")
		}
	}()
    // なんか処理してエラーがあったらpanic
	if true {
		panic(ret)
	}
	return
}
```

正解は呼び出し元にて`hoge error`が出力されます。

これはこれで、プロダクション環境において、正しく動いており、特に問題はなかったのですが、例えば`panic`にエラーではなく、構造体を入れていたりと、リファクタリングをする余地があったため、実施しようと思ったのですが、ふと疑問に思いました。

「retは構造体のポインタでnilになっているはずなのになぜrecoverの分岐に入るのだろうか」


# Goにおけるnilの扱い
ドキュメントに解説がありました。

https://go.dev/doc/faq#nil_error

> An interface value is nil only if the V and T are both unset, (T=nil, V is not set), In particular, a nil interface will always hold a nil type. If we store a nil pointer of type *int inside an interface value, the inner type will be *int regardless of the value of the pointer: (T=*int, V=nil). Such an interface value will therefore be non-nil even when the pointer value V inside is nil.

`interface{}`においての`nil`とは型(`T`)と値(`V`)の両者が`nil`で、`nil`が成立するようです。
つまり、上記の`r := recover()`の部分において、`r`は`interface{}`をとるため、`T`と`V`が`nil`にならなかったということになります。

実際に確認してみました。
```go
func hoge() (ret *struct{}, err error) {
	defer func() {
		if r := recover(); r != nil {
			fmt.Println(r == nil) //false
			fmt.Println(r.(*struct{}) == nil) //true
			fmt.Println("T:", reflect.TypeOf(r)) //T: *struct {}
			fmt.Println("V:", reflect.ValueOf(r)) //V: <nil>
			err = errors.New("hoge error")
		}
	}()

	if true {
		panic(ret)
	}
	return
}
```

結果の通り、`V`は`nil`となりましたが、`T`は`*struct{}`であるため、`interface{}`としての比較`r == nil`は`false`となりました。一方で、`*struct{}`にキャストした状態での比較`r.(*struct{}) == nil`は`true`となっています。

また上記の挙動についての日本語の記事はNoboNoboさんのこちらの記事がわかりやすかったです。

https://zenn.dev/nobonobo/articles/f554041aea1955

# linterによる検知
今回はバグが発生することはありませんでしたが、時として、一見して分かりづらいこの挙動はバグの発生となる可能性もあります。しかし、すでにlinterによるgo-staticcheckがあるため、通常であれば、事前に防ぐことができます。
今回は少し特殊?なパターンだったため、検知されませんでしたが、、

例えば上記の[ドキュメント](https://go.dev/doc/faq#nil_error)にあるような`error`を例に取るとlinterによる検知が可能になりました。

```go
func main() {
	err := fuga(false)
	if err != nil {
		fmt.Println(err)
	}
}

type MyErr struct{}

func (MyErr) Error() string {
	return "MyErr"
}

func fuga(isErr bool) error {
	var my *MyErr = nil
	if isErr {
		my = &MyErr{}
		return my
	}
	return my
}

```
`fuga`の戻り値である`error`インターフェースは実際に`MyErr`型であるため、`err != nil`が`true`になることはありませんが、VSCode以下の様に警告が出てきました。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/457889/de906d62-842c-18e9-1db1-e2585bd17b02.png)


# 終わりに
今回は`nil`の挙動についての一部を紹介させていただきました。
普段はあまり意識することなく、コーディングできるかと思いますが、こういった挙動を知っているだけでも思わぬバグを踏まずに済むかもしれません。

では残り少ないアドベントカレンダーを楽しんでいきましょう！
M1MaxのUserAgent

M1MaxのUA、インテルCPUって出るんですね。知りませんでした。

## 前提

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/90217/3b85a1be-0c63-1d1b-2418-84c405597c2c.png)

Chrome 120.0.0.0

## ログに記録される情報

`Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36`

#### 見やすく 改行入り

```
Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7)
 AppleWebKit/537.36 (KHTML, like Gecko)
 Chrome/120.0.0.0 Safari/537.36
```
discordbotをpythonで作ってみた

どうもこんにちは、いろぱずというものです。今回は、discordに搭載されているbotをつかって色々~~遊んで~~開発してまいりましたので、その行ったことを記事にまとめようと思います。

### 開発環境
```diff
+VScode
+python
+py-cord
```
~~VScodeとpythonの開発環境はは実装済みと勝手に決めつけて~~
まずは、py-cordの開発環境です。VScode内のターミナルで以下のように入力します。
```diff
pip install py-cord
```
ここは人によって違うと思いますが、私はこの方法で行けました。
その次に、適当な.pyファイルを作成します。(私はdiscordbot.pyで作りました。)
ここまで終わったら、次にbotを作成しますが、こちらのサイトが分かりやすかったのでご参照ください。

https://discordpy.readthedocs.io/ja/latest/discord.html

こちらで設定等おわりましたら、いよいよ書き込んでいきます！

### 作った.pyに書き込む
#### まずは起動確認とHello Worldを出そう
まずは、1行目にこちらを入力します。
```py
1 import discord
```
こちらの入力により、discordモジュールを使用できるようになります。
次に、トークンというものを設定します。トークンとは、誰のbotであるかを判別するIDみたいなものです。**逆に言えば、これを知られてしまった場合、そのbotを誰でもあつかえるということになります。絶対に誰にも教えないでください。** 以下のように入力します。
```py
2
3 TOKEN = ##自分のトークンを入力
4
```
botが何の操作を行うことができるかの権限を設定します。よくわからない人はとりあえず下のように打っておけばOKです。
```py
5
6 bot = discordBot(intents = discord.Intents.all())
7
```
次に、botが起動したときにお知らせするために、ターミナルに文字を出力するようにします。
```py
8
9  @bot.event
10 async def on_ready():
11    print("botが起動しました！")
12
```
これで一旦動かしてみましょう...と言いたいのですが、動かすためのコマンドをまだ未入力です。
以下のように打つことで動かすための準備ができます。
```py
13
14 bot.run(TOKEN) ##TOKENを取得して動かす
15
```
これで、準備は完了です。動かしてみましょう！
動かすときはターミナルに次のように打ち込みます。
```py
python ##自分の.pyファイル  私の場合はdiscordbot.py
```
これで動きます！起動すると"botが起動しました！"という表示がターミナルに出力されます！


次に、ある文字を入力した際にHello World と出すプログラムを作成しましょう。
13行目から書いていきます。
```py
12
13 @bot.event
14 async def on_message(message: discord.message)
15       if message.author.bot:
16            return
17       if message.content == "/hello":
18            await message.channel.send("Hello World")
19
```

これで起動してみましょう！botが入っているサーバーで/helloと入力すると"Hello World"と返ってくるはずです！

#### ガチャシステムを作ってみよう
次に、ガチャシステムを作ってみたいと思います。pythonにはrandomモジュールがあり、それを利用して書いていきます。
##### モジュールの追加
1行目に加えて、以下のように記述します。
```py
1 import discord
2 from discord.ext import commands
3 import random
```

2行目のものはのちに出てくる@bot.commands を動かすために必要なモジュールですので、忘れずに記入ください。

##### リストの作成

ここでは、自分がガチャで出したいものを記入していきます。
(確率等々もいじれますが、説明が難しくなるので今回は割愛します。)
以下のように書きます。
```py
10 gatya_list = ["1", "2", "3", "4", ] 
11 ## 1,2,3,4には、自分が入れたいガチャの中身を入力、増やしたい場合は単語ごとに ","で区切る
```
これで、中身の作成が完了しました。

##### コマンド作成

さて、いよいよコマンドを作っていくわけですが、今回は数指定もしたいので、@bot.command を使います！

```py
24
25 @bot.command(description = ##説明を入力 )
26 async def gatya(ctx: discord.ApplicationContext, number: str)
27     try:
28         number = int(number)
29     except:
30         await ctx.respond("数字を入力してください")
31     if number < 1:
32         number = 1 ##0連やマイナスなどの対策
33     if number > 10:
34         number = 10 ##11連以降は10連にする
35     while number >= 1:
36         await ctx.respond(random.choice(gatya_list)) ##gatya_listから一つランダムで取得して返す
37         number -= 1
38
```
これで、ガチャの処理が完成しました！起動して、実際に動かしてみましょう！

### 終わりに
#### しめくくり
今回は、discordbotをpythonで作成してみました。discordはゲーム通話などによく使われるイメージが多いですが、そのときに欲しい機能をいろんな機能を使うことで実現することができます。ぜひ皆さん作成してみてください！




#### 以下、雑談

今回が記事作成初めてなのですが、難しかった...
これを応用してとある人の迷言をガチャで出るようにしましたが、意外と評判でした。
頑張ればゲームも作ることができます。ぜひやってみてください。
あなたは何本、読んだ？2023ブログ 10選

この記事は インフォマティカ [Advent Calendar 2023](
https://qiita.com/advent-calendar/2023/informatica
) Day 25 の記事として書かれています。

さて年末の締めに、2023年を通しての記事の表示回数を、1位から10位までランキングにしてみました。
今年は、75本の記事が公開されましたが、まだ見ていない記事があれば、ぜひご覧ください！

まだ少し早いですが、来年もよろしくお願いいたします。<BR><BR>

1\. 表示回数で、ぶっちぎりトップの記事です！！

https://qiita.com/yasuyuki90/items/76eb94c51ec17a9a79f5

<BR>

2\. やはり根強い人気のOracle データベースをデータカタログ化する手法の記事です。

https://qiita.com/AkiYamano/items/ac59fbe859cab37ebb99

<BR>

3\. IDMCプラットフォームを動作させるに必要なSecure Agentのインストール手順の記事です。

https://qiita.com/daichi-kaneko/items/b3a15116b35dba676b68

<BR>

4\. データカタログ＆ガバナンスのサービスに関するナレッジベースの利用方法とお役立ちサイトへのリンクです。

https://qiita.com/AkiYamano/items/28db2dd17d8102719758

<BR>

5\. 2023に新しく出た、Excelのデータカタログ・スキャナーについて解説している記事です。

https://qiita.com/masatoshimada-max/items/082489f8d9948f5de67b

<BR> 

6\. データ連携(CDI)における、パラメーターハンドリングの記事です。

https://qiita.com/asekine-infajp/items/53d06f1332b1408ca6a4

<BR>

7\. Snowflakeのデータカタログ・スキャナーについて解説している記事です。

https://qiita.com/masatoshimada-max/items/f8cf82e37c9bdb30481a

<BR>

8\. IDMCとして用意されている REST APIの概要と使い方の記事です。

https://qiita.com/daichi-kaneko/items/d9822dffd970f3627bbf

<BR>

9\. S3のデータカタログ・スキャナーについて解説している記事です。

https://qiita.com/nickqinsc/items/887f685e40bbafdefc96

<BR>

10\. 2023.11のデータカタログ・ガバナンスの新機能についての記事です。

https://qiita.com/masatoshimada-max/items/81b6e4ad3782e7efb130


<BR><BR>
いかがでしたでしょうか？2024年もどんどん記事を公開していく予定ですので、ご期待ください！！
個人的Webで使うファイルの種類/その1：画像

# はじめに

この記事は、Qiita Advent Calendar 19日目の記事です。
以下の記事より、すべての記事をご覧になれます。

https://qiita.com/0_terarin_0/items/0f367210e2465f7772c9

# 筆者について

- 現在高校２年生
- 水泳部マネージャー
- 生徒会長
- とある団体の代表

# 本編

## 画像

|拡張子|種類|名称のもと|詳細|
|---|---|---|---|
|.jpg|非可逆圧縮|Joint Photographic Experts Group|1986年に開発された画像形式です。人間が見えない部分のデータを削除しているためデータ量を減らすことができますが、些細な部分までこだわるフォトグラファーは嫌うことが多い画像形式ですが、一般の方なの多くの人がWebなどで利用します。|
|.png|可逆圧縮|Portable Network Graphics|1995年にITエキスパートのOliver Frommeが開発した形式です。GIFが抱えていた問題の多くを解決した画像形式ですが、GIFと異なってアニメーションは利用されていません。|
|.webp|可逆圧縮/非可逆圧縮|-|Googleに買収されたOn2 Technologiesという会社が開発した画像形式です。画像サイズをかなり減らすことができ、Webでの読み込みのスピードはかなり早めることができます。|
|.svg|可逆圧縮|Scalable Vector Graphics|1990年代後半にWorld Wide Web Consortium（W3C）が募集したベクターグラフィック形式に関する提案から選ばれた形式になります。ベクター形式は多くのベクター画像作成用サイトでサポートされており、Webサイトのアイコンやロゴに利用されることが多いです。|
|.tiff|様々|Tag Image File Format|1980年代半ばにTAldusがTIFFファイルをDTP（Desktop Publishing）用として開発しました。テーブルスキャナーなどでよく利用される画像形式で、JPEGのコンテナ保存などにも対応しています。|
|.bmp|非圧縮|BitMaP|1990年代にMicrosoftがWindows向けに開発した画像形式です。ファイル容量が大きくなる傾向がありますが、高画質な画像を保存したりすることができるため、高品質なものを要求される場所で利用されます。|
|.heic|非可逆圧縮|High Efficiency Image Container|2010年代にAppleが開発した画像ファイル形式です。JPEGよりも高品質かつ低容量で利用することができるファイル形式になっており、主にApple製品で利用されます。|
|.ps||PostScript|Adobeが1980年代に開発したファイル形式です。テキストや画像の印刷がとても容易で、古い画像形式の一つです。|

引用元一覧は以下の通りです。

https://www.adobe.com/jp/creativecloud/file-types/image/raster/jpeg-file.html

https://www.adobe.com/jp/creativecloud/file-types/image/raster/png-file.html

https://www.adobe.com/jp/creativecloud/file-types/image/raster/webp-file.html

https://www.adobe.com/jp/creativecloud/file-types/image/vector/svg-file.html

https://www.adobe.com/jp/creativecloud/file-types/image/raster/tiff-file.html

https://www.adobe.com/jp/creativecloud/file-types/image/raster/bmp-file.html

https://www.adobe.com/jp/creativecloud/file-types/image/raster/heic-file.html

https://www.adobe.com/jp/creativecloud/file-types/image/vector/ps-file.html

## 各変換方法

各種変換にはImage Magickを使うことをお勧めします。以下のように利用するだけです。

```zsh:shell
magick convert input.webp output.png
```

説明するとキリがないですので、以下のサイトをご覧ください。

https://imagemagick.biz/

ちなみに、インストール方法などは以下の通りです。Macの方はHomebrewでインストールすることができます。

```zsh:shell
brew install imagemagick
```

https://imagemagick.org/index.php

# 最後に

本日は備忘録と勉強がてら、画像形式に触れてみました。個人的にはWebPを利用するタイミングが多いですが、今後は他のファイル形式にも触れてみたいと思います。ということで、今後のアドカレ 23 の記事をお楽しみにしてください。

https://qiita.com/0_terarin_0/items/0f367210e2465f7772c9
GitHub Actionsを使ってPythonのexe化を自動化しよう！(Nuitka使用)

# はじめに
こんにちは！N中等部ネットコースに所属しているあかずです。
この記事では、タイトルにもある通り、GitHub ActionsでPythonのexe化を自動化する方法を書きます。

# Nuitkaとは
Pythonをexe化するためのライブラリ(?)です。大体PyInstallerと同じですね。
有名なところだとVOICEVOXが利用しているみたいです。
Nuitkaのいいところは、実行速度が早い、起動が早い、ファイルサイズが小さいところです。
(ファイルサイズが小さいは諸説ありそうです)
調べてみるとPyInstallerと違ってウイルス誤判定されないと言われていましたが、自分はしっかりウイルス誤判定されました。

# Actionsに入れてみよう！
:::note warn
> Not all Nuitka options are currently exposed as input parameters to this action. We welcome PRs in case you find anything missing.

Nuitkaのすべてのオプションには対応していないようなので、そこだけ注意してください。
:::

今回紹介するコードは、Windowsのexeでしか動作しませんが、[Linuxや、MacOSの実行ファイルも同時に吐き出してくれるコード](https://github.com/marketplace/actions/build-executables-or-extension-modules-from-python-projects#multi-platform-builds)もあったので、必要な方は使ってみてもいいかもしれません！
公式のコードにnameとonとコメントだけ足したコードですが、こんな感じでできると思います。
```yaml: .github/workflows/main.yml
name: Compile Python
on: [push]

jobs:

  build:
    # こちらはWindowsに対応しておりますわ。
    runs-on: windows-latest

    steps:

      # リポジトリをチェックアウトするのです
      - uses: actions/checkout@v3

      # Pythonのセットアップを行いますわ
      - uses: actions/setup-python@v4
        with:
          python-version: '3.x' # 使用するPythonのバージョンの範囲または正確なバージョンを、SemVerのバージョン範囲の構文を使用して指定しますわ
          architecture: 'x64' # オプションでx64またはx86を指定しますわ。指定がない場合はデフォルトでx64になりますわ

      # Pythonスクリプトをスタンドアロンのexeにビルドしますわ
      - uses: Nuitka/Nuitka-Action@main
        with:
          nuitka-version: main
          script-name: hello_world.py
          onefile: true

      # アーティファクトをアップロードしますわ
      - name: Upload Artifact
        uses: actions/upload-artifact@v3
        with:
          name: exe
          path: build/hello_world.exe
```
このコードだと、hello_world.pyがコンパイルされ、[アーティファクト](https://docs.github.com/ja/actions/using-workflows/storing-workflow-data-as-artifacts)としてhello_world.exeが保存されます。
適宜自分の環境に合わせて変更してみてください！
ちなみにコメントアウトはすべてAIで翻訳しました。あまり気にしないでください。

# 参考文献
https://github.com/marketplace/actions/build-executables-or-extension-modules-from-python-projects#multi-platform-builds

https://blog.tsukumijima.net/article/python-nuitka-usage/
若手エンジニア奮闘記⑪文系の2年目エンジニア奮闘記

# はじめに

皆さん初めまして!
株式会社エグゼクションに入社し、2年目になる工藤です!
今回は初めての奮闘記ということで、まずは私の配属時のお話をしようと思います。
 
# 文系、セキュリティエンジニアになる

ある日の会社のBBQイベントでのこと。
私が美味しいお肉を食べている時にセキュリティエンジニアの先輩方に囲まれ、勧誘を受けたことが私のセキュリティエンジニアへの道の始まりです。
元々、インターネットが大好きで小さい頃からパソコンを使ってあれこれ遊んでいたため、パソコンのウィルスや、詐欺などの手口は多少知識としてある程度でした。
でもやっぱりエンジニアって言ったらアプリがかっこいいよなぁ、と思っていた私に先輩が一言。
「セキュリティにもプログラミングとは違う魅力があるよ！」
プログラミングは楽しいけれど、数字がダメで得意ではなかった私は、その一言でセキュリティエンジニアになろうと決意しました。

# セキュリティって何するの?

私の配属先での業務は SOC というものでした。正式には、Security Operation Center (セキュリティオペレーションセンター)です。
主な業務は、様々な機器やユーザーのログを取り込み・分析し、インシデントを検知する仕組みを使用して、検知があった際にログ解析などを行い調査・対応するというもの。
私が行っていたのは、検知が上がってきたら、検知に該当するログを見て、サイバー攻撃を受けていたり、ウィルス感染したりしていないかを判断する業務です。
「ログ見るだけなんてつまらなそう」と思うかもしれませんが、ウィルスの特徴を知ることやサイバー攻撃の手口を学ぶのは、ミステリー小説を読んでいるようでワクワクしました!


# いざ、配属! 最初に大変だったこと

セキュリティの現場に配属され、SOCの解析業務を行うことになった私が、いちばん大変だったのはインシデント解析を行う時の判断です。
配属時に、新人の教育として「解析のいろは」は教えて貰えるのですが、ちゃんと”何が危険なのか”を理解していないと上手く判断ができません。
何度も解析練習をして、その結果を先輩にレビューしてもらうことで、ログの見方や怪しいと判断できるポイントを理解し、覚えていきました。特に私は文系ということもあり、説明を理解するのは得意なので、理解してしまえば業務も難なくこなせるようになりました!
ログを見続けるのは正直苦しかったのですが、セキュリティの楽しいところは、この大変だったことの先に、自分の知識が身近なところで発揮出来る可能性があること!
私はこの楽しみをモチベーションにして乗り越えることが出来ました。


# 最後に

いかがだったでしょうか?
文系からエンジニアになるのは少しだけ大変な部分もありますが、業務によっては文系の才能を発揮することで活躍出来ることも多くあるため、今はその発揮できる場所を探すのが楽しいです。
次回は、そんな文系の力を発揮できたお話をしようと思います。
ここまで読んでくださり、ありがとうございました!
Stripeを利用したサブスクリプション導入におけるシステム連携注意ポイント


## はじめに

BitStarのモリヤです。
[BitStar Advent Calender](https://qiita.com/advent-calendar/2023/bitstar)21日目です。

現在開発中の[BitStar Match](https://bitstar.tokyo/match/)というプロダクトでは定額課金制の有料機能を提供しています。
サブスクリプション機能を実現するにあたり、以下の観点から外部サービスである**Stripe**を利用することとなりました。

- 決済処理実装の工数削減
- クレジットカード情報等の機密情報のシステム側での保持が不要

https://bitstar.tokyo/match/

#### Stripeとは

オンライン決済処理を安全かつ簡単に導入可能にするサービス。

https://stripe.com/jp

![スクリーンショット 2023-12-21 11.08.20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2607349/77109635-3fba-2b39-1242-5baf2b97142e.png)

## この記事の目的

Stripeのような外部サービスとホスト側のシステムを連携させる上で、重要な注意点があったので共有しようと思います。

## ユーザーへの有料機能提供までのラグ

### Webhook

Stripeは決済完了などのイベント処理を行う上でWebhookを利用することを推奨しています。

https://stripe.com/docs/webhooks

今回の場合、決済手続き開始〜ホスト側システムのデータ更新までは以下のようなフローになります。

*事前準備*
- Webhook用のエンドポイントをバックエンドに実装
- Stripe管理画面で作成したエンドポイントを登録

![Webhook_新規決済_Qiita用.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2607349/b0dc6467-dd66-6dd0-153b-e2c685c02eab.png)

このフローを通ることで、以降にサービスへアクセスした際はユーザー情報は課金済み状態となっているため、ユーザーに有料機能を提供することができます。

.
.
.

**(Webhookの処理)以降に**です。
ココに問題点があります。

### ホスト側サービスへのリダイレクトとWebhookの非同期性

ユーザーが"申し込む"をクリックし、決済処理が完了すると事前に登録しておいたURLに自動的にリダイレクトするようになっています。(Stripeの仕様)

*事前に登録しておいたURL … サービストップ・サンクスページ・プラン利用状況ページ等が一般的*

そして、このリダイレクトとWebhook CALLは非同期で行われています。
**Webhook CALL前にサービスにリダイレクトされることも勿論あります。**

結果、ユーザー情報が更新される前にサービスにアクセスされ「課金したのに無課金扱いされる」という状況が短期間ですが発生します。

お金を扱う機能として、この状況は致命的です。

![Webhook_新規決済_Qiita用_2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2607349/2a9d50b1-127d-3038-8b84-da766b8a68ea.png)

### 解決策

リダイレクト先ページに**Stripeに対する課金情報取得の処理を仕込む。**

Webhookが間に合わないなら、こちらから先にデータを取得しに行っちゃえばいいじゃない！の発想です

今回の場合は、以下のような処理を入れることにより有料機能提供までのラグが発生しないように対処しています。
- リダイレクト先にローディング画面を指定
- ローディング中、裏でStripeへの課金情報取得リクエストを実行
- 取得完了後、DBのユーザー情報を課金済み状態に更新
- 最後にプラン利用状況ページにリダイレクト

![Webhook_新規決済_Qiita用_3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2607349/9b6eaae6-7d2b-ac7c-29cb-24757ac76867.png)

※WebhookでのDB更新・課金情報取得側でのDB更新がバッティングすることによるDuplicateエラーの発生を防ぐ考慮も別途必要です。

## おわりに

Stripeは一見導入コストが低そうに見えますが、至る所にこちら側で考慮しなければならないポイントが散らばっています。
入念にパターン検証してから実装するようにしましょう。
(二重決済対策だったり…とかとか…)

---

BitStarでは冒頭でご紹介させていただいたBitStar Matchの開発に携わっていただける仲間を積極募集中です!

ご興味のある方はぜひ以下の募集情報をご確認ください。

https://www.wantedly.com/projects/1508637
GitHub ActionsでXMLの構文チェック

GitHub ActionsのワークフローでXMLファイルの構文をチェックする方法です。

## xmllint
コマンドラインツールのxmllintが使えます。
簡略化されたものになりますが以下サンプルです。
```yaml
      - name: Install xmllint
        run: sudo apt-get install -y libxml2-utils

      - name: xmllint
        run: xmllint sample.xml
```

## xmllint-action
[xmllint-action](https://github.com/ChristophWurst/xmllint-action)というXMLの構文をチェックできるActionsが存在します。
内部ではコマンドラインのxmllintを使用しており、スキーマファイルを指定した妥当性検証を行っています。

https://github.com/ChristophWurst/xmllint-action

## xmllintの検証方法について
* 妥当性検証
    * DTDやrelaxngなどのXMLスキーマを元に検証
    * 要素名や階層などをチェックする
* 整形式検証
  * XMLの文法に則っているか検証

## まとめ
スキーマファイルを用いた厳密なチェックを行いたい場合は[xmllint-action](https://github.com/ChristophWurst/xmllint-action)を使用し、そうでなく文法のチェックのみであればコマンドラインツールのxmllintをそのまま使用するのが良さそうです。
オブジェクト指向を言語化してみた

# はじめに

qnote Advent Calendar 2023 :cat:21日目

<br>
オブジェクト指向とは？と聞かれた時、<br>
ボヤッとイメージはあるものの言葉で説明できない・・・
<br>
ふとそんなことを感じたため、改めて自分の中で整理をしてみました。

## Q.そもそもプログラミングって...?
A.指示に対してその通りにコンピュータを動かすようにする（プログラムを作る）こと
<br>
この時、プログラムを作る中での"表現方法"として、

<br>
①オブジェクト指向プログラミング

②手書き型プログラミング

③関数型プログラミング
<br>
など分別されます（他にもあるが上記が代表的なもの）
<br>



その中でオブジェクト指向とは

「"モノ"と"操作"に分けてプログラムを組みコンピューターに動作させる表現方法」




# NINTENDO switch で想像してみた・・・

ゲーム機である NINTENDO Switch を例に挙げてみます
<br>

NINTENDO Switchは、

①ゲーム機である本体

②ボタンの操作（ex)マリオを走らせるBボタン

<br>

といった、①本体（＝オブジェクト）＋ ②操作により

初めて遊べるようになります。

<br>
①オブジェクト②操作の２つが揃うことで初めて完成、ということです。


# さらに例を出します

あるアプリケーションに３つのボタンがあるとします。
「登録」「編集」「削除」
<br>

共通して
「width: 100px」「background-color: red;」「color: white;」
で作られるボタンだとする場合、

オブジェクト指向を使わなければ

同じボタンのプログラムを３回書かなければいけなくなります
（さらに多いと腱鞘炎・・）
<br>


「ボタン」 = 「オブジェクト」　として１つ作ってしまえば

別のボタンを作るときには変えたい部分（色など）のみ変えるだけで済みます。


これにより「効率的に開発」できる、ということです。


# もう一つのメリット
もう一つメリットとしては「エラー対処のしやすさ」が挙げられます。
<br>

例えば、
「ボタン」の押下で「登録ができる」「ページが移行する」
<br>
というアプリケーションをオブジェクト指向の定義で表すと、
<br>
「ボタン」＝「モノ(オブジェクト)」

「登録ができる」＝「操作１」

「ページが移行する」＝「操作２」
<br>

となります。
<br>
ではこの時エラーが出たとして・・
<br>
モノに対して

操作１に対して

操作２に対して
<br>



と分別されてエラー分が出てくるので原因特定がしやすくなります！やったー！


# まとめ
簡易的ですがなんとなく説明はできそうになりました
改めて自分の中で言語化するとスッキリするな〜と感じました。
動画ストリーミングをnode.jsで読み込む方法

この記事は[ZOZO Advent Calendar 2023](https://qiita.com/advent-calendar/2023/zozo) #1 21日目の記事になります。


# TL;DR
HLSなどの動画ストリーミングをnode.jsで読み込む際には、fluent-ffmpegが便利です。

# 結論
これだけです。

```typescript
import ffmpeg from 'fluent-ffmpeg'
import fs from 'fs'

...
const url = 'https://example.com/video.m3u8'
const stream = fs.createWriteStream('filename.mp4')

ffmpeg(url, { logger: console })
  .addOutputOptions(
    '-movflags +frag_keyframe+separate_moof+omit_tfhd_offset+empty_moov'
  )
  .format('mp4')
  .on('error', (error) => {
    console.error(error)
  })
  .pipe(stream)
...
```

# ポイント
- システムにffmpegがインストールされている必要があります。
- 例として、HLSのm3u8ファイルを読み込んでいます。
- mp４で保存する部分まで書いています。
- [fluent-ffmpeg](https://www.npmjs.com/package/fluent-ffmpeg)というNPMパッケージを使っていますが、直接execコマンドなどで実行するのでもいいかもしれません。（オプションの付け方がややこしい部分もあるため、このパッケージ内の[examples](https://github.com/fluent-ffmpeg/node-fluent-ffmpeg/tree/master/examples)を確認すると効率的に開発が進められると思います。）

ffmpegコマンド関連
- ストリーミングに必要な[オプション](https://github.com/fluent-ffmpeg/node-fluent-ffmpeg/blob/master/examples/any-to-mp4-steam.js)を付加しています
- errorハンドラーは[必須](https://github.com/fluent-ffmpeg/node-fluent-ffmpeg?tab=readme-ov-file#:~:text=output%20streams%20respectively.-,Warning,-%3A%20you%20should%20always)です。もし無いとerror時にnode.jsが落ちてしまいます。

# 背景 （ポエム）
ある日動画ストリーミングをnode.jsで処理したくなりました。詳しいわけではないため、最初は`HLS ダウンロード node`などのワードで検索していました。他にもNPM内で`HLS`と検索してみたりしました。しかしどのパッケージもそんなに利用者がおらず説明が少ないため、エラーになってもソースを直接読んだり型ファイルから考えたりする必要がありました。そしてようやくたどり着いたのが、上記の`fluent-ffmpeg`パッケージだったというわけです。

この話には続きがありまして、前後の処理も含めたTypeScriptのコードをGPT-4で生成すると、ほぼ完璧なものが出来上がりました。それまでの数時間がたったの数十秒に置き換えられてしまいました笑（当然そこまでの過程がコードの理解につながっているのですが） 今回のように初めての分野では、まずは生成AIに頼るようにしようと心に誓いました。

（今回の場合はffmpegというキーワードに辿り着くのがポイントだったと思います。GPT-4の出力にはそれが含まれています。）
デザインからUIテストの自動化をやりたい

## はじめに
どんな人が考えているかによっても、受け取り方が違うと思いますので、簡単に自己紹介をさせていただきます。
過去に、第三者検証での検証経験を経て、株式会社LITALICO（リタリコ）でQAエンジニアとして働いています。

そんな自分が思う自動化が出来たら嬉しいテストは、
**「デザインからUIテストの自動化をやりたい」** です。タイトルそのままで申し訳ないです。

## 背景
開発未経験のQAエンジニアですが、切に思っていることがあります。
**もっと楽したい…**

決して仕事が嫌いなわけではなく、楽しく働かしていただいているのですが、
歳を取ってなのか、ただの性格なのかわからないですが、細かい部分の確認が苦手になってきました。
同じチームでは、1ピクセルずれているとか、色が少しだけ違うなどに気が付けるなど、スーパーな人達がいて度肝を抜かれている日々です。

マイナスなことを解消する為だけに自動化したいという不純な気持ちだけではなく、デザイナーさんが作成していただいた、とても素晴らしいデザインがあるのに、仕様としてだけ使うのは勿体ないと常々思っているのです。
デザインをそのまま実装後の期待結果に出来たら、みんながハッピーになれるのではないかと考えています。

- **一例ですが、モーダル部分のデザインと開発後の実際の画面です** 

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2987894/fe182450-ce89-451f-e4b9-29b19d6ec284.png)


## 過去の経験を振り返ってみる
#### ホワイトボックステストの自動化
当時のリーダーが作成したのものなのですが、システム内部のパラメーター確認を開発の方が作成する仕様書からテスト設計、テスト実行と自動化したものになります。結果、２人月作業を５人日に短縮するという大幅な工数の削減に成功しました。

#### テスト自動化スクリプトの自動作成
自動という言葉が繰り返し出てくるのでわかりずらいかもしれませんが、
ご存じかと思いますが、自動テストにはどのようにテストをするかが記載されている自動化ツール内での手順書（スクリプト）が必要になってきます。
このスクリプトを作成するのがテストエンジニアだとハードルが高く、今ではノーコードでの自動化ツールが出てきていると思っています。ただ、テストエンジニアはテスト設計は得意分野です。
当時のテスト仕様書にしっかりと手順を記載してくれていたので、そのまま何とか自動化に出来たら楽だなということでやってみました。
少し強引ではありましたが、ExcelのVBAや関数を使って、手順に沿った自動化のスクリプトを作成することによって、テスト仕様書から自動化スクリプトの作成→自動化ツールで取込で、自動化を達成していました。ただ、あくまでUIの確認ではなく、機能の確認を行っていました。

こんな感じですね
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2987894/3b35e196-a65d-6e93-f1b3-a1459c830058.png)


#### その他にもこんなことはやってました
- 動作、UI崩れなどを確認するリグレッションテスト
- テストデータ作成
- テスト観点から、テストパターの作成
- テストパターンから、テストケースの作成


#### 気が付いたこと
テスト自動化を含め、テストケースの作成補助的なものなども行ってきましたが、UI確認の自動化は、あくまで実装後のリグレッションテストでの自動化しか行った経験がありません。
経験あるといっても、テストの自動化に関しての若輩者なので知らないだけかもしれないですが、テストの自動化は主にリグレッションテストを行うことが多く、新規開発での自動化では仕様変更されるリスクや、自動化を実装する工数を考えると、あまり向かない認識でいます。

繰り返しにはなりますが、デザイン段階で素晴らしい仕様が出来ているんです。
デザインからの自動テスト化が実現できれば、仕様書の新しい使い方もそうですが、新規開発時に自動でテストを流せるので、テスト工数の大きな削減も可能になるかと思っています。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2987894/06cc94d7-bdf5-9107-240a-2109a5e3b45b.png)

:::note warn
作成方法によっては、テスト設計も無くせる為さらなる工数削減につながるかも
:::


## まとめ
デザインからUIテストの自動化が行えれば、効果は絶大になることが改めて理解できたのですが、そもそもどうやるかが問題です。
また、自動化だけではなくテスト設計に対しても自動で展開できるような形にできれば、同じく効果は絶大かと思いました。

LITALICOでは、要求→テスト仕様書までを効率的作る為の取組みも行っています。
これはデザインだけに限らず、機能テストの自動化も実現可能かと考えています。
目指している **[「QAのいらない世界へ向けて」](https://qiita.com/yamahiro2022/private/a6a4a14f0e2e80a2b15a)** に一歩近づけるかと思います。
※こちらの記事も興味あれば是非読んでいただけたら幸いです

## 最後に
最後まで読んでいただきありがとうございます。
よくよく考えたら、テストではなくそのままUIの実装まで出来たらいいのでは？と思ってしまいましたが、
開発未経験なので、難易度なども考えずに無邪気に考えているだけなのでお気になさらずに…
「OBSのビルトイン仮想カメラがOpenCVで使えない」問題は解消している

以前、OBSに組み込まれている仮想カメラ機能は`opencv-python`を含むOpenCVで使用できませんでした。代わりに[OBS-VirtualCam](https://github.com/Avasam/obs-virtual-cam)を紹介する方法が各所で紹介されています。なおプラグインはOBS Studio 28.0+に対応するために[Fenrirthviti/obs-virtual-cam](https://github.com/Fenrirthviti/obs-virtual-cam)から以下にフォークされています。

https://github.com/Avasam/obs-virtual-cam

この問題はすでにOpenCV側で解消しているようです。次のコードでビルトイン仮想カメラが利用可能なことを確認できます。

https://github.com/opencv/opencv/pull/23460

`OBS Studio 30.0.2`

```shell-session
> py -3.12
Python 3.12.0 (tags/v3.12.0:0fb18b0, Oct  2 2023, 13:03:39) [MSC v.1935 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> import cv2
>>> cv2.__version__
'4.8.1'
>>> cap = cv2.VideoCapture(2)
>>> while True:
...     _, img = cap.read()
...     cv2.imshow("", img)
...     if cv2.waitKey(1) == 113:
...         break
...
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1550728/8d8d1bfd-01ac-44cd-d7a8-6cd5f80c307c.png)

ただし、ビルトイン仮想カメラはOBSをいくつ立ち上げても一つしか開始できません。複数の仮想カメラを利用したい場合はこれまで通りプラグインを利用する機会もありそうです。
【selenium】headless備忘録



## はじめに
【selenium】headless備忘録に関しての備忘録です。
初心者です😅
間違えてる部分が多々あると思います。
もし見つけた場合、ツッコミいただけると助かります🙇
<br>
## 🦁<INS>**結論**</INS>🦁
headlessはブラウザのGUIを起動なしでで動作できる。
サーバー、WEBスクレイピング、テスト環境などに適している。

:::note info
押さえておくべき点
* ブラウザのGUIを起動せずに動作、実行などができる。
* GUIがないため、処理が早くなる。
* サーバーなどの環境に使う。
* バックグラウンドでの動作が可能。
* スクリーンショットも可能（実際のGUIと異なる場合がある）
:::  
***

:::note warn
利用シーン
* サーバーなどでの自動操作したい
* WEBスクレイピングしたい
* テストをしたい
:::  
***


:::note alert
注意点
* --window-sizeで解像度を指定する必要がある。
* --window-sizeは適切にしないと要素の読み込みなどができないときがある。
* セキュリティ関連の設定を無効にすることが必要な場合がある。
* GUIがなくてもJavaScriptは動いてる。
:::  
***  

## コード例

### <INS>**WebDriverのオプションを設定**
headlessを設定する上で必要
```
options = webdriver.ChromeOptions()
```
***

### <INS>**headlessの有効化**
これでheadlessを有効する。
```
options.add_argument("--headless")
```
***

### <INS>**GPUハードウェアアクセラレーションの無効化**
GPUの処理を停止させることによって処理向上につなげる。
```
options.add_argument("--disable-gpu")
```
***

### <INS>**スクロールバーの非表示**
スクリーンショットを撮影する際にスクロールバーが邪魔になることをなくすため。
またサイトによってはスクロールバーの有無がページのレイアウトや、表示に影響を与える時があるために非表示にする。
```
options.add_argument("--hide-scrollbars")
```
***

### <INS>**シングルプロセスモードの有効化**
分散処理をさせすぎないようにする。
分散処理をさせすぎてしまうと、かえって処理が遅くなることがあるため。
```
options.add_argument("--single-process")
```
***

### <INS>**SSL証明書エラーの無視**
基本はseleniumのテストに使う。
本番環境では使用は避けるべき。
```
options.add_argument("--ignore-certificate-errors")
```
***

### <INS>**ウィンドウサイズの指定**
バック側で開いてるウィンドウのサイズ。
スクリーンショットを撮影したいときなどにも有効。
```
options.add_argument("--window-size=1200x1000")
```
***

### <INS>**セキュリティサンドボックスの無効化**
seleniumを使う場合、セキュリティサンドボックスを使うと制限があるのとがあるため。
セキュリティサンドボックスを使わないと安全性は下がる。
※基本はあまり使う必要はない。
```
options.add_argument("--no-sandbox")
```
***

### <INS>**一時ディレクトリの設定**
一時的にデータを保管する場所を特定する。
データ容量が増えたりする場合に必要。
```
options.add_argument("--homedir=/tmp")
```
***

### <INS>**WebDriverのインスタンスを作成**
定義したオプションをこれにより使えるようにしてる（インスタンス化）
オプション定義後に必ず記述。
```
driver = webdriver.Chrome(options=options)
```
***

## まとめ😺
headlessはGUI起動なしで動作、実行ができるseleniumのオプション。
サーバーではよく使う技術。
***
クリスマスが近づいているのにサマータイム問題

# はじめに
株式会社ピー・アール・オーのアドベントカレンダー15日目を書きます。

もうすぐクリスマスですがサマータイム問題について書きます。
具体的なバージョンは記載しませんがタグにある構成でサマータイムに該当する日付をMySQLに保存すると、なぜか１日マイナスされた日付が登録されてしまいました。
1948-07-02 を登録しようとすると 1948-07-01 が登録されてしまうといった感じです。

# 日本のサマータイムについて
自分は、そもそも日本にもサマータイムって導入されてたの！？というところからで、
意外だったのですが調べてみると戦後間もないころに導入されてた時期があったようです。

参考
https://ja.wikipedia.org/wiki/%E5%A4%8F%E6%99%82%E5%88%BB%E6%B3%95#:~:text=%E3%81%9F%E3%81%AE%E3%81%A7%E3%81%82%E3%82%8B%E3%80%82-,%E5%A4%8F%E6%99%82%E5%88%BB%E3%81%AE%E9%81%A9%E7%94%A8%E6%9C%9F%E9%96%93,-%5B%E7%B7%A8%E9%9B%86%5D

> 1948年（昭和23年） - 五月の第一土曜日の翌日（日曜）から九月の第二土曜日まで （附則第二項）
> 1949年（昭和24年） - 四月の第一土曜日の翌日（日曜）から九月の第二土曜日まで （本則）
> 1950年（昭和25年）及び1951年（昭和26年） - 五月の第一土曜日の翌日（日曜）から九月の第二土曜日まで （改> 正法）
> 1952年（昭和27年）以降 - 廃止

つまり下記の日付を登録しようとすると冒頭のような事象が発生することを確認しました。
1948-05-02（日）～1948-09-11（土）
1949-04-03（日）～1949-09-10（土）
1950-05-07（日）～1950-09-09（土）
1951-05-06（日）～1951-09-08（土）

# 対処法
PlayFrameworkのORMであるEbeanにおいては java.time.LocalDate が使えそうでタイムゾーンに依存することなく保存されること期待してたのですが、うまく保存することができず NULL が登録されてしまいました…
そもそもなにか認識が誤っているのか、扱いを間違えてるのかもしれません。
ひとまず下記のように１時間プラスして登録することにしました。

```Java
		Date date;
		SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
		try {
			date = sdf.parse("1948-07-02 01:00:00");
		} catch (ParseException e) {
			System.out.println("An invalid date" + e.getMessage());
		}
```
サマータイム以外の日付も１時間プラスしてることになりますが日付の登録なので特に問題はありません。

# 別のサマータイム問題も
冒頭にあげた事象の前に発生していた別の問題があったので、そちらについても紹介したいと思います。
サマータイムの開始日に問題がありまして、、、
サマータイムというのは１時間早めるという制度なので開始日である 1948-05-02 00:00 ～ 00:59 という時間帯は JST においては存在しない時間ということになります。

日本時間では以下の日時が存在しない。
1948-05-02 00:00 ～ 00:59
1949-04-03 00:00 ～ 00:59
1950-05-07 00:00 ～ 00:59
1951-05-06 00:00 ～ 00:59

なので上記の値を PlayFramework からMySQLに保存したときに例外発生しました。

# 対処法
MySQLの ServerTimezone をグリニッジ標準時 GMT+9時間と設定することで回避しました。

このあたりの日付を扱うシーンは少ないかもしれませんが誕生日を登録する機能でこの問題に遭遇しました。

以上、日本におけるサマータイム問題のご紹介でした。

最後まで読んで頂きありがとうございます。

尚、対処法に記載した内容については自分が対応したのではなく弊社のスペシャルなエンジニアが対応した対処法になります。
尊敬するエンジニアの1人です:thumbsup:
2023アドカレ21:Figmaでコンポーネントのフォントを変更した後、直す方法

# 何の記事？
これは、[ぐらだけアドカレ2023](https://qiita.com/advent-calendar/2023/c9h11o2)の21日目の記事です。

Figmaで誤ってコンポーネント適用先のフォントを変更してしまった際、参照コンポーネントがあれば、一括で戻せたのでその方法を残します。

# 誰向け？
- Figmaで欠落フォントを誤って一括置換してしまった人

# 何が起こったか
使用フォントがインストールされていないPCでテキスト内容を変更した際に、適用フォントを一括でデフォルトのフォントに置換してしまいました。
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/964152/02f0ad47-c17a-935c-aad4-ee511405c0f1.png" width=50%>

使用フォントがインストールされていないPCでファイルを開き、テキストを選択すると、上記のような`A?`の表示が出ます。
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/964152/fed31ca9-ec5d-6e0c-e4ae-a6a6de819f11.png" width=50%>

さらに、テキスト部分の編集を続けようとすると、使用できないフォントを一括で代替しますか？……というポップアップがでます。今回は誤って一括変更をかけてしまいました。
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/964152/b63c74ad-3be8-beef-1e85-5887472601bf.png" width=50%>
当然ですが、フォントが全て変更されます。

# 対処法
### 参照元コンポーネントのテキストを選択
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/964152/95037954-81e0-b79f-160d-0457ad948168.png" width=50%>


### テキストを変更
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/964152/4ad24b34-3b3f-7d27-0d84-5574274bfe99.png" width=50%>

一瞬で戻ってくれるので、一括で置換してしまった……！という場合は使用フォントが使えるPCで再度変更してあげれば戻ります。

# 備考
当然ですが、コンポーネントの連携を解除していると変更が効かないので
同じフォントを使う、同じデザインを適用する……という箇所はコンポーネント機能を上手く使っていけると良いかと思います。
【Laravel】datetime-localのinputにCarbonでformatを整形した日付データを入れても表示されない場合

# 環境
Laravel 10.22.0

# 状況
データベースからのdatetime型の日付データをBladeのtype="datetime-local"のinputに表示させたい。

以下のように記述しても表示されない

```hoge.blade.php
<input class="form-control" type="datetime-local" value="{{ Carbon::parse($date)->format('Y/m/d H:i') }}">
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2532816/1b34c114-042b-9c02-2ed3-708ad9c8784f.png)


# 解決方法
type="datetime-local"のinputはYYYY-MM-DDThh:mmで受けとることを期待しているため、`Carbon::parse($date)->format('Y-m-d\TH:i')`という風に記述すればよい

```hoge.blade.php
<input class="form-control" type="datetime-local" value="{{ Carbon::parse($date)->format('Y-m-d\TH:i') }}">
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2532816/afa6daf8-a641-cc8a-8653-04012dc151cb.png)

おわり
keyballに雑にスクロール反転機能を搭載した

# 動機
macとwindowsを使用しており、スクロールの方向を統一したかった。

# 前提
keyballのリポジトリをクローンし、自分でビルド可能な環境

# やり方
### 変更を加えるファイル
* qmk/keyboard/keyball/lib/keyball.h
* qmk/keyboard/keyball/lib/keyball.c
* qmk/keyboard/keyball/{所持しているkeyball}/keymap/{任意のkeymap}/config.h

以下ではファイル名を省略してます。

### keyball.h
```
// 20行目あたりのconfigurationsの中に追記
#ifndef KEYBALL_SCROLL_INV
#    define KEYBALL_SCROLL_INV 0
#endif
```
### keyball.c
```
// 184行目あたりのmotion_to_mouse_scrollの最後に追記

static void motion_to_mouse_scroll(keyball_motion_t *m, report_mouse_t *r, bool is_left) {
    // consume motion of trackball.
    uint8_t div = keyball_get_scroll_div() - 1;
    int16_t x   = m->x >> div;
    m->x -= x << div;
    int16_t y = m->y >> div;
    m->y -= y << div;

    // apply to mouse report.
#if KEYBALL_MODEL == 61 || KEYBALL_MODEL == 39 || KEYBALL_MODEL == 147 || KEYBALL_MODEL == 44
    r->h = clip2int8(y);
    r->v = -clip2int8(x);
    if (is_left) {
        r->h = -r->h;
        r->v = -r->v;
    }
#elif KEYBALL_MODEL == 46
    r->h = clip2int8(x);
    r->v = clip2int8(y);
#else
#    error("unknown Keyball model")
#endif

#if KEYBALL_SCROLLSNAP_ENABLE
    // scroll snap.
    uint32_t now = timer_read32();
    if (r->h != 0 || r->v != 0) {
        keyball.scroll_snap_last = now;
    } else if (TIMER_DIFF_32(now, keyball.scroll_snap_last) >= KEYBALL_SCROLLSNAP_RESET_TIMER) {
        keyball.scroll_snap_tension_h = 0;
    }
    if (abs(keyball.scroll_snap_tension_h) < KEYBALL_SCROLLSNAP_TENSION_THRESHOLD) {
        keyball.scroll_snap_tension_h += y;
        r->h = 0;
    }
#endif

// !ここを追記!
// ---------------------
#if KEYBALL_SCROLL_INV
    r->h = -r->h;
    r->v = -r->v;
#endif
// ---------------------
}

```
### config.h
自分のキーマップのconfig.hに以下を記載
```
// どこでも良いので以下を記載
#define KEYBALL_SCROLL_INV 1
```

あとは通常通りビルドしてpromicroに書き込めば完了です。

# あとがき
PR送ったほうがいいものなのかな、と思いつつgithubの使い方覚えられてないので後回し
[Next.js]Next.jsでのSSR実現、SQLite実装方法！[SQLite]

## 初めに
Next.jsにてサーバーサイドレンダリング（SSR）を実現、SQLiteをデータベースとして活用する方法について紹介します！
この記事では、以下の「nihongo.db」データベースの「nihongo」テーブルの情報を取ってきて、表示する手順を具体的に紹介します！

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3570986/4c8af36f-212f-0a32-ecb2-78d38eefdd74.png)


# 1. Next.jsプロジェクトの雛形作成
以下のコマンドにてNext.jsプロジェクトをセットアップします！
その後、作成したプロジェクトへ移動します。
```bash
npx create-next-app プロフェクト名
cd プロジェクト名
```
# 2. SQLiteデータベースとの接続
SQLiteデータベースとの接続を確立するための util/db.js ファイルを作成します！
以下のコードは、nihongo.dbへの接続を確立する openDatabase 関数が定義されています。open メソッドを使用してデータベースへの接続が行われています！

```typescript
// util/db.js
import sqlite3 from 'sqlite3';
import { open } from 'sqlite';

export async function openDatabase() {
  return open({
    filename: './nihongo.db',
    driver: sqlite3.Database,
  });
}
```
次に、接続用のAPIエンドポイントを pages/api/db.js に作成します！
このコードは、他の部分でデータベースに接続するためのconnectDatabase 関数を定義しています。
```typescript
// pages/api/db.js
import { openDatabase } from '../../util/db';

export async function connectDatabase() {
  const db = await openDatabase();
  return db;
}
```
# 3. データの取得とSSRの実装
次に、nihongo.dbからデータを取得し、サーバーサイドでページを描画するコードを pages/index.js へ実装します！
以下のgetServerSideProps 関数は、サーバーサイドでのデータ取得を行います。
connectDatabase 関数を使用してSQLiteデータベースに接続し、db.all メソッドを使用してクエリを実行。
取得したデータは props にセットされ、HomePage コンポーネントで表示されます。

```typescript
// pages/index.js
import React from 'react';
import { connectDatabase } from './api/db';

const HomePage = ({ data }) => {
  return (
    <div>
      <h1>Next.js SSR with SQLite</h1>
      <ul>
        {data.map((item) => (
          <li key={item.aiueo}>{item.aiueo}</li>
        ))}
      </ul>
    </div>
  );
};

export async function getServerSideProps() {
  const db = await connectDatabase();
  const data = await db.all('SELECT * FROM nihongo');

  return {
    props: { data },
  };
}

export default HomePage;
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3570986/db785901-caaf-772b-155a-0ec77a0b2991.png)




## まとめ
これで、SQLiteデータベースとの連携が確立され、サーバーサイドでのページ描画が可能になりました。
DBへの接続は重要な要素となってくるため、今回のモノを参考に沢山使用していきましょう！
秘密鍵のネット経由での簡単で安全な運び方

UNIXまたはLinuxのコマンドラインに慣れていたら、通常の環境であれば、どこでも余分なインストール作業をせずに出来る方法です(そうでない環境があれば知りたい)。

なお、秘密鍵などを運ぶ場合は、その運び方について、そのサーバーごとに秘密鍵の運び方はポリシーがあるかもしれないので気をつけてください(暗号化してもメールでもslack経由は禁止とかあるかもしれません)。

あと、下記の方法は、複数の人による秘密の搬送は、あまり考えて無いです。「合言葉と反復回数」のみ電話で声で話すなどのやり方を、追加的に必要とします。

**以下ですること** :
**openssl** コマンドを使って、安全とされる **aes-256-cbc**の方式を使って、ヒストリに残らないように、その日だけ覚えておけば良い呪文のような合言葉を使って(例, 1waseda2waseda3waseda)
何か秘密にしたい概ねキロバイト程度のファイルを、**base64**コマンドを使って、暗号化された平文ファイルに変換し、後で、同じ合言葉で復号する。
さらに、時間が少し掛かるようにして、スパイされそうになっても何分も待たせる心理的シールドの効果も追加する。


1. **コマンドラインで関数を定義** :
```
# bash用の関数を定義 : 
encode () { openssl aes-256-cbc -e -in <( cat ) -pass pass:$2 -iter $3 | base64  > $1 ; } 
decode () { openssl aes-256-cbc -d -in <( base64 -d $1 ) -pass pass:$2 -iter $3 ; } 
```


2.  **パスフレーズと圧縮するファイルの名前を指定** :
暗号化するときも、復号化するときも、その時に使うサーバーで以下を実行する。つまり、最低、合計2回実行。
```
read -s AIKOTOBA  #  ヒストリなどに全く履歴を残さずに合言葉を変数に格納。その日くらいだけ頭に残すので長めがお勧め。
FILE='暗号化ファイルの名前' # 次の項目3.のコマンドラインが理解出来るなら、ここで決めなくても良い。
```

3. **以下の2行のどちらかで、パスフレーズ付きの圧縮または解凍ができる** :
```
cat 元ファイル  | encode $FILE $AIKOTOBA 100000000 # ← 暗号化する時の端末で実行。
decode $FILE $AIKOTOBA 100000000 > 元ファイル  # ← 復号する時の端末で実行。 > による出力先は元ファイルと違う名前も可。
```
ここで上記のコマンド中の1億(100000000)という数は、反復する計算の回数であり、今の計算機なら約1分程度。20億を指定すると約20分(2の31乗以上の数は指定できないようだ)。― この反復は、一見、暗号論的には意味が余りないかも知れない。しかし、万一パスフレーズがばれても、反復回数が非常に多いことで計算時間を数分かかるので、スパイをしている人からすると、いつまで経っても計算機の調子が悪いように見える。

他、上記で pass: の文字列は必須である。省略するとエラーが起こる。場合によっては小文字で無くて大文字かもしれない。( OpenSSLについての参考となるぺーし:[とほほのOpenSSL入門](https://www.tohoho-web.com/ex/openssl.html) )
AWS認定セキュリティ（専門分野）の有効期限を更新した話

# はじめに

AWS認定は、有効期限が３年までとなっています。

https://aws.amazon.com/jp/certification/recertification/

有効期限を延長するためには、現行の本試験を再度受験して合格せねばなりません。

AWS Certified Security - Specialty (SCS)
は、試験バージョンのバージョンアップがあり、
+ SCS-C01 (前回：合格時）
+ SCS-C02 (今回：合格時）
とバージョンが上がってます。

差分で感じたこと、出来事、など、メモ書きしておきます。

# スコア
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/281768/1907e0cc-8f57-1f11-27bb-a431a05d54a9.png)

一時期、オンライン受験は予約取り放題という感じだった気がするんですが、ちょっと予約の時間枠が減ってきたかも？という印象が予約時にありました。
リアル受験に人が戻ってきているという証左でもありそうです。

+ 確信をもって回答できる問題回答していく。（３分以上悩みそう＆２～３回設問を読み返しそうはフラグをつけて飛ばす）・・・１時間弱
+ フラグを付けた問題を時間多めにとって回答・・・３０分
+ 見直し・・・１０～２０分

位の時間感覚で、ギリギリのギリまで見直してたり、あれこれ悩んだりといった事はしませんでした。

:::note warn
 **初回受験は注意**
プロフェッショナル＆スペシャリティは、設問の文章が飛躍的に長くなります。
一定の受験慣れができるまでは、見直し時間を確保するのも難しいかもしれません。
:::

# 受験対策

## 公式模擬試験

https://explore.skillbuilder.aws/learn/course/15232/aws-certified-security-specialty-official-practice-question-set-scs-c02-japanese

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/281768/843c5874-77e9-6f8c-fb1a-c570552965a0.png)

前回受験から、今回受験の差分という所で、以前はAWS公式模擬試験が有料だったの **無料** になってます。
しかも有料なのに点数しか分からず、正答がなんだったのか分からず仕舞いだったのですが、無料な上に正答と解説もついてるので、受験前の腕試しに受験しておくと良いと思います。

## AWS Web問題集で学習しよう

https://cloud-license.com/

の問題集が、私の感想としては有用でした。

## 抑えておいた方が良いサービスとワンポイント
+ SecureString形式 SystemManager ParameterとSecrets Managerの特徴と使い分け
+ Amazon GuardDutyは、各種、重点的に出題されるので活用方法を網羅
+ AWS KMSを用いた、暗号化・複合の問題（S3の暗号化、キーローテーション関連など多岐）
+ IAMポリシー・SCPの定義の書き方
+ Cloud Trailの活用方法
+ SCPの利用シーン

# 受験トラブル(過去話：再掲)

オンライン受験で予約していたのですが、「ネットワークテスト：７５％から進まない」の事象に引っかかりました。
今までは、ルーターを再起動したり、別PCで試したり、等で上手く回避してこれたのですが、今回は、本当に何をやってもダメな感じで、チェックイン猶予時間：３０分を使い切ってしまいました。

「試験クライアント」の初回起動時だと、Windowsファイヤーウォールの許可ダイアログがポップアップするあたりです。
念のため、Windowsファイヤーウォールを無効にもしてみましたが事象を解消できませんでした。

https://www.pearsonvue.co.jp/Test-takers/Customer-service.aspx

チェックイン時刻が過ぎてしまったら１５分以内にサポートセンターに電話して、日程振替を依頼しましょう。

電話で聞いたら、オンライン受験の一部の人にチェックインできない障害が発生していた模様です。

![ピアソンサポート.JPG](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/281768/d7dfa143-1538-0717-2592-bd3893d9108d.jpeg)


+ 申し込み時メール記載：オーダー番号

を用意しておくとスムーズです。

環境システムチェックは、前日夜に通しておくと「ネットワークテスト：７５％」に引っかからない打率が高いような気がします。
（当日まで１回もやらないと、何故か引っかかりやすい気が。。。）

# まとめ

AWS認定セキュリティ（専門分野）の更新は、試験バージョンが上がってる物の、劇的な変化があったという程の出題内容に変化はなかったように思います。
「AWS Control Tower」関連が比較的、目新しくて普段業務で触らない領域だったので印象深い感じがありました。

https://aws.amazon.com/jp/ec2/nitro/nitro-enclaves/

上記、業務と全く関りがなかったですが、概要位は調べておくと良いかもしれません。

# AWSの相談・お困りごとありましたら、、、

AWSの活用方法や、お困りごとの相談、随時、お仕事の受付しております。

https://www.cs-cloud-aid.com/
Processingでクリエイティブなデータビジュアライゼーションを始めよう

本記事は、[Processing Advent Calendar 2023](https://adventar.org/calendars/8532)用の記事です。

最近、「Processingでデータビジュアライゼーションしたいのだけど、分かりやすい入門書がない」という声をよく聞きます。

たしかに最近はデータビジュアライゼーションを始める場合、PythonやTableauなどから入る人が多いように思います。

Processingはクリエイティブコーディングとしては老舗中の老舗のプログラミング環境であり、Processingの使い手や学習者は、ジェネラティブ・アートやメディア・アートなどに興味がある（＝美しい表現やデザインに興味がある）場合が多く、そうした方々がデータビジュアライゼーションにどんどん参加できるようになることはとても意義深く思っています。

実際、Processingのデータビジュアライセーションの書籍や資料は、かなりレベルが高いものが多く手が出しにくい感は否めません。（[これ](https://www.oreilly.co.jp/books/9784873113784/)とか、[これ](https://bnn.co.jp/products/9784802510134)など）

そこで、私が各大学で担当しているデータビジュアライゼーション・デザインの超基本を学ぶための演習用資料を公開することにしました。

[Data Visualization with Processing (for Beginners)](https://design-and-programming-inc.gitbook.io/data-visualization-for-beginner/)

次のようなビジュアライズをProcessingで作ることをゴールにしてサンプルコードとともに手順を基本から紹介しています。

__バーチャート__
![barchart.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/80141/5961b6db-7401-d79d-c91c-6f967d7e3a1c.png)

__地図__
![map.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/80141/fe34802d-75ba-bc88-3737-5672287180c5.png)

__円環表現（極座標）__
![circle.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/80141/87eee9bf-87c1-d13c-992b-307fe2cac59a.png)


これらは基本コードなのであまり面白くないかもしれませんが、Qiitaで紹介しているコード（[これ](https://qiita.com/masakiyamabe/items/5c5ebc1878865b524d4b)とか[これ](https://qiita.com/masakiyamabe/items/b131c2c2d6ddd2886ba5)）のベースとなる部分です。しっかり基本を身につけたら、面白い独自のビジュアライゼーションデザインに是非トライしてみてください。

感想や質問等ありましたら、コメントにお願いします。
なお、こういった例や解説を充実させたデータビジュアアライズデザインの入門書的な書籍も計画中です。
【ChatGPT有＋DALL-E3＋Code Interpreter】でアニメGIF、その手順です。


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

　今回は、アニメGIFの作成をします。ChatGPT内で完結していますので、それほどの精度は出せませんが、楽しむ分には良いかと。

:::note info
本記事は、ChatGPT有料版＋DALL-E3＋Code Interpreterで行なってお
ります。ChatGPT無料版ではでき
ません。あしからず。
:::

　まずは、
　　作成した作品を
　　　ごらんください。

　なお、X-Twitterに
　　上げたものになります。
　　　Qiitaにアップ
　　　　できなかったのでw

　あれ、X-Twitterでも
　　弾かれた。なんでだ？

　ということで、
　　アップはしません(泣)

　内容は、
　　東京タワーの四季です。
***
　アニメGIF動画を
　　作成するにあたって、
　　　必要なものは、
　　　　以下のとおり。

　・ChatGPT Plus
　・DALL-E3
　・Code Interpreter
　　です。ほかは使いません。

　では、手順です。

　まず、下記の画像を
　　ひとつずつ描画指示。
　　　秋の東京タワー
　　　冬の東京タワー
　　　春の東京タワー
　　　夏の東京タワー

　一度のプロンプトだと、
　　視点が変わってしまいました。
　　　ですから、使えません。
　　　　もちろん、
　　　　　視点を固定できる
　　　　　　プロンプトを
　　　　　　　作成すれば
　　　　　　　　いいわけですが。

　次のPromptを入力。
```Text:アニメGIF作成Prompt
この４つの画像を使ってアニメGIFに変換してください。その際、ゆっくりとモーフィングさせてください。
```

　解析が一度失敗するかも
　　しれませんが、そのままで
　　　再度解析してくれます。

　アニメGIFが生成されたら、
　　ダウンロードリンクが
　　　示されますので、
　　　　クリック（タップ）して、
　　　　　ダウンロードしてください。

　あとは、アニメGIFを見るだけです。

　“モーフィング”について、
　　Google SGEに尋ねてみました。
***
***GoogleSGE***
モーフィング（morphing）とは、コンピュータグラフィックスの手法の1つで、ある物体から別の物体へと自然に変形する映像をみせる技術です。美術や映像、デザイン分野などで多く利用されます。
﻿
モーフィングは、2つの形状を同じ数の点で構成し、それらを対応させることで、形状の変形を行います。そのため、美しく滑らかな変化を実現でき、品質の向上にも利用されます。
﻿
モーフィングは、映画やアニメーションの中で使用されるSFXの1つで、映画の特殊効果によく使われます。
﻿
モーフィングは、前後の画像データをコンピュータで数値的に変形・補完してその中間の画像のデータをつくっていくという手続きを繰り返し、連続的に見えるようにします。
﻿
たとえば、狼の写真と人間の写真を用意してモーフィングを行えば、狼男のような中間画像を生成することができます。﻿
***
　簡単に言うと、と
　　書いておいたけど、
　　　Google SGEの方が、
　　　　いいですねw

　この技法を使う際の
　　ポイントとしては、
　　　動きを抑えることです。

　動きが大きいと、
　　単なる切り替えに
　　　なってしまいます。
***
　モーフィングをしない場合は
　　ただの画像の連結になります。

　画像の切り替えに、
　　別の画像として、
　　　字幕だけの画像を
　　　　差し込む方法も採れます。

　“テキストショット”と
　　呼ばれているようです。

　昔の白黒映画で、
　　無声映画がありましたね。
　　　チャップリンやキートンの。
　　　　アレみたいになります。

　これに活動弁士が
　　いれば、面白いかも。

　“活動弁士”とは、
　　“活弁士”とも呼ばれ、
　　　無声映画の説明役です。

　現在でも
　　活躍されている方がいます。

　山崎バニラ、という名前を
　　ご存知の方も多いかと思います。
　　　テレビに出ていましたね。
　　　　あれはコメンテーター？

　彼女は、
　　声優さんでもあります。
　　　ドラえもんのジャイ子だとか。
***
　話が逸れてしまいましたねw

　アニメGIFにする上での
　　注意点があります。

　ChatGPTの制約かは
　　わかりませんが、
　　　画像のアップはできても
　　　　アニメGIFに組み込まれない
　　　　　場合があります。

　多くは、
　　画像枚数が
　　　多い場合です。

　次にあげるアニメGIFは
　　九枚で構成されていますが、
　　　本来はタイトル画像が
　　　　入る予定でした。

　どこまで
　　できるのかは、
　　　実験していませんので、
　　　　注意をしながら
　　　　　やってみてください。

　あっ、こっちは、アップできた。
　　どうゆうこと？
![animated_sequence_updated.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3457238/b32280fe-e8be-172f-965c-d389e4c75250.gif)

　今回は、ここまで。
ClickupのViewを活用して、直近1週間のタスクを見やすくしてみた

## はじめに

初めまして！

この記事は、ミロゴス Advent Calendar 2023 21日目の記事です。

私はオペレーションチームに所属している一橋と申します。

オペレーションチームでは、タスク管理にclickupを活用しています。

タスクが膨大＆多岐に渡ってくると、おおまかに全体を見渡すことが大変になってきます。

今回はClickupのViewと呼ばれる機能を活用して、直近1週間期日となっている全てのタスクが一目で分かる状態を作っていきたいと思います。

## 前提

- Clickupの構成要素
    - スペース/フォルダ/リスト/タスク/サブタスクという階層構造になっています。
        - スペース=フォルダの一群、フォルダ=リストの一群、以下同文という具合です。
    - 要素が増えてくると、階層構造を掘っていかないと下位にあるものたちの状況を確認することができない状態になっていきます。
- View機能
    - View機能は最上位のスペースに対して使用して、下位にあるものたちをフィルターをかけて絞り込んだり、お好みの見え方にしたりして、整理することができます。今回はタスクを整理していきます。
    

## 実際にやってみます！

- 該当のスペースのページに入り、+Viewを押下して、新規でViewを作成します。
    
    ![Viewを追加.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2981518/4019b66d-07ba-5569-402c-66d80edd12ac.png)

    
- 選択肢の中からどういう見え方にしたいかを選びます。今回は一番オーソドックスなListという形式を選択します。他にもガントチャートやカレンダー、表っぽいものなど様々ありますので、お好みに合わせて試してみてください。
    
    ![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2981518/61f148c4-6be8-ff30-f246-4810ff5bbad8.png)


    
- 新しくviewが追加されました。分かりやすいように「今週のタスク」と名前をつけてみます。こちらのスクリーンショットには映っていないのですが、下部にはスペース配下にある全ての情報が表示されている状態です。
    
    ![View例.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2981518/666d88f2-e8c4-39f1-f1f1-9e8a31e3c96b.png)

    
- 表示する情報を絞り込むためにフィルターを使用します。
    
    ![filter.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2981518/3e03408b-9d4e-bbc9-1d9a-acc8b3cb5618.png)

    
- 今回は期日が今週中かつ、未完了のタスクに絞り込みます。「Add Filter」で条件を追加することができます。
    
   ![filter例.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2981518/cfb95e19-ee64-8e9a-0ee5-5ab1103a98b6.png)

    
- 期日毎に整理するために、Groupを「Status」から「Due Date」に変更します。
    
    ![グルーピング.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2981518/0c6dad45-6348-7502-c736-37a5488dba5f.png)

    
    ![list.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2981518/cc62fabf-fed1-4790-eb75-f4400588a928.png)

    
- Due dateのカラム付近をクリックして、期日の早い順に並び替えて、完成です！
    
    ![並び替え.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2981518/63020b35-9f4e-b692-e05f-61f097b83146.png)

    

## おわりに

とても簡単に整理ができました！皆さんも是非Viewを使ってみてください。
rooksのuseKeyでShift+Keyを使用したい

結論
仮に、shift + kキーの処理を行いたい場合。
shift + kではなく大文字の```K```とする。

```tsx
useKey("K", (e) => {
  // ここに処理
});
```

あるショートカットキーを実装しているときに、Shift+kキーを処理したいときがありました。
useKeysを使用して、["Shift", "k"]としても効果がありません。
kから先に押してShiftならいけるのに……。なぜ……。と思ったら。
e.shiftkeyとかにそもそもたどり着けない。

useEffectでonKeyPressを取得していろいろ調べていると、そもそも大文字Kとして処理されていることが判明。
シンプルだけど有用なグラフ 「ドットプロット」で世界の平均寿命分布を可視化

日本は世界有数の長寿国と言われていますが、他の国々の寿命はどのような状況なのでしょうか？

このことを確かめるために、データを収集してグラフ化してみたのですが、改めて <font color="red">ドットプロット</font>がわかりやすいなあと感じたので以下に掲載しました。2021年の世界各国に対する平均寿命を示しています。
![画像1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/417820/96e3f4b1-ca34-ce9d-9afb-670474bb5aaf.png)
データの出典：世界銀行　Life expectancy at birth, total (years)

このグラフでは、各国の平均寿命について小数点第一位を四捨五入して整数化し、横軸に平均寿命（データ値）、縦軸に該当国を積み上げ、点の数で度数を表現しています。

#### ■ドットプロットについて
どうやら今は、小学校6年生の算数でドットプロットを学習するようです。度数分布表が示されていれば、ソフトウェアを使わなくても簡単に描くことができるグラフです。ドットプロットにより、データにばらつきがあることを理解できます。

ドットプロットは一次元の散布図とも呼ばれ、おおまかな分布や外れ値の確認に有用なグラフです。

<font color="red">またJMPではグラフとデータが連動しているので、ドットプロット上で気になるデータを選択すると、そのドットの詳細（この例では該当する国）をすぐに確認できます。</font>

例えば、日本のデータを選択すると、（男女合わせたときの）平均寿命は84歳であり、世界的に長寿国であることが分かります。
![画像2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/417820/a7d44854-d9fe-6462-3c79-f0a86b105b94.png)

#### ■JMPでドットプロットを描く方法
ドットプロットは「グラフビルダー」で描くことができますが、グラフをドットプロットに切り替えるアイコンなどがあるわけではないので、ここで描き方を説明します。

<font color="blue">ドットプロットの作成</font>
1.	連続尺度の列（この例では、各国の寿命を入力した列）を [X]　ゾーンにドロップします。
2.	左下の「点をずらす」のプルダウンメニューから [正のグリッド]　を選択します。
![画像3.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/417820/fa6eb588-5c2f-1f28-2caf-6b8b4d9e6845.png)

手順2の [正のグリッド]で点をずらすと、以下のように点がX軸に積み重なるように配置されます。

必要に応じて、グラフ右側の凡例の点を右クリックし、マーカーサイズを調整します。
![画像4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/417820/441467eb-30a2-bade-f81e-22bdda708d5f.png)
これでドットプロットの完成です！　操作がわかってしまえば簡単ですね。

#### ■「グラフビルダー」でドットプロットを描くことのメリット
JMPの「グラフビルダー」はグループ変数を使ってグラフを分割したり、色を付けたりできることが大きな特徴です。今回のドットプロットを地域別（アジア、ヨーロッパ、アメリカなど）に分割し、さらに色分けすると、地域間の分布を比較できます。

例えばアジアは値のばらつきが大きく、ヨーロッパ（中央アジアを含む）は平均寿命が高い国々が多く、南アフリカは平均寿命が低い国々が多いことが分かります。

グラフではG7の加盟国にラベルを付けていますが、中でもアメリカの平均寿命の低さが際立っています。
![画像5.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/417820/045fd7a9-5cde-5e5b-4866-09afc3e25f4e.png)
連続変数の分布を表すグラフとしてはヒストグラムが有名ですが、階級の中に属する度数を棒で表すため、今回のように個々の点（国）を選択して詳細を調べてみるといったことが難しい場合もあります。

シンプルなグラフだけど、時として有用なドットプロット。皆さまの業務の中で役立つことがあれば、是非とも使ってみてください。

最後に、平均寿命を地図上で色分けして表示したものも示します。これからヨーロッパの国々の平均寿命が高さや、アフリカの国々の平均寿命の低さが一目で分かります。
![画像6.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/417820/1a8153b6-9986-f40d-c057-5f19e8b36ee8.png)

by  増川 直裕（JMP Japan）

[**Naohiro Masukawa - JMP User Community**](https://community.jmp.com/t5/Naohiro-Masukawa/bg-p/nmasukawa-blog)

■30日間全機能無料の[**JMPトライアル版**](https://www.jmp.com/ja_jp/download-jmp-free-trial.html?utm_campaign=bl&utm_source=jmpblog&utm_medium=article)をぜひお試しください。
DiscordのWebHookで遊んでみよう

初投稿なので文が変になっているかもしれません。
変なところはあまり気にしないでください。

**追記:見返したら文章がおかしかったのでほぼすべて書き直しました。**

# はじめに
DiscordにはWebHookという機能があります。
Discord Botよりも簡単に動かせて、面倒な認証などせずに使えます。

# 実際に遊んでみよう
使うものはDiscordのWebHookURLとHTTPクライアント(cURLでもなんでも)
WebHook URLの取得方法はDiscord>サーバー設定>連携サービスから取得ができます。
https://discord.com/api/webhooks/123456789012345678/abcdefghijklmnopqrstuvwxy
というようなURLが取得できると思います。

## Curlでとりあえず動かす

```bash:bash or cmd
curl -H "Content-Type: application/json" \
-X POST \
-d '{"content": "Hello!"}' \
<WebHookのURL>
```
\<WebHookのURL>の部分は取得したWebHook URLを入れてください。
これを実行させると画像のようなメッセージが送信されます。
![1000004961.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3655292/244a9c8b-7bd7-a115-6219-bd7ea387f0b4.png)

## これを使って何ができるのか
例えば、githubと連携させてPull requestの通知を特定のチャンネルに送ったり、Discord Botと組み合わせてグローバルチャットBotを作ることもできます。

# おわりに
DiscordのWebHookはDiscord Botより多機能というほどではないですが、Discord Botを作らなくても今日の予定や天気などの通知することができるのでみなさんもWebHookを使ってみてはどうでしょうか。

# 参考記事

https://qiita.com/nairoki/items/0ff44cb4a2b8042374c5

https://qiita.com/Eai/items/1165d08dce9f183eac74