OmniAICreator/Qiita-1.07M huggingface dataset:
[TypeScript] ビットコインのウォレットを作成する


```typescript: ウォレットの作成
import { Address, Bn, KeyPair, PrivKey, TxBuilder, TxOut, deps } from '@ts-bitcoin/core'

// make change address
const privKey1 = PrivKey.fromRandom()
const keyPair1 = KeyPair.fromPrivKey(privKey1)
const addr1 = Address.fromPubKey(keyPair1.pubKey)

// make address to send from
const privKey2 = PrivKey.fromBn(new Bn(1))
const keyPair2 = KeyPair.fromPrivKey(privKey2)
const addr2 = Address.fromPubKey(keyPair2.pubKey)

const txOut = TxOut.fromProperties(new Bn(2e8), addr2.toTxOutScript())
const txHashBuf = deps.Buffer.alloc(32).fill(0)

// make address to send to
const privKey3 = PrivKey.fromBn(new Bn(2))
const keyPair3 = KeyPair.fromPrivKey(privKey3)
const addr3 = Address.fromPubKey(keyPair3.pubKey)

const tx = new TxBuilder()
    .setFeePerKbNum(0.0001e8)
    .setChangeAddress(addr1)
    .inputFromPubKeyHash(txHashBuf, 0, txOut, keyPair2.pubKey)
    .outputToAddress(new Bn(1e8), addr3)
    .build()

const raw = tx.toHex()

console.log("accoun1: ", addr1)
console.log("accoun2: ", addr2)
console.log("accoun3: ", addr3)
console.log(raw)

```
IOptionsSnapshotを生み出す

コンストラクタの引数に`IOptionsSnapshot<TOptions>`を保有するクラスがあるとします。

```csharp: MyApp.cs
public class MyApp
{
    private readonly IOptionsSnapshot<MySettings> mySettings;

    public MyApp(IOptionsSnapshot<MySettings> settings)
    {
        this.mySettings = settings;
    }

    public void DoSomething()
    {
        Console.WriteLine(this.mySettings.Value.Name);
    }
}
```

このクラスのテストコードを記述するとなった場合、MyAppクラスに渡すために何らかの方法でテスト用の`IOptionsSnapshot<TOptions>`を生み出す必要があります。
以下の例ではモック用のライブラリであるMoqを使って`IOptionsSnapshot<TOptions>`を生成しています。

```csharp: IOptionsSnapshot<TOptions>のモック生成例
var myOptionsMock = new Mock<IOptionsSnapshot<MySettings>>();
myOptionsMock
    .Setup(o => o.Value)
    .Returns(new MySettings
    {
        Name = "test",
    });
var app = new MyApp(myOptionsMock.Object);
```

この方法では、`IOptionsSnapshot<TOptions>`を生み出すためにモックを定義する必要があります。
今回はモックを定義したくなかったので`IOptionsSnapshot<TOptions>`を自力生成する方法を試そうと思います。
そのために、以下の2つのクラスを予め作成します。

```csharp: OptionsSnapshot.cs
public static class OptionsSnapshot
{
    public static IOptionsSnapshot<TOptions> Create<TOptions>(TOptions options) where TOptions : class, new()
    {
        return new OptionsSnapshotWrapper<TOptions>(options);
    }
}
```

```csharp: OptionsSnapshotWrapper.cs
public class OptionsSnapshotWrapper<TOptions> : IOptionsSnapshot<TOptions> where TOptions : class, new()
{
    public TOptions Value { get; }

    public OptionsSnapshotWrapper(TOptions options)
    {
        Value = options;
    }

    public TOptions Get(string name)
    {
        // 一旦これで
        throw new NotImplementedException();
    }
}
```

これらのクラスを用いて、`IOptionsSnapshot<TOptions>`を生成するコードは以下のように書けます。

```csharp
var myOptions = OptionsSnapshot.Create(new MySettings
{
    Name = "test"
});
var app = new MyApp(myOptions);
```

### まとめ

`IOptionsSnapshot<TOptions>`を生み出せた。
Widget更新時にImageが更新されない場合の対処

下記の様に実装していた。setStateでWidgetの更新自体は発火していたが、画像が差し替えされなかった

```dart
child: Image.file(
  imagePath,
),
```

Image.fileの代わりにImage.memoryを使えばいいらしい

```dart
child: Image.memory(
  File(imagePath).readAsBytesSync(),
)
```

参考元
Flutter Image Widget won't update on change state
https://stackoverflow.com/questions/58794144/flutter-image-widget-wont-update-on-change-state

Image.file()の説明にも下記の様に書いてあるので、この辺りが起因している？
> Loading an image from a file creates an in memory copy of the file, which is retained in the ImageCache.
> ファイルから画像をロードすると、ファイルのメモリ内コピーが作成され、ImageCache に保持されます。
【AWS】S3ファイルのストレージクラスを表形式で出力してみた

