OmniAICreator/Qiita-1.07M huggingface dataset:
Tiled Map Editorでのポリラインの分割方法

オブジェクトの配置ツールとして、
TiledMapEditor を使用できるか検証中
若干はまったので備忘録がてらメモ。

# TiledMapEditor について
導入にあたり、こちらにかかれていたものを参考にさせていただきました。
https://qiita.com/muzudho1/items/ac3602a29f8536031fe4

# ポリラインについて

Objectですので、レイヤーにObjectレイヤーを追加して配置を行います。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/252918/6ab35901-2f88-50b7-d1ee-6a63dc0eb853.png)

作成したObjectレイヤーにポリラインを配置していきます。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/252918/215c4412-9233-55fb-30d1-b7144da0bd22.png)

配置後に、ポリゴン編集を選択すると配置後の位置情報を変更できます。
![image.png](https://qiita-image-store.s3.amazonaws.com/0/252918/e765b005-8709-b67c-2d09-cd04548b5b21.png)

この時
左クリックで各位置情報を選択、マウス操作で位置の変更が行えます。
右クリックで、メニューが表示されますが、
１ノードを削除　のみがアクティブになっており、
その他の項目、ノードの結合、分割　が選択できません。
これに難儀しました。が、

Ctrl 左クリックで隣合う複数ノードを指定後に、右クリックで項目が活性化して
分割、結合が行えました。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/252918/d15c5175-7f12-7628-8ced-cce70e7ae5b1.png)

指定された２点間でその中心に分割されたノードを増やせるのと、
２点間の中心に結合されたノードが出来上がります。

考えてみればあたりまえの仕様ですが、当初わからなかったのでメモしてみます。
一目瞭然にする

<p>タイミング情報を取得していて、受信機が妨害電波の範囲内にある場合は、電波妨害信号からタイミング情報を取得します。GPS妨害操作を実行しようとしているという事実は、これらの新たな電子戦術の脅威がどの程度大きな脅威になっている。<strong><a href="http://www.buykamera.com/smart-phone-jammer/c-1_2.html">携帯電話ジャマー</a></strong>は要な&quot;強制的な措置を取るために教室に権利を持っている</p>
<p>教育省の携帯電話妨害機の性能をテストした。この装置は、箱のように、イタリアの軍事および防衛産業の専門家によって開発された。<strong><a href="http://www.buykamera.com/gps-type-jammer/c-1_3.html">gps 妨害</a></strong>が唯一の方法かもしれません。学生が実際に携帯電話を使用するのを防ぐことは非常に難しいと言わざるを得ない。</p>
<p>ユーザーは教育目的と緊急のニーズを持っているかもしれませんが、原則として電話は限られています。携帯電話のジャマー。携帯電話の信号が完全に消えていること、電話をかけようとしていること、携帯電話の信号が完全に消えている.詳細な検査に信号<strong><a href="http://www.buykamera.com/wifi-radio-jammer/c-1_4.html">wifi ジャマー</a></strong>線を検査装置の監視の都市で6つのテストサイトを持っています。</p>
<p>セキュリティに再び教室のスタッフの観察を一目瞭然にすることができる.新しい建物の教室には、携帯電話の信号ジャマーが装備されています。これは、生徒が携帯電話を授業でプレイするのを防ぐ良い方法です。携帯電話の信号遮蔽装置は、<strong><a href="http://www.buykamera.com/the-camera-detector/c-15.html">盗撮発見器</a></strong>は標準化された検査室の要件に沿ってインストールされている</p>
Androidのリソース名/IDを一覧する

そんなAPIはないから自分で頑張るんだよォ！
（ネタ記事です）

# コード

## stringリソースの一覧を得る

```kotlin:kotlin
val fields = R.string::class.java.fields
```

## リソースIDを得る

```kotlin:kotlin
val ids = R.string::class.java.fields
                .map { 
                    it.getInt(null)
                }
```

### もっと安全に

```kotlin:kotlin
val ids = R.string::class.java.fields
                .filter {
                    Modifier.isStatic(it.modifiers)
                }
                .map { 
                    it.getInt(null)
                }
```

### 最大限安全に

```kotlin:kotlin
val ids = R.string::class.java.fields
                .filter {
                    Modifier.isPublic(it.modifiers)
                            && Modifier.isStatic(it.modifiers)
                            && Modifier.isFinal(it.modifiers)
                }
                .filter {
                    it.type == java.lang.Integer.TYPE 
                }
                .map {
                    it.getInt(null)
                }
```

## リソースIDからリソース名を得る

```kotlin:kotin
val names = R.string::class.java.fields
                .filter {
                    Modifier.isPublic(it.modifiers)
                            && Modifier.isStatic(it.modifiers)
                            && Modifier.isFinal(it.modifiers)
                }
                .filter {
                    it.type == java.lang.Integer.TYPE
                }
                .map {
                    it.getInt(null)
                }
                .map { 
                    resources.getResourceEntryName(it)
                }
```

## stringだけと言わずRの中全部欲しい

```kotlin:kotlin
val ids = R::class.java.classes
                .filter {
                    // styleableだけリソースIDじゃないので闇が深くて除外
                    it != R.styleable::class.java
                }
                .flatMap {
                    it.fields.asIterable()
                }
                .filter {
                    Modifier.isPublic(it.modifiers)
                            && Modifier.isStatic(it.modifiers)
                            && Modifier.isFinal(it.modifiers)
                }
                .filter {
                    it.type == java.lang.Integer.TYPE
                }
                .map {
                    it.getInt(null)
                }
```

# 学び

全然関係ない学びがあった。

* Class&lt;int>が存在している
* Class&lt;int>は`Integer.TYPE`で取得できる
  * 他のプリミティブ型も各々のラッパークラスにTYPEが定義されてる 
  * Class<int>をどう作ってるのか調べたら、配列型を使ってゴニョゴニョしてて笑った
* `Integer.class` != `Integer.TYPE` (Class&lt;int>)
GoogleAppsScriptで２４時間を超える経過時間の取得に困った時の対処法

# GASで標準時間を超える経過時間の取得や利用

SpreadSheetで勤怠管理などをしていたら月の労働時間が24時間を超えることはざらにありますよね。
でもそれを取得して色々触りたい場合、なかなかうまくいきませんでした。
例えばA1セルに　35:00:00 のように色々と足し合わされて35時間と表示されていたとします。
これを普通に取得しようとすると

```javascript:time.gas
var ss = SpreadsheetApp.getActiveSpreadsheet();
var sheet = ss.getSheetByName('労働時間');
var time = sheet.getRange('A1').getValue();
Logger.log(time);
```
```
[18-05-25 00:48:07:869 PDT] Sun Dec 31 11:00:00 GMT+09:00 1899
```
こんな風に表示されて、24で割ったあまりしか出てきません。

GASは1899年12月30日0時0分0秒が基準時刻となっているようなので、これを引きミリ秒計算します。

```javascript:time.gas
var baseTime = new Date("Sun Dec 30 00:00:00 GMT+09:00 1899");
Logger.log((tim-baseTime)/1000/60/60);//ミリ秒を時間に換算
```

```
[18-05-25 00:48:07:869 PDT] 35.0
```

時を操るのは難しいなぁ
【Git】SourceTreeで階層構造のブランチ作成がエラーになる対処法

##はじめに
Gitを視覚的に利用できるSourceTree。私も便利に利用させていただいているのですが、ちょっと躓いた箇所があったので対処法をメモしておきます。

##概要
ブランチを作成するにあたってブランチ名を入力する際、`hghg/fgfg`とスラッシュを入れることで、SourceTreeが自動でブランチを階層表示してくれるようになります。
この時`hghg`というブランチを作成してから`hghg/fgfg`ブランチを作成しようとするとエラーになります。

>git -c diff.mnemonicprefix=false -c core.quotepath=false branch hghg/fgfg
>error: unable to create directory for .git/refs/heads/hghg/fgfg
>fatal: Failed to lock ref for update: No such file or directory

>エラー終了しました。エラーの内容は上記をご覧ください。

原因は、ブランチが管理されるフォルダ内で同名のファイル/フォルダ(このケースではhghg)を作成できないからでした。

対処法としては、`hghg`ブランチを`hghg/all`などに名前変更し、階層の中に入れることで解決します。

##原因の詳細
`hghg/fgfg`ブランチを作成しようとした場合、ブランチが管理されるフォルダ(.git\refs\heads)内では「hghg」というフォルダが作成され、その中で「fgfg」というファイルが生成されます。

しかし最初に`hghg`ブランチを作成すると、headsフォルダにファイル「hghg」が作成されるため、`hghg/fgfg`ブランチを作成するときに「一つのフォルダ内で同じ名前のファイルとフォルダは共存できない」ルールに引っかかってhghgフォルダが作成できなくなります。
hghgフォルダが作成されなかったのだから、「hghgフォルダにfgfgファイルを作成」という命令は通りませんよね。存在しない場所にモノを作ることはできません。

