OmniAICreator/Qiita-1.07M huggingface dataset:
PhoenixアプリにTailwindcssを導入してFly.ioにデプロイする方法

**注）以下、tailwindパッケージのバージョンが0.1.4以下が前提です。**

去年12月に[ChrisMccord氏のブログ](https://fly.io/phoenix-files/tailwind-standalone/)で発表されたようにTailwindcssがNode-freeでPhoenixアプリに導入できるようになりました。

それを受け、Tailwindcss + PhoenixでFly.ioにデプロイしてみました。

Tailwindcssが動かず、コミュニティーで[トピック](https://elixirforum.com/t/tailwind-not-working-in-production-no-styles-just-plain-html/45192)を作成したところ、Chris Mccord氏から返答をいただけたので解決方法を共有します。

基本的な設定は[ChrisMccord氏のブログ](https://fly.io/phoenix-files/tailwind-standalone/)でできます。念の為Tailwindcssのバージョンを最新版にしておいてください。

# 結論
Dockerfileで

```:Dockerfile
COPY lib lib
```
を

```:Dockerfile
RUN mix assets.deploy
```
よりも上に記述してください。

app.jsでapp.cssのインポートをコメントアウトしてください。

```javascript:assets/js/app.js
// (追記) tailwindが ~> 0.1.5 の場合はすでにコメントアウトされた状態だと思います
// import "../css/app.css"
```

Chris Mccord氏に回答いただいたのでこのやり方でうまくいくはずです。

# 参考
[トピック](https://elixirforum.com/t/tailwind-not-working-in-production-no-styles-just-plain-html/45192)で[既存のプロジェクトからNPMを消してTailwindcssを動かす方法](https://andrewbarr.io/posts/removing-npm/show)についてご説明されている記事を共有いただきました。既存プロジェクトを今後デプロイする予定の方はご参考にされると良いかもしれません。
Fly.ioでiexが起動できない時の解決方法

Phoenixアプリをfly.ioにデプロイして

```
fly ssh console
```
でFlyのインスタンスのシェルに入った後に

```
app/bin/my_app remote
```
というコマンドでiexシェルに入れると公式で説明されていますが、手順通りにやってもうまくいかず、

```
Could not contact remote node {app_name}@{id}, reason: :nodedown. Aborting...
```
というエラー文が出て失敗します。

[コミュニティー](https://community.fly.io/t/ssh-console-and-checking-app-says-its-down-but-its-not/3534/11)でも同じ経験をしている人が散見されたため、自分がうまくいった解決方法について共有します。

# 結論
env.sh.eexでELIXIR_ERL_OPTIONSの行を消せばとりあえず動きます。

```sh:rel/env.sh.eex
#!/bin/sh

ip=$(grep fly-local-6pn /etc/hosts | cut -f 1)
export RELEASE_DISTRIBUTION=name
export RELEASE_NODE=$FLY_APP_NAME@$ip
#export ELIXIR_ERL_OPTIONS="-proto_dist inet6_tcp" <- commented out
```

ドキュメントではELIXIR_ERL_OPTIONSをつけた形で書かれていたため、気づきづらく罠？かと思いました。

ELIXIR_ERL_OPTIONSはクラスタリングする際に使われるのでしょうか。ご存知の方いらしたらご教授いただければ幸いです。
ADBを使ってスクリーンショットを撮ってPCに取り込む方法

この前にADBのセットアップ方法の投稿をしたので、今回はADBを使ってスクリーンショットを撮り、PCに取り込む方法を書こうと思います。


#スクリーンショットを保存したいフォルダに移動します。

必要ならターミナルを開いて、cdコマンドを使いフォルダ移動します。

```
cd 移動したいフォルダのパス
```

※初心者の方へ、移動したいフォルダをターミナルに向けて、ドラッグ&ドロップするとそのフォルダのパスがわかります。


# Androidの画面をスクリーンショット撮りたい画面にする。
スクリーンショットを撮りたい画面にしておきます。


# スクリーンショットを撮影する
下記のコマンドで撮影できます。

```
adb shell screencap -p /sdcard/screen.png
```

# PCに取り込む
下記コマンドで取り込むことができます。

```
adb pull /sdcard/screen.png
```

最初に移動しておいたフォルダにscreen.pngの名前で保存されています。


以上です。
簡単にスクリーンショットを撮ることがでできるのでおすすめです！
cloud9 トラブルシューティング

## エラーメッセージ : Oops VFS connection does not exist の場合
## エラーメッセージ : Third-party cookies disabled の場合

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/90217/6a52da61-5889-aa14-dea1-0a15229d771d.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/90217/a359363d-1406-9787-0376-d6fa81bbd3d9.png)

うーん、めちゃくちゃ読みづらい。

`Third-party cookies disabled` と書いてあるようです。

### Chrome の場合

設定 → 詳細設定 → セキュリティとプライバシー → サイトと設定 → Cookie とサイトデータ → Cookie をすべて受け入れる

### ブラウザ設定でない場合

[プラグインや拡張機能が悪さをしている場合もあるようです](https://teratail.com/questions/135669)
【Project Euler】Problem 32: パンデジタル数の積

* 本記事は[ProjectEuler](https://projecteuler.net/about)の「100番以下の問題の説明は記載可能」という規定に基づいて回答のヒントが書かれていますので、自分である程度考えてみてから読まれることをお勧めします。

### 問題 32：パンデジタル数の積

原文 [Problem 32: Pandigital products](https://projecteuler.net/problem=32)

**問題の要約：39×186=7254のように1-9のすべてを使った掛け算になる式の積の合計を求めよ（重複は除く）**

いろいろ試してみると右辺の積は4桁、よって左辺は1桁x4桁か2桁x3桁であることが分かります。よって"123456789"の順列すべてを(1,4,4)と(2,3,4)に分割して探します。重複はセットを用いて除きます。

```python
import itertools
ans = set({})
for parr in itertools.permutations("123456789"):
  pstr = ''.join(parr)
  for (la,lb) in [(1,4),(2,3)]:
    a, b, c = int(pstr[:la]),int(pstr[la:la+lb]),int(pstr[la+lb:])
    if a * b == c:
      print(a, b, c)
      ans.add(c)
print(f"Answer = {sum(ans)} ({ans})")
```

（開発環境：Google Colab）
【Project Euler】Problem 31: コインの合計

* 本記事は[ProjectEuler](https://projecteuler.net/about)の「100番以下の問題の説明は記載可能」という規定に基づいて回答のヒントが書かれていますので、自分である程度考えてみてから読まれることをお勧めします。

### 問題 31：コインの合計

原文 [Problem 31: Coin sums](https://projecteuler.net/problem=31)

**問題の要約：1p,2p,5p,10p,20p,50p,£1(100p),£2(200p)のコインを使って£2(200p)にするのは何通りあるか求めよ**

再帰呼び出しでの実装です。使うコインの枚数はリスト**numc**に格納します。リストを引数にすると関数の中で値が変わってしまうので**copy**を使ってコピーを渡すようにしています。特に高速化はしなくても十分早いので行っていません。

このTotal＝10のコードではデバックしやすいように結果のコインリストを表示しています。

```python 
from copy import copy
Total = 10                 # Total amount
coins = [200,100, 50, 20,10, 5, 2, 1]     # Coin values
numc = [0 for i in coins]      # store the number of coin used for each coin

def coinsums(cp, numc, r):
  if cp >= len(coins):   # End of coins
    if r == 0:
      print("#",numc)
      return 1
    return 0
  ret = 0
  for i in range(r//coins[cp], -1, -1):  # Descendint order
    numc[cp] = i
    ret += coinsums(cp+1,  copy(numc), r-coins[cp]*i)
  return ret

# input: coin index, list of num of coin, remaining value
print(f"***Answer = {coinsums(0, numc, Total)}")
# [0, 0, 0, 0, 1, 0, 0, 0]
# [0, 0, 0, 0, 0, 2, 0, 0]
# [0, 0, 0, 0, 0, 1, 2, 1]
# [0, 0, 0, 0, 0, 1, 1, 3]
# [0, 0, 0, 0, 0, 1, 0, 5]
# [0, 0, 0, 0, 0, 0, 5, 0]
# [0, 0, 0, 0, 0, 0, 4, 2]
# [0, 0, 0, 0, 0, 0, 3, 4]
# [0, 0, 0, 0, 0, 0, 2, 6]
# [0, 0, 0, 0, 0, 0, 1, 8]
# [0, 0, 0, 0, 0, 0, 0, 10]
***Answer = 11
```

使うコインのリストを表示する必要がなければ以下の簡単なコードで答えがでます。
```python 
coins = [200, 100, 50, 20, 10, 5, 2, 1]     # Coin values
def coinsums1(cp, r):    # coin pointer, remaining value
  if cp >= len(coins):   # End of coins
    if r == 0: return 1
    return 0
  return sum(coinsums1(cp+1, r-coins[cp]*i) for i in range(r//coins[cp], -1, -1))

print(f"***Answer = {coinsums1(0, 200)}")
```


（開発環境：Google Colab）
SAML RequestとResponseの解析方法

みんな大好きSAML。
Box等のクラウドサービスをADFSとSAML連携してSSOを実装している企業も多いのでは？
先日SSO絡みでトラブルが発生した際にSAML RequestとResponseの解析方法を調べたので、備忘録として残しておく。

#解析手順
**1.Chromeで認証画面を開く**
Chromeで、普段通り認証画面（ユーザIDとパスワードを入力する画面）を開く

**2.F12キーを押してChrome開発者コンソール（DevTools）を開く**
標準だとWebページと同じウインドウ上に立ち上がってしまって見にくい。
下記を押せば、別ウインドウとして切り離すことが出来る。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2492453/4b48657c-bec8-273b-fa1a-87fedbbda9ae.png)

**3.Networkタブを開き、Preserve logにチェックを入れる**
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2492453/81566433-092b-a527-ef14-550655b1dd97.png)

**4.Clearアイコンを押して、ログを一旦クリアする**
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2492453/6b63c8f2-f0d7-330d-ed06-4fa53b88b788.png)


**5.認証画面でユーザIDとパスワードを入力し、いつも通りサインインする**
サインインする事でIdpとSP間で、SAML Request/Responseのやり取りが動く。

**6.適当なところを右クリックして、Save all as HAR with contentをクリックして、HAR形式でログを保存する**
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2492453/d229a209-9a1e-728b-6d28-f1fc0410e1b9.png)

**7.保存したHARログをテキストエディタ等で開く、SAML Request/Responseを見つける**
下記のような形で表示されており、Value部がSAMLメッセージ本体。

```
"queryString":[
    "name":"SAMLRequest",
    "value":"pojWEDjeofiwjeroigneotgiuhtrg・・・"
],
```

**8.取得したvalueを[Google Admin Toolbox](https://toolbox.googleapps.com/apps/encode_decode/?lang=ja)でSAMLデコードする**
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2492453/98862af9-248b-4396-a8ed-192462c0a05d.png)

**9.デコード結果を調査して、何が問題なのか考える**

#SAML Request/Responseが見当たらない
理由はよくわからないけど、MSISSamlRequestやResponseというパラメーターに保管される場合もあるようだ。

```
"Cookies":[
    "name":"MSISSamlRequest",
    "value":"pojWEDjeofiwjeroigneotgiuhtrg・・・"
    ～以下略～
```

この場合、上記のvalueを[Google Admin Toolbox](https://toolbox.googleapps.com/apps/encode_decode/?lang=ja)でBse64デコードを行う。
MSISSamlRequestのBase64デコード結果にはSamlRequest以外にも複数のパラメータがバックスラッシュで区切られて格納されているようなので、
バックスラッシュを目印にSamlRequest本体のvalueを取得してSamlデコードすれば解析できる。

#感想
SAMLはめんどい。
IAM製品を検討しよう。
Ubuntu 20.04 安装 wordpress

### 查看系统版本

```
lsb_release -a

Distributor ID:	Ubuntu
Description:	Ubuntu 20.04 LTS
Release:	20.04
Codename:	focal
```

### 下载并解压

查看 `https://wordpress.org/download/releases/`

```shell
wget https://wordpress.org/wordpress-5.8.3.zip # 下载源码
sudo apt install unzip # 安装 unzip
unzip wordpress-5.8.3.zip # 解压
```

### PHP

```shell
sudo apt install -y php php-fpm php-mysql
sudo apt install php-curl php-gd php-mbstring php-xml php-xmlrpc php-soap php-intl php-zip

php -v
# => PHP 7.4.3 (cli) (built: Nov 25 2021 23:16:22) ( NTS )
```

### MariaDB 数据库

```shell
sudo apt install -y mariadb-server mariadb-client

mysql -V
# => mysql  Ver 15.1 Distrib 10.3.32-MariaDB, for debian-linux-gnu (x86_64) using readline 5.2
```

```shell
sudo mysql -u root -p # 登陆
```

```sql
CREATE DATABASE wordpress DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci;

GRANT ALL ON wordpress.* TO 'wordpress'@'localhost' IDENTIFIED BY 'wordpress';

FLUSH PRIVILEGES;
```

`sudo lsof -Pn -iTCP:3306` 访问端口

`sudo apt install mycli` 也可以安装 mycli，访问 mysql 数据库

### Nginx

```shell
sudo apt install -y nginx

nginx -v
# => nginx version: nginx/1.18.0 (Ubuntu)
```

Nginx 配置文件

```conf
# /etc/nginx/sites-enabled

server {
  listen 80;
  server_name abc.com;
  root <wordpress目录>;
  index index.php index.html index.htm index.nginx-debian.html;

  location / {
    try_files $uri $uri/ =404;
  }

  location ~ \.php$ {
    fastcgi_pass unix:/run/php/php7.4-fpm.sock;
    fastcgi_index index.php;
    fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
    include fastcgi_params;
  }
}

```

### 修改 php 配置文件

`cp wp-config-sample.php wp-config.php`

```php
define( 'DB_NAME', 'wordpress' );
define( 'DB_USER', 'wordpress' );
define( 'DB_PASSWORD', 'wordpress' );
define( 'DB_HOST', 'localhost' );
```

`sudo chown -R www-data:www-data wordpress`

---

参考：

https://www.hostinger.com/tutorials/how-to-install-wordpress-on-ubuntu-using-lamp-stack

https://linuxize.com/post/how-to-install-mariadb-on-ubuntu-18-04

https://github.com/kevinoid/postgresql-for-wordpress

http://www.voidcn.com/article/p-pavmiupn-bqw.html

https://www.digitalocean.com/community/tutorials/how-to-install-wordpress-on-ubuntu-20-04-with-a-lamp-stack
1週間でReact(Next)をキャッチアップした際の学習手順【ほぼリンク集】

## 初めに
今回はタイトルの通り、僕が1週間程度で最低限Reactを使いこなしポートフォリオを作成できるようになるまでに行ったことをまとめようと思います！
Reactといってもクラスコンポーネントと関数コンポーネント(Hooks)がありますが、今回はHooksについてのみ触れます。
最終的なゴールは成果物を作ることで、Next.jsを利用します。

余談になりますが、なぜ1週間という短期間でキャッチアップする必要があったかと言いますと
転職活動の際に第一志望の企業様との最終面接を控えていたのですが体調不良で大幅に延期していただくことになってしまったため、誠意として急いで志望先企業の技術を使いポートフォリオを作成してお出ししたという感じです...笑

<br>

ちなみに僕のスペックは以下の通りです↓

- 最終学歴は美容専門卒
- 未経験からエンジニアに転職、3年目（歴2年3ヶ月程度）
- 業務で用いている技術は主にVue.js（Nuxt.js）,TypeScript


## 対象読者
フロントエンドの基本的な知識はあるがReactは未経験という方に一番適している記事かと思います。
自分が学習する際にClassベースの書き方とHooksの情報が入り乱れておりどこから手をつければ良いか迷ったため記事を書くに至ったのですが、**本記事はHooksを速習したい方のみに向けています。**


## 本題
基本的に自分は動画学習が好きなので、Youtubeのリンクが多めです📺

### 1. Reactの基礎
- [新・日本一わかりやすいReact入門【基礎編】Reactの基礎知識 #1 〜 #9](https://www.youtube.com/watch?v=XKSYF2aZnkQ&list=PLX8Rsrpnn3IWPoM7-1YPDksRRkamRY25k)

### 2. Next.jsの基礎
- [【日本一わかりやすいNext.js入門】#1 〜 #8](https://www.youtube.com/watch?v=uqnSr7LtYGM&list=PLX8Rsrpnn3IUGEyanrHYGjY1WOzNe7Jd-&index=11)

Reactに続きこちらもトラハックさんという方のYoutube講座です🐯
Next.jsの[公式チュートリアル](https://nextjs.org/learn/basics/create-nextjs-app)を元に作られているので英語が得意な方は公式チュートリアルでも良いかもしれません。

全部で10講座ありますが、Nextについてだけ学べば良い方であれば#8までご覧いただけば十分かと思います。
Vercelへのデプロイまで含んでいるので、短期間で成果物を作りたい自分にとても合っていました。

### 3. 成果物用に環境構築
- [Next.jsで作る技術ブログ [Part1 - セットアップ]](https://www.youtube.com/watch?v=5obR4PzQObI&list=PLnAaDnJLkFtJYZLC_93J_9IDN86Bz87b6&index=2)

こちらのYoutube講座はpart4までありますが今回はpart1のみで大丈夫です。
動画からは主にLinter周りのsetupを参考にしました。

該当するChapters📌
> 3:45 ESLint
> 9:17 Prettier

⚠️ TSを用いたい場合の注意点です！
動画には登場しませんが、下記の通りにすればTSの設定を自動で行ってくれます。（収録された時期にはオプションが無かったのかもですね🤔 ）
また動画の通りの設定にするとTSの型チェックが甘めになるので、厳格にしたい方は`tsconfig.json`にて`strict: true` の指定をお忘れなく。

``` bash
npx create-next-app@latest --ts
# or
yarn create next-app --typescript
```

<br>

余談ですが、dockerコンテナを立てたりmysqlを用意したりしたい場合はこちらがとても参考になりました😚
[Docker+Express+MySQLの環境をつくる](https://note.com/kawa1228/n/nb18e19fbf4cc)

### 4. 成果物作成に取り掛かろう！
ここからは上記の1.2.で学んだことを用いてお好きなwebアプリを作成してください！（丸投げ）

自分の場合は特にCSSの技術選定に迷いましたが、Vueでの実装でRSCSSとITCSSを組み合わせての書き方に慣れていたのでCSS Modulesにしました。
（ですが後で調べたら将来的に非推奨になるっぽい？です😂　 
参考：https://github.com/webpack-contrib/css-loader/issues/1050#:~:text=In%20the%20near%20future%20we%20want%20to%20deprecate%20CSS%20modules%2C ）

この辺りは自分も特に詳しくないので有識者の方にコメントいただけるととても嬉しいです...！


## 最後に
僕は公式ドキュメントみっちりとを読み込む精神力を持ち合わせていないタイプで、新しいことを学ぶ際にはとりあえず概要だけサクッと知りたい...と言った心理になります。
そのため、いつもYoutubeやUdemy、またQiita,Zennなどで速習できるような教材をいくつか組み合わせて学ぶのですが、もしかしたら同じ価値観の方の役に立てるのでは？?と考え執筆した次第です。

とはいえ、僕自身もまだまだReact初心者なので間違ったことを言っていた場合はぜひコメントください🙇‍♂️
またQiitaの記事も書き慣れていないので何か問題行為があればこちらもコメントいただけると幸いです、すぐに修正いたします。
最後までお読みいただきありがとうございました！！
共用ファイルサーバが容量不足でつらい時にやるやつ

ファイルサーバの容量が足りないけどディスクの増設が見込めない時の覚書です。
基本的には目視で削除または圧縮をします。

まず、何度もファイルサーバに負荷を掛けると迷惑になるので、とりあえず一覧を csv に吐きます。

```powershell
ls -force -recurse -file \\xxx.xxx.xxx.xxx\share `
    | select lastwritetime,extension,length,Name,Directory,FullName `
    | convertto-csv -nti `
    | out-file share.csv
```

とりあえずこの状態でエクセルで開くと素人でも要らないファイルを探せるようになります。

とはいえ、PowerShell を使いたいので、引き続きサイズの大きい項目を探します。

```powershell
import-csv share.csv | ? extension -ne .zip | ? length -gt 1gb
import-csv share.csv | ? extension -ne .zip | ? length -gt 500mb
import-csv share.csv | ? extension -ne .zip | ? length -gt 100mb
```

見つかった項目を削除または圧縮していきます。
テキスト系は圧縮が効きやすく、1/50 程度になることが期待できます。
圧縮前のファイルは忘れずに削除しておきます。

次に作業履歴系のフォルダを圧縮します。
何らかの作業履歴系のフォルダは、「いつか参照するかもしれない」などの理由で長年保管されている場合が多いです。
また、「削除に慎重な人」の反感を買うので、基本的に削除ができません。
これらのフォルダ群は、大抵 `FullName` が `yyyymmdd` にマッチします。

```powershell
import-csv share.csv | ? { $_.FullName -match "\d{8}" }

# 履歴が溜まっているフォルダを指定して
ls -directory \\xxx.xxx.xxx.xxx\share\hoge\fuga\history `
    | % {
        $z = $_.fullname + ".zip"
        compress-archive -dest $z -path $_.fullname # パスが長すぎると失敗する
        if ($? -and (Test-Path $z)) { rm -force -recurse $_.FullName }
    }
```

残念なファイルサーバには歴史が詰まっていることが多く、割と効果があります。
また、ファイル数が多い場合は、実際のデータ量よりもディスクを圧迫するので、フォルダ単位で圧縮してファイル数を減らすと効果が高いです。
副次的な効果として、ファイル数が減ると csv の見通しが良くなってファイルの整理が捗ります。

最後に`LastWriteTime`を見て、部署で一番古株の人よりも古いファイルの削除を試みます。

```powershell
$old = (date).addyears(-10)
import-csv share.csv | ? { [datetime]$_.lastwritetime -lt $old } | % { rm -force $_.fullname }
```

後で大惨事にならないことを祈りながら実行しましょう。
共用ファイルサーバの寿命が伸びたら良いですね。

このような問題が起こる原因は杜撰なデータ管理と削除ルールの未整備（と年々ファイルサイズが大きくなる問題）ですが、データの管理者とルールの整備責任者は特に困っていないことが多くて救えないですね。
ReactでMUI v5でスタイリングエンジンに`styled-components`を使用するための設定

# TL;DR
### 1. 以下のコマンドを実行してMUIのコアライブラリである`@mui/material`、`styled-components`とラッパーライブラリである`@mui/styled-engine-sc`をインストールします。

```bash
$ yarn add @mui/material @mui/styled-engine-sc styled-components
```

### 2. `package.json`で`@mui/styled-engine`が参照するスタイルエンジンの指定を`@mui/styled-engine-sc`に変更します。

```diff
 {
   "dependencies": {
-    "@mui/styled-engine": "latest"
+    "@mui/styled-engine": "npm:@mui/styled-engine-sc@latest"
   },
+  "resolutions": {
+    "@mui/styled-engine": "npm:@mui/styled-engine-sc@latest"
+  },
 }
```

# 詳細 
### 1. `@mui/material`、`styled-components`とラッパーライブラリである`@mui/styled-engine-sc`をインストールします。

https://mui.com/getting-started/installation/#npm

```bash
yarn add @mui/material @mui/styled-engine-sc styled-components
```

ライブラリをインストールしただけの状態でビルドすると以下のエラーが発生してしまいます。

```
ERROR in ./node_modules/@mui/styled-engine/GlobalStyles/GlobalStyles.js 3:0-40
Module not found: Error: Can't resolve '@emotion/react' in '/app/node_modules/@mui/styled-engine/GlobalStyles'

ERROR in ./node_modules/@mui/styled-engine/StyledEngineProvider/StyledEngineProvider.js 3:0-47
Module not found: Error: Can't resolve '@emotion/react' in '/app/node_modules/@mui/styled-engine/

ERROR in ./node_modules/@mui/styled-engine/index.js 6:0-39
Module not found: Error: Can't resolve '@emotion/styled' in '/app/node_modules/@mui/styled-engine'

ERROR in ./node_modules/@mui/styled-engine/index.js 26:0-62
Module not found: Error: Can't resolve '@emotion/react' in '/app/node_modules/@mui/styled-engine'
```

### 2. スタイリングエンジン変更の設定
リファレンスにも書いてある通りなのですが`styled-components`をスタイリングエンジンに使用する場合はもう一手間加える必要があります。

https://mui.com/guides/styled-engine/

MUIのコアライブラリである`@mui/material`は内部で`@mui/styled-engine`に依存しているのですが、`@mui/styled-engine`のデフォルトの設定ではスタイリングエンジンに`emotion`が指定されているので、スタイルエンジンの指定を`@mui/styled-engine-sc`に変更する様に設定します。

**`@mui/styled-engine-sc`は公式リファレンスの`Installation`セクションに書いてあるように`yarn add`コマンドでインストールするのではなく`package.json`を手書きで以下の様に書き換えて`yarn install`する必要があります。**

```diff
 {
   "dependencies": {
-    "@mui/styled-engine": "latest"
+    "@mui/styled-engine": "npm:@mui/styled-engine-sc@latest"
   },
+  "resolutions": {
+    "@mui/styled-engine": "npm:@mui/styled-engine-sc@latest"
+  },
 }
```

# その他

> ❗ Warning: Using styled-components as an engine at this moment is not working when used in a SSR projects. The reason is that the babel-plugin-styled-components is not picking up correctly the usages of the styled() utility inside the @mui packages. For more details, take a look at this issue. We strongly recommend using emotion for SSR projects.

CSSの名前を動的に決定する仕組みの関係からSSRで使用する場合に正しく動作しないとの事で、SSRで使用したい場合は`emotion`をスタイリングエンジンに使用することを推奨しています。
【Unity】別プロジェクトのGameObjectを完全再利用する

完全に個人用メモです。

A_project で使用した GameObject を再利用して、
B_project でも使えるようにする方法。

# GameObjectの設定等を含めてexportする
Unityの 「Assets」 > 「Export Package」 で再利用したい項目にチェックを付ける。

「Export」をクリック。

任意の名前で保存。

「hoge.unitypackage」が生成される。

# 新規プロジェクト側でimportする
Unityの 「Assets」 > 「Import Package」 > 「Custom Package」
から先程exportしたファイルを選択。

すると、新規プロジェクト側で完全な状態で再利用が可能になります。
python:AWSのRekognitionで画像の数字を読み取る

#目的
・スマホの育成ゲームの結果をデータベースにまとめたい。
・1つずつ手入力するのは手間である。
・AWSに画像上の文字を認識して出力するサービスがあるので利用してみる。
（日本語は無理そうだが、アルファベットや数字は問題なさそう。）
#実行内容
①画像の準備（スマホでスクリーンショットで収集）
②画像の加工（OpenCVで大きさや不要な箇所を隠すなど実施）
→文字認識結果をまとめやすくするため
③AWSのRekognitionを使ってテキスト検出を行う。
④結果をデータベースにまとめる
#記載内容
今回は③のRekognitionのテキスト検出について記述する。
#参考
①Qiita記事（コードの内容）
https://qiita.com/banquet_kuma/items/560787299b83fb924ff7
②AWS_Rekognition公式入門ガイド
https://aws.amazon.com/jp/rekognition/resources/
#テキスト検出結果
######加工した画像
![アグネスタキオン_1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/698556/1cc1c8ec-350c-9810-87c9-236bf8c57349.png)
#####出力結果
![screen.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/698556/f46924a4-8670-946c-95f5-624355caf858.png)
※一番最初には読み込んだ画像名を出力してます。（テキスト検出の範囲外）
　「NN」という文字はどこから検出したか不明ですが、収集後削除すれば良し。
#コード
```python:code
import boto3
import configparser

region = "画像を保存しているS3のRegion"
bucket = "画像を保存しているS3のバケット名"

#アクセスキーが記述されているiniデータから必要な情報を抽出
ini = configparser.ConfigParser()
ini.read("読み込む.iniデータ","utf-8")

access_key = ini["AWS_KEY"]["aws_access_key_id"]
secret_key = ini["AWS_KEY"]["aws_secret_key"]
session = boto3.Session(aws_access_key_id=access_key,aws_secret_access_key=secret_key,region_name=region)

#S3に保存している画像一覧の取得
s3 = session.client("s3")
objects = s3.list_objects_v2(Bucket=bucket)

for filename in objects["Contents"]:

    filename = filename["Key"]
    idname = filename.split(".")[0].split("/")[1]

#idnameは読み込んだデータ名
    data = [idname]
    rekognition = session.client("rekognition")

#テキストの検出
    response = rekognition.detect_text(Image={"S3Object":{"Bucket":bucket,"Name":filename}})
    textDetections = response["TextDetections"]

    for text in textDetections:
        data.append(text["DetectedText"])

#収集した結果を出力
    print(data)
```
#所感
・精度がよくて、満足。
・育成データの手入力が不要って、すごく便利！！
・知らないうちに世の中がさらに便利になっていく、、、驚きです。

※本記事には記載していないが、収集結果をデータベースにまとめて、欲しいデータをSELECT文で抽出してグラフで表示することまで行った。
![test.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/698556/5daac5d0-6b8e-e3ca-e1a9-81da28fb688e.png)

以上。
【OOP】03_カプセル化

こんにちは、コイキングです。

本記事では OOP(Object Oriented Programming == オブジェクト指向プログラミング)の説明のうち、カプセル化について、説明したいと思います。

******
# 1. カプセル化とは？
カプセル化とは関りがあるデータと行為をまとめて、'クラス'という'カプセル'に盛り付け事を意味します。
実はクラス作る際に知らず知らずのうちにカプセル化をしていたとも言えます。

# 2. カプセル化の理由
## 1) コードの活用・管理
例えると犬クラスに翼という属性を定義すると、犬クラスに翼属性があるとは思えないでしょう？
つまり、関りがない属性とメソッドはちゃんと活用されたり、管理されることが難しいでうｓ。
関りがある物だけクラスというカプセルに集めておくとソースコードを再活用・管理する事がより良くなります。

## 2) 情報隠蔽
クラス内に集めておいたメンバー変数とメソッドをどこにでも呼び出せると**クラスの元の設計された意図通り動作しない可能性が高くなります。この様なことを予防するための特性が情報隠蔽**です。
どこにでもメンバー変数とメソッドを呼び出すのではなく**必要な所で決まった方法にたけ呼出すと**クラスの元の設計された意図通りに動作する可能性が高くなります。
Javaでは情報隠蔽をアクセス制御子を用いて実装できます。

## ※ アクセス制御子
### (1) public 
クラス、コンストラクター、変数、メソッドに定義可能、とこにでもアクセス可能。
### (2) default
アクセス制御子を定義しない状態、同じパッケージ内でアクセス可能。
### (3) private
コンストラクター、変数、メソッドに定義可能、同じクラス内部からでのみアクセス可能。
### (4) protected
コンストラクター、変数、メソッドに定義可能、同じパッケージ内 又は継承したクラスからアクセス可能。

```java:Main
public class Main {
	
	public static void main(String[] args) {
		Dog dog = new Dog("Mary", 200, "Akita");
		Bird bird = new Bird("Wings", "Long-beak");
		
		// public 
		System.out.println("Dog's Name : " + dog.name); // アクセス可能。
		
		// default
		//System.out.println("Dog's hp : " + dog.hp);     // 同じパッケージではないためアクセス X
		
		// private
		// System.out.println("Bird's wing : "+bird.wing); // privateのため、アクセス X
		 System.out.println("Bird's wing : "+bird.getWing()); // privateの場合、getメソッドを用いてアクセス
		
		// protected
		System.out.println("Bird's beak : "+bird.beak); // 同じパッケージのため、アクセス O
		
	}
}

```

******

※ 例示コード
https://github.com/leeyoungseung/algorithmBasic/blob/master/algorithm/src/objective/basic03

※ 韓国語のポストは以下のURLで確認できます。
https://koiking.tistory.com/89
リモートでiOS開発(Xcode)をTeamsの遠隔操作を使ってペアプロする

リモート作業でiOSアプリ開発のペアプログラミングをする環境をご紹介します。

# 環境
リモート作業, iOSアプリ開発, Mac, Xcode, Teams


# 手順
1. （ドライバが）Teamsで画面共有をしておく
1. （ドライバが）Xcodeで実装を進める
1. （お互い）同じ画面を見ながらペアプログラミングをする
1. （ナビゲータが画面操作したい時は）Teams画面上部の「制御を要求する」をクリックし、ドライバの画面操作権限を要求する
1. （ドライバが）画面上部の「許可」をクリックすれば、ナビゲータが遠隔操作可能となる
1. （ナビゲータが）ドライバの画面を直接操作する

Teamsの使い方は以下の記事がわかりやすいです。
[Teamsの画面共有の使い方と、共有画面を遠隔操作する方法を解説 | WEB会議DEどうでしょう](https://webmtg-dodesho.com/teams-screen-sharing/)


# 役割

## ナビゲータの役割

以下の解説がとてもわかりやすいので転記させていただきます。
[ペアプログラミングのやり方 - Qiita](https://qiita.com/kanatatsu64/items/3f04d0116e22392efaca#%E5%BD%B9%E5%89%B2-1)

* プログラムの大局的な構成を考える
* テストを書く
* ドキュメントを書く
* ドライバの疑問をググる
* ドライバが書いたプログラムをレビューする

(以上に加えて)

* プログラムの局所的なアルゴリズムを考える
* レビューを積極的に行う(付きっぱなしでも良い)
* 関連するtipsを教える
* (一緒にプログラムを書く)

## ドライバの役割

* 実装する


# 注意点
* 同じOS同士でないと、遠隔操作はうまく動かなかったです
    * （私が試した環境では、WinとMacでの遠隔操作は出来なかった）
* 時間は決めて休憩をとりましょう
    * （時間を決めておかないとエンドレスになり、お互い疲れ果てます）


# その他参考サイト
* [プログラミング未経験者とリモートペアプログラミングをしてみた | DevelopersIO](https://dev.classmethod.jp/articles/try-remote-pair-programming/)

# ペアプロの振り返り

約1ヶ月ペアプロを続けて振り返りを行なったところ、かなり好評でした。
「なんで今までやらなかったんだろうと思うぐらいやって良かった」という声もあり、始めた甲斐もありました。
ペアプロには賛否両論あると思いますが、個人的にはやって良かったかなと思います。

以下は振り返りの抜粋です。

## 良かったこと
- 分からないことが相談することですぐに解決できた
	- 一人で悶々と考えるよりも解決が早かった
- 雑談がしやすかった
	- リモートで一人でやるよりもコミュニケーションをとりやすい
- 教育
	- 社内教育としてペアプロは適している
	- チーム内での考え方、方向性の統一がしやすい
- 品質
	- 一人で考えるよりも正しい方向に進みやすい
	- 声に出すことで客観的に自分を見れる
- コミュニケーション
	- リモート環境でのコミュニケーションに最適
	- 雑談がしやすい
	- チームでの一体感が生まれる

## 悪かったこと
- Teamsの遠隔操作が私の環境からは出来なかった
	- 謎の解明が必要
	- ナビゲータは遠隔操作を出来たのに、ドライバー側からの遠隔操作が出来なかった
- ペアプロをやって悪かったことが思い浮かばない
	- （ドライバにとっては良いことずくめ）
- ナビゲータの作業時間が奪われる

## こうすれば良かったこと
- 時間が足りなかった
	- 30分ではもの足りない
	- 最低１時間は欲しい
- もっとペアプロをできる人を増やしたい
	- 個人のやる気、チーム全体の雰囲気、組織の仕組みが必要
        - [自走するエンジニアが育つ組織の作り方 - tebiki-techblog](https://techblog.tebiki.co.jp/self-drive-engineer-510b3c567bfd)
	- モブプロをもっとやりたい

## ペアプロをやった感想
- なんで今までやらなかったんだろうと思うぐらいやって良かった
	- 今後も絶対やった方が良いと思う
	- 特に現場に入ったばかりの人にはペアプロをやった方が良い
- ペアプロ最強
	- モブプロはもっと最強
- リモート環境なら尚更ペアプロをやるべき
	- ストレス発散にもなる
- 何よりもペアプロをやって楽しかった
	- おそらくこれが一番大事
remote: HTTP Basic: Access denied fatal:Authentication failed for エラー

#概要
開発環境のgitをsoucetreeにクローンしてきて、プッシュしようとした際にタイトルのエラーが発生しました。

エラー文を見るに認証がうまくいってないようなのですが、とりあえずエラー文コピペで検索していると認証情報の削除を推奨している記事が多かったです。
今回はその対応で解決できなかった方のために。

#原因
自分の場合はsoucetreeに登録しているリモートリポジトリのパスが異なっていることが原因でした。
初歩的過ぎて、記事が無かっただけかもしれません…。

#対処
soucetreeのリモートリポジトリを正常なパスに修正します。
右上にある設定からパスを選択して、編集してください。
自分の場合は「https〜」になっていたところを「git@〜」に修正しました。
![スクリーンショット 2022-01-16 15.29.02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1340120/75834c59-f4c4-ae17-64ae-190fcbc5616e.png)
【Ruby】条件分岐  if文　gets  to_iメソッド

※初心者向け
※アウトプット練習の為

開発環境
rails 6.0.4.4
ruby 2.6.5

##問題内容
ターミナルから数字を入力して、数字に応じて以下のように出力するプログラムを書いてください。

**・10以下なら10以下の数字です**
**・10より大きい数値なら10より大きい数字です**
**・10以下でかつ0以下なら0以下の数字です**

ソースコードは以下の雛形を使ってください。

```ruby
input = gets.to_i

# ここからソースコードを書いてください
```

##解答

```ruby
input = gets.to_i

if input <= 0
  puts "0以下の数字です"
elsif input <= 10
  puts "10以下の数字です"
else
  puts "10より大きい数字です"
end
```

##解説
**①ターミナルから数値を入力する書き方**
**②条件分岐の書き方**
の2つに分けて解説します。

**①ターミナルから数値を入力する書き方**
ターミナルから数値を入力するには**gets**というメソッドを使います。この**getsメソッド**を使って入力した値は全て文字列になります。そのためターミナルでは数字を入力しても、プログラムで使うときには文字列に変換されてしまいます。

そこで**gets**の値を**to_iメソッド**を使って数値に変換します。

```ruby
input = gets.to_i
```

**②条件分岐の書き方**
条件分岐はif文を使います。今回は3つのパターンで条件を分けるため、**elsif**と**else**も使います。

```ruby

if 条件1
  # 条件1のときの処理
elsif 条件2
  # 条件2のときの処理
else
  # 条件3のときの処理
end
```

今回の条件は数値の比較です。比較には**<**や**==**などの比較演算子を使います。
今回は10以下や0以下という比較なので、**<=**を使います。 **=**を付けた場合は以下や以上という意味になります。

```ruby
input <= 10
```

今回の問題で難しいのは、**3つの条件のうちどの条件から記載するか**ということです。
if文は先に書いた条件から判断していきます。そのため上の条件に当てはまったら、たとえ下の条件に当てはまっても、下の条件の処理はスルーされます。

今回の問題で以下のように書くとどうなるか考えてみましょう。

```ruby
if input <= 10
   puts "10以下の数字です"
elsif input <= 0
  puts "0以下の数字です"
end
```

このとき、inputが-1だったとすると、最初の条件式にも当てはまってしまい、**10以下の数字です**と出力されます。本来は**0以下の数字です**と出力されなければいけません。

よって正解は条件式の順番を入れ替えた以下になります。

```ruby
if input <= 0
 puts "0以下の数字です"
elsif input <= 10
 puts "10以下の数字です"
end
```
10以下でなければ10より大きいため、10より大きい数値の場合の条件は**else**のあとに書きます。

```ruby
if input <= 0
 puts "0以下の数字です"
elsif input <= 10
 puts "10以下の数字です"
else
 puts "10より大きい数字です"
end
```
以上です。
仮想環境上で構築されたドメインコントローラ運用の注意事項

#はじめに
WindowsServer2012以降のOSで構築されたドメインコントローラは仮想環境に対応していると色々な文書に記載されています。ただし、仮想環境上でドメインコントローラを構築する場合構成によってはActiveDirectryじたいが正常に動作しなくなるケースがあります。今回はその点について記載したいと思います。

#そもそも仮想環境に対応したとはどういうことか？
ActiveDirectryは、複数のドメインコントローラ間で双方向にデータベースを複製しながら動作しています。WindowsServer2012以前のドメインコントローラを仮想環境上で仮想環境で構築している場合、その仮想マシンをスナップショットを利用して復元した場合、「USNロールバック」というデータベースの不整合が発生してしまう仕様でした。WindowsServer2012以降では、スナップショット復元時の不整合問題が発生しないよう実装が変更されました。これが**ドメインコントローラが仮想環境に対応した**と言われている内容となります。

#USNロールバックが発生しない仕組み
仮想マシン上で構築されたドメインコントローラは、仮想マシンの属性「VM-GenerationID」の後をを常に参照しています「VM-GenerationID」はスナップショットで復元された場合に値が変更されるため、ドメインコントローラはスナップショットで復元されたものと判断し「権限のないリストア （non-authoritative restore）」のリカバリーが自動実行され、他のドメインコントローラからの複製待ち状態となり、他のドメインコントローラから複製が完了する事で整合性がとれた状態で復旧されるという仕組みとなります。

逆に言うと、他のドメインコントローラから複製がされるまでは、正常に機能しない事を意味します。

#市販のバックアップソフトでバックアップを取得した場合
仮想環境のバックアップには、ARCServeUDPやAcronisなどのイメージバックアップソフトが主流です。
ただし、どのバックアップソフトでも各ハイパーバイザーのスナップショット機能を使用してバックアップイメージを作成するため、バックアップソフトを用いてリストアしたした場合も上記の仕様にてリカバリーが実行されます。

※各バックアップソフトの仕様についてメーカーの仕様をご確認ください。

#仮想環境上で構築する場合の注意点
ようやく本題となりますが、上記で説明したように仮想環境上でのスナップショットの復元は、複製パートナーのドメインコントローラが存在する事が大前提となります。そのため全てのドメインコントローラを仮想環境上に構築する場合は注意が必要です。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/124085/47585fa3-f85f-e10e-7561-b053e92065e2.png)

上記はシンプルな例として、1台の仮想ホスト上に2台のドメインコントローラの仮想マシンを構築した場合の図です。仮にこの仮想ホストに障害が発生し、仮想マシンのリストアが必要となった場合2台ともリストアされた事によりお互いのドメインコントローラが複製待ちとなり永久に復元されない状態となります。

通常仮想ホストは冗長化されますがそのためには共有ストレージを用います。共有ストレージは冗長性が高いため可能性は低いですが、上記と同じような状態となる可能性はゼロではありません。

そのため、**安全面を優先するのであれば**物理サーバと仮想環境のそれぞれにドメインコントローラを構築したり、BCPとして遠隔地にドメインコントローラを設置する事が推奨となります。

#同一仮想環境上で構築する場合の対処方法

コストや環境面の理由で、同一仮想環境上にドメインコントローラを構築しなければならない場合、WindowsServer標準のバックアップツールである**「WindowsServerBackup」**の機能である「システム状態」のバックアップを用いる事で対処が可能となります。「システム状態」を用いると「権限のあるリストア (Authoritative Restore)」でのリストアが可能となり手順は複雑になりますが、バックアップ取得時点のデータベースを正としてActiveDirectry環境を復旧する事ができます。
VBAでSFDCのオブジェクト一覧と定義を取得

###要件
SFDCのSandboxまたProductに接続して、Excelに主なオブジェクトの一覧と明細を取得したい
#####オブジェクト一覧
[image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/801991/87cdb2cc-d8d9-b43e-8883-f5758845968b.png)![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/801991/1a3e6a1a-8886-4b99-84cc-1c2d58ea3d50.png)
#####オブジェクト定義
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/801991/42670af4-8cd1-14d3-b17b-6eb6f7e4ed26.png)




###操作説明
####設定
　Sandbox：https://test.salesforce.com/services/Soap/u/52.0
　Product: https://login.salesforce.com/services/52.0 
  ログインID：ｘｘｘ
　ログインパスワード：xxx
　　※パスワードの後ろにTokenを付ける場合がある
　Proxy設定：あれば
####一覧取得
　ディフォルトはカスタマイズオブジェクトだけを取得される
　標準オブジェクトを取得したい場合、セールC3にセミコロンつけで名前を記述する
####定義明細
　一覧のNameをクリックすると、最初の場合オブジェクト定義明細シートを生成される。
　すでに定義明細がある場合、Jumpだけです。再取得したい場合、既存の定義明細を改名するかまた削除する。
###マクロ添付（ご自由に使ってください）
https://drive.google.com/file/d/1E3_evMYUxxA2wy5whHg2OYp6JVILMJAf/view?usp=sharing
円の方程式/円周率/ルート/切り捨て/切り上げ(Ruby)

Ruby３.1
<a href = "https://docs.ruby-lang.org/ja/latest/method/Math/c/PI.html">MathモジュールPI</a>
<a href = "https://docs.ruby-lang.org/ja/latest/class/Math.html#M_SQRT">Mathモジュールsqrt</a>
<a href = "https://docs.ruby-lang.org/ja/latest/method/Float/i/floor.html">Floatクラスfloor</a>
<a href = "https://docs.ruby-lang.org/ja/latest/class/Float.html#I_CEIL">Floatクラスceil</a>


xy軸の座標で（0,0）を中心点とする
円の方程式　 x² × y² = 半径²

```ruby
#円周率
p = Math::PI
puts p
# => 3.141592653589793

#平方根を求める方法:√２の場合
Math.sqrt(2)
# => 1.4142135623730951

#小数点以下切り捨て
p.floor
# => 3

#小数点以下切り上げ
p.ceil
# => 4
```
[Kotlin]lazyとlateinit

## この記事は
iOSに最近触れる機会があって、lazyプロパティに沢山出会いました。
その際に、改めて普通の宣言と何が違うのだろう？と疑問に感じました。
それを解消させる記事にしたいと思います。

## 初期化の遅延とは？
文字通り、初期化の「遅延」を実現してくれます。

kotlinだと、初期化を遅延する言語仕様は二つありますね。
`lateinit`が`var`、`non-null`で宣言し、予約語の型が使えないなどの制約があります。
`lazy`の方は、`val`、初期化後は同じ値を返し続けるなどの制約があります。

```kotlin
private lateinit var sonic: Sonic
private val speed: Int by lazy { 1000 }
```
このような宣言をすることで、これらの値は最初の呼び出し時に初めて初期化することが出来ます。

## 使いどころ
文法的な事は掴めても、それの何がいいの？というのがあるあるかなと思います。

### 重いプロパティがあるとき便利

初期化するのに計算コストが割とかかってしまうもの関しては、やはり遅延させた方がパフォーマンスとしては良いと思います。
これは、他のオブジェクトに依存していたり、使用箇所が少ないなどあるとクラス作成するタイミングでは初期化不要となります。

### `var`や`null`をセットを回避できる 

`lateinit`と`lazy`を使用しない場合

```kotlin
private var sonic: Sonic? = null
```
こんな感じで、`var`かつ`nullable`にするしかない・・
しかし、`lazy`の方を用いることで`val`かつ`non-null`な値を持つことが出来るようになります。

## まとめ
このくらいかな？
他にメリットがあれば、教えて頂きたいです！

自分が見たあのlazyが使われていた箇所は、割と重いオブジェクトだったのかな。
また、`lazy`と`lateinit`は仕様が異なるので上手く使いたい所です。

## 参考
https://agrawalsuneet.github.io/blogs/lazy-property-in-kotlin/
Node.js Express ミドルウェア

#【Node.js Express ミドルウェア】

##Expressで足りないものは、**ミドルウェア**でカバー
- リクエストレスポンスに対して、任意の追加処理を行う関数のこと。
    - リクエストオブジェクトの変更
    - レスポンスオブジェクトの変更
    - リクエスト・レスポンスを用いた独自の追加処理　...etc

##ミドルウェアの実装
- 通常処理

```
function (req, res, next) {
  //何かの処理 （次の処理を呼べるように next ） 
  next();
}
```


- 　エラー処理

```
function (err, req, res, next) {
  //何かの処理 （次の処理を呼べるように next ） ​
 ​next();
}
```

##ミドルウェアの組み込み

```
const express = require("express");
const app = express();

app.use((req, res, next) => {
    //アプリケーションレベルのミドルウェア
});

app.listen(3000);

```

※ コードの上から順に、全てのリクエストに対して処理が実行される。
備忘録）css3のテキストグラデーション

参考を見ながら適用しようとしたら詰まったのでメモ

#概要
参考を見て試すも
background-clip: text;が適用されず文字抜きが上手く表示されなかった

#原因・結果
backgroundセレクターでは反映されず、background-image又はbackground-textでは反映されるみたい

````ruby:style.css
 /*-- NG --*/
.textGr{
  color: #ae9b7a;
  background: linear-gradient(90deg, rgba(174,155,122,1) 0%, rgba(255,241,215,1) 50%, rgba(174,155,122,1) 100%);
  -webkit-text-fill-color: transparent;
  -webkit-background-clip: text;
  display: inline-block;
}

 /*-- OK --*/
.textGr{
  color: #ae9b7a;
  background-image: linear-gradient(90deg, rgba(174,155,122,1) 0%, rgba(255,241,215,1) 50%, rgba(174,155,122,1) 100%);
  -webkit-text-fill-color: transparent;
  -webkit-background-clip: text;
  display: inline-block;
}
```

#参考先
https://www.i-ryo.com/entry/2018/09/13/131709
LambdaChip を MS-Windows で試す

Docker インストールして動かすまでです

# dockerをPCにインストール

以下の Windows が必要となります

- Windows 11 64 ビット: 21H2 以降
- Windows 10 64 ビット: 21H1 (ビルド 19043) 以降




https://docs.docker.com/get-docker/

上記の「Docker Desktop for Windows」を押して進めていきます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139524/4d058240-cbac-81bb-5707-72ac4deec1a6.png)

インストールした後、再起動が必要となります。

インストール時に、WSL 2 installation is incomplete というエラーが表示された場合は、Restartを選ばす、そこに表示されるURLをクリック
https://aka.ms/wsl2kernel

これを無視するとdocker自体はインストール完了しても Docker Engine failed to start...と表示されて失敗する。

> 手順 4 - Linux カーネル更新プログラム パッケージをダウンロードする
> x64 マシン用 WSL2 Linux カーネル更新プログラム パッケージ

の順で更新プログラムもインストール

```

Docker Engine starting...
```

のあと、以下が表示されれば Docker のインストールは成功

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/139524/4bc7f072-c2b1-d340-56da-0394d68305f6.png)



# LambdaChip Dockerインストール

https://lambdachip.com/articles/docs/1

上記LambdaChipの公式ページの「ALONZO BOARD QUICK START」参照

##  Lacoコンパイラーのdockerイメージをダウンロード

コマンドプロンプトで以下を実行します。
```

docker pull registry.gitlab.com/lambdachip/laco:latest
```

※dockerのImagesのNAMEに registry.gitlab.com/lamb... と表示されればダウンロード成功

## dockerで上記をRUN

適当なディレクトリで、 lambdachip-workspaceというフォルダを作成

```

mkdir lambdachip-workspace

```

```

cd lambdachip-workspace
```

  docker イメージにログイン

```

docker run -it --rm -v %cd%:/workspace -w /workspace -u "lambdachip:lambdachip" registry.gitlab.com/lambdachip/laco:latest bash

```


```

lambdachip@9e43fbe7cf38:/workspace$

```

※@後の数字は毎回異なる。
上のようになればログインできている


# サンプルプログラムつくってみる

-  サイト上のソースコードを使いprogram.scmというファイル名で保存

***.txtのままだとダメなので、フォルダの表示で拡張子を変更できるようにしてから、メモ帳で作った後に名前の変更で拡張子を.txt→.scmに変更する。

-  program.scmをlambdachip-workspaceフォルダへ移動

- lambdachipのwrokspaceにログインした状態でlaco program.scmのコマンドを実行


```

laco program.scm
```

program.lef ファイルが実行ファイルです

# Alonzo ボードで実行

手元に Alonzo ボードがある方は、program.lef  を MicroSDカードへコピーします。

LambdaChipにMicroSDを挿入し、Type-CケーブルでLambdaChipに電源供給するとプログラム（先程のlefファイル）が自動で実行されてLEDが点滅します。

手元に Alonzo ボードが無い方は、ワークショップ主催者が用意したリモート Alonzo ボードを使ってみます。

```

scp program.lef (ログオンユーザ名)@(リモートAlonzoボードアドレス):/home/(ログオンユーザ名)/(ワークショップユーザ名).lef 
```

で転送しましょう。

主催者が ログオンユーザ名とリモートAlonzoボードアドレスを用意します。

例えば、リモートAlonzoボードアドレスが 123.456.789.012 、ログオンユーザ名が lambda とします。 あなたのワークショップユーザ名が taro とすると、

```

scp program.lef  lambda@123.456.789.012:/home/lambda/taro.lef 
```
とすると、リモートAlonzo ボードに転送されます。
【Rails】Rails7.0でyarn build yarn build:cssが起動しない

# 前提

Rails 7.0.1
Ruby 2.7.2
docker 20.10.11

### 発生したエラー

rails new -j esbuild で作成した後にサーバーを起動させる際に yarn build と yarn build:css がエラーが出てバンドルされない状態になってしまう。

```console:console
~/rails(master) $ bin/dev
20:59:27 web.1  | started with pid 94024
20:59:27 js.1   | started with pid 94025
20:59:27 css.1  | started with pid 94026
20:59:27 js.1   | yarn run v1.22.15
20:59:27 css.1  | yarn run v1.22.15
20:59:27 js.1   | error Command "build" not found.
20:59:27 js.1   | info Visit https://yarnpkg.com/en/docs/cli/run for documentation about this command.
20:59:27 css.1  | error Command "build:css" not found.
20:59:27 css.1  | info Visit https://yarnpkg.com/en/docs/cli/run for documentation about this command.
20:59:28 js.1   | exited with code 1
20:59:28 system | sending SIGTERM to all processes
20:59:28 css.1  | exited with code 1
20:59:28 web.1  | terminated by SIGTERM
```

# 本文

bin/dev コマンドでサーバーを起動させると foreman がインストールされ、プロジェクトディレクトリ直下にある Procfile.dev が実行されます

```bash:bin/dev
#!/usr/bin/env bash

if ! command -v foreman &>/dev/null; then
  echo "Installing foreman..."
  gem install foreman
fi

foreman start -f Procfile.dev

```

サーバーの起動と別プロセスで js と css のバンドルが行われ、yarn のコマンド使用して実行されています。

```bash:Prodfile.dev
web: bin/rails s -b '0.0.0.0' -p 3000
js: yarn build --watch
css: yarn build:css --watch
```

エラー文では error Command "build" not found 　と出ているので package.json でコマンドが設定されていないことでエラーが出ています。
コマンドを手動で追加します。
今回は css を Bootstrap を利用してますので、他の css を利用している場合はコマンドを各自書き換えてください

```json:package.json
{
  "name": "app",
  "private": "true",
  "dependencies": {
    "@hotwired/stimulus": "^3.0.1",
    "@hotwired/turbo-rails": "^7.1.0",
    "@popperjs/core": "^2.11.2",
    "autoprefixer": "^10.4.2",
    "bootstrap": "^5.1.3",
    "esbuild": "^0.14.11",
    "postcss": "^8.4.5",
    "sass": "^1.48.0",
  },
  "scripts": {
    "build:css": "sass ./app/assets/stylesheets/application.bootstrap.scss ./app/assets/builds/application.css --no-source-map --load-path=node_modules",
    "build": "esbuild app/javascript/*.* --bundle --sourcemap --outdir=app/assets/builds"
    //上記を追加する
  }
}

```

これによってサーバー起動時に bin/dev を利用することで js と css のバンドルをやってくれるようになります。

# まとめ

rail ｓ 6 の時のようにちょっとだけファイルの変更があったとしても、ほんの数秒でバンドルをしてくれるので DX がめちゃくちゃいいです。
色々と変更点が多いのでいきなりバージョンを上げるのはもう少し待ったほうが良さそうです。
youtube動画　【AWS 入門】EC2とDockerでHello Worldしよう　の手順メモ

# 概要
youtubeの[【AWS 入門】EC2とDockerでHello Worldしよう](https://www.youtube.com/watch?v=HvrIPQ77xRY)の(EC2起動後の)手順をこちらにメモしておく。

- 上の動画の手順通りにやれば、ブラウザからEC2のIPアドレスにアクセスして、Hello World docker !!の文字を表示することができました。

## EC2起動後の手順

```
    1  sudo yum update
    2  sudo yum install docker
    3  sudo service docker start
    4  sudo docker info
    5  mkdir hello-docker
    6  cd hello-docker/
    7  vi hello.html
    8  vi Dockerfile
    9  sudo docker build -t hello-docker-ec2 .
   10  sudo docker run --rm -d -p 80:80 hello-docker-ec2
   11  sudo docker ps
```

### 7. vi hello.html　で作成するhtmlファイル
```hello.html
Hello from docker !!
```

### 8. vi Dockerfileで作成するDockerfile
```Dockerfile
FROM nginx
COPY ./hello.html /usr/share/nginx/html/
```
###  10.  sudo docker run --rm -d -p 80:80 hello-docker-ec2
- --rm 
    - コンテナ停止後にコンテナを削除するというオプション
- - d
    - バックグラウンドで起動させるというオプション。
- -p 80:80
    - どのportを使うかを指定する設定。
    - セキュリティグループの設定時にport80番でのアクセスのみを許可するように設定した。そのため、このオプションを付ける必要がある。

## コンテナの停止方法

docker ps コマンドで出力される、CONTAINER ID を使用して以下のコマンドを打つ。

 - docker stop 英数字(CONTAINER ID)

例

```
docker stop 728afd82290e
```

 - docker ps

``` 
CONTAINER ID   IMAGE              COMMAND                  CREATED         STATUS         PORTS                                       NAMES
728afd82290e   hello-docker-ec2   "/docker-entrypoint.…"   6 minutes ago   Up 6 minutes   0.0.0.0:30->30/tcp, :::30->30/tcp, 80/tcp   silly_goldstine
```
備忘録）jqueryイベント時のアロー関数のthisについて

jqueryでアロー関数を使って詰まったので忘れないようメモ

#概要
クリックイベント時にアロー関数を使い$(this)を使おうとしたところ
undefinedになった。

#結論
```
$('#btn').on('click',(event) => {
 event.preventDefault();
 const $this = $(event.currentTarget);
 $this.css('text','red');
});
```
アロー関数ではファンクション関数の呼び出し元を指すのではなく、
windowsオブジェクトがthisとなる、アロー関数ではイベント命令であれば引数のイベントからevent.currentTargetを使うとthisと同じ挙動になる
※引数を受け取らないものではthisは使えないのでファンクション関数を使う


#参考サイト
https://codecodeweb.com/blog/424/
Xcode でテストにタイムアウトを設定する

## 概要

Swift 5.5 で入った Concurrency を使ったテストで、`await` 時に想定外のことが起きて結果が返ってこずテストが永遠に終わらないということが起こったので、テストにタイムアウトを設定する方法を調べてまとめました。

動作検証はすべて Xcode 13.2.1 で行いました。

## TestPlan を設定する

まず、タイムアウトを設定するために TestPlan を有効にします。タイムアウトの設定のみであればビルド時に特定のコマンドラインオプションを渡すことでも可能なようですが、細かく設定しようと思うと TestPlan を作ってしまった方が便利なのでそちらの方法をとることにします。

Xcode の window 上部の Scheme をクリックして `Edit Scheme...` から `Test` の `Info` タブを開きます。右下の方に `Convert to use Test Plans...` というボタンがあるのでこれをクリックします。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159260/a2c8d37a-9a4b-91b3-2ccd-12343b943e1c.png)

３つのオプションが出てくるので、一番上の `Create Test Plan from scheme` を選びます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159260/418cb514-4b08-f2de-6420-98d8e9bf4c6b.png)

作成された TestPlan の `Configuration` タブを開き `TestExecution` > `Test Timeouts` を `On` にすることでタイムアウトが有効になります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159260/a0944c8e-f3a8-592b-3a6b-583c42671171.png)

## タイムアウト値の設定

`executionTimeAllowance` という `XCTestCase` のプロパティを編集することでタイムアウト値を設定することができます。

- https://developer.apple.com/documentation/xctest/xctestcase/3526064-executiontimeallowance

ドキュメントにあるように、 `executionTimeAllowance` の値自体は秒数ですが実際のタイムアウト値は分単位での切り上げになることに注意しましょう。例えば `1` を設定すると1秒の切り上げの1分、 `150` を設定すると2分30秒の切り上げの3分でテストがタイムアウトするようになります。この振る舞いは分かりづらいので `executionTimeAllowance` の値は `60` `120` `180` のようにちょうど分単位になるように設定するのがよい気がします。

例えば `executionTimeAllowance` を `60` にしてテスト中に `61` 秒待つようにすると、期待通りにテストが落ちてくれます。エラーメッセージもなかなかわかりやすいと思います。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159260/c4fa5e90-77e9-1e38-95fd-f35d7959ef5a.png)

以上でテストにタイムアウトを設定することができましたが、すべてのテストでいちいち `executionTimeAllowance` を設定するのは大変です。TestPlan の `Test Timeouts` の下の `Default Test Execution Time Allowance` という項目で `executionTimeAllowance` のデフォルト値の設定ができます。以下のように設定すれば、すべてのテストが1分でタイムアウトするようになります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159260/04e68717-64fc-b513-d94b-758800d9193a.png)

ちなみに `Default Test Execution Time Allowance` 自体のデフォルト値は `600` なので、 `Test Timeouts` を `On` にした時点ですべてのテストが10分でタイムアウトするようになっていたことになります。

`Default Test Execution Time Allowance` で決まるタイムアウト値を各テストメソッドごとに上書きしたい場合は `executionTimeAllowance` に値を入れることでそちらが優先されます。

## まとめ

- テストがなんらかの原因で hang しないようにテストメソッドにタイムアウトを設定するとよい
- TestPlan を有効にして `Test Timeouts` を `On` にすることでテストがタイムアウトするようになる
- タイムアウトまでの時間は、 TestPlan の設定の `Default Test Execution Time Allowance` と `XCTestCase` の `executionTimeAllowance` プロパティでそれぞれ設定できる
    - 後者の設定が優先される
    - どちらの設定も単位は秒だが、タイムアウトまでの時間は分単位での切り上げになることに注意

## 参考

- https://developer.apple.com/documentation/xctest/xctestcase/3526064-executiontimeallowance
- https://benoitpasquier.com/advanced-testing-tips-xcode/
tcpdumpの使用方法

今回の場合
11004ポートかつ
46790ポートは除いて
さらに
54008ポートものぞきたい場合


```
 tcpdump -i ens192 port 11004 and not port 46790 and not port 54008
```

次に
このtcpdumpで取得した結果をファイルに出力したいとき

```
 tcpdump -i ens192 port 11004 and not port 46790 and not port 54008 -w test.out
```

ダンプしたファイルを確認する場合

```
tcpdump -r test.out
```

※ただし、このダンプしたファイルを詳細にみたいなら、wiresharkでみないとだめだと思う。。。
GraalVM(native-maven-plugin)で「JEP 290: Java Serialization Filtering」の仕組みを利用する

GraalVMのnative-imageコンパイラで生成したnative-imageの中で[Serialization Filtring](https://docs.oracle.com/en/java/javase/11/core/serialization-filtering1.html#GUID-0A1D23AB-2F18-4979-9288-9CFEC04F207E)を利用する方法がわかったのでメモっておきます。

# ビルドツール

* Maven([native-maven-plugin](https://docs.oracle.com/cd/F44923_01/enterprise/21/docs/reference-manual/native-image/NativeImageMavenPlugin/))

# 指定方法

`buildArgs`にフィルタリングルールを指定すればOK！

```xml
<plugin>
  <groupId>org.graalvm.buildtools</groupId>
  <artifactId>native-maven-plugin</artifactId>
  <version>0.9.9</version>
  <extensions>true</extensions>
  <configuration>
    <buildArgs>
      <arg>-Djdk.serialFilter=com.example.entity.*;java.util.*;java.lang.*;!*</arg>
    </buildArgs>
  </configuration>
  <!-- ... -->
</plugin>
```
CUDA on WSLで分子動力学シミュレーションを行う

先日、分子動力学 (MD) シミュレーションを Windows OS で実行するより、Linux で実行する方が良いという[投稿](https://www.researchgate.net/post/How_would_i_exploit_my_GPU_for_NAMD_simulation)を見つけました。そこで今回は、MDシミュレーションの計算時間を  Windows Subsystem for Linux (WSL) 2 と Windows11 とで比較しました。

# 環境

- Ryzen5 3600
- RTX2060
- Windows11
- WSL 2 (Ubuntu 20.04)
- CUDA Version: 11.6

[CUDA on WSL User Guide](https://docs.nvidia.com/cuda/wsl-user-guide/index.html) に従って環境設定を行った。

# 手順

### NAMDのインストール

[NAMDの公式サイト](https://www.ks.uiuc.edu/Development/Download/download.cgi?PackageName=NAMD)から Linux-x86_64-multicore-CUDA (NVIDIA CUDA acceleration) と Win64-CUDA (NVIDIA CUDA acceleration) をダウンロードして任意のディレクトリに解凍する。

### ベンチマークのダウンロード
今回のベンチマークとして ApoA-1 (善玉コレステロールの構成成分) を用いた。
![apoa1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2509479/fb78376a-337e-69a7-840c-2054f3c5f082.png)

```bash
$ wget https://www.ks.uiuc.edu/Research/namd/utilities/apoa1.tar.gz
$ tar -xvf apoa1.tar.gz
```

### MDシミュレーションの実行
NAMD の実行ファイル (apoa1.namd) を以下のように変更した。

```:apoa1.namd
cellBasisVector1     108.8612 0.0 0.0
cellBasisVector2     0.0 108.8612 0.0
cellBasisVector3     0.0 0.0 77.758
cellOrigin           0.0 0.0 0.0

coordinates          apoa1.pdb
temperature          300
seed                 74269

switching            on
switchdist           10
cutoff               12
pairlistdist         13.5
margin               0
stepspercycle        20

PME                  on
PMEGridSizeX         108
PMEGridSizeY         108
PMEGridSizeZ         80

structure            apoa1.psf
parameters           par_all22_prot_lipid.xplor
parameters           par_all22_popc.xplor
exclude              scaled1-4
1-4scaling           1.0

timestep             1.0
fullElectFrequency   4

numsteps             100000  ;# 100 ps
outputtiming         1000

outputname           apoa1-out
```


WSL 2 で実行する場合

```:zsh
$ NAMD_2.14_Linux-x86_64-multicore-CUDA/namd2 +p4 apoa1/apoa1.namd > apoa1_wsl.log
```

Windows11 で実行する場合

```:PowerShell
> NAMD_2.14_Win64-multicore-CUDA/namd2 +p4 apoa1/apoa1.namd > apoa1_win.log
```

# 結果

![apo1a.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2509479/bc6ca964-5eb1-9261-6121-30da547df82a.gif)


MDシミュレーションの WSL 2 での実行結果と Windows11 での実行結果を比較したところ、WSL 2 の方が Windows11 で実行するよりも2倍以上速かった (N=3、エラーバーは標準偏差を示す)。

![result.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2509479/a341573c-09fa-066a-82a4-9599894ccfb6.png)

MDシミュレーション実行中における GPU の使用率は、WSL 2 も Windows11 も90%以上で推移していたが、CPU の使用率は WSL 2 では40%～50%、Windows11 では20%～30%だった。この CPU 使用率の差が、Linux 版と Windows 版の NAMD のプログラムによる違いによるのか、 Linux と Windows の違いによるのかはわかりません。

# まとめ

- ApoA-1 の 100 ps のMDシミュレーションの結果、Windows11 よりも WSL 2 で実行した方が速かった。
- WSL 2 と Windows11 で実行した場合、CPU 使用率に差があった。

# 参考資料

- ResearchGate https://www.researchgate.net/post/How_would_i_exploit_my_GPU_for_NAMD_simulation

- CUDA on WSL User Guide https://docs.nvidia.com/cuda/wsl-user-guide/index.html
- NAMDの公式サイト https://www.ks.uiuc.edu/Development/Download/download.cgi?PackageName=NAMD
フロントエンドとNode.jsで繋いだ時のCORSエラーについて

フロントエンド(Angular)とバックエンドの繋ぎこみを行なった時にcorsエラーが表示され、それに対応した流れを書いていこうと思います。

####エラーの内容

```
core.js:6498 ERROR Error: Uncaught (in promise): HttpErrorResponse: {"headers":{"normalizedNames":{},"lazyUpdate":null,"headers":{}},"status":0,"statusText":"Unknown Error","url":"http://localhost:3000/some","ok":false,"name":"HttpErrorResponse","message":"Http failure response for http://localhost:3000/some: 0 Unknown Error","error":{"isTrusted":true}}
    at resolvePromise (zone.js:1213:1)
    at resolvePromise (zone.js:1167:1)
    at zone.js:1279:1
    at ZoneDelegate.invokeTask (zone.js:406:1)
    at Object.onInvokeTask (core.js:28679:1)
    at ZoneDelegate.invokeTask (zone.js:405:1)
    at Zone.runTask (zone.js:178:1)
    at drainMicroTaskQueue (zone.js:582:1)
    at ZoneTask.invokeTask [as invoke] (zone.js:491:1)
    at invokeTask (zone.js:1600:1)
```

フロントエンドは
`localhost:4200`
で起動

バックエンドは
`localhost:3000`
で起動しています。

したがってお互いのポートが異なるためにcorsエラーを引き起こしています。

####やったこと
node.js側でcorsのライブラリを入れました。

```app.ts
import express from 'express';
import cors from 'cors';

const app = express();
app.use(cors());
```

これにより、フロントエンド側でのcorsエラーを解消することができました。

corsのライブラリについての説明があったので下記にリンクを記載します。
[express.jsのcors対応](https://qiita.com/chenglin/items/5e563e50d1c32dadf4c3)
DynamoDB Local環境構築手順 メモ

* DynamoDB Localの環境構築手順についてメモする。

## DynamoDB Localとは

* AWS製のローカル環境向けDynamoDB
* Dockerイメージとして提供

## 前提条件

* Docker,docker-compose環境構築済みであること。

* nodejsインストール済みであること。

* ディレクトリ構成

  ```
  dynamo_test	--	docker-compose.yml
  			|_	docker/dynamodb
  ```

  

## 環境構築手順

**1.`docker-compose.yml`準備**

   ```yaml
   version: '3.8'
   services:
     dynamodb-local:
       command: "-jar DynamoDBLocal.jar -sharedDb -dbPath ./data"
       image: "amazon/dynamodb-local:latest"
       container_name: dynamodb-local
       ports:
         - "8000:8000"
       volumes:
         - "./docker/dynamodb:/home/dynamodblocal/data"
       working_dir: /home/dynamodblocal
   ```

**2.マウントディレクトリ作成+権限設定**

   ※コンテナ内部で`dynamodblocal`ユーザーとして処理するために必要

   ```shell
   mkdir -p ./docker/dynamodb
   sudo chmod 777 ./docker/dynamodb
   ```

**3.コンテナ起動**

   ```shell
   docker-compose up
   Starting dynamodb-local ... done
   Attaching to dynamodb-local
   dynamodb-local    | Initializing DynamoDB Local with the following configuration:
   dynamodb-local    | Port:       8000
   dynamodb-local    | InMemory:   false
   dynamodb-local    | DbPath:     ./data
   dynamodb-local    | SharedDb:   true
   dynamodb-local    | shouldDelayTransientStatuses:       false
   dynamodb-local    | CorsParams: *
   dynamodb-local    |
   ```

   ※localhost:8000でコンテナが起動する。

## 動作確認

**0.dynamodb-admin(DynamoDB用GUIツール)**

   * . 次のコマンドを実行する。

      ```shell
      npm install -g dynamodb-admin
      set DYNAMO_ENDPOINT=http://localhost:8000
      ```

      ※筆者環境はWindowsのため、上記接続先設定を行っている。

**1.dynamodb-admin起動**

   ```
   dynamodb-admin
   ```
**2.`http://localhost:8001`にアクセス**

   ![dynamodb_admin.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/586535/9fb8b19b-bf20-70f0-8dbc-0cbdab457bc5.png)


**3.テーブル作成**

   * `Create Table`ボタンを押下し、テーブル情報を入力してテーブルを作成する。

   



## 参考情報

* [DynamoDB ローカル (ダウンロード可能バージョン) のセットアップ](https://docs.aws.amazon.com/ja_jp/amazondynamodb/latest/developerguide/DynamoDBLocal.html)
* [aaronshaf/dynamodb-admin](https://github.com/aaronshaf/dynamodb-admin)
* [DynamoDBの初心者に伝えたい初めて触るときの勘所](https://www.slideshare.net/ryosasaki376695/dynamodb-238931115)