OmniAICreator/Qiita-1.07M huggingface dataset:
SpringBoot + Thymeleaf のページネーションのシンプルなViewサンプル※画面のみ

# 環境
| 名称 | バージョン |
|:-:|:-:|
| Spring Boot | 3.1.4 |
| spring-boot-starter-data-jpa | 3.1.5 |
| thymeleaf | 3.1.5 |
# コード
元のコードから雑に書き換えているので間違っていたらsry。
```TestController.java
  @GetMapping(value = TEST_SEARCH)
  public String showSearchPage(@Validated @ModelAttribute TestSearchConditionsForm conditionForm,
      @RequestParam(name = "page", required = false, defaultValue = "0") int showPage,
      @RequestParam(name = "size", required = false, defaultValue = "20") int showSize,
      BindingResult bindingResult, Model model) {

    // 中略

    // ページネーションの設定
    Pageable pageable = Pageable.ofSize(showSize).withPage(showPage);
    // serviceでデータ取得
    Page<TestForm> TestFormPage = service.searchTest(conditionForm, pageable);
    
    // 中略
    
    model.addAttribute("page", TestFormPage);
    
    // 中略

  }
```
```main.html
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">

<head>
  <!-- 中略 -->
</head>

<body>
  <h1>検索</h1>

  <!-- 検索条件 -->
  <form th:action="@{/test_search}" th:object="${testSearchConditionsForm}" method="GET">
    <!-- 中略 -->
  </form>
  <!-- 検索結果 -->
  <p th:text="'検索結果：' + ${page.TotalElements} + '件'"></p>
    <table id="search_result">
      <tr>
        <!-- 中略 -->
      </tr>
      <tr th:each="_r : ${page.content}">
        <td class="test_code" th:text="${_r.testCode}"></td>
        <td class="test_name" th:text="${_r.testName}"></td>
      </tr>
  </table>
  <div th:insert="~{/page/pagination :: pagination}"></div>
</body>

</html>
```
```pagination.html
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">

<head>
  <title></title>
</head>

<body th:fragment="pagination">
  <ul id="pagination">
    <li>
      <span th:if="${page.isFirst}">≪</span>
      <a th:if="${not page.isFirst}" th:href="@{/test_search(page=0, size=${page.size})}">≪</a>
    </li>
    <li>
      <span th:if="${not page.hasPrevious}">&lt;</span>
      <a th:if="${page.hasPrevious}" th:href="@{/test_search(page=${page.number - 1}, size=${page.size})}">&lt;</a>
    </li>
    <li>
      <span th:if="${not page.hasNext}">&gt;</span>
      <a th:if="${page.hasNext}" th:href="@{/test_search(page=${page.number + 1}, size=${page.size})}">&gt;</a>
    </li>
    <li>
      <span th:if="${page.isLast}">≫</span>
      <a th:if="${not page.isLast}" th:href="@{/test_search(page=${page.totalPages - 1}, size=${page.size})}">≫</a>
    </li>
</body>

</html>
```
# 参考

https://qiita.com/kthksgy/items/4b7142a836c8da062ef8

https://qiita.com/KevinFQ/items/ca68a3001bae19f92879
[Swift] CLIアプリでのasync functionのデバッグにはtop-level-awaitが使える

# 背景

CLIアプリでasync functionをデバッグしたい時

`Task.init`ではクロージャーの終了を待たないので結果が不安定になったり、そもそも結果が出なかったりします。


```swift
func doSomething() async {
    ...
    print("end")
}

Task {
    await doSomething()
}
```

# 解決策

## Swift 5.7以降

top-level awaitが使えます。

```swift
func doSomething() async {
    ...
    print("end")
}

await doSomething()
```

https://github.com/apple/swift-evolution/blob/main/proposals/0343-top-level-concurrency.md

## Swift 5.5.2〜

```swift
func doSomething() async {
    ...
    print("end")
}

@main struct Main {
    static func main() async {
        await doSomething()
    }
}
```

https://github.com/apple/swift-evolution/blob/54d85f65fefce924eb4d5bf10dd633e81f063d11/proposals/0323-async-main-semantics.md
単回帰のまとめ

# 単回帰分析について

単回帰分析は、統計学と機械学習の基本的なテクニックの一つです。この記事では、単回帰分析の概要、用途、実行方法について説明します。

## 単回帰とは

単回帰分析は、1つの説明変数（独立変数）と1つの応答変数（従属変数）の関係を調査する統計的手法です。一般的な単回帰式は以下のように表されます。

$$ y = wx+b $$

- $y$: 応答変数
- $ x $: 説明変数
- $b$: 切片（バイアスともいう）
- $w$: 傾き

## 単回帰の用途

単回帰分析は、以下のような用途で広く使用されます。

- 2つの変数間の関係を理解する
- 予測モデルを構築する
- 因果関係を推定する

## 単回帰の実行

単回帰分析を実行するためには、以下のステップを実行します。

1. データ収集: 説明変数応答変数のデータの組を$N$組 $(x_i,y_i) (ただしi=1..N)$を収集します。
2. モデル設定: $w,b$の値を最急降下法や、最小2乗法を元に決定します。
4. 予測: モデルを使用して新しいデータポイントの応答変数を予測します。

## モデル設定の方法

色々な方法がありますが、ここでは最急降下法と最小2乗法について説明します。

## 最急降下法
最急降下法は直線のフィッティングを行うことを誤差関数を定めて行っています。誤差関数は直線がデータの組に対して、適合するほど誤差関数の値が少なくなるように定義されています。
### 誤差関数

誤差関数は、モデルの予測値と実際のデータポイントの差を評価するために使用されます。通常、平均二乗誤差（MSE）が使用され、次のように定義されます。


$$ E(w, b) = \frac{1}{N} \sum_{i=1}^{N} (y_i - (wx_i + b))^2 $$

ここでは$N$ はデータポイントの数、$y_i$ は実測値、$x_i$ は説明変数の値です。2乗誤差の平均がとられています。

### 更新アルゴリズム
最急降下法は、誤差関数を最小化する $w$ と $b$ の値を見つけるための反復的なアルゴリズムです。このアルゴリズムは偏微分を使用して、誤差関数を $w$ と $b$ について偏微分し、勾配と逆方向に$w$、$b$の値を更新します。

- $w$ についての偏微分：
$$
\frac{\partial E}{\partial w} = -\frac{2}{N} \sum_{i=1}^{N} x_i(y_i - (wx_i + b))
$$

- $b$ についての偏微分：
$$
\frac{\partial E}{\partial b} = -\frac{2}{N} \sum_{i=1}^{N} (y_i - (wx_i + b))
$$

最急降下法は、$E(w,b)$を最小にする$w$と$b$を偏微分を元に求める方法のことです。再急降下法では$w$と$b$を適当に初期化したのちに誤差関数の値を計算し、そののちに以下の更新式を使用して、$w$ と $b$ の値を更新します。

- $w$ の更新：
$$
w_{\text{新}} = w_{\text{古}} - \alpha \frac{\partial E}{\partial w}
$$

- $b$ の更新：
$$
b_{\text{新}} = b_{\text{古}} - \alpha \frac{\partial E}{\partial b}
$$

ここで、$α$ は学習率と呼ばれ、更新ステップの大きさを制御します。適切な学習率を選択することが重要です。

最急降下法は、これらの更新ステップを繰り返して、誤差関数を小さくする $w$ と $b$ の値を見つけます。誤差関数の値が閾値を下回るまで以上のパラメータの更新処理は継続されます。

## 最小2乗法
最小2乗法も偏微分を元に計算を行うため、偏微分を求めるところまでは同一です。誤差関数を最小化するために、上記の偏微分の値がゼロになる$w$と$b$を求める必要があります.

$$\frac{\partial E}{\partial w} = 0$$

$$\frac{\partial E}{\partial b} = 0$$

これらの条件を満たすとき、誤差関数 $E(w, b)$ は最小化されます。この条件を満たす $w$ と $b$ の値を求めると以下のようになります。
- $w$ に関する解

$$w = \frac{\sum_{i=1}^{n} (x_i - \bar{x})(y_i - \bar{y})}{\sum_{i=1}^{n} (x_i - \bar{x})^2}$$

ここで、$\bar{x}$ は $x$ の平均、$\bar{y}$は $y$ の平均です。分散と共分散を用いて表すと

$$ w =\frac{Cov(x,y)}{Var(x)Var(y)} $$

- $b$ に関する解

$$b = \bar{y} - w\bar{x}$$

以上の解析的な解き方はベストな解が一発で求まります。機械学習では最急降下的なアプローチと解析的なアプローチのどちらもで解けることがあります。どちらを用いるかは計算量や必要な精度のバランスを見て決定します。
## まとめ

単回帰分析は、変数間の関係を理解し、予測モデルを構築するための強力なツールです。単回帰モデルを理解し、実行できると、さまざまな分野でデータ分析の力を発揮できます。
AppStoreConnectのTestFlight審査ステータスについて

## 背景
要件：TestFlightで作成したビルドを外部テストに公開したい。バージョンは新バージョンとする。

困りごと：Xcode Cloud経由でビルドを作成して、TestFlight公開しようとしたがステータスが審査待ちとなっていたので次どういうアクションをすれば良いか忘れた。
あと偶にAppStoreConnectのUIも変わることがあるので都度混乱しているのもあるかも。

目的：今まで審査など雰囲気で見ていたので、今回きちんと調べてステータスがどういう状態であるのか確認する。

## ステータスの確認
App および提出物のステータス
https://developer.apple.com/jp/help/app-store-connect/reference/app-and-submission-statuses/

## 結論
審査待ちのステータスの時にできるアクションは待ちになる。
期間はおおよそ半日〜1日程度を見ておく。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/245300/51b28df3-b874-74d0-2ebf-533a8550d8a4.png)
【社内勉強会④】CI/CDについて

