OmniAICreator/Qiita-1.07M huggingface dataset:
Terraformの個数管理リファクタリング

Workspaceが増えると、`resource`の管理、及びそれに付随する`variable`の管理が辛くなってきます。
ここでは、`count`を例にリファクタリングを考えたいと思います。

# リソースの個数管理

`resource`におけるmeta-argument[^1]として、`count`を設定することができます。
これは数値を設定することで、設定されたリソースの個数を指定することができます。例えば、GCPのリソースの場合は以下に使います。

[^1]: https://www.terraform.io/docs/configuration/resources.html#meta-arguments

```sh
variable "count_standard" {
  default = {
    "prod" = 1
    "dev"  = 1
  }
}

resource "google_compute_instance" "standard" {
  name         = "sample"
  count        = var.count_standard
  machine_type = "n1-standard-1"
  zone         = "asia-northeast1-b"

  boot_disk {
    initialize_params {
      image = "debian-cloud/debian-9"
    }
  }
  ...（以下略）...
}
```

さて、上のコードではカウントの値を`variable`に切り出しています。また、カウントの数値は`1`なので、作成されるリソースは1つになります。

上の例のように`workspace`機能を用いて、開発環境と本番環境など複数の環境で、リソースの個数を変えたい場合は、変更者が特に気を使う必要があります。環境が多くなればなるほど、設定するカウントの個数も増えていくので、設定ミスが発生する可能性も上がります。
作成したいリソースが、要件上、1つもしくはある定数のみしか扱わない場合、コンストな変数を使うことができればこのような不安を払拭することができます。

そこで、リソースが定数の場合には`locals`で、コンストな変数に見せかけるようにします[^2]。以下が書き換えたコードです。

[^2]: https://febc-yamamoto.hatenablog.jp/entry/2018/01/30/185416

```sh 
variable "use_standard" {}

locals {
  "cont_standard" = "${var.use_standard == "" ? 0 : 1}"
}

resource "google_compute_instance" "standard" {
  name         = "sample"
  count        = local.count_standard
  machine_type = "n1-standard-1"
  zone         = "asia-northeast1-b"

  boot_disk {
    initialize_params {
      image = "debian-cloud/debian-9"
    }
  }
  ...（以下略）...
}
```

`locals`を使って、リソースの有無を`use_standard`によって決定するように書き換えました。
少しはマシになりましたが、今度は作成の有無を決定する`variable`の管理が大変になります。複数の`workspace`がある場合はなおさらです。そこで、`list`と`contains`関数を用いて改善してみます。

```sh 
variable "use_standard" {
  default = [
    "prod"
    "dev"
  ]
}

locals {
  "cont_standard" = "${contains(var.use_standard, terraform.workspace) ? 0 : 1}"
}

resource "google_compute_instance" "standard" {
  name         = "sample"
  count        = local.count_standard
  machine_type = "n1-standard-1"
  zone         = "asia-northeast1-b"

  boot_disk {
    initialize_params {
      image = "debian-cloud/debian-9"
    }
  }
  ...（以下略）...
}
```

`resource`, `locals`, `variable`をそれぞれ別ファイルで管理すると、`count`については対応する`variable`を変更するだけになります。移行時のPRも、ブロックの意味が取りやすいので、読みやすいかと思います。
[Angular] TAB押下時の制御をしたいからDOMに直接イベントを登録する

## やりたかったこと
どうしてもTABの制御をしたかったため、DOMに対してイベントを登録する必要があった。

## やり方
```js
  constructor (
    private elementRef: ElementRef,
  ) {}

  ngAfterViewInit() {
    this.elementRef.nativeElement.querySelectorAll('selector').forEach((element: Element) => {
      element.addEventListener('keydown', this.onTab.bind(this));
    });
  }

  private onTab(event) {
    if (event.key === 'Tab' || event.code === 'Tab') {
      event.preventDefault();
      // 制御
    }
  }

```

## ポイント
- `this.onTab.bind(this)`で値をバインディングする
- `preventDefault()`で動作を抑制する

## 参考
https://stackoverflow.com/questions/41609937/how-to-bind-event-listener-for-rendered-elements-in-angular-2
（メモ）Djangoのチュートリアルをやる。サイト通りやってもうまくいかない。

最近はDjangoをちょっと触ってみようと思います。
herokuを用いたFlaskのwebアプリのデプロイに失敗したから。

