OmniAICreator/Qiita-1.07M huggingface dataset:
PythonでExcelシートの目盛線を非表示または表示する

Excel表のインターフェースの直感性は、表内の目盛線のデザインに大きく依存しています。これらの線は、データの正確な整列を助け、セルを明確に区分します。目盛線はExcelインターフェースにデフォルトで表示される補助線で、セルの境界線とは異なり、印刷出力には影響しません。しかし、異なるアプリケーションシナリオでは、データ表示のニーズは多様で、レポートの視覚効果を高めたり、読者の注意をデータ自体に集中させたりするために、目盛線の表示状態を調整することが重要です。目盛線を表示すると表の読みやすさが向上し、特に大量のデータを扱う際にデータの区分が明確になります。一方、目盛線を非表示にすると、レポートがより簡潔でプロフェッショナルに見え、特にプレゼンテーションに適しています。本記事では、**Pythonを使用してExcelワークシートの目盛線を非表示または表示する**方法を紹介し、自動化およびバッチ処理を実現します。

- **[Pythonを使用してExcelワークシートの目盛線を非表示または表示する](#pythonを使用してexcelワークシートの目盛線を非表示または表示する)**

[無料ライセンス申請](https://www.e-iceblue.com/TemLicense.html)

この記事で使用する方法は、[Spire.XLS for Python](https://www.e-iceblue.com/Download/Spire-XLS-Python.html)に基づいています。PyPI：`pip install Spire.XLS`。

## Pythonを使用してExcelワークシートの目盛線を非表示または表示する
ライブラリに提供されている`Worksheet.GridLinesVisible`プロパティを使用して、指定されたセルの目盛線の表示・非表示を設定できます。このプロパティを設定することで、指定されたワークシートの目盛線を非表示または表示できます。操作手順は以下の通りです：
1. 必要なモジュールをインポートします。
2. `Workbook`インスタンスを作成し、`Workbook.LoadFromFile()`メソッドを使用してExcelファイルを読み込みます。
3. `Workbook.Worksheets.get_Item()`メソッドを使用して、指定されたワークシートを取得します。
4. `Worksheet.GridLinesVisible`プロパティを使用してワークシートの目盛線を非表示または表示します。
5. `Workbook.SaveToFile()`メソッドを使用してブックを保存します。
6. リソースを解放します。

コード例
```python
from spire.xls import *
from spire.xls.common import *

# Workbookインスタンスを作成
workbook = Workbook()

# Excelファイルをロード
workbook.LoadFromFile("Sample.xlsx")

# 最初のワークシートを取得
sheet = workbook.Worksheets.get_Item(0)

# ワークシートのグリッド線を非表示にする
sheet.GridLinesVisible = False

# ワークシートのグリッド線を表示する
# sheet.GridLinesVisible = True

# ファイルを保存
workbook.SaveToFile("output/Excelグリッド線.xlsx", FileFormat.Version2016)
workbook.Dispose()
```

結果
![PythonでExcelシートの目盛線を非表示または表示](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/278784/3c8ff9bd-367a-c68d-d5d9-5a85add40ec7.png)

この記事では、Pythonを使用してExcelワークシートの目盛線を非表示または表示する方法を紹介しました。

さらに多くのExcelファイル操作のテクニックについては、[Spire.XLS for Pythonのチュートリアル](https://www.e-iceblue.com/Tutorials/Python/Spire.XLS-for-Python/Program-Guide/Spire.XLS-for-Python-Program-Guide-Content.html)をご覧ください。
[Unity] Built-inとURP(SRP)を切り替える

プロジェクトを新規作成するとき、URPにするか、Built-inにするか、悩んでいませんか？
|Built-in|URP(SRP)|
|:-:|:-:|
|<img width="150" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/89194ff2-ff4e-511d-a453-b093a7bc98b2.png">|<img width="144" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/2735ed1a-9ccb-2e32-3a47-269c6cd31f61.png">|

実はBuilt-inとURP(SRP)、スクリプトから結構簡単に[切り替えられる](https://docs.unity3d.com/ja/2021.2/Manual/srp-setting-render-pipeline-asset.html)んです。

Built-inのシーン上に、URPのオブジェクト(左) と、Built-inのオブジェクト(右) を置きます

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/207d37f1-0f55-15e1-ec09-2c84a4f59348.png)

下記スクリプトを空のオブジェクトにアタッチし、

```
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Rendering;

[HelpURL("https://docs.unity3d.com/ja/2021.2/Manual/srp-setting-render-pipeline-asset.html")]
public class CoreUrpChange : MonoBehaviour
{
    public RenderPipelineAsset exampleAssetA;
    public RenderPipelineAsset exampleAssetB;

    void Update()
    {
        if (Input.GetKeyDown(KeyCode.A))
        {
            GraphicsSettings.renderPipelineAsset = exampleAssetA;
            Debug.Log("Default render pipeline asset is: " + GraphicsSettings.renderPipelineAsset?.name);
        }
        else if (Input.GetKeyDown(KeyCode.B))
        {
            GraphicsSettings.renderPipelineAsset = exampleAssetB;
            Debug.Log("Default render pipeline asset is: " + GraphicsSettings.renderPipelineAsset?.name);
        }
    }
}
```

Aは空に、BにURPのRenderPipelineAssetをセットします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/20e9e4ab-6579-ddc0-8d22-3e22baef4edd.png)

実行し、A、Bのキーを押すとBuilt-in,URPが切り替わります。
| A | B |
|:-:|:-:|
|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/1666db39-023f-f9e9-f5ca-2915a6d2b827.png)|![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/59911/d88882fa-d556-6ea2-48b8-d500ea745277.png)|
【terraform】IAMユーザーに対してMFAを必須化する

## 概要
IAMユーザーに対し、MFAの登録を必須化させたい。
対応として作成したポリシーを備忘録として上げる。

## どうやって作ったの？
- dataドキュメントを使い、IAMポリシーを作成した。
- 詳細は以下

```iam_policy.tf
data "aws_iam_policy_document" "Force_MFA_Policy" {
  statement {
    effect = "Deny"
    not_actions = [
      "iam:ResyncMFADevice",
      "iam:ListVirtualMFADevices",
      "iam:ListMFADevices",
      "iam:GetAccountPasswordPolicy",
      "iam:EnableMFADevice",
      "iam:DeleteVirtualMFADevice",
      "iam:DeactivateMFADevice",
      "iam:CreateVirtualMFADevice",
      "iam:ChangePassword"
    ]
    resources = ["*"]
    condition {
      test     = "BoolIfExists"
      variable = "aws:MultiFactorAuthPresent"
      values   = ["false"]
    }
  }
}

resource "aws_iam_policy" "Force_MFA_Policy" {
  name   = "Force_MFA_Policy"
  path   = "/"
  policy = data.aws_iam_policy_document.Force_MFA_Policy.json

  tags = {
    Name = "Force_MFA_Policy"
  }
}
```

## まとめ
上記ポリシーを管理対象者の所属するグループにアタッチすることで、該当者全てがMFAを登録しなければ何も参照できないような動作となることを確認した。
昨今のセキュリティ観点からも、該当者がMFAの必須化を行ってくれるよう促すことも大切。


以上！
最後まで見ていただき、ありがとうございました。

## 参考文献
https://registry.terraform.io/providers/hashicorp/aws/latest/docs/data-sources/iam_policy_document

https://dev.classmethod.jp/articles/forced_mfa/

https://qiita.com/moko_Swallows/items/daf0456f3a47fd323e1a

https://blog.serverworks.co.jp/2021/06/11/063705#%E5%85%AC%E5%BC%8F%E3%83%89%E3%82%AD%E3%83%A5%E3%83%A1%E3%83%B3%E3%83%88%E3%81%AB%E8%BC%89%E3%81%A3%E3%81%A6%E3%81%84%E3%82%8BIAM%E3%83%9D%E3%83%AA%E3%82%B7%E3%83%BC%E3%81%A7%E3%81%AE%E5%AF%BE%E5%BF%9C%E6%96%B9%E6%B3%95

https://dev.classmethod.jp/articles/force-mfa-with-iam-changepassword/
ngx-translate で Angular の多言語対応

Angular の多言語対応を ngx-translate で行ったのですが、シンプルな対応方法の日本語情報がなかなか見つからなかったので、こちらにメモを残しておきます。

## はじめに
この記事では、以下の内容に対応します。
* 日本語と英語に対応する
* それ以外の言語の場合は英語を表示する
* ブラウザの言語設定に合わせる

動作環境のバージョンは、投稿時点から考えると少し古いですが以下の通りです。
* Angular 11.2.14
* ngx-translate 6.0.0

## インストール
ngx-translate をインストールします。
Angular のバージョンによって、それぞれ対応するバージョンが異なりますので、 [リリース](https://github.com/ngx-translate/core/releases) のページを確認して、必要に応じてバージョンを指定しましょう。

```bash
npm install --save @ngx-translate/core @ngx-translate/http-loader
```

## モジュールのインポート

app.module.ts の `import` に以下の内容を追加します。

```typescript:src/app/app.module.ts
import { HttpClientModule, HttpClient } from '@angular/common/http';
import { TranslateLoader, TranslateModule } from '@ngx-translate/core';
import { TranslateHttpLoader } from '@ngx-translate/http-loader';
```

app.module.ts の `import` の後に以下の内容を追記します。

```typescript:src/app/app.module.ts
export function HttpLoaderFactory(http: HttpClient) {
  return new TranslateHttpLoader(http);
}
```

app.module.ts の `@NgModule` の `imports` に以下の内容を追加します。

```typescript:src/app/app.module.ts
  imports: [
    // BrowserModuleなど...
    HttpClientModule,
    TranslateModule.forRoot({
      loader: {
        provide: TranslateLoader,
          useFactory: HttpLoaderFactory,
          deps: [HttpClient]
      }
    })
  ],
```

## 初期化

AppComponent で ngx-translate を初期化します。
app.component.ts に `import` を追加して、 `AppComponent` のコンストラクタを以下のようにします。

```typescript:src/app/app.component.ts
import { TranslateService } from '@ngx-translate/core';
```

```typescript:src/app/app.component.ts
  constructor(translate: TranslateService) {
    translate.setDefaultLang('en');
    translate.use(window.navigator.language);
  }
```

## 辞書ファイルの配置

辞書ファイルは src/assets/i18n に配置します。ファイル名は {lang}.json の形式です。ここでは en.json と ja.json を置きます。

```json:en.json
{
  "hello": "Hello"
}
```

```json:ja.json
{
  "hello": "こんにちは"
}
```

## 翻訳の適用

翻訳を適用するには、コンポーネントの HTML の中で以下のように書きます。

```html
<p translate>hello</p>
```

以下のようにバインディングの中でパイプで渡すこともできます。

```html
<p>{{ 'hello' | translate }}</p>
```

これで最低限の多言語対応ができるようになったと思います。

### 参考
https://www.digitalocean.com/community/tutorials/angular-ngx-translate
JavaScriptでtry文を使った際にcatch句で正しく例外が捕捉されない原因

# はじめに

JavaScriptでtry文を使った際にcatch句で正しく例外が捕捉されないという事象が発生したので、原因をまとめました。



# 当該ソースコード

以下が問題のソースコードです。

``` JavaScript:main.js
// 処理を実行している最中に例外が起きても例外処理が実行されない
try{
  btnElm.addEventListener('click', () => {
    // 処理
  });
} catch(e) {
  // 例外処理
}
```

ボタンをクリックして呼び出した処理を実行している最中に例外が発生しても例外処理が実行されません。

# 原因と対策
### 原因
ずばり、addEventListenerが非同期で行われる処理であることが原因です。図にすると以下の通りで、addEventListenerの処理が別のコンテキストで行われており、try文で例外を捕捉することができません。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3287818/126075ca-6039-71b9-f4de-53952dd98dc3.png)

### 対策
以下の通りコードを書き直しましょう
```JavaScript:main.js
btnElm.addEventListener('click', () => {
    try{
        // 処理
    } catch(e) {
        // 例外処理
    }
});
```
非同期的に実行されるaddEventListener内で例外を捕捉しているので、ただしく例外処理が実行されます。処理の流れを図に表すと以下の通りです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3287818/743711ba-917a-0bdc-8978-00506792391b.png)
【Mac→Ubuntu】サクッとVSCodeリモート開発&リモートデスクトップ

## やったこと

- Ubuntu 22.04 LTS
- MacBook Air

で、外出先のMacからUbuntuにアクセスしてリモート開発とリモートデスクトップができる環境を**サクッと**構築した。

難しいコマンドは不要で、ほぼ画面ポチポチでできる。

## VPN

- Ubuntuに[Tailscale](https://tailscale.com)をインストール
- MacにTailscaleをインストール

外出先でMacから自宅のUbuntuにアクセスしたかったので、VPNに接続する。
100デバイスまで無料で、インストールするだけでVPNが使えて便利。

## リモート開発

- サーバー: Ubuntuでsshdを有効にする
- クライアント: VSCodeの「[Remote - SSH](https://marketplace.visualstudio.com/items?itemName=ms-vscode-remote.remote-ssh)」拡張機能を利用

拡張機能のおかげで、リモート上のプロジェクトであっても、ローカルのプロジェクトの場合とほとんど同じような開発体験が得られる。
拡張機能はサーバー側で動くので、サーバー側のマシンスペックをフル活用できる。
ポートフォワーディングもしてくれるので、リモート側で立ち上げた開発サーバーもlocalhost:8000みたいにローカルの場合と同様に簡単にアクセスできる。

## リモートデスクトップ

- サーバー: Ubuntuの設定アプリからリモートデスクトップを有効にする
- クライアント: Macに[Microsoft Remote Desktop](https://apps.apple.com/jp/app/microsoft-remote-desktop/id1295203466)をインストール

Ubuntu 22.04 LTSでRDPが設定アプリから簡単にセットアップできるようになったので便利。
参考: [Ubuntu Weekly Recipe 第713回 Ubuntu 22.04 LTSの新機能、リモートデスクトップのRDPサポートを使用する](https://gihyo.jp/admin/serial/01/ubuntu-recipe/0713)

SSHがあればリモートデスクトップは必要ないと思うこともあるが、あったらあったで痒いところに手が届いて便利。
出先で、ああリモートデスクトップがあれば…とたまに思うことがなくなる。
SECCON CTF for Begginer 2024 WriteUp

# はじめに
少し遅くなってしまいましたが，2024/06/15から16にかけて行われたSECCON BEGINNERS CTF 2024のWriteupを書いていきたいと思います．  　　

当初の目標としては難易度`beginnrs`を全部解けたらいいなとか思ってたんですが現実はそんなに甘くなく結局2問しか解けず，結果は513位と散々な結果でした．　　
  
しかし去年は1問しか解けてない(去年はチームで参加して解いたのは僕ではないので実質0問)のに対して今年は2問解けたので多少は成長してるかなと思います．
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3015493/3a67ed81-aed3-0f5c-54a3-fa495b30aa0b.png)


# simpleoverflow
以下のようなソースコードが配布されます．
```C:src.c
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

int main() {
  char buf[10] = {0};
  int is_admin = 0;
  printf("name:");
  read(0, buf, 0x10);
  printf("Hello, %s\n", buf);
  if (!is_admin) {
    puts("You are not admin. bye");
  } else {
    system("/bin/cat ./flag.txt");
  }
  return 0;
}

__attribute__((constructor)) void init() {
  setvbuf(stdin, NULL, _IONBF, 0);
  setvbuf(stdout, NULL, _IONBF, 0);
  alarm(120);
}
```
このコードのおかしいところは配列`buf`が要素数10で定義されているので，10バイト分確保されていますが，`read`関数では`0x10(16バイト)`分読み込むようになっています．  
定義の順番からしても配列`buf`の後に`is_admin`が定義されているので入力する際にオーバーフローを狙っていけそうですね．

目標としては`is_admin`の中身を1にすればいいので`\x1`を書き込めればいいと思います．また`is_admin`は`int`型で定義されているので4バイト確保されています．  

なので入力する文字列としては，`buf`に書き込む10バイト分はなんでもいいのでとりあえず`AAAAAAAAAA`とかにしときます．問題の`is_admin`に書き込む内容ですがリトルエンディアンで書き込む必要があるため`\x1\x0\x0\x0`とする必要があります．  

なので最終的には`AAAAAAAAAA\x1\x0\x0\x0`を入力すればflagがgetできます．  


# getRank
配布される`main.ts`の中身の一部です．
```ts:main.ts
const RANKING = [10 ** 255, 1000, 100, 10, 1, 0];

type Res = {
  rank: number;
  message: string;
};

function ranking(score: number): Res {
  const getRank = (score: number) => {
    const rank = RANKING.findIndex((r) => score > r);
    return rank === -1 ? RANKING.length + 1 : rank + 1;
  };

  const rank = getRank(score);
  if (rank === 1) {
    return {
      rank,
      message: process.env.FLAG || "fake{fake_flag}",
    };
  } else {
    return {
      rank,
      message: `You got rank ${rank}!`,
    };
  }
}

function chall(input: string): Res {
  if (input.length > 300) {
    return {
      rank: -1,
      message: "Input too long",
    };
  }

  let score = parseInt(input);
  if (isNaN(score)) {
    return {
      rank: -1,
      message: "Invalid score",
    };
  }
  if (score > 10 ** 255) {
    // hmm...your score is too big?
    // you need a handicap!
    for (let i = 0; i < 100; i++) {
      score = Math.floor(score / 10);
    }
  }

  return ranking(score);
}
```
変数`rank`が1の時にFlagがGETできるみたいですね．
rankの求め方は`const RANKING = [10 ** 255, 1000, 100, 10, 1, 0];`のどの値よりも大きいかで決まるみたいですね．  

＊例えばScoreが1001だったら`10 ** 255`よりも小さく`1000よりも大きいので`rankは2になります．なので`10 ** 255`よりも大きい値を入力すればいいのですが以下のような条件があるため，これではうまくいきません．
- score>10**255よりも大きい
    - この場合入力したスコアよりも減点されてしまいます
- 入力文字数が300文字より大きい
    - この場合-1になってしまいます．  
  
ここで`input`が`parseInt`を適用してscoreに渡されていることがわかります．　　

[リファレンス](https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Global_Objects/parseInt#%E6%A7%8B%E6%96%87)によると入力された文字列に`0x`が含まれている場合，16進数と解釈されるようです．　　

なのでBurpsuite使って，`0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF`みたいな感じで300文字超えない程度に送信すればOKです．  

# 最後に
多少は考え方がわかるようになってきた気がしますが，まだまだ実力不足を感じました．  

特にcryptoやreverseなどはほとんど何も知らないので少しずつ勉強していきたいです．  

次はWani CTFですね．どのくらい参加できるかわかりませんが参加される皆さん頑張りましょう！
homebrewでjavaをインストールしたがUnable to locate a Java Runtimeエラーになった時の解消法

## 背景

```
$ brew install java
```

でmac book proにインストールをしたのに

```
$ java --version
The operation couldn’t be completed. Unable to locate a Java Runtime.
Please visit http://www.java.com for information on installing Java.
```

になった

## PCスペック

| 項目 | 情報 |
| --- | --- |
| OS | macOS Sonoma 14.4.1  |
| ハードウェア | MacBook Pro 16inc 2023 |
| プロセッサ | Apple M2 pro |
| メモリ | 32GB |


## 解消法

シンボリックリンクを張るといいらしい。

### 以下のようにして対応

javaのインストール


```
$ brew install java
```

シンボリックリンクを張る
```
$ sudo ln -sfn $(brew --prefix)/opt/openjdk/libexec/openjdk.jdk /Library/Java/JavaVirtualMachines/openjdk.jdk
```

```
$ java --version
openjdk 22.0.1 2024-04-16
OpenJDK Runtime Environment Homebrew (build 22.0.1)
OpenJDK 64-Bit Server VM Homebrew (build 22.0.1, mixed mode, sharing)
```

出来た！
PHP 8.2 から PHP 8.3 にアップグレードするための手順（Linux）

PHP 8.2 から PHP 8.3 にアップグレードするための手順を以下にまとめます。

### 手順 1: 現在のPHPパッケージのリストを取得

現在インストールされているPHPパッケージのリストをファイルに保存します。

```bash
rpm -qa | grep php > current_php_packages.txt
```

### 手順 2: PHP 8.3 リポジトリを有効化

必要なリポジトリをインストールし、PHP 8.3のリポジトリを有効にします。

```bash
sudo dnf install -y epel-release
sudo dnf install -y https://rpms.remirepo.net/enterprise/remi-release-9.rpm
sudo dnf module reset php
sudo dnf module enable php:remi-8.3
```

### 手順 3: 現在のパッケージを削除

保存したリストを使用して現在のPHP 8.2のパッケージを削除します。

```bash
sudo xargs dnf remove -y < current_php_packages.txt
```

### 手順 4: インストールコマンドを生成するシェルスクリプトを作成

以下のシェルスクリプトを `generate_install_command.sh` という名前で保存します。

```bash
#!/bin/bash

# 現在のPHPパッケージのリストファイル
input_file="current_php_packages.txt"

# 新しいインストールコマンドの出力ファイル
output_file="install_php_packages.sh"

# 出力ファイルの初期化
echo "sudo dnf install -y \\" > $output_file

# 入力ファイルを読み込み、パッケージ名を変換して出力ファイルに追加
while IFS= read -r package
do
    # パッケージ名を抽出してバージョン番号を削除
    package_name=$(echo $package | sed 's/-[0-9].*//')

    # プレフィックスが 'php' で始まるパッケージだけを処理
    if [[ $package_name == php* ]]; then
        echo "    $package_name \\" >> $output_file
    fi
done < "$input_file"

# 最後の行のバックスラッシュを削除
sed -i '$ s/\\//' $output_file

# スクリプトを実行可能にする
chmod +x $output_file

echo "Install command script created: $output_file"
```

### 手順 5: スクリプトを実行してインストールコマンドを生成

シェルスクリプトを実行してインストールコマンドを生成します。

```bash
bash generate_install_command.sh
```

### 手順 6: インストールコマンドを実行してPHP 8.3をインストール

生成されたインストールコマンドを実行して、PHP 8.3のパッケージをインストールします。

```bash
sudo bash install_php_packages.sh
```

### 手順 7: PHP-FPM の再起動

PHP-FPMを使用している場合は、再起動します。

```bash
sudo systemctl restart php-fpm
```

### 手順 8: PHP バージョンの確認

PHPのバージョンを確認して、アップグレードが成功したことを確認します。

```bash
php -v
```

### 手順 9: Nginxの設定確認と再起動

Nginxの設定ファイル `/etc/nginx/conf.d/server.conf` を確認し、設定が正しいことを確認します。次に、Nginxを再起動します。

```bash
sudo systemctl restart nginx
```

### 手順 10: PHP情報ページの確認

PHPの設定と連携が正しく機能しているかを確認するために、ドキュメントルート（例： `/var/www/html`）に `info.php` を作成し、ブラウザで確認します。

```bash
echo "<?php phpinfo(); ?>" | sudo tee /var/www/html/info.php
```

ブラウザで `http://your_server_address/info.php` にアクセスし、PHP情報ページが表示されることを確認します。

これで、PHP 8.2からPHP 8.3へのアップグレード手順は完了です。
Azure DevOpsで、過去の状態を確認する方法

# まとめ
Azure DevOpsに対して、クエリでASOF句を書くことで過去の状態を取得することができる。
ASOF句を含むクエリを書き、実行する簡単な方法の一つとして、Azure CLIを用いる方法がある。
Azure CLIを用いてクエリを実行すると、結果がJSONで取得できる。

# はじめに
Azure DevOpsでは、Work Itemごとに変更履歴を持っており、個々のWork Itemの過去の状態であればUIから確認することが可能です。しかし、この方法である時点で複数のWork Itemがどのような状態だったかを確認するには、複数のItemを見ていく必要があり、現実的ではありません。

Azure DevOpsのクエリは内部的には[WIQL](https://learn.microsoft.com/ja-jp/azure/devops/boards/queries/wiql-syntax?view=azure-devops)という言語で記述されており、APIなどでは直接WIQLでクエリを指定することも可能です。
WIQLではASOF句が定義されており、これを用いることで指定した時点でのWork Itemの値を取得することができます。
本稿では、Azure CLIからクエリを実行することで過去の状態を取得する方法を説明します。

# 事前準備
- Azure CLIをインストールします。
  [Azure CLI をインストールする方法 | Microsoft Learn](https://learn.microsoft.com/ja-jp/cli/azure/install-azure-cli)

# 手順

1. Azure DevOpsにログインします。  
   ```
   az devops login --org https://dev.azure.com/xxxxx
   ```

2. クエリを実行します。  
   ```
   az boards query --org https://dev.azure.com/xxxxx --wiql "クエリ"
   ```

こうすることで、クエリの実行結果がJSONで返されます。例えばこれをファイルにリダイレクトし、JSONビューワなりで開くことで結果を確認することができます。
PHPってそもそも何ができるの？PHPとは？


こんにちは、KoenigWolfです。今日はHTMLとCSSの勉強を終えた人向けに、PHPによるWebアプリケーションの話をしていきたいと思います。これに関してはいくつかのシリーズものとして連載していきたいと思っています。直近の予定としては、今回の記事では「PHPってそもそも何ができるの？」という話をしていきたいと思います。次回の記事では、皆さんのPC上、ローカルPCでPHPを動かすためのツールであるMAMPやXAMPPなどを紹介していきたいと思います。

さて、今日はHTMLとCSSの勉強を終え、次に何を勉強するか迷っている人向けに、PHPについてお話ししたいと思います。その前に、HTMLとCSSを初めて学び、ある程度サイトを作れるようになってきた方が、更なるスキルアップとして大きく2つの方向性があります。1つはサイト制作、もう1つはWebアプリ開発です。

サイト制作の方向に進みたいという方は、次にJavaScriptやjQueryを学ぶことになります。Webアプリ開発に進みたいという方は、PHPやRubyなどのプログラミング言語を勉強することになります。もちろん他にも選択肢はありますが、初心者がWebアプリ開発の勉強をするのであれば、PHPかRubyがオススメです。情報量が多く、他の選択肢に比べて敷居が低いので、初心者にとって良い選択肢だと思います。

サイト制作とWebアプリ開発の違いについて説明すると、Webアプリ開発のイメージは、TwitterやInstagramのようなサービスです。ユーザー登録をして、ユーザーが投稿して楽しむサービスです。こういったサービスを作ってみたい方は、Webアプリ開発を志すと良いと思います。一方、サイト制作の場合は、ユーザー登録やユーザーが投稿するといった機能はなく、企業のコーポレートサイトやイベントの特設サイトなど、ユーザーに情報を発信するためのWebサイトを作ることになります。

どちらの方向に進みたいかを考えてみて、Webアプリ開発を選んだ方は、PHPやRubyを使ってユーザーのログインや投稿を制御する必要があります。今回はPHPにフォーカスを当てて話を進めますが、Rubyに置き換えても同じ内容が通じるので、興味がある方はPHPの部分をRubyに置き換えて続きを見てください。

#### WebアプリケーションにおけるPHPの役割

PHPの役割は大きく2つあります。1つ目はHTMLを作ること、2つ目はデータを管理することです。この2つについて詳しく説明します。

まず、皆さんがWebブラウザを使ってWebサイトを見るときの流れについて説明します。ブラウザでサイトを見るときは、URLを指定する必要があります。例えば、ブラウザに「https://www.google.com/index.html」というURLを入力すると、Googleのサーバーから「index.html」という書類が返されて、ブラウザがそれを表示します。HTMLファイルはテキストファイルであり、自分で書き換えない限り内容は変わりません。

しかし、現在の時間を表示したい場合など、動的に内容を変えたいときがあります。その場合、PHPを使うと便利です。PHPはHTMLを動的に生成することができるため、例えば現在の時間を表示することが可能です。

次に、データの管理について説明します。昔のWebサイトでは、「今日は何人の方が訪れました」や「累計何人の方が訪れました」という訪問者カウンターがよく使われていました。これを実現していたのがPHPです。PHPはデータを計算することが得意ですが、記憶することは苦手です。そのため、データベースというツールを使ってデータを記録します。PHPがデータベースを使うことで、訪問者数などを管理しています。

最後に、PHPの具体的なコード例を見てみましょう。例えば、現在の時間を表示するPHPコードは以下のようになります：

```php
<?php
echo "現在の時間は " . date("Y-m-d H:i:s") . " です。";
?>
```

このコードを実行すると、現在の時間が表示されます。

### 結論

PHPはHTMLを動的に生成し、データを管理することができます。HTMLやCSSに加えてPHPを使えるようになると、Webアプリケーションの幅が広がります。ぜひ、PHPを学んでオリジナルのWebアプリケーションを作ってみてください。

今回はここまでです。面白かったよ、参考になったよという方はいいねとフォローをお願いします。では次回の記事でまたお会いしましょう。
NotchでNVIDIA Virtual Backgroundがなぜか使えないとき

# 症状
NVIDIA Virtual Backgroundノード (https://manual.notch.one/0.9.23/en/docs/nodes/post-fx/image-processing/nvidia-virtual-background/) を使おうと思ったが、いきなりエラーを吐くようになった。この前まで使えていたはずなのに...? SDKは入っているはずなのに、入っていないという旨のメッセージが出ている。

# 対処
ノードを選択した状態で、雑に`Ctrl + R` をするとSDKを認識してくれてエラーが消えた。ルートにつながったことでなにかしら状態の更新が走ったのだと思う。

どなたかの助けになれば...!
【Laravel11.x】例外(Exception)のテストはExceptions::fake()が便利

## はじめに
例外が投げられたか？をテストするとき、決まり事のように`expectException`を使ってましたがExceptionsという便利なファサードが増えていたのでメモ

:::note warn
Exceptionsファサードを使用するには**Laravel11.4** 以上が必要です
:::

## 例外が発生したことをテストしたいとき

```HogeTest.php
use Illuminate\Support\Facades\Exceptions;
use App\Exceptions\FugaException;

Exceptions::fake();

// テストしたい処理をここで実行する

// FugaExceptionが発生したことをアサート
Exceptions::assertReported(FugaException::class);

// コールバックも可能
// 以下の例はキャッチしたFugaExceptionのメッセージが'The order was invalid.'の場合のみ成功する
Exceptions::assertReported(function (FugaException $e) {
    return $e->getMessage() === 'The order was invalid.';
});
```

## 例外が発生しないことをテストしたいとき

```HogeTest.php
use Illuminate\Support\Facades\Exceptions;
use App\Exceptions\FugaException;

Exceptions::fake();

// テストしたい処理をここで実行する

// FugaExceptionが発生して"いない"ことをアサート
Exceptions::assertNotReported(FugaException::class);

// なんの例外も発生して"いない"ことをアサート
Exceptions::assertNothingReported();
```

## 特定の例外だけテストしたいとき

```HogeTest.php
use Illuminate\Support\Facades\Exceptions;
use App\Exceptions\FugaException;
use App\Exceptions\PiyoException;

// FugaExceptionをのみテスト
Exceptions::fake(FugaException::class);

// FugaExceptionが投げられても処理続行
throw new FugaException('fakeしているので処理はここで止まらない');

// FugaExceptionが発生していることをアサート→true
Exceptions::assertReported(FugaException::class);

// PiyoExceptionはExceptions::fakeに入っていないので、ここで処理が止まる
throw new PiyoException('fakeしていないので処理はここで止まる');
```

```HogeTest.php
// 配列で複数指定することもできます
Exceptions::fake([FugaException::class, PiyoException::class]);
```

## expectException()ぽい書き方もできる

例外のテストで調べると大体でてくるexpectExceptionっぽい書き方もできます

```HogeTest.php
use Illuminate\Support\Facades\Exceptions;
use App\Exceptions\FugaException;

Exceptions::throwOnReport([FugaException::class]);

throw new FugaException();

// FugaExceptionが発生したのでthrowOnReportは成功します
```

この場合最初にEvent::fake()を書かなくてもOKです

## おわりに
公式ドキュメントをみて知識をアップデートしていかないと、あっという間に古い知識になっていきますね。

Exeptionsファサードは`assertThrows`や`expectException`に比べて可読性が高いと思うので、どんどん使っていきたいです

## 参考

https://laravel.com/docs/11.x/http-tests#exception-handling

https://laravel-news.com/laravel-11-4-0

https://github.com/laravel/framework/pull/50704#issue-2201000660
新登場！Slackリストでメンバーのタスクを見える化しよう

## Slackリストとは

先日発表されたSlackリストが、私の利用しているワークスペースに追加されたので、早速試してみました。

https://www.publickey1.jp/blog/24/slackslack.html

Slackリストというのは、Slack上でメンバーや自身のタスク管理ができるSlackの新機能です。
メンバーのタスクを見える化したいと思っていたので、ちょうどよいタイミングでした。

## Slackリストの使い方

Slackリストは、Slackの左のサイドバーにある「リスト」からアクセスできます。
Slackのサイドバーのアイコン増えてきたので、並び替えも設定できると嬉しいなぁ・・・

![スクリーンショット 2024-06-21 13.18.16.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3741957/22b8ab44-39eb-8912-96da-c60aef040d0d.png)


リスト画面を開くと、空っぽのリストから作る「新規」ボタンが表示されます。
テンプレートからリストを作成することもでき、こちらのほうがオススメ。
テンプレートの、「すべてを表示」をクリックすることにより、テンプレートが表示され、使いたいテンプレートを選択したら「テンプレートを使用する」ボタンをクリックします。
するとテンプレートデータが差し込まれた状態でリストが作成されます。
私はカンバン方式で使いたかったので、「プロジェクトの追跡」というテンプレートを使ってみました。

![スクリーンショット 2024-06-21 13.39.08.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3741957/bdefbbf3-a02a-d865-ea56-9265cffed8cd.png)


新しいタスクを追加するには、画面右下の「アイテムを追加」ボタンをクリックします。
ここでステータス、優先度、担当者、期限を設定することができます。
それぞれの項目は好みに合わせて変更できます。

![スクリーンショット 2024-06-21 15.44.43.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3741957/f3652054-f14d-a5c2-cfc0-1d2bed081432.png)


## チャンネルメンバーに共有する

画面右上に共有というボタンがあり、ここからチャンネル全体に共有できます。

![スクリーンショット 2024-06-21 15.47.04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3741957/19bfef54-91c8-d419-0b3f-4f2600f8955f.png)


チャンネル単位で「閲覧可能」や「編集可能」を設定できます。
チャンネルに共有し、メンバー全体のタスクを登録してもらうことで見える化できます。

## ビューを変更して見やすく管理

メンバーにタスクを登録してもらったら、今度は見やすくするためビューの機能を使ってみましょう。
Slackリストの画面左上のビューのアイコンをクリックすると、ビューの変更ができます。

![スクリーンショット 2024-06-21 15.49.43.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3741957/b9c41b0d-2fc7-ddcb-e5d0-2e913f41b4ae.png)

デフォルトで以下のビューがあります。

* **私が担当**: Slackにログインしている現在のユーザーが担当しているタスクを表示
* **優先度**: 優先度ごとにグループ表示
* **完了**: 完了のみ表示
* **未完了**: 完了以外を表示
* **ステータス**: カンバン方式での表示

このビューは個人管理の設定になるため、他のメンバーには影響しません。
自分が「ステータス」表示にしたからといって、他のメンバーには影響しないので、自分好みのビューに変更しましょう。

## これからに期待な部分

* タスクで期限を設定してもなにも通知されない
  これは早めになんらかの通知が出せるようにしてほしいなぁ・・・

## まとめ

Slackの新機能であるSlackリストを使うことで、Slack上でメンバーや自身のタスク管理ができるようになりました。以下のようにSlackリストを活用することで、効率的なタスク管理が可能です。

1. テンプレートを使ってリストを作成することで、すぐに使い始められる
2. タスクにはステータス、優先度、担当者、期限を設定でき、管理しやすい
3. チャンネル単位でリストを共有し、メンバー全体のタスクを見える化できる 
4. ビュー機能を使って、自分好みの見やすい表示にカスタマイズできる

Slackリストを使えば、わざわざ別のツールを使わなくてもSlack上だけでタスク管理ができるので、ワークフローがシンプルになります。
実装されたばかりの機能なので、これからの機能追加に期待です！
今後のアップデートに期待です！
[Dify] Human in the Loop 情報収集

どうも、やまぐちです。
今回はHuman in the loop的に情報収集ができるようにDifyのChatFlowで工夫してみました。
情報検索を満足いくまで行ってからまとめるとかをDifyでもしたいですよね...?
今回はそれができるDifyのChatFlowを作成してみました。

以下のような感じで情報集めができます。

https://x.com/hudebakonosoto/status/1804055111825805534

## 全体像
まず全体像です。
検索フェーズとまとめフェーズに分かれています。
検索で満足いく内容が出てきたら、まとめフェーズに移ってまとめてもらいます！
基本Difyではフェーズ分けが苦手なのですが、チャット内容にワードを検知してフェーズ分けしています。
今回は「検索」から始まるか、「まとめ」から始まるかで分岐しています。
質問分類器でやってもいいのですが、割と間違えることもあるのでロジックで制御したかったのです。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/376115/59a00dc8-8f25-c57c-e576-ffe998421ac4.png)

## 開始ノード
まず最初に情報収集したい内容をThemeに入れ、どれだけ深掘りするかの内容をlimitに入れます。
limitの説明は検索フェーズの説明で行います。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/376115/4378db33-a584-fe83-d911-cfc731c3dbd1.png)

## 分岐ノード
チャット内容にワードを検知してフェーズ分けしています。
今回は「検索」から始まるか、「まとめ」から始まるかで分岐しています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/376115/52a6f523-1543-ea41-e6d0-67d25549e30a.png)

## 検索フェーズ

### フェーズ概要
検索フェーズでは基本最初に入力したThemeの内容を検索して深掘りしていくフェーズです。
深掘りのしたかはマルチクエリリトリーバーを参考にしています。
最初に入力するlimitの数だけ質問を拡張させ、その内容をWeb検索用に最適化しTavilyで検索していきます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/376115/f465967b-a0f0-db64-7b6a-cdf7de9b83bf.png)

※ マルチクエリリトリーバーは！[こちら](https://qiita.com/hudebakononaka/items/84a81d3b091dc0410647)でDify構築してます

### 質問拡張

質問を拡張します。拡張する時にlimitの数だけ質問を作成します。出力は文字列で出てくるので質問抽出器で質問をリスト化します

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/376115/3f9eb460-95c1-d160-1fe3-31bab92cc81b.png)


### イテレーション
質問ごとにWeb検索用に最適化し、Tavilyで検索していきます。出力するLLMでは必ずメモリを有効にしておきましょう！これがないと情報収集した内容がまとめ時に使用できないので。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/376115/a9603df5-61b5-087a-96b5-927517a0285f.png)

## まとめフェーズ
もう特に話すことがないのですが、クエリで「まとめ」がきたらまとめフェーズにうつります。
この時に、まとめるLLMはメモリを有効にしておきましょう！
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/376115/3a8391aa-64c2-a4a7-30ac-51b478a1242b.png)

## 補足
最後にこれだとなかなか初見で使うの難しいのでチームで使う想定であれば、会話開始機能は有効にしてどう使うべきかを書いておいてあげましょう！
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/376115/957eacc9-fa6b-c115-b368-ee49b8615a0f.png)

## 最後に
これだとチューニングもまだまだなので、みなさんチューニングしたり、キーワードごとの検索もできるようにしたりとカスタマイズしてみてください！
Xやってるので気になる方はフォローお願いします。
https://x.com/hudebakonosoto
[AWS #12] KMS

## はじめに
こんにちは、今回もセキュリティ分野の記事です。
その中でも 今回は **「KMS」** についてご紹介いたします。
スマートに、コンパクトに作成いたしました。
## KMS
KMSとは **「Key Management Service」** の略称であり、<font color=red>**暗号化操作に使用されるキーを簡単に作成および管理できるマネージドサービスです。**</font>
![AWS12_01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3806875/0588614a-53d9-b553-8772-d86fb61cb366.png)

---
KMSは、キーの **「一元管理」** が可能です。
**AWS CloudTrail**とも統合されており、暗号化キーの**使用履歴（ログ）** を確認することができます。
![AWS12_02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3806875/d01934e1-7186-2e65-83aa-dac2c2c00862.png)

## AWS KMSの利用料金
AWS KMSの利用料金は **「カスタマー管理のキー（CMK）」** の**使用量や暗号化リクエストの回数**によって**変動**します。KMSでCMKなどを保管している期間は、月に1USD（1時間ごとに割り引かれる）の料金がかかります。

[AWS Key Management Service の料金はこちら](https://aws.amazon.com/jp/kms/pricing/)

:::note info
**キー作成やキーを保管するストレージ**に対する**料金はかかりません**
:::

## おわりに
ちょっとしたまとめになります。

:::note info
**KMS**は、AWS上で暗号化キーを**作成、管理するもの**である
:::

:::note info
作成した**暗号化キー**は**AWS上のサービスやアプリケーションなどに使用可能である**
:::
AWS KMSはキーに必要な**アクセスコントロールの特定のレベルを選択する**ことができます。
そして**一時的にキーを無効にして誰にも使えないようにする**ことができます。

暗号化されたキーは AWS KMS の**外部に出ることはなく**、**常に制御できる**ということが理解できました。
最後までお読みいただきありがとうございました！

>日頃より活用している参考書です。
>> **「参考書」**
[AWS認定クラウドプラクティショナー改定第3版](https://x.gd/19i6N)
>
> **「AWS公式サイト」**
[AWS KMS](https://aws.amazon.com/jp/kms/)
>
> **「AWS公式サイト」**
[AWS Cloud Trail](https://aws.amazon.com/jp/cloudtrail/)
>
> **「参考元」**
[AWS KMSとは？](https://business.ntt-east.co.jp/content/cloudsolution/column-186.html)
>
> **「参考元」**
[AWS CloudTrail基礎](https://www.sbbit.jp/article/cont1/81207)
>
> **「Youtube」**
[【CLF-C02：AWSクラウドプラクティショナー】第16回 AWS KMS・AWS Artifact (セキュリティとコンプライアンス分野)](https://x.gd/WN4wT)
【CSS】初学者がやりがちなCSSのミス10選！

## 1. 不要な!importantの使用
### 問題点
CSSの特定のルールに!importantを使うことは、後でのメンテナンスを難しく、予期しない副作用を引き起こす可能性があるので基本的には使わないように。

```css
.button {
    color: red !important;
}
```
### 修正方法
より特定性の高いセレクタを使うか、他のCSSルールを再検討しましょう。

```css
.button.primary {
    color: red;
}
```

## 2. タグに全般的なスタイル
### 問題点
タグに対してスタイルを指定してしまうと、パフォーマンスに悪影響を及ぼす可能性があります。

```css
p {
    margin: 20px;
}
```
### 修正方法
必要最小限の要素にのみスタイルを適用するようにします。

```css
.content p.lasttext {
    margin: 20px;
}
```

## 3. セレクタの過剰なネスト
### 問題点
過剰なネストはCSSの読みやすさを損ない、思わぬところで悪影響を与える可能性があります。

```css
html body main header.header nav.nav ul li a {
    color: #333;
}
```

### 修正方法
より単純で特定性の高いセレクタを使用します。

```css
.nav-link {
    color: #333;
}
```

## 4. ショートハンドにより不必要な値の設定
### 問題点
CSSで値を指定する際に、ショートハンドを使い不用意に値を設定したために、無駄な打ち消しが発生する場合があります。

```css
.container {
    width: 100%;
    margin: 20px;
}
.container {
    margin-left: 0px;
    margin-right: 0px;
}
```

### 修正方法
必要な箇所にのみ値をいれる。

```css
.container {
    width: 100%;
    margin: 20px auto;
}
```

## 5. ベンダープレフィックスの入れ忘れ
### 問題点
ブラウザによっては一部のCSSプロパティでベンダープレフィックスが必要な場合があります。

```css
.div {
    display: flex;
    align-items: center;
    justify-content: center;
}
```

### 修正方法
オートプレフィックスツールを使用して、必要なプレフィックスを自動的に追加できるようにしましょう。

```css
.div {
    display: -webkit-flex;
    display: flex;
    -webkit-align-items: center;
    align-items: center;
    -webkit-justify-content: center;
    justify-content: center;
}
```


## 6. 適切でないセレクタの使用
### 問題点
より特定的なセレクタを使用せず、汎用的なセレクタを使うことで、意図しないスタイルの影響を与えることがあります。

```css
#content > div {
    margin-bottom: 20px;
}
```
### 修正方法
より具体的で特定性の高いセレクタを使用して、意図した要素にのみスタイルを適用します。


```css
.article-content > .paragraph {
    margin-bottom: 20px;
}
```

## 7. ハードコーディングされた数値
### 問題点
固定数値を直接CSSに記述することで、レスポンシブデザインやスケーラビリティに対応できない場合があります。


```css
.header {
    color: #333;
}
```
## 修正方法
変数や計算式を使用して、柔軟性のあるスタイルを実現します。
CSS変数やSASS,SCSSの変数を使う

css
```
:root {
    --color-base: 80px;
}

.header {
    color: var(--color-base);
}

```
## 8. フォントの管理不足
### 問題点
フォントの指定が不足していると、ブラウザがデフォルトのフォントを適用する可能性があり、デザインの一貫性が失われることがあります。

```css
body {
    font-family: Arial, sans-serif;
}
```
### 修正方法
フォントスタイルを詳細に指定し、フォールバックオプションも考慮します。
```css

body {
    font-family: 'Helvetica Neue', Arial, sans-serif;
    font-weight: 400;
    font-size: 16px;
}

h1 {
    font-size: 24px;
    font-weight: 600;
}
```
## 9. インラインスタイルの乱用
### 問題点
HTML内で直接スタイルを定義することで、メンテナンス性が低下し、制御するのが難しくなります。

```html
<div style="width: 50%; float: left;">
    <!-- content -->
</div>
```
### 修正方法
CSSファイルにスタイルを移動し、クラスやIDを使って適切にスタイルを管理します。

```html
<div class="half-width">
    <!-- content -->
</div>

<style>
.half-width {
    width: 50%;
    float: left;
}
</style>
```

## 10. 不必要なコメントの残留
### 問題点
開発中に挿入したコメントが、残ってることがあり、不要なコメントがあると、何か重大な意味があるのではと考えてしまいます。

```css
/* 例のサイトからの引っ張ってきたもの */
.header {
    background-color: #fff;
}
```
### 修正方法
不要なコメントを削除し、必要な場合には適切にコメントを管理します。

```css
.header {
    background-color: #fff; 
}
```

## 最後に
これらのポイントを考慮することで、メンテナンスのし易いCSSを実装することができるはずです。
CSSの基礎と実践的な使用方法

こんにちは。この記事では、CSSの基本概念から実践的なコーディングまで、丁寧に解説していきます。HTMLの基礎が少し分かる方を対象にしていますが、HTMLも全く分からない方は、HTMLの基礎を学んでから、この記事に戻ってくると良いでしょう。

### 目次
1. CSSとは
2. 開発環境の準備
3. CSSの基本構造
4. よく使われるCSSプロパティ
5. セレクタと詳細度
6. ボックスモデルと表示の制御
7. メディアクエリ
8. 実践例

### 1. CSSとは
CSSは、ウェブページの見た目をスタイリングするための言語です。HTMLがウェブページの構造を定義するのに対し、CSSはその構造をどのように見せるかを指定します。CSSを使うことで、テキストの色やサイズ、背景色、レイアウトなどを自由にカスタマイズできます。

### 2. 開発環境の準備
CSSを書くための開発環境として、テキストエディタが必要です。ここではVisual Studio Code（VS Code）を使用します。VS Codeをインストールし、HTMLファイルとCSSファイルを作成しましょう。

### 3. CSSの基本構造
CSSは以下のような基本構造を持っています：

```css
セレクタ {
  プロパティ: 値;
}
```

例えば、段落タグ（`<p>`）のテキスト色を赤にするには以下のように書きます：

```css
p {
  color: red;
}
```

### 4. よく使われるCSSプロパティ
CSSには多くのプロパティがありますが、よく使われるものをいくつか紹介します：

- `color`: テキストの色を指定します。
- `background-color`: 背景色を指定します。
- `font-size`: フォントサイズを指定します。
- `margin`: 要素の外側の余白を指定します。
- `padding`: 要素の内側の余白を指定します。

### 5. セレクタと詳細度
CSSセレクタは、どのHTML要素にスタイルを適用するかを指定します。代表的なセレクタには以下があります：

- 要素セレクタ：`p`、`h1`、`div`など
- クラスセレクタ：`.className`
- IDセレクタ：`#idName`
- 擬似クラス：`:hover`、`:active`など

詳細度（Specificity）は、複数のスタイルが競合した場合にどのスタイルが適用されるかを決定します。詳細度は以下のように計算されます：

- インラインスタイル：1000
- IDセレクタ：100
- クラスセレクタ：10
- 要素セレクタ：1

### 6. ボックスモデルと表示の制御
ボックスモデルは、HTML要素がどのようにスペースを占有するかを示す概念です。ボックスモデルは以下のように構成されています：

- マージン（margin）
- ボーダー（border）
- パディング（padding）
- コンテンツ（content）

ブロック要素とインライン要素の違いも理解しておきましょう。ブロック要素は、常に新しい行から始まり、幅いっぱいに広がります。一方、インライン要素は、行内に並びます。

### 7. メディアクエリ
メディアクエリを使うと、デバイスの種類や画面サイズに応じてスタイルを変えることができます。以下は、画面幅が768ピクセル以下の場合に適用されるスタイルの例です：

```css
@media (max-width: 768px) {
  body {
    background-color: lightblue;
  }
}
```

### 8. 実践例
最後に、実際のコーディング例を通してCSSの使い方を確認しましょう。例えば、以下のHTMLとCSSを使って、簡単なウェブページを作成します。

```html
<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>CSSの例</title>
    <link rel="stylesheet" href="styles.css">
</head>
<body>
    <header>
        <h1>CSSの例ページ</h1>
    </header>
    <main>
        <p>これは段落です。</p>
        <p class="highlight">これはハイライトされた段落です。</p>
    </main>
</body>
</html>
```

```css
/* styles.css */
body {
  font-family: Arial, sans-serif;
  line-height: 1.6;
}

h1 {
  color: navy;
}

p {
  color: darkslategray;
}

.highlight {
  background-color: yellow;
  font-weight: bold;
}
```

このコードを使って、自分のウェブページを作成し、CSSの効果を確認してみてください。
この記事では、CSSの基本から実践までをカバーしました。これらの知識を使って、ウェブページのデザインをカスタマイズし、より魅力的なウェブサイトを作成できるようになりましょう。
iOSアプリやSDKのドキュメントをコマンド一発でいい感じに作る

# はじめに

Xcodeを使ってアプリやSDKを作る仕事をしていると「インターフェースのドキュメント作って。明日までね」なんて言われることがあります（怒）
そんなときのために、コマンド1個でいい感じのドキュメントを生成する方法をここに残しておきます。

# 必要なもの
- Xcode
- 対象プロジェクト
- jazzy（後述）

# 手順
## 1. jazzyのインストール

ターミナルを開いて以下を実行します。
```
> sudo gem install jazzy
```

`
Successfully installed jazzy-0.15.1
`
となれば成功です。

jazzyはSwiftとObjective-C用のソウルフルなドキュメント生成ツールらしいです。

https://github.com/realm/jazzy

## 2. 設定ファイルを作成
プロジェクト直下に.jazzy.yamlという名前で作成し、以下をコピペします。
（設定値は自分のプロジェクトに合わせて適宜変更してください）

```YAML:.jazzy.yaml
# public以上がドキュメント化される。より低いアクセスレベルも指定できる。
# [private | fileprivate | internal | public | open]
min_acl: public

#実行前に出力先フォルダをクリーン
clean: true

# ドキュメント出力先フォルダ
output: document

# 著者
author: 著者

# コピーライト
copyright: '&copy; 2024 <a class="link" href="" target="_blank" rel="external noopener">コピーライト</a>. All rights reserved.'

# xcodebuildの引数
xcodebuild_arguments: [archive,-scheme,【プロジェクトのScheme】,-configuration,Debug,-destination=iOS,-arch,arm64,-sdk,iphoneos,SKIP_INSTALL=NO,BUILD_LIBRARY_FOR_DISTRIBUTION=YES]
```

## 3. ドキュメント生成
ターミナルで以下のコマンドを実行します。
```
> jazzy
```
outputに指定したフォルダへドキュメントが生成されます。
手順としてはこれで終了です。簡単ですね。

# 成果物

## サンプルプロジェクト
どんなものができるのか、例として以下のようなプロジェクトを作って試してみます。

![スクリーンショット 2024-06-21 16.19.07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2961919/b9d3cea3-f064-b03d-936b-2667fee0ff75.png)

```swift:ViewController.swift
import UIKit

public class ViewController: UIViewController {
    /// **viewDidLoad**
    public override func viewDidLoad() {
        super.viewDidLoad()
        // Do any additional setup after loading the view.
    }

    /// **XX処理**
    ///
    /// XXの処理を行います。
    public func test1()  {
    }
    
    /// **XX判定**
    ///
    /// XXの判定を行います。
    ///
    /// - note:
    ///     - 〇〇だった場合、true
    ///     - △だった場合、false
    /// - Parameters:
    ///   - val: 引数
    /// - Since: 1.0.0
    /// - SeeAlso: SDK初期化要求 ``test1()``
    /// - SeeAlso: 合否結果``Constants.Result``
    ///
    public func test2(val: Int) -> Bool {
        return true
    }
}

public class Constants {
    public enum Result {
        /// 正常終了
        case success
        /// 異常終了
        case failure
    }
}
```

## できたもの
![スクリーンショット 2024-06-21 16.27.30.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2961919/5bcb34bd-1428-6c7b-81ae-0bf772a256fb.png)

![スクリーンショット 2024-06-21 16.29.21.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2961919/ae846c26-3c44-64dd-b45f-4bfef2265a3c.png)

いい感じのドキュメントが出来上がりましたね。
READMEをプロジェクトに設置しておけば、ドキュメントにも反映してくれます。

![スクリーンショット 2024-06-21 16.31.57.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2961919/70fb1635-ecbe-e62e-dbbe-f5ed19cc385c.png)

# さいごに
楽ちんですね。
.jazzy.yamlをgit等でチームメンバーと共有すれば、誰でも作る事ができます。
READMEに更新履歴を残しておくような運用にすれば社外に出しても恥ずかしくないドキュメントになるのではないでしょうか。
コードのエラー文を自動でChatGPTに読み込ませる

# 1. 何でそんなことするの？
エラーの原因がよくわからない時、エラー文をコピペしてChatGPTに投げるということを頻繁にやっているのですが、コピペがめんどくさい。

# 2. この記事でやること
Google Colaboratoryで実行したコードの「エラー文をChatGPTに投げる＋その結果をColab上で出力する」を全自動で行います。

# 3. 方法
### 3.1 必要なライブラリをインストール
```
!pip install openai
import openai
import os

# APIキーを設定します
openai.api_key = 'YOUR_API_KEY'
```
・「YOUR_API_KEY」：実際の自分のAPI Key
OpenAI API Keyの取得方法はコチラ（簡単!）↓

https://qiita.com/iamtaro/items/09306b81d6e479dce2d9


### 3.2 エラー文をChatGPTに送信するための関数(send_error_to_chatgpt)を定義
```
def send_error_to_chatgpt(error_message):
    response = openai.ChatCompletion.create(
      model="使用するモデル", 
      messages=[
        {"role": "system", "content": "You are a helpful assistant."},
        {"role": "user", "content": f"以下のエラーメッセージの原因と解決策を教えてください：\n\n{error_message}"}
      ],
      max_tokens=2048
    )
    return response.choices[0].message['content'].strip()
```
・「使用するモデル」：gpt-4o、gpt-3.5-turboなどの実際のモデル名
・「max_tokens」:出力する解答文のトークン数

### 3.3 任意のコードを実行
```
cell_code = """

コード

"""

execute_and_handle_error(cell_code)
```
・「コード」：実際のコード
#### 3.3.1 実行例
ChatGPT-3.5 Turboを使って上記コードを実行したらこんな感じです（めっちゃ便利！）↓
![スクリーンショット 2024-06-21 15.50.47.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3820324/ad8b6a79-d989-3488-a1d9-65bd37fe2473.png)

# 4. おわりに
これで「cmd/ctrl + c/v」の回数が格段に減り、作業効率が上がりました。まだやったことない方はぜひお試しください。
他にもAPIを使ったtipsあればなんでも教えてください。
ChatGPTのAPI Keyを取得する

# 1. はじめに
n番煎じのOpenAI API Keyの取得方法をなるべく簡潔にメモ書きしておきます。

# 2. 方法
### 2.1 OpenAI PlatformのAPI Keysにアクセス。
https://platform.openai.com/api-keys

### 2.2 右上の「+ Create new secret key」をクリック
![スクリーンショット 2024-06-21 16.02.31.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3820324/b71107c2-1936-d8d7-fef1-e0c7871a0b0d.png)

### 2.3 「Create secret key」をクリック
特にこだわりがなければ下記画面で設定をいじる必要はないです。
![スクリーンショット 2024-06-21 16.04.40.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3820324/e7953aa7-2cbf-68ad-174b-5bb879f77c87.png)

下画面が出てくれば成功です。

![スクリーンショット 2024-06-21 16.09.03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3820324/fdbcab87-3eb6-3d01-d646-5fb40e9f2d85.png)

最初の画面（API keys）に戻ると、作成したAPIがリストに追加されていることが確認できます。
![スクリーンショット 2024-06-21 16.14.34.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3820324/a1c460a3-83b8-6b83-22dd-fa4295479038.png)

# 3. おわりに
他にも関連するtipsあれば教えてください！
XAMPP5.6.40でXdebugをインストールしVSCodeでデバッグしてみた

今回は久々にPHPの開発を行った。
PHP5で開発する必要があったため、少々手こずりました。
なのでメモメモ

## Xdebugのインストール
基本phpinfoで表示された画面をコピーして
https://xdebug.org/wizard
のサイトに貼り付けると有効なXdebugのバージョンを教えてくれるのですが、
今回はPHP5.6が古すぎるとのことでサポートしませんとのメッセージが表示されてしまいます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/b70af6da-219e-321b-5afd-b2e4e3752b63.png)

調べるとXdebug2.5.5が対応しているみたいです。
PHP5.5VC11TS(64bit)をダウンロード
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/e82960ae-5d97-63d9-fb2b-ace05c04230b.png)

C:\xampp\php\ext
のフォルダーにコピーします。

## php.iniの編集
XAMPPのコントロールパネルからPHP.iniを編集
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/3667270b-110a-b0b1-8e47-4b95d16ec01d.png)

PHP.iniの最後の以下の文を追加
```
[XDebug]
zend_extension = "C:\xampp\php\ext\php_xdebug.dll"
xdebug.remote_enable=1
xdebug.remote_host=localhost
xdebug.remote_handler=dbgp
xdebug.remote_mode=req
xdebug.remote_autostart=true
```
正常にインストールされたらphpinfoでxdebugが表示されているか確認してください。
![スクリーンショット 2024-06-21 155005.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/fff17911-54bd-70d5-8102-7a7aecbdb267.png)

## VSCodeにPHP Debugをインストール

拡張機能を選択し、検索で「PHP debug」を入力。
PHP Debug(Xdebug)をインストール
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/5609a58d-6808-7109-bc73-34b92c87d4b1.png)

## PHP Debugの設定
VSCodeを開いてエクスプローラから「フォルダーを開く」をクリックし、
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/74ad41a6-139e-0205-5a89-a650bf531d82.png)


Apacheのルートフォルダの「htdocs」をフォルダーの選択にする
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/20100315-60ef-a453-8cca-8aca53a002fb.png)

「作成者を信頼します」をクリック
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/527c3c62-2b0e-7bc9-fc05-5ca3c34fc4fb.png)

実行とデバッグを選択し、「launch.jsonファイルを作成します。」をクリック。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/3a34d7a2-757f-f1cb-66fe-339b9191c6b8.png)

PHPを選択後、port番号を9003から9000に変更
↓変更前
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/c29c5272-1eda-3c70-983b-16c7a2603bf5.png)
↓変更後
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/d94e60b7-eaea-d16a-3b25-9fe13320a2ad.png)



