OmniAICreator/Qiita-1.07M huggingface dataset:
Oracle Analytics Cloud Classic： SmartViewでOACに対する接続の作成方法 

はじめに
---
ExcelからOracle Analytics Cloud(OAC)に直接、接続し利用する方法としてSmartView for Officeを利用します。
利用時は、まず"新規接続"でOACに対する接続を作成します。

作成方法
---

"SmartView"メニューから"パネル"をクリック、プライベート接続をクリックします。
![{5DB2ECAB-E045-4E79-BEA6-90E21F38D16E}.tmp.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/fb649309-5669-ceb6-5d43-418ab5cdfd8a.png)

右下部の"新規接続の作成"をクリックします。
![{5DB2ECAB-E045-4E79-BEA6-90E21F38D16E}.tmp.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/6a3e147a-b8c0-8bfa-71e2-33a17f111845.png)

新規接続プロバイダ・タイプに"Oracle BI EE"がでてきます。"Oracle BI EE"をクリックします。
![{5DB2ECAB-E045-4E79-BEA6-90E21F38D16E}.tmp.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/d2bb28c2-e1b9-bb52-46a0-43c372b60925.png)

接続URLはOACのホスト名に/analytics/jbipsを付けて入力します。
https://<OAC URL>/analytics/jbips
![{5DB2ECAB-E045-4E79-BEA6-90E21F38D16E}.tmp.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/16c4350d-ea2f-a1ad-1d58-0f1ef286f80f.png)

名前を適宜つけて、OKをクリックします。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/07104554-518e-2ac9-0612-3dab0926ed3c.png)

接続が作成されました。
![{5DB2ECAB-E045-4E79-BEA6-90E21F38D16E}.tmp.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/c4910f46-e29c-906f-8233-bf2d1b6b8c79.png)

以上
Deviseでletter_openerを用いたパスワードリセット

# 環境
MacOS
Rails 6.1.6
Ruby 3.1.2

# 前提
Deviseでログイン、ログアウトの実装を完了している。

# 注意
同じような検索をかけると、sorceryという謎のものが出てくるが、Deviseとは別の認証モジュールなので、一緒には使えない。はず。

# 実装イメージ
ログイン画面　にforgot password？
この案内リンクからメール送信画面へ
letter_openerで送信
/letter_openerで受信確認
再設定リンク踏んで、パスワード再設定
再設定したらログイン画面へ遷移し、成功メッセージを確認

# 手順
## forgot password?の実装
```view/divise/session/new.html.erb
<%= link_to "forgot password?", new_user_password_path %>
```
リンク先は　`＄rails routes`で確認
`view/devise/passwords/new.html.erb`に飛びたいので、
`devise/passwords#new`を探す

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/855269/91b09918-e842-1079-5169-187fd2c73d47.png)

先頭の文字列に_pathを付与して、リンク先完成
`new_user_password_path`

Deviseではパスワード再設定画面は既に用意されている。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/855269/0257e102-82a2-9e4f-d0fa-574a5fe365b8.png)


## メール送受信の実装
ジェム letter_openerを利用。

### module インストール
```Gemfile.
gem 'letter_opener_web', '~> 2.0'
```
```
$ bundle
```

### `:recoverable`が含まれていること確認
```db/migrate/devise_create_users.rb
## Recoverable
      t.string   :reset_password_token
      t.datetime :reset_password_sent_at
      t.boolean  :allow_password_change, :default => false
```


```models/user.rb
  devise :database_authenticatable, :registerable,
         :recoverable, :rememberable, :validatable
```

### 送受信方法と送信先の設定
```config/environments/development.rb
  config.action_mailer.delivery_method = :letter_opener_web
  config.action_mailer.default_url_options = { host: 'localhost', port: 3000 }
```

### ブラウザでメールの送信結果を確認できるように設定
```config/routes.rb
mount LetterOpenerWeb::Engine, at: "/letter_opener" if Rails.env.development?
```

### メール受信確認
`/letter_opener`