Djangoのwebアプリを作るにはPyCharmというIDEを使うのが良いらしい。
[PyCharmのインストール方法](https://gammasoft.jp/python/pycharm-install-on-windows/)
無料版でも十分使えるけど、学生教職員は有料版を無料で使える。
[JetBrains Student Pack（学生・教職員向け無料ライセンス）と申し込み方法](https://blog.jetbrains.com/jp/2019/08/22/2105)

Djangoの使い方
[Djangoによるwebアプリケーション開発](https://eiry.bitbucket.io/index.html)
上のURLの環境設定のやり方に変更があった。下を参照した。
[環境設定方法](https://docs.python.org/ja/3/tutorial/venv.html?highlight=pip)
```startproject```をやっても全然動かないな、、、って思ってて調べてたら、「.py」入れてはいけないと下のサイトが教えてくれました。最後に``` .```をつけるかでもちょっとだけ変わる。今回はつけない。
[Djangoのプロジェクトを作成する](https://medium.com/@kjmczk/django-project-268687f919b6)
51歳からのプログラミング　備忘　Laravel  日付でデータ検索

```html:html
<?php
  $date = new DateTime();
  $date = $date->format('Y-m-d');
?>

<form name="sample" action="sample" method="post">
   {{ csrf_field() }}
      開始日<input type="date" name="start" value="{{$date}}">
      至　日<input type="date" name="end"   value="{{$date}}">
      
     <button>送信</button>
</form>
```
<font color="red">
\<input type="date">の日付型は、yyyy/MM/dd ( 2019-12-24 )という表示形式。</font>
なのでPHPでフォーマットを合わせてます（'Y/m/d')

```php:controller
public function sample(Request $request){
  $form  = $request->all();
  if(!empty($form)){
      $start = date('Y/m/d 00:00:00',strtotime($form['start']);
      $end   = date('Y/m/d 00:00:00',strtotime($form['end']);
  }
}

if(empty($start)){ $start = '1970-01-01 00:00:00'; }
if(empty($end)  ){ $end   = '9999-12-31 23:59:59'; }

$sample = Sample::whereBetween('created_at',[$start,$end]);
```

#####if(!empty($form))について
<form>で送信されるデータがNULLだったとしても、formデータは配列で送られるので、配列データは中身なしで送られる。なので<form>を空送信しても、

isset($form) = true
となってしまう。
<br>
配列が空であることを確認するのは、emptyを使いましょう。emptyで<form>を空送信すると

!empty($form) = false
になってくれます。

---
#####日付の調整(00:00:00)
日付検索する場合に、
`whereBetween('created_at',['2019-12-24','2019-12-24'])`としてしまうと検索されない。
`whereBetween('created_at',['2019-12-24 00:00:00','2019-12-24 23:59:59']`としよー。

忘れるな！俺！
List.minByの挙動がわからぬ

どうにもminByの挙動が不可解。
僕の理解が浅いだけなのか、それともissue投げるべきバグなのかがわからない・・・。

2019/12/27
バグじゃなくてそもそも使い方おかしいよ教えて頂きました！（コメント欄参照）
僕の使い方がおかしいだけでしたね:tired_face:
本当にありがとうございます！

##対象のリスト
```fsharp
// トランプのカード
type Card = 
  {
    // 値
    Number : int
    // 柄
    Suit : string
    // 表示上の数値(A,J,Q,K用)
    Write : string
  }

// ジョーカーを除くトランプの集合体を作る
let makeSuitCards suit = 
  [ for i in 1..13 -> 
    {
        Number = i;
        Suit = suit;
        Write = 
          match i with 
            | 1  -> "A"
            | 11 -> "J"
            | 12 -> "Q"
            | 13 -> "K"
            | _ -> i.ToString()
    }]

let makeDeck = makeSuitCards "H" @ makeSuitCards "C" @ makeSuitCards "S" @ makeSuitCards "D"
let cards = makeDeck
```

##minByする

```fsharp:minBy試す
// 最小値を取る、条件付き -> Cの1が取れるはずなんだが・・・
cards |> List.minBy(fun elm -> elm.Number = (List.min cards).Number && elm.Suit = "C" ) |> printfn "%A"
```

↓↓↓

```txt:実行結果
{Number = 13;
 Suit = D;
 Write = K}
```
！？
なんか想定と違うものが返ってきた。

##maxByだと
```fsharp:maxByでやってみる
// C1が取れるよね
cards |> List.maxBy(fun elm -> elm.Number = (List.min cards).Number && elm.Suit = "C" ) |> printfn "%A"
```

↓↓↓

```txt:実行結果
{Number = 1;
 Suit = C;
 Write = A}
```
意図通り取れるんだよなぁ。

## 複数条件なのが悪い？
```fsharp:Numberだけ指定してみる
// Number=2を指定してるけどやっぱりminByだと取れない
cards |> List.minBy(fun elm -> elm.Number = 2 ) |> printfn "%A"
cards |> List.maxBy(fun elm -> elm.Number = 2 ) |> printfn "%A"
```

↓↓↓

```txt:実行結果
{Number = 13;
 Suit = D;
 Write = K}
{Number = 2;
 Suit = H;
 Write = 2}
```

```fsharp:Suitだけ指定してみる
// Suit="C"を指定してるけどやっぱりminByだと取れない
cards |> List.minBy(fun elm -> elm.Suit = "C" ) |> printfn "%A"
cards |> List.maxBy(fun elm -> elm.Suit = "C" ) |> printfn "%A"
```

↓↓↓

```txt:実行結果
{Number = 13;
 Suit = D;
 Write = K}
{Number = 1;
 Suit = C;
 Write = A}
```

##謎
やっぱりmaxByはちゃんと絞れるけどminByは絞れてない感じ。
なんでやねん( ；∀；)

公式リポジトリらしきところで実装見ても、変な事してるようには見えないんだけどなぁ
https://github.com/fsharp/fsharp/blob/master/src/fsharp/FSharp.Core/list.fs

```fsharp:fsharp/list.fsから抜粋
        [<CompiledName("MinBy")>]
        let inline minBy projection (list:list<_>) =
            match list with 
            | [] -> invalidArg "list" LanguagePrimitives.ErrorStrings.InputSequenceEmptyString
            | h::t ->
                let mutable acc = h
                let mutable accv = projection h
                for x in t do
                    let currv = projection x
                    if currv < accv then
                        acc <- x
                        accv <- currv
                acc


        [<CompiledName("MaxBy")>]
        let inline maxBy projection (list:list<_>) =
            match list with 
            | [] -> invalidArg "list" LanguagePrimitives.ErrorStrings.InputSequenceEmptyString
            | h::t ->
                let mutable acc = h
                let mutable accv = projection h
                for x in t do
                    let currv = projection x
                    if currv > accv then
                        acc <- x
                        accv <- currv
                acc
```
MFI、構造化データ、Lighthouse(Audits)覚え書き

※2019/11/08時点の情報です。
#MFI
###MFIとは
* MFIとは「Mobile First Index（モバイルファーストインデックス）」の略称。
* 2016年にGoogleが導入を発表、2018年3月から頃から順次適用開始された。
<br><font color="blue">→これによって、GoogleにおけるSEOの評価基準が変わった。</blue>

###どう評価基準が変わったのか
* MFI導入以前：PCページが検索順位を決める上での評価対象、モバイルは評価対象外。
* MFI導入後：モバイルページが評価対象のメインに。

###MFI導入後、どのような対策が必要か
* 今までPCページに行ってきたSEO対策を、モバイルページにも行う必要がある。
* PCページにしかない重要なコンテンツを、モバイルページにも反映する必要がある。
* PC向けのページしか存在しない場合、モバイル向けのページを作成することが推奨される。

###参考サイト
<a href="https://www.seohacks.net/basic/terms/mfi/">MFIとは（モバイルファーストインデックスとは）</a>
<a href="https://webmaster-ja.googleblog.com/2018/03/rolling-out-mobile-first-indexing.htmlGoogle">ウェブマスター向け公式ブログ</a>
<a href="https://qiita.com/chika_1127/items/44318fb2569e23f41066">MFI（モバイルファーストインデックス）の情報まとめ</a>

#構造化データ
###構造化データとは
* Googleのクローラーにテキスト情報やコンテンツ内容をより適切に伝えるためのコード。
* HTMLにマークアップする。

###構造化データのメリット
* Googleにコンテンツが認識されやすくなる、評価されやすくなる。
* Googleの検索結果がリッチリザルトになる。

###構造化データのマークアップ
* 説明すると長くなりそう＆日々仕様が更新されそうなので、下記参考サイトをご参照ください。

###参考サイト
<a href="https://www.akindo2000.net/blog/structured-markup/">構造化マークアップはSEO対策に効果があるのかやってみた</a>
<a href="https://seolaboratory.jp/95442/">構造化データとは？マークアップ方法からSEO効果まで解説！</a>
<a href="https://webtan.impress.co.jp/e/2019/08/05/33500">SEO担当者向けJSON-LD構造化データの書き方ガイド（超入門）</a>
<a href="https://developers.google.com/search/docs/guides/sd-policies?hl=ja">構造化データに関するガイドラインに準拠する</a>

#Lighthouse(Audits)
###Lighthouse(Audits)とは
Chromeに搭載されている、サイトパフォーマンス計測ツール。
得られる情報を基に、Webページのスコア改善(速度改善)を行う。
###使い方
下記サイトを参照。
<a href="https://qiita.com/fumihiko-hidaka/items/d1355ce4ea34975ad3bc">サイトの速度改善をしたい？それChromeのAuditsで（だいたい）できるよ！</span>

###スコア改善の方法
* 計測結果と一緒に、改善ポイントが英語で表示されるので、そこを調整。

###スコア改善を行うとどうなる？
* コンテンツの表示速度や、実行速度が上がる。
* GoogleからのSEO評価が上がる。<br>

###参考サイト
<a href="https://qiita.com/TanakanoAnchan/items/01c02a5bfae4c04465e5">Lighthouseの計測結果を見ていく</a>
PlayCanvasでクリックできるボタンを設置する

### PlayCanvasでクリックに反応するボタンを追加する方法
<img width="1278" alt="スクリーンショット 2019-12-27 16 39 11" src="https://user-images.githubusercontent.com/39250588/71507310-fed9da80-287b-11ea-8648-b32fcebe39cb.png">

#### 今回のプロジェクトの詳細はこちらになります

- 動作（デモ）
https://playcanv.as/p/eWCvBycn/

- プログラム
https://playcanvas.com/project/657221

PlayCanvasでクリックできるボタンを4つ追加するには、このヒエラルキーになります。

- 2D Screen
  - Button
    - Text
  - Button
    - Text
  - Button
    - Text
  - Button
    - Text

### 2D Screenとボタンをエディターから追加する
2D Screenを「Add Entity」　→ 「User Interface 」 → 「2D Screen」から追加します。

<img width="1340" alt="スクリーンショット 2019-12-27 15 54 45" src="https://user-images.githubusercontent.com/39250588/71506936-b968dd80-287a-11ea-8e74-ccfd7c00362a.png">

### クリックに反応させる

ボタン(Element Component)にクリックを検出するには、 `this.entity.element.on`でクリックイベントを取得します。

https://developer.playcanvas.com/en/api/pc.ElementComponent.html

```javascript
var Popup = pc.createScript('popup');
// エディターから変更できるようにattribteusを追加する
Popup.attributes.add("message", {type: "string", default: "message"})

// 起動時
Popup.prototype.initialize = function() {
    //　タッチできる端末だったら
    if(this.app.touch){
         // element componentがタッチされたらattributes: messageアラートとして表示する
        this.entity.element.on(pc.EVENT_TOUCHSTART, () => this.show(this.message))
    }else{
         // element componentがクリックされたらattributes: messageアラートとして表示する
        this.entity.element.on("click", () => this.show(this.message))
    }
    
};

Popup.prototype.show = (message) => alert(message)
```


<font color="OrangeRed">
PlayCanvas開発で参考になりそうな記事の一覧です。
</font>
<font color="OrangeRed">
入門

- [PlayCanvas入門- モデルの作成～ゲームに入れ込むまで](https://qiita.com/yushimatenjin/items/2a2c35fe7b1d08f9e361)
- [JavaScriptでスロットを実装する。【PlayCanvas】](https://qiita.com/yushimatenjin/items/e84c42da74df1eb07386)
- [3Dモデルのビューワーを3分で作る【初めてのPlayCanvas】](https://qiita.com/yushimatenjin/items/4b09c9e2076a0b2a6933)
</font>
<font color="OrangeRed">
応用
</font>

- [PlayCanvasのコードエディターでes6に対応する](https://qiita.com/yushimatenjin/items/a61a21c64c1c1a550dd4)
- [Gulpのプラグインを書いたらPlayCanvasでの開発がめちゃくちゃ便利になった](https://qiita.com/yushimatenjin/items/5f0f178e8a4ba4a5ee57)
- [PlayCanvas Editorに外部スクリプトを読み込む新機能が追加されたので開発方法を考える。- Reduxを組み込む](https://qiita.com/yushimatenjin/items/7a64220cceac66843d7d)
</font>
<font color="OrangeRed">
その他の記事はこちらになります。

- [React Native + PlayCanvasを使ってスマートフォンゲームを爆速で生み出す](https://qiita.com/yushimatenjin/items/7c7ad5d35473c11f32f2)
- [PlayCanvasのエディター上でHTML, CSSを組み込む方法](https://qiita.com/yushimatenjin/items/814b4a32db53397219df)
- [【iOS13】新しくなったWebVRの使い方 ](https://qiita.com/yushimatenjin/items/344d86b3d193e0a88567)
</font>

<font color="OrangeRed">
その他関連
- [PlayCanvasタグの付いた記事一覧](https://qiita.com/tags/playcanvas)
</font>


### PlayCanvasのユーザー会のSlackを作りました！
少しでも興味がありましたら、ユーザー同士で解決・PlayCanvasを推進するためのSlackを作りましたので、もしよろしければご参加ください！

[日本PlayCanvasユーザー会 - Slack](https://t.co/IdSRIfJhN5?amp=1)
【Rails】日付の入力フォームの作成とブラウザへの出力についてのまとめ

#はじめに
railsでのWEBアプリ開発中において、日付関係の取り扱いで悩んだのでその備忘録です。

#やりたいこと
　htmlの**inputタグ**には**type = "date"**が指定できます。
　この機能をそのまま利用して入力フォームを作成します。

　この属性は、特殊な日付選択インターフェイスを使用して、ユーザーに日付を入力させる入力フィールドを生成します。結果の値には年、月、日が含まれますが、時刻は含まれません。
　ブラウザによってインターフェースはまちまちです。

## inputタグ
Androidのchoromeでは以下の画像のように表示されます。
下手に自分でフォームを作るより、ユーザビリティが高いなーと思います。
![102628 (2).jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/541458/9f9991d6-901e-47f1-e58b-4cf19f72964f.jpeg)

## Ruby strftimrメソッドで表示するフォーマットを整える
Rubyのstrftimeメソッドは、日付や日時のデータを編集して文字列に変換するためのメソッドです。
例として、”2019-12-27 16:04:05”といった日時データを”12/27”だけ表記したい場合があります。
むしろ時刻で秒単位まで表示する必要がある時のほうが少ないのではと感じます。

strftimeメソッドは上記のようなフォーマットを整えるとき使用すると便利です。

##【問題点】datetime型とdate属性の相性が悪い
inputタグ属性dateを使用するメリットとstrftimeメソッドの利便性は理解いただけたでしょうか。
この二つを組み合わせるときに以下の制約が邪魔します。

1.　inputタグ属性dateは**日付しか**入力できない
2.　strftimeメソッドは日付・時刻どちらかが**NULLだと使用できない**
　　- 付随して、strftimeメソッドを使用し参照できるテーブルの**カラム型はdatetime**である必要がある

まとめると、inputタグ属性dateでそのまま保存しても、strftimeメソッドは使用することができません。

##【解決策】いったん置き換える
### to_datetimeメソッド
date型をdatetime型に置き換えてくれます。この時設定されていない時刻のデータには０が置き換えられます。
### 手順
1. inputタグ属性dateでとりあえずdatetime型のカラムにデータを保存する。
2. カラムのデータをto_datetimeメソッドを用いてNULLを0に置き換える。
3. strftimeメソッドでフォーマットを整えて表示する。

以上のプロセスでエラーを吐くことなく実行することができました。

##　実際の処理
フォーム

```html:new.html.erb
<!-- 日付 -->
            <div class ="input-date">
                <input name="date" type="date" />
            </div>
```
コントローラにて入力フォームからの値の受け取り

```ruby:posts_controller.rb
    @homework_post = Hindext.new(deadline:params[:date])
    @homework_post.save
```

viewでおきかえ（本来コントローラで行うべき処理ですが都合上viewファイルで行っています。）

```erb:new.html.erb
<!-- 日付 -->
<% date = index.deadline %>
<% dated = date.to_datetime %>
<%= dated.strftime('%m/%d') %>
```

問題なく動作しました。

#まとめ
いろいろ壁があって疲れるにゃ
エクセルを把握するように、エクセルの小技4選

元記事：[https://jp.scrapestorm.com/tutorial/4-excel-tricks-to-grasp-excel/](https://jp.scrapestorm.com/tutorial/4-excel-tricks-to-grasp-excel/)
ExcelスプレッドシートはOfficeシリーズオフィスソフトの一種で、日常生活·作業中のフォームへのデータ処理を実現しています。これは，友好的なヒューマンインタフェースにより、学びやすい知能化操作方式により，ユーザに実用的で個性的なリアルタイムテーブルを容易に持たせることができ、仕事、生活における右腕になります。
![エクセル.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/482909/a1b61670-ecff-211b-5139-0a2d4037b2e3.png)
エクセルの達人になるにはどうすればいいのか、実は1つの道しかありません。それは、ショートカットの方法を多く知って、自分の仕事の効率を高めることです。そこで、いくつかの上級者のテクニックをご紹介します。
####1.数字、英文字、特殊記号、単位などの追加
まず、目標列を選択して、右クリック、「セルの書式設定」に行きます。出できたポップアップに「ユーザー設定」を設定してください。ユーザー設定に「0000円」の形式で入力する。「0」の数は文字数です。後ろに数字、英文字、特殊記号、単位などの追加ができます。
![数字、英文字、特殊記号、単位などの追加.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/482909/e954279a-35b9-d06e-e271-aa3c5f129b34.gif)
####2.電話番号の分け
日本には電話番号をより便利に検索するために、「‐」で番号を分けます。「‐」の追加方法は上記単位などの追加に似っています。同じく、列を右クリックして、「セルの書式設定」で設定します。ユーザー設定に「00－0000－0000」を入力してください。もちろん、場合によって、
![電話番号の分け.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/482909/9bfdf2c5-e39c-a693-57d2-7096dd4a0f83.gif)
####3.サム公式
ExcelはOfficeソフトとして、最も強力な計算能力があります。仕事によく使えるの公式はやはりサムですね。サムを手入力はちょっと面倒だと思います。今回は一つのショ—トカットキ— を紹介します。列を選択して、キーボードの「Alt」+「＝」を押すと、サム公式は自動的に生成します。
![サム公式.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/482909/6452ecf6-5268-41e3-0e39-9404b6a44866.gif)
####4.数字の抽出
[スクレイピング](https://jp.scrapestorm.com/tutorial/4-excel-tricks-to-grasp-excel/)で抽出されたデータが時々混雑しています。下記画像のように、名前と点数を混ぜ合わせています。
![数字提取.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/482909/c6283ebd-9be8-c506-85f7-b2a09d7bd74e.png)
素早く数字などを引き出すのは、Excel2013に追加した、クイックフィル機能、ショートカット「Ctrl」+「E」を利用してください。第一行目に引き出す数字を入力して、「Ctrl」+「E」を押すと、エクセルは自動的に他の数字を引き出します。
![数字の抽出.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/482909/386dde10-d6ed-5511-60ec-aad4fcceb894.gif)
補足ですが、このスキルは現在office 2013とそれ以上のバージョンしか適用されておらず、officeバージョンが比較的低いならダメかもしれません！
Ethereum pet shop におけるContract has not been deployed to detected network (network/artifact mismatch)エラーの対処法

# コンソール上で上記エラーが起きた時の対処法<br>（Adoptを押しても処理が行われない場合）

1.　bulidフォルダ内の全てのJSONファイルを削除。（Adoption.jsonと Migrations.json）
<img width="259" alt="スクリーンショット 2019-12-27 16.21.04.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/328421/682acb9c-8b7b-97e3-ccc5-e22c79db48bd.png">

2.　`truffle compile`, `truffle migrate`を再度実行。
3.　最後に`npm run dev`を実行するとバグが治っているはず。

## 参考文献
- [スマートコントラクトのデプロイから実行まで](http://toughandglobal.hateblo.jp/entry/2017/12/22/075332)
- [Truffleのpetshopチュートリアルの自分用の要点まとめ](https://qiita.com/jansnap/items/694d42120d364fd5c833)
独習C++の勉強メモ_2章の3

２章のまとめ③
#コンソールからの入力
コンソールから出力　std::cout
コンソールから入力　std::cin
文字列入力には、１行を取得できるstd::getline()関数を利用

```C:
std::getline(std::cin,line)
```

#関数のオーバーロード
引数やreturnは違うが同じ名前の関数を定義できる。なんの定義もなく関数を宣言すれば使えるけど、オーバーロードした関数の中で、元の関数を使うのも賢い。これは教わらないと瞬間的にでない発想だった。。。

```C:
int sum(int a, int b, int c) {
	int d = a + b + c;
	return d;
}

int sum(int a, int b) {
	return sum(a, b, 0);//↑のsumを呼んでる
}
```

仮引数の型が異なっていても、呼び出しの方の実引数でどの関数か判断できるため、異なる引数型の関数でも同名可能。

##型が違うオーバーロード
その構造体専用のオーバーロード関数も定義可能

```C:
struct vec2d{
int x;
int y;
};

int add(int a, int b){
int c = a + b;
return c;
}

//vec2d専用のadd関数（引数も戻り値も異なる）を新しく定義できる！
vec2d add(vec2d lf, vec2d ri){
vec2d v;
v.x = le.x + ri.x;
v.y = le.y + ri.y;
return v;
}
```

引数のタイプがint double / double int とかのパターンはコンパイラが暗黙型変換できないので利用不可だが、**どちらの引数もfloatだった場合はdoubleをつかったオーバーロードが呼び出されるので注意が必要とのこと**。これは、より安全な型変換のほうが優先されるため。（floatよりdoubleのほうが表現できる変数の幅が広い）・つまりオーバーロード解決は暗黙の型変換が少なくて済む（データの欠損が発生しずらい）ものを優先的に呼び出す。

#デフォルト引数
関数呼び出し時に実引数が省略されている場合、関数内部に暗黙的に渡される実引数をていぎしておくこと。実引数側の欠損を補うことができる。順番的に最初や途中の引数がデフォルト引数を設定できないことに注意。

#結局オーバーロードかデフォルト引数か
指針としては、
オーバーロード：引数が省略されたときに処理の中身を変える必要があるもの
デフォルト引数：引数が１つずつ省略されても問題ないもの、関数の処理が変わらないもの
にする
[WordPress] カスタム投稿タイプで投稿した記事からRSSを取得する流れ

WordPressのカスタム投稿タイプからRSSにする流れを
メモしておきます。

# 1.WordPressに「カスタム投稿タイプ」プラグインを導入
追加編集　※注.各テーマごとに設定する

```php:〜/wp-content/themes/○○○○○（各テーマフォルダ）/functions.php
// カスタム投稿タイプの追加
add_action( 'init', 'create_post_type' );
function create_post_type() {
register_post_type( 'news', // 投稿タイプ名の定義
	array(
			'labels' => array(
			'name' => __( '新着情報' ), // 表示する投稿タイプ名
			'singular_name' => __( '新着情報' )
		),
			'public' => true,
			'menu_position' => 5,
		)
	);
}
```
ここまでで設定終わり

# 2.WordPressリロードして投稿
新着情報という枠が出てくるのでそこから投稿可能
※新着情報という見出しはfunctions.phpに追加したところで変更可能

```php
// 省略
'name' => __( '新着情報' ), // 表示する投稿タイプ名
'singular_name' => __( '新着情報' )
// 省略
```

# 3.サイト表示＆URLにRSS取得のパラメータを書く

`http://www.example.com/news/feed/`　news以降追加
もしくは
`http://www.example.com/feed/?post_type=news`　feed以降追加

「news」の部分にfunctions.phpで設定した「register_post_type」の第1引数の値を入れる

参考. [WordPress カスタム投稿タイプのフィード URLを取得する方法](https://hirashimatakumi.com/blog/2879.html)

# 最後に
3で取得したURLをphp等を利用して情報を抜き出していろんなサイトに埋め込むことが可能です。
その方法はこちらを参照
参考. [[php]シンプルなRSSのサンプル](https://qiita.com/dai_designing/items/2dbd2c58854e57afb812)
Svelte - めちゃくちゃツウに思われる一言＠2020年JavaScriptトレンド

# ツウに思われる一言

「好きなJavaScriptフレームワークは何ですか？（どうせreactかvueだろ）」
「・・svelte かな」
「こいつできる・・！！！」

なんていう冗談はさておき。

# The State of JavaScript

2万人以上の開発者にアンケートをとって
その年のトレンドなどをまとめたWebサイトがある。

その2019年版が最近公開されて、
特筆すべきは「関心のあるJavaScriptのフレームワーク」に svelte が2位にランクインした。

![スクリーンショット 2019-12-27 15.48.34.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/124296/46119224-cbee-5cd5-3fca-8fddc0b7f4ee.png)

引用：https://2019.stateofjs.com/front-end-frameworks

# Svelteとは

JavaScriptフレームワークの一つ。
reactやvueと決定的に違うのは、コンパイルが必要になること。
ただし、コンパイルすることでピュアなJavaScriptになるので
ライブラリのバージョンに依存することがなく、ランタイムが無いのが特徴。

## 簡単に言うと

実行がめっちゃ早くて、 `svelte.js` みたいな読み込みが不要ということ。

# Svelteの開発者

svelteの開発者はリッチハリス (Rich Harris) という人で、rollupの開発者としても有名。
rollupとは、webpackと同様のバンドルツールで
まあ、界隈では有名な方。

そんなリッチハリスが作ったJavaScriptフレームワークということもあって
品質はある程度担保されているし、業界的にも注目されていることがわかる。

svelete自体は2016年の11月にリリースされていたが
ようやく世間の関心がsvelteに向いたと言える。

# 関連プロダクト

## cliツール （reactでいう create-react-app）

現状、cliツールは存在していなくて、テンプレートから作るスタイル。

```sh
npx degit sveltejs/template my-svelte-project
cd my-svelte-project
npm install
npm run dev
```

参考： 公式サイトの Getting Start から
https://svelte.dev/blog/the-easiest-way-to-get-started#2_Use_degit

## SSR対応ツール （reactでいう Next.js）

sapperというプロダクトが公式からリリースされている

https://sapper.svelte.dev

## 静的サイトジェネレータ(reactでいう GatsbyJS)

現状、存在していない。
厳密に言うと sapper で静的ページの生成も可能となっている。

```
npx sapper export
```

参考：　公式サイトより
https://sapper.svelte.dev/docs#sapper_export

# まとめ
- State of JavaScript で `svelte` がランクインした
- `svelte` はコンパイルが必要なフレームワーク
- ピュアなJavaScriptになるのでライブラリ依存やランタイムが無い


これだけ関心が高いと
2020年は「svelteを使ってみた」という記事が増えてくると思われる。

動画解説：https://youtu.be/9_zUZ25soRo
さらば、リアクションエンジニア

# 最初に
とあるプロジェクトで自らslackの絵文字を作成し、自らslackのリアクションを押しまくるエンジニアがいた
そのエンジニアは2019年を持って、プロジェクトから抜けることになった

最終的には **リアクションエンジニア** と呼ばれ、そこそこの規模で若手メンバーが多かったり、
遠隔メンバーがいたりする中、確実にチームメンバーの心理的安全性が上がったと思った

少しでもその証拠を残そうということでこの記事を書いてみる

# リアクションエンジニアはプロジェクトにどのような効果があったのか？

## プロジェクトの説明
開発～運用までやりながら5年目を迎えているプロジェクト
プロジェクト工数推移

| 2018年(人月) | 2019年(人月) | 増率    |
|:-------------|:-------------|:--------|
| 146.85       | 218.3　　　　　 | 183%  |

世代別工数推移

| 世代 | 2018年(人月) | 2019年(人月)    | 増率    |
|:-------------|:-------------|:--------|:----------|
| 20代|60    |80.8  | 134%  |
| 30代|55.1  |106.1 | 192%  |
| 40代|31.75 |31.4  | 98%  |

## 集計
### slack登録絵文字数
| 2018年(人月) | 2019年(人月) | 増率    |
|:-------------|:-------------|:--------|
| 196       | 505　　　　　 | 257%  |
### リアクションエンジニアが作成＆登録した絵文字数(2019年に本格的に襲名した模様)
| 2018年(人月) | 2019年(人月) | 増率    |
|:-------------|:-------------|:--------|
| 13| 218　　　　　 | 1676%  |

### 総リアクション数
| 2018年(人月) | 2019年(人月) | 増率    |
|:-------------|:-------------|:--------|
| 18875| 75953　　　　　 | 402%  |

### 絵文字上位ランキングTOP3(リアクションエンジニア作成限定)
| 順位| 2018年 | リアクション数 | 備考 |
|:-------------|:-------------|:-------------|:------------|
| 1位| ランボーの画像 | 146   | 諸事情により画像は投稿できません。<br> ランボーのような感情のときに利用。  |
| 2位| ![83d17149032467ab.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/320579/b93fec9a-49a2-3ede-2320-4562ca9e357d.gif) | 54　　 | 何か依頼されたものを対応したときに利用<br> 以前のプロジェクトから持ち込んだ|
| 3位| タシカニの画像 | 30　　 | 諸事情により画像は投稿できません。<br>「確かに」というときに利用 |

| 順位| 2019年 | リアクション数 | 備考 |
|:---|:-------------|:-------------|:--------|
| 1位| ランボーの画像 | 548   | 諸事情により画像は投稿できません。<br> ランボーのような感情のときに利用。  |
| 2位| ![965e1a490b85903d.gif](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/320579/c38f12ff-c49e-b361-0dcb-259a7dff2ee6.gif)| 291　　 | 先輩っぽいことをやるときに利用 |
| 3位| ビールジョッキが震えている画像 | 290　　 | 諸事情により画像は投稿できません。<br> ビールが飲みたいときに利用 |

# 最後に
再び、リアクションエンジニアが現れることを楽しみにしている

# 2021/1/7 続き
リアクションエンジニアが去ってから1年が経過、チームにどのような変化が起きたのか
https://qiita.com/sasamamo/items/7cdcf2200f197707c8c3
[Oracle Cloud] Custom Image を使って、汎用化した Windows Server Image の作成

# はじめに

Oracle Cloud Infrastructure(以下OCI)では、イメージを指定して Compute Instance を作成します。Oracle 側で提供されているイメージを使用してCompute Instance を作成することもできますし、独自に作成したカスタムイメージを準備して作成することもできます。

今回の記事では、Windows Server 2012 の汎用的なカスタムイメージを作成する手順を説明します。汎用的なイメージとは、インスタンス固有の情報を削除した事を指します。

削除される主な内容は以下の通りです。

- SIDと呼ばれる Windows に設定される ID の削除
- イベントログ
- ホスト名やIPアドレスなどのネットワーク設定
- デバイスやドライバの情報



汎用的なカスタムイメージを作成したい理由を説明します。OCIで提供されている Compute Instance のイメージは英語となっており、日本語のものは提供されていません。日本語版 Windows Server を多く作成するときに、1個ずつ日本語化を設定していくのは手間がかかります。汎用化された日本語のカスタムイメージを使うことで、手間の削減が可能です。



# 事前準備

- OCI 上で Compute Instance (Windows Server 2012 Standard) の作成
- 日本語言語パックのインストール
- Time zone を日本に変更
- Windows Updateの実施
- その他イメージに事前に入れておきたいアプリケーションがあればインストール



詳細な手順は、適当にググって探します。



# 汎用的なカスタムイメージの作成

Oracle がイメージの汎用化に使うツールを提供しています。以下のURLで、Windows OS に合わせた3種類のツールを公開しています。

- ベア・メタルX7インスタンス
- ベア・メタルX5とVM X5、X7インスタンス
- Windows Server 2008インスタンス

今回は仮想マシンイメージとなるため、「ベア・メタルX5とVM X5、X7インスタンス」から、「oracle-cloud_windows-server_generalize_2019-02-06.SED.EXE」をダウンロードします。

https://docs.oracle.com/cd/E97706_01/Content/Compute/References/generalizedimage.htm

![1577347366300.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/104247/3ebeb55d-aa18-e2ee-dfc9-395558ebd50e.png)



事前準備で作成した Windows Server 2012 にファイルを格納して、管理者として実行します。ツールの解凍先「C:\Windows\Panther」を入力して、OKを押します。「C:\Windows\Panther」は、Compute Instance 作成時に Default で作成されているディレクトリとなります。

![1577347857854.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/104247/f086623b-2fac-9a86-fb64-5d6668ff0dcf.png)



以下の4つのファイルが生成されます

- Generalize.cmd
- Post-Generalize.ps1
- Specialize.cmd
- unattend.xml

![1577348038653.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/104247/d1abff1e-98f3-d0c2-e99b-20b41b0a91e2.png)



汎用化処理の時に、Windows Server のデフォルトアカウント opc とそのパスワードを保持し続けたい場合は、以下のファイルの imageType を`custom` に変更します。今回は、opcのデフォルトパスワードは保持しておきたいため、`custom`と変更します。
`C:\Program Files\bmcs\imageType.json`

```
{
    "imageType":  "custom"
}
```



解凍したファイルの中にある、`Generalize.cmd` を管理者として実行します。実行すると、コマンドプロンプトの画面が表示され、以下のように Sysprep が自動的に実行されます。

![1577348478253.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/104247/7bf49ed1-95f1-abec-7cb9-c3d29b553d65.png)



実行を待機していると、自動的に リモートデスクトップから遮断されます。リモートデスクトップから遮断した直後では、まだ汎用化処理をしているため、ここから数分待ちます。

![1577348500476.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/104247/8d5fe1b5-7ac0-f9f2-7e7e-0be0a98e6283.png)



OCI のコンソールにある、Compute Instance の一覧から事前準備で作成したインスタンスを指定して、Create Custom Image を押します。

![1577348720272.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/104247/423c878b-74e7-364b-8c3e-ec9c161563b0.png)



Create Custom Image を実行します。約5分ほど作成時間が掛かります。

![1577348762610.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/104247/e651c6b1-e808-3793-38a5-954ca0237824.png)



これで、汎用化された日本語版の Custom Image が作成されます。Custom Image を使用して新たに 日本語版のWindows Instance を簡単に作ることが可能です。RDP でアクセスする時には、以下のユーザーとパスワードでログインを行います。パスワードは忘れずに変更をしておきましょう。

- opc ユーザー
- Custom Image 作成時に、opcユーザーの既存パスワード



# 参考URL

https://docs.oracle.com/cd/E97706_01/Content/Compute/References/windowsimages.htm
今年のQiita以外のアウトプットと感想

## Qiita以外のアウトプット（DMM inside)
- [心理的安全性を高めるワークショップを行いました](https://inside.dmm.com/entry/2019/06/20/review-psychological-safety)

- [チームで行っている心理的安全性の担保に役立つ取り組み](https://inside.dmm.com/entry/2019/08/14/review-psychological-safety-effective-efforts
)

## 今年の感想と来年の抱負
アウトプットをちゃんと出来てる人はすごいなぁと尊敬する。

アカウント作ってから全然書けてなかったQiitaも今年から書こうと思っていたけどあんまり書けなかった。

色々な物に手を出していると今年のはじめに触った言語とか仕組みとか年末の忘年会終わった後にはすっかり忘れてました。

ちゃんとアウトプットしてない事で振り返りもしにくいというのもあるので、来年は今年よりは多くアウトプット出来るようにしたい。
.zshrcを自分で書いてみた

`zsh`の設定は`oh-my-zsh`をインストールしてよしなにやってもらってもらってたんですが、プロンプトの見た目をいい感じにするためにしか使用してないと思ったので一度アンインスールして自分で設定することにしました。
# やりたいこと
`oh-my-zsh`の`eastwood`というテーマを使用していたので、こちらと同じようになるように`.zshrc`を書きました。
https://github.com/ohmyzsh/ohmyzsh/wiki/Themes#eastwood

# 最終的な`.zshrc`
```.zshrc
export PATH="$HOME/.rbenv/bin:$PATH"
if which rbenv > /dev/null; then eval "$(rbenv init -)"; fi

# 環境変数
export LANG=ja_JP.UTF-8
export KCODE=u           # KCODEにUTF-8を設定

## 色を使用出来るようにする
autoload -Uz colors
colors

## 補完機能を有効にする
autoload -Uz compinit
compinit

## タブ補完時に大文字小文字を区別しない
zstyle ':completion:*' matcher-list 'm:{a-z}={A-Z}'

## 日本語ファイル名を表示可能にする
setopt print_eight_bit

#pecoでhistory検索
function peco-select-history() {
  BUFFER=$(\history -n -r 1 | peco --query "$LBUFFER")
  CURSOR=$#BUFFER
  zle clear-screen
}
zle -N peco-select-history
bindkey '^r' peco-select-history

# 履歴ファイルの保存先
export HISTFILE=${HOME}/.zsh_history
# メモリに保存される履歴の件数
export HISTSIZE=1000
# 履歴ファイルに保存される履歴の件数
export SAVEHIST=100000
# 重複を記録しない
setopt hist_ignore_dups

setopt prompt_subst #表示毎にPROMPTで設定されている文字列を評価する

## PROMPT
# vcs_infoロード
autoload -Uz vcs_info

# PROMPT変数内で変数参照する
setopt prompt_subst

# vcsの表示
zstyle ':vcs_info:*' enable git svn hg bzr
zstyle ':vcs_info:*' check-for-changes true
zstyle ':vcs_info:*' stagedstr "+"
zstyle ':vcs_info:*' unstagedstr "*"
zstyle ':vcs_info:*' formats '[%b%c%u]'
zstyle ':vcs_info:*' actionformats '(%b(%a)%c%u)'

# プロンプト表示直前にvcs_info呼び出し
precmd () {
    psvar=()
    LANG=en_US.UTF-8 vcs_info
    [[ -n "$vcs_info_msg_0_" ]] && psvar[1]="$vcs_info_msg_0_"
}

#add-zsh-hook precmd _update_vcs_info_msg
PROMPT="%F{cyan}%1v%f%F{green}[%~]%f%1 %B$%b "

# RVM settings
if [[ -s ~/.rvm/scripts/rvm ]] ; then
  RPS1="%{$fg[yellow]%}rvm:%{$reset_color%}%{$fg[red]%}\$(~/.rvm/bin/rvm-prompt)%{$reset_color%} $EPS1"
else
  if which rbenv &> /dev/null; then
    RPS1="%{$fg[yellow]%}rbenv:%{$reset_color%}%{$fg[red]%}\$(rbenv version | sed -e 's/ (set.*$//')%{$reset_color%} $EPS1"
  fi
fi
```

# こんな感じになりました
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/115271/da566f81-0a3c-6ea1-2873-f651040ea41c.png)


# 参考にしたもの
https://qiita.com/knao124/items/04e3625eb12237de5743
https://github.com/ohmyzsh/ohmyzsh/blob/master/themes/eastwood.zsh-theme
🖼【CSS】filterのみを使用して黒い画像を任意の色に変更する


## やりたいこと

黒のみで書かれている下記png透過画像をcssのみを利用して色変更させたい
![test.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/188242/6258e034-dd3a-6b48-76e5-09410c677c87.png)

## やったこと

filterでがんばってもらう

```color.html
<hr>

<div>
    <img src="/img/test.png"/>元画像
</div>

<hr>

<div class="red">
    <img src="/img/test.png"/>赤
</div>

<hr>

<div class="green">
    <img src="/img/test.png"/>緑
</div>

<hr>

<div class="blue">
    <img src="/img/test.png"/>青
</div>

<hr>
```

```color.css
.red {
    filter: invert(15%) sepia(95%) saturate(6932%) hue-rotate(358deg) brightness(95%) contrast(112%);
}

.green {
    filter: invert(17%) sepia(91%) saturate(7085%) hue-rotate(128deg) brightness(100%) contrast(106%);
}

.blue {
    filter: invert(8%) sepia(99%) saturate(7044%) hue-rotate(247deg) brightness(100%) contrast(145%);
}
```

### その他の色達

```other.css
白
.white {
    filter: invert(88%) sepia(61%) saturate(0%) hue-rotate(229deg) brightness(107%) contrast(101%);
}

灰色
.grey {
    filter: invert(50%) sepia(0%) saturate(11%) hue-rotate(143deg) brightness(101%) contrast(93%);
}

黄色
.yellow {
    filter: invert(81%) sepia(81%) saturate(633%) hue-rotate(359deg) brightness(106%) contrast(105%);
}

オレンジ
.orange {
    filter: invert(72%) sepia(26%) saturate(6428%) hue-rotate(1deg) brightness(105%) contrast(102%);
}

水色
.aqua {
    filter: invert(88%) sepia(100%) saturate(2929%) hue-rotate(104deg) brightness(99%) contrast(104%);
}

紫
.purple {
    filter: invert(11%) sepia(71%) saturate(5170%) hue-rotate(293deg) brightness(87%) contrast(111%);
}
```

## 結果

このCSSだけで別の色の画像データを用意しなくても色々変えられます

![css.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/188242/7726043b-c1dd-342d-4244-041753ec0f1a.png)

また、filterは縦並びにすると効かなくなるので注意です

あとdivのalign="center"は非推奨なので消しました
ImageJとRを融合したソフト「Bio7」


この記事ではBio7というソフトを紹介します。
あまり日本語資料がないですが、Bio7はRとImageJの二つを併せた機能を持つソフトです。

公式ホームページ：https://bio7.org/
公式youtubeチャンネル：https://m.youtube.com/channel/UCFY-w-tMbVzhrLro4Q2KbFg/



ちなみにImageJもRもオープンソースのため、他にも様々なディストリビューションがあります。
ImageJのディストリビューションでは「Fiji」が有名で、よく使われています。
Rのディストリビューションでは「easyR」があり、ノンプログラマー向けのツールです。(GUIで簡単に使えるようにしたRで、自治医科大学のホームページで公開されています。http://www.jichi.ac.jp/saitama-sct/SaitamaHP.files/statmed.html)



##Bio7の機能
ソフトには画像や表を処理する部分と、コンソールからRのコマンドを実行する部分が実装されています。

plotのGUI機能やR解析のGUI機能もあり、簡単に可視化や解析が出来ます。

Rのパッケージもインストール出来て、パッケージ管理が簡単に行えるようになっています。

また、RのほかにもPythonやShellのも使うことができるようになっています。

JavaFXを用いてGUIを作ることも出来て、簡単に独自の解析GUIソフトを作ることができます。

まだ機能を完全に把握していませんが、使いこなせばかなりいい解析ツールになるのでないでしょうか。

特に、ImageJで処理した画像をそのままRで解析できるため、画像解析では特に役に立ちそうです。

新しい機能がわかったらまた更新します。
PHPでバッチの二重起動防止処理を実装する

# バッチの二重起動防止処理
バッチをcronで定期的に実行する場合、二重防止処理を入れていないと何らかの理由でバッチの起動時間が延びた場合に、バッチプロセスが複数溜まり続けてしまう。

# 実装方針

* **pidファイル**を作成し、ファイルには**プロセスID**を記録するようにする。
* 異常終了したときや、**Ctrl+C**で終了したときはpidファイルが残り続けないようにする。

# 実装内容

PIDを取得するためにphp-processが必要。

```sh
yum install php-process
```

```php
class なんたらバッチ {
	const PID_PATH = '/var/run/hogehoge/hogebatch.pid';

	public function __construct() {
		// 既に同一タスクが起動中の場合
		if (file_exists(static::PID_PATH)) {
			exit(1);
		}
		file_put_contents(static::PID_PATH, posix_getpid());

		// Ctrl+C等で中断されたときにメッセージを表示し、pidファイルが削除されるようにする
		pcntl_async_signals(true);
		pcntl_signal(SIGINT, function() {
			exit;
		});
	}

	public function __destruct() {
		unlink(static::PID_PATH);
	}
}
```

# FuelPHPのTaskクラスでの実装例

```php
<?php

/**
 * タスクの基底クラス
 */
abstract class Task {

	/**
	 * @var boolean タスクを実行しているか
	 */
	protected $running = false;

	/**
	 * タスクの事前処理を行う。
	 */
	public function __construct() {
		// 既に同一タスクが起動中の場合
		if ($this->is_running()) {
			// ログとコンソールに出力し、終了する
			$message = get_class($this) . ' already running';
			\Log::warning($message);
			\Cli::error($message);
			exit(1);
		}

		// 実行状態にして開始ログを出す
		$this->running = true;
		$this->log_start_message();
		$this->set_running();

		// Ctrl+C等で中断されたときにメッセージを表示し、pidファイルが削除されるようにする
		pcntl_async_signals(true);
		pcntl_signal(SIGINT, function() {
			\Log::warning(get_class($this) . ' halted');
			exit;
		});
	}

	/**
	 * タスクの事後処理を行う。
	 */
	public function __destruct() {
		// 終了ログを出す
		$this->log_finish_message();
		// 実行を行っていた場合はpidファイルを削除
		if ($this->running) {
			$this->set_running(false);
		}
	}

	/**
	 * タスクが既に起動中かどうかを返す。
	 *
	 * @return boolean タスクが起動中か
	 */
	protected function is_running() {
		$filename = $this->get_pid_filename();
		// PIDファイル名を設定していない場合はチェックをしない
		if ($filename === null) {
			return false;
		}
		// PIDファイルがあるかチェック
		return file_exists(\Config::get('run_dir') . "$filename.pid");
	}

	/**
	 * PIDファイルを生成もしくは削除してタスクの起動状態を切り替える。
	 *
	 * @param boolean $running 起動中にするか
	 */
	protected function set_running($running = true) {
		$filename = $this->get_pid_filename();
		// PIDファイル名を設定していない場合は何もしない
		if ($filename === null) {
			return;
		}

		$pid = \Config::get('run_dir') . "$filename.pid";
		// 起動中にする場合はPIDファイルを生成
		if ($running) {
			file_put_contents($pid, posix_getpid());
		// 終了にする場合はPIDファイルを削除
		} elseif (file_exists($pid)) {
			unlink($pid);
		}
	}

	/**
	 * 開始メッセージをログに出力する。
	 */
	protected function log_start_message() {
		\Log::warning(get_class($this) . ' task start');
	}

	/**
	 * 終了メッセージをログに出力する。
	 */
	protected function log_finish_message() {
		$time = number_format(microtime(true) - FUEL_START_TIME, 4);
		\Log::warning(get_class($this) . " task finish [execution time: $time sec.]");
	}

	/**
	 * このタスクのPIDファイル名を返す。
	 *
	 * @return string PIDファイル名 (拡張子部分は除く)
	 */
	protected function get_pid_filename() {
		return preg_replace('/^.*\\\\/u', '', strtolower(get_class($this)));
	}
}
```

こんなクラスを用意しておけば、Task作成時にこのクラスを継承するだけで二重起動防止処理が実装され、
バッチ単位で別々のpidファイルを自動的に生成してくれる。
ネームエラーの解消

現在、メルカリのダミーサイトを作成してます。
その中で、商品の紹介窓を作成で下記hamlを組んだら、下記エラーが出ました。
<img width="922" alt="スクリーンショット 2019-12-27 15.40.01.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/557936/9d4c8174-40b5-66d7-99f5-577b316301ec.png">

<img width="780" alt="スクリーンショット 2019-12-27 15.37.16.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/557936/f7a4b596-e612-53a3-cf72-1453020a9282.png">

model
<img width="448" alt="スクリーンショット 2019-12-27 15.43.27.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/557936/16dd726b-832e-cfd5-58fe-42742dfd657e.png">

route
<img width="448" alt="スクリーンショット 2019-12-27 15.42.35.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/557936/226bf52c-2f1a-1fac-2988-9550b4dba829.png">


controller
<img width="448" alt="スクリーンショット 2019-12-27 15.41.55.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/557936/6b5793ff-992d-a95b-b46f-2d3e580020e7.png">

該当する所に関しては、一通り情報は入れているつもりですが
多分、brandの名前間違いが原因だと考えてます。

解決方法を御教示ください
DatadogをKubernetesに導入して気づいたNamespace名やPod名を付けるときの注意点

Kubernetesを監視するためにDatadogを入れてダッシュボードを作成したときに、Namespace名とPod名をこうやっておけばよかったと反省したのでそのことを記録しておきます。

## TL;DR

結論から言うと、

**Namespace名やPod名に環境名(devとかstgとか）を入れるのはやめよう。環境ごとにクラスタを作ろう。**

ということです。

## 君の名は

namespace名やpod名はどう命名しているでしょうか。
私の関わったプロジェクトでは下記のような感じでやっていました。

- Namespace名

`hoge-dev`
`hoge-stg`
`hoge-prd`

- Pod名（厳密にはDeployment名）

`fuga-dev`
`fuga-stg`
`fuga-prd`

名前に環境名を入れてました。
ちなみにクラスタは環境ごとに分かれていました。

## 何が問題か

Datadogのダッシュボードには `Configure template variables (テンプレート変数設定)` というものがあります。
変数と、変数に入れる値を抽出する項目を指定すると、グラフなどを作成するクエリに変数を埋め込めるというものです。
これによって動的フィルタリングが可能になります。詳しくは下記URLを参照してください。

https://docs.datadoghq.com/ja/graphing/dashboards/template_variables/

このテンプレート変数を利用すると何が便利かというと、 **1つのダッシュボードで複数環境の状態を切り替えられる** ようになります。
上記ドキュメントにも載ってますが、 `env` という変数を指定しておいて `dev/stg/prd` を切り替えて、１つのダッシュボードで、全ての環境のメトリクスを切り替えて見ることが可能です。

**ですが、**Namespace名やPod名に環境名が入っているとどうなるでしょうか。
例として、hogeアプリケーションが配置されているNamespaceで動いているPod数をカウントしてみましょう。

```
sum:kubernetes.pods.running{kube_namespace:hoge-prd}
```

こんなクエリになると思います。
このPod数、今回はprdですが、dev環境とstg環境のも見たいとします。

```
sum:kubernetes.pods.running{kube_namespace:hoge-dev}
```

```
sum:kubernetes.pods.running{kube_namespace:hoge-stg}
```

こんな感じで１つのダッシュボードに各環境用のものが必要になります。
もしくは各環境用のダッシュボードを作成する必要があります。
これは結構手間です。

## 解決策？

では、テンプレート変数にNamespace名を登録するとどうでしょうか。
一応Namespaceを切り替えることが可能になります。

```
sum:kubernetes.pods.running{$kube_namespace}
```

ですが、思い出してください。
Namespaceには `default` `kube-system` などが存在します。
hogeアプリケーションのNamespaceに配置されてるPod数をカウントしたいですが、余計なものが混じります。

## 解決策

Namespaceとして `hoge` のみを登録します。
名前から環境名を抜くので、クラスタは環境ごとに用意してください。

Datadogのタグ機能を利用して、クラスタごとに環境が分かるタグを埋め込んでください。

```development/datadog.yaml
datadog:
:
  tags: env:dev
:
```

そしてそのタグ情報を `env` などのテンプレート変数に割り当ててください。

そうすると、クエリは下記のようになります。

```
sum:kubernetes.pods.running{$env,kube_namespace:hoge}
```

これで、 `env` を切り替えるだけで各環境のhogeアプリケーションNamespaceのPods数をカウントできるようになります。

## まとめ

Namespace名やPod名に環境名を埋め込んでしまうと、Datadogでダッシュボードを作るときに面倒な感じになります。
例としてNamespaceを挙げましたが、Pod名に環境名が入っていると、さらに様々なところで面倒なことになります。

なので最初で述べたように、

**Namespace名やPod名に環境名(devとかstgとか）を入れるのはやめよう。環境ごとにクラスタを作ろう。**

というのが重要だと思います。
Ubuntu18.04(wsl1,wsl2)でOpenModelicaをビルドする

# 概要

OpenModelicaをソースからビルドしたときの備忘録です。(2019/12月時点)
Ubutnu-18.04の場合の例であり、Windows10+wslでも同じ方法でビルドできます。

## 前提パッケージ

OpenModelicaのgithubで列挙されている前提要件を、
Ubuntu-18.04で配布されているパッケージ名で紹介します。

```
sudo apt install \
    autoconf make cmake \
    clang-8 clang++-8 libstdc++-8-dev libboost-all-dev \
    gfortran \
    default-jre \
    gettext libncurses5-dev libreadline-dev libexpat-dev libopenblas-dev liblpsolve55-dev libsundials-dev \
    qt5-default qttools5-dev-tools \
    libqt5webkit5-dev libqt5svg5-dev libqt5xmlpatterns5-dev
```

- ビルドツール
- C/C++ コンパイラ
- Fortran コンパイラ
- java 実行環境
- ライブラリ群(数値計算ソルバほか)
- qt5 (GUIフレームワーク)

# githubよりソースを取得

最新のリリースが欲しいだけなら素直にパッケージマネージャでとればいいので、過去のリリース版v1.13.2のソースを取得します。

## `git clone` でリポジトリを取得

git clone するだけですが、２点注意点があります。

OpenModelicaの構成要素のうちいくつかは、git submoduleで管理されていますので、
--recursive オプションをつけて、再帰的にcloneする必要があります。

また、あるタイミングのアップデートで、もともとOpenModelica本体に含まれていたコードがsubmoduleに移動したり、逆にsubmoduleが本体に移動したりしているようで、cloneしてから過去のリリースにcheckoutすると、submoduleの参照を貼り直したりしないといけなくなったりします。

ですので、以下のようにタグを直接指定してcloneすることをお勧めします。

```
git clone -b v1.13.2 --recursive \
  https://github.com/OpenModelica/OpenModelica.git OpenModelica-v1.13.2
```

# ビルド

autoconfしてmakeするだけです。

```
autoconf
./configure CC=clang-8 CXX=clang++-8 --with-cppruntime
make -j4 omc omplot omshell omedit
make install
```

## インストール先の変更 (複数バージョンを入れたい場合)

上の設定だと、`make install`したときのインストール先がデフォルトとなるので、二回目以降ビルドしたときに上書きされてしまいます。 それを避けるために、configureの段階でインストール先を変更しておきます。

```diff
- ./configure CC=clang-8 CXX=clang++-8 --with-cppruntime
+ ./configure CC=clang-8 CXX=clang++-8 --with-cppruntime --prefix=/opt/OpenModelica/v1.13.2
```

こうすると、`/opt/OpenModelica/v1.13.2`にアプリケーションやライブラリをインストールするようになります。

OpenModelicaの各アプリケーションは、`/usr/bin/` にインストールされることを期待して、`/usr/lib/omlibrary`のModelica Standard Libraryを読みに行きます。
上の手順でインストールすると、ビルドされたアプリケーションは`/opt/OpenModelica/v1.13.2/bin/../lib/omlibrary`つまり`/opt/OpenModelica/v1.13.2/lib/omlibrary`を読みにいき、ここにはModelica Standard Libraryが存在しないため、うまく動きません。この問題は、当該ディレクトリに`/usr/lib/omlibrary`へのシンボリックリンクを貼ることで解決できます。

```
ln -s /usr/lib/omlibrary /opt/OpenModelica/v1.13.2/lib/omlibrary
```

## `omc -g=MetaModelica` のテストが失敗してビルドできない時 (対応については要検討)

omc (OpenModelicaによるModelicaコンパイラ)のビルド時に、テスト用のコードやスクリプトを実行して、omcのテストをするステップがあります。
このテストに失敗をして`make omc`が通らなくなるケースがしばしばありました。何度か試していたところ、テスト用のスクリプトが起動するomcと、今ビルドしているomcが一致していないことが原因とわかりました。

たとえば、ここまでの説明の設定では、ビルドされたomcのパスは、`path/to/OpenModelica-v1.13.2/build/bin/omc`なのですが、失敗したテストでは`/usr/bin/omc`を起動していることがわかりました。(このページで解説した複数バージョンインストール以外に、最新版をパッケージマネージャから入れて運用していた状況。)

テストに使うomcの場所を、configureなどで指定できるのではないかと、試行錯誤しているのですが、現時点(2020/07/15)では実を結んでおらず、`apt remove openmodelica`で一時的にパッケージマネージャから入れたopenmodelicaを消し、(もちろん`/usr/bin/omc`も消える)この状態でなら`make omc`が通ることまでは確認しています。
[小ネタ]削除を確認するには、フィールドに [Delete] と入力してください。

## 追記(2020/01/09)
さっき見たら修正されてました。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/214614/1d3e24ee-c8b7-613b-2c02-e87404767658.png)



## コンソールから起動テンプレートを消そう

**削除を確認するには、フィールドに [Delete] と入力してください。**
ふむふむ…Delete…と。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/214614/61742f98-d2d5-494c-d0ae-a0b55ccd4a4d.png)
**消せない！！！**

ん？プレースホルダーには"削除"って書いてあるな…
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/214614/68f85740-c776-5a31-6159-74ca5113dc09.png)


![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/214614/5f0f60f3-5662-1912-955c-4030d8968803.png)
**消せる！！！**

## 他の言語のとき
### フランス語
**Delete(Supprimer)** とあるのでフランス人もちょっと間違えそう
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/214614/f9a5b751-0748-80b8-3599-43709949b354.png)

### 中国語
**Delete** の表記はなし
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/214614/09b61239-ef4e-9b01-f4f6-83a8a1d6ae12.png)

### 韓国語
こちらも **Delete** の表記はなし
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/214614/6f64616d-66d6-caef-a076-c27370c15cdc.png)

## 結論
**CLIを使おうね！！**
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/214614/a671e162-f5f6-fe63-e619-754c0ea68e3a.png)
Laravel 検索フォームとページネーション連携

一覧ページ(index.blade.php)に実装することを想定
ここでは標準で用意されているuserテーブルの検索を実装する

1. viewファイル(blade)にフォームを追加する
2. controller(UserController.php)に検索処理とページネーション処理を実装する

## Viewファイルの修正
検索条件を保持するためinputのvalueに`$name`を追加

```html:index.blade.php
...(略)...
      <form action="{{ url('users/') }}" method="get">
        @method('GET')
        @csrf
        <div class="form-group row">
          <label for="searchName" class="col-sm-2 col-form-label">{{ __('Name') }}</label>
          <div class="col-sm-10">
            <input type="text" class="form-control @if (!empty($errors->first('name'))) is-invalid @endif" id="name" name="name" value="{{ old('name', $name ?? '') }}" placeholder="{{ __('Name') }}">
            @error('name')
              <span class="invalid-feedback" role="alert"><strong>{{ $errors->first('name') }}</strong></span>
            @enderror
          </div>
        </div>
        <div class="form-group row">
          <div class="offset-sm-2 col-sm-10">
            <button type="submit" class="btn btn-primary"><i class="fas fa-search mr-1"></i>{{ __('Search') }}</button>
          </div>
        </div>
      </form>
...(略)...
```
これでアクション`users.index`のGETメソッドがリクエストパラメータ付きで呼ばれる

## コントロール修正
`index()`の引数に`Request`を追加する。
`$query->paginate(10)`でページネーション付きのユーザー一覧情報になる。
retunでviewに検索条件も渡す。

```php:UserController.php
public function index(Request $request)
{
    $name = $request->input('name');
    $query = User::query();
    if (!empty($name)) {
         $query->where('name', 'like', '%' . $name . '%');
    }
    $users = $query->paginate(10);
    return view('users.index', compact('users', 'name'));
}
```

## ページネーション連携
通常は`$users->links()`だが、メソッド`appends(['name' => $name ?? ''])`を追記する

```html:index.blade.php
...(略)...
  {{ $users->appends(['name' => $name ?? '' ])->links() }}
...(略)...
```
Bluetooth IchigoJam

IchigoJamにBluetoothモジュールのHC-05を接続してみました。

![写真（2019-12-27 14.18）.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/104066/387fcdd0-bf10-23dd-0b10-b8e6d763eeac.jpeg)

くどいですが、IchigoJamのユニバーサル基板は今は廃番になってしまったサンハヤトのICB-89です。わかる人にはわかるとおもいますが、

接続は以下のようにしました。

![HC-05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/104066/99e10e96-57c1-9741-9ed9-5c5e572e9524.png)

HC-05はデフォルト9600なのですが、IchigoJamは115200なのでHC-05の設定をATコマンドで変える必要があります。

HC-05はKEY(34ピン)をボタンスイッチでプルアップするとATコマンドモードになります。電源投入後に押したときは9600(デフォルト)で、押しながら電源を入れたときは38400になるようです。

HC-05をFTDIの3.3V系USBシリアルに接続して、[Macのターミナルソフト](https://qiita.com/yamori813/items/29e6bcd2f090983abb9a)jermで試したのですがATコマンドを入力するとOKやERROR:(0)が連続して出力され設定できません。

いろいろ試したところHC-05は改行がCRだと暴走してしまい、CR+LFにしなければいけませんでした。

jermでは以下のように起動すると設定できました。

```
$ ./jerm -r rntn -b 38400  /dev/cu.usbserial
```

これで

```
AT+UART=115200,0,0
```

を設定すると115200になります。この設定は電源を切っても残るようです。

たしかMacと接続するのであればMac側でIOBluetoothRFCOMMChannelで制御可能だったと思うのですが、プログラムを書くのも面倒なので、設定してしまったほうが良いです。

HC-05は他にも使っているので、名前も設定してみました。

```
AT+NAME=IchigoJam
```

設定が終わったらHC-05をIchigoJamにつないでペアリングして、接続してみます。

```
$ ./jerm  -b 115200 /dev/cu.IchigoJam-DevB 
Jerminal v0.8096  Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005, 2007 candy
Type "Ctrl-M ~ ." to exit.
 ispeed 115200 ospeed 115200
 +IGNBRK -BRKINT -IGNPAR -PARMRK -INPCK -ISTRIP -INLCR -IGNCR -ICRNL -IXON -IXOFF -IXANY -IMAXBEL
 -OPOST -ONLCR -OXTABS -ONOEOT
 cs8 -CSTOPB +CREAD -PARENB -PARODD +HUPCL +CLOCAL -CCTS_OFLOW -CRTSCTS -CRTS_IFLOW -MDMBUF -ECHOKE -ECHOE -ECHO -ECHONL -ECHOPRT -ECHOCTL -ISIG -ICANON -ALTWERASE -IEXTEN
 -EXTPROC -TOSTOP -FLUSHO -NOKERNINFO -PENDIN -NOFLSH
IchigoJam BASIC 1.3.1 by jig.jp
                               OK
```

設定変えずにBASICで

```
BPS 9600
```

として9600で通信する方法もあります。

IchigoJamのOUTピンでKEYをコントロールしてATコマンドモードに入れるようにすれば、HC-05のGPIOをいじることができて楽しいかもしれません。

このHC-05はRXのエッジのパターンをはがしてしまい、無理やり引きづり出しました。このモジュールはエッジのパターンが弱いので、力がかからないようにしたほうが良いです。
初めての独学Python②

Python学習の備忘録です。
初めての方でもこの記事で学習ができるよう
編集していきます。

#関数
関数とは入力値を受け取り、関数内部に記述された命令を実行し、出力値を返すというものです。
プログラムを関数で記述すれば何度も同じプログラムを再利用することができます。

記述のイメージはこんな感じです。
>def [関数名] \([引数]) :
　　[関数定義]

数学の関数f(x) = x * 2をPythonを記述すると

```python:
def f(x):
    return x * 2
```
のようになります。

実際にこの関数を使うと

```python:
def f(x):
    return x * 2

result = f(2)
print(result)
```
\>>4
となります。

関数に複数の引数を渡すことも可能です。
その場合は「,」で引数を区切ります。

```python:
def f(x, y, z):
    return x + y + z

result = f(2, 3, 4)
print(result)
```
\>>9

#組み込み関数
自分で関数を作らなくても最初から用意されている関数があります。それを組み込み関数と呼びます。前に書いたプログラムのprintも組み込み関数です。組み込み関数をいくつか紹介します。

-len
文字列の長さを返してくれます。

```python:len.py
len("yakiniku")
```
\>>9

-str
オブジェクトを引数で受け取り、strデータ型の新しいオブジェクトを返します。

```python:str.py
len(999)
```
\>>'999'

-int
オブジェクトを引数で受け取り、整数オブジェクトを返します。

```python:int.py
int(1.23)
```
\>>1

-float
オブジェクトを引数で受け取り、浮動小数点オブジェクトを返します。

```python:float.py
float(100)
```
\>>100.0

-input
プログラムを動作させている人から情報を集めることができます。

```python:input.py
print("What is your age?")
age = input("Enter your age:")
int_age = int(age)
if int_age < 21:
    print("You are young!")
else:
    print("Wow, you are old")
```
\>>What is your age?
\>>Enter your age:26
\>>Wow, you are old

#オプション引数と必須引数
今まで紹介してきた関数の引数は省略できませんでした。これを必須引数といいます。これの反対で、生薬できる関数もあります。それをオプション引数といいます。引数を省略した場合あらかじめ設定しておいたデフォルト値が使用されます。

```python:
def f(x = 2):
    return x ** x

print(f())
print(f(3))
```
\>>4
\>>27
git pushしたときにリモートリポジトリが読み込めなくなった時の対処法

##背景

laravelでwebアプリをチーム開発しているときにgitを頻繁に使っているのですが、
いつも通りブランチを作って編集作業、そしてリモートリポジトリにプッシュし、
コミットしようとするが、なぜか以下のようなエラーが出てしまい、
pushできなくなってしまいました。



```
$git push -u origin hogehoge
fatal: 'branch-name' does not appear to be a git repository
fatal: Could not read from remote repository.

Please make sure you have the correct access rights
and the repository exists.
```


##解決方法

何やらわたしに正しいアクセス権限とリモートリポジトリの所在を教えてとの
ことだったので調べてみると、以下のコマンドで
リポジトリの在りかを教えることができ、無事git push&commitすることができました。



```
$git remote set-url origin https://hogehoge@bitbucket.org/to/hoge.git
```

URLの部分を使用しているリモートリポジトリにしてもらえれば
実行できるかと思います。