# 1．前書き
S3の特定バケット内にあるファイルのストレージクラスをCLIから確認したくなり、やり方を調べてみた。
[s3apiコマンド](https://docs.aws.amazon.com/ja_jp/cli/latest/userguide/cli-services-s3-apicommands.html)を使用すれば、json形式でS3に保存されているファイル情報を確認することができる。
そして出力されるパラメータのうち、「StorageClass」を確認すればいいことが分かった。


```<出力イメージ>.json
{
    "Contents": [
        {
            "Key": "hoge.txt",
            "LastModified": "2023-09-01T02:22:22+00:00",
            "ETag": "\"999999999999\"",
            "Size": 99,
            "StorageClass": "STANDARD",
            "Owner": {
                "DisplayName": "hogehoge",
                "ID": "999999999999999999"
            }
        }
    ]
}
```

ここで正直な心の声が聞こえた。
`「ファイル数が増えるとパッと確認しづらい！」`
`「json形式じゃなくて表形式で確認したいんじゃ...」`

そんな心の声にしたがい、スクリプトを書いてみた。

本記事はその備忘録である。


# 2．処理の概要
* s3apiの結果をjsonファイルに出力する。
* 出力したjsonファイルを[ConvertFrom-Json](https://learn.microsoft.com/ja-jp/powershell/module/microsoft.powershell.utility/convertfrom-json?view=powershell-7.3) コマンドレットをベースに整え、表形式で出力する。

# 3．作成したスクリプト
```exp_S3api_01.ps1
# 変数設定
$bucket_name = "<特定のバケット名>"
$path = "C:\Work\Test"
$json_file = $path + "\s3api_list.json" #s3apiコマンドの出力ファイル

# s3apiコマンドで特定バケット内のファイル情報を出力（json形式）
aws s3api list-objects --bucket $bucket_name | Out-File $json_file

# jsonファイルを読み込んで表形式で出力
(Get-Content $json_file | ConvertFrom-Json).Contents | 
Select-Object Key,StorageClass,Size,LastModified
```

# 4．できあがるもの
問題なくどのファイルが、どのストレージクラスで保存されているのか、
表形式で出力することができた。
（ファイル数が増えるなら、やはり表形式の方が見やすいでしょう...）

<img width="600" alt="shot-001.JPG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2015081/2b2988fb-d06c-ae73-46ee-3824a36e2b8d.jpeg">

また、オプションとしてcsvファイルでの出力も簡単にできる。

```exp_S3api_02.ps1
# 変数設定
$bucket_name = "<特定のバケット名>"
$path = "C:\Work\Test"
$json_file = $path + "\s3api_list.json" #s3apiコマンドの出力ファイル
$exp_file = $path + "\s3file_list.csv" #出力するcsvファイル

# s3apiコマンドで特定バケット内のファイル情報を出力（json形式）
aws s3api list-objects --bucket $bucket_name | Out-File $json_file

# jsonファイルを読み込んでcsvファイルへ変換
(Get-Content $json_file | ConvertFrom-Json).Contents | 
Select-Object Key,StorageClass,Size,LastModified | 
Export-Csv $exp_file -Encoding default
```

出力結果は以下の通り。

<img width="600" alt="shot-002.JPG" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2015081/eb1ad461-7bec-a87b-cb82-41326265d8ce.jpeg">

ファイル数が増えたりストレージクラスの種類が増えたりすると、
フィルターをかけて見たくなる瞬間があると思うので、今後もどこかで使うかなーと考えている。

# 5．参照

https://dev.classmethod.jp/articles/manage-s3-storage-class-with-aws-cli/
EC-CUBE42からメール送信できない件を解決）2例

[１）.envの書き方が間違っていたケース](#１envの書き方が間違っていたケース)
[２）EC-CUBEで使えないメールパスワードを設定していたケース](#２ec-cubeで使えないメールパスワードを設定していたケース)

# １）.envの書き方が間違っていたケース

EC-CUBE4.2.2をインストールしたら、メール送信しない
会員登録メール
受注メール
出荷メール
…

# 動作環境
サーバー　さくらレンタルサーバー　スタンダード
EC-CUBE 4.2.2
PHP Version 8.1.20

# .envで確認

```:vim root/.env
MAILER_DSN=smtp://[メールアドレス]:[passwd]@http://[メールサーバー]:[ポート番号]?auth_mode=plain

```

# いろいろ試すが失敗

MAILER_URL=smtp://[メールアドレス]:[ポート番号]?encryption=ssl&username=[ユーザー名]&password=[passwd]

MAILER_URL=smtp://[メールサーバー]:[ポート番号]?encryption=ssl&auth_mode=login&username=[メールアドレス]&password=[passwd]

MAILER_URL=smtp://[メールサーバー]:[ポート番号]?username=[メールアドレス]&password=[passwd]

MAILER_URL=sendmail://localhost

# 成功スクリプト

MAILER_DSN=smtp://[メールアドレス]:[passwd]@[メールサーバー]:[ポート番号]?auth_mode=plain

`ポイント`

メールサーバーの頭にあった　`"http://"`　が不要だった

`MAILER_URL=`　ではなく　`MAILER_DSN=`　だった

# ２）EC-CUBEで使えないメールパスワードを設定していたケース

# 動作環境
サーバー　MacOS Sequoia
EC-CUBE 4.2.3
PHP Version 8.1.20

# .envスクリプト
```
MAILER_DSN=smtp://[メールアドレス]:**(**)**#**@[メールサーバー]:587?auth_mode=plain
```
パスワードに `(` `)` `#` が入っていたため、ソースコードが途中で止まってしまっていた
DockerをHomebrewで入れる

# DockerをHomebrewで入れる
この記事は、Docker(GUI版)をHomebrewで入れる方法について説明する。
また、既にCUI版がインストールされている場合の対処法についても説明する。

## 目次
[1. 実行環境](#実行環境)
[2. インストール方法](#インストール方法)
[3. CUI版と競合するエラーの解消法](#CUI版と競合するエラーの解消法)
[4. 終わりに](#終わりに)


## 実行環境
- MacOS Ventura 13.5
- Mac book Air 2022 m1
- Homebrew 4.0.26


## インストール方法
ここでは、Homebrew(cask)のインストールが済んでいるものとする。
単純に、GUI版をインストールする場合次のコマンドをTerminal上で実行するだけで良い。
``` bash
brew install --cask docker
```
:::note warn
`--cask` オプションが無いとCUI版がインストールされるため注意
:::


![docker.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3509684/a09990a1-8c3c-4aa1-5d62-e2fd5c1a73e7.png)
すると、上記のようなアイコンがApplicationsに追加され、インストールが完了する。

## CUI版と競合するエラーの解消法
もし、[2. インストール方法](#インストール方法)を実行した際に以下のエラーが発生した場合の解消法を解説する。
```bash
Error: It seems there is already a Binary at '/opt/homebrew/etc/bash_completion.d/docker'.
```
これは、すでにCUI版をインストールしている場合に発生するエラーである。
これを解消するには単純にCUI版を削除すればよいだろう。
以下のコマンドを利用することで、アンインストールすることができる。
```bash
brew uninstall docker
```
その後、[2. インストール方法](#インストール方法)に従って再度インストールを行えばよいだろう。

## 終わりに
GUI版はCUIの要素も含んでいるため、基本的に問題はないだろうが、CUI版も同時に使いたい方は他の方法を探してほしい。
ライティング技術だけでサイトが作成した。

もともとライティングをしていましたが、
https://catchmove.net/digital-marketing/


縁があってサイト作成のお手伝いをさせていただました。
https://pknd-msg.main.jp/

WPで作成。大した技術がないけど、色々といじって完成しました。
ポスドクから企業に転職後2年目の１年間を振り返りました

# はじめに
ポスドクから民間企業のサラリーマンにキャリアチェンジしてから約２年１０ヶ月が経ちました。本記事では、[昨年のAdvent Calendarの記事](https://qiita.com/tk-ml/items/d514e25ff8cf9553c0ca)に引き続き、２年目の１年間、仕事で経験したことや学んだことをまとめした。また、趣味で行っている深層学習やWavelet の勉強、研究についても記載しました。こちらは、少々専門的な内容となっております。

# 
今年は最適化アルゴリズムの開発を約２ヶ月（２ヶ月と一週間程度）、画像認識のアルゴリズム及びソフト開発を約１０ヶ月実施しました。分析ではなく開発よりの案件を希望しておりまして、その希望をプロジェクトのアサインに反映していただきました。

# 配送最適化アルゴリズム開発（約 ２ヶ月）
商品の最適な配送計画を算出するアルゴリズムを構築し、Pythonで実装、ライブラリー化しました。データ構造は木を使って設計しました。このプロジェクトで、Pythonのコーディングスキルがさらに向上しました。


# 画像認識のアルゴリズム及びソフト開発（約１０ヶ月）
<!--ある施設では人手である画像をチェックしているのですが、それが大きな負担になっています。それを自動化
人手で行っている -->
目視による画像チェックを自動化するために、画像認識アルゴリズムを開発、実装しました。高速な処理とメモリ消費量を抑えることが必要だったので、C/C++でアルゴリズムを実装しました。ただし、速い速度が求められない一部のアルゴリズムはPythonで実装して開発、検証しました。

 C言語は実装経験が数年あったのですが、C++はほぼ未経験で基本的なことしか知らない状態でした。本プロジェクトを通じて、STLやC++様々な機能を習得しC++のスキルが大幅に向上しました。これにより、ある程度自信を持ってC++コードを実装できるようになりました。

ソースコードのバージョンはGitで管理しました。本プロジェクトでは、一つのファイルを複数人で編集する等、密な連携が必要なこともあり、Gitの様々な機能利用する必要がありました。これによって、Gitのスキルが大幅に向上しました。


<!--本版環境から切り離して検証できる一部のアルゴリズムはPythonで実装して開発、検証しました。
C/C++で実装
認識モデル作成ツールの開発
リファクタリング
画像処理アルゴリズムの開発
画像認識アルゴリズム検証
Gitを活用しチームで開発-->

# 深層生成モデルの研究
業務時間外に趣味で深層学習やWavelet Scattering (Waveletを使った特徴抽出法) を勉強し、Wavelet Scatteringを使った深層生成モデルを研究しています。
## 深層学習とWavelet Scatteringの勉強
<!-- Wavelet Scatteringや深層生成モデル（特にVAEやdisentanglement関係の話題）を調査しました。-->

深層学習に関してあまり詳しくなかったので、書籍、Webサイト、アイシア=ソリッドさんの動画等で深層学習を勉強しました（e.g., 畳み込み層、バッチ正規化、Optimizer、RNN、LSTMなど）。認識や予測モデルよりも深層生成モデルに興味がわいたので深層生成モデルを中心に勉強しました。深層生成モデルの中でも特にVAEに興味がわき、力を入れて学習しました。統計的モデリングやベイズが好きなこと、様々な応用、拡張が考えられることが理由です。<!-- その過程でβ-VAEを知り、教師なし学習でDisentangled表現を得ることができるということに非常に魅力を感じました。-->中でもβ-VAEは、教師なし学習でDisentangled表現を得ることができるため、非常に魅力を感じました。

Waveletを使った機械学習にも興味があったのでWavelet Scatteringを勉強しました。Wavelet Scatteringは局所的にシフト不変であるなど、パターン認識等への応用において、優れた性質を有しています。計算手順はCNNに似ているのですが、パラメータを学習する必要がありません。具体的には、時系列データ（音響・音声信号等）、画像データに対するWavelet Scatteringの論文を調査し、Wavelet Scatteringの性質、パターン認識への応用について学習しました。論文では、Wavelet Scatteringによる特徴量と他の手法による特徴量をSVM等に入力して認識率を比較するといった検証がよく行われていました。データ数が少ない場合（数百から数千）は、Wavelet Scatteringによる特徴量を使った認識が当時のSOTAを達成しており、パターン認識においては、データ数が少ない場合に非常に有力な特徴抽出法であると思われます。また、Wavelet ScatteringがCNNに似ていることもあり、Wavelet ScatteringをDNNの一部に組み込む論文もあります。例えば、DNN認識モデルの第一層にWavelet Scatteringを組み込んで、Wavelet Scatteringの出力をDNNに入力するといった方法が提案されています。

## Wavelet Scatteringを用いた深層生成モデルの改良

Wavelet Scatteringを用いた画像の深層生成モデルも提案されています。画像をWavelet ScatteringとPCAでエンコードして、得られた潜在変数ベクトルをDCGANのGeneratorのようなネットワーク入力して画像を復元するモデルです。この生成モデルは、エンコーダーが解釈可能であり、かつ、学習が必要なパラメータを有していない（エンコーダーに学習が必要なパラメータが含まれていない）といったメリットがあります。しかし、正規乱数から生成した画像の質は悪く、生成モデルとして不十分です。この画像の生成能力を改善するための研究を行っています。

なお、[こちらのブログ](https://zenn.dev/tkmtark/articles/c4009e0a5030dc)でWavelet Scatteringを用いた深層生成モデルを解説しています。よろしければご覧ください。
<!---また、Disentangled表現もあまり得ることができません。
このモデルのエンコーダーをうまく拡張すれば、上記メリットをあまり損なわずに、VAEと同等の生成画像の精度を有し、Disentangled表現をある程度得ることができる生成モデルを構築することができるのではないかと考えました。
　（このモデル拡張の研究を進めるにあたってまず）現在、上記Wavelet Scatteringを用いた生成モデルを実装し、検証を行っています。
　なお、
Pytorchで実装し、Google Colaboratory（Colab Pro、有料）で実験を行っています。
-->


 

<!---

(深層生成モデルは、GANとVAEが代表的なモデルですが、VAEの方は画像生成以外にも応用があり、特徴抽出もでき、広がりがあるので、VAEを中心的に勉強することにしました。)
――
研究所にいた頃から趣味の研究は行っていました。
-->
画像の効率的な集め方

AIイラスト生成などを行い、画像を学習させるためには、元の画像が必要。
ではどのように画像を集めるか。
※もちろん権利だけは気をつけて

・chrome の Image downloaderをインスコし、画像ファイルを一括でダウンロード

・オールリネームで適宣ファイル名を変更

・重複画像があるのでDupFileElimintorで類似画像を削除

という流れが良い。
ビープ音を鳴らしたい

正式な定義は知りませんでしたが、パソコン本体から「ﾋﾞｯ」っていう音がなるのが、なんかダサかっこいいなという思い出があったので、久しぶりに聞いてみたくなりました。

# ビープ音とは
エラーや状態異常を知らせる音です。  
OSやアプリケーション、BIOSなど発信元は様々です。  
また、ベンダーによりその音や長さ、回数が異なりそれぞれに意味があるとのことです。

# C言語で鳴らしてみる
## 簡単に
そもそもビープ音の存在を認知したのはprintfのリファレンスでした。  
`\n`や`\t`など様々ある中で`\a`でビープ音が鳴りますという説明は当時衝撃でした。  
XP時代だっと思いますが、なんとなくエラー音っぽいのが出てたのは覚えています。

具体的には以下
```c:beep.c
#include <stdio.h>

int main()
{
    printf("\a");
    return 0;
}
```

Windows10 VisualStudio2022で実装して、鳴る音は以下  
[Windows 10 Error Sound](https://www.youtube.com/watch?v=v76-ChTSLJk)

## これじゃない
こんなおしゃれな通知音を効きたかったわけではないのです。  
もっとエラーっぽい、聞いたら焦るような音を出したかったのです。

# PowerShellで鳴らしてみる
手っ取り早く聞きたかったため、検索トップに出てきたPowerShellを使ってみます。
```powershell:beep.ps1
[console]::beep()
```
「ピ」という聴力検査のような音が鳴りました。かなり求めていた音でしたが、まだエラー感は薄いです。

ちなみにlinuxでは以下で音が鳴ります
```bash:beep.sh
echo -e "\a"
```
ubuntuで動かしたところ「ポン」という音が出ました。

## カスタマイズする
音の長さと音程が気に入らないのでカスタマイズ方法を探しました。  
`[System.Console]::Beep`を使用することで、周波数（Hz）と持続時間（ミリ秒）を指定できるようです。
スピーカーからですが、一応求めていたエラー音を出すことができました。  
鳴らしっぱなしにするとより深刻さを味わえます。

また、周波数だとピンとこないかもしれませんが、一般的な音階と紐づけることで、演奏が可能です。  
1節くらい遊びで作ってみてください。

```powershell:beep2.ps1
[System.Console]::Beep(1000, 500)  # 周波数 1000Hz、持続時間 500ms
```

音階の参考は以下  
[ドレミの振動数！ピアノ88鍵全音域の周波数一覧表](https://inalesson.com/frequency_list/2417/)

# TODO
* ネイティブアプリから簡単に出す方法
* BIOSからより深刻さを出す方法

以上です。
cssで入れ子が便利になった

# Overview
- CSSで入れ子がめっちゃ便利になったよ。
- 任意の要素の中のタグだけにcss適応する時に入れ子にできるよ。
- クラスやidは普通にネストできるけど、タグの場合は`&`が必要になる。

# Get started!
```html
<div class='wrapper'>
    Wrapper Text
    <div class='child'>
        Child Text
    </div>
    <p>
        p　Text
    < p>
</div>
```

```css
.wrapper {
  color: red;
  .child {
    color: green;
  }
  & p {
    color: purple;
  }
}
```
[JavaScript] ビットコインのウォレットを作成する

# ビットコインのウォレットを作ってみる
暗号資産（仮想通貨）におけるブロックチェーン開発を行うにあたって、必要となるのが「ウォレット」という存在です。それを今回は作っていこうと思います。

## ウォレットとは？
> 暗号資産のウォレットとは、通貨を保管する場所のことです。ウォレットには、財布という意味がありますので、暗号資産用の電子財布と理解すればよいでしょう。

[暗号資産（仮想通貨）のウォレットとは？特徴や種類は？](https://coincheck.com/ja/article/143) より．

<br>

## ウォレットに必要なもの
基本的にウォレットとして必要なものは，ウォレットのID = ウォレットアドレス が一番にあがります．
今回ではその他にも，送金などにも必要な公開鍵と秘密鍵の生成を同時に行います．
<br>

## ウォレットアドレス，公開鍵，秘密鍵の生成をする．

### 注意事項
今回は，"[bitcoinjs-lib](https://www.npmjs.com/package/bitcoinjs-lib)"を使用しています．記事では，バージョン6.1.3を使用しており，バージョン，4や5の場合と挙動が大きく違いますので，その場合は別の記事を読んでください．（下の方に参考を書いておきます．）

<br>

```javascript: ウォレットアドレス / 公開鍵 / 秘密鍵の生成
// bitcoinjs-lib@6.1.3
const bitcoin = require('bitcoinjs-lib')
const { ECPairFactory }  = require('ecpair')
const ecc = require('tiny-secp256k1')
const ECPair = ECPairFactory(ecc);


// ウォレットの生成
function createWallet() {
    //select testnet
    const network = bitcoin.networks.testnet;
    
    const keyPair = ECPair.makeRandom(network)
    // genetare addresss by Pay to Public Key [Hash]
    // P2PKHはLocking Scriptに送金相手のPublicKey：公開鍵のRIPEMD160(SHA256(PublicKey))したハッシュ値を含むLockgin Scriptで送金することを言います。
    const { address } = bitcoin.payments.p2pkh({ pubkey: keyPair.publicKey })
    console.log("address: " + address) 
    var publicKey = keyPair.publicKey.toString('hex')
    
    console.log("public key: " + publicKey) 
    
    var privateKey = keyPair.toWIF()
    console.log("private key: " + privateKey) 
}

function main() {
    createWallet();
}

// execuse
main();
```


## Bitcoin faucet 

送金体験とかをするために，ちょっとだけbitcoinをもらっておく．



## バージョン4または5の方向けの記事

https://bitcoinjs-guide.bitcoin-studio.com/bitcoinjs-guide/v5/index.html

https://fibjs.org/docs/awesome/module/bitcoinjs-lib.md.html
【Redux】頭が痛くなるReduxの仕組みを完全に理解した（い）


# Introduction

本記事では Redux の概要を備忘録として残します。
Web 開発では React が好きなのですが、実務では使わず趣味程度のため、大規模開発向けと聞いていた Redux は敬遠していました。

ある程度 React には慣れたため props のバケツリレー解消目的で Redux を試すと、動くけど理解しきれていないものが出来上がりました。
意味を理解しながら実装できるように Redux の基礎を固めます。

:::note warn
警告
備忘録のため正確さよりも（私にとっての）理解しやすさを意識して記述しています。
:::

**本記事が少しでも読者様の学びに繋がれば幸いです！**
**「いいね」をしていただけると今後の励みになるので、是非お願いします！**

## 環境

Ubuntu22.04

## Redux とは

状態管理のこと。
Redux で監視している現在の状態に応じて処理を変える。

### ex. 飲食店

<details><summary><b>=======================<br>&nbsp;&nbsp;&nbsp;飲食店でのRedux<br>&nbsp;========================</b></summary><div>

- 注文前
  - 客
    - 状態：メニューを悩んでいる。
  - 店員
    - 状態：何もしない。
- 注文
  - 客
    - 状態：店員を呼ぶ。
  - 店員
    - 状態：注文を聞きに行く。
- 注文後
  - 客
    - 状態：何もしない。
  - 店員
    - 状態：注文を伝える。

</div></details>

客の注文に応じて店員の処理を変える。
− 客が注文前か、注文するのか、注文後なのかをReduxで監視する。

### ex. X

<details><summary><b>=======================<br>&nbsp;&nbsp;&nbsp;XでのRedux<br>&nbsp;========================</b></summary><div>

- ログイン済
  - プロフィールを見せる。
- ログイン前
  - ログイン画面を見せる。

Redux でページの画面を変更する。

</div></details>

### React のみとの違い

- React：Component から子、孫、それ以下にバケツリレーして渡す。
  - 小規模でバケツリレーをあまりしなくて良い場合。
  - 保守性に欠ける。
- Redux：1 箇所で管理してどこの Component からでも呼び出せる。
  - 大規模でバケツリレーが必要な場合。
  - 保守性に優れる。

### Redux の仕組み

![Image](https://user-images.githubusercontent.com/113032853/268547801-bdb29500-9a8c-426d-a887-a6c3376fc13a.gif)

> Quoted from <https://redux.js.org/tutorials/essentials/part-1-overview-concepts>

<details><summary><b>=======================<br>&nbsp;&nbsp;&nbsp;Reduxによる処理の流れ<br>&nbsp;========================</b></summary><div>

1. State：状態

   - ex. $0

2. UI：Button

   - Deposit $10：ボタンを押して+$10 する。
     - Action 実行。

3. Dispatch：Action をStore に通知

   - Event Handler：Event(Deposit $10)を処理する。

4. Store：1 箇所で状態を管理し、どの Component でも使えるようにする。

   - Global に扱う。
   - Reducer：State（以前の状態） を Action（新しい状態） に更新。
     - Action と State を同時に取得する。
       - Action：Event(Deposit $10)）が Reducer に遷移する。
       - State：以前の状態（$0）が Reducer に遷移する。
     - R：Reducer 内のロジック
   - State：$0→$10 に更新。

</div></details>

### 最後に

最後まで閲覧頂きありがとうございました。

非常に基礎的な部分ではありますが、本記事にまとめた内容が実装する際の理解に役立ちました。
Redux に限らず少し複雑に感じる内容は以下の手順で進めることをおすすめします。

1. 軽く実装を見てみる。
2. 公式ページで言葉の定義を知る。
3. 実装してみる。
4. 理解できなかった箇所を公式ページで理解する。
5. 再度実装してみる。

成果に目を向けると精神的に苦しくなるので、成長に目を向けて 1 つずつ理解していきましょう！

本記事がお役に立てば幸いです！

### 参考 URL

https://redux.js.org/tutorials/essentials/part-1-overview-concepts
記事を書く目的と構成について

# 記事を書く目的
目的は、2つあります。

**＜1つ目＞**
　自分が作業で学んだ内容の整理と理屈を確認すること。

**＜2つ目＞**
　新人エンジニアが記事を読んで何かの手助けになること

### 1つ目の目的について
1つ目については、教えてもらった内容や学んだ内容を自分で解釈し、
どのような理屈（仕組み）になっているかを理解したいと思い、設定しました。

作業をしていて、どのように進めてよいか分からなかった内容を教えてもらうことがありましたが、理屈を教えてもらえず、修正方法や記載内容など。「答え」だけを教えてもらうことが多く、なぜその「答え」になるか分からない場面が多くありました。

また、１～2年目で知識がない中説明を受け、「何を言っているんだろう・・」状態になり、説明された内容のついていけない、何が分からないか分からない状態になり、整理ができないことがよくありました。

「答え」を出すための理屈を理解する「解釈する場」や教えてもらった内容の「整理をする場」として記事を書き、エンジニアとして必要な知識を蓄えたいと考え、目的を設定しました。

### 2つ目の目的について
2つ目については、知識があまりない新人エンジニアという弱い立場の方の役に立てれればと思い、設定しました。

知識がなく右も左も分からない中、何を聞いて作業を進めてよいか、作業で困ったことをどのように（ツールやエディタなど使って）解決するか分からないことが多くあると思います。

新人が疑問に思うことや分からないことを何とか解釈した内容を質問すると、「当たり前のことなんで聞くの」、「馬鹿だろ」など理不尽に責め立てられてしまい、理不尽に壊されてしまうことがあることをよく聞きます。

自分としては、
「仕事ができる（裁量権がある）からといって人を壊してよい」
ことは間違っていると強く思っています。

弱い立場のエンジニアを理不尽に壊されないよう、何か手助けになれればと考え記事を残してみようと思いました。

記事の構成について
記事を次のような構成で作成していこうと考えています。

＜記事構成＞
　1、事象について
　2、教えてもらった内容
　3、教えてもらった内容の補足や調べた内容
　4、実際の使用方法

## 1、事象について
どのようなことで困ったのか、問題が起きたのかをイメージしやすくすることを目的として記載します。

## 2、教えてもらった内容
教えてもらった内容をそのまま記載します。

## 3、教えてもらった内容の補足や調べた内容
「2、教えてもらった内容」から、内容を解釈するのに、どのように解釈したか、どのように調べたかを記載して、自分がどう整理したかを思い出せることを目的として記載します。

## 4、実際の使用方法や使用のされ方
作業イメージや解釈イメージを湧かせやすいことを目的として記載します。
キャプチャーや図などを使用して、内容をまとめたいと考えています。
Miller's Algorithmの定義の読み方

## Miller's Algorithm の定義
[Ben Lynn のウェブサイト](https://crypto.stanford.edu/pbc/notes/ep/miller.html)で Miller's Algorithm が次のように紹介されている。

---
#### Miller's Algorithm

Consider $E[l]$, the $l$-torsion points of an elliptic curve $E$. Write $f_P$ for the rational function with divisor $l(P)-l(O)$.

Let $g_{P,Q}$ be the line between the points $P$ and $Q$, and let $f_c$ be the function with divisor $(f_c) = c(P) - (cP) - (c-1)(O)$. Then for all $a,b \in \mathbb{Z}$, we have $ f_{a+b}(Q) = f_a (Q) f_b (Q) g_{aP,bP} (Q) g_{(a+b)P, -(a+b)P} (Q)$. Let the binary representation of $l$ be $l_t,\cdots,l_0$. Then Miller's algorithm computes $f_P(Q)$ as follows.

1. set $f \leftarrow 1$ and $V \leftarrow P$
1. for $i \leftarrow t-1$ to $0$ do
    1. set $f \leftarrow f^2_{g_{V,V}}(Q) / g_{2V,-2V}(Q)$ anf $V \leftarrow 2V$
    1. if $l_i = 1$ then
        1. set $f \leftarrow f_{g_{V,P}}(Q) / g_{V+P,-(V+P)}(Q)$ and $V \leftarrow V + P$

---

### 前提
- 楕円曲線の式は、変数が $x, y$ で、coefficient が finite field (以後 F) の要素の polynomial ring (以後 R)。例えば、BLS12-381 の G1 だと、$y^2 = x^3 + 4$ で、$x,y$ の coefficient と $4$ が $F_q$ の要素。

- 楕円曲線上の点は、楕円曲線の式を満たす F の要素 $x,y$ の組み合わせ。

### 読み方
- $E[l]$: 位数が $l$ の点の集合

- Function: R の要素の比 (rational function)。点を入力に取って、比の式の $x,y$ を点の $x,y$ で置き変えることで評価できる。評価結果は F の要素。

- Divisor: function のふるまいを表すもの。プラスの項はゼロになる点、マイナスの項は評価不能になる点 (pole) を表す。係数はそれぞれ項の multiplicity。より具体的には、$g(x,y)$ が、点 $P$ でゼロや評価不能にならない関数で、$xP$ が $P$ の $x$ 座標だとして、$f_P$ の divisor が $l(P)$ を含んでいる場合は、$f_P(x,y)=(x - xP)^l g(x,y)$ のように、$xP$ が関数のルートになる項が $l$ 個含まれている。

- $g_{P,Q}$: 点 $P,Q$ を通る直線の式  $y = mx + b$ の右辺の項を左辺に移項した $y - mx - b = 0$ の左辺が分子で、分母が $1$ の rational function。$m$ は直線の傾きで、$b$ は $y$ 切片。通常の関数と同じように、点を入力として、F の要素に評価できる。

- $f_c$: $c(P) - (cP) - (c-1)(O)$ という divisor を持つ rational function。 $c$ は F の要素。divisor の定義内の $c$ が、$f_c$ の $c$ で置き変わる。

- $f_c(Q)$: $f_c$ を、点 $Q$ で評価する。評価結果は、F の要素。

- $g_{A,B}(Q)$: $g_{A,B}$ を、点 $Q$ で評価する。評価結果は、F の要素。

- $l_t,\cdots,l_0$: $l$ を binary で表したビットベクター。例えば、[1,0,0,...,1] 。
Vue3でプロジェクト作成　SCSSを使う

# Vue2とVue3についてまとめ
まずVue2とVue3の違いをざっとおさらい
|  | Vue2 | Vue3 |
| ---- | ---- | ---- |
| リリース | 2014年 | 2020年9月 |
| プロジェクト作成ツール | Vue CLI | create-vue |
| プロジェクト実行環境 | Webpack | Vite |
| TypeScriptサポート | 非標準 | 標準 |
| ステート管理機能 | Vuex | Pinia |
| ユニットテストツール | Jest | Vitest |

# プロジェクト作成
プロジェクトを作成したいディレクトリで以下コマンドを実行
```@terminal:terminal
npm init vue@latest
```

続いてプロジェクト名やオプションを聞かれるので選択。今回は「portfolit_vue3」という名前でプロジェクト作成。
TypeScriptを使いたいかとかJSX記法使いたいかとか色々聞かれる。これは作生するプロジェクトによって変更してほしい。
今回自分はテストツール以外はYesにした。
```@terminal:terminal
✔ Project name: … portfolit_vue3
✔ Add TypeScript? … No / Yes
✔ Add JSX Support? … No / Yes
✔ Add Vue Router for Single Page Application development? … No / Yes
✔ Add Pinia for state management? … No / Yes
✔ Add Vitest for Unit Testing? … No / Yes
✔ Add an End-to-End Testing Solution? › No
✔ Add ESLint for code quality? … No / Yes
✔ Add Prettier for code formatting? … No / Yes
```

続いて指示された通り作成したプロジェクトに移動し、npmインストール、開発環境起動のコマンドを実行するとローカルサーバが立ち上がる
```@terminal:terminal
  cd portfolit_vue3
  npm install
  npm run dev
```

今回はSCSSを使いたいので一旦ローカルサーバは閉じて続いて以下コマンドを入力
```@terminal:terminal
npm i -D sass
```

main.cssの拡張子をmain.scssにする
main.tsでimportしているCSSの拡張子をSCSSにする
各vueファイルではlang="scss"　にして記述すればSCSSが使用できる
```@typescript:main.ts
import "./assets/main.scss";
```
```@vue:各vueファイルのstyle記述部分
<style lang="scss" scope>
```

今後global変数などの設定の仕方も残していきたい。。今回はここまで。

### 参考
[Vue 3　フロントエンド開発の教科書](https://amzn.asia/d/csYTp6y)
[Vue3でSCSSの変数を呼び出して使う方法](https://note.com/yoko_0413/n/na2e1a7a0905f)
[vue3の新規アプリ（プロジェクト）を create-vue コマンドで作成する。scssを使用する](https://pgmemo.tokyo/data/archives/2245.html)
【ChatGPT無】「むかしむかし」に単語を続けて、一文を作成してもらいます。


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

　今回は、「むかしむかし」に単語を続けて、一文を作成してもらいます。でも、とあるルールでの作成です。

:::note info
本記事は、ChatGPT（無料版）で
行なっております。GPT4での確認
はできておりません。あしからず。
:::
　ChatGPTの説明に
　　よく使われる
　　　「むかしむかし」ですが、
　　　　その説明を聞いていて、
　　　　　今回のプロンプトを
　　　　　　思い付きました。

　最初の言葉に続く単語で、
　　確率の高いものが、
　　　その言葉に結合していく。

　それを繰り返して、
　　一文が作られていく。

　それを
　　わざと低い確率の単語を
　　　結合していったら、
　　　　どうなるだろう？、と。
***
　まずは、Promptです。
```Text:単語を続けて、一文作成Prompt
# 目的
「むかしむかし」に続けて、一文を作成してください。

# 処理手順
1.「むかしむかし」→変数Ａ
2.変数Ａに続く単語の候補を確率とともに表示。
3.2の候補から、低い確率の候補を変数Ａに連結。
4.変数Ａが一文（“。”を終端とする）として、完成していないならば、2に戻る。
5.変数Ａが一文（“。”を終端とする）として、完成したならば、変数Ａを表示する。
```
　確率の低い単語を
　　繋げていく。

　これは、
　　アイディア出しの
　　　ひとつの方法になります。

　以下が、
　　上記Promptの結果です。
```Text:結果
処理手順に従って、一文を作成します。

1. 「むかしむかし」→変数Ａ
2. 変数Ａに続く単語の候補を確率とともに表示。

   例: 
   - ある日、0.3
   - 森の中で、0.2
   - 昔々、0.4
   - 遠い国で、0.1

3. 2の候補から、低い確率の候補を変数Ａに連結。

   変数Ａ＝「むかしむかし、遠い国で」

4. 変数Ａが一文（“。”を終端とする）として、完成していないならば、2に戻る。

   2. 変数Ａに続く単語の候補を確率とともに表示。

      例: 
      - ありました、0.2
      - 王様がいました、0.3
      - とても美しい姫がいました、0.1
      - 冒険が始まりました、0.4

   3. 2の候補から、低い確率の候補を変数Ａに連結。

      変数Ａ＝「むかしむかし、遠い国で冒険が始まりました」

   4. 変数Ａが一文（“。”を終端とする）として、完成していないならば、2に戻る。

      ...（繰り返し）

5. 変数Ａが一文（“。”を終端とする）として、完成したならば、変数Ａを表示する。

   完成した一文：「むかしむかし、遠い国で冒険が始まりました。」
```

　ただ、
　　このPrompt、
　　　Regenerateを
　　　　繰り返すと、
　　　　　異なった出力をする
　　　　　　困ったちゃんですw

　うまく意図した
　　結果を導けない可能性が大。

　それでも
　　思いがけない
　　　結果を出力することも
　　　　あります。

　その思いがけない出力が、
　　アイディア出しに
　　　なったりもします。

　創作活動する方の
　　一助になったら、
　　　うれしいです。

　以上。
ionicでダークモード対応アプリ作成

# ソフトウェア準備
```bash
# Angularバージョンアップ
npm uninstall -g @angular/cli
npm install -g @angular/cli

# ionicバージョンアップ
npm uninstall -g @ionic/cli
npm install -g @ionic/cli
```

Android　Studioをダウンロードしてインストール
https://developer.android.com/studio

# ionicサンプルアプリ作成

```bash
# サンプルアプリ作成
ionic start ionic-darkmode blank
```

# ダークモード切替処理実装

VSCodeを起動する。

```bash
cd ionic-darkmode

# VSCode起動
code.
```

app.components.ts にダークモード切替処理を実装する。

```typescript
import { Component, OnInit } from '@angular/core';

@Component({
  selector: 'app-root',
  templateUrl: 'app.component.html',
  styleUrls: ['app.component.scss'],
})
export class AppComponent implements OnInit {
  constructor() {}
  ngOnInit(): void {
      // メディアクエリーのchangeイベントリスナーに切替処理を登録
      const darkModeMediaQuery = window.matchMedia('(prefers-color-scheme: dark)');
      darkModeMediaQuery.addEventListener('change', this.handleDarkModeChange);
  }

  /**
   * ダークモード切替処理
   */
  handleDarkModeChange(e: any) {
    if (e.matches) {
      document.body.setAttribute('color-theme', 'dark');
    } else {
      document.body.setAttribute('color-theme', 'light');
    }
  }
}
```


# Androidアプリ作成

ionicのコマンドで、Androidアプリ機能を付加して、Android Studioを起動する。

```bash
cd ionic-darkmode

# 前回のビルドで生成されたファイルを削除
rm -rf android
rm -rf www

# Androidアプリ属性付与
ionic cap add android

# Androidアプリのビルド
ionic cap build android
```

Android Studioが起動したら
エミュレータもしくは実機接続して動作検証する。
【エラー解決】Google Cloud CLI 「UnicodeDecodeError: 'utf-8' codec can't decode byte 0xb0 in position 37: invalid start byte」

# 概要
ターミナルでgcloudコマンドを使えるようにしたく、手順に従ってセットアップするもエラー

UnicodeDecodeError: 'utf-8' codec can't decode byte 0xb0 in position 37: invalid start byte

私が解決した方法をご紹介します。

# 環境
・Apple M1 Ventura 13.5.2
・arm 64　(uname -mとターミナルで実行すると確認できます)
・Python 3.9.13
・Homebrew 4.1.11

# 解決法

1.以下リンクより、プラットフォーム「macOS 64 ビット
(ARM64, Apple M1 silicon)」のパッケージ　「google-cloud-cli-445.0.0-darwin-arm.tar.gz」をダウンロード

https://cloud.google.com/sdk/docs/install-sdk?hl=ja#mac

2.ダウンロードしたファイルを「~.tar.gz」のまま、配置したいフォルダに移動させる


3.cdコマンドでフォルダまで移動
cd "フォルダ"

4.「google-cloud-cli-445.0.0-darwin-arm.tar.gz」を以下コマンドで解凍する
```
$tar -zxvf google-cloud-cli-445.0.0-darwin-arm.tar.gz
```
5.google-cloud SDKの初期化をする
```
$./google-cloud-sdk/bin/gcloud init
```
6.coogle cloud SDKをインストールする
```
$brew install google-cloud-sdk
```
7.gcloud versionと打って、以下のようなコードが出てくれば成功です！
```
Google Cloud SDK 446.0.1
bq 2.0.98
core 2023.09.13
gcloud-crc32c 1.0.0
gsutil 5.25
```

8.gcloudにログインする
```
$gcloud auth login
```
# 最後に
もし解決できない方いらっしゃいましたら、コメントお願いいたします。
アンビエント宣言(declare)について理解する

# 目次
1. 背景
2. アンビエント宣言(declare)とは
3. 型定義ファイルとは

# 1.背景
[Branded Type について理解する](https://qiita.com/yamatai12/items/e972833b3105883202a3)
この記事の中でdeclareキーワードが出てきた為です。

# 2. アンビエント宣言(declare)とは
```typescript
declare var foo: any;
foo = 123; // allowed
```
- 実装を定義しない宣言です。
- 他の場所に存在するコードを記述しようとしていることをTypeScriptに伝えることができます。
- 宣言された項目が実行時に存在しなければエラーになります。
    サンプルコードは実行時に
    ```javascript
    foo = 123
    ```
    しかない為、エラーになります。

[サンプルコード](https://www.typescriptlang.org/play?#code/CYUwxgNghgTiAEA3W8BmB7dAueUB2AngNwBQG68AvPAIwBMAzEfAPQu4QToDuIwQA)

# 3. 型定義ファイルとは
他のファイルで利用したい型(type/interface)を記述するファイルです。
この型宣言ファイルの定義に基づき、コンパイル時に型推論や型チェックが行われるようになります

例）JavaScriptで記述されたライブラリcalc.jsがあるとします。
```calc.js
exports.sub = function(a, b) {
    return a - b;
}
```
型定義ファイルを以下のように宣言します。
```calc.d.ts
export function sub(a: number, b: number): number;
```
これにより、exec.tsはcalc.d.tsを通してsub関数を認識することができ、コンパイルが通るようになります。

```index.ts
import { sub } from "./calc";
console.log(sub(100, 1));
```
[動作確認用リポジトリ](https://github.com/yamatai12/sample-declare)
型チェックもされています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/405182/c4b3565d-0214-bb54-e621-f9daf9940ae8.png)

## DefinitelyTyped
[DefinitelyTyped](http://definitelytyped.org/)というコミュニティプロジェクトが存在しており、ここにはJavaScriptで記述されたライブラリの型宣言ファイルが集まっています。

DefinitelyTypedに登録されている型宣言ファイルは、npmコマンドでプロジェクトに取り込むことができます。
```
npm install --save @types/jquery
```

## [トリプルスラッシュディレクティブ](https://js.studio-kingdom.com/typescript/handbook/triple_slash_directives#reference_types)
viteのvite/clientで以下のような型定義ファイルを見つけました。
```vite-env.d.ts
/// <reference types="vite/client" />
```
///をトリプルスラッシュディレクティブと言います。
>- 1つのXMLタグを含む1行コメントです。
>- それが含まれる各ファイルの先頭でのみ有効です。
>- 別のトリプルスラッシュ・ディレクティブを含めて、単一行または複数行のコメントの前にのみ置くことができます。それらがステートメントまたは宣言の後にある場合は、通常のコメントとして扱われて特別な意味を持たなくなります。

## [型ディレクティブ](https://typescriptbook.jp/reference/declaration-file#-reference-types--%E5%9E%8B%E3%83%87%E3%82%A3%E3%83%AC%E3%82%AF%E3%83%86%E3%82%A3%E3%83%96)
```
/// <reference types="..." />
```
型ディレクティブは型のimportのようなものです。
型定義ファイルに依存していることを示しています。
```vite-env.d.ts
/// <reference types="vite/client" />
```

この例だとvite/types/clientに依存していることが分かります。
[vitejs.dev guide Features](https://vitejs.dev/guide/features.html#client-types:~:text=Client%20Types,typescript)

https://www.typescriptlang.org/docs/handbook/triple-slash-directives.html#-reference-types-

# 参考
- [アンビエント宣言(declare)](https://typescript-jp.gitbook.io/deep-dive/type-system/intro)
- [型定義ファイル](https://typescript-jp.gitbook.io/deep-dive/type-system/intro/d.ts)
- [TypeScript】初心にかえってTypeScriptを理解する。](https://qiita.com/crml1206/items/1ffe928339950c4938a4)
- [Modules](https://www.typescriptlang.org/docs/handbook/modules.html#working-with-other-javascript-libraries)
- [【TypeScript】型定義ファイル(.d.ts)ファイルについて
](https://zenn.dev/nash/articles/bb5048a2754245)
- [レガシーなアプリケーションにこそTypeScriptを採用するべき４つの理由](https://tech-blog.rakus.co.jp/entry/20200709/typescript)
- [アンビエント宣言(declare)と型定義ファイル(.d.ts)](https://www.wakuwakubank.com/posts/501-typescript-declaration/)

## 参考になる記事を書いてくださった皆様ありがとうございました！

## 宣伝させてください！
https://recruit.iimon.co.jp/
Django(Python)でAPIを3日で作成した

# はじめに
Djangoで（詳しくはDjango REST Frameworkで)でAPIを作成しました。
私はポイ活が好きなこともあり、クレジットカードの基本情報を調べるのが好きです。

作成したソースコードです

https://github.com/takuya-wooooo/CardInfoAPI

# 作成した理由
クレジットカード選びは、多くの人にとって難しい選択の一つです。
還元率や年会費、特典など、考慮すべき要素は多いです。
そこで、これらの情報を一元的に提供するAPIがあれば便利だと考え、今回のAPIを開発しました。
プロトタイピングなので荒く作成しています。

# 技術スタック
```
Python 3.11.5
Django 4.2.5
Django REST framework 3.14.0
SQLite 3.37.0
Sentry 1.30.0
drf-yasg 1.21.7
pip 23.2.1
```

# 主な機能
+ カードの特性情報取得: カードの名前、ポイント還元率、年会費などの基本情報を取得できます。
+ カードのカテゴリやタイプ: カードのカテゴリ（例：ゴールド、プラチナなど）による絞り込みが可能です。
+ 利用者のレビューや評価: 実際の利用者のレビューや評価を参照できます。
+ カードの比較機能: 2つ以上のカードを選んで、その特性を比較することができます。
他には、セキュリティやパフォーマンスの面でも多くの機能を取り入れています。CORS対応、セキュリティヘッダの設定、キャッシング、レートリミティングなど、APIとしての基本的な要件をしっかりと満たしています。

READEME.mdに細かく書いています
![スクリーンショット 2023-09-11 17.36.45.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/603047/8cfb43df-a51f-ecbb-3442-8158bdc9c46f.png)


# セキュリティ
+ CORS対応
+ セキュリティヘッダーの設定
 iframeで表示不可
+ データベース
 パスワードのハッシュ化
 SQLインジェクション対策

# 管理・モニタリング
Sentryを採用しました。
モニタリングツールのSentryに関しては別記事に書いています

https://qiita.com/wooooo/items/6bce68f47ec4b6dc3c9e

# あとがき
様々なクレジットカードの情報を返すAPIを調べてみましたが、自分調べでは無く。
最後の頼みの価格コムのAPIでは商品情報などを返す機能はありましたが、さすがにクレジットカード情報はありませんでした。
クレジットカードのまとめ情報としては、(アフィリエイト)ブログでまとめで紹介している媒体しかなかったです。
今はPythonやGo言語を主戦場としているため、これらの言語で何か作ろうかなと思い立ち、考えた結果、自分の好きなクレカ領域で作成してみました。
自分の好きな領域だと開発がスイスイ進みました。
例えばクレジットカードだと、新興のバンドルカードのカンムさんやUPSIDERさん、大きいところですと楽天カードやPayPayカードなどあります。
ちなみに、自分の好きな領域は他にもあります。。。笑
農業、地域活性化、GIS、データ分析、、、etc
やはりエンジニアは好きな領域で開発するのは良いのでは無いかと思いました。
あと、読者の方で採用の方やBPを探している方がいらっしゃいましたら中途、SESに関してX(旧Twitter)の方でDMお願いします

https://twitter.com/TakuyaEngeener
Makefileのtarget・phony targetとは

## targetとは

- makeコマンドによって作成されるファイルのこと

### 記述の仕方

```
作成するファイル（=ターゲット）: ターゲット作成処理が依存するファイル
    ファイル作成のためのコマンド
```

### 具体例

```
app.exe: main.o
    gcc main.o -o app.exe
```

## phony targetとは

- 成果物を持たない偽のターゲットのこと
- phony：「偽の」という意味


### 記述の仕方

```
.PHONY: phony target名

phony target名:
    実行したいコマンド
```

### 具体例

```
.PHONY: clean

clean:
    rm app.exe main.o
```

### 何が嬉しいの？

- 成果物が無いコマンドも、まとめられる
- 通常のターゲットは「makeコマンド実行によって作成される成果物」を指す
    - ※ターゲットを作成するときの挙動
        - ターゲット（app.exe）がすでに存在するかチェック
        - 存在したら、ターゲットが「依存するファイル（main.o）」より新しいかチェック
        - 新しかったら、makeコマンドは処理を実行しない
            - ※最新の依存関係でmake処理を実行済みということなので、処理が不要
- 成果物が無いけど、makeコマンドでまとめたい処理がある場合
    - phony targetを使える
    - 「ターゲット（app.exe）が実際のファイルじゃなく、処理をまとめたシンボルを指している」とmakeコマンドに教えることができる


## 参考文献
- [MakefileのPHONYで便利コマンドを書く - なるぽのブログ](https://yu-nix.com/archives/makefile-phony/)
Databricks の replaceWhere による選択的上書きにて IN 句の利用可否の検証

## 概要

Databricks の replaceWhere による選択的上書きにて IN 句（例：`datasource in ("bbb.txt","ccc.txt")`）の利用可否の検証結果を共有します。結論としては、IN 句で指定したデータが上書きされました。replaceWhere による選択的上書きとは、次のドキュメントにて記載されている機能です。

- [Delta Lake を使用してデータを選択的に上書きする - Azure Databricks | Microsoft Learn](https://learn.microsoft.com/ja-jp/azure/databricks/delta/selective-overwrite)


## 検証方法と検証結果

次のようなデータをもつテーブルを用意します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/31ef9e1e-0cc7-2161-d4fb-d88b23155cbc.png)

`datasource`列にて`bbb.txt`と`ccc.txt`の値のレコードを次のようなデータに上書きします。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/be923683-b516-eb8d-0e7b-cbffa170acbf.png)

replaceWhere による選択的上書きを実施したところ、次のようにデータが上書きされました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/8323da03-a0d8-1716-685b-2b5e1eb8c95f.png)


## 検証コード

### 1. スキーマを作成

```python
%sql
create schema if not exists replace_test;
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/c11d64b5-f425-b308-2c5c-f99a77d0fb5e.png)

### 2. テーブル作成と初期データの挿入

```python
%sql
create or replace table replace_test.tbl_01
(
  str_col string,
  int_col int,
  datasource string
);
 
INSERT INTO replace_test.tbl_01
(
  str_col,
  int_col,
  datasource
)
SELECT 'a',NULL,'aaa.txt'
UNION ALL
SELECT 'b',NULL,'aaa.txt'
UNION ALL
SELECT NULL,NULL,'bbb.txt'
UNION ALL
SELECT NULL,NULL,'bbb.txt'
UNION ALL
SELECT NULL,NULL,'ccc.txt'
UNION ALL
SELECT 'd',NULL,'ddd.txt'
UNION ALL
SELECT 'e',NULL,'ddd.txt'
;
select * from replace_test.tbl_01;
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/7e8bfd72-0c04-2013-9ae6-6aedecbe9d81.png)

### 3. 上書きデータを保持したデータフレームを作成

```python
src_d = [
    {
        'str_col':'c',
        'int_col':222,
        'datasource':'bbb.txt'
    },
    {
        'str_col':'d',
        'int_col':333,
        'datasource':'bbb.txt'
    },
    {
        'str_col':'e',
        'int_col':444,
        'datasource':'ccc.txt'
    },
]
 
src_s = """
str_col string,
int_col int,
datasource string
"""
 
df = spark.createDataFrame(src_d,src_s)
df.display()
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/f36b2185-f330-6dab-cc12-c6048725c605.png)

### 4. replaceWhere による選択的上書きの実施と結果確認

```python
(
    df.write
        .mode("overwrite")
        .option("replaceWhere", 'datasource in ("bbb.txt","ccc.txt")')
        .saveAsTable("replace_test.tbl_01"
    )
)
spark.table("replace_test.tbl_01").display()
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/5d849cdd-6904-3ead-afc5-39a050c7e799.png)

### 5. リソースの作成

```python
%sql
drop schema replace_test cascade
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/625d7148-ac5f-cbb3-d90d-1fd143f4fd24.png)
Field Service Lightningの勉強メモ③


#### ライセンス名の変更
MoblileEmployee→Fieldテクニシャン
FSL＋→FS＋

#### メンテナンス計画
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/450298/58f82ce4-4a77-de26-de93-11daa81627ea.png)
https://trailhead.salesforce.com/ja/content/learn/modules/field_service_maint/field_service_maint_plan
・毎月訪問、とかだけではなく、条件ベース（XXが50％切ったら）も可能
https://trailhead.salesforce.com/ja/content/learn/modules/field_service_maint/field_service_maint_plan

▽メンテナンス計画に紐づけて条件定義も可能
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/450298/b774591b-25ce-d2b2-293c-d127854ffd87.png)


#### アクセス権限は2パターン
①FieldServiceの設定
・設定方法：FieldServiceの設定＞以下2つのOption
　　（１）[割り当て済みサービス予定を割り当て済みリソースと共有する]
　　（２）[サービス予定の親作業指示を割り当て済みリソースと共有する]
・タイミング：即時
・条件：サービス予定の状況がDispatchになったタイミング（Scheduledでは動かない）
・付与先：割り当てられたサービスリソースを、サービス予定、作業指示へ権限付与

②ユーザテリトリ
・タイミング：バッチ（ユーザテリトリをもとに公開Gを作らえれるのが日次のため）
・条件：サービス予定のテリトリ項目＝ユーザテリトリの公開グループの時。
・付与先：上記ユーザテリトリを、以下に付与。
　　- リソース不在
　　- サービス予定
　　- サービスリソース
　　- サービステリトリー
　　- 共有サービス予定の親オブジェクト (取引先、納入商品、商談、作業指示、および作業指示品目など)
https://help.salesforce.com/s/articleView?id=sf.fs_sharing.htm&type=5

※ユーザテリトリレコードは、ユーザテリトリタブより作成

▽サービス予定のサービステリトリーの紐づけ
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/450298/033973fd-ce4d-6aae-0a4a-6a3a1d42d6ea.png)

▽サービステリトリ（場所や営業時間など管理）
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/450298/7fa68d91-767d-f784-c9e0-363d8cbefbe6.png)
※開始日・終了日を持ち、サービルリソースとの紐づけも可能

▽ユーザテリトリがアプリから出てこなかったが、Classicで項目から漁ったら定義有り
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/450298/f2d78be6-5397-81ab-06a0-2bbd065006f9.png)

▽FieldServiceの設定
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/450298/4911ef03-e5ce-7835-160d-d227beaf651f.png)
Django import-export 文字コード charsetを変更する方法

Django用のパッケージimport-exportは便利なものである。
xlsxやcsvのフォーマットで入出力が簡単にできる。

ただしDBにUTF-8に対応していない文字列、例えばゼロ幅スペース(\u200b)などが紛れ込んでしまった場合は
ServerError500('cp932' codec can't encode character)が発生してしまう。

Varidationを強化して対象文字列をはじく方法もあるが、今回はimport-exportを直接を修正して対応できるようにする。

## 環境
　Server側：AWS + ubuntu + NGINX + gunicorn + Django
　アクセス側：Windows PC

## 手順
まずはimport-exportが保存されているsite-packagesの場所を確認する。
わからない場合は[こちら](https://qiita.com/startours777/items/552b6ae5a3ed2915406a)の記事の対処方法2を参考に。

次にExportできるようにする。
\site-packages\import_export\admin.py
```Python
# from_encoding = "utf-8"
from_encoding = "utf_8_sig"
```
```Python
# response = HttpResponse(export_data, content_type=content_type)
response = HttpResponse(export_data, content_type=content_type, charset='utf_8_sig')
```
最後にImportできるようにする。
\site-packages\import_export\tmp_storages.py
```Python
# return open(self.get_full_path(), mode)
return open(self.get_full_path(), mode, charset='utf_8_sig')
```
以上です。

## 補足
次のように記載するサイトもありましたが意図する処理がされなかったため記事にしました。
```Python
class UserAdmin(ExportMixin, admin.ModelAdmin):
...
    base_formats.CSV.CONTENT_TYPE = 'text/csv; charset=CP932'
...
```
ありがとうございました。
フルスタックエンジニアのキャリアパスをchatGPT先生に聞いてみた

フルスタックエンジニアとしてのキャリアパスは多様で、技術的スキル、ビジネススキル、コミュニケーション能力などが組み合わさる形で進行します。以下に一般的なキャリアパスとその各ステージで考慮すべきポイントを示します。

### 初級フルスタックエンジニア
- **主な仕事**: シンプルな機能の開発、バグの修正、ドキュメント作成
- **スキルセット**: 基本的なプログラミングスキル、バージョン管理（Gitなど）、データベース操作
- **成長のために**: メンターを見つけてフィードバックを求める、プロジェクトでの責任範囲を広げる

### 中級フルスタックエンジニア
- **主な仕事**: 複雑な機能の設計と実装、コードレビュー、テスティング
- **スキルセット**: 複数のプログラミング言語とフレームワーク、CI/CD、ユニットテスティング
- **成長のために**: 技術的な知識を深める、コミュニケーションスキルを向上させる、プロジェクトマネジメントの基礎を学ぶ

### 上級フルスタックエンジニア / テックリード
- **主な仕事**: アーキテクチャの設計、チームのテクニカルガイダンス、製品の方向性への影響
- **スキルセット**: システムアーキテクチャ、マイクロサービス、API設計、セキュリティ
- **成長のために**: ビジネスと技術の橋渡しをする、メンタリングとコーチングスキルを磨く

### マネジメント / CTO
- **主な仕事**: 技術戦略の策定、チームや部門のマネジメント、採用、予算管理
- **スキルセット**: ビジネス戦略、プロジェクトマネジメント、財務知識
- **成長のために**: ビジネススキルとリーダーシップスキルを高める、ネットワーキング

### その他の道
- **スペシャリスト**: 特定の技術に深く特化する
- **フリーランス / コンサルタント**: 独立して複数のクライアントと働く
- **教育 / コーチング**: 知識を他人に教える、コースや書籍の作成
- **スタートアップ**: 自分自身または他のスタートアップ企業で働く

フルスタックエンジニアのキャリアは多岐にわたるため、自分自身の興味や強み、キャリアゴールによって、どの道を選ぶかが変わってきます。一方で、どのステージでも継続的な学習と自己啓発、ネットワーキングは重要です。
paiza.ioでelixir その253


# 概要
paiza.ioでelixirやってみた。
練習問題、やってみた。

# 練習問題
gtkwaveのvcdファイルを生成せよ。
3ch、実装せよ。

# 写真

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/18104/c8ecb05a-5b8c-c82f-e519-c27b271a45e2.png)

# サンプルコード

```

defmodule Va do
	use Agent
	def start_link() do
		Agent.start_link(fn ->
			0
		end, name: __MODULE__)
	end
	def get() do
		Agent.get(__MODULE__, fn v ->
			v
		end)
	end
	def inc() do
		Agent.update(__MODULE__, fn v ->
			v + 1
		end)
	end
end

defmodule Main do
    def main(src0, src1, src2) do
        IO.puts "$date"
        IO.puts "  Sat Mar 27 16:11:10 2023"
        IO.puts "$end"
        IO.puts "$version"
        IO.puts "  plunker"
        IO.puts "$end"
        IO.puts "$timescale"
        IO.puts "  1ms"
        IO.puts "$end"
        IO.puts "$scope module test $end"
        IO.puts "$var reg 1 ! a $end"
        IO.puts "$var reg 1 # b $end"
        IO.puts "$var reg 1 % c $end"
        IO.puts "$upscope $end"
        IO.puts "$enddefinitions $end"
        IO.puts "#0"
        IO.puts "$dumpvars"
        IO.puts "x!"
        IO.puts "x#"
        IO.puts "x%"
        IO.puts "$end"
        Enum.map(0..2, fn i ->
	        Enum.reduce(String.split(src0, ""), 0, fn x, n ->
	            if x != "" do
	                Va.inc
	                IO.puts "##{Va.get}"
	                IO.puts "#{String.slice(src0, n, 1)}!"
	                IO.puts "#{String.slice(src1, n, 1)}#"
	                IO.puts "#{String.slice(src2, n, 1)}%"
    	            n = n + 1
    	        else
    	            n
	            end
	        end)
        end)
    end
end

Va.start_link
Main.main("111111111000", "111111000111", "110001111111")



```

# 実行結果

```
$date
  Sat Mar 27 16:11:10 2023
$end
$version
  plunker
$end
$timescale
  1ms
$end
$scope module test $end
$var reg 1 ! a $end
$var reg 1 # b $end
$var reg 1 % c $end
$upscope $end
$enddefinitions $end
#0
$dumpvars
x!
x#
x%
$end
#1
1!
1#
1%
#2
1!
1#
1%
#3
1!
1#
0%
#4
1!
1#
0%
#5
1!
1#
0%
#6
1!
1#
1%
#7
1!
0#
1%
#8
1!
0#
1%
#9
1!
0#
1%
#10
0!
1#
1%
#11
0!
1#
1%
#12
0!
1#
1%
#13
1!
1#
1%
#14
1!
1#
1%
#15
1!
1#
0%
#16
1!
1#
0%
#17
1!
1#
0%
#18
1!
1#
1%
#19
1!
0#
1%
#20
1!
0#
1%
#21
1!
0#
1%
#22
0!
1#
1%
#23
0!
1#
1%
#24
0!
1#
1%
#25
1!
1#
1%
#26
1!
1#
1%
#27
1!
1#
0%
#28
1!
1#
0%
#29
1!
1#
0%
#30
1!
1#
1%
#31
1!
0#
1%
#32
1!
0#
1%
#33
1!
0#
1%
#34
0!
1#
1%
#35
0!
1#
1%
#36
0!
1#
1%
```

# 成果物

https://paiza.io/projects/3hc3Vi45hTt8Y9GX-QGsOA?language=elixir

以上。
複数属性を持つレコードの表現について ゆるコンピュータ科学ラジオ#90を見て

ゆるコンピュータ科学ラジオ#90 を見ていて複数属性を持つデータについて言及されてない設計があったので書きます
[動画はこちら](https://www.youtube.com/watch?v=OsgJuesilg8)

# 性質毎にテーブルを作成する設計
性質毎にテーブルを作成し、そのテーブル内にデータがあればそのデータはそのテーブルの性質を持っているとする設計です

## 例
”語釈がおもしろい” テーブル と ”知らなかった” テーブルを作成
”朝涼” を ”語釈がおもしろい” と ”知らなかった” にINSERTすることでその属性であることを示す

# 題材（第５正規形の表）
動画１１分あたりの第５正規形の表

※単語テーブル
|単語|意味|備考|
|---|---|---|
|朝涼|５月ごろの、朝起きた時の涼しい感じ。|朝寒もある（１０月）|
|揚げ雲雀|空に高く飛び上がるヒバリア。|そんなん載るの？|


※性質テーブル
|単語|性質|
|---|---|
|朝涼|語釈がおもしろい|
|朝涼|知らなかった|
|揚げ雲雀|知らなかった|


# 属性テーブルを作成する設計

※単語テーブル
|単語|意味|備考|
|---|---|---|
|朝涼|５月ごろの、朝起きた時の涼しい感じ。|朝寒もある（１０月）|
|揚げ雲雀|空に高く飛び上がるヒバリア。|そんなん載るの？|

※語釈がおもしろいテーブル
|単語|
|---|
|朝涼|

※知らなかったテーブル
|単語|
|---|
|朝涼|
|揚げ雲雀|


以上のような実装でも複数性質を表現することは可能ですね
レコードが存在するかどうかで性質を特定します

# 水野さんの提案はビットフラグだよね
動画７分あたりからの水野さんの言う小数点を使った設計はビットフラグだよねというつっこみをしようと思ったら動画コメント欄でたくさん指摘されてのでここで言及しなくても良さそうですが
古来からの技だし堀元さんがつっこむだろうな思って見てたら動画の最後まで言及されることがなかったのであえて触れないのかなとか思いましたが、アカデミックにコンピュータを学んだ人間と現場で設計・実装している人間の差なのかもなと思いました



## 正規化によりパフォーマンスが落ちる問題の解決策の一例
パフォーマンスについて言及があったのでそこについて一例だけ設計を書きます
秒単位のリアルタイム性を捨ててJOIN後のレコードを収めるキャッシュテーブルを作る手法です、実装が楽で物理的に切り離すこともできるのでリアルタイム性を捨てて良い状況であれば常套手段かと思います

本件のテーブル例で作成するなら

SELECT * FROM 単語テーブル LEFT JOIN 性質テーブル ON 単語テーブル.単語 = 性質テーブル.単語
として選択したレコードをあらかじめ作成したキャッシュテーブルにINSERTします

※キャッシュテーブル
|単語|意味|備考|性質|
|---|---|---|---|
|朝涼|５月ごろの、朝起きた時の涼しい感じ。|朝寒もある（１０月）|語釈がおもしろい|
|朝涼|５月ごろの、朝起きた時の涼しい感じ。|朝寒もある（１０月）|知らなかった|
|揚げ雲雀|空に高く飛び上がるヒバリア。|そんなん載るの？|知らなかった|

こういったクエリを１分一回とか１０分一回とか定期実行することで検索遅延を軽減することが可能です
本体DBとキャッシュDBを物理的に分けることでCPUやメモリリソースを適切に割り当てることもできます


以上です
パフォーマンスチューニング実践用環境の構築 〜ISUCON本ハンズオン

# 概要
[達人が教えるWebパフォーマンスチューニング〜ISUCONから学ぶ高速化の実践](https://gihyo.jp/book/2022/978-4-297-12846-3)(通称ISUCON本)を読みつつ、
その内容を参考にパフォーマンスチューニング実践用の環境を構築しました。

アウトプットの練習と手順の備忘も兼ねて、その記録を残します。

なおISUCON本の内容およびその感想については、本記事では主題としておりませんのでご留意ください。

# 検証用サーバ(private_isu)構築
[公式リポジトリ](https://github.com/catatsuy/private-isu)に記載のAMI IDを参照してEC2を起動します。

### アーキテクチャ
`x86_64`にしました。
~~(コストを気にして一度`arm64`で立ててみたのですが、Linux用[alp](https://github.com/tkuchiki/alp/releases)でarm64向けのものが見当たらなかったため作り直しました。)~~
筆者が見落としていただけで、arm64向けのものもリリース済みでした。
### インスタンスタイプ
推奨を無視して`t3.micro`にしました。
スペック不足が無視できなくなるごとにスケールアップおよびインスタンスタイプ変更をしていく方針です。
なお`t3.nano`では流石にメモリ不足でMySQLが起動しませんでした。

### ネットワーク設定
SSMでのコンソール接続ではなくSSH接続を使用するため`パブリック IP の自動割り当て`を有効化しました。
個人使用であり、起動のたびにIPアドレスが変わることも許容できることからEIPは使用しません。

セキュリティグループに必要最低限の穴開けを行います。
(筆者は送信元IPアドレスを手元の端末のみに限定し、`ssh`、`HTTP(S)`、`ICMP`でのアクセスが可能となるよう穴開けしました)

# 動作確認
上記条件で起動すれば最低限
* SSH接続できる
* Webアプリケーションが動作する
* WebアプリケーションにHTTP(S)接続できる

ことが確認できるはず。
![スクリーンショット 2023-09-17 22.50.51.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3555024/9399a3f6-fa68-bbfb-fab5-62c2c50423b3.png)
ヨシ！

# 負荷試験環境を用意する
後々ベンチマーカーサーバを別途構築することになると思いますが、ひとまず検証用サーバ内で負荷試験環境を整備します。

### アクセスログの出力形式を調整する
alpでnginxのアクセスログを集計するため、まずはアクセスログの出力形式をJSON形式に変更します。
（詳しい手順は省略します）

### alpをインストールする
アクセスログの集計のため、alpを[公式リポジトリ](https://github.com/tkuchiki/alp/releases)からダウンロードします。
```
wget https://github.com/tkuchiki/alp/releases/download/v1.0.16/alp_linux_amd64.tar.gz
tar xvzf alp_linux_amd64.tar.gz
sudo install ./alp /usr/local/bin
```

### ベンチマーカー(ab)をインストールする
負荷試験実施のため、abをインストールします。
```
sudo apt update
sudo apt install apache2-utils
```

# おわりに
ここまでで最低限パフォーマンスチューニングに着手できる環境が整ったかと思います。
余分な課金防止のためインスタンスを停止し、一息つきましょう。
neosでlogix その144

# 概要
neosでlogixやってみる。
modloader導入してみた。

# 手順

- ダウンロードする。
 NeosModLoader.dll
 0Harmony.dll
- C:\Neos\appにフォルダを2つ作る。nml_modsとnml_libs
- \LibrariesにNeosModLoader.dll設置
- \nml_libsに0Harmony.dll設置
- \nml_modsにmod.dll設置
- 配置
```
C:\Neos\app
│	 Neos.exe
│	 NeosLauncher.exe│
├───\Logs
│	 <Log files will generate here>│
├───\nml_mods
│	 InspectorScroll.dll
│	 MotionBlurDisable.dll
│	 NeosContactsSort.dll
|	 <More mods go here>
├───\nml_libs
│	 0Harmony.dll
└───\Libraries
	 NeosModLoader.dll
```

# 使い方

NeosLauncher.exeを起動しNeosModLoaderにレ点を入れる

# 写真

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/18104/16dfb41b-8557-eef7-f7b3-eaa0bb80db14.png)


以上。
SSHする時に省略可能箇所

# 概要
SSHする際、基本的なコマンドの構造は以下の通りになると思う。
ここでは、Windows環境をもとに実行できるSSHエージェントを利用している。
ユーザー名の省略まではmacでもできるが、パスワード省略は別のSSHエージェントが必要。

```
ssh -i xxx.rsa user@192.160.1.1
その後、パスワードを入力
```
この際、以下の設定を入れていくことで、入力箇所を省略することが可能になる。


# ユーザー名の省略

以下のコンフィグを確認。ない場合は作成する。
```
/Users/ユーザ名（カレントディレクトリ）/.ssh/config
```
基本的なパラメータは以下の通り。
- Host
    - sshで繋ぎたいサイト名
- Hostname
    - 接続先IPもしくはドメイン名
- User
    - ログインユーザネーム
- IdentifyFile
    - 接続先に用いる鍵ファイル

以下のような形で指定できる。

```:.ssh/config
Host remote_pc
    Hostname 10.0.0.1
    User user1
```
これを実施すると、
```
ssh remote_pc
```
で、`ssh user1@10.0.0.1`コマンドと同様のコマンドになる。

また、ワイルドカードを設定することができる。
```:.ssh/config
Host *-group1
    User user2
    Hostname 10.0.0.2
#共通の設定
Host *
    User user1
```
その時にsshを実行すると、以下のように省略できる。
```:実行するコマンド
ssh 10.0.0.1
ssh sample-group1
```
```:認識されるコマンド
ssh user1@10.0.0.1
ssh user2@10.0.0.2
```
このように、`user1`,`user2`が省略できる。

普段指定している鍵がある場合、それも今まで`ssh -i ~~`としていた部分を省略できる。

# パスワードの省略

パスワードの省略には、SSHAgentを利用することで実現が可能である。
これによるメリットは以下の通り。
- 秘密鍵を登録・保持して常駐させる。
- エージェントを起動すると、SSH接続のたびに秘密鍵の指定はいらなくなる。
- SSHエージェント転送を用いれば、踏み台が必要なSSH接続にもエージェント鍵認証が可能
    - scpなどで鍵ファイルを踏み台サーバに送る必要がなくなる。
    - これは、SSHクライアントがエージェントに対して秘密鍵を問い合わせて利用しているため。


## 設定方法
以下のリンク先から、Puttyをインストールする。
自分のPCのbitに合わせた最新版を選択する。ここからは、日本語化されている独自のパッチなどもあり、使用しやすい。

https://ice.hotmint.com/putty/

なお、以下からもインストール可能。

https://www.ranvis.com/putty

展開すると、以下のように様々なツールがあるのを確認できる。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1288524/3b6f9287-c3b2-e0f3-c30b-dd575ae4dd52.png)

例えばPuttygenでは、ssh-kengen のように秘密鍵を生成する事ができる。

## 新規でSSH鍵生成する場合

Puttygenを起動し、パラメータがrsa/2048bitになっていることを確認した後
生成ボタンを押す。
この時、マウスを空白部分で動かす事でランダムシードを生成できるとのこと。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1288524/feadfe14-50cf-79fb-11d5-6f1225c93dfe.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1288524/53d79802-fbfc-ac34-1760-1a4294e470ba.png)

生成されたら、鍵につける名称と、パスフレーズを設定する。
`パスフレーズは鍵の利用に際して必要になるものであり、ユーザーパスワードとは異なる。`
基本的には空のパスフレーズにしない。

Actionから、秘密鍵・公開鍵をPC上に保存する。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1288524/a5aa2e64-59c7-4840-1f8c-e8f259005918.png)

公開下記を接続先のホストに設定する。

内容はここでは省略する。以下のような手順が役に立つ。

https://qiita.com/soushiy/items/fabe64ec382a007a753c#:~:text=Linux%E3%83%A6%E3%83%BC%E3%82%B6%E3%83%BC%E3%81%AE%E8%BF%BD%E5%8A%A0%E3%80%9CSSH%E5%85%AC%E9%96%8B%E9%8D%B5%E7%99%BB%E9%8C%B2%E3%81%BE%E3%81%A7%201%201.root%E3%81%AB%E3%81%AA%E3%82%8B%E3%80%82%202,2.%E3%83%A6%E3%83%BC%E3%82%B6%E3%83%BC%E3%82%92%E8%BF%BD%E5%8A%A0%E3%81%99%E3%82%8B%E3%80%82%203%203%20%E5%85%AC%E9%96%8B%E9%8D%B5%E3%82%92%E3%80%81%E3%83%A6%E3%83%BC%E3%82%B6%E3%83%BC%E3%81%AE%E3%83%9B%E3%83%BC%E3%83%A0%E3%83%95%E3%82%A9%E3%83%AB%E3%83%80%E9%85%8D%E4%B8%8B~%2F.ssh%2Fauthorized_keys%E3%83%95%E3%82%A1%E3%82%A4%E3%83%AB%E3%81%B8%E8%BF%BD%E5%8A%A0%E3%80%82

## Pagentの利用

Pagentでは、複数の秘密鍵を読み込む事が可能である。
読み込む際、パスフレーズを求められる。Pageantで秘密鍵をロードするときに「パスフレーズを記憶する」をチェックしないようにすると良い。

秘密鍵を選択した後、パスフレーズを入力して、Pagentの起動が完了する。
その状態でTeratermであれば、Pagentの利用を選択すると、パスフレーズを省略する事が可能になる。


![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1288524/c9361fa0-e3d0-c33e-0682-72714391d92c.png)