OmniAICreator/Qiita-1.07M huggingface dataset:
Db2 warehouse on cloud (dashDB)で表をコピーする

##表のコピー方法
表をまるっと別表にコピーしたい場合とか、
集計結果を表を作成してロードしたいとかそういうとき

Db2 warehouse on cloud (以後Db2 WoC : 旧dashDB for Analytics)の環境で大量にデータをコピーするとログフルになるケースがあります。
（※ユーザーシナリオに依存。通常はないと思う）

Db2 WoCは**フルマネージド**で提供されるので、ログの設定を変更する事が出来ません。
なので、できるだけログに書かれない方法でデータをコピーしたい。

たとえば
`CREATE TABLE xxx AS (SELECT ...) WITH DATA`
とやっちゃうとINSERTの処理が実行されるんで表のデータ量が大きいと、
ログに書かれるしログ・スペースが必要だしでパフォーマンスもイマイチ。
INSERT SELECT と同様ですな。
"`insert into <ターゲット表> select * from <ソース表>`"
>必要に応じて CREATE TABLE の時に NOT LOGGED INITIALLY を使用する方法もあります。


**LOADユーティリティを利用**
こういうときはログを出力しないLOADユーティリティを利用します。
Db2 WoCのサンプル表　GOSALES.PROCUCT表をコピーしてみます。

```CREATE TABLE *hoge* LIKE *gosales.product*;
CALL SYSPROC.ADMIN_CMD ('LOAD FROM   
           (SELECT * FROM *gosales.product*)
     OF CURSOR  
     REPLACE INTO *yourschema.hoge*');```
Jenkins2のPipelineScriptでChatworkに投稿する

Jenkins2のパイプラインでChatworkプラグインを使わずに投稿したかったのでCurl使ってみました。

```groovy:
stage('Chatwork') 
{
    def ChatworkToken = "チャットワークAPIトークン"
    def RoomID = "ルームID"
    def PostMessage = "[info][title]タイトル[/title]投稿文[/info]"
    def PostURL = "https://api.chatwork.com/v2/rooms/$RoomID/messages"
    sh("curl -X POST -H \"X-ChatWorkToken:$ChatworkToken\" -d \"body=$PostMessage\" \"$PostURL\"")
}
```
UbuntuでRaspberryPiのOSをSDカードに読み込む




# 1 OSダウンロード・ハッシュ値の確認
1 以下のサイトからOSのイメージファイルをダウンロード
https://www.raspberrypi.org/downloads/raspbian/

ダウンロードサイトにはSHA-256のハッシュ値が公開されているので、sha256sumコマンドの結果と照らし合わせる。ダウンロードサイトにあるSHA-256ハッシュ値をコピーしてテキストファイルを作成する（checked.txtとする）

2 SHA-256のハッシュ値を計算する。以下のsha256sumコマンドで「.sha256」ファイルを作成する

```
$sha256sum 2017-07-05-raspbian-jessie-lite.zip > 2017-07-05-raspbian-jessie-lite.zip.sha256
```
Macの場合は`shasum -a 256`とする

3 作成した「checked.txt」と「2017-07-05-raspbian-jessie-lite.zip.sha1」をdiffで比較し、コードの部分が一致していればOK

```
$diff checked.txt 2017-07-05-raspbian-jessie-lite.zip.sha256
```


4 zipファイルを解凍する

# 2 SDカードの確認・アンマウント
1 SDカードを接続する前に接続されているデバイスを確認

```
$sudo parted -l
```

2 SDカードを接続する前にマウント済みのファイルシステム名を確認

```
$df -h
```
3 SDカードのロックを解除して、PC（Ubuntu）に接続する
4 再度デバイスを確認し、SDカードのDisk名を確認する
今回は /dev/sdc

```
$sudo parted -l
```
5 再度マウント済みのファイルシステム名を確認する(Disk名とは違うので注意)
今回は/dev/sdc1

```
$df -h
```

6 SDカードをアンマウントする

```
$umount /dev/sdc1
```


7 アンマウントできたか確認する

```
$df -h
```
アンマウントしたデバイスが消えて入ればOK


# 3 SDカードへの書き込み
1 以下のコマンドを入力してSDカードに書き込む

```
sudo dd if=2017-07-05-raspbian-jessie-lite.img of=/dev/sdc bs=1M
```

「if=」に読み込むフィイルを、
「of=」に書き込み先を指定する
###ここでデバイス名を間違えると悲惨。コマンドの実行前にデバイス名を再度確認する。
bsは一度にバッファに読み込むバイト数を指定
2 実行すると、4〜５分程度で以下のようなメッセージが表示される

```
1237+1 レコード入力
1237+1 レコード出力
1297862656 bytes (1.3 GB, 1.2 GiB) copied, 40.2724 s, 32.2 MB/s
```
3 キャッシュを同期させる

```
$sync
```


4 SDカードを取り出す
もう一度SDカードをPCに挿してみて、複数のファイルが存在すればインストール成功

5 マウント済みのファイルシステム名を確認し、アマウントしてから取り外す
インストール後にはファイルシステム名が変わることがある模様
今回は/dev/sdc1と/dev/sdc2になりました

```
$umount /dev/sdc1
$umount /dev/sdc2
```

参考:https://hombre-nuevo.com/raspberrypi/raspberrypi0025/
JDBC, CP, JPA, ORM.. Java と RDB の間にある奴らを整理する

# 注意
私は Java に詳しい自信も RDB に詳しい自信もありません。内容に責任も基本的に負いません。

# なぜこの記事を書くか
筆者は Java での Web サービス開発に携わるエンジニアだが、普段何気なく使っている（実は業務では NoSQL が多くそもそも使ってないのだが） ORM などのライブラリについて少し調べているときに、自分が思った以上にデータベースとの接続周りについて疎いことに気づいたので、まとめてみようと思った。

# JDBC
まずはここから。JDK 1.1 で登場。
Java からデータベースにアクセスするための標準 API。この「標準」というのは各 JVM のベンダ間で差異のないインタフェースだという意味。
以下のドライバ、ドライバマネージャを通じてアクセスするので、JDBC API はデータベース間で差異はない。JDBC という仕組み全体で、**JVM ベンダ・RDB の差異を吸収している**と言える。

