OmniAICreator/Qiita-1.07M huggingface dataset:
New Relic APMのMost time consumingを特定のUser Agentでフィルタして分析する

これは、[New Relic Advent Calendar 2021](https://qiita.com/advent-calendar/2021/newrelic) | 12日目の投稿です。

## やりたいこと

New Relic APMでシステムのパフォーマンスのボトルネックを調査する際、はじめに確認するのは`Transactions　>　Most time consuming`ではないでしょうか。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/94938/df0cab5d-fbaf-b7d1-f786-384903536cb8.png)

このビューはWebのリクエストを処理時間×リクエスト数が多い順に表示しているため、ユーザが待機しているサーバ処理時間の中で支配的なリクエスト特定するために役立ちます。また、リアルタイムにユーザのアクセスパターンを知ることができるのも運用の知見を獲得する上でメリットがあります。
このような集計をする場合、GETリクエストはURIの中にユーザIDやアイテムIDを含むことが多く、アクセスログではグループ化が面倒なことがありますが、APMであればコントローラの処理単位となるため集計に頭を悩ませることがないのが良いですね。

この集計はAPMを導入しているアプリケーション単位で行われていますが、パフォーマンスのボトルネック調査はユーザ体験の改善に焦点を当てているため、同一アプリケーションの中でもクライアント別に集計したい要件がでてきます。

- Botや内部サーバからのリクエスト、ヘルスチェックは集計対象外にしたい
- Webとスマホアプリでアクセスパターンが異なるため、それぞれごとに集計したい

## やりかた

New Relic APMのUI上ではクライアントによって集計範囲をカスタマイズする機能はなさそうだったので（New Relic MobileやNew Relic Browserと連携すればできるのかもしれませんが）、元データのNRDBを当たってみることにしました。

NRQLを叩いてAPMのデータソースであるTransactionsをみてみると、`request.headers.userAgent`というデータが入っています。WHERE句で任意のフィルタを書いた上で、コントローラの処理の名称（name）でグループ化(facet）して、処理時間（duration）の合計（sum）を高い順に表示してあげれば、特定のUser Agentで`Transactions　>　Most time consuming`とほぼ同じ集計結果を表示することができそうです。

```sql
FROM Transaction SELECT sum(duration) as total_duration
WHERE request.headers.userAgent NOT LIKE '{USER AGENTの文字列}%'
FACET name ORDER BY total_duration DESC
```
ウィジェット追加画面からNRQLを実行して、
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/94938/68975533-4cce-231d-f05b-a9f00ab7d011.png)

全体・Web・スマホアプリでリクエストの傾向の違いを可視化するダッシュボードを作成してみました。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/94938/f984d542-bea7-b190-5ece-0890d11e29fe.png)

## まとめ

- 普段APMのUIでなんとなく見ているビューも大元のNRDBにあるデータをNRQLでクエリすればカスタマイズして表示することができる
- `SELECT * FROM Transactions`でどんなデータが入っているのかを一度確認しておくと何かに使えるデータを発見できるかも

New Relic APMを使いこなしてユーザ体験を改善しましょう！
SchemaSpyで生成したドキュメントを眺めてみる

## はじめに