あとはデバッグ開始ボタンを押します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/6298dd86-b393-8663-daaa-c59cd9d7d4d0.png)

そしてブレイクしたいところにマークを入れれば完了です。
自分の一時停止したいところで止まってくれます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1339052/144e8718-2cf9-fba3-fafc-3cb4105ff894.png)
語呂合わせで覚える基本情報技術者試験①

# はじめての基本情報技術者試験

## 1\. 前提条件
### 今回使用するテキスト
- [かやのき先生の基本情報技術者教室 令和6年版](https://www.kayalab.jp/fe-lec.html)

### このページで紹介するもの
- 語呂合わせ

## 2\. 目次
 第1章 コンピュータ構成要素　←今ここ
 第2章 ソフトウェアとマルチメディア
 第3章 基礎理論
 第4章 アルゴリズムとプログラミング
 第5章 システム構成要素
 第6章 データベース技術
 第7章 ネットワーク技術
 第8章 情報セキュリティ
 第9章 システム開発技術
 第10章 マネジメント系
 第11章 ストラテジ系
 第12章 科目B対策

## 3\. 第一章 コンピュータ構成要素
### 1-01 情報の表現
なんとなく、大きな数値を表す接頭語(キロ、メガ、ギガ、テラ）は分かります。
でも、小さな数値を表す接頭語はあまり親しみがないのでは？

m（ミリ）, 10の-3乗
μ（マイクロ）, 10の-6乗
n（ナノ）, 10の-9乗
p（ピコ）, 10の-12乗

### ゴロ合わせ 「見舞いなの、ピコ太郎？」
解説：見(m)舞い(μ)なの(n)、ピコ(p)太郎？

ちなみに、AIで画像を生成してもらうとこうなります。
![_c2e2db6b-e263-4faf-9275-16ea99d21eea.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3781397/8ffb43f5-50b2-38b7-92a7-71488937d3ac.jpeg)
もうペンとリンゴの時代ではないそうです。

### 1-04 CPUの動作原理
コンピュータは、主記憶（メインメモリ）上のプログラムを一つずつ解読・実行します。
プログラムは命令が集まったものです。
命令は機械語（命令語）に翻訳され、解読・実行されます。
命令語は「命令部」と「アドレス部（オペラント部）」で構成されます。
例えばJavaなら、命令部は代入や＋、－などの演算、オペラント部はa, b, 5などの値と理解できそう。

命令のアドレス部の値から、処理対象のデータが格納されている実行アドレス（有効アドレス）を求める方式のことを、アドレス指定方式と呼びます。（別名：アドレス修飾）
※アドレス部に直にデータがあるとは限らず、欲しいデータに行きつくまでにいくつか方法があるということです。

アドレスの指定方式は以下のようなものがあります。（詳しくはお手持ちの教科書を参照、またはググりましょう）
- 即値アドレス指定方式
- 直接アドレス指定方式
- 間接アドレス指定方式
- 相対アドレス指定方式
- 指標アドレス指定方式
- 基底アドレス指定方式

### ゴロ合わせ「そっち直感、葬式て！」
解説：そっち（即値）直（直接）感（間接）、葬（相対）式て（指標、基底）！

ちなみに、AIで画像を生成してもらうとこうなります。
![_d7382b10-88d2-4f66-b1f7-8d8c7eec088f.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3781397/abbc6b7a-e4f0-b0e4-008a-e90eddacbfc1.jpeg)
葬式の概念が覆されます。

## 4.おわりに
自身の資格試験のアウトプット用として、教科書を写すだけではなく、誰かの役に立つようなひと工夫を、と考え至ったコーナーです。

誰かのお役に立ちますように。
python非同期並列処理の並列数を指定

# はじめに
スクレイピングやAPIの実行などの非同期処理を並列に実行したいが、並列数を指定したい

# 実装
 - asyncioの[gather](https://docs.python.org/ja/3/library/asyncio-task.html#asyncio.gather)を用いて非同期処理を並列に実行
 - asyncioの[Semaphore](https://docs.python.org/ja/3/library/asyncio-sync.html#semaphore)を用いて非同期処理を並列数を指定

```python
from asyncio import Semaphore, gather, sleep
from collections.abc import Awaitable

async def parallel(tasks: list[Awaitable], concurrency: int) -> list:
    """複数の非同期タスクを並列実行数の上限を設けつつ並列実行する"""
    assert concurrency > 0

    sem = Semaphore(concurrency)

    async def exec(task):
        async with sem:
            return await task

    return await gather(*[exec(task) for task in tasks])
```

# コード例
非同期関数であるtest関数を3個並列で処理させる
```python
async def test(i: str) -> int:
    print(f"start: {i}")
    # 非同期処理
    await sleep(2)
    print(f"end  : {i}")
    return i

async def process():
    tasks = [test(i) for i in range(10)]
    result = await parallel(tasks, concurrency=3)

await process()
```
出力
```
start: 0
start: 1
start: 2
end  : 0
end  : 1
end  : 2
start: 3
start: 4
start: 5
end  : 3
end  : 4
end  : 5
start: 6
start: 7
start: 8
end  : 6
end  : 7
end  : 8
start: 9
end  : 9
```
ChatGPT-3.5先生へ「そうめんとひやむぎの違いを教えて下さい。」(抜粋) 調理法の追加

# 20240624 追加
・???調理法
User
```
価格の安いそうめんを、価格の高いそうめんの味にするにはどうしたらいいですか
```
(抜粋)
1. 麺の茹で方を工夫する
...
2. 良い出汁を使う
...
3. トッピングを工夫する
...
4. 麺の温度を調整する
...
これらのポイントを実践することで、安価なそうめんでも高級な味に近づけることができます。ぜひお試しください。



# 当初

・ランキングは実行毎に、変わります。

# ChatGPT-3.5先生へ(1回目)
User
```
そうめんとひやむぎの違いを教えて下さい。
そうめんのおすすめの品名を教えて下さい。
そうめんのおすすめの品名をランキング順に教えて下さい。
そうめんのおすすめの品名をランキング順に教えて下さい。日本語で。
```

# ChatGPT-3.5先生へ(2回目)
User
```
そうめんの商品名をおすすめランキング順に教えて下さい。
メーカー名とJANコードを、markdown表形式のソースコードを教えて下さい。
```

| ランキング | 商品名          | メーカー       | JANコード        |
|:----------:|:---------------:|:--------------:|:----------------:|
| 1          | 揖保乃糸 特級品 | 兵庫県手延素麺協同組合 | 4970181131122   |
| 2          | 小豆島 手延べそうめん | 小豆島産業振興協議会 | 4902508300282   |
| 3          | 三輪そうめん 上級品 | 三輪素麺組合 | 4902112600017   |
| 4          | 半田手延べそうめん | 半田そうめん株式会社 | 4960772000118   |
| 5          | 島原手延べそうめん | 島原そうめん株式会社 | 4901673010011   |

いつの時点ですか

このランキングは**一般的な評価** に基づいたもので、特定の時点に基づくものではありません。...



# ChatGPT-3.5先生へ(3回目)
User
```
そうめんの商品名をおすすめランキング順に教えて下さい。
メーカー名とJANコードを、markdown表形式のソースコードを教えて下さい。
商品名とメーカー名とJANコードの文字は左寄せでお願いします。
```
???ランキングが順位になりました。
???順位も左寄せになりました。
| 順位 | 商品名                  | メーカー名       | JANコード      |
|:--- |:---------------------|:---------------|:-------------|
| 1   | 揖保乃糸 手延べそうめん | 兵庫県手延素麺協同組合 | 4970180611000 |
| 2   | 半田手延べそうめん       | 半田製麺         | 4904563000011 |
| 3   | 三輪素麺 手延べそうめん   | 三輪そうめん山本 | 4902766000417 |
| 4   | 小豆島手延べそうめん     | 小豆島オリーブ  | 4970192000034 |
| 5   | 島原手延べそうめん       | 島原手延素麺協同組合 | 4906011500114 |

# google先生へ
(同じ)

# 参考

https://qiita.com/mrrclb48z/items/910310f79c3ecd83dadd
GraphQLとは

## 概要
- Facebookが開発したQuery言語の仕様
- REST APIの問題点を解決することを目指して開発された

----
## REST APIの問題点（1/2）
- エンドポイント爆発：大量のエンドポイントに飲み込まれる！
- 検索条件の表現：URLのクエリストリングでは限界がある
- 不要なカラムまで取得してしまう
  この問題を解消しようとしてエンドポイントが更に大量に・・・

----
## REST APIの問題点（2/2）
- 複数リソースをまとめて取得するエンドポイントを素直に表現できない
- 通信回数の問題：画面の初期表示に必要なデータの種類は多くなりがち

総じて、クライアントは大規模かつ複雑に変化していくが、それに追従するのがREST APIだと辛い！

----
## GraphQLの考え方
- Query Languageの、名前の通り、検索するための仕様
- 取得するリソース（**複数可**）／取得条件／取得するプロパティ
- 更新／削除も可能

----
## SQLでいいんじゃない？
- GraphQLにJOINはできない（たぶん）
- SQLは結果の形式は表形式、かつ１種類という制約がある
- SQLは階層化されたデータを扱うのが苦手

----
## GraphQLの弱点
- 利便性とセキュリティは表裏一体
  基本的にはリソースに対して許可する操作をユーザグループに対して指定
- 自由度と分かりやすさは表裏一体

----
## Graphゆえの仕様
- 階層化されたデータをどこまで掘るか
  ある程度で留めておかないとデータ量がとてつもなく増えることになる

----
## サーバ側をどう実装するか
- Azure API Management：既存のエンドポイントにGraphQLインターフェイスを追加することが出来るそうです
  誰かやってみてください！
- AWS Amplify：デフォルトのAPIがGraphQL！

----
## 有名なGraphQL
- [GitHub GraphQL API](https://docs.github.com/ja/graphql)
- [GraphQL Pokémon](https://kakakakakku.hatenablog.com/entry/2019/12/30/135420)
複数画像の平均を求める

 画像内の物体を検出する際に動くもの(人，車など)を削除(薄くする)することができる．

画像を追加する予定です．


```python
# 画像を読み込み配列に入れる
def read_images(filenames):
  images = []
  for filename in filenames:
    img = cv2.imread(filename)
    images.append(img)
  return images

# 画像の平均を求める
def average_images(images):
  num_images = len(images)
  if num_images == 0:
    return None
  total_image = np.zeros(images[0].shape, dtype=np.float32)
  for img in images:
    total_image += img.astype(np.float32)
  average_image = total_image / num_images
  return average_image.astype(np.uint8)

if __name__ == "__main__":
  # 画像ファイルのパス
  filenames = [img1, img2, img3]  
  
  images = read_images(filenames)
  average_image = average_images(images)
  cv2.imshow(average_image)
```
Docker リフレッシュ


```shell:リフレッシュ
docker container stop $(docker container ls -aq)
docker container rm -f $(docker container ls -aq)
docker network rm $(docker network ls -q)
docker volume rm -f $(docker volume ls -q)
docker image rm -f $(docker image ls -aq)
docker compose down --volumes --remove-orphans --rmi all
docker image prune --all -f
docker container prune -f
docker system prune --volumes -f
docker network prune -f
docker volume prune -f
docker builder prune --all -f
```

殺意高め