## JDBC ドライバ
各データベースに対して実際に JDBC API を実装しているコネクタのようなもの。例えば MySQL 用、MariaDB 用のドライバがあるということになる。
ググるとわかるが、４種類の接続の方法があるが、それについては一旦割愛する。現在は主に TYPE 4 (Pure Java のドライバである）は主流だとされている。

## JDBC ドライバマネージャ
上記ドライバを管理して、アプリケーションから接続するための管理者の役割をする。ユーザが使う場合はこいつに JDBC ドライバを指定してやる。

# Connection Pooling (CP)
この文脈におけるコネクションプーリングとは、Java アプリケーションとデータベース間の接続をプールして使いまわす仕組み。
本来はこれに関してはプログラミング言語依存の話ではないし接続先もデータベースに限らないのだが、実際にコネクションプーリングと言ったらアプリケーションとデータベース間の接続のことを指すことが多いと思う。
主に知られているのは、 Tomcat などのアプリケーションサーバに付属したコネクションプーリングライブラリや、Commons DBCP、HikariCP といった専用ライブラリを利用する方法っぽい。**すごく簡単に言うと JDBC の Connection オブジェクトを使いまわすことができるようにするラッパーである。**
CP の目的（というかCPによって得られる効果といったほうが近いのか）は主に２つあって、

1. コネクションの永続化
2. 同時接続数の節約

1はクライアント視点で接続の入り切りは少し重い処理なのだということ（RDBMSによってはサーバ側もという話らしい。今は流石にそんなことなさそうだが、、）。2はどちらかというとアプリケーションでたくさんの処理がデータベースを使うような処理をする際は断続的なことが多いので、うまいことあいてるやつを使いまわしてサーバ側の負荷下げようね、って話かなと思う。

# Object/Relation Mapper (ORM)
要は RDB の「行」と Java などの「オブジェクト」をマッピングするためのライブラリ。言うても JDBC を使っても ORM なのではという言説もあるみたい。
Hibernate, MyBatis などが知られている。ORM 自身には CP の仕組みはないので、hibernate-HikariCP など組み合わせて使うことが多いと思う。先程の CP が JDBC を接続管理の視点からラップしているのに対し、こちらは**利用勝手の側面からラップしている**と言っていいと思う。

# Java Persistence API (JPA)
Java で RDB を使ったアプリケーションを開発する際のフレームワーク、ということになっているらしい。API とはいうものの、どうやらマッピングを外部記載したりするメタデータなどの部分も総称するみたいだ。それはもはや実装に近いのでは・・？という気もするが。あとは JPQL という SQL ライクな言語で、Java オブジェクトを操作するというのも要素の一部だ。
JPA 2.0 までは Java EE の一部だったらしい。
狭義の JPA、つまり API specification が規定された理由だが、JDBC が(正確には JDBC ドライバマネージャが）データベース間の差異を吸収するならば、こちらは **ORM 間の差異を吸収する**。要は、様々な ORM 実装がいろんな仕様になってしまうと利用側は差し替えしにくいので、共通の API 仕様を決めてしまい、それを実装するようにしましょう、ということっぽい。ただし、各 ORM は独自機能を持っている場合もあり、完全に1-on-1で対応しているわけではないことに注意。

有名な実装には Hibernate ORM や EclipseLink がある。
なお、ORM の定義にもよるが、MyBatis などを ORM と分類する向きもある。当然 MyBatis は JPA を実装したもの**ではない**。

# おまけ: Spring JDBC, Spring Data JPA
## Spring JDBC
https://stackoverflow.com/questions/9469643/difference-between-spring-jdbc-vs-plain-jdbc
まあこれもざっくりいうと JDBC をより簡単に使えるようにしたラッパーだと思う。ORM といってもいいかも。

## Spring Data JPA
https://stackoverflow.com/questions/16148188/spring-data-jpa-versus-jpa-whats-the-difference
https://stackoverflow.com/questions/42470060/spring-data-jdbc-spring-data-jpa-vs-hibernate
JPA を実装した ORM をさらにラップして Spring アプリケーションから簡単に使えるようにしたもの。これもラッパー。

# 感想
なんでも抽象化されているので、抽象化って、確かに綺麗だけど学習コストはやっぱりあがるなあ。コンピュータ難しいなあ。

# その他の参考資料
- http://www.atmarkit.co.jp/ait/articles/0106/26/news001.html
- http://morizyun.github.io/blog/connection-pooling-database-db-postgresql/
- http://murayama.hatenablog.com/entry/20090927/1254034778
    - コネクションプーリング
- https://stackoverflow.com/questions/27462185/jpa-vs-orm-vs-hibernate
    - 同じことを考える人はいるものだなあ
Apache Shiro Quickstart その２

前回はサンプルをそのまま動かしましたが、さすがに設定ファイルにユーザー情報を直書きはないと思います。
http://qiita.com/namikitakeo/items/fc593526fd354a381fbd

    [users]
    # format: username = password, role1, role2, ..., roleN
    root = secret,admin
    guest = guest,guest
    presidentskroob = 12345,president
    darkhelmet = ludicrousspeed,darklord,schwartz
    lonestarr = vespa,goodguy,schwartz

    [roles]
    # format: roleName = permission1, permission2, ..., permissionN
    admin = *
    schwartz = lightsaber:*
    goodguy = winnebago:drive:eagle5

ここらへんを参考にユーザー情報をデータベースから取得するようにします。MySQLを使うほどでもないのでApache Derbyを使います。
https://nhachicha.wordpress.com/2012/06/30/mysql-apache-derby-as-jdbcrealm-for-apache-shiro/

Apache Derbyサービスを起動します。

    $ sudo su -
    # cd /usr/share/derby
    # ./NetworkServerControl start

ユーザー情報データベースを作成します。

    $ ij
    ij> connect 'jdbc:derby://localhost:1527/test;create=true';
    ij> CREATE TABLE USERS (ID varchar(255) PRIMARY KEY NOT NULL, PASS varchar(255) NOT NULL);
    ij> CREATE TABLE ROLES (ID varchar(255) PRIMARY KEY NOT NULL, ROLE varchar(255) NOT NULL);
    ij> INSERT INTO USERS (ID,PASS) VALUES ('root','password');
    ij> INSERT INTO ROLES (ID,ROLE) VALUES ('root','admin');

webディレクトリに移動。

    $ cd shiro-root-1.3.2/samples/web

以下のようにshiro.iniを修正します。

    jdbcRealm=org.apache.shiro.realm.jdbc.JdbcRealm
    jdbcRealm.authenticationQuery = select pass from users where id = ?
    jdbcRealm.userRolesQuery = select role from roles where id = ?

    ds = com.jolbox.bonecp.BoneCPDataSource
    ds.driverClass=org.apache.derby.jdbc.ClientDriver
    ds.jdbcUrl=jdbc:derby://localhost:1527/test
    jdbcRealm.dataSource=$ds

    # We need to set the cipherKey, if you want the rememberMe cookie to work after restarting or on multiple nodes.
    # YOU MUST SET THIS TO A UNIQUE STRING
    #securityManager.rememberMeManager.cipherKey = kPH+bIxk5D2deZiIxcaaaA==

    #[users]
    # format: username = password, role1, role2, ..., roleN
    #root = secret,admin
    #guest = guest,guest
    #presidentskroob = 12345,president
    #darkhelmet = ludicrousspeed,darklord,schwartz
    #lonestarr = vespa,goodguy,schwartz

    #[roles]
    # format: roleName = permission1, permission2, ..., permissionN
    #admin = *
    #schwartz = lightsaber:*
    #goodguy = winnebago:drive:eagle5

以下のようにpom.xmlに依存関係を追加します。

    <dependency>
        <groupId>com.jolbox</groupId>
        <artifactId>bonecp</artifactId>
        <version>0.7.1.RELEASE</version>
    </dependency>
    <dependency>
        <groupId>org.apache.derby</groupId>
        <artifactId>derbyclient</artifactId>
        <version>10.4.2.0</version>
    </dependency>

Jettyを実行。

    $ mvn jetty:run

WEBブラウザで以下のURLを参照してください。
http://localhost:9080/
iOS11からApp StoreのUIが劇的に変わるために審査や運用ですべきこと

iOS11では、これまで以上にApp Storeの見た目が変化します。
アプリ開発者ならびにデザイナー各位、お仕事です！
※iOS11 beta5で確認

# スクリーンショット

## これまでの縦型は3枚に
<img width="375" alt="Image uploaded from iOS (5).jpg" src="https://qiita-image-store.s3.amazonaws.com/0/24308/8e86063e-4fd7-fa18-75b8-593391fe9c11.jpeg">

縦の表示領域が減り、3枚表示になります。テキストの見せ方を変える必要がありそうです。

## 横向きのスクリーンショット
<img width="375" alt="Image uploaded from iOS (4).jpg" src="https://qiita-image-store.s3.amazonaws.com/0/24308/692226a9-f0b2-ec90-2df7-aef73b427647.jpeg">

静止画は横向きが最適なのかもしれません。

## 動画は自動再生に

<img width="375" alt="Image uploaded from iOS (6).jpg" src="https://qiita-image-store.s3.amazonaws.com/0/24308/5f2e7c0a-a6ca-050b-7f6a-7f7002882808.jpeg">

（↑では分かりづらいですが、クラッシュ・オブ・クランで検索すると動画が自動再生されます）
これは大きな変更点ですね。より魅力的に見せるためにこれまで以上に動画も効果的です。

# タイトル（30文字）

## 文字数は50文字から30文字に

[新 App Store 審査ガイドライン 翻訳&差分ガイド 2017年6月号](http://qiita.com/midnightSuyama/items/522e1eeabc763ccb032f)
によると

>App names must be limited to 50 characters から App names must be limited to 30 characters に変更。

>App subtitles are a great way to provide additional context for your app; they must follow our standard metadata rules and should not include inappropriate content, reference other apps, or make unverifiable product claims. を追記。

>iOS 11 以降、アプリ名は最大 30 文字になるが代わりにサブタイトル項目が追加される。

アプリ名以外の文言を入れることを禁止される可能性がありそうですね。

# サブタイトル（30文字）
サブタイトルも最大30文字です。（申請、審査が必要）

<img width="375" alt="Image uploaded from iOS (3).jpg" src="https://qiita-image-store.s3.amazonaws.com/0/24308/59964c02-f28c-0f5c-d522-cfbcbb623470.jpeg">

↑このように一覧だと僅かにサブタイトルが見えることになります。

<img width="375" alt="Image uploaded from iOS (2).jpg" src="https://qiita-image-store.s3.amazonaws.com/0/24308/201c070f-657a-a876-29cc-6a69c4f484f9.jpeg">

↑詳細ページではもう少し表示されます。

# プロモーションテキスト（170文字）
Appleの説明によると
>プロモーション用テキストを使用すると、更新内容を提出することなく、App Store の訪問者に現在の App の機能について知らせることができます。このテキストは、iOS 11 以降を搭載した端末を使用するカスタマーに対して、App Store の説明の上に表示されます。

申請・審査なく、テキストが更新出来るようになるようです。
どこに表示されるかというと、
<img width="375" alt="Image uploaded from iOS (7).jpg" src="https://qiita-image-store.s3.amazonaws.com/0/24308/6a745d75-08a3-243a-0695-18f8de60be5c.jpeg">
↑のあたりに表示されることになり、タップするとこれまでの「概要」が表示されるようになります。


# 評価が引き継げるようになるらしい。
[次期iOS App Storeでは評価とレビューを維持できる――インクリメンタルなアップデートが可能に](http://jp.techcrunch.com/2017/06/10/20170607ios-app-developers-will-be-able-to-keep-app-store-ratings-when-releasing-an-update/)

という情報が出ていたが、どうやら本当のようです。

<img width="375" alt="Image uploaded from iOS (8).jpg" src="https://qiita-image-store.s3.amazonaws.com/0/24308/1788db27-b629-4a38-2151-e3974ce5e124.jpeg">

評価のない状態では、「デベロッパによりリセットされました」と表示されています。
2017年8月16日現時点では、iTunes Connectに継続orリセットの設定項目は見当たらないですね。

# 最後に
ぜひ今のうちに実機にiOS１１ betaを入れて確認しておくことをオススメします。
macOS での CVE-2017-1000117 対応メモ

## システムのgit

/usr/bin/gitの更新は面倒なので、brew で最新のgit入れよう。

```shell-session
$ brew update
$ brew upgrade
$ git --version
```

~~デフォルトの環境変数では、/usr/local/bin/の方が/usr/binより優先されるはずなので、brewで入れるだけで問題ないはず。~~

ちゃんと設定しないとだめな可能性あり。(自分の場合は、過去に設定したのかもしれなかった)

参考:
[macOSのgitをXcode Command Line Tools版からHomebrew版に乗り換えてみた](http://qiita.com/306_san/items/3cab1882e3035c646a65)


## XCode

内部にgitを持っている(XCode Commandline Tools?)が、使用するgitを選べるようにはなっていなさそうなので、
アップデートが来るまでは、使わないようにしよう。
(そもそも使っている人が居るのか…)


## rubymine / Android Studio 等、JetBrain製品

基本的には環境変数にあるgitを読むので、システムのgitを更新する(=brew)だけでいいはず。
もし、それで更新されないようなら、以下の設定項目を変更して最新のgitを指定しよう。

Preferences > Version Control > Git > Path to Git Executable: ____


## SourceTree

brewでシステムのgitを最新にして、

環境設定 > git のバージョン > システムのgitを使用する


## Github Desktop for Mac, Github for Mac

使用していないのでわからない。情報求む。
Android 開発で使う SDK やライブラリのバージョンとリリース時期

**2017/11/20追記**
表のメンテを[GitHubのリポジトリ](https://github.com/okaxaki/android-sdk-release-timing)で行うことにしました。
こちらも一緒に更新しようと思いますが、忘れた時はすみません。

# 動機
Android 開発で利用する SDKやライブラリは、バージョンの組み合わせによってよくトラブルが発生します。SDKもライブラリも基本的には上位互換性がありますが、正しく動くはずの組み合わせでも、動かないことがしばしば。Undocumentedな仕様変更やバグのため、ビルドがコケずアプリも起動するが、特定のタイミングでクラッシュ...なんて恐ろしいことも日常茶飯事です。

結局、どのバージョンの組み合わせがちゃんと動くのかはやってみて勝負なのですが、同時期にリリースされているコンポーネントの組み合わせは比較的よくテストされているようで問題は少なめです。そして利用者も多いから現象もググりやすい（気がします）。ということで Android 開発でよく利用する SDK とコンポーネントについて、最近のバージョンとリリース時期を表にしてみました。
[SDK Platform Tools]: https://developer.android.com/studio/releases/platform-tools.html
[SDK Build Tools]: https://developer.android.com/studio/releases/build-tools.html
[Android Plugin]: https://developer.android.com/studio/releases/gradle-plugin.html
[Google Services Plugin]: https://developers.google.com/android/guides/google-services-plugin
[Support Library]: https://developer.android.com/topic/libraries/support-library/revisions.html
[Play Services]: https://developers.google.com/android/guides/releases
[Firebase SDK]: https://firebase.google.com/support/release-notes/android
# 表
|リリース月|[SDK Platform Tools]|[SDK Build Tools]|[Android Plugin]|[Google Services Plugin]|[Support Library]|[Play Services]|[Firebase SDK]|
|:-:|:-:|:-:|:-:|:-:|:-:|:-:|:-:|
|Mar 2018|||||28.0.0 Alpha1|12.0.0|12.0.0|
|Feb 2018|||||27.1.0|||
|Dec 2017|27.0.1<br>27.0.0|27.0.3<br>27.0.2||||11.8.0|11.8.0|
|Nov 2017||27.0.1|3.0.1||27.0.2<br>27.0.1|11.6.2<br>11.6.0|11.6.2<br>11.6.0|
|Oct 2017|26.0.2|26.0.2|3.0.0||27.0.0|11.4.2|11.4.2|
|Sep 2017||||3.1.1||11.4.0|11.4.0<br>11.2.2|
|Aug 2017|||||26.0.2<br>26.0.1|11.2.2<br>11.2.0|11.2.0|
|Jul 2017||26.0.1|||26.0.0|11.0.4<br>|11.0.4|
|Jun 2017|26.0.0|26.0.0|2.3.3||26.0.0-beta2<br>25.4.0|11.0.2<br>11.0.1<br>11.0.0|11.0.2<br>11.0.0|
|May 2017|||2.3.2|3.1.0|26.0.0-beta1|10.2.6|10.2.6|
|Apr 2017|25.0.5|25.0.3|2.3.1|||10.2.4|10.2.4|
|Mar 2017|25.0.4||2.3.0||26.0.0-alpha1<br>25.3.1<br>25.3.0|10.2.1|10.2.1|
|Feb 2017|||||25.2.0|10.2.0|10.2.0|
|Jan 2017|||||25.1.1|||
|Dec 2016|25.0.3<br>25.0.2|25.0.2|2.2.3||25.1.0|||
|Nov 2016|25.0.1|25.0.1|||25.0.1|10.0.1<br>10.0.0|10.0.0|
|Oct 2016|25.0.0<br>24.0.4|25.0.0|2.2.2<br>2.2.1||25.0.0|9.8.0|9.8.0|
# 余談
- Google Play Services は Support Library に依存しています。Play Servicesのバージョンがほとんど変わらなくても、依存するSupport Library のバージョンが違う場合があるので要注意です。
  - Play Services 9.8.0 〜 10.2.4 -> Support Library 24.0.0 に依存
  - Play Services 10.2.6 以降 -> Support Library 25.2.0 に依存
MySQL5.6.xxでイベントログに警告が出力される

MySQL サーバ 5.6 系でサービス起動時等に以下のような警告メッセージがログに出力されるようになりました。

TIMESTAMP with implicit DEFAULT value is deprecated. Please use --explicit_defaults_for_timestamp server option (see documentation for more details).

![image](https://qiita-image-store.s3.amazonaws.com/0/196787/687d1a0c-1838-1d91-a6cc-0ec11d4d7e85.png)

【解決策】
この警告の意味と警告を出さないようにする方法は、
[MySQL - 5.6 系で TIMESTAMP 型デフォルト値警告！](http://www.mk-mode.com/octopress/2013/05/31/mysql-5-6-timestamp-default-warning/)
を参照してください。
「ポート3306は既に使用されています」

本現象は、MySQLインストール中に、
 「ポート3306は既に使用されています」
 というエラーが表示され、処理が中断されるというものです。
 
 早速、netstatコマンドで原因を調べてみます。
     　>netstat -n 3306
 
 するとすぐに原因がわかりました。
 3306ポートを使用しているプロセス（pid）が表示され、タスクマネージャーでpidを調べると犯人はRedmineでした。
 犯人が見つかったのでこれで一安心。
 但し、今回インストールするMySQLのポートは訳あって3306でなければならないため、Redmineで設定したポートを変える必要があります。ところが、その対応は思ったほど簡単ではなかったので、Redmineを一旦アンインストールすることにしました。
 
Redmineをアンインストールする前に、まずデータをバックアップしておく必要があるので、以下の方法でバックアップしました。
    　>cd Redmineのホーム\mysql\bin
    　>mysqldump -uroot -pパスワード bitnami_redmine > ファイル名.sql

　注）
　　・-uとユーザ名の間は空白なし
　　・-pとパスワードの間は空白なし
　　・データベース名はbitnami_redmine

Redmineデータをバックアップ後、引き続きRedmineをアンインストールし、MySQLのインストールをやり直すと（ポートの競合が解消されていて）無事完了しました。

---
【注意】
　Redmineアンインストール時に、データも削除するかを聞いてきますが、削除する場合は先程バックアップしたsqlファイルを別の場所に移動しておかないと折角のバックアップが一緒に消えてしまいます。
---
その後、Redmineをポート3307で再インストールします。データ復旧は簡単で、次の通りです。
    　>cd Redmineのホーム\mysql\bin
    　>mysql -uroot -pパスワード bitnami_redmine < ファイル名.sql

　注）ファイル名はバックアップしたファイルの名前
オブジェクトの属性「年齢」って何？

　これが、例えば「入社時の年齢」や「誕生日」であればわかりますが、「年齢」となると、それは_ある時点での数値_ですから随時計算が必要になりますね。しかもその「ある時点」とはいったい何でしょう？
 ウィキペディアのように、その人物を「照会した時点」で動的に計算するというイメージでしょうか。つまりいずれにしても仕様が曖昧ということですね。
 
 　人物オブジェクトの属性を考えるとき、安易に「年齢」を使用しますが、話が「永続化」に進むとき、それは慎重であるべきです。というのも（故人でなければ）「年齢」は時間に対して可変であり、また「誕生日」から導出できる情報だからです。
　 例えば、売上データで「合計金額」は商品の「単価」と「数量」から導出されるものであり、通常永続化すべき情報ではありません。何故なら、後日、単価や数量に変動があった場合、データベースを矛盾なく修正するには_大きなコストがかかる_<sup>(*注1)</sup>ことと同時にその対応自体がナンセンスだからです。
  
　 以上のことはデータベースの論理設計において正規化を行う上で吟味するとよいでしょう。
  
  
  ---
  *注1）データベースの関連個所を一斉に更新するバッチ処理が必要となり、またその実施タイミングを含め大きな課題となる。
Git に脆弱性があったようなのでバージョンをあげる（Mac版）

Gitに脆弱性があってバージョンアップしましょうという通知が来たのでメモ

MacでHomebrewの使用を前提としたの場合の手順

## とりあえず現状の Git のバージョンを確認する

~~~
$ git --version
~~~

## homebrewをインストールしていない場合

とりあえずhomebrewをインストールしてない場合はインストールする

## brewでgitをインストールしていない場合

gitをインストールする

~~~
$ brew install git
~~~

インストールが完了すると

~~~
/usr/local/Cellar/git/2.14.1: 1,485 files, 33.5MB
~~~

というような表示が出る

これでとりあえず homebrewにGitがインストールされる。
新しくインストールした場合は最新版なので次のアップデートをする必要はたぶんないと思う。

## brewにgitがインストールされている場合

### brewにインストールされたgitをアップデートする

~~~
$ brew upgrade git 
~~~

## パスを通す

/Users/ユーザー名/ の中に .bash_profile というファイルが無い場合は作る

.bash_profile に

~~~
export PATH="/usr/local/Cellar/git/2.14.1/bin:$PATH"
~~~

を追加して保存する。
※gitをインストール完了した時に出て来るパスにする

[PATHを通すとは？ (Mac OS X)](http://qiita.com/soarflat/items/09be6ab9cd91d366bf71)

## ターミナルを再起動

ターミナルを新規ウィンドウで開き

~~~
$ git --version
~~~

を叩いて gitのバージョンが新しくなってるかどうか確認する

## SouceTreeで使用するGitのバージョンを変更する

1. SourceTreeを起動
2. メニューの　　SourceTree > 環境設定
3. 上部タブ（？）でGitを選択
4. Gitのバージョンで「システムのGitを使用する」をクリック
5. homebrewでインストールしたgitのバージョンのディレクトリを選択する

[[Git] SourceTree で使用する Git を Homebrew でインストールした Git へ変更する方法（Mac）](https://memocarilog.info/webdesign/7855)
定期バックアップの方法（Windows７）

　定期バックアップのやり方には色々ありますが、その中で最も気に入ったのが差分のみコピーしてくれるrobocopyコマンドを使用した方法です。

１．robocopyコマンドの実行
　まずはrobocopyを体験してみましょう。

　最初に、手動でバックアップの練習を行います。
例として、Cドライブ直下のtempフォルダー配下を、Dドライブの外付けHDDにバックアップするものとします。
では、コマンドプロンプトを起動し、次のコマンドを実行してみてください。

    　>robocopy "C:\temp" "D:\backup\temp" /MIR /R:0 /W:0 /LOG:"C:\work\backup.log" /NP /NDL /TEE /XJD /XJF

　注）
　ログファイルは、Cドライブ直下のworkフォルダーとしていますので、workフォルダーがなければ事前に作成しておいてください。

　処理結果はログファイルで確認しましょう。
　（コマンドの詳細は、robocopyコマンドの説明を参照してください。）

２．2度目以降のバックアップ
　次に、robocopyの優秀性を味わうためにもう一度手動でバックアップしてみましょう。2回目は差分だけのコピーですので処理はすぐに終わります。
　尚、コマンドを実行する前に、バックアップ元（例、C:\temp配下）を少し変更（追加、削除等）しておいてください。（もちろん、変更がない状態でバックアップしても問題ありません。）

　では、変更ができたら、上記１と同じ操作をしてください。

３．バッチファイルの作成（定期スケジュールで使用）
　先ほどコマンドプロンプト画面で入力したコマンドをバッチファイル化します。

　【手順】
　　・テキストエディタを開き、先ほど実行したコマンドをコピーまたは入力します。
　　・次に、ファイルを名前を付けて保存します。そのときにファイル名は”～.bat”とします。
  　　（～の部分は自由な名前）
　　　ここでは、仮に"myBackup.bat"とし、"C:\work"に保存するものとします。

４．定期スケジュール化
　定期スケジュール化を行うとPCが自動でバックアップしてくれるのでとても便利です。手順は少し長くなりますが、一つ一つの操作は簡単ですので面倒がらずにやってみましょう。

　(1）「タスクの作成」画面の表示
　　・「スタートボタン」→「すべてのプログラム」→「管理ツール」→「タスクスケジューラ」をクリックすると、タスクスケジューラが起動
　　・「タスク スケジューラ ライブラリ」を右クリックし、「タスクの作成」をクリック

　(2）全般タブの設定
　　・「名前」はバックアップのわかりやすい名前を入力
　　・「ユーザーがログオンしているかどうかにかかわらず実行する」を選択
　　　　※Windowsにログオンしていなくてもバックアップが実行されます。
　　・「最上位の特権で実行する」をチェック
　　・画面最下部の「構成：」で「Windows７」を選択

　(3)トリガータブで時刻を設定
　　・新規ボタンをクリックし、「新しいトリガー」画面を表示
　　・「タスクの開始」は「スケジュールに従う」を選択
　　・「設定」は毎日を選択し、「開始」の時刻には17:00:00を入力。←指定した時間に実行されます。
　　・「間隔」は毎日なので、1日で良い。
　　・「有効」にチェックを入れる。

　(4)操作タブ
　　・新規ボタンをクリックし、「新しい操作」画面を表示
　　・「プログラム/スクリプト」は実行するバッチファイルのパスを入力
　　　　←今回は「C:\work\myBackup.bat」とします。
　　・「開始（オプション）」に実行するバッチファイルがあるフォルダのパスを入力
　　　　←今回は「C:\ｗork」とします。
　　　※このパスを指定しておかないと、バッチファイルが正常に起動できません。

　(5)条件タブ
　　そのままでよい

　(6)設定タブ
　　そのままでよい

　(7)タスクを実行するユーザ名とパスワードを入力
　　・「タスクの作成」画面でOKボタンをクリックするとユーザ名とパスワードの入力が督促されます。
　　・PCのユーザ名とパスワードを入力し、OKボタンをクリック

　以上で定期スケジュール化は完成です。
　タスクスケジューラ画面で手動で実行できますので、事前に確認しておくとよいでしょう。
　（方法）
　　・真ん中のウィンドウで自分が作成したタスクを選択
　　・一番右にある「操作」ウィンドウで「実行」をクリック
　すると実行できます。
　実行されたかどうかは、ログファイルの日時で確認できます。
robocopyコマンドの説明

１．コマンド形式
　robocopy バックアップ元 バックアップ先 /MIR /R:0 /W:0 /LOG:"C:\work\backup.log" /NP /NDL /TEE /XJD /XJF

　説明：
　　バックアップ元：バックアップするフォルダー名
 　　　　　　　　　　例）"C:\プロジェクト"
　　バックアップ先：自由なフォルダー階層＆出力フォルダー名
 　　　　　　　　　　例）"D:\バックアップ\プロジェクト"
　　/MIR       ：バックアップ元とバックアップ先をミラーリングします。
　　/R:n       ：ファイルコピーに失敗した場合に再度コピーを試す回数です。
　　/W:n       ：再試行する時の待ち時間（秒）です。
　　/LOG:”ログファイルのパス”　：指定したパスにファイル出力します。既にログファイルがある場合、上書きします。
　　/NP        ：バックアップ中の進行状況を表示しません。
　　/NDL       ：バックアップ結果として、ログファイルにファイルのみが出力されるようになります。
　　/TEE       ：バックアップの結果をコマンドプロンプトとログファイルの両方に出力します。
　　/XJD       ：フォルダの接合ポイントを除外します。必ずパラメータに指定してください！
　　/XJF       ：ファイルの接合ポイントを除外します。必ずパラメータに指定してください！
　　/FFT       ：バックアップ元と先のファイルの更新時間を比較する時、2秒の誤差を許します。

２．主な利点
　　・更新されたファイルだけをコピーするので、2回目以降のバックアップが速い。
　　・ミラーリング機能があるので、バックアップ元でファイルを削除すると、バックアップ先でも同じように削除してくれる。
　　・ファイルコピーに失敗した時でも再試行できる。
　　・ファイルやフォルダのアクセス権限もコピーできる。
　　・ファイルのパスが256文字を超えても大丈夫。
　　　（普通はファイルのパスが256文字を超える場合、バックアップできないことが多い。）
　　・Microsoftの純正コマンドなので安心。
kubernetesのingressでhttpsリクエストのみ許可する


公式に書いてあるんですけどメモとして
httpsリクエストのみ許可すると言っているので、httpでのリクエストが来ても404を返すようになります
実際はhttpへのアクセスが来たらhttpsにリダイレクトさせたいですよね、残念ながら現在のingress(GCE)の設定では出来ないようです
※リダイレクトさせるにはnginx ingressか何らかのwebサーバーでリダイレクトするようにしないといけません
僕はリダイレクトさせたいので結局httpを許可してフロントエンドで使用しているnginxでhttpsへリダイレクトさせました

使わなかったけど調べたのでとりあえず書いておきます

参考
[GitHub kubernetes/ingress#Blocking HTTP](https://github.com/kubernetes/ingress/tree/master/controllers/gce#blocking-http "kubernetes/ingress#Blocking HTTP")
[StackOverFlow: How to force SSL for Kubernetes Ingress on GKE](https://stackoverflow.com/questions/37001557/how-to-force-ssl-for-kubernetes-ingress-on-gke "StackOverFlow How to force SSL for Kubernetes Ingress on GKE")


## httpリクエストを許可しないingress.yamlの例

```yaml:ingress.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
  name: test
  annotations:
    kubernetes.io/ingress.allow-http: "false" # ここの行を追加するとhttps強制できる
spec:
  tls:
  # This assumes tls-secret exists.
  # To generate it run the make in this directory.
  - secretName: tls-secret
  backend:
    serviceName: echoheaders-https
    servicePort: 80
```


これで終了(書く必要あったか…)
以上
リモートデスクトップ接続

　Windowsには「リモートデスクトップ接続」という機能があって、外出先にPCを持ち出さなくても自宅にあるPCを外出先から使うことができます。しかしながら不用意にこの機能を使うと3389ポートを盗まれ、不正に利用される危険があります。
　ということで、私も最近までこの機能を使わないでいましたが、最近になって無性に使いたくなってきました。自宅内で使うので安全かというと、外出時と同じリスクなのです。でもとりあえず、しばらくぶりなのでやってみることにしました。

　すると、結論から言うとWindowsの**Home版**では、この機能は使えなくなっていました。昔はできたのになかなかうまくいかず、ファイアウォールを疑ったりと色々やってみたのですが、結局だめなのでガッカリでした。そしてTeamViewerとかいうフリーソフトを見つけてインストールしてもみましたが、何か違和感を感じてやめました。（できるだけ知らないソフトは入れない方針です。）
　そんなとき、Google Chromeのリモートデスクトップ接続機能があることを偶然知りました。これはChromeの拡張機能で、グーグルのアカウントさえ持っていれば簡単に環境を作れます。
（環境を作る詳細な操作は、検索すれば有志の方が沢山情報を載せてくれてますので、そちらを参照してください。）
ここでは、大まかな手順のみ備忘録として残します。

前提として、PCが2台（PC_OUT、PC_HOME）あるとします。
（スマホでもできるようです）
そして外出先PC（PC_OUT）からリモート接続で自宅PC（PC_HOME）を使うことを想定します。

この場合、まず両PCに
　①ブラウザーのGoogle Chromeをインストール
　②グーグルのアカウントを作成
　③Chromeの拡張機能「リモートデスクトップ」をインストール
　④「リモートデスクトップ」のショートカットを作成
を実施します。

次に、接続されるPC_HOMEで「リモートデスクトップ」を起動し、
　⑤マイコンピュータのリモート接続を有効にする
　⑥PIN番号を登録する（PIN番号はメモしておきます）
を行います。

後は、外出先でPC_OUTの「リモートデスクトップ」を起動し、
　⑦PC_HOMEのPIN番号を入力する
を行えばOKです。

　以降は、従来のWindowsで使用していたリモートデスクトップ接続のときと同じように、PC_HOMEをリモートから使用できます。
 
　使い終わったら外出先からPC_HOMEのシャットダウンすることもできますが、使いたいときは自宅でPC_HOMEの電源を入れることになります。もしくは、WOL（ウェイク・オン・ラン）で遠隔自動電源ONできればもっと便利です。
　いずれにしてもログインはリモート操作でできますので、プリンターと同じような感覚で、PCを部屋の隅っこに置いておくことができるので非常に便利です。
Openssl 1.1.0でもファイルを復号化する

[CircleCIでプライベートなファイルを暗号化してレポジトリ管理する - Qiita](http://qiita.com/tomoima525/items/dbeeb6d451304333b17d) を参考に、GitHubに暗号化したファイルを置いておいて、CircleCIでのビルドに利用していました。

今回、[あるAndroidアプリ](https://github.com/noboru-i/SlideViewer)をCircleCI 1.0から2.0に変更するにあたって詰まったのでメモ。

## 最初に結論

1.1より古いバージョンで暗号化したファイルを復号化するときは、 `-md md5` をつける必要があるっぽい。
（ホントは、最新バージョンで暗号化しなおした方がいいはずですが。。）

## 何をしようとしたか

CircleCI 2.0にするにあたって、[Language Guide: Android - CircleCI](https://circleci.com/docs/2.0/language-android/)を参考に、CircleCI側が用意しているDockerを利用しました。

そして、今までと同じように、暗号化しておいた `google-services.json` をCircleCI上で復号化させようとしました。

## 何が起こったか

```bash
#!/bin/bash -eo pipefail
openssl aes-256-cbc -k $DECRYPT_KEY -d -in app/encrypted_google-services.json -out app/google-services.json
bad decrypt
140487411111168:error:06065064:digital envelope routines:EVP_DecryptFinal_ex:bad decrypt:../crypto/evp/evp_enc.c:535:
Exited with code 1
```

（[CircleCIへのリンク](https://circleci.com/gh/noboru-i/SlideViewer/166)）

## 調査してみた

しばらく放置していたので、暗号化のキーを変えて忘れてた、とかファイルを差し替えてたけどブランチマージしてなかった、など考えていましたが、ローカルでは復号化できました。

で、調べていくうちにOpenSSLのバージョンが違うのでは？と思い至り、出力させてみると1.1.0fでした。
（[CircieCIへのリンク](https://circleci.com/gh/noboru-i/SlideViewer/171)）

成功しているmasterブランチでも出力させてみると、1.0.1fでした。
（[CircieCIへのリンク](https://circleci.com/gh/noboru-i/SlideViewer/173)）

マイナーバージョンが違っていました。

そこでstackoverflowを探してみると、 https://stackoverflow.com/a/39641378 の回答があり、それを実行してみました。

## 対応してみた

コマンド末尾に `-md md5` を追加し、下記のようにしました。

```
openssl aes-256-cbc -k $DECRYPT_KEY -d -in app/encrypted_google-services.json -out app/google-services.json -md md5
```

そうしたところ、復号化が成功し、ビルドにも成功しました。

（[CircieCIへのリンク](https://circleci.com/gh/noboru-i/SlideViewer/176)）

## なにが起こってたか

stackoverflowに書いてあるままですが、OpenSSL1.1以降でデフォルトのdigest？の方式がmd5 -> sha256に変わったらしいです。
そのため、sha256でチェック？しようとしててエラーになってたっぽいですね。
Square APIの公式ライブラリを使ってみよう

Square APIはHTTP/HTTPSで呼び出して使うものが多いですが、さらに使いやすくするために各プログラミング言語向けにライブラリを提供しています。square_connectという共通の名前なのですが、今回はRuby向けの利用法について紹介します。

## ライブラリのインストール

square_connectはRubygemsでインストールできます。

```
gem install square_connect
```

## セットアップ

まず最初にアクセストークンを含めたセットアップを行います。 `REPLACE_WITH_YOUR_ACCESS_TOKEN` は自分のアクセストークンに置き換えてください。

```
require 'square_connect'

access_token = 'REPLACE_WITH_YOUR_ACCESS_TOKEN'

SquareConnect.configure do |config|
  config.access_token = access_token
end
```

## 拠点情報を得る

今回はデモとして拠点情報を取得してみたいと思います。その場合、まずAPIのオブジェクトを作ります。

```
locations_api = SquareConnect::LocationsApi.new
```

そして呼び出します。

```
locations_response = locations_api.list_locations
```

ネットワーク接続やアクセストークンの問題があると `SquareConnect::ApiError` が発生します。

そして取得できた locations_response の中にある拠点一覧の中で利用できるもの（`capabilities` が `CREDIT_CARD_PROCESSING` になっているかどうかで判定できます）を探します。この状態になっている拠点は利用可能です。

```
location = locations_response.locations.detect do |l|
  l.capabilities.include?("CREDIT_CARD_PROCESSING")
end
```

もしそうした拠点がなかったならば、Squareのアクティベーションが必要になります。

```
if location.nil?
  raise "Activation required. 
  Visit https://squareup.com/activate to activate and begin taking payments."
end
```

後は取得できた拠点に対して処理を行うだけです。今回は単に出力します。

```
puts location
=> {:id=>"CBASEJqRSQmT1vVfMXar4RcrtCcgAQ", :name=>"ヤマモト 東京", :address=>{:address_line_1=>"中　１丁目", :locality=>"東京都", :administrative_district_level_1=>"国立市", :postal_code=>"186-0004", :country=>"JP"}, :timezone=>"Asia/Tokyo", :capabilities=>["CREDIT_CARD_PROCESSING"]}
```

----

Square Connectを使うことでSquare APIの利用が簡単になります。[Ruby](https://github.com/square/connect-ruby-sdk)の他、[PHP](https://github.com/square/connect-php-sdk)/[Java](https://github.com/square/connect-java-sdk)/[Python](https://github.com/square/connect-python-sdk)/[C#](https://github.com/square/connect-csharp-sdk)向けに提供されています。ぜひ自分たちのプロジェクトにあったものを選択してください。

[Square Connect API Documentation](https://docs.connect.squareup.com/articles/processing-payment-ruby)
Angular 製のアプリケーションを Google App Engine にデプロイする

# はじめに

* Angular 製のアプリケーションを Google App Engine にデプロイして動かしてみる
* ルーティングを利用するアプリケーションを想定し App Engine の設定を使ってどんなパスでも基本的に index.html で処理する

# 前提条件

* Angular 及び Angular CLI はインストール済みとする
* App Engine の SDK はインストール済みとする
  * https://cloud.google.com/appengine/downloads

# Angular アプリケーションの作成

```
ng new angular-gae-app
```

# App Engine のプロジェクトを作成

* Google Cloud Platform コンソールからプロジェクトを作成
* メニューから App Engine を選択してサービスを開始

# App Engine 用のファイルを用意

## 設定ファイルを用意

* 拡張子付きのリクエストに対しては dist 以下の実ファイルを返す
* それ以外のリクエストに対しては dist/index.html を返して Angular アプリケーション内のルーティングに任せる

```yaml:gae/app.yaml
runtime: go
api_version: go1

handlers:
- url: /(.*\.(gif|png|jpeg|jpg|css|js|ico))$
  static_files: dist/\1
  upload: dist/(.*)
- url: /(.*)
  static_files: dist/index.html
  upload: dist/index.html
```

## Goファイルを用意

* runtime を go にしているので .go ファイルがないとデプロイができない

```go:gae/app.go
package main

import "net/http"

func init() {
    http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
        // no op
    })
}
```

# Angular アプリケーションのビルド

```
ng build --prod --output-path=./gae/dist/
```

# 開発サーバーで動作確認

```
cd gae
goapp serve
```

* ブラウザで `http://localhost:8080/` にアクセスして動作確認

# App Engine 用のビルドスクリプトを npm スクリプトに追加

```json:package.json
{
  ...
  "scripts": {
  ...
    "build:gae": "ng build --prod --output-path=./gae/dist/"
```

# App Engine にデプロイ

```
cd gae
gcloud app deploy app.yaml --project [PROJECT_ID] -v [VERSION]
```

# Angular を提供するパスを変更したい場合

* Angular を提供するパスを変更したい場合はビルドコマンドと app.yaml を変更する
* 以下は `http://{HOST_NAME}/client/` で提供する場合

## ビルドコマンド

* `--base-href` オプションで js や css の参照先を指定する

```sh
ng build --prod --output-path=./gae/dist/ --base-href=/client/
```

## app.yaml

* `handlers.url` にパスを追加する

```yaml:gae/app.yaml
runtime: go
api_version: go1

handlers:
- url: /client/(.*\.(gif|png|jpeg|jpg|css|js|ico))$
  static_files: dist/\1
  upload: dist/(.*)
- url: /client/(.*)
  static_files: dist/index.html
  upload: dist/index.html
```

# 参考リンク

* https://stackoverflow.com/questions/39782506/deploying-basic-angular-2-app-to-google-app-engine
* https://github.com/googlearchive/appengine-angular-hello-world-python
全自動起動時間計測器を作ってみた

ビットトレードワンの赤外線リモコンを制御できるmruby-remoconとmruby-pingで起動時間計測器を作ってみました。

仕組みは[mruby-remoconで秋月電子のSSRをコントロール](http://qiita.com/yamori813/items/a7379d750518f174c0c4)できるようにして100VのOFF/ONを行い、その後にpingが通るまでの時間を計測します。

![boottime.png](https://qiita-image-store.s3.amazonaws.com/0/104066/0153bfc5-9b2c-95cd-d018-037bab38b37d.png)


mruby-pingはlibnetというライブラリを使っていてFreeBSDの場合pkgかportsからインストールが必要でした。

FreeBSD/amd64 10.3Rでmruby 1.2で実行しています。

```rb:boottime.rb
def ir(pat)
  t = Remocon.new()
  num = 0
  while num < 3 do
    t.send(pat)
    usleep 45*1000
    num = num + 1
  end
end

sig = [0x33, 0x89, 0x00]
ir(sig)
usleep 1000*1000
sig = [0x33, 0x09, 0x00]
ir(sig)

start_time = Time.now

pin = ARPPinger.new('re0')

pin.set_targets([ARGV[0]])

while pin.send_pings(1).count == 0 do
  sleep 1
end

p "#{Time.now - start_time}s"
```

mruby-remoconとmruby-pingともにroot権限が必要なのでsudoで実行します。

結果

```
microserver % sudo mruby boottime.rb 10.10.10.60
"29.830396s"
microserver % sudo mruby boottime.rb 10.10.10.65
"36.884279s"
```

最初がFreeBSD/MT7620で後の方がFreeBSD/RT5350です。
CVE-2017-1000117 対策のメモ

http://blog.recurity-labs.com/2017-08-10/scm-vulns
の対策のメモ

https://github.com/greymd/CVE-2017-1000117
で再現できるレポジトリを作ってる方がいたのでコードを読んでみた

勉強がてら自分でも上記のレポジトリでやってることを真似てみた
https://github.com/bells17/CVE-2017-1000117

ローカルの Mac では　brew で git をインストールしていたので
http://tokyo-engineer.com/git-cve-2017-1000117/
で紹介されてる手順と同じような感じで脆弱性を修正したバージョンの git をインストールできた

```
brew update
brew upgrade git
```

git のコードの変更は以下のあたりのよう

Github compare
https://github.com/git/git/compare/v2.14.0...v2.14.1

対象の commit
https://github.com/git/git/commit/a4f234bf9bd3fb11fb1608a507783d9412af27a9


---

脆弱性の影響度がどれくらいなのか気になったので調べてみた

例えば npm だと
https://github.com/npm/npm/issues/6700
で submodule は標準だとインストールされないようになっている

Gem も
http://qiita.com/orange-lion/items/03a699e6764317d6083f
で

```
submodules: true
```

をしないとインストールされないので直接被害受ける可能性は高くない？？
「正しい例外の使い方」の説明は難しいが、「間違った例外の使い方」の説明は簡単だ。

タイトルは釣りです。

[PHPの現場](http://php-genba.shin1x1.com/)で公開されている[PHPの例外](http://php-genba.shin1x1.com/1)　というPodcastを聞いていて、考えたこと。
**お断り: 以下は個人の見解であって、所属先の見解ではありません。**

聞けば聞くほど、「正しい例外の使い方」というのは難しいものだと思いました。

例外関連の話題となると例外とは何か？　とか、例外の正しい使い方は？　となるわけですが、大抵の場合は禅問答のような難しい話題になりがちです。
参考: [例外設計における大罪](https://www.slideshare.net/t_wada/exception-design-by-contract)

「だから例外は難しい。」で思考停止にるのではなく、「間違った例外の使い方」を避けるようにしていけば地雷を踏むことはないはずです。

# 自分で投げた例外を自分自身でcatchしてはいけない。

関数・メソッド内で投げた例外を自分自身でcatchするなら、例外を投げる必要はありません。
例外は自分自身（関数・メソッド）以外の誰に向かって投げるものです。

それは例外を `goto` の代わりに使っている証拠です。素直に `goto` を使いましょう。

# 例外が必ずおきることを前提にしてはいけない。
例外は**起きるかもしれない**ことを前提にした機構です。
必ず例外が起きることを前提としたコードは書いてはいけません。

```php:極端な例
try {
    while(true){
        // いつか例外をthrowする。はず…。
        foo();
    }
} catch (Exception $e) {
}
```

`foo()` の中で例外が発生しないと、無限ループになります。

# 理由を明記せずに、例外を握りつぶしてはいけない。
発生した例外を `catch` して、そのまま握りつぶすことがあります。

その理由が明記されていないと、その理由や、ただ単にコーディング漏れではないことを判断できません。
なぜその例外を握りつぶして良いかコメントに記述しましょう。


# （以下、おまけ）PHP組み込みExceptionの分類案
Podcast内で話題になっていた、組み込みExceptionの`LogicalException`と`RuntimeExceptoin`という大分類の違いをどうとらえるかです。

私としては「実行時にだけ発生するようなエラー」で分類してしまったのが失敗の元だったと考えます。
http://php.net/manual/ja/class.runtimeexception.php

例外（コンパイルエラーも含む）は常に実行時にしか発生しえないので、この分類自体あまり意味があるとは思えません。

こんな感じの分類を提案したいところです。
上記に従い、例外は「例外は自分自身（関数・メソッド）以外の誰に向かって投げるもの」とすれば、関数（メソッド）の呼び出し関係が切り口になります。

1. 呼び出し側に責任がある
    1. ランタイムが判断できる
        - 存在しないメソッド（関数）を呼び出した場合
        - 引数が足りない場合
        - 引数の型エラー（Type Mismatch）の場合
        - 0除算エラーの場合
        - アンダーフロー・オーバフロー発生の場合
        - 制御構造（`if`, `for`, `foreach`）への不正な引数。[^1]
    1. ランタイムが判断できない
        - 引数の値が（ビジネスロジックの観点で）不正の場合
1. 呼び出された側に責任が無い
    1. 実装側に責任がある
        - Assesionに引っかかった場合
    1. 実装側に責任が無い
        - メモリ不足が発生した場合
        - ファイルシステム関連のエラーが発生した場合
        - I/O（ディスク、ネットワーク、DB、外部API）エラーが発生した場合
        - シグナル割り込み発生の場合

それでは良い例外ライフを。

[^1]: ここでは、演算子は関数（メソッド）とみなしています。配列の参照 `[]` も演算子とみなしています。
armgを利用してRidgepoleでgeometry型が存在するスキーマのexportとapplyを実現する

[Rails / Active RecordでMySQLのgeometry型をサポートするライブラリを書いた](http://so-wh.at/entry/2017/08/11/134530)

ActiveRecordでもgeometry型がサポートされる世界がやってきました。

実は他にもRgeoを利用したgeometry型をサポートするadapterは存在しているのですが ([これ](https://github.com/stadia/activerecord-mysql2rgeo-adapter) とか)、個人的にはRidgepoleの作者が作ってくれていることに価値があります。

なぜなら私はRailsユーザではなくRidgepoleユーザだから。

もしかしたらRidgepoleでもgeometry型が標準サポートされる世界がやってくるかもしれません。
（ちなみに個人的感想ですが、「Railsで使う」というユースケース的には、ActiveRecordがgeometry型をサポートしないかぎりRidgepoleは標準サポートしなさそうという感じです）

## Ridgepoleとarmgを使ってスキーマをexportしてみる

これはwinebarrelさんの[エントリ](http://so-wh.at/entry/2017/08/11/134530)にもあるように `-r` オプションに `armg` を渡してやるだけでOKです

```sh
ridgepole -c database.yml -r armg --export -o Schemafile
```

## Ridgepoleとarmgを使ってスキーマをapplyしてみる

こちらは `-r armg` だけでは足りません。
( `Ridgepole::DSLParser::TableDefinition::TYPES`に `:geometry` が必要 )

なので、まず、以下のようなファイル `geometry.rb` を用意します。

```ruby
class Ridgepole::DSLParser
  class TableDefinition
    TYPES.push(:geometry) # この行はなくても良いけどなんとなく
    def geometry(*args)
      options = args.extract_options!
      column_names = args
      column_names.each {|name| column(name, :geometry, options) }
    end
  end
end
```

そして `geometry.rb` も `-r` オプションに渡してあげれば apply が可能になります。

```sh
ridgepole -c database.yml -r armg,/full/path/to/geometry --apply -f Schemafile
```

これで geometry型があるスキーマをRidgepoleで管理できます！便利！
SwiftプロジェクトでCommonCryptoをインクルードする[Xcode10では不要]

## Xcode10以降
この対応がなくてもCommonCryptoが使えるようになりました。

## Xcode9以前
1.対象のターゲットにこのシェルを追加

```bash
mkdir -p "${BUILT_PRODUCTS_DIR}/CommonCryptoModuleMap"
cat <<EOF > "${BUILT_PRODUCTS_DIR}/CommonCryptoModuleMap/module.modulemap"
module CommonCrypto [system] {
    header "${SDKROOT}/usr/include/CommonCrypto/CommonCrypto.h"
    export *
}
```

2.Import Pathsの設定にパスを追加

```
$(BUILT_PRODUCTS_DIR)/CommonCryptoModuleMap/module.modulemap
```

3.Importする

```swift
import CommonCrypto
```


シンプルにこれで終了。
ブログとかスタックオーバーフローを見てたらヘッダーファイルをコピーして、プロジェクトに含めるような回答が多かったけど
シェルでランタイムに応じたヘッダーをビルド時のtmpディレクトリにコピって参照する方が管理しなくていいので楽だとおもったのでメモ。
【Python】インストールしたはずのMuduleが「No module named '***'」になったときの解決策

環境：OSX　sierra 10.12.4
Python 3.6

```
pip install "module名"
```

でインストールしたはずのmoduleをインポートしようとしたところ、

```
import "module名"
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ModuleNotFoundError: No module named 'module名'
```

こうなりました。


調べてみた結果、インストールされた場所とPythonが見にいっている場所（？）が違う模様。

インストールされた場所
/usr/local/lib/python3.6/site-packages/

見にいっている場所
/Users/名前/anaconda/lib/python3.6/site-packages


インストールしたmoduleを丸ごとよっこらせと移動することで無事読み込めるようになりました。
AndroidStudio3.0 (IntelliJ)で、メソッド引数のヒント表示をOFFにする方法

####問題

Android Studio 3.0では、下記のようにメソッドの引数にその引数名がデフォルトで表示されている。IntelliJでは IntelliJ IDEA Preview 2016.3からの機能らしい。
これが、引数を変更したいときなどに引数を消すと、このヒントが消えるのに0.5秒くらいの時間がかかりタイピングがもたついてストレスになっていた。

![Slice 1.png](https://qiita-image-store.s3.amazonaws.com/0/51328/5db4daf5-19f3-6dbb-e161-d6644c9826ec.png)

####解決
調べた結果、下記の方法で設定OFFにできた。(Macで確認)

```
AndroidStudioの設定画面にて、
Settings → Editor → General → Appearance → Show parameter name hints
```

####参考
https://www.jetbrains.com/idea/whatsnew/#v2016-3-user-interface
OS起動時に php-fpm が起動しなくなった際に対応した箇所

# 概要
- yum update で php-fpm をアップデート後、OSを再起動したら php-fpmが起動しなくなってハマったのでメモ

# 環境
- centos7 で remi から php71-php-fpm を取得して使っていた環境

# 対象バージョン
- 更新前: php71-php-fpm-7.1.5-1.el7.remi.x86_64
- 更新後: php71-php-fpm-7.1.8-1.el7.remi.x86_64

# サービス起動時のエラー確認
- `systemctl -l status php71-php-fpm.service` 
- `ERROR: unable to bind listening socket for address '/var/run/php-fpm/php-fpm.sock': No such file or directory (2)` といったエラーが出る

# エラーメッセージにあるディレクトリを作成
- パッケージのアップデートでディレクトリが消された？
- `mkdir -p /var/run/php-fpm/`

# 再度サービスを起動
- `systemctl start php71-php-fpm.service`
- 正常化を確認

# OS再起動すると /var/run/php-fpm が消える
- http://qiita.com/suemoc/items/e29285e8e67263298f35 記事の落とし穴3にもハマっていたので対策
- `/etc/tmpfiles.d/php-fpm.conf` を作成

```
d /var/run/php-fpm 0755 nginx nginx
```

- OS再起動しても /var/run/php-fpm が消されないことを確認
バックエンドでUTCで管理してフロントでは現地時間で表示する方法

世界各国から利用されるサービスを作る際にUTC→現在位置のタイムゾーン変換ができると一気にグローバルなサービスになるよね？？ じゃあやっちゃいましょうー

# 前準備
### Google デベロッパー登録をする
https://console.developers.google.com

### デベロッパーサイトでAPIの認可
- Google Maps JavaScript API
- Google Maps Geolocation API
- Google Maps Time Zone API

を有効にする


#実際にやってみる
### GOOGLE_API_KEYのセット

`process.env.GOOGLE_API_KEY = 'AIz*****************';`
### Google Maps Geolocation APIを利用して現在位置の緯度経度取得

```js
function getGeolocation() {
    if (!'geolocation' in navigator) return { latitude: undefined, longitude: undefined };

    return new Promise((resolve, reject) => {
      navigator.geolocation.getCurrentPosition(
        (position) => resolve({
          latitude: position.coords.latitude,
          longitude: position.coords.longitude,
        }),
        (err) => reject(`ERROR(${err.code}): ${err.message}`)
      );
    });
  }
```
### Google Maps Time Zone APIを利用してタイムゾーンを取得する

緯度経度を入れてtimestampをセットして叩くとその箇所のタイムゾーンが手に入る

###### UTC → UnixTimestamp

```js
function utcToUnixTime(ts) {
  return Date.parse( ts.replace( /-/g, '/') ) / 1000;
}

utcToUnixTime("2017-10-14T00:00:00Z");
```
###### API押下
(JSのコードはまだ作っていないのでかけたら今後書きますー)
https://maps.googleapis.com/maps/api/timezone/json?location=48.5643009,136.627638&timestamp=1458000000&key=AIz*****************

```json
{
   "dstOffset" : 0,
   "rawOffset" : 36000,
   "status" : "OK",
   "timeZoneId" : "Asia/Vladivostok",
   "timeZoneName" : "Vladivostok Standard Time"
}
```

### mement.jsで変換！！
```js
moment(‘2017-08-10T12:34:56.008Z’).tz(“Asia/Vladivostok”).format()
```

# 参考
- [Moment Timezoneを使って日付をJSTに変換する - Qiita](http://qiita.com/masato/items/32464b45c78962cb5831)
Neural Network > link (2010) > How to choose the number of hidden layers and nodes in a feedforward neural network? > pruning | { Machine Mode | Regression Mode } | one hidden layer | between the size of the input and size of the output layers

```txt:動作環境
GeForce GTX 1070 (8GB)
ASRock Z170M Pro4S [Intel Z170chipset]
Ubuntu 16.04 LTS desktop amd64
TensorFlow v1.1.0
cuDNN v5.1 for Linux
CUDA v8.0
Python 3.5.2
IPython 6.0.0 -- An enhanced Interactive Python.
gcc (Ubuntu 5.4.0-6ubuntu1~16.04.4) 5.4.0 20160609
GNU bash, version 4.3.48(1)-release (x86_64-pc-linux-gnu)
```

https://stats.stackexchange.com/questions/181/how-to-choose-the-number-of-hidden-layers-and-nodes-in-a-feedforward-neural-netw

answered Aug 2 '10 at 2:20
doug
の目を引いた部分の抜粋。

### pruning

> one family of these works by pruning nodes based on (small) values of the weight vector after a certain number of training epochs--in other words, eliminating unnecessary/redundant nodes (more on this below).

weightが小さいものをpruningする。

### Machine Mode| Regression Mode

> Is your NN going running in Machine Mode or Regression Mode (the ML convention of using a term that is also used in statistics but assigning a different meaning to it is very confusing). Machine mode: returns a class label (e.g., "Premium Account"/"Basic Account"). Regression Mode returns a value (e.g., price).

### one hidden layer

> One issue within this subject on which there is a consensus is the performance difference from adding additional hidden layers: the situations in which performance improves with a second (or third, etc.) hidden layer are very few. One hidden layer is sufficient for the large majority of problems.

### number of nodes of the hidden layer

> So what about size of the hidden layer(s)--how many neurons? There are some empirically-derived rules-of-thumb, of these, the most commonly relied on is 'the optimal size of the hidden layer is usually between the size of the input and size of the output layers'. Jeff Heaton, author of Introduction to Neural Networks in Java offers a few more.

Regression Modeでも(between the size of the input and size of the output layers)で正しいか疑問に思う。

2017年8月16日現在、TensorFlowで精度を調べているものでは30x100x100のhidden layerが一番良い結果を出している（が希望の精度に達してはいない）。
5 input nodes, 6 output nodesに対して(5+6)/2nodesでは希望精度を出せるようには思わない。
艦これプレイ動画キャプチャ用スクリプト Linux用(bash+ffmpeg)

## このスクリプトを書いた経緯

Linux環境で艦これのプレイ動画を撮りたかったけど、やり方の解説が全然見つからない。
ffmpegの"x11grab"オプションを使えば撮れそうなので、ウィンドウの座標を取得してffmpegを実行するだけのスクリプトを書きました。

同じ事をやりたい人が居るかも知れないので、ココに置いときます。


## 環境
- arch Linux
- bash 4.4.12(1)
- xwininfo 1.1.3-1
- gawk 4.1.4
- ffmpeg 3.3.3


## 使い方

### $window_titleに対象ウィンドウの名前を設定する
1. 艦これを起動する
2. ターミナルを起動して、"xwininfo"(オプション無し)を実行
3. マウスカーソルが"＋"(十字マーク)になるので艦これのウィンドウをクリック
4. ターミナルにウィンドウの情報が表示されるので、Window id の後ろにある名前をコピーする
5. スクリプトの"window_title="の名前を書き換える

### Y座標のオフセットを設定する
xwininfoの座標はウィンドウタイトルバーのすぐ下、ブラウザ画面領域の左上隅の位置なので、タイトルバーと艦これの画面の間にアドレスバーやメニューバーなどがあるとその分画面の下が見切れます。
その場合は各種バーを非表示にするか、バーの幅(ピクセル数)をoffset=の行に指定して下さい。


### 実行
kancolle_movie_capture.sh [保存先ファイルパス]


## 注意点
- 各種エラー処理は全く入ってません
- ffmpegはの全く分からないのでパラメータは適当です

## ソース

```kancolle_movie_capture.sh
#!/bin/bash

# 艦これプレイ動画キャプチャ用スクリプト
# 使い方：kancolle_movie_capture.sh [保存先ファイルパス]

# ウィンドウ座標取得用関数
# xwininfoに指定するウィンドウの名前はxwininfoをオプション無しで実行して艦これの画面をクリックすれば確認できるので、
# $window_titleの値をその名前に編集する

get_position(){

  local window_title=$1

  xwininfo -name "${window_title}" |\
  gawk '
    BEGIN{
      FS = ":";
    }
    
    {
      num = gensub(" ","", "g", $2);
    }
    
    $1 ~ /Absolute upper-left X/{
      x = num;
    }
  
    $1 ~ /Absolute upper-left Y/{
      y = num;
      exit;
    }

    END{
      print(x, y);
    }
  '
}


# 録画用関数
# get_position()で取得した位置座標、サイズ、保存先ファイルのパスをffmpegに渡して実行する
# ffmegの設定は良く分からないので適当

rec(){
  local size=$1
  local pos_x=$2
  local pos_y=$3
  local file_path=$4
  
  ffmpeg \
    -video_size ${size} \
    -rtbufsize 100M \
    -r 24 \
    -draw_mouse 0 \
    -vsync passthrough \
    -f x11grab \
      -i :0.0+${pos_x},${pos_y} \
    -f alsa \
      -ac 2 \
      -i pulse \
        -acodec copy \
    -c:v libx264 \
      -crf 20 \
      -auto-alt-ref 0 \
      -y \
    ${file_path}
}


#Main 

file_path=$1
window_title="艦隊これくしょん -艦これ- - オンラインゲーム - DMM GAMES"
size="800x480"
offset=0

declare -a pos=($(get_position "${window_title}"))
pos[1]=$((${pos[1]} + ${offset}))
rec ${size} ${pos[0]} ${pos[1]} ${file_path}

exit
```
[CSS] チェックボックスをオリジナルデザインにカスタマイズする際のまとめ

cssのみでinput要素のcheckbox属性のデザインをカスタマイズする際の、方法と注意点などのまとめ。

## 要件
- cssで装飾できないcheckbox属性の代わりに、装飾用の要素（spanなど）を内包したlabelタグを使用して装飾を行う
- idやforの紐付けは必要ない
- 擬似クラス（CSS3）を使用するので、未対応のIE8以前のブラウザでは元のinput要素がそのまま表示される様にする

## 全体の要点
1. [HTML] labelタグでinput[type="checkbox"]タグと代替の要素（spanなど）をラッピングしてマークアップ
2. [CSS] [type="checkbox"]を非表示にしする
3. [CSS] 疑似属性／擬似クラス（befoer要素、checkedクラスなど）を用いてinputの代替要素（spanなど）にチェックボックスのデザインをCSSで作成する

### HTML

```html:html
<label class="c-checkbox">
    <input type="checkbox"></input>
    <span class="c-checkbox__input"></span><!-- 代替要素 -->
</label>
```
装飾をする為の要素、"span.c-checkbox__input"をlabelタグの中に内包します。

### CSS

```css:css
/* input要素の代替 */
.c-checkbox__input{
    position: relative;
    display: block;
    vertical-align: bottom;
    width: 20px;
    height: 20px;
}
.c-checkbox__input::before,
.c-checkbox__input::after{
    content: "";
    display: block;
    position: absolute;
    -webkit-box-sizing: border-box;
    box-sizing: border-box;
}

/* input要素の代替（外側） */
.c-checkbox__input::before{
    width: 20px;
    height: 20px;
    border: 1px solid #ccc;
    top: 0;
    left: 0;
}

/* 本来のinput[type="checkbox"]を非表示 */
.c-checkbox input[type="checkbox"]{
    display: none;
}

/* input要素の代替（外側）：チェック後 */
.c-checkbox input[type="checkbox"]:checked + .c-checkbox__input::before{
    background-color: #fcfcfc;
    border-radius: 4px;
}

/* input要素の代替（内側）：チェック後 */
.c-checkbox input[type="checkbox"]:checked + .c-checkbox__input::after{
    width: 10px;
    height: 10px;
    background-color: gray;
    border-radius: 50%;
    top: 5px;
    left: 5px;
}
```
本来のinput要素".c-checkbox input[type="checkbox"]"を非表示にし、
代替要素の"span.c-checkbox__input"に対してcssで装飾を行います。

チェックボックスを選択したか否かは、擬似クラス"checked"で判別しています。
そして、
"checked"されたinput要素に隣接( + )した代替要素にチェックのデザインを当てることでチェック済を表現します。

この為、htmlの構造では必ずinput要素と代替要素は隣接する形を崩さない様に気をつけてください。


## IE8以前のブラウザを考慮
メディアクエリがIE8以前のブラウザに対応していない点を利用し、
チェックボックスのデザインを設定しているstyleを、メディアクエリを使用して書き分けます。

```css:css
@media (min-width: 1px) {
  /* 〜デザインカスタマイズの記述（上記のcss）のみ、こちらに書く */
}
```

メディアクエリの記述で囲った部分はIE8以前のブラウザでは対応していない為、
無視されます。

したがって、
IE8以前のブラウザで閲覧した際は、ブラウザ固有のチェックボックスが表示されます。

## 参照記事
- http://nanndemoiikara.hatenablog.com/entry/2015/05/04/154954
- http://qiita.com/hashimoto-1202/items/e7f69718e526319f2e10
- https://levelf.jp/checkbox-css/
- https://lab.sonicmoov.com/markup/css/css-checkbox-radio/
- https://www.m-field.biz/archives/3200
- http://webdev.jp.net/checkbox-radio-custom-css/
- https://developer.mozilla.org/ja/docs/Web/HTML/Element/Input
- https://ja.stackoverflow.com/questions/17819/inputtype-checkbox-%E3%81%AB%E5%AF%BE%E3%81%97%E3%81%A6-before-after-%E7%96%91%E4%BC%BC%E8%A6%81%E7%B4%A0%E3%81%8C%E4%BD%BF%E3%81%88%E3%82%8B%E3%81%AE%E3%81%AFchrome%E3%81%A0%E3%81%91
単語の出現頻度をカウントする

**from collections import Counter**
a = input().split() #Thank you for your mail and your lectures
counter = **Counter(a)**
for word, cnt in **counter.most_common()**:
    print(word, cnt) #your 2
                     #Thank 1
                     #you 1
                     #for 1
                     #mail 1
                     #and 1
                     #lectures 1
シェルにおける（シングルクオート、ダブルクオート、バッククオート）の違い

変数をクオートで囲った時の挙動が異なります。

'（シングルクオート）: 文字列として出力 
"（ダブルクオート）: 変数の中身を文字列として出力
`（バッククオート）: 変数の中身をコマンドとして実行

```
$ ls
static templates app.py 
$ CMD="ls"
$ echo $CMD
ls
$ echo '$CMD'
$CMD
$ echo "$CMD"
ls
$ echo `$CMD`
static templates app.py
```
7Zipの別名保存のコマンドライン

7zipで複数の異なるzipファイルなのに、解凍すると同じファイル名になるために連続解凍が
難しかったのですが、GUIではできるので、コマンドラインでもできないか見つけてみました。

#やりかた
-ao{a|s|t|u}　(上書きモード)を使います。

オプション
a:すべて上書き
s:skip
t:謎
u:別名で保存
例
-aoa：既存ファイルをすべて上書きします。
-aou：別名にしながら解凍します。

#具体例
c:\tempにhogeとパスワードのかけてあるzipをすべて解凍するには
7za.exe x -aou -oc:\temp -phoge *.zip
from と to を指定して java.time.LocalDate の List を作る

`var` を避けるシリーズ.

```scala
import java.time.LocalDate

def dates(fromInclusive: LocalDate, toExclusive: LocalDate): Seq[LocalDate] = 
    Stream.iterate(fromInclusive)(_.plusDays(1)).takeWhile(_.compareTo(toExclusive) < 0)
```