- [前回](https://qiita.com/enuswi/items/be5982f7ff02d88547b5)は、WordPressを立ててSchemaSpyを試しました
- で今回、SchemaSpyで出力したドキュメントを見ていこうと思ったのですがWordPressだとあまり見どころがなさそうだなと感じたので、代わりに、以前運用していたことのあるECパッケージ `Magento2` を使ってみようと思います

## Magento2とは？

- PHP製の越境ECパッケージで無料版・有料版があります
- フロントサイトと管理画面が標準で用意されておりますし、ECで必要となる多くの機能を備えています
- 拡張性が高く、また標準で多言語・多通貨対応されております
- 国内ではあまり聞かれないですが海外では結構利用されているようです

## WordPressとMagento2のDB比較

- 見ての通り、テーブル数から全然差があり、WordPressで出力した際には数秒で終わったのですが、Magento2で出力した際には正味、数十分かかりました。。。!
- それでは各ページを眺めていきましょう

||テーブル数|カラム数|
|----|----|----|
|WordPress|12|94|
|Magento2|346|2846|

![スクリーンショット 2021-12-12 0.26.44.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46053/984de6e1-7275-fca0-b6d9-a2989bef8f05.png)

## Tables（テーブル一覧）

![スクリーンショット 2021-12-12 1.01.20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46053/e17e5f10-920c-52a3-f8c2-20748c950fcb.png)

## Columns（カラム一覧）

- キーや型などがぱっと見でわかりますね

![スクリーンショット 2021-12-12 1.09.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46053/09f0c62e-94b1-4489-f149-f1ad8386ec37.png)

## Constraints（外部キー一覧）

![スクリーンショット 2021-12-12 1.17.23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46053/5dcfc42f-6899-b5f9-6b42-bb1854a189c7.png)

## Relationships（リレーション）

- リレーションが多過ぎて一部しか表示できない・・・

![スクリーンショット 2021-12-12 1.19.29.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46053/038e348c-a7ed-6ba5-5094-14f6b10845f3.png)

## Orphan Tables（独立したテーブル一覧）

![スクリーンショット 2021-12-12 1.23.27.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46053/ff090180-7556-5dee-e7c8-6e23690c3da7.png)

## Anomalies（不整合？）

![スクリーンショット 2021-12-12 1.27.18.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46053/275ddbb0-f726-37db-bd2c-e045508a4e2f.png)

## Routines（ストアドルーチン）

![スクリーンショット 2021-12-12 1.47.33.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46053/4937bbbb-fb3d-2ba5-7674-5d9c7567dd3c.png)

## テーブル詳細

- サンプルとして `wishlist` テーブルを取り上げてみました
- デフォルトでシェア（Amazonのほしい物リストの公開的な）機能が用意されていたり、複数ストアに対応されていたりと非常に多機能ですね

![_Users_s.yoshimoto_mine_repositories_schemaspy-sample_magento2_schema_tables_wishlist.html.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/46053/a58100f8-8d0d-b517-5454-350af17f10bd.png)

## おわりに

- 今回は、SchemaSpyで生成したドキュメントの各ページを眺めていきました
- 全体の外部キーがまとめて確認できたり、リレーションが見れたり結構良いなぁと思いました
- また、今回は手間を省くためデフォルトで多数のテーブルが用意されるパッケージをサンプルに見ていきましたが、例えば途中から引き継いだプロジェクトで「DB定義ないっすー」みたいな時に、まずパッと作ってみて全体を俯瞰で見るのにも良いかなと思いました
Vue router を使った時の GitHub Pages での 404 対策

# どんな問題？
vue-router は SPA なので `/` 以外のページを直接叩きに行くと 404 する。

自分で nginx なんかでデプロイする場合は `try_files /index.html` とかで[綺麗に解決する](https://router.vuejs.org/guide/essentials/history-mode.html#nginx)が、 GitHub Pages だとこの設定はできない（たぶん）。

普通に `/` 以外のページに行ったあと F5 するだけで 404 するのでけっこうキツい。

## 追記
GitHub Pages では SPA ではなくMPA にするほうがよさそう。

https://qiita.com/kamicop/items/c5c0917ed226234ee288

MPA にすれば複数 index.html ができるので以下の対策は必要ない。

# 対策方法
GitHub Pages は `404.html` があると使ってくれるので、 `404.html` にスクリプトを仕込んでそこから `/#/hoge/fuga/` へリダイレクトする（これで `/` がロードされる）。
`/` 側では Vue が動く前に URL を `/hoge/fuga/` へ書き換える。

# 実装例
`public/404.html` をいい感じに作って `<head>` の中に下を追加。

```
    <script>
      (function (l) {
        l.replace(l.origin + "/#" + l.pathname);
      })(window.location);
    </script>
```

次に、 `public/index.html` の `<head>` の中に下を追加。

```
    <script>
      (function (l) {
        if (l.hash) {
          window.history.replaceState(null, null, l.hash.slice(1));
        }
      })(window.location);
    </script>
```

* `window.location.replace` は[履歴を残さない](https://developer.mozilla.org/ja/docs/Web/API/Location#methods)ので、戻るを押してもう一度リダイレクトされる心配はない。
* `window.history.replaceState` は[ページ遷移せずに URL を書き換える](https://developer.mozilla.org/ja/docs/Web/API/History/replaceState)。ここに `replace` を使うと無限ループするので注意。

# さいごに
上の実装例だとステータスコードは 404 になってしまう。
~~実際 [naca-nyan.github.io/converter/](https://naca-nyan.github.io/converter/) とかを開いて Dev Tool を見ると 404 が出る。うーん。~~
~~もっといい実装あったら教えてください。~~
MPA にしたので Not Found しなくなりました。

# 参考にした記事

https://qiita.com/hiyoko3/items/64e0658439c66b16e18c
NotionでJiraのプレビューを表示する

アルプ株式会社でエンジニアをしています、集約のエンティティ@pictinyです。
これは[Notion Advent Calendar 2021](https://qiita.com/advent-calendar/2021/notion) 11日目のエントリです。
10日目は[Notionの同期ブロックを使う](https://qiita.com/pictiny/items/62cc49058bfd1c3f7037)でした。

# Jira連携
Notionでは認証が必要なコンテンツのURLで[ブックマーク](https://qiita.com/pictiny/items/745cfcf562c6429a3efc#%E3%83%96%E3%83%83%E3%82%AF%E3%83%9E%E3%83%BC%E3%82%AF)を作ると、faviconやドメインが展開されるだけでコンテンツの中身が展開されません。
NotionとJiraを連携すればブックマークの作成時に認証を突破して、チケットのプレビューを表示することができます。

JiraのチケットのURLをペーストすると表示される `Connect to Jira to update` のボタンを押すと、Atlassianの認証画面が表示されます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/427952/a640ede1-301b-e017-5f43-840d3b1559a6.png)

認証したいアカウントでログインするとJiraと連携でき、連携後にJiraチケットのURLをペーストするとプレビューが表示されます。

連携したアカウントでは見れないチケットをペーストした場合には `Can't load preview` のメニューが表示されます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/427952/10a05c55-8b98-ff26-88ae-7759d972b131.png)

`Connect a different Jira account` で別のアカウントに連携することもできます。

# まとめ
Jiraのプレビューはとても便利なので、Jiraでチケット管理をしているなら連携を済ませておきましょう！
[裏技] githubのコントリビューションを手っ取り早く増やす方法

## 注意
- ※良いか悪いかでいうと、良くはないです。
- ※何のためにやるのかは正直不明です。
- ※実際にやるのはおすすめしませんが、できますよという話をします。

## 発端
githubを湿潤にしたい（草を生やしたい）と思ったけど、過去の日付を遡らないと面倒くさい……。
どうにかならないだろうか？

## それ、出来ます
ポイントは

```
git commit --date="日付型"
```

あとは必要な部分を適宜対応すれば期待した結果が得られるでしょう。

## コントリビューション数を稼ぐには
元々の発端は上記の通り、古い日付も草で茂らせる事でした。
が、別に日付を気にしないでもコントリビューション数は稼げます。
`git commit`さえ通ってしまえばよいのです。


ちょっと端折りすぎたのできちんと説明します。
githubに草を生やすので当然といえば当然ながらコントリビューションにカウントされます。
つまり、この仕組みを悪用すればコントリビューション数は事実上改竄が可能です。
その気になれば、1分で60コントリビューションはできるので、一気に数を稼ぐならマルチプロセスで動かせば良いです。
コンフリクトを確実に避けたいならファイルを分けたり、プロセスごとにリポジトリを分ける方法もあります。

## コントリビューション数を稼ぐとどうなるか
さて、私は元々Githubを使った就活・転職を主に行っています。
その中ではGithubへのコントリビューション数を聞かれる事は当然ありませんでした。
具体的にはGithubにどういうものを上げているか、セールスPRとか価格をつけたらいくらにするか、と言ったお話が主なので何の役にも立ちません。
精々マウンティングが関の山と思います。

## 注意
`git commit`まではローカル作業なので特に怒られはしないですが、
`git push`はサーバーに負荷を掛けるので、連発してはいけません。
何度もpushしたい瞬間はあると思いますが、せめて5秒ぐらい開けましょう。
また、5分間で10回以上アクセスがあったら攻撃行為っぽく見える[^1]ので、やりすぎはほどほどにしましょう。
[^1]: 【連続アクセスは何回までなら許されるか？】このあたりは人によります。

## 有効活用する方法があれば
コメント欄などで教えて下さい。。。

### 注釈
SQL Server: DBのレイテンシをパーセンタイル値で表現する方法について考えてみた

# 背景
SQL Serverにおけるクエリパフォーマンス関連のメトリックには「SQLServer:Batch Resp Statistics」があります。
これは、クエリベースでは以下のようなクエリで取得できます。

```sql
select * 
from sys.dm_os_performance_counters with(nolock)
where object_name like '%batch resp%'
and instance_name like '%Elapsed Time:Requests%'
```
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148310/cc9aa4f8-40f9-aeaf-d4b1-7477a61c0c3f.png)

この結果は累計値のため、サーバーが起動してから今までの間に、0-1msec未満のバッチが累計で249544168589回実行された、ということが分かります。そのままだとあまり価値のない情報ですが、2点間の差分をとることで、例えば1分間に0-1msecのバッチが10回、1-2msecのバッチが3回実行された、といった事実が分かります。

この情報でも有用なのですが、DBのレイテンシの傾向として、90パーセンタイル値、95パーセンタイル値、99パーセンタイル値を取得してグラフ化できるとより有益な情報になるのではと考えました。

完全に正確な値を取得する方法は思いつきませんでしたが、近似値であれば取得する方法を考えたので、本記事でクエリを共有したいと思います。

クエリは以下の通りです。5秒間におけるサーバーの90パーセンタイル値、95パーセンタイル値、99パーセンタイル値の近似値を取得することができます。

```sql
select getdate() as sampled_at, * 
into #stat
from sys.dm_os_performance_counters with(nolock)
where object_name like '%batch resp%'
and instance_name like '%Elapsed Time:Requests%'

waitfor delay '00:00:05'

insert into #stat
select getdate() as sampled_at, * 
from sys.dm_os_performance_counters with(nolock)
where object_name like '%batch resp%'
and instance_name like '%Elapsed Time:Requests%'

select
*
into #stat2
from
(
	select 
	*
	,cntr_value - LAG(cntr_value, 1, cntr_value) OVER(partition by counter_name order by sampled_at) as lag_value
	,row_number() over(partition by counter_name order by sampled_at desc) as rownum
	from #stat
) as a
where rownum = 1
order by sampled_at

select
*
,accmulated_lag_value*100. / sum_lag_value as accumlated_perentage
into
#stat3
from
(
select
*
,sum(lag_value) over(order by counter_name) as accmulated_lag_value
,sum(lag_value) over() as sum_lag_value
from
#stat2
) as a
order by counter_name

select
min(case when rownum_90 = 1 then counter_name else 'ZZZ' end) as percentile_90
,min(case when rownum_95 = 1 then counter_name else 'ZZZ' end) as percentile_95
,min(case when rownum_99 = 1 then counter_name else 'ZZZ' end) as percentile_99
from
(
select
row_number() over (order by case when accumlated_perentage >= 90 then accumlated_perentage else 99999 end) as rownum_90
,row_number() over (order by case when accumlated_perentage >= 95 then accumlated_perentage else 99999 end) as rownum_95
,row_number() over (order by case when accumlated_perentage >= 99 then accumlated_perentage else 99999 end) as rownum_99
,*
from #stat3
) as a
```

結果は、例えば以下のようになります。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/148310/774125d4-bef6-91ef-9ca9-5a8214dd6502.png)

結果のように、「90パーセンタイル値は5msec-10msecである」といった少し曖昧さの残る値しか分かりません。
また、正確に90パーセンタイル値や95パーセンタイル値を表現できるわけではなく、「90パーセントを超える値の中で最小のもの」という条件になるので、こちらも曖昧さの残る数値となります。

したがって、完全に正確なパーセンタイル値を表現できるわけではありませんが、普段からダッシュボード化しておくことでDB全体のレイテンシの傾向の変化には気づきやすくなるかと思います。
WaterFox GLIBC_2.30 not foundと出て起動できない

WaterFoxの最新をダウンロードしたが以下のようなエラー出て起動できない。

```
/lib/x86_64-linux-gnu/libc.so.6: version `GLIBC_2.30' not found (required by /waterfox/libnspr4.so)
Couldn't load XPCOM.
```

https://github.com/WaterfoxCo/Waterfox/issues/1356

>Official Waterfox Current 2020.02 Linux build works for me in Xubuntu 18.04 after running sudo apt-get install libc++1 tada
Same for Debian 10.3 live CD.

>It also works in Xubuntu 16.04 after also installing libc++abi1.

isuusのやり方でlibc++abi1をインストールしてみたがうまくいかず。

Waterfox Classicで起動できたのでこっちを利用することにする

https://github.com/WaterfoxCo/Waterfox-Classic


環境

Ubuntu 18.04 LTS
Box APIカスタムコネクタをpower automteに追加する



みなさん、power automate flow使っていますか？

power automate flowとはMicrosoftが提供しているiPaaSです。IFTTTに近い製品です。

添付メールが届いたら、添付ファイルをboxにアップロードするとか、boxにファイルがアップロードされたらteams/slackに通知するみたいなことができます。

参考：
https://qiita.com/glenn/items/f37cecb228618c1a718b

各種SaaSサービスとつなげるためのAPIコネクタが多数用意されています。

Power automate はboxのコネクタを用意しているのですが、すべてのAPIが用意されているわけではありません。

用意されているコネクタは実は結構貧弱。。。
https://docs.microsoft.com/en-us/connectors/box/

![画像](https://dbox.box.com/shared/static/a5v53qdkny39a1cqcawuuc1wlce16a81.png)

たとえば自動で誰かをフォルダにコラボレーターとして呼びたい、そんなフローを作ろうと思ってもデフォルトのコネクタではできません。

この場合、カスタムコネクタを作成して、好きなbox apiを追加することができます。

カスタムコネクタはpostman collectionやswaggerを使用してインポートすることもできますが、このガイドではマニュアルで追加する方法を記載します。

詳しくは知りたい人はこちらのガイドを参照してみてください。
https://docs.microsoft.com/ja-jp/connectors/custom-connectors/use-custom-connector-flow


カスタムコネクタを追加するには、flow.microsoft.com > Data > custom connectorから新規コネクタ

![](https://dbox.box.com/shared/static/2e3q1lmw0ptyqy97tx87gp6qvmgc4us3.png)




この画面ではコネクタの名前やコネクタの画像やbox apiのurlを設定します。

![](https://dbox.box.com/shared/static/12qq2wc6s4vf3nunt5w8ewqnfvelz4ej.png)

security設定は、box apiに接続するための認証情報をいれます。
flowにはすでに用意されているboxコネクタの認証情報を使って認証を行うことができます。

![](https://dbox.box.com/shared/static/wla9km8ysaetvzu5x1vlvks6z5n8wh1j.png)

APIの設定を追加します。

![](https://dbox.box.com/shared/static/i5tye15ov32diggpa6qp7jth3lkctj8d.png)

①追加しようとしているAPIのわかりやすい名前

②Flow上に表示されるオペレーション名

③次にRequestを追加します

④ここにはAPIの呼び出しかたやリクエスト詳細をいれます。
box apiのドキュメンテーションからAPIのURL,リクエストのサンプルをコピペします

今回はコラボレーターの追加を例にフィールドをいれていきます。

https://developer.box.com/reference/post-collaborations/

あとは画面にしたがって次へ次へと進めていき、最後に保存します。

途中api testせよと言われますが、無視して次にすすめてokです。

保存したら新しいフローを作成して先ほど作ったコネクタを使うことができるようになります

![](https://dbox.box.com/shared/static/o0tgwdz5wqyucpwvwi8f7acvhz2a7o73.png)


セットアップ時に入れてjsonを自動解析して必要なフィールドを入力するよう求められます！

これで好きなAPIを追加して使うことができるようになります、すごい！

happy collaborating!
全ての曲を1分にする

タイトル通り。長い曲聴くのだるいと思ったから作った。

# 1分にする
1分になる速度まで速くする

```python:

path = "motoneta.mp3"

import pydub
from pydub import AudioSegment

base_sound = AudioSegment.from_file(path, format="mp3")
time = base_sound.duration_seconds

speed = time/60
base_sound = base_sound.speedup(playback_speed=speed, crossfade=0)
base_sound.export("one.mp3", format="mp3")
```

おしまい

# 感想

速くしたら訳わからなくなって聴く気なくなった。



#裏技コマンド

1分未満のファイルでやると壊れる
実は、デザイン好きエンジニアはココを見てます…！

# はじめに
日頃 iOS アプリエンジニアとして活動している私は、個人アプリ開発でデザインも自身で行うなど、趣味レベルでデザイン領域を嗜むことがよくあります。今回は、そんな私が **デザインデータを見る時に注視しているポイント** をご紹介します。

- あ、、そこ適当にしがちだ…
- へぇ！そんな視点で見てるんだ！
- お！！私は問題なさそうだ！

こんな気付きを得てもらえたらと思い、執筆しました。
最後まで読んでいただけますと幸いです。

# 前提
iOS アプリのデザインデータであることを前提とします

# Font
文字ラベルに指定されている **フォントの種類** は必ず確認を行います。フォントの種類でそのデザイナーが Apple 製品の **フォント事情にどれだけ詳しいかがわかる** くらい重要だと私は考えています。
例えば、Apple 公式サイトの日本語フォントには「SF Pro JP」という Apple オリジナルの非公開フォントが使われています。これにできるだけ近いフォントを採用するという **こだわり** は、個人的には好きですね。他にも、**Android と iOS** で表示差異が大きくならないフォントを利用するなどの視点もアプリデザインでは必要になってきます。

# Margin, Width, Height
オブジェクトのX・Y軸、縦・横幅を決定する要素に **規則性があるか** は非常に重要です。ソフトウェアエンジニアは **再利用性** を重要視して効率よく UI 設計することを目指します。ですから、規則性がないと再利用が可能な **汎用的設計** を行うことができないのです。

私は、利用する **Margin を定数として定義** しておき、それ以外を利用できないように制約をかけています。これによって、デザイナーのミスをプロダクトに反映してしまう **多重ミスを防止** できています。

```swift
extension CGFloat {
    static let space2: CGFloat = 2
    static let space4: CGFloat = 4
    static let space6: CGFloat = 6
    static let space8: CGFloat = 8
}
```

# Color
色の管理方法に関しては、デザイン時とプログラミング時でほぼ同じなので、デザインデータ内での色管理が **プロダクトの質と開発効率に直結** してきます。下記3点は特に注意が必要です。

- ネーミング（ex: primary_\*, secondary_\*）
- ダークモードとライトモード
- 利用用途（ex: Text Color, Error）

# Auto Layout
AutoLayout は iOS の UI 設計方法ですが、それに近い挙動を再現できるデザインツールも存在します。つまり、文字数・画像サイズ・画面サイズなどが **動的に変動したときのデザイン** がどれだけカバーできているかということです。
モバイルアプリケーションは特に **表示領域が限定的** であるため、コンテンツによる UI の変動が激しめです。ですから、ここの充実度合いからモバイルアプリのデザイン経験値をなんとなく知ることができてしまうかもしれません。

# Design Tool
最近では Figma, Sketch, AdobeXD を使うケースが多いかと思います。エンジニアの開発ツールと同じく、デザインツールにも **世代交代タイミング** がありますので、それを追えているかは一つのチェックポイントになっていることがあります。

# さいごに
最後まで読んでいただき、ありがとうございます！
今回紹介したものは表面的なものが多めですが、 **デザインシステム** にも繋がる非常に重要なパーツであると考えています。
ぜひ皆さんも、エンジニアとデザイナーとの **コミュニケーションの種** に使っていただければと思います。
このオブジェクトはエンティティかバリューオブジェクトか

この記事は　[ZOZO #4 Advent Calendar 2021](https://qiita.com/advent-calendar/2021/zozo) １5日目の記事になります。

[実践ドメイン駆動設計（以下、IDDD本）](https://www.amazon.co.jp/dp/B00UX9VJGW)を読んでいて、一つ気がついたことを今回は共有します。

> 値型を作るのは簡単だとはいえ、あまりDDDの経験がない人は、そのインスタンスをエンティティとすべきなのか値とすべきなのかの判断に迷うことがある。実際のところ、経験豊富な人でさえも、ときどき迷うことがあるものだ。

> ヴァーン・ヴァーノン. 実践ドメイン駆動設計 (Japanese Edition) (Kindle の位置No.5579-5581). Kindle 版. 

この１節を読んで、なぜ迷う？と一瞬思ってしまいました。
それは自分のなかでのエンティティの解釈を誤解していたからです。

## 識別子があればエンティティということではない

もちろん、識別子があって、各オブジェクトが識別されることはエンティティの大きな特徴の一つです。

エンティティの役割ではあるのですが、、、これバリューオブジェクト側から見れば***識別子があればバリューオブジェクトではないと言っているわけではない***ということです。

もうほんと言葉ゲームみたいなのすが、***識別子があってもバリューオブジェクトになり得る***ということです。

ではどれがエンティティでどれがバリューオブジェクトなのか・・・と判断は難しい。。。ということで冒頭のIDDD本の言葉に戻るわけですね。

とりあえず、集約のルートであれば紛れもなくエンティティでしょう。
その他はケースバイケース。ただ、バリューオブジェクトで問題なければバリューオブジェクトにしてしまったほうが楽でしょう。

## バリューオブジェクトで問題なければバリューオブジェクトにしてしまう

理由としては、管理がしやすいからですね。
不変ですし、バリューオブジェクトとしての仕事しかしませんし、バリューオブジェクトでいいかと判断できるならバリューオブジェクトにしてしまうというのがベストプラクティスでしょう。

例えば、こちらの集約で生成されるものではないものとか、コンテキスト内では集合で扱う必要がないもの（識別する必要がないもの）とか、集約のライフサイクル内で変更されるものではないものとか。。。そういったものはバリューオブジェクトにしてしまいましょう。

というコラムでした。

明日も自分ですね。「CQRS/コマンドのレスポンスについて考える」というタイトルでお届けします。
つくるバーチャルライドバイク

# BBC micro:bit で室内サイクリング

バーチャルライドアプリで室内サイクリングを楽しむには、FTMSに対応したバーチャルライドバイクが必要です。BBC micro:bitは、BLE機能があり、FTMSを実装することが可能です。
そこで、BBC micro:bitで使えるバーチャルライドバイク用のMakeCode拡張ブロックをつかって、バーチャルライドバイクをプログラミングしてみましょう。

https://github.com/jp-96/pxt-ubit-virtualride

# 準備

- BBC micro:bit (本体)
- 小型サーボモーター
- 室内サイクルトレーナー
- [`Virtual Ride`拡張ブロック - https://github.com/jp-96/pxt-ubit-virtualride](https://github.com/jp-96/pxt-ubit-virtualride)  
【ご注意】micro:bit v2.0には対応して**いません。**

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/252891/1771abbb-ba67-6232-19d1-1e97ddf8a570.png)

# バーチャルライド

いくつかのバーチャルライドアプリがFTMSに対応しています。

- Zwift - https://www.zwift.com/
- Kinomap - https://www.kinomap.com/
- RGT CYCLING - https://www.rgtcycling.com/
- OneLap - https://www.onelapjapan.jp/ , https://www.onelap.com/

# MakeCode でプログラミング

## Fitness Machine Service を開始します

「最初だけ」で、`Start the Fitness Machine Service` を呼び出します。
これにより、micro:bitは、`Fitness Machine Service`を開始しますので、パソコンやスマホのバーチャルライドアプリから、接続できます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/252891/add2243d-70f2-418e-0a17-ac1f7f0f2fa6.png)

## 1秒おきに、Indoor Bike Data を通知します

「ずっと」で、１秒おきに、`Calc And Notify Indoor Bike Data`を呼び出します。
このブロックでは、`CrankIntervalTime`と`Resistance Level`とで、ケイデンスやスピード、パワーを算出して、バーチャルライドアプリへ`Indoor Bike Data`として、通知しています。
`CrankIntervalTime`の値は、室内サイクルトレーナーのセンサーから取得してください。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/252891/821b2389-88df-a2e3-e2e7-f63bdf73958d.png)

## シミュレーション情報に従って、負荷を変更します

クライアント（アプリ）からシミュレーション情報が送られてくると、`On Set Indoor Bike Simulation Parameters Procedure through Fitness Machine Control Point`ブロックが呼び出されますので、`Get Simulation Grade`で、斜度（%）を取得し、負荷を変化させます。
室内サイクルトレーナーの負荷部分を小型サーボモーター駆動に改造し、取得した斜度（%）に連動するようにサーボホーンの角度をプログラミングしてください。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/252891/8f6d2535-080f-ed00-3353-5c91b7369a10.png)

# おわりに

今回、Microsoft MakeCode for micro:bit の独自拡張機能である`Virtual Ride`拡張ブロックを使うことによって、バーチャルライドバイクを簡単につくることができるようになりました。`Fitness Machine Service (FTMS)`に対応したバーチャルライドアプリであれば、どれでも室内サイクリングが楽しめます。

- [`Virtual Ride`拡張ブロック - https://github.com/jp-96/pxt-ubit-virtualride](https://github.com/jp-96/pxt-ubit-virtualride)  


参考： https://qiita.com/jp-96/items/07bde8fa4248a4beb258
phpMyAdminでバックアップしたzipファイルで復元に失敗したときの対処法

DBでのバックアップはphpMyAdminを使っています。
保存形式はzipを使っています。

ある時、バックアップしたzipファイルを使ってインポートしようとしたら、エラーが出てできませんでした。。。
いろいろやってみて解決法が見つかったので、備忘録としてメモします。

## 起こっている問題
レコード内容を書き換える作業が発生し他ので、作業前にphpMyAdminを使ってバックアップを作成した。
作業に失敗したので、復元しようと考える。
既存のテーブルは一度全て削除。その後、バックアップしておいたzipファイルをインポートすると、以下のエラーが発生した。

``` SQL
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'PK' at line 1
```

エラーがでDBを復元できない。
全てのテーブルを削除してしまっているので、困った。。。

## 解決方法
いろいろ悪戦苦闘したが、エラーメッセージでググったら以下のサイトを見つけた

[#1064 - You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'PK' at line 1](https://forums.mysql.com/read.php?10,596193)

これによると、`problem solved, it was an issue with the zip file, after unpacking the zip import was successful.`とあるので、zip→gzipに変更してみた。

```
$ unzip backup.sql.zip
$ gzip -c backup.sql > backup.sql.gz
```

gzip化したバックアップファイルを使い、再度インポートしてみたところ、エラーは発生せずにインポート完了！！


## 最後に
解決できなくて、一晩悩み続けたけど、寝てからやってみたらすんなりできた。
やっぱりうまくいかない時には眠ってみるっていうのは有効な問題解決の手段なんだと再認識した。
Teamsを外部からAPIで更新する方法

本記事は[Web API Advent Calendar 2021](https://qiita.com/advent-calendar/2021/webapi)の14日目の記事です。

リモートワークの普及でチャットツールが導入された会社も多いと思います。
小さい会社だとChatworkやSlackを利用することが多いと思いますが、大企業を中心にTeamsを利用するほうが多いのかなと思います。

今回は外部システムからAPIを使ってTeamsを更新する方法を説明します。

#前提条件
##環境構築
Teamsで連携するにはMicrosoftTeams のチーム（紛らわしい）が必要になります。
Microsoftには個人アカウント（マイクロソフトアカウント）と組織アカウント（学校/企業アカウント）があります。
組織アカウントをテストで試す用に取得する方法は限られるようで一応こちらを参考ください。

https://www.rurururuda.com/?p=582

##連携方法について
今回連携方法を二種類紹介しますが両方**Microsoft Teams API**という技術を使っていることに変わりはないです。
ただ実現方法が別なので別の方法として紹介させてください

https://docs.microsoft.com/ja-jp/graph/teams-concept-overview


#API連携の方法
1.Incoming Webhookを使う
2.Microsoft Graphを使う

##Incoming Webhookを使う
Incoming Webhookについてはこちらの記事がとても参考になりました。

https://qiita.com/wataash/items/72b49509c3964294dd67

Microsoft Teams APIを使ってこちらの方法で作られたIncoming Webhookコネクタを使います

https://docs.microsoft.com/ja-jp/microsoftteams/platform/webhooks-and-connectors/what-are-webhooks-and-connectors

特徴としてはURLを発行して認証などもなく簡単に連携が可能なことです。

#Microsoft Graphを使う
Microsoft GraphはMicrosoft 365をAPI操作するための方法です。
なのでMicrosoft Teams APIはMicrosoft Graphの機能の一つということになります。

https://docs.microsoft.com/ja-jp/graph/overview

Microsoft GraphにはGraph Explorerという試用環境があります。

https://developer.microsoft.com/ja-jp/graph/graph-explorer?request=me&version=v1.0

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/137987/861864ae-fc14-11fd-526e-713b83bf5bb8.png)

このようにいろいろなAPI連携の方法があります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/137987/6dbf5e7b-5ccd-aac5-858d-91a3111c7cba.png)

Teamsの場合はベータ版を除くとこのような操作ができ、ベータ版があるということは今後拡充されていくと思います。

Graph Explorerを使ってAPIテストを実施してあとは呼び出し処理を実装していく形になります。
こちらはTeams側の設定は特に必要ないです。

今後の予定としてはローコード、ERPなどの他ツールからAPI連携してTeamsに通知を出すアプリを作ってみようと思います。
WindowsでTclスクリプトのメモリ使用量を調べる方法 ～ WMI編

[以前の記事](https://qiita.com/qoLop/items/1aa561ae619f94870715)でTWAPIパッケージのget_process_memory_infoメソッドを使う方法を紹介しましたが、そこに行きつくまでにWMIを使う方法も調べていたので、ついでに紹介しておきます。

# WMIでメモリ使用量を調べる方法
「WMI PrivateBytes」でググっていて、以下のサイトを見つけました。

https://zenn.dev/tera1707/articles/d23687c83111f4

こちらのサイトにC#のサンプルコードがあるのですが、何やらSQL文のような文字列を使って問い合わせているようでした。

[TWAPIでWMI問い合わせを行う記述例](https://wiki.tcl-lang.org/page/TWAPI+and+WMI)でも同じようにSQL文のような文字列で問い合わせていたので、これらを合わせて

```Tcl
package require twapi
set wmi [::twapi::wmi_root]
set query "SELECT * FROM Win32_PerfRawData_PerfProc_Process Where IDProcess=\"[pid]\""
$wmi -with {
    {ExecQuery $query}
} -iterate app {
    puts "PrivateBytes=[$app PrivateBytes]"
    $app -destroy
}
```

のように実行してみると、以下のような結果になりました。

```Tcl
PrivateBytes=17342464
```

余談ですが、上記のスクリプトの中でwmiやappはTclOOオブジェクトなのですが、実用的にTclOOが使われているのを初めて見てとても新鮮でした。
Dockerのキャッチアップと練習

# 概要
`これは学習メモです`
docker-composeなどは使わず、シンプルに`network、MySQLコンテナ,WordPressコンテナ作成`を作成。
+α、dockerを理解する上で最低限のあるべき知識メモ.

#### dockerの概念
dockerのコア概念は`「データやプログラムを隔離」`。
そのためコンテナとコンテナ独立してるので、大きな依存関係が生じず、イメージ化も可能。
#### コンテナのライフサイクル(2~5がサイクルするイメージ)
「作って立てて落として削除」のシンプルな流れ。故に起動してるものを落とす前に削除はできないので忘れずに。

```
1. imageを持ってくる
2. コンテナを作成
3. コンテナを起動
4. コンテナを停止
5. コンテナを削除 
```

# 手を動かしてみよう
### 作成

#### netwrok作成
```
docker network create wordpress000net1
```

#### network確認
```
docker network ls
```

#### MySQLコンテナを作成・起動
```
docker run --name mysql000ex11 -dit --net=wordpress000net1 -e MYSQL_ROOT_PASSWORD=myrootpass -e MYSQL_DATABASE=wordpress000db -e MYSQL_USER=wordpress000kun -e MYSQL_PASSWORD=wkunpass mysql --character-set-server=utf8mb4 --collation-server=utf8mb4_unicode_ci --default-authentication-plugin=mysql_native_password
```

#### WordPressコンテナを作成・起動
```
docker run --name wordpress000ex12 -dit --net=wordpress000net1 -p 8085:80 -e WORDPRESS_DB_HOST=mysql000ex11 -e WORDPRESS_DB_NAME=wordpress000db -e WORDPRESS_DB_USER=wordpress000kun -e WORDPRESS_DB_PASSWORD=wkunpass wordpress
```

#### 下記URLにアクセスし、言語選択+Continueが押せれば成功
```
http://localhost:8085/
```

### 削除
#### dockerを止める
```
docker stop mysql000ex11
docker stop wordpress000ex12
```

#### dockerを削除
```
docker rm mysql000ex11
docker rm wordpress000ex12
```

#### imageを削除
```
docker image rm mysql
docker image rm wordpress
```

#### networkを削除
```
docker network rm wordpress000net1
```
データ分析コンペの登録・学習の進め方[2021年度版]

## はじめに

こんにちは！株式会社会社エイアイフィールドに新卒で入社した傍示です。現在はフロントエンドの開発を主に担当させて頂いております。この記事は[株式会社エイアイフィールドアドベントカレンダー2021](https://qiita.com/advent-calendar/2021/aifield)の12日目の記事です。

この記事は[8日目の記事](https://qiita.com/Kenta_Hoji/items/07759636c03149f625ce)で軽く紹介したデータ分析コンペサイトの紹介やコンペサイトを利用した勉強の進め方を紹介します。


## 1. データ分析コンペサイトに登録しよう！
まずデータ分析コンペサイトに登録と言っても、どのコンペサイトがいいのか分からない方もいらっしゃるかと思います。

そこでKaggleなどの私が登録しているコンペサイトについて個人的な主観を紹介させて頂きます。自分のレベル感や趣向にあったサイト選びの参考になれば幸いです。

[1. Kaggle](https://www.kaggle.com/)
世界最大級のコンペサイトで約40万人ほどのデータサイエンティスト、機械学習エンジニアが切磋琢磨しているコミュニティとなっています。コンペ中のディスカッションも盛んで、メダルや称号を獲得する事で自分の実力を対外的にアピールすることが可能です。


[2. SIGNATE](https://signate.jp/)
Kaggleの日本語版として紹介されている日本最大級のコンペサイトです。コンペ以外にも [SIGNATE QUEST](https://quest.signate.jp/about)といったデータサイエンスを学べるコンテンツも充実しており初心者の方にもオススメです。


[3. Nishika](https://www.nishika.com/)
データサイエンティスト特化型求人も充実しているコンペサイトです。最近では[特許庁とのコラボをしたコンペ](https://www.nishika.com/competitions/22/summary)や開催されていたり、副業の紹介も行っているので、データサイエンス関連の仕事をしてみたい方は登録するメリットがあると思います。

[4. ProbSpace](https://comp.probspace.com/)
自社主催コンペが中心のサイトで、毎回分かりやすいチュートリアルが付属しているため参加のハードルは他のサイトより低いと思います。またスプラトゥーンやプロ野球などの中々身近で面白い題材を取り扱ったコンペが多い印象です。

## 2. ディスカッションをもとにコードを提出してみよう

上記のサイトに登録したら、コンペの楽しさを体感するために何らかのコンペに参加して用意されているチュートリアルや他の方が書いたコードを真似て投稿することから始めてみましょう。

上記で紹介したサイトではコンペごとに参加者がコードを共有するページ(Kaggle：Code、SIGNATE：フォーラム、Nishika：ディスカッション、Probspace：トピック)があり、まずはそこのコードをコピーして実行結果を確認してみます。

すると実行結果と自分の順位がすぐに確認する事が出来るので、「コンペに参加した！！」といった実感が湧いてきます。

その次は複数のチュートリアルのコードを組み合わせてみたり、コードの中のパラメータらしき数字を変更してみて精度が変わるかどうか確認してみましょう。

そうした試行錯誤を繰り返していく中で順位の変動や、コードを中身を理解する事が出来るのでデータ分析コンペの楽しさをより実感できるかと思います。

## 3. コンペに必要な知識を増やそう
コンペを続けていると他の人のチュートリアルを真似るだけでなく、「自分のアイデアを実装してみたい！」、「もっと上位を目指したい！」となってくるかと思います。

そうした方のための勉強の進め方について紹介していきます。

### ・Kaggle関連の本を読む
コンペに行き詰った際にはKaggle関連の書籍を読んでみましょう。
Kaggleで使えるテクニックや勉強の進め方などを、実際にKaggleで活躍されている方からの視点で学ぶことが出来るのでオススメです。
もちろんKaggle以外のコンペでもこのテクニックは活かせます！

例)
・[Kaggleで学ぶデータ分析の技術](https://gihyo.jp/book/2019/978-4-297-10843-4)
・[実践Data　Scienceシリーズ　PythonではじめるKaggleスタートブック](https://www.kspub.co.jp/book/detail/5190067.html)
・[Kaggle Grandmasterに学ぶ機械学習実践アプローチ](https://book.mynavi.jp/ec/products/detail/id=123641)

### ・講座に参加する
データサイエンス関連の講座は様々な企業や団体が開催していますがそういった講座に参加するのもオススメです。データサイエンスの知識が身につくのは勿論ですが、講座専用のコミュニティチャンネルが用意されていることが多く、受講生同士で切磋琢磨しながら課題に取り組むことが出来るので参加する価値は大いにあります。

今回は筆者が参加した中で特に良かった講座をピックアップして挙げさせていただきます。

・[AI QUEST](https://aiquest.meti.go.jp/)
・[データサイエンティスト養成講座](https://www.datascientist.or.jp/news/ds-training-program202104/)
・[東京大学グローバル消費インテリジェンス寄附講座](https://gci.t.u-tokyo.ac.jp/)

## おわりに
今回はデータ分析コンペの始め方や学習の進め方について紹介していきました！

個人的にはゲームの順位を上げる感覚で取り組める部分がコンペに参加するモチベーションに繋がっていると感じています。
是非皆さんも、コンペに参加してこの楽しさを味わいながら一緒に切磋琢磨していきましょう！！
WordPress テーマ使用でのランディングページ制作についてメリット・デメリットなど【LP】

以下ページ、知り合いがWordpressを使って作ったランディングページなのであるが、

https://hukugyou-diamond.com/lp/engineer/

たまたまエンジニア関連の記事である奇遇性は置いておくとして(笑)

メリット・デメリットそれぞれ解説していくとする。


※これはあくまで本質的なところを捉えて書いており、そこまで詳しい技術面に関しては書いていない。


■メリット■


操作が簡単


操作は言うまでもなく簡単であり、初心者の方でも視覚的に操作できるため、参入障壁を下げることが出来る点、効果的である。


綺麗なテンプレートが用意されている


比較的整ったテンプレートや素材・ボタンなど用意されているため、余計な手間・タスクを省くことが出来る。
また、初心者の方にとっては品質向上にもつながってくるため、クオリティーを求める手段の1つにもなる。


■デメリット■


スキルがあまり身に付かない


HTMLやCSS、Javascriptなどのスキルはあまり身に付かない。
例えば、ある1色の色の素材しかない場合に、HTMLの色コードを変更する必要などがあればそれに応じて多少のスキルは身に付くが、1から製作するのに比べるとあまり身に付かない。


カスタマイズ（変更・編集など）出来る範囲が限られてくる

自分で1から作ったものであれば、ほぼ自由に編集や手を加えることが出来るのだが、カスタマイズに制限がかかってくる代表的な例としてテンプレート素材の使用があげられる。


外部プラグインなどが不具合を起こすこともたまにあるが、これはどのテーマを用いても同じであるため、ここでは端折らせて頂く。
天気予報通知Bot　OpenWeatherMap+LINE Messaging+Node-RED+RaspberryPi

概要
-------------
天気予報を見る習慣が無くて、いつも天気を見るの忘れて傘持っていったらよかったとか、
子供の雨具忘れたりするので、
朝に昼と夕方の天気予報を通知するアプリを作ってみました。

下記の記事を存分に参考にさせてもらいました。
違いはenebularを使っていないことと、現在の天気でなく、予報データを使っているところです。
https://qiita.com/kmaepu/items/facecab4c67ca9c16a1a



■構成概要
![Instagram post - 10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/204852/02e0bba5-eca1-3df8-ef46-61adddee476f.png)



RaspberryPi＋Node-REDを使ってSmartHome化をしており、これに追加する形で構築。

■我が家の全体構成
![Instagram post - 1 (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/204852/55bcf8a7-3c97-c830-4202-6034439ddd37.png)


天気情報用にOpenWeatherMap　API取得
-------------
OpenWeatherMapは無料で利用できる天気予報API.

https://openweathermap.org/

無料で利用できるAPIの項目は以下の通りなので、ほぼ個人利用であれば無料でOK.
(1分間に60コール/1ヶ月に1,000,000コールまで)

・現在の天気
・3時間ごと5日間の天気予報

OpenweatherMapのAPI KEYの取得する。
取得したKEYをNode-REDのOpenweatherノードに入力。
![Instagram post - 3 (1).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/204852/0e4253e9-d654-95ea-f935-38a2f1f05bfb.png)

OpenweatherMapの５dayforecastのデータは多分かきのようなイメージになっているので、そこから使いたい予報時刻のデータのみをNode-RED側で処理して使う。
![Frame 1.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/204852/3170fe09-b673-02f7-5949-75d34e3f20d3.png)



通知用にMessenger APIを取得
------------
・LINE Messenger API 
Messaging APIを使って、ユーザー個人に合わせた体験をLINE上で提供するボットを作成できるBot、とのこと。

LineMessenger　APIの取得

https://developers.line.biz/ja/services/messaging-api/

アカウントを設定し、プロバイダー作成、チャンネル作成。

![Instagram post - 4.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/204852/9ebf7857-64c3-55e9-be31-a1b298a59fde.png)

USER IDはビジネスアカウントと連携しないと出てこないので注意が必要。




Node-RED 構成
----------
node-openweathermapのノード　インストール
line-messaging-apiのノード　インストール

![Frame 2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/204852/7a52da7b-e95c-e54d-4d69-47f4c4c3268c.png)
![Instagram post - 5 (2).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/204852/a8fe5f58-b108-a306-e79f-9fa63b5fefab.png)

毎朝7:30に天気予報が通知されるようになりました。
他のセンサーデータの通知などにも使えるので今後発展させていく予定です。

参考

https://qiita.com/kmaepu/items/facecab4c67ca9c16a1a


https://qiita.com/YSFT_KOBE/items/8dc62ac40c5112df2ed3
学内で開催したiOS勉強会の感想

# はじめに
こんにちは、HCB Advent Calendar 2021の11日目を担当する、kudokaiです。
現在僕は、大学の仲間数人と学内ハッカソンを企画・運営しており、ハッカソンイベントの一部として各種勉強会を企画し開催しています。
僕はiOS勉強会を担当したので、どんな勉強会だったのかを今回紹介します。

# 勉強会の資料作成まで
今回の勉強会は1年生や2年生をメインターゲットとしているため、分かりやすい資料かつ、振り返りでも使えることが要求されます。
勉強会を開催したことがなかったため、どこまで盛り込めばいいのか・どこまで説明したらいいのか線引きがとても難しかったです。
経験者からするとかなり冗長な部分があり、「そんなん説明せんでも分かるわ！　舐めとんか！」と思われるかもしれないですが、プロジェクト作成やファイル作成の仕方も説明しています。
完成図を見せただけで、実装をサクサク進めることができるほど簡単なアプリを題材にしました。

# 勉強会の内容
当初はオンラインでの実施を予定していましたが、大学から貸し出せるMac Bookの台数を超えてエントリーがあったため大学で対面での実施となりました。
30名近いエントリーをいただきました！
非常にありがたいです！
今回はSwiftUIを使い、じゃんけんアプリを作りました。
完成イメージは以下の通りです。
![my_janken.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/425368/b09d4878-e9da-9fc8-6a70-dda63f582cb9.gif)
一応、作った[スライド](https://speakerdeck.com/kaitokudou/iosmian-qiang-hui-zi-liao)と[ソースコード](https://github.com/SmileHackathon/swift_practice)も載せておきます...

# 勉強会を終えて
僕は今回初めて勉強会を企画し、開催しました。
勉強会本番ではアプリの完成まで進行させることができず、中途半端なところで終わってしまいました。
自分の中では「このくらいだったら出来るやろ」と思っていたところが初心者にとっては難しい部分だったりというのがありました。

じゃんけんアプリを90分で完成させるというのがキツかったか...
もっと簡易的なアプリにするべきだったのか...
ソースコードを事前に共有するべきだった...
勉強会資料の確認を徹底してやるべきだった...

振り返ってみると反省すべきところしかないですね。
僕は今年度で大学を卒業するため、来年はハッカソンや勉強会の企画には携わることは難しくなりますが、iOS勉強会の反省点を引き継いで来年はもっといい勉強会を開催してほしいです。
そして一人でも多くの学生にiOSアプリ開発の楽しさを知ってほしいです。
EC2にLaravelのDocker環境を構築

# Dockerで作成したファイルをEC2にデプロイしたので備忘録としてアップ

1. インスタンスを作成（Amazon linux2）
2. Dockerなどインストール
3. コンテナ立ち上げ
4. Laravelセットアップ
5. Nuxtセットアップ

※インスタンス作成は省きます

## Dockerなどインストール
#### sshで作成したインスタンスに接続したあと
- sudo yum update -y

#### git インストール
- sudo yum install git -y

#### dockerインストール
- sudo yum install -y docker

#### docker起動
- sudo service docker start
- sudo chkconfig docker on
- sudo usermod -a -G docker ec2-user
- docker --version


#### docker-composeインストール
- sudo curl -L "https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
- sudo chmod +x /usr/local/bin/docker-compose
- docker-compose --version

#### nodeインストール
- curl --silent --location https://rpm.nodesource.com/setup_14.x | sudo bash -
- sudo yum -y install nodejs
- npm -v
- node -v

#### ソースをgit clone


このあとはソースの手順通りに進め、インバウンドルールなどを設定してアクセスすると表示される
[ソースはこちら](https://github.com/y0913/laravel_project#readme)

※DB作成などはREADME.mdを参照のこと


#### dockerfileなどは以下の記事を参照させていただきました。（ありがとうございました。）


[【超入門】20分でLaravel開発環境を爆速構築するDockerハンズオン](https://qiita.com/ucan-lab/items/56c9dc3cf2e6762672f4)
機械学習

https://qiita.com/arigra/items/f0e0cce59e8fdf84bfc6

https://qiita.com/arigra/items/27f4cc5f3b495277bfc7

https://qiita.com/arigra/items/3de9a7f3037b43f8d5df

https://qiita.com/arigra/items/68a3d770da1e73aaecb8

https://qiita.com/arigra/items/06bd2de7f2ede7d81bcb
Javaの学習について

TechCommitアドベントカレンダー12日目を担当します！
よろしくお願いします。

新卒でプログラム未経験でSIerに入社し、Javaのプログラムを主に扱っています。
(現在入社3年目)

入社1年目に研修でJavaの基本的な文法を学び、
業務ロジックの中身だけであれば書ける状態になっていたのですが、
その後が難しいなと思っています。

今取り組んでいることを書きます。

##Javaをちゃんと理解していく
Javaの基本資格であるJavaSilverを入社1年目で取得していたので、軽い気持ちでJavaGoldとっとくか、
と問題をみてみると...

**さっぱりわかりませんでした!!**

[Oracleのサイト](https://www.oracle.com/jp/education/certification/jse11-5570635-ja.html)を見てみると、以下の定義になっていました。
>Oracle Certified Java Programmer, Silver SE 11 認定資格は、Javaアプリケーション開発に必要とされる基本的なプログラミング知識を有し、上級者の指導のもとで開発作業を行うことができる開発初心者向け資格です。

>Oracle Certified Java Programmer, Gold SE 11 認定資格は、設計者の意図を正しく理解して独力で機能実装が行える中上級者向け資格です。Javaアプリケーション開発に必要とされる汎用的なプログラミング知識を有し、設計者の意図を正しく理解して独力で機能実装が行える能力評価することを目的としています。


初心者と中上級者の壁は厚いな、と感じました。
「プログラムが動いた！やった～」と喜んでいては中上級者にはなれないみたいです。（←当たり前ですね…）

まだ合格していないので偉そうなことは言えないのですが、
Goldの学習過程で初学者にはない設計の観点を持てるようになってきた気がします。

Techcommitの方におすすめいただいた黒本著者の方のYoutubeチャンネルが、
ポイントをわかりやすく解説してくれているのでおすすめです。
⇒[黒本著者が教える やさしくない!? Java](https://www.youtube.com/channel/UC42DlV-0RDb6fJ8A3IbAang)

##他の言語も勉強してみる
前述のJavaGoldの勉強が大半を占めていて最近は進められてないのですが、
udemyでJava以外の言語も学習しています。


- [【JavaScript＆CSS】ガチで学びたい人のためのWEB開発徹底実践（フロントエンド編）](https://www.udemy.com/course/front-dev-tutorial/)
- [現役シリコンバレーエンジニアが教えるGo入門 + 応用でビットコインのシストレFintechアプリの開発](https://www.udemy.com/course/go-fintech/)

「流行している技術を調査して教えて！」と会社に強制されて渋々勉強をはじめたのですが、他の言語の仕組みや背景を知るとJavaの特徴をより意識するようになりました。

特にフロントエンド系の知識は業務に直接役に立つことも多かったです:sunny:

---

今取り組んでいることは、以上です。

最近の学習の一番の課題は、**残業せずに帰ること**です。
（残業すると気力と体力がほぼなくなってしまいます。。）
コンスタントに勉強し続けるのは一番難しいことだなと感じます。

最低限、TechCommitの自習時間（20:00~22:00）は確保するようにしようと思います:muscle:

最後までお読みいただきありがとうございました。
みなさま良い年末をお過ごしください！
【PHP】MacM1でPHP7.4をインストールする方法

## 利用環境
MacOS：BigSur
バージョン：11.6.1
チップ：Apple M1

## PHPインストールの手順
※ここでは「Homebrew」はインストール済み前提で進めます。

念の為、Homebrewでアップデートが必要ないか確認しました。

```terminal:ターミナル
brew doctor
```

ターミナル起動する前に「Rosettaを使用して開く」にチェックをつけておきます。
参考資料：https://blog.looseknot.jp/mac/m1mac_terminal_rosetta.html

確認後、ターミナルを起動し下記を実行
※管理者パスワードが求められます

```terminal:ターミナル
/bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"
```

次にPHPをインストールします。

```terminal:ターミナル
brew install php@7.4
```

インストールが無事に終わったら続いてpathを通します。

```terminal:ターミナル
echo 'export PATH="/usr/local/opt/php@7.4/bin:$PATH"' >> ~/.zshrc
echo 'export PATH="/usr/local/opt/php@7.4/sbin:$PATH"' >> ~/.zshrc
```

最後にPHPの再起動

```terminal:ターミナル
brew services start php@7.4
```

バージョンを確認し問題なければ完了です。

```terminal:ターミナル
php -v
```
Swift Type Alias から学ぶ開発指針と雑学

# はじめに
iOS15 対応時に遭遇したとあるライブラリに対する **技術的対応方法** と、そこから学べる **雑学** をご紹介します。
Advent Calendar も後半に突入しましたので、気分転換として読んでいただければと思います。

# iOS15 対応
とあるプロジェクトで [BonMot](https://github.com/Rightpoint/BonMot) という Swift 製ライブラリを利用していました。
BonMot は文字の装飾をサポートするライブラリで Foundation.NSAttributedString を拡張して作られています。

結論、この BonMot 内のオブジェクト名と同様のオブジェクトが Foundation にも iOS15 から定義されることになったのです。それが StringStyle です。このように **Framework 間で名前の衝突** が発生した場合、Foundation が優先されるようで、iOS15 対応時にビルドエラーが発生するようになりました。

```swift
typealias StringStyle = BonMot.StringStyle
```

対応方法は README にも記載がありますが、上記のように **typealias を利用して参照先を変更** するというものになります。次にこの対応の詳細をまとめます。

# Type Alias
```swift
public let stringStyle: BonMot.StringStyle
```

まず、typealias を利用せずに対応する場合は上記のようになります。StringStyle を参照する所全てに `BonMot.` を加えていく必要があります。 **そんな時に便利なのが typealias** なのです。

```swift
final class ViewController: UIViewController {
    typealias StringStyle = BonMot.StringStyle // Type Alias

    public let stringStyle: StringStyle // This
    init() {
        stringStyle = StringStyle( // This
            .color(.red),
            .font(.systemFont(ofSize: 14)),
            .minimumLineHeight(24)
        )
    }
}
```

次に、typealias を利用すると上記のようになります。typealias を定義したネームスペース内であれば Foundation.StringStyle ではなく BonMot.StringStyle を参照するようになります。
では、これを **全てのクラスに対して適応** したい場合はどうしたら良いでしょうか。

```swift
public extension NSObject {
    typealias StringStyle = BonMot.StringStyle
}
```

かなり大胆なことをしていますが、上記のようにすることで今回の事例に対しては対処が可能です（*厳密には「全てのクラスに対応」を実現できていません*）。
**ただ、ここまでして BonMot を継続していく必要はあるのでしょうか。**

# 開発方針の見直し
- サードパーティ製フレームワークの利用理由
- 新しい API への置換
- 暫定対応であると明記

## サードパーティ製フレームワークの利用理由
OS のアップグレードは1年に一度だけの **ビッグイベント** です。この機会を最大限に生かさない手はありません。
外部依存は苦戦しがちだからこそ、このタイミングでその **ライブラリを利用している理由を明確に** しておくと良いかもしれません。当時は UIKit ベースであることによって発生する問題解決のために導入したライブラリで、SwiftUI への移行で解決してしまう、なんてこともあるかもしれません。

## 新しい API への置換
Apple が提供する公式 API も年々進化を続けています。Cocoa に限らず、Swift に関してはサードパーティだった機能が次々取り込まれています。ですから、今後の **メンテナンスコストが増大する前に** 、新しい API への移行を優先度高く進めるべきかもしれません。


## 暫定対応であると明記
とは言ったものの、対応に時間がかかる、サポートバージョンの関係で完全に切り離せないなどの事象は発生しがちです。そんな時は、 **一時的対応であることを明記して暫定対応** を行いましょう。`TODO:` とコードにコメントを残してワーニングを出力するなど、 **目立たせること** と **それに慣れない環境づくり** がポイントです。

# NSObject
さて、改めて **NSObject** とは何でしょうか。
ルートオブジェクトであることはご存知かと思いますが、「NS」の語源に関して知っている iOS エンジニアの割合は年々低くなっているのではないでしょうか。答えですが、[NeXTSTEP](https://ja.wikipedia.org/wiki/NEXTSTEP)の略だと言われています。こういったところから **Apple の歴史を振り返る** のも良いかもしれませんね。

# さいごに
最後まで読んでいただき、ありがとうございます。
ご指摘、ご感想などありましたら気軽にコメントください！
ピープルウエアを読んだらデマルコ節に魅了された

リブセンス アドベントカレンダー12日目です。

表題の通り、ピープルウエアの輪読会を通してトム・デマルコ先生の言葉の言い回しに魅了されました。
ピープルウエア、という本について感想をまとめつつ、心に残ったデマルコ節を書きたいと思います。
読もうと思っている人の参考になれば幸いです。

# ピープルウエアとは
<div align="center">
　　　　　　　　　　　<img width="300" alt="ファイル名" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/234908/ae8e954b-0830-40bb-c10f-33afbb924ecd.jpeg">
<div>
ピープルウエアはトム・デマルコ、ティモシー・リスターの著書のタイトルです。
プロジェクトの失敗の原因について、考えていた両名が
「どうも、システムの仕事での大きな問題は、技術的なものというよりも、社会学的なもんもなんじゃないかな」
という発想に至り、その仮説の検証や二人の経験をマネジメントや組織文化の問題と原因を紐付けてまとめてくれている書籍です。
# どんな本なの
直接的なエンジニアリングに関する書籍ではないです。
ですが、立場関係なく一度読んでみても面白い本だと思います。
組織運営のおいて望ましいこと、より良くしたい時の指針が載っているタイプの書籍で一見マネジメント層向けの書籍に思えるのですが、会社の属する以上、組織やチームに属することになるのでそれらを見るときの視野を広げることができるので非マネジメント職の方にもおすすめです。
また、人と意見を交わしつつ読むのもおすすめです。
今回、私は同僚にお声掛けいただき、ピープルウエアを読み進めて意見を交わす、いわゆる輪読をしました。
同僚はマネージャー寄りで、自分はプレイヤーであることから読んだ結果の感想も変わってくる状態で意見を交わすのがとても楽しかったです。
# デマルコ節って？
オリジナル語です。輪読してた私ともう一人の間ではピープルウエアに出てくるユニークな言葉をこう呼んでいました。
ピープルウエアはとても勉強になる本です。
しかも、ただ勉強になるだけじゃなく本の随所に出てくる独特な言い回しが印象深く、記憶に刻み込まれます。
共同著書だから厳密にはそうじゃないのかもしれないですが、ここではデマルコ節で強行します。

# デマルコ節を抜粋してご紹介
そんなデマルコ節で私が特にグッときたものを少し紹介させてください。
ページも載せますが、私が読んでいるのは第３版なので他の版では変わるかもしれません。

## p.110 屍を支える仕事は人に満足を与えない
**多くの手が支えようとするから、屍はすぐには倒れないが、屍を支える仕事は人に満足を与えない**

特に大きな理由もなく、社員に画一性を求める文化についてばっさりと切り捨てる一文です。
例では服装規定が挙げられており、そういった画一性が定まり過ぎていることで従順であることが評価されて本当の自分を見てもらえないことに憤りを覚える人材は去ってしまう、とのことです。
どうやら服装規定はピープルウエア的には末期症状らしく、この状態の会社のことを「屍」と表していました。

## p.136 最悪のクソ野郎である
**これは専門用語を使うなら、最悪のクソ野郎である**

専門用語*#とは*。
会社の移転に伴う弊害、という章の一文です。
他の著書の文を大胆に引用した直後にこの一文です。
ただ、実際に例に挙げられている移転の仕方については同ページで解説されている通り、あまりにも見落としが多く、社員に強いるものが多すぎるものの例として挙げられていました。
移転を続けて、社員の質を上げていく、という首を傾げてしまいそうな手法についての話なのでこれは確かに専門用語を行使したくなるのかもしれません。

それはそうと弊社も近々移転です。今後ともよろしくお願いいたします。

## p.226 それほど多くないはずだ~~~せいぜい90%程度のものだろう

**こんな政治的な理由で、早期に過剰人員を投入するプロジェクトはどれくらいあるろうか？それほど多くはないはずだ。全てのプロジェクトのうち、せいぜい90%程度のものだろう**

早期の過剰人員投入について繰り出されたシニカルな一文です。
設計→開発という流れの中で設計の段階で多くの人員がいることはあまり意味をなさないが
マネジメントとして早期人員投入が決定されてしまうことは、せいぜい9割くらいらしいです。
ピープルウエアでは、知的労働者の仕事を従来のマネジメントと同じように仕事をマニュアル化し、人員を代替可能なものと考えるやり方をNGとしています。
なのに、上記のような人を増やそう、という発想が先行してしまうことに憤りを感じているのかもしれません。

ただ、ここに関しては輪読をする過程で当時の開発体制と今の体制は違いもあるため全てを鵜呑みにするのも違うのかもしれない、という意見もあり別の意味でも楽しめたページでした。

# 終わりに
ピープルウエアは私が初めてデマルコ先生と出会った本でした。
こんなに衝撃を受けた本は初めてだと思います。
また、Twitterにトム・デマルコBotなるものがあることを知りました。
https://twitter.com/demarco_bot_jp

次は「熊とワルツを」を読もうと思っています。
【JavaScript】ローカルでpaizaの問題を解くための環境構築

paizaのスキルチェックのような標準入力が渡される問題の解答コードを書く方法として、問題ページに直接書く方法や、[paiza.io](paiza.io)等のオンライン実行環境を使う方法がありますが、今回はローカルに環境を構築してみます。

※この方法はpaizaの他に、AtCoder等の競技プログラミングの問題を解く場合も使えます。

# ローカルでコードを書くメリット

- お好みのフォーマッター・リンターを導入できる
- 使い慣れたキーボードショートカットが使える

その他いろいろカスタマイズでき、自由度が高いというメリットがあります。

# 環境

- Windows 10
- Visual Studio Code
- node v16.13.2

# 環境構築の手順

作業用のフォルダを作成し、その中に以下の名前のファイルを作成します。

- case1.txt
- case2.txt
- case3.txt
- case4.txt
- case5.txt
- main.js
- main.template.js
- package.json

## case1.txt ~ case5.txt

動作確認として渡す標準入力を、これらのファイルにそれぞれ貼り付けます。

```plaintext:(例)case1.txt
3 5
.#...
...#.
#..#.
```


## main.js

解答のコードを書くファイルです。書き終わったらコピーして提出しましょう。

## main.template.js

新しくコードを書き始める時のテンプレート用のファイルです。
標準入力は配列`args`に1行ずつ入ります。

```javascript:main.template.js
process.stdin.resume().setEncoding("utf8");
const args = [];
require("readline")
  .createInterface({ input: process.stdin })
  .on("line", (input) => args.push(input))
  .on("close", main);

function main() {
  // ここからコードを書き始める
}

```

## package.json

標準入力を渡してプログラムを実行するためのコマンドのショートカットを記述します。

```json:package.json
{
    "scripts": {
        "1": "node main < case1.txt",
        "2": "node main < case2.txt",
        "3": "node main < case3.txt",
        "4": "node main < case4.txt",
        "5": "node main < case5.txt",
        "new": "cp main.template.js main.js && rm case1.txt && touch case1.txt && rm case2.txt && touch case2.txt && rm case3.txt && touch case3.txt && rm case4.txt && touch case4.txt && rm case5.txt && touch case5.txt"
    }
}
```

# 画面レイアウトの例

ウィンドウの右側に、標準入力ファイルのタブを配置させるのがおすすめです。

![VSCode 2021-12-11 215030.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1183281/abf12a76-928d-421c-7d72-664126770518.png)

# ターミナルで使うコマンド

## 初期化コマンド

**main.template.js**の中身を**main.js**にコピーし、**case1.txt** ~ **case5.txt**の中身を空にします。

```bash
npm run new
```

## 実行コマンド

**case1.txt** ~ **case5.txt**のそれぞれの標準入力を渡してプログラムを実行できます。

```bash
npm run 1
```

```bash
npm run 2
```

```bash
npm run 3
```

```bash
npm run 4
```

```bash
npm run 5
```
Angular フォーム (1)：基礎

## フォームモジュールを使うには
app.module.ts で、FormsModule をインポートする

```typescript
import { FormsModule } from '@angular/forms';

@NgModule({
  declarations: [ 省略 ],
  imports: [
    FormsModule
  ],
  providers: [ 省略 ],
  bootstrap: [ 省略 ]
})
```

## テンプレート駆動型：双方向バインディング
コンポーネントのクラス変数値とフォーム値を同期する仕組み。
例えば、画面で入力した値をクラス変数にも反映する場合に使います。逆も然り。
テンプレート側が主導して値をバインドしているので、テンプレート駆動フォームと呼ばれている。
次のサンプルでは、入力値が上に表示されます。

### コンポーネントTSファイル
```typescript
xyz:string = "abc";
```

### コンポーネントHTMLファイル
```html
xyz: {{xyz}}<br>
<input type="text" [(ngModel)]="xyz">
```

## リアクティブ型フォーム
コンポーネントクラス側で、モデルを用意して、それをテンプレート側に設定する方法をリアクティブ型フォームと呼ぶ。

### 利用方法

app.module.ts で、ReactiveFormsModule のインポートが必要です。

```typescript
import { FormsModule, ReactiveFormsModule } from '@angular/forms';

@NgModule({
  declarations: [ 省略 ],
  imports: [
    FormsModule,
    ReactiveFormsModule
  ],
  providers: [ 省略 ],
  bootstrap: [ 省略 ]
})
```

### FormControl

コンポーネントTSファイルにて、FormControlクラスの変数を定義する。
ボタンをクリックしたら、フォームコントロール変数の値を画面に表示するメソッド show() も実装します。

```typescript
sampleControl:FormControl = new FormControl('Sample');
message:string = "";

show() {
  this.message = sampleControl.value;
}
```

コンポーネントHTMLファイルでは formControl属性に、定義した変数を指定する。
フォームコントロールの入力値がボタンクリックで、メッセージに表示されます。

```html
<p>{{message}}</p>
<input type="text" [formControl]="sampleControl" />
<button (click)="show()">Click</button>
```

### FormGroup
FormControlだけだと入力項目数だけ変数作成して個別に管理するのは大変。そんな時に、フォーム全体を１つにまとめて管理するのがFormGroupです。

#### コンポーネントTSファイル
```typescript
import { Component, OnInit } from '@angular/core';
import { FormControl, FormGroup } from '@angular/forms';

@Component({ 省略 })
export class ...Component implements OnInit {
  sampleGroupForm:FormGroup;
  ngOnInit() {
    this.sampleGroupForm = new FormGroup({
      name: new FormControl(''),
      mail: new FormControl(''),
      age: new FormControl(0),
    });
  }
}
```

#### コンポーネントHTMLファイル
```html
<form [formGroup]="プロパティ" (ngSubmit)="メソッド">
  <input type="text" formControlName="名前" />
  <input type="submit" value="登録">
</form>
```

参考本では、リアクティブフォームを使う際は、(submit)="" ではなく(ngSubmit)="" 使うと記載があるのだが、(submit)の方を使っているサンプルもあり、理由が分からず混乱中・・・。

本家サイトでは、(ngSubmit)を使っているサンプルがあった。
https://angular.jp/start/start-forms

使い分ける必要があるのか、どちらでも構わないのかは分からず。

formControlは、関連付けるタグの種類( ```<input type>```, ``` <select>``` ) によって valueも変わる。例えば、```<input type="checkbox">```なら真偽値になる。

### FormBuilder
更にFormGroupよりも、簡易に扱えるのがFormBuilderを使った方法です。

#### コンポーネントTSファイル
```typescript
import { Component, OnInit } from '@angular/core';
import { FormGroup, FormBuilder } from '@angular/forms';

@Component({ 省略 })
export class ...Component implements OnInit {
  fg:FormGroup;

  constructor(private fb: FormBuilder) {}

  ngOnInit() {
    this.fg = this.fb.group({
      name: [''],
      mail: [''],
      age: [0]
    });
  }
}
```

# 関連記事
* [Angular はじめに覚えること](https://qiita.com/thankkingdom/items/ca8acd2fd75c7778443d)
* [Angular フォーム (2)：バリデーション](https://qiita.com/thankkingdom/items/6a32cc6edf2f431a8b43)
* [Angular 次に覚えること](https://qiita.com/thankkingdom/items/13eb62a8d35a65c819dd)

# 参考資料
* 『Angular超入門』 著者：掌田 津邪乃
* https://angular.jp/start
WindowsでTclスクリプトのメモリ使用量を調べる方法

Tclスクリプトの特定の処理のメモリ使用量を調べたくて、Win32 APIを使う方法とか、WMIを使う方法とか、色々調べていたのですが、TWAPIパッケージのget_process_memory_infoメソッドが一番簡単でした。

# [The Tcl Windows API (TWAPI)](https://twapi.magicsplat.com/)
TWAPIはいくつかのWindows APIやWindowsに依存する処理を集めたパッケージです。

Win32 API関数を使いたい場合はサポートしていないものもあるので、Ffidlパッケージで悪戦苦闘しながら実装していましたが、Windows Management Instrumentation(WMI)を使う場合や、メモリ使用量の取得のような汎用的な情報取得に便利な機能が詰まっているようです。

# メモリ使用量の取得
[get_process_memory_infoメソッドでメモリ使用量に関する情報を取得できます。](https://twapi.magicsplat.com/v4.6/process.html#get_process_memory_info)

```Tcl
package require twapi
array set process_memory_info [::twapi::get_process_memory_info]
parray process_memory_info
```

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

```Tcl
process_memory_info(-pagefaults)            = 8895
process_memory_info(-pagefilebytes)         = 20496384
process_memory_info(-pagefilebytespeak)     = 20496384
process_memory_info(-poolnonpagedbytes)     = 20496
process_memory_info(-poolnonpagedbytespeak) = 20496
process_memory_info(-poolpagedbytes)        = 261832
process_memory_info(-poolpagedbytespeak)    = 262008
process_memory_info(-privatebytes)          = 20496384
process_memory_info(-workingset)            = 34123776
process_memory_info(-workingsetpeak)        = 34127872
```

`get_process_memory_info`は`{key value key value ...}`というリストで結果を返します。

リストから特定のkeyのvalueを取得する方法はいくつかありますが、ここでは一覧表示するのに`parray`メソッドが簡便だったので、いったん配列にしました。
Autifyエンジニアが利用している業務ツールまとめ

＊この記事は [Autify アドベントカレンダー2021](https://qiita.com/advent-calendar/2021/autify) の8日目のエントリです。

この記事は先日公開された「[Autify カスタマーサクセスチームが利用している業務ツールまとめ](https://note.com/74lieco/n/na95fcf867e08)」のエンジニア版になります。コミュニケーションツール等はカスタマーサクセスチームと同じなのでこの記事ではプロダクト開発時に2021年12月時点で利用しているツールをご紹介します。

### GitHub

説明は割愛します :smile:

http://github.com/


### CircleCI

基本的にCI/CDのパイプラインはCircleCIを利用しています。具体的には、コードの静的の解析、単体テストの実行、Autify の実行、Dockerイメージの作成とアップロード等に利用しています。

https://circleci.com/

### GitHub Actions

基本的にCI/CDのパイプラインはCircleCIを利用しています。GitHub ActionsではPRにラベルが付いているか確認したりリリースブランチを作成したり開発ワークフローにまつわる細かいことを自動化するために利用しています。

https://github.com/features/actions

### BentoML

BentoMLはモデルに対応するAPIエンドポイントを簡単に提供できるようにしてくれるツールです。MLチームはこのツールを近いアプリケーションチームがすばやくモデルを利用できるようにしています。

https://github.com/bentoml/BentoML

### AWS

基本的に弊社のサービスはAWS上で動いています。具体的に利用しているサービスや用途については以下のプレゼン資料をを見ていただければと思います。 

https://aws.amazon.com/

https://speakerdeck.com/doublemarket/building-a-scalable-e2e-test-execution-platform-with-aws-fargate-and-lambda

### Heroku

一部のサービスで利用しています。やはりさくっとデプロイできるHerokuはとても便利ですね。

https://www.heroku.com/

### Codecov

コードカバレッジ測定ツールです。コードカバレッジは100%を目指すというよりはこのツールで行ごとのカバレッジを視覚化し重要な部分がカバーできているか？などを確認し日々テストを追加しています。

https://codecov.io/

### Sentry

エラートラッキングツールです。フロント、サーバサイドのすべてでこれを利用してエラーが発生した場合にSlackの特定チャンネルに通知をするようにしています。ただログ等に利用しているDatadogでもフロントのエラートラッキングができるので一部のプロジェクトではフロントだけDatadogで管理するようにしています。

https://sentry.io/

### Autify 

Autify for Web, for Mobile ともに Autify for Web を利用してE2Eテストを行っています。テストはステージングにマージされるたびに自動で実行されるようになっています。また定期実行もしていて問題があればSlackに通知するようにしています。

https://autify.com/

### Datadog

モニタリングツールです。かなり機能が豊富で弊社ではその中で、ログ、RUM、Session Replay, エラートラッキング、モニタリング、メトリクスを利用しています。

https://www.datadoghq.com/

### Statuspage

プロダクトの状況をユーザーに伝えるためのツールです。障害発生時などのワークフローをもと更新し顧客がプロダクトが正常に動作しているのか、何か問題が発生しているのか？問題が発生している場合どういう状況なのかを簡単に共有できるので便利です。

https://www.statuspage.io/

https://status.autify.com/

### PagerDuty

インシデント管理ツールです。

https://www.pagerduty.com/

### ConfigCat

Feature Flagを管理するツールです。一部の顧客に限定的に機能を公開するときや、大きな変更で影響範囲が広い場合に、問題がないことを確認しながら段階的に全体に展開していくときに利用しています。

https://configcat.com/

## まとめ

理由がはっきりしていれば基本的にいろいろなツールを試すことができるので、新しいツールを触ることが好きな人には楽しい環境かなと思います。引き続き、プロダクト開発に集中するために、面倒なことはどんどん便利なツールに投げていきたいなと思います。