# 気になるがやらないこと
・Vagrant machine とか Docker container　からアプリケーションを立ち上げている時
この場合変なメッセージが出てくるのを回避したりするために、[letter_opener_web](https://github.com/fgrehm/letter_opener_web)を使うといいらしい。

・メール本文の変更
新しくmailerコントローラ作っていろいろやるらしい
`$ bundle exec rails g mailer new_user`
[参考サイト](https://opiyotan.hatenablog.com/entry/rails-gem-letter_opener)


# あとがき
やはり、見返さないとしても、こうやって記録を残しておくことは、頭が整理されていいですね。
MySQLの権限まわりの備忘録

・ユーザー作成
```
create user 'username' identified by 'password';
```

・ユーザー一覧の確認（usernameとhostnameのみ）
```
mysql> select user, host from mysql.user;
+------------------+-----------+
| user             | host      |
+------------------+-----------+
| root             | %         |
| scraper          | %         |
| mysql.infoschema | localhost |
+------------------+-----------+
3 rows in set (0.00 sec)

```

・ユーザー情報の確認（権限も確認可能、where句は検索条件、;の代わりに\Gで縦書きに変更)
```
mysql> select * from mysql.user where user='root'\G
*************************** 1. row ***************************
                    Host: %
                    User: root
             Select_priv: Y
             Insert_priv: Y
             Update_priv: Y
             Delete_priv: Y
             Create_priv: Y
               Drop_priv: Y
             Reload_priv: Y
           Shutdown_priv: Y
            Process_priv: Y
               File_priv: Y
              Grant_priv: N
         References_priv: Y
              Index_priv: Y
              Alter_priv: Y
（中略）
```

・ユーザー権限のみ確認
```
mysql> show grants for scraper\G
*************************** 1. row ***************************
Grants for scraper@%: GRANT USAGE ON *.* TO `scraper`@`%`
1 row in set (0.00 sec)
```
※「GRANT USAGE 」だと何も権限が付与されていない

※ 権限一覧の説明はこちら
https://www.javadrive.jp/mysql/user/index5.html
※ 公式ドキュメント
https://dev.mysql.com/doc/refman/8.0/ja/privileges-provided.html

・ユーザー権限の追加（Grant Option権限を付加）
```
mysql> update user set Grant_priv = "Y" where user = "root";
Query OK, 1 row affected (0.01 sec)
Rows matched: 1  Changed: 1  Warnings: 0
```

・grantテーブルの読み込み
```
mysql> flush privileges;
Query OK, 0 rows affected (0.02 sec)
```
（以下公式ドキュメントより引用）
https://dev.mysql.com/doc/refman/8.0/en/flush.html、

FLUSH PRIVILEGES

Re-reads the privileges from the grant tables in the mysql system schema. As part of this operation, the server reads the global_grants table containing dynamic privilege assignments and registers any unregistered privileges found there.

Reloading the grant tables is necessary to enable updates to MySQL privileges and users only if you make such changes directly to the grant tables; it is not needed for account management statements such as GRANT or REVOKE, which take effect immediately.

（翻訳）
mysql システム スキーマの付与テーブルから権限を再度読み取ります。 この操作の一環として、サーバーは、動的な権限の割り当てを含む global_grants テーブルを読み取り、そこで見つかった未登録の権限を登録します。 許可テーブルに直接変更を加えた場合にのみ、MySQL 権限とユーザーの更新を有効にするために、許可テーブルのリロードが必要です。 すぐに有効になる GRANT や REVOKE などのアカウント管理ステートメントには必要ありません。
Pythonのopenpyxlを使ってExcelシートの罫線を取得する

英語記事も色々調べ倒して、どこにも無かったのでどっかの誰かの役に立てば…（と言う名の備忘録）と思い残しておくことにした。

動作環境：
　Python = 3.10.8
　OS = windows11
　IDE = VScode 1.74.3

### コード
```python
from openpyxl import load_workbook

filename = 'testExcel.xlsx'

wb = load_workbook(filename)

ws = wb.active

print('left: ', ws['C39'].border.left.border_style)
print('right: ', ws['C39'].border.right.border_style)
print('top: ', ws['C39'].border.top.border_style)
print('bottom: ', ws['C39'].border.bottom.border_style)

```

結果
```
left:  medium
right:  medium
top:  medium
bottom:  thin
```

### 解説
上のコードではセル'C39'の罫線左右上下を返すようにしている。
どうやって見つけたかというと、VScodeのデバッガーで対象にブレイクポイントを貼った。
ちなみに、thinは標準の線、mediumは太めの線になる。
Function interface andThen method, compose method

f1.andThen(f2)は、f1,f2
f1.compose(f2)は、f2,f1

下記の例
fc1  integer→string, string→integer
fc2  string→integer, integer→string

```java
public class Outer {
    public static void main(String[] args) {
        Function<Integer, String> f1 = x -> String.valueOf(x + 2);
        Function<String, Integer> f2 = x -> Integer.valueOf(x) * 2;
        Function<Integer, Integer> fc1 = f1.andThen(f2);
        System.out.println(fc1.apply(5));
        System.out.println(f1.andThen(f2).apply(5));
        Function<String, String> fc2 = f1.compose(f2);
        System.out.println(fc2.apply("5"));
        System.out.println(f1.compose(f2).apply("5"));
    }
```
```
14
14
12
12
```
WinMerge：フォルダ比較で、差分のみのレポートを出力



    winMergeU.exe "%dirA%" "%dirB%" -minimize -noninteractive -noprefs -cfg Settings/ShowIdentical=0 -cfg Settings/DirViewExpandSubdirs=1 -cfg ReportFiles/ReportType=2 -cfg ReportFiles/IncludeFileCmpReport=1 -r -u -or diff.html


-minimize
　→ウインドウを出さない
-noninteractive
　→処理が終わればWinMergeも終了
-noprefs 
　→レジストリの読み書きをしません
-cfg Settings/ShowIdentical=0 
　→一致するときはスキップ
-cfg Settings/DirViewExpandSubdirs=1 
　→サブディレクトリを展開する
-cfg ReportFiles/ReportType=2 
　→リポートはhtmlで(0:CSV、1:TSV、2:HTML、3:XML)
-cfg ReportFiles/IncludeFileCmpReport=1 
　→ファイルの差分の中身を出す
-r 
　→再帰する
-u
　→?
-or
　→reportのファイルパス


参考

https://sourceforge.net/p/winmerge/support-requests/109/
selenium メモメモ　個人用3



```
from selenium import webdriver
import chromedriver_binary
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import Select
import time 
import time_now
import yaml


driver_path = './chromedriver.exe'
driver = webdriver.Chrome(executable_path=driver_path)

#-------------------------------エラーメッセージを消す-------------------------------
ChromeOptions = webdriver.ChromeOptions()
ChromeOptions.add_experimental_option('excludeSwitches', ['enable-logging'])
#----------------------------------------------------------------------------------


# urlを指定してブラウザで開く
url = ''
driver.get(url)
time.sleep(1)

#入力操作
search=driver.find_element(By.ID,('twotabsearchtextbox'))
search.send_keys('バトスピ')
time.sleep(1)


#クリック操作
search_on=driver.find_element(By.ID,('nav-search-submit-button'))
search_on.click()
time.sleep(1)

# drop=driver.find_element(By.CLASS_NAME,('a-button-text a-declarative'))
# drop_select = Select(drop)
# drop_select.de('新着商品')
# time.sleep(2)

# drop=driver.find_element(By.ID,('a-autoid-0-announce'))
# drop.click()
# time.sleep(1)

#ドロップダウン操作
# drop=driver.find_element(By.NAME,('url'))
# select = Select(drop)
# select.select_by_value("search-alias=audible")
# time.sleep(5)

nowtime_str=time_now.dtnow()
result ="現時刻は" + nowtime_str
print(result)

with open('para.yaml') as file:
    obj = yaml.safe_load(file)
    print(obj['z'])












```
CSRFトークンはもはや不要です

タイトル通りです。CSRFトークンはもはや旧ブラウザへの対応が必要である場合を除いて不要です。CSRFトークンを頑張って実装しなくても、Cookieの`SameSite`属性を用いればCSRFは防御可能です。

# CSRFの原因
そもそもCSRFはあるオリジンから別のオリジンへCookie付きのPOSTリクエストを行えてしまうことによって起きる問題でした。たとえばCSRFの脆弱性がある`bank.example.com`という銀行サイトにログインした状態で、下記のコードが含まれる第三者の悪意あるサイト`malicious.example.com`を開いて「今すぐクリック！！！」をクリックすると、お金が勝手に送金されてしまいます。

```html:malicious.example.com
<form action="https://bank.example.com/transfer" method="post">
  <input type="hidden" name="to" value="cracker" />
  <input type="hidden" name="amount" value="¥10000000" />
  <button>今すぐクリック！！！</button>
</form>
```

問題は何の関係性もない`malicious.example.com`のサイトから発せられた`bank.example.com`へのリクエストに`bank.example.com`の認証情報（Cookie）が付与されてしまうことです。これによって`bank.example.com`に対するユーザ認証付きの操作を第三者がそれと分からない形で実行させることができてしまうわけです。

そこで導入されたのが`Set-Cookie`ヘッダの`SameSite`属性です。

# `SameSite`属性
`SameSite`は`Set-Cookie`ヘッダの属性でたとえば以下のように設定します。

```
Set-Cookie: sessionId=9284769; SameSite=Lax
```

`SameSite`属性の値は3種類、`None`、`Lax`、`Strict`です。

`Lax`または`Strict`を指定すればCSRFは起こりません。`Strict`を指定するとブラウザは別オリジンのサイトによって開始されたリクエストではCookieを送信しません。`None`は昔のブラウザと同じ挙動で、常にCookieを送信します。`Lax`はGETリクエストの場合は`None`相当だが、POSTリクエストの場合は`Strict`相当になるといった設定です。`Lax`もしくは`Strict`であれば別の第三者のサイトからのPOSTリクエスト時にはCookieを送信しないのでCSRFは起こり得ません。

上の例のフォームでは`malicious.example.com`上のサイトから開始された`https://bank.example.com/transfer`へのリクエストは別オリジンへのリクエストとなるためCookieが付与されず、銀行サイトのバックエンドからはユーザ認証がないリクエストとして扱われます。そうなれば当然送金はできずに攻撃は失敗するというわけです。

多くの場合、`Strict`は厳しすぎるので`Lax`を使うことになると思います。`Strict`を指定した場合、GETメソッドでもCookieが送られないと言うことは、別のサイトに自分のサイトのリンクが貼ってあったとき、それをクリックしてもCookieが送信されない、つまり必ずログインされていない状態で遷移するということです。一般公開しているサイトならそれは不便すぎますよね。

# ブラウザサポート状況
`SameSite`属性はすでにモダンブラウザの全てで、最低でも2,3年前からサポートされています。

https://caniuse.com/same-site-cookie-attribute

Google ChromeではSameSite属性を指定しない場合のデフォルト値が`Lax`になっています。しかしFirefoxやSafariは互換性重視でデフォルトが`None`なので指定は必須です。

SafariやIE11の数年前のバージョンとマイナーなモバイルブラウザではサポートされないものもあるようです（2023年1月現在）。彼らのためにCSRFトークンを実装してあげるかどうかと言う話ですね。私としては、ここまで普及していて特に難易度が高いとも思えないセキュリティ機能を未だに実装していないようなブラウザはそもそも使うべきではない、と言う感想ですが。

# まとめ
- CSRF対策は`Set-Cookie`ヘッダに`SameSite=Lax`を付与すれば足りる。
- `SameSite`属性はモダンブラウザの全てで数年前からサポート済み。
- CSRFトークンは古かったり一部のマイナーなブラウザへの対応が必要な場合を除いて不要。
Oracle Analytics Cloud Classic：SmartViewで新規接続作成時に「Oracle BI EE」がでてこないときの対処

はじめに
---
ExcelからOracle Analytics Cloud(OAC)に直接、接続し利用する方法としてSmartView for Officeを利用します。
直接、接続する際に、"新規接続"を作成してアクセスします。
このとき、「Oracle BI EE」がでてこないときがあります。たとえば初めてSmartViewをインストールすると下図のようなOracle BI EEが出てこないとき。
![{5DB2ECAB-E045-4E79-BEA6-90E21F38D16E}.tmp.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/02966e2f-c453-6406-fbca-6a51a55fca3f.png)

対処
---
JBIPSProviderInstaller.svextをインストールします
インストール方法は、
1.SmartViewをインストールしたディレクトリの配下のextentionsに移動する
図ではc:\Oracle\SmartView\extentions
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/b87f23e4-1923-e490-55be-504c526a4453.png)

2.JBIPSProviderInstaller.svextを右クリックする。メニューから"プログラムを開く"をクリックする
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/be610130-0f33-2b7c-297b-c449d797b6b0.png)

3.このファイルを開く方法を選んでください。で、"Oracle Smart View for Office"を選択する。OKをクリックする
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/68160f4a-6900-0b4d-06ab-2c4259bc5fed.png)

インストールされましたと表示されれば、OKです
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2516153/15a96fb1-ef16-19ad-5ed0-ed3782a4ef8a.png)

Excelを起動すると、新規接続作成時に「Oracle BI EE」がでてきます。


以上
オブジェクト配列の操作

オブジェクト配列の操作のサンプルプログラムです

```html
    <!DOCTYPE html>
<html lang="ja">
<head>
  <meta charset="UTF-8">
  <meta http-equiv="X-UA-Compatible" content="IE=edge">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>TEST21</title>
</head>
<body>
  <script>
          document.write(`<h1>成績一覧</h1>`);
          const array1 = [ 
                      { 'name': 'katoshi', 'score': 70 },
                      { 'name': 'kosakana', 'score': 60 },
                      { 'name': 'sasaku', 'score': 80 },
                      { 'name': 'hinano', 'score': 40 },
                    ];

          for(let i=0;i<array1.length;i++){
            let a = array1[i]["name"];
            let b = array1[i]['score'];
            document.write(`<p>${a}の成績は${b}点です</p>`);
          }          
  </script>            
</body>
</html>
```