##事の発端
私はリポジトリを作成後、masterブランチはとりあえず置いておいて、developブランチを作成しました。
更にfeatureブランチを作ってそちらに移動し、いくつかのフォルダを用意したり、空のスクリプトを作成して開発の準備を進めました。
そしていざ個々の機能を作り始めようと「feature/camera」というブランチを作成しようとしたところ、このエラーに当たったのです。
普段からGitに使い慣れている方ならまず起こさないであろう初歩的なエラーでしたが、これからGitやプログラミングを勉強し始める方々がここで立ち止まったり挫折してしまうのは大きな機会損失になるなと思い、Qiitaにまとめることにした次第です。

##前提の知識
先述の通り、初心者を意識した記事としておりますので、この記事を読むために必要な情報をまとめておきます。
他に読んでいて分からないことがありましたらコメント等で質問していただけたら追記しようと思います。

###ファイルとフォルダの違い
ファイルとフォルダは似ている名前ですし、コンピュータに詳しくない方は混同されているケースもよく見られます。
写真や音楽のように、一つ一つにデータが格納されている状態のものをファイルと呼びます。各ファイルは（中身が空の場合を除いて）蓄えているデータ分の容量を持っています。
一方フォルダは、複数のファイルまたはフォルダを格納するための入れ物であり、これ自体は容量を持っていません。
「このフォルダは○○GBの容量があります」などと表示される場合は、そのフォルダの中に含まれるすべてのファイルの容量の合計を表しています。

###拡張子について
ファイルには「.exe」「.mp3」といった「拡張子」が付けられていることがほとんどですが、当記事で扱うブランチ情報を格納したファイルには拡張子はありません。拡張子がなくてもファイルとして存在は可能なのです。
拡張子はOSの設定によっては非表示になっている場合がありますが、表示するようにしておくと、例えアイコンが設定されていないファイルでも、その種類がひと目で分かるようになります。
また、非表示設定にしているユーザーをターゲットとしたウイルスファイル（「file.mp3.exe」などの名前で、拡張子を非表示にするとfile.mp3と表示される）なども存在するため、常に表示しておくに越したことはないでしょう。

###フォルダとディレクトリの違い
同じと考えて差し支えありません。
MacのターミナルやWindowsのコマンドプロンプトなでどコンピュータをコマンド操作する際には「mkdir(make directoryの略)」などの呼び方が使われるので、ディレクトリと言われたらフォルダのことだなと覚えるようにしておくと何かとスムーズです。

###.gitフォルダが見つからない
OSの設定で、隠しフォルダや隠しファイルが非表示になっているのでしょう。これも設定を変えれば表示されるようになります。
今回の原因が特定できたのは隠しフォルダである.gitフォルダが表示されており、中身を参照できたからですし、他にもブラウザのキャッシュデータを参照したり、ゲームのセーブデータをコピーしたりと便利に利用することが可能です。
ただし、隠しフォルダや隠しファイルなどは、ユーザーがうっかり変更、削除するとシステムトラブルになるデータを保護する目的で隠されている場合がほとんどですので、よく分からない隠しフォルダや隠しファイルを目障りだからと破棄するのはやめておきましょう。