# 1. DevOps
## DevOpsとは
DevOpsは、開発と運用を融合させたアジャイルなアプリケーション開発手法です。開発と運用のチームが密接に連携し、アプリケーションのリリースから運用、改善までのライフサイクルを通じて、高品質で迅速なアプリケーションの提供を目指します。
アプリの利便性を高めたい開発者と、安定的な運用をしたい運用者との間で対立が生じてしまうという問題を解決し、コラボレーションを促進します。

***

## DevOpsライフサイクル
![DevOpsライフサイクル](https://storage.googleapis.com/zenn-user-upload/4b4ee8eea0f0-20231102.png)
1. **Plan**
Planプロセスでは、アプリケーションの開発計画が立てられます。このプロセスでは、ビジネス目標や要件を定義し、プロジェクトのスケジュールや予算を策定します。  
   
2. **Code**
Codeプロセスでは、プログラマーがアプリケーションのソースコードを書きます。このプロセスでは、コードの品質や保守性を高めるために、コーディング規約やベストプラクティスに従って開発が行われます。  
   
3. **Build**
Buildプロセスでは、ソースコードをビルドし、実行可能なアプリケーションを作成します。このプロセスでは、自動化されたビルドプロセスを用いることが多く、ビルドエラーを早期に検知することができます。  
   
4. **Test**
Testプロセスでは、アプリケーションをテストします。このプロセスでは、自動化されたテストスイートを用いてアプリケーションの品質を確保します。また、テスト結果は開発チームと運用チームで共有され、必要に応じて修正が加えられます。  
   
5. **Release**
Releaseプロセスでは、リリースするアプリケーションのバージョンを定義し、リリースノートやドキュメントの作成、承認プロセスの実施などが行われます。  
   
6. **Deploy**
Deployプロセスでは、アプリケーションを本番環境にデプロイします。このプロセスでは、自動化されたデプロイプロセスを用いることが多く、デプロイエラーを早期に検知することができます。  
   
7. **Operate**
Operateプロセスでは、アプリケーションを運用します。運用チームは、アプリケーションの稼働状況を監視し、必要に応じて修正や改善を行います。  
   
8. **Monitor**
Monitorプロセスでは、アプリケーションの稼働状況を監視し、問題が発生した場合には迅速かつ正確に対応します。このプロセスでは、監視ツールやログ解析ツールを用いて、アプリケーションの健全性を確認します。

***

# 2. CI/CD
## CI（継続的インテグレーション）
DevOpsライフサイクルにおける**Build～Test**に当たります。
継続的インテグレーションとは、コードに変更が発生するたびに（継続的に）、すぐに共有ソースコードリポジトリに取り込み、自動的にテストや静的解析、セキュリティスキャン、ビルドを行う（インテグレーションする）ことです。
最終的な成果物として、コードを実行可能なモジュールにまとめたもの（アーティファクト）を提供します。
継続的インテグレーションによって、エラーやセキュリティの問題をより簡単に、開発プロセスのかなり早い段階で特定し、修正することができます。

***

## CD（継続的デリバリー／デプロイメント）
DevOpsライフサイクルにおける**Release～Deploy**に当たります。
CIプロセスにおいて、コードがテストされビルドされたら、CDは最終段階で引き継ぎ、どんな環境でもデプロイできるように必要なものをパッケージ化します。CDは、インフラストラクチャのプロビジョニング（ネットワークやコンピューティングリソースなどのリソースを提供できるよう準備すること）から、テスト環境や本番環境へのアプリケーションのデプロイまで、すべてをカバーします。
CDでは、いつでも本番環境にデプロイできるようにソフトウェアが構築されます。その後、デプロイを手動でトリガーするか、デプロイも自動化される継続的デプロイに移行することができます。

***

# 3. GitLab CI/CD
GitLabにはCI/CDを管理・実行するための機能が備わっています。

***

## GitLab CI/CDのアーキテクチャ
### Runner
[公式ドキュメント(日本語訳)](https://gitlab-docs.creationline.com/runner/)

### Executor
[公式ドキュメント(日本語訳)](https://gitlab-docs.creationline.com/runner/executors/)

***

## GitLab CI/CDパイプラインの実行手順
1. Runnerが使用可能であることを確認する
RunnerはCI/CDジョブを実行するエージェントです。
使用可能なランナーを表示するには:
[Settings] > [CI/CD] に移動し、 [Runners] を展開します。

2. ジョブ定義の作成
`.gitlab-ci.yml`ファイルを作成し、CI/CDパイプラインのジョブ定義を記述します。
[.gitlab-ci.ymlのリファレンス](https://gitlab-docs.creationline.com/ee/ci/yaml/)

3. コードの変更のコミットや、Marge Requestのマージ等を実行する
4. 自動的にパイプラインが起動し、`.gitlab-ci.yml`に定義された各ジョブが実行される
生成AIは、勘？

# 今更、AIブームについて

生成AIが発表され、仕事でも使われ始めて、AIばやりになっている。
孫正義さんも、10年後20年後の話を、金魚・サルをたとえ話にして、AIの進化について語っている。

AIというのは、今回が3次ブームらしい。
最初のブームは、推論AIで、チェスなど決められたルールの回答を早く導き出すというAIだった。
これは、ルールが明確になっていて不変であるという前提なので、現実の世界とは全く違う物であった。
次のブームはエキスパートAIで、あらかじめ与えられたデータをもとに答えを導き出すというものであった。
これはあらかじめ与えた知識から選ぶだけなので、全ての正解をあらかじめ蓄積しておく必要があり、すぐに限界にぶつかった。

そして、今回の生成AIと呼ばれるものは、第3次ブームになる。
これは、あらかじめ知識を教えていくだけでなく、自分で学習を続けるというモデルである。
したがって、何らかの回答を導き出す根拠がブラックボックスになって、よくわからなくなっている。

# なんか似てるぞ！

そう！「勘」も今まで経験した様々な体験と今起きていることを、なんとなく結び付けて、
なんとなく「こんな気がする、こうなる気がする」という答えを出したものである。
実は、勘も当たる時は当たる。なぜならば、当てずっぽではなく、説明は出来ないが、複数の状況から判断したものだから。
でも、「勘違い」もある。判断材料とした状況の把握を間違えたり、そもそも関係ない状況を判断材料に加えたりするからである。

たとえば、「赤い車をたくさん見たら、その日は運がいい！」なんて、明かに関連性はないが、
本人の経験として、それが多ければ、関連性があると理解し、無意識のうちに勘の材料になる。
AIも学習材料の中に、赤い車が多いと火事の現場が近いと、赤い車が火事の原因と勘違いするかもしれない。
それが、火事の現場に駆け付けた、消防車とは分からずに。
帽子をかぶった人が多いと、・・・みたいに、本来は無関係なのに、そこに相関を見いだしてしまうかもしれない。

一方で、こんな例もある。
昔流行ったが、おむつとビールを同じ売り場に置くとビールの売り上げが上がるというのがあった。
これは、人の導線をコンピュータが分析し、おむつ売り場に若いお父さんが自分の赤ちゃんのおむつを買いに来ている。
と分析した結果で、正解であった。

# 結局、生成AIの答えは、勘に近づく
これらは、あまりに単純な例だが、こういったことの小さな積み重ねで生成AIは判断するのではなかろうか？

「KKD」＝経験と勘と度胸で判断するのは、ダメな経営者である。
ちゃんとした経営は、データで判断すべきであるといわれて、勘は、避けられている。

しかし、現時点の生成AIは、実は勘に似たものではないだろうか？
生成AIが賢くなればなるほど、人間の勘に近づくのではなかろうか？
生成AIは勘の根拠を説明できるようになるのだろうか？
ST7735SとST7789V2の最小限の初期化を比較して遊ぶ


![o_cop763.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/11377687-561f-1c9e-d30f-4f1dc60d090a.jpeg)

![o_cop764.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/463c340f-6a99-0467-ca4c-1871a3ea46c4.jpeg)

![o_cop765.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/3941271a-9647-f159-d644-79c8987b3ab3.jpeg)


解説

LCD_RESET=1;　の　RESETは、カタカナでリセット
意味は、物理リセット線による。
カラー液晶装置の物理的リセットです。


SOFTWARE RESET　は、カタカナでソフトウエアリセット
意味は、装置内部の論理リセット(初期化)


SLEEP OUTは、カタカナでスリープ　アウトです。
意味は、低電力モードからの起動です。

display onは、カタカナでディスプレー　オンです。
意味は、液晶が動いて画面が表示されます。


RGB-BGR format
RGB mode　　　　　は、カタカナでアールジービ　ビージーアール
　　　　　　　　　フォーマット　アールジービ　モードです。
意味は、カラーの配列を示しています。

Interface pixel format
16bit mode　　　　　　　は、カタカナでインタフェース　ピクセル
　　　　　　　　　　　　フォーマット　ジュウロクビット　モード
意味は、データのカラービットの長さを示しています。

Reverse　は、カタカナでリバース
意味は、カラーの反転です。

ST7735S

```c++

//液晶の初期化処理
void NA_ST7735_P::TXDT144TF_ST7735S_Init(void)
{

  //----------  ST7735S Reset Sequence  --------//

  GPIO_RESET(1);//LCD_RESET=1;

  delay(1); //Delay 1ms

  GPIO_RESET(0);//LCD_RESET=0;

  delay(1); //Delay 1ms

  GPIO_RESET(1);//LCD_RESET=1;

  delay(120); //Delay 120ms

  LCD_Write_CMD(0x01);//SOFTWARE RESET
  delay(50);

  LCD_Write_CMD(0x11);//SLEEP OUT
  delay(200);

  LCD_Write_CMD(0x29);//display on
  delay(100);

  LCD_Write_CMD(0x3a);//Interface pixel format
  LCD_Write_Data(0x05);//16bit mode
  delay(100);

  LCD_Write_CMD(0x36);//RGB-RGR format
  LCD_Write_Data(0x08);//RGB mode
  delay(100);

} //TXDT144TF_ST7735S_Init



```

ST7789V2

```c++

//液晶の初期化処理
void NA_ST7735_P::TXDT144TF_ST7735S_Init(void)
{

  //----------  ST7735S Reset Sequence  --------//

  GPIO_D9(1);//LCD_RESET=1;
  delay(1); //Delay 1ms

  GPIO_D9(0);//LCD_RESET=0;
  delay(1); //Delay 1ms

  GPIO_D9(1);//LCD_RESET=1;
  delay(120); //Delay 120ms

  LCD_Write_CMD(0x01);//SOFTWARE RESET
  delay(50);

  LCD_Write_CMD(0x01);//SOFTWARE RESET
  delay(50);

  LCD_Write_CMD(0x11);//SLEEP OUT
  delay(200);

  LCD_Write_CMD(0x29);//display on
  delay(100);

  LCD_Write_CMD(0x36);//RGB-RGR format
  LCD_Write_Data(0x00);//RGB mode
  delay(100);

  LCD_Write_CMD(0x3a);//Interface pixel format
  LCD_Write_Data(0x55);//16bit mode
  delay(100);

  LCD_Write_CMD(0x21); //Reverse
  delay(100);

} //TXDT144TF_ST7735S_Init


```
[node.js] VS code で Vitest 実行中に break point を仕込む方法

めっちゃ簡単でびっくりした。

## 手順

1. ブレイクポイントをコード上に設定する。
1. メニューから `Debug: JavaScript Debug Terminal` を選択する。
1. shellが開くので、そこで通常通り、`npm run test`を実行する。

以上。
Reactのfavicon、titleの追加

## はじめに
Reactのfavicon、titleの追加方法の備忘録です💁
初心者です😅
間違えてる部分多々あると思います。
もし見つけた場合、ツッコミいただけると助かります🙇


## 内容
Reactのfavicon、titleの追加はReactフォルダの中の「public」の中にある「index html」ファイルを修正することで反映する。
また別のやり方（Helmet）もあるが基本はこれになる。

```html:index html
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <link rel="icon" href="%PUBLIC_URL%/myfavicon2.png" />
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    <meta name="theme-color" content="#000000" />
    <meta
      name="description"
      content="Web site created using create-react-app"
    />
    <title>mysite</title>
    <link rel="apple-touch-icon" href="%PUBLIC_URL%/yourLogo.ico" />
```

:::note info
押さえておくべき点🧠
* 「public」は静的なものを保管してる場所
* faviconの拡張子は「.ico」を使うのがより良い。
:::
作業効率を上げるショートカットキーまとめ(for Mac)

#### 超基礎
- コピー　Cmd+c
- ペースト Cmd+v
- 切り取り Cmd+x
- 全選択 Cmd+A
- 新規ファイル Cmd+N
- 保存 cmd+S
- 名前をつけて保存 Cmd+shift+S
- ファイルを開く Cmd+O
- 新規ウィンドウ Cmd+shift+N
- アプリの切り替え cmd + Tab
- アプリを閉じる cmd + Q


#### 基本的なもの

- spotlight cmd + space
- カナに文字変換 Ctrl + K
- 半角英数に文字変換 Ctrl + ;
- 言語入力の切り替え　Ctrl + space
- 文字を大きくする　Cmd + "+"
- 文字を小さくする Cmd + "-"
- 行の先頭に移動　Cmd + ←
- 行の後ろに移動　Cmd + →
- 最前列に移動　Cmd + ↑
- 最後列に移動　Cmd + ↓
- 単語の先頭に移動　Opt + ←
- 単語の後ろに移動　Opt + →
- 単語を選択 Opt + shift + →/←
- １つ前の状態に戻す Cmd + Z
- １つ後の状態に戻す Cmd + Shift + Z
- キャンセル(ウィンドウを消す)　Esc


- フォームで次の入力欄に移動 Tab
- フォームで前の入力欄に移動 Tab + space
- チェックボックス ON/OFF space


- ページ内検索 Cmd + F
- 検索結果を順番に移動　Enter
- 検索結果を逆順に移動　Enter + space

#### Chrome
- ダウンロードページを開く Cmd + Shift + J
- 履歴ページを開く Cmd + Y
- 設定画面を開く Cmd + ,
- 新規タブ　Cmd + T
- タブを閉じる　Cmd + W
- タブの移動 Cmd + Opt + →/←
- 更新　Cmd + R
- キャッシュクリア更新　Cmd + shift + R
- 印刷　Cmd + P
- ウィンドウを最小化　Cmd + M

### Finder
- 見えないファイルの表示　Cmd + Shift + .

- スクリーンショット撮影　Cmd + shift + 4

カナ文字変換とTabキーが神すぎて10年前に知りたかったです。
【JavaScript・初学者】Reactでよく使われる頻出記法 / 関数について

# はじめに
`React`を学習していましたが、`JavaScript`の記法についてフワッとしている部分がよくあったので、簡単ですが今回は**関数**について少し調べました。

# 関数の種類

```javascript:関数宣言(文)
function func(number) {
  return number + 1
}
```

```javascript:関数式
const func = function (number) {
  return number + 1
}
```

```javascript:アロー関数
const func = (number) => {
  return number + 1
}
```
# 関数宣言と関数式 / アロー関数の違い
明確な違いは、**関数の呼び出しの挙動が異なる**ことです。

`関数宣言`の場合、ブラウザがレンダリングする際に**関数を巻き上げる**ことで、**関数宣言**を最初に読み込みます。

イメージとしては、例えば下記の`関数宣言`がファイルの100行目に書かれているとします。
その際にブラウザが`関数宣言`の場合は、**1行目に巻き上げる**という処理を内部的に行なっています。

```javascript:実際のコード
console.log("50行目")

// 100行目
function func(number) {
  return number + 1
}
```

```javascript:内部処理
// 1行目
function func(number) {
  return number + 1
}

console.log("50行目")
```

その為、ブラウザの挙動によって最終的には**1行目に定義される**事と変わらないので、`関数宣言`で定義した場合は、どこからでも呼び出すことができます。



```javascript:
console.log("50行目")

// 100行目
func(2)
function func(number) {
  return number + 1
}
// => 2
```

```javascript:関数宣言
console.log("50行目")

// 100行目
function func(number) {
  return number + 1
}
func(2)
// => 2
```

一方で`関数式`もしくは`アロー関数`の場合は、`関数宣言`と異なりブラウザの**巻き上げる**対象からは外れる仕様となっている為、定義した後に関数を呼び出さないとエラーになってしまいます。

```javascript:関数式
func(1)
const func = function (number) {
  return number + 1
}
// => Uncaught ReferenceError: func is not defined
```

```javascript:関数式
const func = function (number) {
  return number + 1
}
func(1)
// => 2
```

```javascript:アロー関数
func(1)
const func = (number) => {
  return number + 1
}
// => Uncaught ReferenceError: func is not defined
```

```javascript:アロー関数
const func = (number) => {
  return number + 1
}
func(1)
// => 2
```
Yolactで学習が強制終了し、json.decoder.jsondecodeerror:expecting value: line 1 column 1 (char 0) というエラーが出て学習ができなくなった時の対処法

## 成り行き
yolactで学習中、batch_sizeがデカすぎたのかどうかはわからないが、pcが耐えきれず強制的に再起動になった。その後学習を再開しようとすると、
json.decoder.jsondecodeerror:expecting value: line 1 column 1 (char 0)
というエラーが出て学習できなくなってしまった。

## 原因
yolactフォルダの中のlogsフォルダにyolact_base.logファイル（私の場合）がある。それが前回の学習記録であり、それが原因のようだ。

## 解決方法
yolact_base.logファイルを消せばよい
SHARP Brain のキーボード

#SHARP Brain のキーボード

最近 G5300 を入手して、色々試したら スペースキーないのかよ！
ってことで調べてみようと思いました。

## レイアウト マップ
Google スプレッド シートにアップロードしました。

https://docs.google.com/spreadsheets/d/12qI2mbyxYiBZ0ZUCtft1Jja4Ow7VAdl4ut00bEDaoPs/edit?usp=sharing

## キーコードを取得するやつ
https://turboz.to/sandbox/wince-keyscan.zip
- .exe (Windows および Brain)とソースコードを含みます
- キーを押すとなんか表示します
- マウスクリック(Windows) or 画面タッチ(brain) すると終了します

## 乾草
- SW2 って ファンクションは連続してないし、シフトは CapsLock なのかよ
- そりゃキー アサインを設定したくなりますね。。。
気分の浮き沈みが激しい若手エンジニアが持つ悩みとちょっとした対策

#**はじめに**
こんにちは。今年で入社3年目になる若手エンジニアです。
皆さんは、ミスに落ち込んだり、漠然とした不安感に気が滅入ったりすることはありませんか？
私はまさにこんなタイプです。ミス一つで大きく気分が沈んだり、目の前のタスクに対してを不安を感じて気が滅入ったりします。かと思えば、課題が過ぎ去るとすぐにケロッとしたりします。俗にいう気分の浮き沈みが激しいってやつです。
そんな私が現場に出るようになってから抱える三つの悩みとその対策を書いていきます。
（具体的な原因についてはここでは省きます）

#**その①**
**◎悩んでいたこと**
「小さな間違いでも大きく気分が沈む」
全社会人に共通することですが、極力仕事でミスはしないように努めていると思います。それでも人ですので、どこかしらでケアレスミスなどが発生してしまいます。
私の場合、このミス大小にかかわらず大きく気分が沈んでしまうという悩みを持っています。そのせいで、仕事だけでなく私生活にも影響が出てくる時があります。

**◎対策したこと**
「どこか（誰かに）落ち込んでいることを吐き出す」
私が仕事のミスで気分が沈んでしまったときは、会社の日報提出時に所感として、「今、ミスって落ち込んでます」みたいなことを書いて提出しています。**どうしようもない感情を吐き出すことで気持ちが楽になりました**。もしかしたら、誰かが見て声をかけてもらえるという安心感のようなものもあるのかもしれません。（ある種のかまってちゃんのようですが）

#**その②**
**◎悩んでいたこと**
「やる気にムラがある」
目の前の仕事に対して、不安があるかどうかでその日のモチベーションに大きくムラがあります。
私の場合は、小さなことでも不安を感じてしまうので、モチベーションが低い日が多めです。逆に、順調に進んでいる時は何でもできるかのように感じ、事前にミスに気づいたり、早めの行動ができています。

**◎対策したこと**
「相談して不安を潰す」
モチベーションが低くなるそもそもの原因は、不安を感じていることだと考えました。私が不安に感じていることとして、①自分の認識はあっているのか、②ミスをしてしまうのではないか、という2点が多いです。
そこで、少しでも疑問を感じていることはとにかく相談や認識合わせを行うようにしました。
そうして、自分が感じている不安を潰しています。

#**その③**
**◎悩んでいたこと**
「考え込んで眠れなくなる」
この悩みを抱えている人は少なくないんじゃないかなと思います。
私の場合は、いざ寝ようと思うとその日のミスやこれからのタスクに対しての不安感で眠れなくなることが多くあります。その場で考えたところで何かが解決することは少ないですが、自然と考え込んで眠れなくなります。次の日の体調に大きく影響してしまうので、かなり厄介な悩みです。

**◎対策したこと**
「運動をする」
私が対策として考えたのは、寝る前に考え込める体力を残さないということです。寝れない原因は、ミスを後悔したり、仕事がうまくいくか不安を感じていること（これらの対策は**その②**にて前述したので省きます）ですが、逆に運動して体力を削り、疲れて寝てしまうようにすればいいのでは？と考えました。
そこで、仕事終わりにランニングと軽い体幹トレーニングを始めました。実際、運動したことによる体の疲れを感じて、何かを考える余裕もなく寝れる日が増えました。加えて、ダイエットにもなったので良いことづくめでした。

#**まとめ**
私が持つ三つの悩みとその対策について一つ一つご紹介させていただきましたが、最終的には病院に行って診てもらうことにしました。そこで悩みを話して解決したことがいくつもあります。ただ、どの行動も一つの正解だったと私は思います。

自分で悩みが解決できそうなときは考えてみるのもありだと思いました。でも、頼れるところにはどんどん頼って、少しでも無理をしないでバランスを保って過ごしていこうと思います。



<!--#**悩んでいたこと**
ここでは、私が現場に出るようになってから抱えた悩みを一つずつ上げていきます。

##①小さな間違いでも大きく気分が沈む/ミスしてからの切り替えができない
全社会人に共通することですが、極力仕事でミスはしないように努めていると思います。それでも人ですので、どこかしらでケアレスミスなりが発生してしまいます。私の場合、このミス大小にかかわらず大きく気分が沈んでしまうという悩みを持っています。ミスをした事実を大きく引きづってしまって、切り替えるのが遅いイメージです。

##②不安感で眠れなくなる


##③


#**対策**
ここでは、悩みに対して私が行ったことを挙げていきます。

##①

##②

##③-->
サイトを高速化するといくら儲かるのか見積もってみる

# 結局いくら儲かるか知りたい！

サイトを高速化すると儲かると言うエピソードは聞きます。

でも「じゃあうちのサイトだと具体的にいくら儲かるのさ？」と聞いてもはっきり答えてくれる人がいませんでした。

今回、実際の通販サイトに協力いただき、ページの読み込み時間とCVRの関係を詳しく調査したので、その結果を紹介し、収益増の見積もり方法を考えてみます。

:::note info
**2024年3月21日追記**
この記事で紹介したサイト高速化の成果を事前に見積もるアクセス解析サービスをリリースしました！
ぜひお試しください。
:::

https://qiita.com/miyanaga/items/fc20039f3c3db3c46b79

# 結論

調査対象サイトでは、**高速化により読み込み時間を一律20%短縮できると、売上が14%上がる**見込みです。

いかにこの見積もりの流れを解説します。

# 平均読み込み時間とCVR

セッション平均読み込み時間とCVR(注文成約率)の関係を計測したところ、以下のようになりました。

![セッション平均読み込み時間(秒) と CVR.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/35178/3e767c0a-cc4a-6e01-5887-c1bd2d7cc3b4.png)

CVRは全体で`3.076%`でしたが、セッション平均読み込み時間が

- 1〜1.5秒だとCVRが最大9%に達する
- それ以降は遅くなるほどCVRが低下する
- 4秒を超えるとCVRが2〜2.5%で横ばいになる

ページの読み込みが遅いと露骨に離脱が増える様子がよくわかります。

## 読み込み時間が短すぎてもCVRが低い理由

上のグラフを見て、**1.5秒未満だと逆にCVRが低い**のが気になった方もいるかと思います。「早すぎてもダメ」というのは理屈に合わない気がしますが、これには理由があります。

次は平均読み込み時間と平均PVのグラフです。

![セッション平均読み込み時間(秒) と 平均PV (2).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/35178/fec43f1b-58fa-866b-fd9a-1b547bee0ace.png)

注文まで行き着くには購入手続きが必要なので一定以上のPVが必要です。

さらに購買意欲の高いお客さんは商品を熱心に比較するでしょうから、PVが増える傾向にあります。実際、CVRの高い2秒前後のPV数が多いことからもそれがわかります。

PVが多いと、極端に短い平均読み込み時間を出し続け、平均読み込み時間も極端に短いという可能性はとても低くなります。

逆に直帰であれば、偶然、平均読み込み時間が極端に短いとそれがそのまま平均値になります。

要は生存バイアスの逆のようなもので、極端に短い平均読み込み時間は直帰でないと出にくいため、見かけのCVRが低くなるということです。

# 実際のセッション数の分布

次に平均読み込み時間と、実際のセッション数の分布を見てみます。

![平均読み込み時間(秒) と セッション数.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/35178/f7248c60-fda7-5aae-0458-23787549a7cf.png)

3秒をピークに偏った山型になっていて、遅い方のなだらかな坂は延々と続きます。17.5秒以上が突然上がっているのは、それをギュッと寄せたからですが、それだけロングテールが長いということです。ちなみに17.5秒以上は全体の約5%に相当します。

先ほど平均読み込み時間とCVRの関係では、1.5秒のときにCVRが最大値を示しました。しかし実際のセッション数のピークは1.5秒ではありません。

![セッション平均読み込み時間(秒) と CVR.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/35178/3e767c0a-cc4a-6e01-5887-c1bd2d7cc3b4.png)


そのズレが機会損失となっており、CVRの高い読み込み時間にセッションが集まるほど、収益最大化に迫ります。これがサイトの高速化で収益が上がるということの正体です。

「サイト高速化で収益増」って、話には聞くけど実際に見たことがあるという人は少ないと思います。「やっぱりあるんだ。むしろ絶対にある！」と共感いただけたら幸いです。

# 高速化による収益増を見積もる

もし計測前に時間を戻してサイトを改善し、読み込み時間を一律20%早くできたとします。すると平均読み込み時間によるセッション数の分布はこのように変化します。

![20%改善後 平均読み込み時間(秒) と セッション数  (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/35178/4308e8af-ce39-5d98-c098-41596a983c29.png)

:::note info
この変化によって後のユーザーの行動も変わりますが、その辺は無視します。おそらくポジティブな変化の方が多く結果は上振れすると思われます。
:::

よりCVRの高い平均読み込み時間帯(1.5秒付近)により多くのセッションが集まるので、全体のCVRが改善されます。

これを実際に計算すると以下のようになります。

- 改善前のCVR 3.076%
- 改善後のCVR 3.507%
- 売上 約14%アップ

このサイトではサイトを読み込み時間を20%高速化すると、売り上げが14%上がる見込みがあることがわかりました。

あとは効果がどのくらい持続するかを評価し、広告など他の打ち手と比べて、20%高速化のためのコストが妥当であるか具体的に検討できます。

# もし10%読み込み時間が悪化すると

逆に平均読み込み時間が遅くなってしまうと、収益性は低下します。


# 最後に

いかがでしょうか。ざっくりとした計算ではありますが、サイトの高速化プロジェクトは、見込みや予算なしの勢いで始まることが多かったと思います。

また、「1秒短縮するとCVRがX%改善」のような他社のエピソードもありますが、そういったものを根拠にするよりずっと精度が高いはずです。

サイトを高速化したいが、組織を納得させられない、とお悩みの方はぜひ参考にしてみてください。
VSCodeでSSH先のDockerコンテナの指定ディレクトリを一瞬で開きたい【2023年度版】

# TL;DR
ターミナルから
```bash
$ code --folder-uri vscode-remote://someurl/path/to/directory
```

# これはなに

VSCodeでローカルのファイルを見る時には
```bash
$ code path/to/directory
```
と一瞬で開ける

それに比べてSSH先のファイルを見るとなると左下の緑の><を押して、ホストに接続して、コンテナを開いて、とボタンをポチポチしないと......とぼやいていたのですが、全然そんなことなかったので備忘録

# やり方
1. JSONを見つける
VSCodeは過去に開いたworkspaceをJSONで記憶しています
Macなら`~/Library/Application\ Support/Code/User/globalStorage/storage.json`にあります
2. URIを探す
JSON内にて、
最後に開いたウィンドウ `"lastActiveWindow"` とか
過去に開いたことのある一覧 `"profileAssociations"` とかを見つけてください。
おそらく他の場所にもありますが、とにかく以下のような文字列を探します

最近Remote-SSHを使用してSSH接続をしてなんらかのフォルダを開いたのであれば
`vscode-remote://ssh-remote%2B{.ssh/configに設定したHost名}/path/to/directory`

Dev Containersを使用してDockerコンテナを開いたのであれば
`vscode-remote://dev-container%2{エンコードされた文字列}/path/to/directory`

`vscode-remote://attached-container%2B{エンコードされた文字列}@ssh-remote%2B{.ssh/configに設定したHost名}/path/to/directory`

の場合もあるっぽい

ちなみに、16進数にエンコードされた部分の文字列をデコードして復元すると
```plaintext
{"hostPath":"docker-compose.yamlを置いていたディレクトリへの絶対パス","localDocker":false,"configFile":{"$mid":1,"path":".devcontainer.jsonへの絶対パス","scheme":"vscode-fileHost"}}
```

3.ターミナルで`code --folder-uri + URI`を打つと完成
```bash
# 例
$ code --folder-uri vscode-remote://dev-container%2{エンコードされた文字列}/path/to/directory
```

注意点として、コンテナが起動していない場合はVSCodeが立ち上がったのちDev Containersがエラーを吐きます。再度コンテナを起動させてからやり直すと解消します

# その他

勘の良い方はお気付きでしょうが、`/path/to/directory`で指定するディレクトリを変えると、開くディレクトリを変えることができます

`.zshrc`の例（alias名や関数名は適宜変えてください）
```bash
# 毎回同じディレクトリで足りるやつ
alias remote_host_dir='code --folder-uri vscode-remote://ssh-remote%2B{.ssh/configに設定したHost名}/path/to/directory'

# たまにディレクトリを可変にしたいやつ
open-remote-container() {
    if [ "$1" = "--folder" ] && [ -n "$2" ]; then
        code --folder-uri vscode-remote://ssh-remote%2B{.ssh/configに設定したHost名}/home$2
    else
        code --folder-uri vscode-remote://ssh-remote%2B{.ssh/configに設定したHost名}/home
    fi
}

# 使用例
#   /homeが開く
#   $ open-remote-container
#   /root/some_dirが開く
#   $ open-remote-container --folder /root/some_dir
```

良いVSCode生活を!

# Reference

https://qiita.com/Slowhand0309/items/293fc5db362df9ceba67
2D PSD Importerの調査記録


## 2D PSD Importer
* [公式マニュアル](https://docs.unity3d.com/Packages/com.unity.2d.psdimporter@9.0/manual/index.html)

2D PSD Importerを使用するとレイヤー単位でスプライト化しレイアウト構造そのままにPrefab化してインポートできるようになります。  

注意されたいこととして、`2D PSD Importer`とうパッケージ名なのですが、読み込むファイル形式が`PSD`ファイルではなく、ビックドキュメント形式の`PSB`ファイルになります！  



# 使い方
## .psbファイルの取り込み
パッケージをプロジェクトにインポートすると  
.psbファイルをUnityのAssetsフォルダ内に入れると自動でPrefabが作成されるようになります。  

## レイヤー名は重複してはいけない
重複していてもエラー等は一切表示されないので注意が必要です


## 非対応なもの
- チャネル
- ブレンドモード
- レイヤーの不透明度
- 効果


# Import Settings
特定のレイヤーだけをインポートしないようにするような機能はないようです。  

## Settings タブ
### Layer Import
#### Include Hidden Layers
TrueにするとPSD上で非表示になっているレイヤーもインポートすることができます。  

#### Keep Duplicate Names
スプライト名のみの設定で、プレハブ内のゲームオブジェクト名についてはここの設定に関わらず勝手にリネームされるようです。  

* True
PSDのレイヤー名そのままのスプライト名でインポートされる。  
* False
重複しているスプライト名がリネームされてインポートされす。  
例：「Ribbon」 > 「Ribbon_1」

#### Use Layer Group
`Character Rig > Use as Rig`がTrueのときのみ有効にできます

* True
PSDのフォルダ構造は無視され、表示レイヤーのみがプレハブのトップ階層にインポートされる。  
* False
PSDのフォルダ構造でインポートされる。  

### Character Rig
Texture TypeがMultipleに設定され、Import ModeがIndividual Sprites (Mosaic)のとき使用可能。  

## Layer Management タブ
手動でレイヤー毎に細かく設定ができる。  
後からPSDを修正し再インポートされることを考えると、整合性を保つのが難しくなるのでこちらはイジらないでおいたほうが良いと思われる。  


# 再インポートについて
レイヤーの表示・非表示状態は再インポートのたびにプレハブに追加・削除されるようです。  


# ピボット位置について
プレハブでは有効なテクスチャの中心位置になります。  
PSDでピボット位置を示すレイヤーを作り1ドット打っておいてこれをピボット位置とするのもよいかもしれません。
関数コンポーネントの作り方

# 関数コンポーネントの作り方

- [関数コンポーネントの作り方](#関数コンポーネントの作り方)
  - [関数コンポーネントとは](#関数コンポーネントとは)
    - [Componentモジュールの定義](#componentモジュールの定義)
  - [関数コンポーネントの定義](#関数コンポーネントの定義)
    - [タグに任意の属性を受け取る](#タグに任意の属性を受け取る)
  - [配置場所](#配置場所)
  - [Viewモジュール内の関数コンポーネント](#viewモジュール内の関数コンポーネント)
  - [結論](#結論)

https://hexdocs.pm/phoenix/components.html#function-components

## 関数コンポーネントとは

**関数コンポーネント**とは、heexを返す関数のことである。

具体的には、関数内で<font color="red">**`~H`シジルによって**</font>コンポーネントの構成を定義したものを返すことによって、
**関数を用いてコンポーネントを呼び出す**仕組みのことである。

関数コンポーネントは、**Componentモジュール**内に定義する。

### Componentモジュールの定義

Componentモジュールを定義するには、以下の例のような形式で記述を行う。

```elixir
defmodule SampleComponent do
  use Phoenix.Component

  # 関数コンポーネントを定義
end
```

Componentモジュールには**命名規則がない**ので、用途がわかるようにつける。

## 関数コンポーネントの定義

関数コンポーネントは、呼び出し時にデータを受け取る

以下の例のような形式で定義することができる。

```elixir
attr :name, :string

def sample(assigns) do
  ~H"""
  <button class="bg-blue-500 text-white"><%= @name %><button>
  """
end
````

受け取るデータの型を指定したい場合は、<font color="red">**`attr`マクロ**</font>を使用することができる。

`attr`マクロは、<font color="red">**`attr データ名atom, 型`**</font>と記述して使用する。
(任意の型を受け取る場合は<font color="red">**`:any`**</font>と指定するとよい。)

定義した関数コンポーネントを呼び出す場合は、以下の例のように記述する。

```heex
<SampleComponent.sample
  name={@name}
/>
```

### タグに任意の属性を受け取る

LiveViewでは処理を実行するために、タグに追加の<font>**`phx-click`**</font>や<font>**`phx-target`**</font>などの属性を追加する。

しかし関数コンポーネントは、<font color="red">LiveViewを使用する場合と使用しない場合の両方で呼び出される</font>可能性がある。

この場合は**追加の任意の属性を受け取れるようにする**ことで、対応することができる。

追加の任意の属性を受け取れるようにするには次のように`attr`マクロを記述する。

```elixir
attr :rest, :global,
  include: ~w(phx-click phx-target)
```

<font color="red">**`:global`型**</font>は**HTMLの属性を受け入れる**ことを表し、<font color="red">**`include: ~w()`**</font>で**受け入れる属性リスト**を記述している。

以下のように`~H`シジルに追加することで、関数コンポーネントに追加の属性を受け入れることができる。

```elixir
~H"""
<button class="bg-blue-500 text-white" {@rest}><%= @name %><button>
"""
```

またこの場合の関数コンポーネントの呼び出しは、次のように記述する。

```heex
<SampleComponent.sample
  name={@name}
  phx-clici="push_button"
  phx-target={@myself}
/>
```

## 配置場所

Componentモジュールは基本どこにおいてもよいが、**再利用可能なコンポーネントを提供するという用途がある**ので、`省略Web/components`に配置したほう把握しやすい。

## Viewモジュール内の関数コンポーネント

(LiveViewを使用しない)Phoenixは**Viewモジュール**を使用する。

このViewモジュールは、**テンプレートをレンダリングするための関数**を提供する。

Viewモジュールとは次のように定義することができる。

```elixir
def SampleWeb.ExampleHTML do
  use SampleWeb, :html
end
```

またテンプレートを定義するための関数は、関数コンポーネントと同じである。

Viewモジュールで定義するコンポーネントは、**特定のテンプレートのレンダリングのために提供される**という点で、関数コンポーネントと用途が異なる。

## 結論

関数コンポーネントは次の手順で定義＆呼び出しを行うことができる。

* Componentモジュールを作成
* 関数コンポーネントを定義
* テンプレート内で呼び出す

アプリの外観にマッチしており、使いまわしたいコンポーネントは関数コンポーネントとして定義したい。
【React】100本ノックやってみた #01 Hello World

# はじめに
最近フロントエンドのフレームワークを勉強しようと思い、Udemyで一通り勉強しました。
しかしどうも身についた気がしないのと、もう少し実践的なことをやりたいと思ったため、
@Sicut_study(Watanabe Jin)さんが公開しているReact100本ノックをやってみました。

https://qiita.com/Sicut_study/items/3c5cd798313854a471a0


この記事ではその1本目であるHelloWorldコンポーネントを作成しました。

# ルール
* React, TypeScriptを使う
* その他ツールやライブラリの使用は自由

# 作成するもの
文字列「Hello World」を画面中央に表示するコンポーネント

# 成功条件（抜粋）
> 1. Reactの新しいプロジェクトが正しくセットアップされていること。
> 2. 画面に"Hello World"というテキストが中央に表示されていること。

# 成果物
## 使用技術
* React 18.2.0
* TypeScript 4.9.5
* Chakra-UI 2.8.5


## URL

https://phenomenal-truffle-b0bc4b.netlify.app/

## キャプチャ
### PC
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/622183/663d6d2d-7d2e-d56a-4a71-511e31d50a24.png)

### SP
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/622183/45ce130d-7049-40c6-02f1-398c9be717c0.png)


# 実装手順
## プロジェクトのセットアップ
```bash
# React×TypeScriptのプロジェクト作成
npx create-react-app helloworld --template typescript

# ディレクトリ変更
cd helloworld
```

```bash
# Chakra-UIのインストール
npm i @chakra-ui/react @emotion/react @emotion/styled framer-motion
```

## コンポーネントの作成
```Typescript:App.tsx
import { Center } from '@chakra-ui/react';
import { HelloWorld } from './components/HelloWorld';

const App = () => {
    return (
        // Centerコンポーネントを使ってテキストを画面中央に配置する
        <Center h="100vh">
            <HelloWorld />
        </Center>
    );
}

export default App;
```

```typescript:HelloWorld.tsx
import { Text } from "@chakra-ui/react"

export const HelloWorld = () => {
    return (
        <>
            <Text color="#B83280" fontSize="32px" as="b">Hello World</Text>
        </>
    );
}
```

## デプロイ
NetlifyにGitHubを連携してデプロイ


# さいごに
React初学者のためプロジェクト作成〜アプリ作成〜デプロイの実践的な流れを学ぶことができました。
時間とやる気が許す限りは100本ノックやっていこうと思います。

# 次の記事

https://qiita.com/kmmch/items/c370a5227a0f5bd0fc1b
8th Wall タッチで3Dモデルを回したり大きくしたり動かしたりする xrextras-gesture-detector

`<a-scene>`にxrextras-gesture-detectorコンポーネントを追加すると、3Dモデルに対して様々な操作ができるようになる。

* xrextras-one-finger-rotate - 1つの指でまわす。(Y軸)
* xrextras-two-finger-rotate - 2本指でまわす。(Y軸)
* xrextras-pinch-scale - 2つのタッチ入力に基づいて拡大縮小する。
* xrextras-hold-drag -  1本の指で持ち上げて下にドラッグ/移動。Raycasterの設定が必要。

## 手順
8th WallでA-frameプロジェクトを作成する。

head.htmlにXRExtrasをインポートする。
```html
<meta name="8thwall:package" content="@8thwall.xrextras"/>
```

body.htmlの`<a-scene>`にxrextras-gesture-detectorコンポーネントを追加する。
```html
<a-scene
    xrextras-gesture-detector>
  ...
</a-scene>
```

### xrextras-one-finger-rotate
`<a-scene>`内の3Dモデルのエンティティにコンポーネントを追加する。
```html
<a-entity xrextras-one-finger-rotate gltf-model="#jelly-glb"></a-entity>
```

### xrextras-two-finger-rotate
`<a-scene>`内の3Dモデルのエンティティにコンポーネントを追加する。
```html
<a-entity xrextras-two-finger-rotate gltf-model="#jelly-glb"></a-entity>
```

### xrextras-pinch-scale
`<a-scene>`内の3Dモデルのエンティティにコンポーネントを追加する。
```html
<a-entity xrextras-pinch-scale gltf-model="#jelly-glb"></a-entity>
```

### xrextras-hold-drag
`<a-camera>`を次のように設定する。
```html
 <a-camera
    id="camera"
    position="0 8 8"
    raycaster="objects: .cantap"
    cursor="fuse: false; rayOrigin: mouse;">
  </a-camera>
```
`<a-scene>`内の3Dモデルのエンティティにコンポーネントを追加する。
```html
<a-entity xrextras-hold-drag gltf-model="#jelly-glb"></a-entity>
```

## 参考記事
https://github.com/8thwall/web/tree/master/xrextras/src/aframe#xrextras-gesture-detector

https://www.8thwall.com/8thwall/flyer-aframe/code/

https://www.8thwall.com/8thwall/manipulate-aframe/code/
B2C Commerce 商品にカスタム属性を追加し、値を設定

# システムオブジェクトに属性を追加
管理 >  サイトの開発 >  システムオブジェクトタイプ > （設定するオブジェクト） - 属性定義
新規ボタンを押下

![スクリーンショット 2023-11-08 19.04.38.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2674841/2b505a9b-e89d-9781-39f5-1efcec188947.png)

# 追加した属性をグループ化
管理 >  サイトの開発 >  システムオブジェクトタイプ > 商品 - 属性グループ
グループを追加し、編集
![スクリーンショット 2023-11-09 9.51.46.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2674841/62b5ab29-7001-a832-867e-53cfca0d5d3a.png)

属性グループに属性を追加する
![スクリーンショット 2023-11-09 9.54.07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2674841/add10ddb-bf02-3d62-35fe-d616be857c83.png)

# 特定の商品に属性を追加
マーチャントツール >  商品とカタログ >  商品 > 00001 - 全般
![スクリーンショット 2023-11-09 9.56.31.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2674841/242ce49e-8b2c-18c3-6b34-4b0df53fb0fc.png)

一番下に属性グループと追加した属性の編集ができるようになる。
![スクリーンショット 2023-11-09 9.56.45.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2674841/bf951b46-69cf-1d84-40a1-4257f9dc201c.png)
Gitブランチのマージとコンフリクト解消方法

## Gitブランチのマージとコンフリクト解消方法
前回は、ブランチの作成方法を紹介しました。

今回は、**Gitブランチの変更内容をマージする方法**と、**コンフリクトが発生してしまったときの解消方法**を具体例とともに紹介していきます！


# 1. Gitブランチのマージ
ブランチを**マージ**するときは、<font color="Red">**git merge**</font>を使用します！
現時点のブランチに、指定するブランチの変更内容を**マージ**することができます。

指定したブランチの内容は変更されません。

```bash
git merge <指定するブランチ名>
```

<font color="Red">**注意：必ずマージする前にgit branchコマンドにて現在のブランチ状況を確認するようにしましょう**</font>

# 2. コンフリクトの解消方法

マージを行うと、<font color="Red">**コンフリクト**</font>が発生してしまうことがあります。コンフリクトは、異なるブランチで同じ部分のファイルが変更され、マージを行うと発生します。

コンフリクトを解消するためには、基本的に手動で操作します。コンフリクトが発生しても、冷静に対処できるようにしましょう。

# コンフリクトを解消する例

### 1. mainブランチには、index.htmlファイルに以下の行が含まれているとします。 
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3570986/d185edd7-7701-3b2c-8960-73ffc958d31a.png" width=80%>

### 2. 以下のコマンドにてtest1ブランチを作成し、checkoutコマンドを使用してブランチを切り替えます。
```bash
git branch test1
```
### 3. test1ブランチにて、一行目を以下のように変更し、コミットを行います。
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3570986/37e3eedd-978c-319f-016a-771b6fe72640.png" width=80%>

### 4. mainブランチに切り替えて、1行目を次のように変更し、コミットを行います。
**これにより、mainブランチとtest1ブランチで同じ部分のファイルにて異なる変更がコミットされました。**
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3570986/5514a16d-538b-ea6c-9c91-8478626cda7f.png" width=80%>

### 5. test1ブランチの変更内容をマージしようとするとコンフリクトが発生し、mainブランチのindex.htmlファイルが次のように変更されます。

**上部分は現在のブランチ（HEADブランチ）の内容で、下部分はtest1ブランチの変更内容です。**
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3570986/2115f272-6f40-2e7b-6b2e-2967c7583027.png" width=80%>

### 6. これを手動で修正し、次のようにコミットすることで、コンフリクトが解消され、マージに成功します。
<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3570986/28517cf1-5d4f-47f6-5f5b-257566cca648.png" width=80%>


# まとめ

この記事では、Gitブランチのマージ方法とコンフリクト解消方法について紹介しました！

プロジェクトの管理において、ブランチのマージとコンフリクトの解消は重要なスキルですので、今回紹介した内容を参考にしてください！
Linear Method 私家訳

### あらすじ

[弊社](https://sotas.co.jp/) にて、新進気鋭の [Linear](https://linear.app) というタスク管理ツールを使ってみようということになり、その Linear が実践している Linear Method というものを学ぼうと思って翻訳してみました。

### 免責事項的な

- 以下はあくまで個人的な理解のために翻訳したものです。Linear社は一切関係がありません
- 以下の翻訳の利用は利用者の責任によるとし、翻訳者は翻訳の正しさに責任を持ちません
    - 私は特に英語が得意なわけでもないですし、誤訳が含まれている可能性があります。また、ところどころ意訳が含まれている一方、カタカナ語としてそのままにしているところもあります
- 誤訳、ご指摘大歓迎です。助かります！


# Linear Method

プロダクト作りの実践法

https://linear.app/method

Linear ではソフトウェアは魔法みたいに思えるものだと信じられている。クリエイター自身の才能や、ソフトウェアを作っている間にクリエイター達がどう感じるかにによって、ソフトウェアの品質は左右される。正しくフォーカスし続けるために、Linear の開発においては、以下の事柄が基礎であり、Linear 自身を支える発展的な考え方である。


## Introduction（はじめに）

https://qiita.com/hiraiva/items/ed3c99dcebb7c3dc8571

## Direction（プロダクトやチームの方向づけ）

https://qiita.com/hiraiva/items/c3e3b50645cd287d2605

## Building（実際のプロダクト開発）

https://qiita.com/hiraiva/items/f19359ce07a86ff7d0db?d
【AWS Lambda】ローカル環境でRubyのLambda関数を作成してデプロイする

どうもこんにちは。

今回はローカル環境でRubyコードを書いてLambdaにデプロイしたので、その方法をまとめてみました。

今回はRubyのコードをデプロイすること、RDSの接続情報を所持していること、RDSには以下のようなテーブルデータが入っていることを前提として話を進めていきます。

テーブル名: users
| カラム名 | ID | name | age |
| --- | --- | --- | --- |
| 型 | integer | string | integer |
| データ1 | 1 | 太郎 | 25 |
| データ2 | 2 | 花子 | 23 |

# 手順

## 1. Gemfileを用意する

```Gemfile
source 'https://rubygems.org'

gem 'mysql2'
```

## 2. lambda_function.rbを用意する

```ruby
require 'json'
require 'mysql2'

def lambda_handler(event:, context:)
    { statusCode: 200, body: JSON.generate('Hello from Lambda!') }
end
```

## 3. Dockerfileを用意する

```Dockerfile
FROM public.ecr.aws/sam/build-ruby3.2:latest-x86_64

WORKDIR /var/task

COPY lambda_function.rb /var/task

RUN yum -y install mysql-devel

RUN gem update bundler

RUN bundle install

CMD ["/bin/bash"]
```

## 4. docker buildする

```
$ docker build -t ruby_test_lambda .
```

## 5. dockerコンテナを実行する

```
$ docker run --rm -it -v $PWD:/var/task -w /var/task ruby_test_lambda
```

このコマンドを実行するとbashプロンプトが実行されます。

```
bash-4.2#
```

## 6. bundle installを実行する

```bash
bash-4.2# bundle config set --local path 'vendor/bundle' && bundle install
```

Gemfileのライブラリがインストールされます。

## 7. lambda_function.rbを編集する

```ruby
require 'json'
require 'mysql2'

def lambda_handler(event:, context:)
    user_id = event['Details']['Parameters']['Id']
    client = Mysql2::Client.new(host: <DBのホスト名>,
                                username: <DBのマスターユーザのusername>,
                                password: <DBのマスターパスワード>,
                                database: <アクセスしたいDBの名前>)

    users = client.query("SELECT users.name, users.age FROM users WHERE users.id = #{user_id} LIMIT 1;").to_a

    exe_lambda_name = context.function_name

    if users.empty?
        result = "#{exe_lambda_name}が実行されました。検索されたユーザは見つかりませんでした。"
    else
        result = "#{exe_lambda_name}が実行されました。検索したユーザは#{users[0][name]}で#{users[0][age]}歳です。"
    end

    result
end
```

## 8. デプロイ用zipファイルを生成する

```bash
bash-4.2# zip -r my_deployment_package.zip .
```

## 9. Lambdaにデプロイする

以下の画面のアップロード元をクリックすると、アップロード用の画面が表示されるので、生成したzipファイルをアップロードします。

![スクリーンショット 2023-11-09 11.06.28.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2711491/786faafb-0a70-4da1-c6b0-02f344dc058d.png)

![スクリーンショット 2023-11-09 11.07.21.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2711491/30c2250d-9bd9-1932-79a2-7478ee676ce3.png)

## 10. テスト

イベントJSONに以下のJSONコードを入力してテストを実行します。

```json
{
    "Details": {
        "Parameters": {
            "Id": 1
        }
    }
}
```

以下の結果が出力されていたら成功です。

```
ruby_test_lambdaが実行されました。検索したユーザは太郎で25歳です。
```

# まとめ

dockerコンテナを立ち上げる時に、似たようなイメージを使用してしまうとうまく動作しないので気をつけてください。

必ず、以下のイメージを使用してください。

```Dockerfile
public.ecr.aws/sam/build-ruby3.2:latest-x86_64
```

# 参考サイト

https://docs.aws.amazon.com/ja_jp/lambda/latest/dg/ruby-package.html
本番DBでカラムへnot nullを設定する時の危険性について

先日、　既に本番環境でサービス開始しているデータベースに対して、カラムに「not null」制約を追加したいという事象が発生したのでその危険性について記事を書きました。

この操作は、データの整合性を保つために重要なステップの一つですが、慎重に行う必要があります。以下は、本番データベースで「not null」制約を設定する際に考慮すべきいくつかのリスクです。

データ損失のリスク
既存のNULLデータの扱い：

既存のカラムにNULL値が含まれている場合、それらをどのように処理するかが問題となります。「not null」制約を適用する前に、これらのNULL値を適切なデフォルト値に更新する必要があります。
データ変換エラー：

NULL値を適切な非NULL値に変換する際に、データ型の不整合やフォーマットの誤りなどによってデータ損失が発生する可能性があります。
パフォーマンスの影響
更新のオーバーヘッド：

大量のデータを含むカラムに「not null」制約を適用する際、全てのレコードを更新する必要があります。これにより、システムのパフォーマンスに影響を与える可能性があります。
ロックと可用性：

大規模な変更はテーブルロックを引き起こすことがあり、その間は該当テーブルが利用できなくなることがあります。これにより、本番環境のアプリケーションに影響を与える可能性があります。
アプリケーションの互換性
アプリケーションコードの変更：

「not null」制約の追加により、アプリケーションがデータベースとやり取りする方法が変更される必要があるかもしれません。これにより、追加の開発とテストが必要になります。
エラーハンドリング：

新しい制約が適用された後は、NULL値を挿入しようとするとエラーが発生します。これを適切に処理するためには、アプリケーションのエラーハンドリングロジックを見直す必要があります。
デプロイメント戦略
段階的な実施：

大規模な変更を一度に行うのではなく、小さなステップで順次実施することで、リスクを最小限に抑えることができます。
バックアップと復元：

万が一のために、変更を行う前にデータベースの完全なバックアップを取得しておくことが重要です。
テスト環境での検証：

本番環境に適用する前に、変更をテスト環境で十分に検証し、問題がないことを確認することが不可欠です。
結論
本番環境のデータベースに「not null」制約を追加する際には、データの整合性、パフォーマンス、アプリケーションの互換性、そして適切なデプロイメント戦略を考慮する必要があります。これらのリスクを事前に理解し、適切な計画と準備を行うことで、本番環境でのデータベースの変更を安全に実施することができます。

最後に
エンジニアの皆さん、エンジニア未経験の皆さん、若手エンジニアの皆さん、勉強方法について悩みがあればなんでも気軽に質問して下さい！
これからも記事を書いていきますので、モチベーションアップのためフォロー、イイねお願いします。
本番DBでカラムへnot nullを設定する時の危険性について

先日、　既に本番環境でサービス開始しているデータベースに対して、カラムに「not null」制約を追加したいという事象が発生したのでその危険性について記事を書きました。

この操作は、データの整合性を保つために重要なステップの一つですが、慎重に行う必要があります。以下は、本番データベースで「not null」制約を設定する際に考慮すべきいくつかのリスクです。

### データ損失のリスク

1. **既存のNULLデータの扱い：**
   - 既存のカラムにNULL値が含まれている場合、それらをどのように処理するかが問題となります。「not null」制約を適用する前に、これらのNULL値を適切なデフォルト値に更新する必要があります。

2. **データ変換エラー：**
   - NULL値を適切な非NULL値に変換する際に、データ型の不整合やフォーマットの誤りなどによってデータ損失が発生する可能性があります。

### パフォーマンスの影響

1. **更新のオーバーヘッド：**
   - 大量のデータを含むカラムに「not null」制約を適用する際、全てのレコードを更新する必要があります。これにより、システムのパフォーマンスに影響を与える可能性があります。

2. **ロックと可用性：**
   - 大規模な変更はテーブルロックを引き起こすことがあり、その間は該当テーブルが利用できなくなることがあります。これにより、本番環境のアプリケーションに影響を与える可能性があります。

### アプリケーションの互換性

1. **アプリケーションコードの変更：**
   - 「not null」制約の追加により、アプリケーションがデータベースとやり取りする方法が変更される必要があるかもしれません。これにより、追加の開発とテストが必要になります。

2. **エラーハンドリング：**
   - 新しい制約が適用された後は、NULL値を挿入しようとするとエラーが発生します。これを適切に処理するためには、アプリケーションのエラーハンドリングロジックを見直す必要があります。

### デプロイメント戦略

1. **段階的な実施：**
   - 大規模な変更を一度に行うのではなく、小さなステップで順次実施することで、リスクを最小限に抑えることができます。

2. **バックアップと復元：**
   - 万が一のために、変更を行う前にデータベースの完全なバックアップを取得しておくことが重要です。

3. **テスト環境での検証：**
   - 本番環境に適用する前に、変更をテスト環境で十分に検証し、問題がないことを確認することが不可欠です。

### 結論

本番環境のデータベースに「not null」制約を追加する際には、データの整合性、パフォーマンス、アプリケーションの互換性、そして適切なデプロイメント戦略を考慮する必要があります。これらのリスクを事前に理解し、適切な計画と準備を行うことで、本番環境でのデータベースの変更を安全に実施することができます。

# 最後に
エンジニアの皆さん、エンジニア未経験の皆さん、若手エンジニアの皆さん、勉強方法について悩みがあればなんでも気軽に質問して下さい！
これからも記事を書いていきますので、モチベーションアップのためフォロー、イイねお願いします。
.gitignoreの例外（否定文!)が冗長なのでスッキリさせる。

## 結果
```diff:.gitignore
- /configs/*
- !/configs/alpha
- /configs/alpha/*
- !/configs/alpha/one
- /configs/alpha/one/*
- !/configs/alpha/one/test1.py
- !/configs/beta
- /configs/beta/*
- !/configs/beta/test3.py

+ /configs/**
+ !/configs/**/
+ !/configs/alpha/one/test1.py
+ !/configs/beta/test3.py
```

## 動機

.gitignoreの例外があまりにも長過ぎるのでどうにかできないかと調べた。調査結果をメモ代わりに保存したい。


## 環境
- Ubuntu 18.04 LTS
- git v2.17.1

## 問題

以下のようなディレクトリ構成の時、次のファイルのみを追跡したいとする。
- configs/alpha/one/test1.py
- configs/beta/test3.py

```console
.
└── configs
    ├── alpha
    │   ├── one
    │   │   ├── test1.py
    │   │   └── test2.py
    │   └── test5.py
    └── beta
        ├── test3.py
        └── test4.py
```

このような場合の`.gitignore`の表記は以下のようになる

```.gitignore:.gitignore
/configs/*
!/configs/alpha
/configs/alpha/*
!/configs/alpha/one
/configs/alpha/one/*
!/configs/alpha/one/test1.py
!/configs/beta
/configs/beta/*
!/configs/beta/test3.py
```

確認
```bash
$ git add ./
$ git status
ブランチ master
コミット予定の変更点:
  (use "git reset HEAD <file>..." to unstage)

        modified:   .gitignore
        new file:   configs/alpha/one/test1.py
        new file:   configs/beta/test3.py
$ git reset
```

除外＋例外の追加を繰り返して行っている。

参考：

https://qiita.com/anqooqie/items/110957797b3d5280c44f#%E3%81%82%E3%82%8B%E3%83%87%E3%82%A3%E3%83%AC%E3%82%AF%E3%83%88%E3%83%AA%E4%BB%A5%E4%B8%8B%E3%81%AE%E5%85%A8%E3%83%95%E3%82%A1%E3%82%A4%E3%83%AB%E3%82%92%E7%89%B9%E5%AE%9A%E3%81%AE%E3%83%95%E3%82%A1%E3%82%A4%E3%83%AB%E3%81%A0%E3%81%91%E9%99%A4%E3%81%84%E3%81%A6%E7%84%A1%E8%A6%96%E3%81%97%E3%81%9F%E3%81%84

しかし、この方法は冗長であり、また追加も面倒だ。

## 対策

以下のように変更を行う

```diff:.gitignore
- /configs/*
- !/configs/alpha
- /configs/alpha/*
- !/configs/alpha/one
- /configs/alpha/one/*
- !/configs/alpha/one/test1.py
- !/configs/beta
- /configs/beta/*
- !/configs/beta/test3.py
# 上と同じ例外になる
+ /configs/**
+ !/configs/**/
+ !/configs/alpha/one/test1.py
+ !/configs/beta/test3.py
```

確認
```bash
$ git add ./
$ git status
ブランチ master
コミット予定の変更点:
  (use "git reset HEAD <file>..." to unstage)

        modified:   .gitignore
        new file:   configs/alpha/one/test1.py
        new file:   configs/beta/test3.py
$ git reset
```

同じ結果が得られた。

参考：

https://stackoverflow.com/questions/67975947/how-to-add-an-exception-to-a-deeply-nested-file-in-gitignore

## 例外の追加

また追加したい場合も楽になる。
以下のファイルを追加して、test6.pyのみを追跡したい場合
- configs/gamma/test6.py
- configs/gamma/test7.py

```bash
mkdir configs/gamma/
echo "" >> configs/gamma/test6.py
echo "" >> configs/gamma/test7.py
```

- 従来
```diff:.gitignore
+ !/configs/gamma
+ /configs/gamma/*
+ !/configs/gamma/test6.py
```
- 新規
```diff:.gitignore
+ !/configs/gamma/test6.py
```

確認
```bash
$ git add ./
$ git status
ブランチ master
コミット予定の変更点:
  (use "git reset HEAD <file>..." to unstage)

        modified:   .gitignore
        new file:   configs/gamma/test6.py        
$ git reset
```
asdf-elixir の default-mix-commands で Mix コマンドを自動で実行する


## はじめに

[asdf]（複数のプログラミングツールのバージョン管理ができる便利なプログラム）を用いて関数型プログラミング言語 [Elixir] をインストールするに使う [asdf-elixir] プラグインの機能を一つご紹介いたします。

https://qiita.com/tags/asdf

https://qiita.com/iisaka51/items/eeb3a7fdc2b4f70b2b4f

https://qiita.com/torifukukaiou/items/9009191de6873664bb58

https://qiita.com/mnishiguchi/items/68fb2869110bc823e595

## 結論

ホームディレクトリで `.default-mix-commands` という名前のファイルを作り、その中に [Elixir] がインストールされた直後に自動的に実行してほしい Mix コマンドを列挙します。頻繁に使用されるアーカイブをインストールする場合に特に便利な機能です。

以下は [Phoenix] や [Nerves] を使いたい人向けの設定の一例です。

```bash:$HOME/.default-mix-commands
local.hex
local.rebar
archive.install hex phx_new
archive.install hex nerves_bootstrap
```

各コマンドには自動的に `--force` フラグ が追加されます。

![asdf-elixir-default-mix-commands.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/82804/53970e1b-4fd4-28f0-6bed-756b455363f0.png)

:tada::tada::tada:

## さいごに

若干作業の流れがスムーズになり、より気軽に [Phoenix] アプリや [Nerves] デバイスに取り組めるのではないでしょうか。

本記事は [闘魂Elixir #55](https://autoracex.connpass.com/event/298180/) の成果です。ありがとうございます。

https://autoracex.connpass.com/

https://qiita.com/torifukukaiou/items/1edb3e961acf002478fd

[Mix]: https://hexdocs.pm/elixir/1.16/introduction-to-mix.html
[asdf]: https://asdf-vm.com
[asdf-elixir]: https://github.com/asdf-vm/asdf-elixir
[Phoenix]: https://www.phoenixframework.org/
[Erlang]: https://www.erlang.org/
[Elixir]: https://elixir-lang.org/
[Nerves]: https://github.com/nerves-project/nerves
[Linux]: https://ja.wikipedia.org/wiki/Linux

![toukon-qiita-macbook_20230912_091808.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/82804/fd5c55ec-4fe0-8af6-59bc-bab1ef3d182b.jpeg)
Excelで〇日を含む週からスタートするカレンダーを作る

「うちの会社、15日締だから16日の週から始まるカレンダーをExcelで作りたいんだけど」と言われて作ったので備忘録として残して共有します。
最終的に図のような形になります。

![カレンダ.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/16081/517bfe37-99aa-ba5a-62d9-fe35099e386d.png)

B1～B4のセルには作るカレンダーの設定を入力します。

肝心なのはA7のセルの数式のみです。
```:A7セルの数式
=DATE($B$1,$B$2,$B$3-MOD(WEEKDAY(DATE($B$1,$B$2,$B$3),2)-MATCH($B$4,{"月","火","水","木","金","土","日"},0)+7,7))
```
開始日の曜日から週初め曜日分ずらした日付を表示させます。ずらす日数がマイナスになる場合は7を足す必要があります。IF式で場合分けしてもいいのですが、数式を短くするために7を足して7で割った剰余分をずらしています。

他のセルは簡単です。
```:B7セルの数式
=A7+1
```
B7セルをコピーして、B7～G12にペーストします。

```:A8セルの数式
=G7+1
```
A8セルをコピーして、A9～A12にペーストします。
A7～G12のセルの書式設定で表示形式をユーザー定義にして d と入力します（日だけの表示になります）。

```:A6セルの数式
=A7
```
A6セルをコピーして、B6～G6にペーストします。
A6～G6のセルの書式設定で表示形式をユーザー定義にして aaa と入力します（曜日の表示になります）。

以上です！
複数のコミットを1つにまとめる方法

## 経緯
OJTでアプリ開発をしていた際に、
『〇〇からxxまでのコミットを一つにまとめて再度プッシュして』
とレビューを受けた際に苦戦したので作業メモを残しておくことにしました！


## 必要な拡張機能を追加
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3480176/c2c5ca9c-3b2e-385b-43a7-7479d4be21f6.png)

Visual Studio CodeからこちらのGit Graphという拡張機能を追加しました


## ブログ記事を参考に作業開始

このあたりについてはこの記事を参考にしました
[参考：複数のコミットをまとめる](https://tech.nkhn37.net/git-rebase-vscode-basic/#:~:text=%E3%81%8B%E3%82%8A%E3%81%BE%E3%81%99%E3%80%82-,%E8%A4%87%E6%95%B0%E3%82%B3%E3%83%9F%E3%83%83%E3%83%88%E3%82%92%E4%B8%80%E3%81%A4%E3%81%AB%E3%81%BE%E3%81%A8%E3%82%81%E3%82%8B,-%E6%AC%A1%E3%81%AB%E3%80%81%E8%A4%87%E6%95%B0%E3%82%B3%E3%83%9F%E3%83%83%E3%83%88) 

統合したいコミットたち（赤の四角で囲んだ２つのコミット）の下のコミットを右クリックして
『Rebase current branch on this Commit...』
を選択する
![スクリーンショット 2023-11-09 9.41.24.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3480176/7fd75d57-ae05-a720-e0fe-d829032de142.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3480176/7ba7c952-4100-7c19-e8c5-56db046e68f9.png)

Launch Interactive Rebase in new Terminalにチェックを入れて、rebase開始。

記事どおりにGitLensが開くはず、、、
と思ったら開かなかった。。。

のでvimで作業を継続することにしました


## vimでコミットを統合

![Untitled.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3480176/1832f0cf-91d3-d458-aa4c-f3269aceb06d.png)

実際に作業した際は上の5つを統合しました。
先ほどのGitGlaphのものとは上下が逆になっているみたいです。  
<br>

vimにも慣れていないので、それも込みでメモ
- 『i』でインサートモード   
- 5つのコミットを1つにまとめるために
rails g Model Taskコミットのpickを除いて、下の4つのpickをsquashに変更
- escでインサート解除
- :wqで上書き保存
<br>

※途中で止めるときは:q!でも良いし、中途半端に終えてしまったときは
```

git rebase --abort

```
でリセットできました。

<br>
<br>
ここまで済むとコミットメッセージを編集する画面が出てきました。

![ああntitled.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3480176/b8cc84ba-a3b2-0dbb-8f01-5ac74e05c7ca.png)

スクショし忘れていたので、画像は編集済みのもの。赤い四角の部分に今までの元のコミットメッセージが出てくるので、必要ないものをコメントアウトして、必要なものだけ残して内容を変更しました。

これで上書きすると、５つのコミットが統合されて、コミットメッセージとしては
『ModelTaskを作成してバリデーションとseedsを実装』
となりました。

## 変更をリモートに反映させる
このままpushしようと思ったが、リモートのコミットの構造と違うので衝突が起こって実行できなかった、、
```

git push -f origin HEAD

```
-fオプションをつけることで強制的にプッシュすることができた。今回は一人での開発だったので特に注意もなくできたが、チーム開発時は注意が必要とのこと。


## まとめ
以上でコミットをまとめて、再レビューを上げることができました！めでたしめでたし

もっと良い方法があったらぜひ教えていただきたいです。
MacのMetaTraderのデータフォルダのパス

#### MetaTrader4
/Users/ユーザー名/Library/Application Support/net.metaquotes.wine.metatrader4/drive_c/Program Files (x86)/MetaTrader 4

#### MetaTrader5
/Users/ユーザー名/Library/Application Support/net.metaquotes.wine.metatrader5/drive_c/Program Files/MetaTrader 5

※「ユーザー名」はご自身のものに置き換えてください。