JanaScript部分を表示します。
```JavaScript
document.write(`<h1>成績一覧</h1>`);
          const array1 = [ 
                      { 'name': 'katoshi', 'score': 70 },
                      { 'name': 'kosakana', 'score': 60 },
                      { 'name': 'sasaku', 'score': 80 },
                      { 'name': 'hinano', 'score': 40 },
                    ];

          for(let i=0;i<array1.length;i++){
            let a = array1[i]["name"];
            let b = array1[i]['score'];
            document.write(`<p>${a}の成績は${b}点です</p>`);
          }          
```
以上のようになります。
Python細かいことはこだわらない環境メモ

# 概要
- Pythonコード書く際に細かいことはこだわらずに環境を作りたい
    - AWSのLambda関数とか
- TODO: lintなど入れたい


# docker-compose.yml
```
touch docker-compose.yml
```

コンテナを使い回したいので `stdin_open: true` とする。
`docker compose run` で毎度起動するなら不要。

```docker-compose.yml
version: '3'

services:
  app:
    image: python:3.7-alpine
    volumes:
      - .:/webapp
    working_dir: /webapp
    environment:
      TZ: 'Asia/Tokyo'
    stdin_open: true
```

# 実行ファイル

```index.py
print('hoge')
```

コンテナ内で動作確認できる。

```
python index.py
# hoge
```
DBeaverのテーブルビューでカラム表示を変更する

テーブルのヘッダーを右クリックすると設定の項目がある。

![DBeaverカラム表示設定-0.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/990851/d82e32a3-97da-721d-82ec-12db4f59ecc5.png)

![DBeaverカラム表示設定.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/990851/9c37baec-8543-a945-9a25-3086f8771d15.png)

`nullable`や、型の`length`などを表示できる。

ヘッダーをドラッグアンドドロップすることで、表示列の並び替えも可能。
フォルダ内の拡張子を一括変更する(Windows)

## たくさんあるファイルの拡張子を一つ一つ変える指示を受けた

とある帳票フォーマットを作成するシステムの最新バージョンになるとファイルの拡張子が変わるようで、一度古い拡張子を開いて上書き保存すると、強制で新しい拡張子に変わるとのことでした。

それで全部拡張子変える作業を承りました。

めっちゃ眠くなる作業ですね。一刻も早く終わらせたい。

拡張子の変更なら別にエクスプローラーで名前を変えるだけでも良いのでは？

一応コピー作ってやってみたら問題なさそう。。。

でもそれでも一つ一つやると相当時間がかかる。何か魔法のような方法はないのか！？

# ありました。

そりゃあるでしょうよ。自分が知らないだけで、調べたら1分でした。拡張子を一気に全部変更するって個人ではあまりしないですもの。

これからも使いそうなのでメモです。

## Windowsの場合コマンドプロンプトで行うのが簡単

まず作業したいファイルが入っているフォルダに移動

```
cd c:\[your folder]
```

`dir`コマンドでフォルダ内のファイルを確認

```
dir

>> file1.png
   file2.png
   file3.png
```

`ren`コマンドでワイルドカードを使って拡張子を変更

```
ren *.png *.jpg
```

変更ができてるか確認

```
dir

>> file1.jpg
   file2.jpg
   file3.jpg
```

## Powershellの場合

Powershellの場合は`Get-ChildItem`のコマンドレットを使います

```
Get-ChildItem "C:\[your folder]\*.png" | Rename-Item -NewName{$_.Name -Replace "¥.png",".jpg"}
```

## 個人的にはこの作業だけならコマンドプロンプト

Powershellちょっと長くて面倒ですね。

使用頻度高くないのでわざわざaliasを設定するのも面倒ですね。

一つだけファイル名変更する場合は`Rename-Item`を使うというのも覚えることが増えて面倒ですね

コマンドプロンプトもPowershellもちょっとづつコマンド覚えてCUIに慣れていきたいです。
[TypeScript・Vue3] この呼び出しに一致するオーバーロードはありません....

## 環境
Vue3 × Typescript × Element Plus

### message
* この呼び出しに一致するオーバーロードはありません。
  前回のオーバーロードにより、次のエラーが発生しました。ts(2769)
* runtime-core.d.ts(962, 25): 前回のオーバーロードはここで宣言されています。

### 原因
* 外部のコンポーネントを使うときにおこりやすい？
* どこかしらの型が間違っている。

![ts-overload-notfound.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/990851/d35582f8-9c54-86ab-ff21-f4dece28b985.png)
![ts-overload-notfound-2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/990851/7a02b074-c773-6980-dd92-5e8d92b0f9fc.png)


型定義元を見てみると、

```ts
// ...
export declare const inputNumberEmits: {
    change: (prev: number | undefined, cur: number | undefined) => boolean;
    blur: (e: FocusEvent) => boolean;
    focus: (e: FocusEvent) => boolean;
    input: (val: number | null | undefined) => boolean;
    "update:modelValue": (val: number | undefined) => boolean;
};
// ...

```

となっており、`input`イベントの引数は`number|null|undefined`の三種類である。

```ts
// ...
const onChange = (value: number) => { ...
// ...
```
しかし、定義した関数は`number`のみとなっていたために、エラーとなっていた。

## 解決

`onChange`関数の引数を `(value: number|null|undefined)`とすると、エラーが消えた。
paiza.ioでelixir その164

# 概要
paiza.ioでelixirやってみた。
死活監視やってみた。

# サンプルコード

```
defmodule Counter do
	use GenServer
	def start_link(arg) when is_integer(arg) do
		GenServer.start_link(__MODULE__, arg, name: __MODULE__)
	end
	#@impl true
	def init(counter) do
		{:ok, counter}
	end
	#@impl true
	def handle_call(:get, _from, counter) do
		{:reply, counter, counter}
	end
	def handle_call(:up, _from, counter) do
		{:reply, counter, counter + 1}
	end
	def handle_call({:bump, value}, _from, counter) do
		{:reply, counter, counter + value}
	end
end

children = [
	%{
		id: Counter,
		start: {Counter, :start_link, [10]}
	}
]
{:ok, pid} = Supervisor.start_link(children, strategy: :one_for_one)
|> IO.inspect

Supervisor.count_children(pid)
|> IO.inspect

GenServer.call(Counter, :get)
|> IO.inspect
GenServer.call(Counter, :up)
|> IO.inspect
GenServer.call(Counter, :get)
|> IO.inspect
GenServer.cast(Counter, {:bump, 3})
|> IO.inspect

:timer.sleep(100)

GenServer.call(Counter, :get)
|> IO.inspect

#GenServer.call(Counter, {:bump, "oops"})
#|> IO.inspect

#GenServer.call(Counter, :get)
#|> IO.inspect




```

# 実行結果

```
{:ok, #PID<0.97.0>}
%{active: 1, specs: 1, supervisors: 0, workers: 1}
10
10
11
:ok

02:22:49.888 [error] GenServer Counter terminating
** (RuntimeError) attempted to cast GenServer Counter but no handle_cast/2 clause was provided
    lib/gen_server.ex:819: Counter.handle_cast/2
    (stdlib 3.11.2) gen_server.erl:637: :gen_server.try_dispatch/4
    (stdlib 3.11.2) gen_server.erl:711: :gen_server.handle_msg/6
    (stdlib 3.11.2) proc_lib.erl:249: :proc_lib.init_p_do_apply/3
Last message: {:"$gen_cast", {:bump, 3}}
State: 11
10
```

# 成果物

https://paiza.io/projects/OcchWfMlP-4asCGCbTOeCA?language=elixir


以上。
boto3 APIで実装するAssumeRole（Python）

## AssumeRoleとは
現在のIAMの権限から、異なるIAMロールへ権限委譲するときに利用するAWS API名。
本記事では、Lambdaに付与しているIAMロールからAssumeRole先のIAMロールへ権限委譲するための実装を後述。
![スクリーンショット 2023-01-13 11.04.06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/263017/3ca07396-fb58-9a97-f3dd-d3dcb2e38fad.png)
## IAMロールの構築
Lambdaに付与するIAMロールを作成
![スクリーンショット 2023-01-13 11.06.26.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/263017/659edbd3-e797-91a7-a5eb-ab4b8420069d.png)

AssumeRole先のIAMロールを作成（添付画像の信頼関係の設定必須！）
![スクリーンショット 2023-01-13 11.08.20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/263017/a2f4bbe3-da0d-d45f-4b81-394e2f82953a.png)
```json
{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "Statement1",
            "Effect": "Allow",
            "Principal": {
                "AWS": "arn:aws:iam::${アカウントID指定}:role/Lambda-Role"
            },
            "Action": "sts:AssumeRole"
        }
    ]
}
```

## AssumeRoleをするためのLambdaを作成
Lambda作成後に「AssumeRole用のスクリプト」を貼り付けてデプロイ後に、「Test」をクリック
![スクリーンショット 2023-01-13 11.11.24.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/263017/95a4feec-d77b-6c8a-8fdd-d5ec18c975a3.png)

### AssumeRole用のスクリプト
一部の値を除いて（${アカウントID指定}）、そのまま流用できます！