##参考
ブランチの効果的な利用について、こちらの記事で丁寧に解説されておりましたので紹介させていただきます。
Gitの教本などで「こうやってブランチを分けられるんだよー」と言われても、具体的にどう活用すればいいのか分からない......そんな方にオススメです。
[Gitのブランチモデルについて](https://qiita.com/okuderap/items/0b57830d2f56d1d51692)
[Unity] uGUIでStretch設定の Recttransformのサイズを変更する

Stretch設定ではないRecttransformのサイズ変更はマニュアルに書いてあります
[RectTransform.sizeDelta](https://docs.unity3d.com/jp/current/ScriptReference/RectTransform-sizeDelta.html)

Stretch設定の場合はRectTransform.OffSetMax,RectTransform.OffSetMinを編集すればサイズが変えられるのですが、
left,top,right,bottomとの対応がよくわかりません。
![stretchedRectransform.jpg](https://qiita-image-store.s3.amazonaws.com/0/91234/6f152d9d-009e-c44f-1d42-339c1e2a70d2.jpeg)

そういうわけで分かるようにメソッドにしておきました。

```
    public static void SetStretchedRectOffset(RectTransform rectT, float left, float top, float right, float bottom) {
        rectT.offsetMin = new Vector2(left, bottom);
        rectT.offsetMax = new Vector2(-right, -top);
    }
```

[ [参照: answers.unity.com] "Setting top and bottom on a RectTransform"](https://forum.unity.com/threads/setting-top-and-bottom-on-a-recttransform.265415/)
リダイレクトについて（ターミナル）

# ターミナル常におけるリダイレクトについて

ターミナル上のコマンドをログファイルとして残すことができます。
`>`を使うと、ターミナル上に表示される文字列をファイルにして書き込むことができます。

AWS Cloud9のWorkspaceでの実行結果

```bash
$ ls > log.txt
```

<img width="806" alt="スクリーンショット 2018-05-25 16.28.39.png" src="https://qiita-image-store.s3.amazonaws.com/0/14191/0ec85f91-09f3-23d9-408f-4074040a974c.png">

画像を見ると、カレントディレクトリに`log.txt`という指定した名前でファイルが生成され、ログの実行結果が表示されていることがわかります。ちなみに、ターミナル上には表示されていません。

注意すべきポイントは、`>`は既にファイルが存在した場合に、強制的に上書き　してしまうコマンドです。

`>`のところを`>>`にすると、上書きではなく、末尾に追加されます。

AWS Cloud9のWorkspaceでの実行結果
<img width="820" alt="スクリーンショット 2018-05-25 16.40.28.png" src="https://qiita-image-store.s3.amazonaws.com/0/14191/aa5d87fd-cec9-0f54-58f9-d7815ec9d223.png">
TensorboardのProjectorの画像メタデータに使用するスプライト画像の作り方（画像URLデータから）

TensorboardのProjectorで、各要素に対応する画像をはっつけるためのsprite画像(metadata)を作ろうと思ったが、
それをurlから作る時に参考になるいいサイトがなく苦労したので、ここで紹介する。
使用言語はPython3である。

```python
#必要なモジュールをimport
import urllib.error
import urllib.request
import time
import os
import pickle

#urlをdownloadする関数を定義
def download_image(url, dst_path):
    try:
        data=urllib.request.urlopen(url).read()
        with open(dst_path, mode='wb') as f:
            f.write(data)
    except urllib.error.URLError as e:
        print(e)

#このディレクトリはあらかじめ作っておく。
download_dir='images'

#urlデータを持ってくる
with open('urls', 'rb') as f:
    urls=pickle.load(f)

list=[]
for (i, url) in enumerate(urls):
    #ファイル名はurlの配列順の番号にする（ここは任意）
    dst_path=os.path.join(download_dir, str(i))
    #urlをダウンロード
    download_image(url, dst_path)
    #ダウンロードしたurlの順番を覚えておく。
    list.append(i)

#画像をarrayに変換
image_array=xp.array([xp.array(Image.open('images/'+str(i))) for i in list])
image_array_c=copy.deepcopy(image_array)


#画像の修正
#下は(200,200)のサイズにしたいときの例
import cv2
for i in range(image_array_c.shape[0]):
    image_array_c[i]=cv2.resize(image_array_c[i], (200,200))

#修正した画像を保存
#urlの配列順をsprite画像まで失わないためにファイル名のlistをurlの配列順に作成。ここではその順番をファイル名に使っている。
list=[]
for i in range(image_array_c.shape[0]):
    im=Image.fromarray((image_array_c[i]))
    list.append(str(i)+'.jpg')
    im.save('images/'+str(i)+'.jpg')


#sprite画像生成
#ちなみにlistを特定の配列にすれば好きな順番でsprite画像を作ることができる

from PIL import Image
import os, math, time
max_frames=int(xp.ceil(xp.sqrt(image_array_c.shape[0])))
frames = []
tile_width = 0
tile_height = 0

spritesheet_width = 200
spritesheet_height = 200

files = list

for current_file in files :
    try:
        with Image.open("images/" + current_file) as im :
            frames.append(im.getdata())
    except:
        print(current_file + " is not a valid image")

tile_width = frames[0].size[0]
tile_height = frames[0].size[1]


if len(frames) > max_frames :
    spritesheet_width = tile_width * max_frames
    spritesheet_height = tile_height * max_frames
else:
    spritesheet_width = tile_width*len(frames)
    spritesheet_height = tile_height
    
print(spritesheet_height)
print(spritesheet_width)

#真っ白なシート作成
spritesheet = Image.new("RGB",(int(spritesheet_width), int(spritesheet_height)))

#順番に画像をはめ込んでいく
for current_frame in frames :
    top = tile_height * math.floor((frames.index(current_frame))/max_frames)
    left = tile_width * (frames.index(current_frame) % max_frames)
    bottom = top + tile_height
    right = left + tile_width
    
    box = (left,top,right,bottom)
    box = [int(i) for i in box]
    cut_frame = current_frame.crop((0,0,tile_width,tile_height))
    
    spritesheet.paste(cut_frame, box)
    
spritesheet.save("spritesheet" + time.strftime("%Y-%m-%dT%H-%M-%S") + ".png", "PNG")
```
AWSのELB配下で動作する場合のみhttpsへリダイレクトさせる方法


PHPのフレームワークや関連するライブラリでhttp→httpsのリダイレクトを実現しようとしたら、AWSのELB+EC2の構成ではhttpの判定がうまくできなくてハマった。

アプリケーション内でコードを書くしかないと思ったら、.htaccessの設定だけで回避できたので共有までに。


## 条件
* Apache2.4で公開するWEBアプリケーション。
* 開発環境はローカルで構築し、httpでアクセスする。
* 本番環境はAWSのEC2上に構築し、ELB経由でアクセスする。
* AWSのELB配下で動作するELB→EC2の通信はhttp。
* 本番環境はhttpsでアクセスとし、httpの場合はhttpsの同じURLへリダイレクトさせたい。


## 解決方法

.htaccessで以下の設定をすることで解決した。

```.htaccess
<IfModule mod_rewrite.c>
    RewriteEngine On
    RewriteCond %{HTTP:X-Forwarded-Proto} =http
    RewriteRule ^.*$ https://%{HTTP_HOST}%{REQUEST_URI} [R,L]
    RewriteCond %{REQUEST_FILENAME} !-f
    RewriteRule ^ index.php [L]
</IfModule>
```

`RewriteCond %{HTTP:X-Forwarded-Proto} !=https`としてしまうと、ローカル環境で値が入っていなくてもリダイレクトされてしまうため、`=http`で判定すると希望通りの動きをしてくれた。
Gitで大文字と小文字両方のフォルダができてしまったときにどちらか片方を消す方法

# 目的
GitHubで作業をしていたらある日こんなディレクトリができてしまいました。

<img width="89" alt="スクリーンショット 2018-05-25 16.30.07.png" src="https://qiita-image-store.s3.amazonaws.com/0/100275/f9af0262-af3f-ceca-00a0-5f77789b6874.png">

ファッ！？
macOSのローカルだとuserApiしかないためファイラーの操作では削除できず、一体何が起こっているんだ・・・と思ったのですが、小文字のフォルダだけを消す方法を備忘録として残しておきます。

# 1. Git上で大文字小文字の変更を認識するようにする

```
$ git config core.ignorecase false
```

としてあげると、Git上で大文字小文字のファイル/フォルダ名変更もTrackするようになります。

このとき、**もともと小文字のフォルダに入っていると認識されていた中身のファイルが大文字への変更が認識されることが原因で**Gitに差異が発生するかもしれません。きちんとcommitしておきましょう

```
$ git commit -m "userapi to userApi"
```

# 2. 小文字のフォルダをgit上から削除する

```
$ git rm -r someDir/userapi
```

とすると、中にはいっているファイルも含めGit内にトラックされていた小文字フォルダがすべて削除され、GitHub上からも消えます。

あ、で、変更した分をcommitします！

```
$ git commit -m "remove userapi"
```

最後に、設定したconfigをtrueに戻しておきましょう

```
$ git config core.ignorecase true
```

ちゃんとmergeされるまではこれが残ってるとcheckoutのときに苦労します・・・

以上です！
Chrome拡張機能:ダウンロードしたファイルをアップロードする

# はじめに
## やりたいこと
以下の操作を自動化する。

1. Flickr等で見つけた自由利用可能な画像ファイルをダウンロードする。
2. アップロードフォームにダウンロードした画像ファイルを指定してアップロードする。

## 制限事項
- たとえChrome拡張機能がダウンロードしたものでも、ローカルのファイルにはアクセスできない。
- アップロードフォームのファイル選択ダイアログをChrome拡張機能から操作できない。

こうした制限から、メモリ上の画像データから送信データを作成し、アップロードフォームを使わずに送信する必要がある。

# 手順1:画像ファイルのパスを探す
写真共有サイトは、オリジナル画像を直接表示していない。通信量削減のため縮小したものが表示されているので、まずはリンクをたどってオリジナル画像のURLを取得する。(Flickrの場合は、右下のアイコン「Download this photo」にリンクがある。)

その際、画像ファイルが置かれているドメインを確認し、manifest.jsonの`permissions`に追加する。(Flickrの場合は、「`https://c1.staticflickr.com/`」など。)ワイルドカードが使えないので、連番が降られている場合はすべての番号を追加する必要がある。

# 手順2:画像ファイルのダウンロード
XMLHttpRequestの`responseType`に`blob`を指定することで、画像ファイルをバイナリデータとして取得できる。

```javascript:background.js
const DownloadBlob = (url) => {
  const p = new Promise(resolve => {
    const xhr = new XMLHttpRequest();
    xhr.open('GET', url, true);
    xhr.responseType = 'blob';
    xhr.addEventListener('loadend', () => {resolve(xhr.response);});
    xhr.send();
  });

  return p;
}

const DownloadImage = async (url) => {
  const imageFile = await DownloadBlob(url);
}
```

# 手順3:送信データを作成する

```html:フォーム
<body>
  <form>
    <input type="file" name="file" value=""/><br/>
    <input type="text" name="title" value="タイトル"/><br/>
    <input type="hidden" name="session_id" value="123456789"/>
    <input type="submit" name="submit" value="送信"/>
  </form>
</body>
```

```javascript:background.js
const formData = new FormData();
formData.append('file', imageFile, 'ファイル名');
formData.append('title', 'タイトル');
formData.append('session_id', '123456789');
formData.append('submit', '送信'); //これはいらないかも。
```

`FormData`オブジェクトを作成し、`name`属性をキーに値を追加していく。

ファイルを追加する場合は、第三引数にファイル名を指定する。ファイル名はダウンロードしたURLから切り出してもよいが、自由につけることもできる。

上記の`session_id`のように、非表示になっている値も漏れなく追加する。

# 手順4:データを送信する
作成したFormDataオブジェクトをフォームのURLに送信する。cookieを必要とする場合は、XMLHttpRequestの`withCredentials`に`true`を指定して、フォームを受信してから送信する。

```javascript:background.js
const GetForm = (url) => {
  const p = new Promise(resolve => {
    const xhr = new XMLHttpRequest();
    xhr.open('Get', url, true);
    xhr.responseType = 'text';
    xhr.withCredentials = true;
    xhr.addEventListener('loadend', () => {resolve(xhr.response);});
    xhr.send();
  });

  return p;
}

const PostForm = (url, formData) => {
  const p = new Promise(resolve => {
    const xhr = new XMLHttpRequest();
    xhr.open('POST', url, true);
    xhr.responseType = 'text';
    xhr.withCredentials = true;
    xhr.addEventListener('loadend', () => {resolve(xhr.response);});
    xhr.send(formData);
  });

  return p;
}

const UploadImage = async (url, formData) => {
  await GetForm (url);
  await PostForm (url, formData);
}
```

# 注意

フォームデータを自作するため、アップロードフォームに備わっているバリデーションチェックが行われない。送信前にフォームデータの整合性を確認する必要がある。
ec2/rdsのpostgresにpgadminで接続してるとすぐタイムアウトになるのをなんとかする

# 現象

オンプレのpostgresサーバ等はpgadminで接続していてもそんなにタイムアウトにならない。
のに、RDSやEC2上にpostgresサーバを立てた場合、pgadminで接続しているとすぐタイムアウトになる。
そんなもんかなーと思って我慢して使ってたけど、そろそろタイムアウトしすぎることにイライラしたのでちゃんと調べてみた

# 対応方法

サーバ側の設定を変えずにクライアントにあるpgadminの接続設定を変える方法でいく

- クライアントに `.pg_service.conf` ファイルを作成
- pgadmin接続時の設定でサービスの部分に上記で作成したファイルで指定した名前を設定

## サービスファイルの作成

```

# macの場合
vi ~/.pg_service.conf

# winの場合
notepad %APPDATA%\postgresql\.pg_service.conf
```

```.pg_service.conf
[hoge]
keepalives=1
connect_timeout=20
keepalives_idle=10
```

## pgadminにサービスの設定

pgadminを立ち上げて接続の部分を右クリック、
`サービス` の部分に `.pg_service.conf` で指定した名前を設定
（上記例だと `hoge` ）

![image.png](https://qiita-image-store.s3.amazonaws.com/0/60056/a1fd6ba9-8edd-c0b3-c206-bff54a6909c9.png)


## 接続する

あとはpgadminから接続すればOK
Firebase Cloud Storageに格納した画像を一覧表示する

# はじめに
まずはじめに、ここで記述する方法が正攻法なのかわからないので、もっといい方法があれば教えてほしいという意味も込めて投稿しています。

# 問題点
最近Firebaseをさわり始めました。

Cloud Storageを使っていた際、「Cloud Storage上の特定のフォルダ内に置かれている画像を一括で取得して一覧表示させたい」ということがあった。

単純にCloud Storageに格納されているとある画像を表示させようと思ったら、下記のようにして、 
1. Cloud Storage 参照を作成
2. `getDownloadURL()`でファイルのダウンロードURLを取得
3. `<img>`の`src`に突っ込む
という手順を取ってやればいい。

```js
ref = firebase.storage().ref().child('img/sample.jpg');
ref.getDownloadURL().then((url) => {
  document.getElementById('image').src = url;
});
```

**しかし残念ながら、 Cloud Storage上の特定のフォルダ内に置かれているファイルのダウンロードURLを一括で取得するようなAPIは提供されていない...**

# 解決策
方針としては、Cloud FunctionsとFirestoreを使用します。
1. Cloud Storage上に画像をアップロード
2. Cloud Functions経由でFirestoreに画像のパス、もしくはダウンロードURLを書き込む
3. クライアントサイドからFirestoreに格納された情報からダウンロードURLを取得し、表示する

## Cloud Functions
> Cloud Functions for Firebase を使用すると、Firebase 機能や HTTPS リクエストによってトリガーされたイベントに応じて、バックエンド コードを自動的に実行できます。

今回はCloud Storage上にアップロードされたタイミングでCloud Functionsを実行しFirestore内に必要な情報を書き込むようにします。

## Firestore
> Google の柔軟でスケーラブルな NoSQL クラウド データベースを使用して、クライアント側開発とサーバー側開発のデータを保存、同期します。

データベースみたいなもので、ここへCloud Functionsから必要な情報を書き込んでいきます。

## 実装
とりあえずコード全体

```js
const functions = require('firebase-functions');
const admin = require('firebase-admin');

admin.initializeApp(functions.config().firebase);

exports.writeUrl = functions.storage.object().onFinalize((object) => {
  const bucketName = 'hoge.appspot.com'; // ご自身の
  const filePath = object.name;
  const db = admin.firestore();

  db.collection('images').add({
    filePath,
    downloadUrl: `https://firebasestorage.googleapis.com/v0/b/${bucketName}/o/${encodeURIComponent(filePath)}?alt=media`,
  }).then(() => console.log('Done')); // eslint-disable-line no-console
});
```

Cloud Functionsで使う関数を定義していいます。
`onFinalize()`内で、ファイルのアップロードされたときの処理を記述します。
`object.name`でファイルへのパスが取得できるので、これをFirestoreに書き込みます。
または、`https://firebasestorage.googleapis.com/v0/b/${bucketName}/o/${encodeURIComponent(filePath)}?alt=media`
で、Cloud Storage上のpublicなファイルのURLが取得できるので（[Firebaseの小ネタ集 - Qiita](https://qiita.com/shora_kujira16/items/95216245ecf06c4cd16d#%E9%9D%9E%E6%8E%A8%E5%A5%A8cloud-functions%E3%81%8B%E3%82%89cloud-storage%E4%B8%8A%E3%81%AE%E3%83%95%E3%82%A1%E3%82%A4%E3%83%AB%E3%81%AE%E5%85%AC%E9%96%8B%E7%94%A8url%E3%82%92getsignedurl%E3%82%92%E4%BD%BF%E3%82%8F%E3%81%9A%E3%81%AB%E5%8F%96%E5%BE%97%E3%81%99%E3%82%8B)）、これをFirestoreに書き込みます。

あとは一覧表示したいときに、Firestoreの（上記の例では）`images`コレクションを取得してきて、ドキュメント分ループさせて、はじめに記述したように`filePath`からダウンロードURLを取得して一覧表示させます。
`downloadUrl`を使えば`getDownloadURL()`する必要がないのでもっと楽だと思います。

# 所感
これが正攻法なのかは分からないです...
Cloud Storageの画像を一覧表示するときは普通どうするものなのだろうか...
Azure FunctionsでThymeleafを使う

サーバレスだとJSONを返却するのが一般的なのかなと思っていますが、htmlも返却することができます。
で、テンプレートエンジンがないとhtmlを作成するのが苦行になってしまうので、Thymeleafが使えないものかと試してみました。

# 前提
基本的に以下に従って環境が構築されている前提です。
（Mavenのアーキタイプからプロジェクトを作っていればokです。）
https://docs.microsoft.com/ja-jp/azure/azure-functions/functions-create-first-java-maven

# まずはシンプルにhtmlを返却する例
```java:Function.java
public class Function {
    @FunctionName("html")
    public HttpResponseMessage<String> html(@HttpTrigger(name = "html", methods = {
            "get" }, authLevel = AuthorizationLevel.FUNCTION) HttpRequestMessage<String> req) {
        String html = "<html><head><title>たいとる</title></head><body><h1>ぼでー</h1></body></html>";
        HttpResponseMessage<String> res = req.createResponse(200, html);
        res.addHeader("Content-Type", "text/html");

        return res;
    }
}
```

自前でhtmlを組み立てて、HttpResponseMessage型で返却します。
このとき、addHeaderでContent-Typeをtext/htmlにしておかないと、ブラウザにただの文字列と認識されてしまいます。

このぐらい簡単なhtmlならいいんですが、複雑になったり動的な要素がでてくると、つらみがあるのでThymeleafを使いたいんです。

# Thymeleafを使う
まずは、pom.xmlのdependencyにthymeleafを追加します。
バージョンは現時点で最新のものにしています。

```xml:pom.xml
<dependency>
  <groupId>org.thymeleaf</groupId>
  <artifactId>thymeleaf</artifactId>
  <version>3.0.9.RELEASE</version>
</dependency>
```

続いてソース。

```java:Fuction.java
public class Function{
    @FunctionName("thymeleaf")
    public HttpResponseMessage<String> thymeleaf(@HttpTrigger(name = "thymeleaf", methods = {
            "get" }, authLevel = AuthorizationLevel.FUNCTION) HttpRequestMessage<String> req) {
        
        ClassLoaderTemplateResolver templateResolver = new ClassLoaderTemplateResolver();
        templateResolver.setTemplateMode(TemplateMode.HTML);

        templateResolver.setPrefix("template/");
        templateResolver.setSuffix(".html");
        TemplateEngine templateEngine = new TemplateEngine();
        templateEngine.setTemplateResolver(templateResolver);

        Context context = new Context();
        context.setVariable("message", "hogehoge");
        String html = templateEngine.process("test", context);

        HttpResponseMessage<String> res = req.createResponse(200, html);
        res.addHeader("Content-Type", "text/html");

        return res;
    }
}
```
普段はSpringと一緒に使っているのであまり意識したことがなかったのですが、TemplateResolverはいくつか種類があります。
今回はClassLoaderTemplateResolverを利用します。

また、Thymeleaf側に値を渡すにはContextオブジェクトを作ってやる必要があります。
SpringでいうModelみたいなものだと思っています。

```html:test.html
<html xmlns:th="http://www.thymeleaf.org">
  <head>
    <title>Thymeleaf</title>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
  </head>
  <body>
    <p th:text="${message}">Thymeleaf!!</p>
  </body>
</html>
```
htmlはこんな感じでつくりました。
src/main/resources/templateに配置しています。

あとは起動なり、デプロイなりして動作確認できます。

# 所感
今回はメソッド内でThymeleaf関連のインスタンスを生成していますが、コンストラクタで実施して、インスタンス変数にした方がいいのかもしれません。
ただ、アクセスのたびにコンストラクタが実行されるのであれば意味ないんですが・・・。
サーバレスだと、このあたりの動作がよくわからないのでいずれ検証しなければ、と思っています。

また、ここまでやるんだったらSpring Bootとかでサクッと作ればいいじゃん、という気もしています。
サーバレスだとAuto Scaling機能があるので、その恩恵にあずかることができるという点はメリットなんですかね。
macOS High Sierra 10.13 では gdb 8.1 は動かない

「[mac OS 10.13(High Sierra) で gdb を使う](https://qiita.com/yuzu_afro/items/988020dd65fb4f43962a)」を参考に High Sierra に gdb を Homebrew からインストールしたらはまったので、そのときのメモ。

# 環境
- macOS High Sierra 10.13.4
- Homebrew 1.6.4

参考にした記事よりも Homebrew のバージョンが上がり、  `brew install gdb` を実行すると gdb 8.1 がインストールされる。コード署名をして gdb を実行すると、

```shell-session
During startup program terminated with signal SIGTRAP, Trace/breakpoint trap.
```

のようなエラーが出てしまった。どうやら、gdb 8.1 は macOS 10.13 に対応していないようで、gdb 8.0 をインストールする必要があるようだ。

# gdb 8.0 のインストール

[Stack Overflow のアンサー](https://stackoverflow.com/a/49104154/9588929)を参考にした。

Github 上の gdb 8.0.1 のコードを指定してインストール：

```shell-session
$ brew install https://raw.githubusercontent.com/Homebrew/homebrew-core/9ec9fb27a33698fc7636afce5c1c16787e9ce3f3/Formula/gdb.rb
```

gdb をアップデートしないようにする：

```shell-session
$ brew pin gdb
```

SIP (System Integrity Protection) を無効化していない場合は以下のコマンドも実行：

```shell-session
$ echo "set startup-with-shell off" >> ~/.gdbinit
```

後は[コード署名を作成](https://qiita.com/yuzu_afro/items/988020dd65fb4f43962a#gdbコード署名用の証明書の作成)して、 gdb に適応させれば良い。
Chrome v66.xで動画が自動再生されないので調べてみたらVue.jsのバグのせいだった

Chrome66以降で音声付き動画の自動再生がされなくなった。

https://it.srad.jp/story/18/03/23/2129218/

某案件で動画を自動再生していたサイトがあり、案の定Chrome66で自動再生されないということで依頼を受けて調査した。

回避策としてはvideoタグにmuted属性をつけることなので何も考えることなくmuted属性をつけてデバッグを開始。

ところがmuted属性を付与したvideoが自動再生されないではないか。

全くわけわからん...と丸一日考え込んでいたが、原因は意外なところにあった。

原因はサイト全体で利用していたVue.js。

調べたところVue.jsの2.5.3より前のバージョンではvideoタグのmuted属性の取り扱いにバグがあったよう。

- [
Video attribute 'muted' not applied in Firefox](https://github.com/vuejs/vue/issues/6887)

なのでバージョンを2.5.3以上のVue.jsを利用するように変更するだけで動画の自動再生が正常に働く。

動画の自動再生でハマった人はVue.jsのバージョンも疑ってみましょう。
日付フォーマットの罠

## はじめに
すべての環境でこうなのかどうかわからないが、注意したほうがよいこと（知っておいたほうがよいこと）。

## 年
多くの場合 OK: `yyyy`
多くの場合 NG: `YYYY`

参考: http://d.hatena.ne.jp/nakamura001/20150102/1420213850

> YYYY
> ある年における「最初の木曜日を含む週が、その年の第1週である」というルールで年(西暦)を出力。
> 
> 例えば 2015/1/1 は木曜日なのでその週の日は日曜日～土曜日まで全て2015年の第1週という解釈になり、 2014/12/28(日曜)～2014/12/31(水曜) の時に YYYY を使うと 2015 を返します。

## 月
`MM`が`月`。
`mm`は`分`。

## 日
多くの場合 OK: `dd`
多くの場合 NG: `DD`

`DD`は1月1日から何日たったかを示す。

参考: http://www.unicode.org/reports/tr35/tr35-25.html#Date_Format_Patterns

> | D | 1..3 | 345 | Day of year |

# 時
`hh`が`01`~`12`。
`HH`が`01`~`24`。

`hh`の方は午前(am)か午後(pm）を示す `a` と一緒に用いないと、例えば朝7時なのか夜7時なのか判別不能になる。

# 分
`mm`は`分`。
`MM`が`月`。

# 秒
多くの場合 OK: `ss`
多くの場合 NG: `SS`

参考: http://www.unicode.org/reports/tr35/tr35-25.html#Date_Format_Patterns

> | S | 1..n | 3456 | Fractional Second - truncates (like other time fields) to the count of letters. (example shows display using pattern SSSS for seconds value 12.34567) |
|:--|:--|--:|:--|
How to set up CircleCI in PHP project


## How to set up CircleCI config file on local PC.

#### Install `circleci` command
 
```
curl -o /usr/local/bin/circleci https://circle-downloads.s3.amazonaws.com/releases/build_agent_wrapper/circleci && chmod +x /usr/local/bin/circleci
circleci update
```


#### Create config file

The following file is often used in my PHP project.
Regarding the docker image, please see this [official page](https://circleci.com/docs/2.0/circleci-images/#php).

```
# PHP CircleCI 2.0 configuration file
#
# Check https://circleci.com/docs/2.0/language-php/ for more details
#
version: 2

jobs:
  build:

    docker:
      - image: circleci/php:7.0-apache-node-browsers

    steps:
      - checkout

      - run: echo -e "[Date]\ndate.timezone = Asia/Tokyo" | sudo tee /usr/local/etc/php/php.ini > /dev/null

      - run: chmod -R 777 ./storage
      - run: chmod -R 777 ./bootstrap/cache

      - run: sudo apt-get update -y
      - run: sudo apt-get install -y libpng-dev libjpeg-dev zip unzip git
      - run: sudo rm -rf /var/lib/apt/lists/*
      - run: sudo docker-php-ext-install zip
      - run: sudo docker-php-ext-configure gd --with-jpeg-dir=/usr/lib/x86_64-linux-gnu/
      - run: sudo docker-php-ext-install pdo pdo_mysql gd mbstring zip
      - run: sudo composer self-update

      - restore_cache:
          keys:
            - composer-v1-{{ checksum "composer.json" }}
            - composer-v1-
      - run: composer install -n --prefer-dist
      - save_cache:
          key: composer-v1-{{ checksum "composer.json" }}
          paths:
            - vendor

      - run: cp .env.example .env

      - run:
          name: Run PhpUnit
          command: ./vendor/bin/phpunit
```

#### Validate syntax of config.yml

```
circleci config validate -c .circleci/config.yml
```


#### Run to build and test

```
circleci build .circleci/config.yml
```
Angular5 基礎メモ

## 初期設定

```
npm install -g @angular/cli
cd angular-tour-of-heroes
ng serve --open
```

ng serveコマンドはアプリケーションをビルド、開発用サーバーを起動し、ソースファイルを監視します。 あなたが監視されているファイルに変更を行ったときには、変更があったファイルに対し再ビルドを行います。

--openフラグを指定すると、http://localhost:4200がブラウザで開かれます。



## コーディング規約

https://github.com/Microsoft/TypeScript/wiki/Coding-guidelines


## よく使うngコマンド

```
# Add Component
ng generate component hero-detail --module=app

# Add Service 
ng generate service message

# Add Module
ng generate module app-routing --flat --module=app
※--flatは、固有のフォルダの代わりに、src/appに生成したファイルを置きます。

```


## テンプレート内の記号について

```
# - variable declaration

() - event binding

[] - property binding

[()] - two-way property binding

{{ }} - interpolation

* - structural directives

```

`#` は下記のように使うことができる

```
 <span [hidden]="harry.value">*</span>
 <input type="text" #harry>
 {{ harry.value }}
```
チルダについて（ターミナル）

# `~`（チルダ）について

ホームフォルダはターミナル上だと`~`で表されます。

ホームフォルダには設定ファイルなど（`.conf`ファイルなど）が多数配置されています。設定ファイルや設定フォルダ（？）は隠しファイルや隠しフォルダとなっています。

ホームフォルダにある隠しファイルや隠しフォルダをすべて表示させるコマンド

```bash
$ ls -a -1 ~
```

オプション：`1` は、各ファイルやフォルダを１行で表示するためのやつ

AWS Cloud9のWorkspaceでの実行結果

```bash

$ ec2-user:~/environment $ ls -a -1 ~
.
..
.aws
.bash_history
.bash_logout
.bash_profile
.bashrc
.bashr_profile
.c9
.codeintel
environment
.gitconfig
.npm
.nvm
.pki
.ssh
.viminfo

```

仮にオプション`1`をつけないと...

AWS Cloud9のWorkspaceでの実行結果

```bash

ec2-user:~ $ ls -a ~
.  ..  .aws  .bash_history  .bash_logout  .bash_profile  .bashrc  .bashr_profile  .c9  .codeintel  environment  .gitconfig  .npm  .nvm  .pki  .ssh  .viminfo

```

すべて、１つの行にまとめられます。
Gitのプッシュエラー「error: unpack failed: unpack-objects abnormal exit」の対処

# 経緯
このエラーはほんとに謎。
どこのサイトで見てみも対処に至らず、結局は自分流で対処したわけだがその内容が意味わからん。

原因不明のまま経験則による対処方法をまとめておく。

# エラーメッセージ
```
$ git push
Counting objects: 20, done.
Delta compression using up to 4 threads.
Compressing objects: 100% (15/15), done.
Writing objects: 100% (20/20), 2.77 KiB | 944.00 KiB/s, done.
Total 20 (delta 17), reused 6 (delta 5)
error: remote unpack failed: unpack-objects abnormal exit
To https://www.xxx/yyy.git
 ! [remote rejected] master -> master (n/a (unpacker error))
error: failed to push some refs to 'https://www.xxx/yyy.git'
```

上記のエラーメッセージから下記サイトを参考にしたが対処に至らず。

`git repack`による対処
https://ja.confluence.atlassian.com/bitbucketserverkb/error-unpack-failed-unpack-objects-abnormal-exit-779171795.html

リモート環境の権限修正
http://nu-pan.hatenablog.com/entry/20140413/1397352725
→そもそもリモート環境はアクセスできないので、試せてもいないのだが。。

# 対処方法
どうやら特定のファイルがプッシュできない。
→プッシュできないファイルを割り出す。

例えばファイルが10個あれば、次のようなことを再帰的に行う。

```
初めの5個だけコミット／プッシュ
→NG：5個の内初めの3つをコミット／プッシュ
→OK：残りの5個をコミット／プッシュ
```

で、たどり着いたファイルでは次のような修正をしていた。

```javascript:修正前
import { IonicPage, NavController, NavParams } from 'ionic-angular';
import { BASE_URL, API_VERSION } from '../../app/shared/base.url';
import { Storage } from '@ionic/storage';
```

```javascript:修正後
import { IonicPage, NavController, NavParams } from 'ionic-angular';
import { BASE_URL } from '../../app/shared/base.url';
import { Storage } from '@ionic/storage';
```

変更点はAPI_VERSION を削除しただけ・・・・？？
他のファイルはバンバンプッシュできたのに。

試しに次のように修正してみたらプッシュできた。

```javascript:修正後をさらに修正
import { IonicPage, NavController, NavParams } from 'ionic-angular';

import { BASE_URL } from '../../app/shared/base.url';
import { Storage } from '@ionic/storage';
```

修正行の前に改行を入れてみたらプッシュできるという全く意味の分からない話。
これってリモート環境の権限は関係ある話なのかな・・・？

----
# 2020/9
今更ながらの考察として、改行コードが違ってたりしてたのかな・・・？
当時は、あまりGitに詳しくない（今もめちゃくちゃ詳しいわけではないが）ときだったので、改行コードとかの意識も薄い。
オフショアでやってもらった修正を、プッシュできないと言われてこの対応をしたのだが、オフショアと私でエディタやgitの設定が違う話はよくしていた。
オフショア側に改行コードは\nだよと言っても、何回か\r\nで来たことがある。
まぁ今となっては確かめる事もないのだけど。
Pythonで実験データをプロットするためのコピペ

「実験のレポート書かなきゃ」とか「これから研究生活始まるぞ」とかとか思ってるけど，「Excelはなんとなく使いたくない」という時にどうしようか。

迷ってたらとりあえずPythonで書きましょう。猫も杓子もPythonです。無料だし。
でもプログラミングほぼわからん。みたいな状態でも次のコードをjupyter notebookにコピペすればとりあえず図が出ます。
環境構築はAnacondaをインストールすればなんとかなります。がんばる。

## とりあえず次のコードをコピペしていじればよい

```py
%matplotlib inline #Jupyter上にグラフを表示する

import numpy as np
import matplotlib.pyplot as plt

folder = "hogehoge" #自分の測定データfileがあるフォルダのパス
filename = "test.txt"
data_path = folder + filename

data = np.genfromtxt(data_path, skip_header = 1)#変数dataに2次元の測定データを格納
x = data[:,0]#縦にxデータが並んでいると想定
y = data[:,1]

fig,ax = plt.subplots(1,1)
#プロットのためfigureオブジェクトと，その中にaxesオブジェクトを1×1個(名前 ax)作成

ax.plot(x,y,label = "y label")#凡例をつけてaxにプロット

ax.set_ylabel("y axis")
ax.set_xlabel("x axis")
ax.legend(loc = "best")#凡例表示
```

ここではn行2列のテーブルになっているファイルを想定。
測定データの補足情報とか書いてありそうなヘッダーは１行だとした。

## 結果
ここで，擬似データを
x = np.arange(0,100,1)
y = np.random.rand(100)
でつくってプロットする。

![ダウンロード .png](https://qiita-image-store.s3.amazonaws.com/0/173665/1065da8f-32f9-e007-19de-7277c742d5bf.png)


いい感じ。
あとはググりながらコードの意味を調べるなり，解析してからプロットするなり，理想的な図に近づけていきましょう。

###補足
```
plt.plot(x,y)
```
みたいにプロットするよりこっちの方がオブジェクト指向言語らしくかけてるかと思います。
Reactにおけるテストについて勉強したことまとめ

最近はReactとReact Nativeで掲示板サイトとそのクライアントアプリを作っています。
そろそろテスト駆動開発にしたいと思ったので、テストについて調べたことをまとめます。

もしこの記事を気に入っていただけたり何か間違ったことがあったらツイッターで私(@wabisuke2718)をフォローしてリプを飛ばしていただけるとモチベーションが上がります。

参考にした本やサイトは一番下の「参考資料」にまとめてあります。


#Reactにおけるテスト
##Jestを使おう
JavaScriptでユニットテストを行うには、テストランナー（テストファイルの実行処理を行う）、アサーションライブラリ（expectなどの関数を提供する）、モックライブラリ（特定のモジュールや関数の振る舞いを偽装する）を用意する必要があるが、Jestにはこれらがまとめて入っているのでJestさえインストールすればいい。

##create-react-appでJestを使ってみる
実はJestはcreate-react-appに標準搭載されているので、この方法でプロジェクトを作成した場合、最初からJestが使えます。Reactコンポーネントを簡単にテストするためにenzyme（誰か読み方教えて）も入れます。

```
create-react-app jest-practice
cd jest-practice
npm install --save-dev enzyme enzyme-adapter-react-16
```

enzymeのセットアップファイルを下記のように用意します。（srcディレクトリの下にsetupTests.jsを作成する）

```js:jest-practice\src\setupTests.js
import { configure } from 'enzyme'
import Adapter from 'enzyme-adapter-react-16'

configure({ adapter: new Adapter() })
```

ここまでで準備は完了です。次は実際のテストコードを書いていきます。
create-react-appが用意したApp.jsのテストコードが既にあるのでこれを書き換えます。

```js:jest-practice\src\App.test.js
import React from 'react'
import { shallow } from 'enzyme'
import App from '../src/App'


test('Welcome to Reactという文字列がある', () => {
  const wrapper = shallow(<App />)
  expect(wrapper.text()).toContain('Welcome to React')
})
```

上のコードでAppコンポーネントが描画されたときに「Welcome to React」という文字列が含まれているかテストすることができます。




#参考資料
- 書籍「[React入門 React・Reduxの導入からサーバサイドレンダリングによるUXの向上まで](https://www.amazon.co.jp/React%E5%85%A5%E9%96%80-React%E3%83%BBRedux%E3%81%AE%E5%B0%8E%E5%85%A5%E3%81%8B%E3%82%89%E3%82%B5%E3%83%BC%E3%83%90%E3%82%B5%E3%82%A4%E3%83%89%E3%83%AC%E3%83%B3%E3%83%80%E3%83%AA%E3%83%B3%E3%82%B0%E3%81%AB%E3%82%88%E3%82%8BUX%E3%81%AE%E5%90%91%E4%B8%8A%E3%81%BE%E3%81%A7-NEXT-ONE-%E7%A9%B4%E4%BA%95/dp/4798153354/ref=sr_1_1?ie=UTF8&qid=1527233974&sr=8-1&keywords=react+%E5%85%A5%E9%96%80)」
- 書籍「[React開発 現場の教科書](https://www.amazon.co.jp/React%E9%96%8B%E7%99%BA-%E7%8F%BE%E5%A0%B4%E3%81%AE%E6%95%99%E7%A7%91%E6%9B%B8-%E7%9F%B3%E6%A9%8B-%E5%95%93%E5%A4%AA/dp/4839960496/ref=sr_1_10?ie=UTF8&qid=1527233974&sr=8-10&keywords=react+%E5%85%A5%E9%96%80)」
- サイト「[2017年JavaScriptのテスト概論](https://postd.cc/a-complete-guide-to-testing-javascript-in-2017/)」
- サイト「[Jest + enzymeで行うReactのUT（ユニットテスト ）について](https://mae.chab.in/archives/60066)」
- サイト「[Facebook製のJavaScriptテストツール「Jest」の逆引き使用例](https://qiita.com/chimame/items/e97883fd46b67529d59f)」
Movable Type ローカル（Mac）開発環境

Movable Type を学習する必要がありローカルに開発環境を作ったんだけど、perlの知識がなくてかなり手こずった。

ローカルのOSは、MacOS Sierra 10.12.6

## XAMPP for OS X で試す
いつもWordPressをローカルで動かす時はXAMPPを使っているので、同じ環境で動けばいいなと。
XAMPP(PHP)のバージョンは5.6.30。
DBD::mysqlをインストールしようとしたら、度重なるエラー。
解消しつつ進めてみるも、最終的にmysql.hがないとかエラーが出て詰まる。
なんかどっかのパスの問題？
結局諦めて、Movable Typeは動作させられず。

## XAMPP-VM で試す
新しいもの見たさもあり、最新のXAMPP-VMで試してみる。
足りないperlモジュールをインストールしようとしても、外部にアクセスできない。
DNSの設定とか???
さっぱりわからん。
これじゃmt-check.cgiすら動かせない。
ところで、XAMPP-VMはviすら使えなくて唖然。
apt-getも使えないとか、XAMPP-VMっていったい何なの？

## Mac自体で試す
もう嫌だー！と投げ出したくなるのをグッと堪え、HomebrewでMacにmysqlをインストールする。
perlは元々Macに入ってるので、DBD::mysqlだけインストール。
Apacheの設定とか書き換えて、ディレクトリを設定して、CGIが動かせるように変更。
Movable Typeを設置して、やっとインストール完了！
  
"イメージドライバーが設定されていません。"と出てきたので、ImageMagickもインストール。
なんとか動かすことができた。

XAMPPのApache, MySQLと共存できないので、いちいちstop, startしないといけないのが面倒。
勉強用のサーバをおねだりしようかな。
Unity - パ○ツを遮る謎の光を実装してみた。


# 諸注意
アニメでよく見かけるあの輝かしい光をUnityで実装してみました。
パ○チラは男のロマンであり、夢であり、憧れであります。
安易な気持ちでアプリに組み込んで非難を浴びないようご注意ください(´・ω・｀)

# LensFlareの用意
空のGameObjectを用意して、そこにLensFlareコンポーネントを追加します。
LensFlare用のテクスチャはデフォルトで用意されてますが、光源が小さくスカート全体を隠しきれなかったのでAssetStoreから専用のテクスチャを追加でインポートしておくとよいです
[Lens Flares - Asset Store](https://www.assetstore.unity3d.com/jp/#!/content/5)

# 配置
LensFlareをスカートの中に仕込みます。
モデルが動いてもいいように必ず腰回りのジョイントの配下に設置しましょう。
プロ生ちゃんの場合であばlower_body配下に置く。
![img](http://drive.google.com/uc?export=view&id=0B_c9PQ_b1f3ATzFaY1FVaWloaDQ)


# Colliderの設定
そのまま配置しただけだとフレアがスカートを貫通してしまいます。
![img](http://drive.google.com/uc?export=view&id=0B_c9PQ_b1f3AR3Z5YTFSZDdpQlU)

LensFlareはColliderで隠せるのでスカートのジョイントにそれぞれBoxColliderを追加していきます。
![img](http://drive.google.com/uc?export=view&id=0B_c9PQ_b1f3AVUQ0YWFzNi03UFE)

腰回りから光がもれないようにフタ用のColliderも
![img](http://drive.google.com/uc?export=view&id=0B_c9PQ_b1f3AMjJYQ3JJUHJxZ2M)


# IgnoreLayers(無視するレイヤー)の設定
Colliderを追加しただけだとレイヤー設定がDefaultのままなので、他の無関係なColliderを通して見たときフレア効果が消えてしまう場合があります。
そうならないようにLensFlareを隠すためのColliderには専用のレイヤーを設定しておくとよいです。
例として「Nazonohikari」としておきます。
![img](http://drive.google.com/uc?export=view&id=0B_c9PQ_b1f3ARTVURHZFaDFxNUE)


次にLensFlareのIgnoreLayersに**フレア効果を隠すレイヤー**を設定します。
今回の例であれば「Nazonohikari」レイヤーのみチェックが外れた状態にしておけば、Nazonohikariレイヤーが設定されたスカートのColldierのみフレア効果を隠してくれます。
![img](http://drive.google.com/uc?export=view&id=0B_c9PQ_b1f3AdWJrN3p6YXh3Yms)



# 完成
![gif](http://i.giphy.com/l44QtPDlAgtJWtopW.gif)

フレアの強さやフェード時間などはInspectorでいじれます。
dockerでCakePHPの環境構築をした時に、データベースに接続できない

### 開発環境
> CentOS6.9
> PHP5.6
> apache2.2.15
> MySQL5.6

## 問題
とりあえずDockerの環境を作ってCakePHPをインストールした、あとは設定だ！という場面で、
![スクリーンショット 2018-05-25 14.07.30.png](https://qiita-image-store.s3.amazonaws.com/0/246277/966059fc-e5df-5e72-fa6f-62f336dad772.png)

`SQLSTATE[HY000][2002] No such file or directory`
上の図の様なエラーが出てくることがあります。 エラー文をググると、

```php:app/Config/batabase.php
'host'       => 'localhost' を '127.0.0.1'
```

に変更しろとありますね。 でも直らない！ってときの対策です。

## 対策: MySQLコンテナのIPを調べる
まず、作業コンテナからDBコンテナにはアクセスするには、DBコンテナのIPアドレスがわかっていないといけません。 まずIPアドレスを調べましょう。

```
# mysqlコンテナにログインする
$ docker exec -it (mysqlコンテナ名) /bin/bash

# IPアドレスを表示
$ cat /etc/hosts

```

```
127.0.0.1	localhost
::1	localhost ip6-localhost ip6-loopback
fe00::0	ip6-localnet
ff00::0	ip6-mcastprefix
ff02::1	ip6-allnodes
ff02::2	ip6-allrouters
172.21.0.2	371725c16aa6
```

と出ます。 ここでいうと　
`371725c16aa`がDBコンテナのidなので、`172.21.0.2`がそのコンテナのIPアドレスとなります。

```php:app/Config/batabase.php
'host'       => '172.21.0.2'
```

と修正すると...?
![スクリーンショット 2018-05-25 14.09.58.png](https://qiita-image-store.s3.amazonaws.com/0/246277/bfff1bb2-4e12-42d4-883e-39b33d3e23f1.png)

データベースと接続できたみたいです。やったぜ。

これでもまだ接続できないよ〜><って方は、
php.ini　の設定や、 php-mysql　モジュールがインストールされていない場合がありますので調べてみてください。
RxJSを入門しようと思ったら既存のサンプルコードがエラーになる！(RxJS 6.0)

# 結論
2018 4月からRxJSのメジャーアップデートが行われたため、ネットに転がっているサンプルコードは使えなくなった模様。

・RxJS 6.0 変更点まとめ（@ponday　さん）
https://qiita.com/ponday/items/7966787fa0bc8f3e2dde

・npm RxJSページ
https://www.npmjs.com/package/rxjs



# 初心者のつまづき
2018年から、晴れてプログラマーとして仕事をするようになりました。
通信系の処理を書く際に、上司からRxJSくらい使えるようになっておけと言われたので学習をはじめた次第。

node.js環境なので、いつもの通りにパッケージを追加する。
```npm install rxjs --save```

とりあえず、「RxJS　入門」と調べてサンプルコードを探して試そうと、サイトを巡回してみるも動作しない。
（filterとかmapとか、not a functionとなってしまう。）

【わかりやすい】RxJSで始める関数リアクティブ・プログラミング（@kitfactory　さん）
https://qiita.com/kitfactory/items/c9cba37a12745acf0697

公式リファレンスのサンプルコードを書いてみるも変わらず。
・RxJS Introduction
https://rxjs-dev.firebaseapp.com/guide/overview



パスがおかしいのかと悪戦苦闘するも効果なし。
調べてみると、どうやらバージョン変更で大規模な仕様変更があったとのこと。
npm公式のリファレンスより、以下サンプルコードを実行したところ、動作を確認。

```test.ts
import { Observable, Subject, ReplaySubject, from, of, range } from 'rxjs';
import { map, filter, switchMap } from 'rxjs/operators';
 
range(1, 200)
  .pipe(filter(x => x % 2 === 1), map(x => x + x))
  .subscribe(x => console.log(x));
```

後で気がついたのですが、公式リファレンスも右上に**「WARNING: This is BETA site」**と書かれていました・・・・・・。

![image.png](https://qiita-image-store.s3.amazonaws.com/0/259887/0d4c9d4c-ab05-51fb-237b-d9b9afa57cb8.png)


とはいえ、上司のコードをリファクタする関係で前バージョンと同じ書き方を使いたいので、以下コマンドでダウングレードすることに。

```npm install rxjs@5.5.7 --save```

これで以前のサンプルコードでも動作するようになりました。(5.5.7の理由は、上司の使用バージョンに合わせたからです。)
サンプルコードを拝借する際には、対応バージョンも確認した方がよいなとの教訓を得ました。
python3での入力メモ

プログラミング競技とかで使うのでinputの使い方についてちょっと整理
#結論
```input.py
a=[int(i) for i in input().split()]
```
整数値の複数入力にはこれ使いましょう。
あとは好きに応用してください。終わり！


基礎説明読みたい人は以下見てください。
#説明
入力

```
5
```

```input.py
i=input()
print(i)
print(type(i))
```

出力

```
5
<class 'str'>
```

input文の一番基礎です。キモは文字列型であること。
で、数値の型でやりたくなりますよね。

入力

```
5
3.14
```

```input.py
print('== i ==')
i=int(input())
print(i)
print(type(i))


print('\n== j ==')
j=float(input())
print(j)
print(type(j))
```

出力

```
== i ==
5
<class 'int'>

== j ==
3.14
<class 'float'>

```
int型、float型の場合です。

で、複数の入力を入れる場合です。
入力

```
5 3 9
```
```input.py
a=input().split()
print(a)
print(type(a))
print(a[0])
print(type(a[0]))
```

出力

```
['5', '3', '9']
<class 'list'>
5
<class 'str'>
```

はい、input().split()だとリストは帰ってくるんですが中身が文字列です。
なのでこう書きます。


入力

```
5 3 9
```
```input.py
a=[int(i) for i in input().split()]
print(a)
print(type(a))
print(a[0])
print(type(a[0]))
```

出力

```
[5, 3, 9]
<class 'list'>
5
<class 'int'>
```

ちゃんとした数値ですね。今のとこ一番使ってます。
リスト型にして使いやすいですし。

3つ入力と確定していてabcの別の変数に入れたい場合はこうなります。

```input.py
[a,b,c]=[int(i) for i in input().split()]
```

以上です。
シェルスクリプト中でディレクトリの存在確認をする

ディレクトリの存在を確認する。
```
if [ -d $dirpath ]; then
    echo "ディレクトリあり"
else
    echo "ディレクトリなし"
fi
```

ファイルの場合は-d を-fに変更する。
パスの場合は -d を -e に変更する。
Unity - コールバックの記述まとめ

# 種類
コールバックは「ファイルのダウンロードが完了するまで処理を止めたい」などの場合によく使われる手法です。
今回はUnityで扱えるコールバックを

- UnityAction
- UnityEvent
- delegate

の3つに分けて、それぞれの記述方法をまとめました。

# UnityAction

引数は持てないがシンプルにコールバックが実装できる。
挙動はSystem.Actionと同じです(たぶん)

```c#
// 追加
using UnityEngine.Events;
```

↑忘れずに。

```c#
void Start () {
	// 処理を実行するメソッドにコールバックを受け取りたいメソッドを渡す
	ActionMethod (ActionCallbackMethod);
	// ラムダ式UnityAction
	ActionMethod (() =&gt; {
		Debug.Log("ラムダ式UnityAction実行完了 : "+testVal);
	});
}

// 実行メソッド
private void ActionMethod (UnityAction callback) {
	// コールバック実行
	callback ();
}

// UnityActionのコールバックで呼び出されるメソッド
	public void ActionCallbackMethod () {
	Debug.Log ("UnityAction実行完了");
}
```

# delegate

引数付きのコールバックを実装したいときはこれ。
自分で引数付きの型を作り、その型を使ってコールバック用の変数を宣言する。

delegate型の宣言をする。

```c#
// delegate型の宣言
private delegate void OnComplete (string text);

void Start () {
	// 処理を実行するメソッドにコールバックを受け取りたいメソッドを渡す
	DelegateMethod (DelegateCallbackMethod);

	// ラムダ式delegate
	DelegateMethod ((string text) =&gt; {
	    Debug.Log ("ラムダ式delegate実行完了 : " + text);
	});
}

// 実行メソッド
private void DelegateMethod (OnComplete callback) {
	// コールバック実行
	callback ("文字列だよ");
}

// delegateのコールバックで呼び出されるメソッド
public void DelegateCallbackMethod (string text) {
	Debug.Log ("delegate実行完了 : "+text);
}
```

# UnityEvent

メソッドを複数登録できるので実行対象が多い場合に有効。
登録したメソッドを呼び出すにはInvoke()を使う。
Invoke()を使うと登録したメソッドが一斉に実行される。
Inspector上でもメソッドの登録ができるのがキモ。

```c#
// 追加
using UnityEngine.Events;
```

UnityEventはインスタンスの生成を忘れずに。

```c#
private UnityEvent unityEvent;

void Start () {
	// インスタンスを生成
	if (unityEvent == null)
		unityEvent = new UnityEvent ();
	// Invoke()で実行させるメソッドを登録する
	unityEvent.AddListener (UnityEventCallbackMethod_1);
	unityEvent.AddListener (UnityEventCallbackMethod_2);
	// 登録されたメソッドを一斉に実行する
	unityEvent.Invoke();
}

// Invoke時に実行されるメソッド1
private void UnityEventCallbackMethod_1 () {
	Debug.Log ("UnityEvent実行完了 その1");
}

// Invoke時に実行されるメソッド2
private void UnityEventCallbackMethod_2 () {
	Debug.Log ("UnityEvent実行完了 その2");
}
```

# 以上
GitHubに上記をまとめたプロジェクト置いておきました。
[GitHub - UnityCallbackSample]("https://github.com/kamanii24/UnityCallbackSample")
Spring Security ログインフォームの処理

###ログインのjsp

    <%@ page language="java" contentType="text/html; charset=UTF-8"
        pageEncoding="UTF-8"%>
    <%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
    <%@ taglib prefix="sec" uri="http://www.springframework.org/security/tags" %>
    <%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>
        
    <!DOCTYPE html>
    <html>
    <head>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
    <title>ログイン</title>
    </head>
    <body>
    	<div id="wrapper">
    		<h3>ログインフォーム</h3>
    		<c:if test="${param.containsKey('error')}">
    			<span style="color: red;">
    				<c:out value="${SPRING_SECURITY_LAST_EXCEPTION.message}" />
    			</span>
    		</c:if>
    <%--		<c:url　var="loginUrl" value="/login"/>  --%>
    		<form:form action="/authentication">
    			<table>
    				<tr>
    					<td><label for="username">ユーザー名</label></td>
    					<td><input type="text" id="username" name="username"></td>
    				</tr>
    				<tr>
    					<td><label for="password">パスワード</label></td>
    					<td><input type="password" id="password" name="password"></td>
    				</tr>
    				<tr>
    					<td>&nbsp;</td>
    					<td><button>ログイン</button></td>
    				</tr>
    			</table>
    		</form:form>
    	</div>
    </body>
    </html>

<%@ taglib prefix="c" uri=""%>でcという表記にuriの値を紐づけている
<c:if test="${param.containsKey('error')}">
パラメータにコンテンツキー[エラー]の値が入っていれば、SPRING_SECURITY_LAST_EXCEPTION.messageの値を出力
formの行先は、/authentication
ユーザー名のnameは"username"
パスワードのnameは"password"

###Handlerメソッド
    @Controller
    public class AuthenticationController {

        @RequestMapping(path = "/login", method = RequestMethod.GET)
            public String viewLogin() {
	    	return "loginForm";
    	}
    }

コントローラーです
"/login"に送られてきたGETを受け取り、loginFormを返す単純なメソッドです

###xmlでのBean定義
#####security-config.xml
  	<sec:http>
		<sec:form-login 
                        login-page="/login"
			login-processing-url="/login"
		 	username-parameter="username"
		 	password-parameter="password"/>

		<sec:intercept-url pattern="/login" access="permitAll"/>
		<sec:intercept-url pattern="/**" access="isAuthenticated()"/>
	</sec:http>

login-page属性に"/login"を設定すると、ログインフォームが設定される
login-processing-url属性に、"/login"を設定する
認証処理を行うurlになる
設定をしないとj_spring_security_checkが認証用のパスになる
username-parameter,password-parameter属性にそれぞれ設定する
そうするとユーザー名、パスワードをどういう名前で受け取るかが設定される
※sec:intercept-urlはより指定が細かいほうを上に書きましょう

###認証が成功したときの動作
デフォルトでは、認証前にクライアントが行こうとしていたページにログイン完了後に遷移する
もともとログインフォームに対してアクセスしてきたユーザーはルートに飛ぶ

#####設定
#####security-config.xml
    <sec:http>
        内容
        <sec:form-login default-target-url="/menu" />
    </sec:http>

この設定で、ログイン完了後に"/menu"に飛ぶようになる

###認証が失敗したときの動作
デフォルトではログインフォームに設定されているパスに"error"クエリパラメータを付けてリダイレクトする

#####設定
#####security-config.xml
    <sec:http>
        中身
        <sec:form-login
            authentication-failure-url="/loginFailure" />
    </sec:http>


###まとめ
ここまでで、取りあえず動かしてみると自分で作成したログインフォームが表示されます
ですが、なぜかspring-securityのバージョンを5.0.0.RELEASEに上げないと上手くいきませんでした(4.2.3.RELEASEからの変更)
LaravelでのSPAじゃない場合におけるVueとbladeの共存

とても迷っているのでどうしようかという気持ち。
案件によってLaravelを使う、view関連のjavascriptでロジックを書くときにどういう構成をしようか、bladeとどうかき分けしようか考えている。

# resources配下の構成

構成としてLaravelにおけるビルド前のもろもろはここに入る。
Frontendの構成が分離されつつ、Laravel-mixによってビルドシステムが提供される。designについてはデザイナーチームの作るejs/sassなどが入っている。

```
.
├── README.md
├── assets
│   ├── js
│   └── sass
└── design
```

## design

こっちは別チームで開発が進む、UIのが決まったらまずデザインチームがここでgulp/ejs/sassを使って開発していく、LaravelではそこからビルドされたCSSなど必要なものだけ利用する。
ここでのgulpのタスクにその処理も追加した。

また `git submodule` で管理してるので、どこまでのdesignの更新をLaravel側に反映したかを管理できるようにしている。

## sass

sassは/design配下にあるので利用しないんですがディレクトリのみ残しています。
ここにsassファイルを移す議論もあったんですが、デザインチームがgulpをつかっててLaravelはLaravel-mix(webpack)になるので両方保守するのが嫌で使ってないです。

## js

jsは今回typescriptで書くんですが、名義上jsとしてます。
構成は以下のようになっています。SPAで作ることが多かったので、その構成をひきづって考えました。

```
.
├── js
│   ├── apimock
│   │   └── db.json
│   ├── components
│   │   ├── partials
│   │   │   └── Navbar.vue
│   │   └── views
│   │       ├── Dashboard.vue
│   │       └── Schedule.vue
│   ├── config
│   ├── constants
│   ├── mixins
│   ├── modules
│   ├── pages
│   │   ├── dashboard.ts
│   │   └── schedule.ts
│   └── typings
```

apimockに関してはswaggerに順次移行予定ですが、待ちきれないのでいったん[jsonserver](https://github.com/typicode/json-server)でフロント開発用のmockを用意しています。

基本的にpages配下に1画面ごとに必要なjsファイルをビルドするための設定を入れて、

> 1画面1JS1CSS

を意識して構成をしています。
これによってPHP側の構成はこんな感じがいいかなと思っています。

```
.
├── dashboard
│   └── index.blade.php
├── layout
│   ├── footer.blade.php
│   ├── head.blade.php
│   ├── header.blade.php
│   └── template.blade.php
```

基本的に画面ごとにbladeで基本的な構成を作り、画面内で動的になったりjsで必要なコンポーネントはVueで管理して表示をするような仕組みを想定しています。

せっかくのVueなのでSPAで全てAPIでvue-router駆使して最高のSPAにしたかったんですが、bladeも使いたいので、routingや基本的なviewの描画はLaravelに載せつつ、コンポーネントの管理をVueで載せることにしました。