```python
import boto3

def lambda_handler(event, context):
    
    sts = boto3.client('sts',
                       region_name='us-east-1',
                       endpoint_url='https://sts.us-east-1.amazonaws.com')
                       
    print("## AssumeRole前のLambdaに付与しているIAMロールを出力 ##")
    print(sts.get_caller_identity())

    res = sts.assume_role(RoleArn='arn:aws:iam::${アカウントID指定}:role/lambda-iam-assumerole',
                          RoleSessionName='dev-assume-role')

    session = boto3.Session(aws_access_key_id=res['Credentials']['AccessKeyId'],
                      aws_secret_access_key=res['Credentials']['SecretAccessKey'],
                      aws_session_token=res['Credentials']['SessionToken'],
                      region_name='ap-northeast-1')
                      
    sts = session.client('sts')
    print("## AssumeRole先のIAMロールを出力 ##")
    print(sts.get_caller_identity())
```

## 結果の確認
AssumeRole前とAssumeRole先でIAMロールが変更されていること（権限委譲されていること）を確認できた
![スクリーンショット 2023-01-13 11.16.18.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/263017/9dfbc137-e969-2873-2e30-9d0914723963.png)
Fargateで読み取り専用ルートファイルシステムで動作させる場合の考慮

## 読み取り専用ルートファイルシステム
- コンテナ上のファイルシステムへの書き込みを禁止する設定
- 起動中にファイル書き込みができないため、セキュリティレベルが結構上がる
- 多くの場合、一時ファイル、PID生成、ソケットファイル生成などの挙動があるため、単純に本機能を有効にしただけでは、書き込みエラーでプロセスが上がってこないので、この辺りは調べないといけない


## どのように設定すればよいか

### AWS側
タスク定義に下記を追記

```json
{
  readonlyRootFilesystem = true
}
```

### アプリケーション側
- 書き込みが必要なディレクトリのみをDockerfileのVOLUMEでマウントする
- そうすると、ホストのファイルシステムへの書き込みができるようになる。
- また、このボリュームは揮発性であるため、コンテナ削除のタイミングでボリュームも削除される

#### 例

```Dockerfile
FROM alpine:3.11.3

RUN mkdir -p /hoge /fuga

VOLUME ["/hoge"]
```

### DockerfileのVOLUMEパラメータ
- これ実は使ったことがなかったので少し調べた
- `docker volume ls`で表示されるDocker volumeとは別物
- VOLUMEで指定したファイルシステムは他コンテナからマウントできる
- イメージ的には、Dockerで作るファイルサーバと思うと納得
- ローカルというか通常パッケージでインストールするDockerエンジンでは揮発性ではない（はず）

#### 検証
上記のDockerfileをビルドし起動
```
docker run -it --name work volumetest sh
```

コンテナ内でテストファイルを作成

```
# touch /hoge/aaa /fuga/bbb
# ls -l /hoge/ /fuga/

/hoge/:
total 0
-rw-r--r--    1 root     root             0 Jan 13 01:57 aaa

/fuga/:
total 0
-rw-r--r--    1 root     root             0 Jan 13 01:57 bbb

# exit
```

別コンテナからVolumeをマウント

```
docker run --rm -it --volumes-from work alpine sh
```

/hogeにはファイルがあるが、/fugaにはないことが確認できる。

```
/ # ls /hoge
aaa
/ #
/ # ls /fuga
ls: /fuga: No such file or directory
```
bundle exec cap production deploy でのエラー解決方法

## はじめに
プログラミング初心者による備忘録です。

今回は`Capistrano`を使用してのEC3への自動デプロイをする過程で発生したエラーについて、解決方法を残します。

## 発生している問題・エラーメッセージ
以下のコマンドを実行したところ
```
% bundle exec cap production deploy
```

下記のエラーが発生
```
00:00 git:wrapper
   
    中略

00:05 git:create_release
      01 mkdir -p /var/www/hoge/releases/20230111145424
    ✔ 01 ec2-user@35.79.231.12 0.079s
      02 git archive master | /usr/bin/env tar -x -f - -C /var/www/hoge/releases/20230111145424
      02 fatal: not a valid object name: master
      02 tar:
      02 これは tar アーカイブではないようです
      02
      02 tar:
      02 前のエラーにより失敗ステータスで終了します
      02

    後略
```
`fatal: not a valid object name: master`が何を言っているのか？

## 解決方法

①`deploy.rb`に以下の記述を追加
```
set :branch, 'main'
```
②追加後、GithubDesktopでコミットとプッシュ
③再度ローカルで自動デプロイのコマンド（bundle exec cap production deploy）を実行する

これで解消しました。

## 原因
`Capistrano`のデフォルトの設定としてGithubの`master`ブランチを読み込んでいたことが原因のようです。
（私のGithubではデフォルトのブランチは`main`）
これを`main`を読み込むんだよ、と設定してあげることで正常にGithubを読み込むことができます。
Googleプロジェクト管理：三つの制約モデル

# はじめに

わたしが [Google プロジェクト管理:プロフェッショナル認定証で得られた素晴らしい体験][google]を、要点をまとめ小さく分割して、わかりやすく簡潔に紹介していきます。

興味があれば、ぜひ ***"Google プロジェクト管理:プロフェッショナル認定証"*** を受講してみてください。

[google]: https://qiita.com/mapami/items/317ae776a2268fd54c8f

https://jp.coursera.org/professional-certificates/google-project-management

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2358573/a1cc3407-8d1d-b37c-1d3a-50bf9ea5159f.png" width="800">

# プロジェクトのスコープを管理する

スコープを管理することはゴール設定と密接に関係しています。例えば、スコープを再定義することでゴールが変わり、ゴールの修正でスコープが変わることがあります。

プロジェクトスコープの考え方は、プロジェクト全体を通して重要である。プロジェクトにはそれぞれ固有のゴールがありますが、プロジェクトマネージャーとしてのあなたの全体的なゴールは、スコープの合意事項に従ってプロジェクトを納品することです。これには、与えられた納期と承認された予算内にプロジェクトを納品することも含まれます。

しかし、これは言うほど簡単なことではありません。プロジェクトが進むにつれ、新たな課題、変化、要因が現れるたびに、妥協とトレードオフを繰り返す必要があります。

# 三つの制約モデル

チームメンバーが予定外のタスクを引き受けた場合、そのタスクに費やした時間以上のものが失われることになります。スコープ変更が許容できるかどうか、どのような影響を与えるかを判断するために、プロジェクトマネージャーは通常、三つの制約モデルを参照します。

三つの制約モデルとは、あらゆるプロジェクトの最も大きな制約である、以下を組み合わせたものです。

- ***<font color="MediumVioletRed">スコープの制約</font>***
- ***<font color="MediumVioletRed">時間の制約</font>***
- ***<font color="MediumVioletRed">コストの制約</font>***

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2358573/5028f490-b9e4-eb6b-d47c-05a8c8cd4f29.jpeg" width="600">

- 時間とは、プロジェクトのスケジュールや納期を指します。
- コストとは、予算、リソース、プロジェクトに携わる人たちのことである。

***<font color="MediumVioletRed">『時間とコストは、スコープと並行して慎重に管理されなければならない。』</font>***

この3つはすべてリンクしており、1つを変更すれば、他のものにも影響が及ぶというわけではありません。一方を変更すると、他の2つの制約にどのような影響を与えるかを理解することが重要です。プロジェクトが進むにつれて、どのようなトレードオフを許容するかを検討することが重要です。

これを成功させるためには、プロジェクトの優先順位を明確に理解する必要があります。スコープ、時間、コストに関して、何が最も重要かを知っておく必要があります。もし、守らなければならない期限が決まっているのであれば、その期限を過ぎてしまうようなスコープの変更は制限する必要があります。 

# トレードオフのシナリオ

### シナリオ①

ある製品機能を向上させるための要望が出されました。製品に変更を加えることは、スコープ変更となります。予算は変えられないが、スケジュールを延長することは可能です。そこで、予算が増えない限り、スコープ変更の要求を受け入れて、タイムラインを延長することができます。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2358573/0198b2b3-2fe5-07c3-16bb-28d35ee7b6e2.png" width="550">

### シナリオ②

スコープを変更せずに予算を削減する要求が出された。最終的な成果物は、あなた方全員が最初に合意したとおりの機能を備えている必要があります。もし、予算を減らして、スコープを維持するのであれば、タイムラインを延長する必要があるかもしれません。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2358573/4c40da7c-c5c0-9643-1e80-24061c7994f1.png" width="550">

### シナリオ③

スケジュールを厳しくして早く終わらせたいが、予算は増やせないという要望があります。そのためには、スコープを変更する必要があります。最終的な結果は、当初の合意どおりにはなりませんが、要求どおり早く、予算内で納品できることになります。

<img src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2358573/03c8aadc-9407-4b22-0370-0614cef072d0.png" width="550">

:::note info
結局のところ、三角形のどの要素がプロジェクトにおいて最も重要であるかの優先順位付けが重要なのです。
:::
WebStorm(IntelliJ)における"Promise returned from ... is ignored"の警告を消す

Promiseが返ってくるけど別にawaitする必要ない(できない場合も多々な)ときにWebStormでは以下のような警告が出てしまいます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385410/40e30a2b-70a8-7c90-caee-59370ea273c8.png)

上記のキャプチャはaws-amplifyというライブラリの非同期メソッド"federatedSignIn"を使用しています。

ほんとに些細なことですが、警告が残ってるのは気になるし、一番最初にIDEより提案される解決方法が`then()`をつけるというものです。
これもまた、あってもいいけど不要だしな…とずっと思っておりました。

これに対して個人的にいいと思う解決方法があったのでメモ的に。

# 解決法

`void`をつける。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/385410/2a498aa2-6677-d4fc-524e-2941c6a8475f.png)

以上。

# 軽く解説

あまりJavascriptを書いていて単一のStatementでvoidと書いたことが無かったので改めて調べてみました。

https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Operators/void

簡単に言えばその式の生み出す値をundefinedにするということのようです。

つまり今回で言えばPromiseが生まれていたのがundefinedになったので警告が消えたということですね。
返却値が不要なので記述的にも意味があっており、すっきりして非常に良い解決法だと思いました。
all()とand、any()とorの違い

北海道をこよなく愛するピーターです。
意外にも
「python all and　違い」
「python any or　違い」
で検索してもヒットしなかったので記事に残します。

# はじめに
pythonには条件文を書くときに便利な組み込み関数が存在します。
それは`all()`と`any()`です。
どう便利なのかというと、`and`と`or`を繰り返し記述しなくて済みます。

# 記事を書いた背景
これらの便利な関数の使い方についてネットで検索すると、`all()`と`and`は同一です！という記事ばかりでした。
しかし、両者の挙動は別物です。このことに悩まされたため記事を書きます。

# all()とany()を使ってみる（違いがない場合）
実際に`and`と`or`を使ったコードと`all()`と`any()`を使ったコードを比較してみます。
```all.py
a = 1
b = 2
c = 3

#andを使った場合
if a == 1 and b == 2 and c == 3:
    print('and int')
#組み込み関数all()を使った場合
if all([a == 1, b == 2, c == 3]):
    print('all int')

# and int
# all int

```

```any.py
a = 'a'
b = []
c = 1

#orを使った場合
if a == 1 or b == 1 or c == 1:
    print('or int')
#組み込み関数any()を使った場合
if any([a == 1, b == 1, c == 1]):
    print('any int')

# or int
# any int

```

このように`all()`や`any()`を使うと見た目がスッキリしますね。

# 挙動が異なるとき
先にコードを記載します。

```diffrence.py
#型がintであるか判定する関数
def is_int(v):
    return type(v) is int

l = [i for i in range(2)]
for i in range(len(l)):
    print(f"{i=}")
    #orで記述
    if is_int(l[i]) or is_int(l[i+1]):
        print('or type int')
    #anyで記述　i=1のときエラーが発生します
    if any([is_int(l[i]), is_int(l[i+1])]):
        print('any type int')
    print('-'*50)

# i=0
# or type int
# any type int
# --------------------------------------------------
# i=1
# or type int
# IndexError: list index out of range
```

このように　`or`のときはエラーが発生しないのに`any()`のときはエラーが発生します。
## 原因
`or`ではTrueがあったらそこで条件文の評価を終えて評価を返すのに対し、`any()`ではすべての条件文を評価した後に評価を返すことが原因です。
このことをもう少し挙動に迫ったコードで説明します。

## 検証コード
コード中の`hoge`は未定義の変数です。したがって、`or`を書くと
`NameError: name 'hoge' is not defined`
とでるような気がします。どうでしょうか？エラーはでるのでしょうか？
```or.py
if True or hoge:
    print('True')
# True

```
**エラーは出ません！すなわち`hoge`は読まれていません。**

では`any()`はどうでしょう？

```any.py
if any([True,hoge]):
    print('True')

# NameError: name 'hoge' is not defined

```
**エラーが出ました！listの中身をすべて評価していることが分かります。**

# まとめ
`and`と`or`、`all()`と`any()`は評価方法が違うことが分かりました。

今回の検証ですと`and`と`all()`は同じ結果になります。ただし、評価方法が違うことは頭に入れておきたいです。いつか役に立つ気がします。

「`or`ではうまくいくのに`any()`ではうまくいかないのなんでやねん！」と思った方の疑問解決になれば幸いです。
コードレビューを単純に導入するだけでは問題が起きた話💔 - ラベルバッチをつけよう🤗

# はじめに
ラベルを付けることでレビューのやり取りがスムーズにいくようになった、実体験に基づくお話しです。

# 背景
少人数かつベンチャーだったこともあり、コードレビューの文化がありませんでした。
人によってコードがバラバラで、知識の共有もできていませんでした。
そこでコードレビューを提案し、導入することにしました。
ただ、これまでのバックグラウンドの違いもあり、議論が終わらなかったり、命令口調だったりで以下のような問題が起きました😭
💔 チーム内の雰囲気が悪くなってしまった
💔 レビューが終わらずタスクの進捗が悪くなってしまった

そこで導入したのが**HRT**と**ラベル**です。
今回は**ラベル**についてお伝えします🤗

HRTについては以下の記事を見ていただけると嬉しいです。
[コードレビューを単純に導入するだけでは問題が起きた話 - HRT（ハート）の精神を大切にしよう！](https://qiita.com/miyukoga/items/90d3f449617fdd5d7e42)

# ラベルとは？

レビューの意図を正しく伝えるために、コードレビューにつける分類のようなものです。

|  ラベル  |  意味  |
| ---- | ---- |
|  must  |  必ず対応してほしい！  |
|  imo  |  自分の意見や提案、好み。 自分ならこう書くけどどうかな？  |
|  nits  |  細かい指摘。インデントやタイポなど。  |
|  ask  |  質問や確認。コードの意味や背景が分からないから教えて！こういう理解でOK？  |
|  suggestion  |  提案。こうしたらどうかな？  |


# なぜラベルが必要なのか？

どういう意図でコメントしているのかを伝えることができるので、コミュニケーションがスムーズになります。
必ず対応すべきものが明確になるので、急ぎの際などに最低限対応するなど、状況に合わせての対応が可能になります。

# ラベルをバッジで表示する

見やすくなるので視認性をあげることができます。


|  ラベル  |  バッジ  |  構文  |
| ---- | ---- | ---- |
|  must  |  ![badge](https://img.shields.io/badge/review-must-red.svg)  |  `![badge](https://img.shields.io/badge/review-must-red.svg)`  |
|  imo  |  ![badge](https://img.shields.io/badge/review-imo-orange.svg)  |  `![badge](https://img.shields.io/badge/review-imo-orange.svg)`  |
|  nits  |  ![badge](https://img.shields.io/badge/review-nits-green.svg)  |  `![badge](https://img.shields.io/badge/review-nits-green.svg)`  |
|  ask  |  ![badge](https://img.shields.io/badge/review-ask-blue.svg)  |  `![badge](https://img.shields.io/badge/review-ask-blue.svg)`  |
|  suggestion  |  ![badge](https://img.shields.io/badge/review-suggestion-blue.svg)  |  `![badge](https://img.shields.io/badge/review-suggestion-blue.svg)`  |

# 便利ツール

- **[Text Blaze](https://blaze.today/)**
スニペット管理のブラウザ拡張機能です。入力を省略できるので超便利です。
以下の記事で登録方法を詳しく書かれているので参考になります。
[プルリクエストへのコメントでは Text Blaze でラベルバッジをつけよう！](https://qiita.com/iganin/items/aee297eade84849cc9cd)

# やってみた感想

ラベルをつけることでレビュアーの意図を理解しやすくなり、コミュニケーションがスムーズに行えるようになりました。
優先度も明確になり、状況に合わせて判断することができるようになり、レビューにかかる時間も短縮することができました👍

# 参考

https://qiita.com/iganin/items/aee297eade84849cc9cd

https://qiita.com/jumperson/items/8948989dd641bc9d404e
LPC812MAXとSSD1306で「12345678」を表示(16x24)(Keil Studio)



x なぜかMBEDオンラインコンパイラが終わってしまったのでkeilに移行

x 過去ログをみよ


![o_cop335.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/d9ae8a3f-4f53-85c7-3706-6863762998ae.jpeg)


![o_cop336.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/840352/5b874abc-33c3-abb0-0366-b00a163ba953.jpeg)


元

https://qiita.com/caa45040/items/2fe74b7b7b22142234db



```c++



//oled_test2_16x24_812_1

#include "mbed.h"
#include "SSD1308.h"

//i2c initialization
//       SDA    SCL
I2C i2c(P0_10, P0_11); //812


//メイン関数
int main()
{

    wait_ms(500); //0.5秒の待ち

    int ii; //ループカウンター
    int nn; //文字カウンター

    // Instantiate OLED
    SSD1308 oled = SSD1308( &i2c , SSD1308_SA0);

    //char n1_8[] = "12345678";
    char n1_8[] = "87654321";
    //char n1_8[] =   "88888888";

    ii=0;
    for(nn=0; nn<8; nn++) {
        //                y   x
        oled.writeBigChar(0, ii*16,n1_8[nn]);
        ii = ii + 1;
    } //for
        
    while(1) {}

}//main




```
DP-900: Microsoft Azure のデータの基礎に合格した話

本エントリーはAdvent Calendar 2022「[NKC-UG Advent Calendar 2022](https://qiita.com/advent-calendar/2022/nkc-ug)」の10日目のエントリーです！

# はじめに

こんにちは。[ノル](https://twitter.com/noll6451)です

今回は「NKC-UG」主催のアドベントカレンダー「[NKC-UG Advent Calendar 2022](https://qiita.com/advent-calendar/2022/nkc-ug)」の10日目にエントリーしました
## きっかけ
Microsoftの資格を一通りとったので、備忘録代わりです。(いま調べたらMS900受験できるようになっているので、近いうちに取りに行く)
自分の合格したMicrosoftの資格一覧は[こちら](https://www.linkedin.com/in/rei-suzuki-22b443211/)で見れます。
~~NKC-UGの代表だから仕方なくではない~~

#この記事の対象者

- Microsoftの認定試験を受験予定の人
- Azureのデータに関する勉強したい初心者の方
- 学生向け

## この資格の説明
[公式](https://learn.microsoft.com/ja-jp/certifications/azure-data-fundamentals/)では
>コア データの概念と、Azure データ サービスを使用して実装する方法に関する基礎知識を検証する。
Azure Database Administrator Associate、Azure Data Engineer Associate、Data Analyst Associate、Azure Developer Associate など、他の Azure ロールベースの認定資格の基礎を補強する。ただし、これらの資格の必須条件ではない。

となっております。

クラウド(特にAzure)のデータをどう扱う方法があるかを問う試験です。
ちなみに
この試験も、社会人、学生関係なく**無料**のバウチャーがもらえる方法があります。


## 試験予約編
社会人も学生も無料になる方法があります(社会人の方はこちらの方法ですが、学生の方は2通りあります)
まずは、下から有無言わさず予約してください。この時のメールアドレスはしっかりと保管してください(個人のメールアドレスが推奨です。)

https://www.microsoft.com/ja-jp/events/top/training-days/azure?activetab=a1:primaryr6

前から録画してある動画を流すウェビナーなので、ぶっちゃけどんな状況でも受けれます。ただしっかりと出席だけはしてください。(バウチャーがもらえないので)

## 勉強方法
この試験ですが、前の記事と同様、ほとんど情報少ないです。
上記のウェビナーですが、合格したいなら、真剣に聞くことをお勧めします！(ほんとに！ここでしか言わない情報が多すぎる)

https://learn.microsoft.com/ja-jp/certifications/exams/dp-900


まずは**ヒント**というところをしっかりとみてください(重要です)
実際の試験の操作も体験できます。
その次に下にスクロールすると、勉強できるようにラーニングパスがあるので
それに沿って勉強すれば十分です。(もちろん無料です)

## 公式の問題集

https://learn.microsoft.com/ja-jp/certifications/resources/dp-900-sample-questions?azure-portal=true

# 試験を受けるときの注意点

- 日本語がおかしい場合がある(英語に直す、察する)
- 採点されない問題が出てくる
- 出題範囲にない問題が出てくる(たぶん採点されてない？)
- 人によって問題数が違う
- 意外と時間がないので、サクサク進める(後から回答し直せる)
- 分からなくてもとりあえず何かしら選ぶ(1000点中合格スコア700だけど、7割ではないらしい)


Microsoft試験基礎シリーズの6記事めです。
ぜひこれを機にとってみてはいかがですか？？(実は、基礎資格は有効期限はないです)
ちなみ学生ですが、実は単位認定される可能性があります。

https://learn.microsoft.com/ja-jp/certifications/college-credit


皆さんの合格をお祈りしてます。

Microsoft試験基礎シリーズ
1記事め

https://qiita.com/Rei1729/items/89d693c73e0156764beb

2記事め

https://qiita.com/Rei1729/items/d889385246886ec9dfa9

3記事め

https://qiita.com/Rei1729/items/f635ec940beaef6a6e6a

4記事め

https://qiita.com/Rei1729/items/b6b10aaef702763c0289

5記事め

https://qiita.com/Rei1729/items/6592e2c5b5cdede1fe36

6記事め

https://qiita.com/Rei1729/items/01f0845eaf8b5d88939b
[AWS学習] 責任分担セキュリティモデルとIAMについての学習メモ

## 責任分担セキュリティモデル
**利用者** と**AWS** が協力してセキュリティを高める考え方
・不正アクセスの保護など

### システムのどの階層について責任を分担するかは利用するAWSサービスによって異なる
アブストラクトサービス > コンテナサービス > インフラストラクチャサービス
の順で**AWSの責任範囲** が多い

#### インフラストラクチャサービス（例：EC2）
##### 利用者の責任範囲
・データ
・アプリ
・OS
・ネットワーク
・ファイアウォール
・データ・通信の暗号化
・AWSアカウント
・IAMユーザ
##### AWSの責任範囲
・インフラストラクチャ（物理ホスト/ストレージ/ネットワーク）
・AWSデータセンタ（リージョン/AZ/エッジロケーション）

#### コンテナサービス（例：RDS）
##### 利用者の責任範囲
・データ
・アプリ
・暗号化
・プラットフォーム/アプリケーション管理
・ファイアウォール
・AWSアカウント
・IAMユーザ

##### AWSの責任範囲
・OS
・ネットワーク
・インフラストラクチャ（物理ホスト/ストレージ/ネットワーク）
・AWSデータセンタ（リージョン/AZ/エッジロケーション）

#### アブストラクトサービス（例：S3）
##### 利用者の責任範囲
・データ
・クライアントサイド暗号化
・AWSアカウント
・IAMユーザ
##### AWSの責任範囲
・ネットワーク/サーバーサイド暗号化
・プラットフォーム/アプリケーション管理
・OS
・ネットワーク
・インフラストラクチャ（物理ホスト/ストレージ/ネットワーク）
・AWSデータセンタ（リージョン/AZ/エッジロケーション）

### 注意点
侵入テストなどセキュリティ対策後のテストを行う場合は、AWSに事前申請が必要！
申請なしで実施すると **利用規約違反** となるので注意

## ルートアカウント
アカウント作成時のアカウント
全ての操作が可能
権限の制御はできない
操作ミス、パスワード漏洩などのセキュリティ観点から、**ルートアカウントは使用しない** ことが望ましい。

AWSの操作は、アカウント内に別ユーザーを作成してそのユーザーで行う。
1アカウント内にユーザーは複数作成が可能。

### IAM（Identity and Access Management）
AWSの各種サービスを利用する上での認証とアクセス制御を提供するサービス

IAMで、ユーザー（IAMユーザー）やグループ（IAMグループ）を作成。
ユーザー、グループ毎にアクセス制御を設定（IAMポリシー）する。
（各種リソースにアクセス権限を付与する IAMロール というものもある）


IAMポリシーは、**最小権限のアクセス権**を与えることが望ましい。

＊　アクセスの許可と拒否、両方が設定されている場合は、**拒否のポリシーが優先** される

## AWSサービスの操作方法と認証情報
| 操作方法    |                            | 認証情報                        | 
| ----------- | -------------------------- | ------------------------------- | 
| Webブラウザ | マネージメントコントロール | ユーザー名 / パスワード         | 
| コマンド    | AWS CLI                    | アクセスキー / シークレットキー | 
| プログラム  | AWS SDK                    | アクセスキー / シークレットキー | 

＊　プログラムでの認証情報の利用は非推奨！
→ 認証情報の更新、パスワードの流出の危険性があるため。
**IAMロールを割り当てることが望ましい**
例）　EC2インスタンスにIAMロールを割り当てると、アクセスキー/シークレットキーがなくてもアクセス可能になる


## IDフェデレーション

### 使用シーン
・複数の使用頻度が少ないユーザーに対して、IAMユーザーを登録をするのが手間。回避策としてIDフェデレーションを使用する

### 用語
#### STS（Security Token Service）
一時的に認証情報を付与するサービス

#### IDブローカー（IDプロバイダー）
認証用サーバーのイメージ
認証基盤は、ユーザーが独自で用意

シングルサインインなどにも対応しているのでそちらを使うのもOK
（Google、Facebook、SAMLなど）

### 仕組み
IDフェデーションを使用して、S3に一時的にアクセスする方法

1. ユーザーが社内に立てたIDブローカー（認証サーバー）にアクセス
1. ユーザーID/パスワードなどを入力してログイン
1. IDブローカー（認証サーバー）がSTSから、一時的に認証情報を取得する
1. STSから取得した認証情報を使ってS3にアクセス（アップロードなど）
顧客分析の手順 - データの整理

:::note
この本書は2017年4月1日にTeradata Japanのブログに掲載された内容を、再掲載したものです。
掲載内容の正確性・完全性・信頼性・最新性を保証するものではございません。
また、修正が必要な箇所や、ご要望についてはコメントをよろしくお願いします。
:::


著者 山本 泰史 （やまもと やすし）


# 顧客分析の手順

## 第3回： データの整理
顧客分析でデータを準備するにあたって、どのようなデータが利用可能かを整理する必要があります。通常データウェアハウスには、正規形もしくはそれに近い形でデータが格納されており、それを利用者が使いたい形式に集計、派生、変換して利用します。顧客分析においても同様のプロセスを踏みます。

正規形で格納されたデータとは、技術的定義を抜きにして簡単に表現すれば、データの重複を排除しつつ、各データ項目間の関係性が適切に維持されたデータ保持の形式です。これによって取り出したいデータがどこにあるかを一意に特定でき、あるデータと別のデータを関連付けて取り出せるようになります。しかしながら見たい形は利用者によって異なるため、データを取り出す際にその形式へと変換します。

ここでは、一般に最終消費者と直接的な取引をする企業において保持するであろうデータ項目と分類、そしてその関係性について、大まかにご紹介します。もちろん個別企業によって得られるデータは異なるため、それぞれの企業で適用する際にはこれを雛形に自社向けに定義しなおす必要があります。

### データ項目 
以下の図4 に代表されるデータが分析の対象となります。大きくデモグラフィックデータ、サイコグラフィックデータ、そしてビヘイビアルデータに分けています。

### デモグラフィックデータ:
日本語にすると人口動態データとなりますが、人口動態調査によく用いられるようなデータの意です。性別、年齢といった個人の特徴や保持物品（自動車の車種や不動産等を含む）を表すデータが対象です。例えば自動車保険を扱っている企業であれば自動車の車種データを有することは不自然ではないですが、クレジットカード企業がこれを持つことは困難かもしれません。そのため保持できるデータには業界によって違いがあります。共通して保持できるのはお名前、性別、年齢、住所といったデータが該当すると想定します。また便宜上、顧客を識別するために付与された顧客番号データ（世帯番号や口座番号等も）をここに含めています。

### サイコグラフィックデータ:
心理的特徴に関するデータ。アンケート調査が主な入手ソースとなります。このデータの分析上の強さは、顧客行動の背後に存在する意図をより深くできる点にあります。しかしながら一方ですべての顧客から同一レベルのデータを入手するのは困難であるため、分析目的によってはデータとして適切でない場合もあります。また、アンケート取得時点での心理特徴を捉えたデータでしかないため、その後の心理的変化を考慮するには、継続的に同等のデータを取得していく必要があります。

### ビヘイビアルデータ:
行動的特徴に関するデータ。電子的に構築された POS、ATM、コールセンター、Webサイト等のチャネルであれば、自動的に取得できるという特徴があり、またデータの量としても充分に活用可能なだけ確保できるという特徴を有します。一般に取引データを意味しますが、契約、Webサイトの訪問ログ、電話会社における通話履歴等もここに含まれます。


<img width="800" alt="image.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2768546/888eb191-ea7e-19e4-0ea9-40d4e6ab691e.png">

### データの分類
データベース上のデータは大きく、本来の意味のデータである「実績」データと、実績データがなんであるかを説明してくれる「マスターデータ」に大別されるのが一般的です。実績データは上述したデータ項目におけるサイコグラフィックデータとビヘイビアルデータが該当します。一方でマスターデータ（階層データを含む）に関しては以下が主たるものです。
１. 顧客マスター：上述のデモグラフィックデータが該当（誰の行動なのか？）
２. 商品／サービスマスター（何に関する行動なのか？）
３. カレンダーマスター（いつ発生した行動なのか？）
４. チャネルマスター：店舗マスター、Webサイトのページマスター等（どこで発生した行動なのか？）
括弧内は、実績データをどのように説明してくれるかについて示しています。また、以下のようなマスターデータも保持候補です。しかしながら本稿では、別稿（キャンペーン評価の手法）にてこれらの利用について解説しているため、以下を利用したキャンペーン評価の分析に関しては割愛します。


１. キャンペーンマスター（どんなキャンペーンを案内したのか？）
２. マーケティング経費マスター（幾ら費やしたのか？）


### データ間の関係
ここまでの関係を図示したのが以下の図5 です。実績データは「誰が？」、「何を？（商品／サービス）」、「いつ？」、「どこで？」、そして「どれだけの量の行動を起こしたのか？（もしくはある行動を起こしたか、否か？）」についての履歴を有しています。そしてこれに対してマスターデータを通じて識別、説明ができるように関係が記述されています。データベース上では実績データの外部キーと、マスターデータの主キーが対応するようになっており、このキー（コード情報）を紐づけることによってデータ全体がつながっています。

<img width="800" alt="image.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2768546/ffb3378f-c59d-386b-6349-6a0a4ae462de.png">


以上、顧客分析に利用される代表的なデータを概観しました。次回はこれらのデータを用いて、分析に利用しやすいようにデータを整理しなおします。




#### Teradata Vantageへのお問合せ
[Teradata Vantage へのお問合せ](https://www.teradata.jp/About-Us/Contact)
グローバルIPアドレスを最速で調査する方法

# はじめに
本記事はグローバルIPアドレスを最速で調査する方法について記載しています。

セキュリティインシデント発生時に、[IPアドレス](https://ja.wikipedia.org/wiki/IP%E3%82%A2%E3%83%89%E3%83%AC%E3%82%B9)（※）を調査する際の初動対応を速やかに行うためには、信頼できるソースを基に調査方法を確立しておくことが重要です。
（※本記事のIPアドレスは、グローバルIPアドレスを指しています）

自分が使用しているグローバルIPアドレスは、[NordVPN](https://ja.wikipedia.org/wiki/NordVPN)が提供している、以下のようなサイトから確認することができます。

- [あなたのIPアドレス](https://nordvpn.com/ja/what-is-my-ip/)

国内でも類似サービスが存在しますが、本記事では信頼性の高いipinfo.ioを使用した調査方法や、その他役に立つ情報をまとめています。

## ipinfo概要
**ipinfo.io**は、IPアドレスに関わる信頼できるソースを提供しているIPデータのサービスです。

https://ipinfo.io/

[IPinfo Customers](https://ipinfo.io/customers)のページを見ると、広告などインテリジェンスを意識したサービスを開発するために、世界中の企業が利用していることが分かります。

プロダクトとして、メインである[IP Geolocation API](https://ipinfo.io/products/ip-geolocation-api)など色々なAPIが用意されています。

[Flexible pricing for the most accurate IP data](https://ipinfo.io/pricing)を参考に、Free planが用意されているので、毎月50,000件の範囲であれば無料で利用することができます。

なお、IP Geolocation APIは認証なしでも利用することができます。
試してみましょう。

## IP Geolocation API
**IP Geolocation API**は、IPアドレスに関連する地理情報を取得するためのAPIです。

試すにあたって会員登録も不要です。
ブラウザや、curlコマンドなどを用いて簡単にAPIを実行することができます。

目的毎に応じた簡単な使用例について、以下に記載します。

### 現在使用している端末のIPアドレス及び地理的情報を取得する
ブラウザから[ipinfo.io](https://ipinfo.io/)にアクセスまたは、以下のコマンドを実行することで、現在使用している端末のIPアドレスに関連する地理的情報をJSON形式で取得することができます。

`$ curl ipinfo.io/`

### 現在使用している端末のIPアドレスのみを取得する
現在使用している端末のIPアドレスのみを取得したい場合は、URLのパスに`ip`を指定することで取得できます。

従ってブラウザから[ipinfo.io/ip](https://ipinfo.io/ip)にアクセスまたは、以下のコマンドを実行します。

`$ curl ipinfo.io/ip`

### IPアドレスの調査
IPアドレスを調査する場合、URLのパスに調査したいIPアドレスを指定することで、対象のIPアドレスに関わる情報を取得できます。

以下は[Google Public DNS](https://ja.wikipedia.org/wiki/Google_Public_DNS)のDNSサーバを指定した例です。

- ブラウザの出力例

![スクリーンショット 2023-01-10 22.04.25.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/221759/120b3016-361d-6681-eb5f-4acf7475ede8.png)

- curlの出力例

`$ curl ipinfo.io/8.8.8.8`


```console
{
  "ip": "8.8.8.8",
  "hostname": "dns.google",
  "anycast": true,
  "city": "Mountain View",
  "region": "California",
  "country": "US",
  "loc": "37.4056,-122.0775",
  "org": "AS15169 Google LLC",
  "postal": "94043",
  "timezone": "America/Los_Angeles",
  "readme": "https://ipinfo.io/missingauth"
}
```

## その他
インターネットは、[自律システム (インターネット)](https://ja.wikipedia.org/wiki/%E8%87%AA%E5%BE%8B%E3%82%B7%E3%82%B9%E3%83%86%E3%83%A0_(%E3%82%A4%E3%83%B3%E3%82%BF%E3%83%BC%E3%83%8D%E3%83%83%E3%83%88))の集合です。

グローバルIPアドレスに関するネットワークの調査を行う場合に、役に立つ情報を最後に紹介します。

### AS番号が知りたい
日本の**AS番号**は、[JPNIC](https://www.nic.ad.jp/)によって運営されている、以下`as-numbers.txt`より確認できます。

- [AS番号リスト](https://www.nic.ad.jp/ja/ip/as-numbers.txt)

ASに興味がある場合は、JPNICの以下をご参照ください。

- [AS番号の割り当てに関する参考情報](https://www.nic.ad.jp/doc/jpnic-01244.html)
- [4.2 ASの申請方法](https://www.nic.ad.jp/ja/newsletter/No11/4-2.html)

### ルーティング情報
NTTの**Global IP Network Looking Glass**は、バックボーンインフラストラクチャに関するネットワークのルーティング情報を提供します。（※利用する際は利用規約の同意が必要です。）

- [Looking Glass](https://www.gin.ntt.net/looking-glass-landing/)

外部ASの通信などを確認したい時に重宝すると思います。

# おわりに
IPアドレス一つから色々なことが分かるのが理解できたのではないでしょうか。

興味がある場合は、調べてみると面白いと思います。

## 参考
- [Getting Started](https://ipinfo.io/developers)
画面遷移時・ページ読み込み時に一瞬表示が崩れるのを防ぐ方法

サイトを開いた時、ページ読み込み時に一瞬表示が崩れたり、アニメーションがチラつくことありませんか？

「一瞬だから別に良くね？」

と思ったらダメです。

## 画面遷移時・ページ読み込み時に一瞬表示が崩れる理由

以下の理由から一瞬表示が崩れるorチラつく場合があります。

- CSSとJavascriptの読み込みにちょっと時差がある
- `transform`, `animation`, `transition`を組み合わせいる場合
- `position: fixed`を指定している場合に、`display`で表示・非表示を切り替えていて、子孫要素に`transition`を使っている場合

私の場合は、ヘッダーとかで画面遷移時に一瞬だけアニメーションがチラつくことがよくありました。

## 画面遷移時・ページ読み込み時に一瞬表示が崩れるのを防ぐ方法

解決方法としては、一瞬表示が崩れる要素をCSSで非表示にしておいて、jQueryでフェードインさせます。

※jQueryの読み込みなどは省略

``` css
#header {
  display: none;
}
```

``` js

$(function() {
    $('#header').fadeIn(0);
});
```

これで、画面遷移時・ページ読み込み時に一瞬表示が崩れるのを防ぐことができます。
muiのsx propと styledについて調べてみた

## 調べた結果

- 共通したコンポーネントを作成するときには、`styled()`を利用してstyleも共通化する。しかし、1度しか使用しなければ`sx prop`も利用しても良さそう。


## [sx prop](https://mui.com/system/getting-started/usage/#the-sx-prop)

### 書き方

```
// JSX
<Button
  sx={{
    color: 'primary.main', // theme.palette.primary.main
    borderRadius: 1,
    p: 1, // padding: theme.spacing(1)
    m: {
      xs: 1, // [theme.breakpoints.up('xs')]: { margin: theme.spacing(1) }
    },
    minWidth: 300,
  }}
>
 クリック
</Button>
```
`color`や`p`のプロパティは省略して書かれている。

### 特徴
- Theme対応の[cssプロパティを省略](https://mui.com/system/getting-started/usage/#shorthands)して書くことができる。
    - [対応しているプロパティ](https://mui.com/system/getting-started/the-sx-prop/#theme-aware-properties)
- 特定のHTML要素に対してcssを当てることができる

> The sx prop is best suited for applying one-off styles to custom components.
// 1度限りのstyleを当てる際にsx propは最適

https://mui.com/system/getting-started/usage/#when-to-use-mui-system

> The sx prop, on the other hand, is a new way of styling your components, focused on fast customization.
// 時間をかけずにスタイルを当てる新しい方

https://mui.com/system/styled/#difference-with-the-sx-prop

### Pros
- styledコンポーネントに比べて、学習コストが少ない
    - 最低限のMUIのstyleの当て方を学習すれば良い
- コードの記述が少なくて済む
- 疑似セレクタ、メディアクエリ、入れ子セレクタを記述できる
    - https://maku.blog/p/87p5o2d/

### Cons
- コンポーネントのレンダリング時間が長くなる
    - https://mui.com/system/getting-started/usage/#performance-tradeoffs
    - https://github.com/mui/material-ui/tree/master/benchmark/browser/scenarios

## [styled()](https://mui.com/system/getting-started/usage/#the-sx-prop)

### 書き方
```
const Button = styled(Button)(({ theme }) => ({
  color: theme.palette.primary.main
  borderRadius: theme.shape.borderRadius,
  padding: theme.spacing(1)
  [theme.breakpoints.up('xs')]: {
    margin: theme.spacing(1)
  },
  minWidth: 300,
}));
```
### 特徴
`@mui/system`をimportして利用する。また、`@mui/material`を使っていれば、`@mui/material/styles`でも利用可能です。(それぞれの型をみてみると、使われているデフォルトのThemeが違う)

### Pros
- 複数のコンポーネントに共通したstyleを提供できる
- スタイルのみのコンポーネントとして分けて置ける
### Cons
- 学習コストがかかる
- スタイルのみのコンポーネントの存在に気づきにくい


MUIのスタイルをあててパフォーマンス比較をされている方もいたので、そちらを参考にするとさらに理解が深まると思います。


https://zenn.dev/enish/articles/a2314fc2c00cf7
LEGO SPIKE PRIMEで実際に動くドラえもんロボットを作ってみた

#  ■はじめに
LEGO SPIKE PRIMEを勉強していて、せっかくなので何か作れないかと考えていたところ、
ロボットといえば。。。あー、ドラえもん！と思いつきました。
でも、ハードは苦手なので実際にロボットは作れないな。。。と思案した結果
ぬいぐるみにロボットを入れて動くようにしてみては？と考え、早速、作ってみました(笑)

↓出来上がりはこんな感じ(笑)
<iframe width="560" height="315" src="https://www.youtube.com/embed/J_0ygAqj5_s" title="YouTube video player" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen></iframe>

実際のLEGOロボット
<iframe width="560" height="315" src="https://www.youtube.com/embed/Llcdi8vN-hI" title="YouTube video player" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen></iframe>

#  ■LEGO SPIKE PRIMEとは
LEGO GROUPが出しているSTEAM学習セットです。
※STEAMとは、Science（科学）、Technology（技術）、Engineering（工学・ものづくり）、Art（芸術・リベラルアーツ）、Mathematics（数学）の5つの単語の頭文字を組み合わせた教育概念

簡単に書くとLEGOでロボットを作ってプログラムを組んで、そのロボット動かしながら勉強する学習セットです。

##  どんなことができる？
SPIKE PRIMEセットを使えば以下のようなことができます。
・LEGOで作ったものを動かす（タイヤやプロペラなど）
・物との距離を識別する
・色を識別する
・ボタンを押した強さを判定する（重さにも使える）
・ライトをつける
・電光掲示板のように文字を表示できる
・音を出す
・WEB APIを呼び出す
・Pythonでコードを書くことも可能

## LEGO SPIKE PRIMEについて知りたい人向けおすすめサイト

公式スタートサイト
https://education.lego.com/ja-jp/start
児童用と先生用があります

SPIKEプライムチュートリアル
https://www.youtube.com/@LEGOEducationJapan
まずはこの動画を見るのがよいと思います。

#  ■ドラえもんロボットの制作

## 用意するもの

・LEGO SPIKE PRIME
・ドラえもんハンドパペット
・PC

## ドラえもんロボットの作り方
正面
頭の部分にボタン、上部の２つのタイヤ部分はドラえもんの口を動かすアーム、左右にあるアームはドラえもんの腕、土台の横にある目は何かが近づいてきたのを感知するようにしています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115627/fb173cdf-2765-99dc-a6ee-8d8a8b513d27.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115627/43b0690e-3d33-37b9-87b0-acd54317fe99.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115627/6695f5c8-b856-face-da0d-5ccbf3e56de0.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115627/2037e353-38d1-ffd5-0525-b899d5ecc592.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115627/7b53add7-2d88-f044-07d3-b9d890fbedbc.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115627/ae2bdda7-bfa4-40e4-2ca1-6f404a953b53.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115627/da5ae93a-08db-7b6a-fdd5-75f86965352d.png)

このロボットをドラえもんのハンドパペットに入れて動かします
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115627/70651543-44d6-ad7e-a5c9-8535e0e49a7b.png)

## プログラム
今回はビジュアルコードのみで制作しました。（2023/01時点ではSPIKEアプリのVer3はまだPython対応していないそうです。もうすぐ対応らしいです）いつか、Pythonにしたい。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115627/7e7dbf3f-7e27-8e2e-b104-5cbba76d35ac.png)

#  ■今後の課題
今回はロボットと呼ぶには程遠いできですが、今後はもっと緻密なロボットを製作できるキットが販売されることに期待したいです。

・腕の動きをより細やかに動かせるようにしたい
・歩かせたい
・音声認識して話すようにしたい
・PCからしか音が出せないのが残念(SPIKEの前製品であるmindstorms ev3ならできたのに。。。泣)
・表情がない
　ドラえもんの目の部分をくりぬいて、距離センサーを目にしようかと思ったのですがぬいぐるみに穴をあけるのはかわいそうだと思いとどまりました
・IFTTTやAPI連携で何かさせたい
　今回は天気予報APIで天気データを取得まで
・スマートスピーカー連携