OmniAICreator/Qiita-1.07M huggingface dataset:
BEM(MindBEMding)についてややこしくない説明をしてみた

[エイチームフィナジー アドベントカレンダー2019](https://qiita.com/advent-calendar/2019/ateam-finergy) の20日目 を担当させていただきます！

## 背景
直近の自分の役割として、主にマークアップ寄りの仕事が多いのですが、担当しているサービスで**SCSSをBEMというルールの設計方法で実装**しており、**BEMの知識や考え方をマスターする必要**があるため、備忘録を兼ねて記事を書いていきたいと思います。

そのため、自分と同じように **「BEMって？？」** という方や **「BEMをサッと理解したい！」** という方へ、理解度がアップする一助になれば、と思います！

## BEMについて
### BEMとは？
**CSSの記述方法論のこと** （CSSセレクタの「命名規則」）

BEMは、**Block**、**Element**、**Modifier**という3つの概念を理解できれば、
あとはclass名の命名規則に則って記述するだけの単純な方法です。

### 基本的な考え方
**MindBEMding**
MindBEMding（マインドベムディング）と呼ばれる命名法をベースとしている。
MindBEMding が BEM と呼ばれることが多い。
https://github.com/manabuyasuda/styleguide/blob/master/how-to-bem.md<br><br>

**シングルクラス**
「1つの要素に対して、1つのクラスを指定する」で設計している。

### BEMでの命名方法
以下の3つの概念で、それぞれを分けて考えていくことでCSSを設計･命名していく

① **Block**（ブロック）　　　　　 ： 大きい塊。Elementの親要素。
② **Element**（エレメント）　　　： Blockの子要素。
③ **Modifier**（モディファイア）　： BlockとElementの修飾。


## どうやって使うの？
**Block** と **Element** は、**アンダースコア2つで区切る**<br>
```
block__element
```

**Block** と **Modifier** は、**ハイフン2つで区切る**<br>
```
block--modifier
```

**Element** と **Modifier** も、**ハイフン2つで区切る**<br>
```
block__element--modifier
```


### ファイル例①
**「content」** というクラス を `Block`、その子要素 を `Element` とした場合、
以下の書き方ができます。

```html:index1.html
<div class="content">
  <h1 class="content__title">
    タイトル
  </h1>
  <p class="content__text">
    テキスト
  </p>
</div>
```

```scss:index1.scss
.content {
  width: 100%;

  &__title {
    font-size: 20px;
  }
  &__text {
    font-size: 14px;
  }
}
```

### ファイル例②
**「content」** というクラスを `Block`、その修飾 を `Modifier` とした場合、
以下の書き方ができます。

```html:index2.html
<div class="content--red">
  <h1 class="content__title">
    タイトル
  </h1>
  <p class="content__text">
    テキスト
  </p>
</div>
```

```scss:index2.scss
.content {
  width: 100%;

  &--red{
    background-color: red;
  }
  &__title {
    font-size: 20px;
  }
  &__text {
    font-size: 14px;
  }
}
```

### ファイル例③
**「content」** というクラス を `Block`、その子要素 を `Element` とし、その修飾 を `Modifier` とした場合、以下の書き方ができます。

```index3.html
<div class="content">
  <p class="content__text--red">
    赤いテキスト
  </p>
  <p class="content__text--blue">
    青いテキスト
  </p>
</div>
```

```scss:index3.scss
.content {
  width: 100%;

  &__text {
    font-size: 14px;

    &--red{
      color: red;
    }
    &--blue{
      color: blue;
    }
  }
}
```

## BEMを採用するメリットは？
### 複数人での開発がスムーズになる
BEMはルールがしっかりしているため、**複数の人が開発に関わり、長く運用されるプロジェクト**に特に向いていると言えます。
例として、**期間限定（キャンペーンページなど）サイトなどでも素早く開発を行える**ため、BEM を採用する価値はあります。

### 修正対応コストを低減できる
BEM は **プロジェクトの成長と共に既存ページが変化していくこと** を前提に考え出された手法です。内容に変更があった場合、その**修正対応コストをできるだけ低減**することができます。

### コードの再利用性が容易になる
BEM は **Webサイトを構成するパーツを独立して設計すること**ができるため、コードの再利用が容易になります。（再利用は、CSSだけでなくJavaScript にも及びます。）

などなど、、

## まとめ
いかがでしたでしょうか？
BEMで書いたコードを初めて見たときは、クラス名が長くてどうしても複雑そうに見えますが、シンプルで分かりやすく破綻しづらいコードを書くことができるようになります。

もしBEMが採用されているプロジェクトにアサインされているマークアップ担当の方は、ぜひ実際にBEMでコードを書いてみていただければと思います！

## 参考
* [MindBEMding](https://csswizardry.com/2013/01/mindbemding-getting-your-head-round-bem-syntax/)
* [一番詳しいCSS設計規則BEMのマニュアル](https://qiita.com/Takuan_Oishii/items/0f0d2c5dc33a9b2d9cb1)
* [BEM記法~HTMLコーディングする際のidやclassの命名規則~](https://www.slideshare.net/YounjuPark/bemhtmlidclass-81685592)
PostgreSQLのテーブルをINSERT文のテキストファイルにエクスポートする方法

環境移行等でデータベースを移行したい時が時々ありますよね。
コマンドベースで移行できればいいのですが、ネットワークやセキュリティの制約により新旧同時接続はできない。

そんな時、最初からテーブルをINSERT文としてエクスポート出来たら楽ちんでしょう。

では早速、そのコマンドを紹介します。

コチラ！！

```
$ pg_dump -U ユーザー名 --table=テーブル名 --data-only --column-inserts データベース名 > 出力ファイル名
```

これを使うと1テーブル1ファイルでINSERT文が作られます。
後は、a5mk2などで作成したDDLを実行した後に、今回作成したファイルのSQLを実行してあげれば、移行完了です。

以上。
[ Java ] enum（列挙型）

今回はjavaでenumを使う機会があったので調査してみた。

##宣言方法
enumはクラスと同じように定義する。

~~~java
enum Enum名 {
}
~~~

それを踏まえて果物を列挙してみる。すると以下のようになる。

~~~java
enum Fruit {
    APPLE,
    ORANGE,
    BANANA,
    GRAPE;   //セミコロンの位置がブロックの後ろだったり、無いサンプルもある
}
~~~

##値の使い方
enumの値はstaticフィールドへのアクセスと同様に、enum名.値でアクセスできる。

~~~java
System.out.println(Fruit.APLLE);
~~~

もちろんenum名型の変数を作って代入することも可能である。

~~~java
Fruit apple = Fruit.APPLE;
~~~

##enumが持つメソッド
enumは様々なメソッドをもっている。以下に代表的なものを紹介する。

###name()
enumの値の名称を文字列として返す。

~~~java
System.out.println(Fruit.APLLE.name());  //"APPLE"
~~~

###original()
enumで宣言された順番の番号を返す。APPLEは0番目なので0が返る。

~~~java
System.out.println(Fruit.APLLE.original());  //0
~~~
【laravel】 アクセサでリレーション先を呼び出す使い方について

## 言いたいこと

例えば

```php
public function getIsCategoryPublicAttribute()
{
	return $this->category->is_public;
}
```

リレーション先の情報を使ったアクセサ。
それを以下のように呼び出して、save前のモデルに使ってしまうとエラーになる。


```php
if (empty($record)) $record = new Article($param);

if ($record->is_category_public) {
	// エラー
} 
```

## 問題点はどちらか
1. **save前にアクセサを呼び出すこと**
2. **アクセサでリレーション先を呼び出すこと**

私はアクセサを動的プロパティと同様に扱いたいので、
つまり私の場合は**アクセサでリレーション先を呼び出すこと**が問題になる
（このコード自体は他にも問題はある）

## まとめ
アクセサの役割や使い方をよく考えるべきだと思った。
便利な機能である一方、使い方が整理されていないと思わぬところで設計が崩壊し始める。
MacでのFlutter開発環境構築(iOS&VSCode編)

#1.Flutterインストール

## 1.1 Flutterをダウンロード

FlutterのサイトからSDKをDLします。
https://flutter.dev/docs/get-started/install/macos

## 1.2 SDKを解凍

任意のディレクトリにSDLを解凍

```
$ cd ~/src
unzip ~/Downloads/flutter_macos_v1.9.1+hotfix.6-stable.zip
```

## 1.3 パスを通す

.bashrcにパスを追加。

```
$ vi ~/.bashrc
```
[PATH_TO_FLUTTER_GIT_DIRECTORY] はflutterがあるディレクトリを指定。
今回でいうとsrcになる

```
export PATH="$PATH:[PATH_TO_FLUTTER_GIT_DIRECTORY]/flutter/bin"
```

追加したらファイルを保存して変更を反映。

```
$ source ~/.bashrc
```

echoでパスが追加されたか確認。

```
$ echo $PATH
```

#2.iOS環境のセットアップ

## 2.1 xcodeをダウンロード

Appストからxcodeをインストール
※macで開発してる人ならほぼインストール済みかと。。

```
$ sudo xcode-select --switch /Applications/Xcode.app/Contents/Developer
$ sudo xcodebuild -runFirstLaunch
```

Xcodeライセンス契約に署名する
```
$ sudo xcodebuild -license
```


## 2.2 iOSシミュレーターのセットアップ

シミュレーターを起動します

```
open -a Simulator
```

メニューのHardwea>Deviceでデバイスを指定。


## 2.3 サンプルプロジェクトの作成と実行


任意の作業ディレクトリを作成

```
$ mkdir flutter_src
$ cd flutter_src
```

flutterコマンドを使ってプロジェクトを作成。

```

$ flutter create my_app
$ cd my_app
```

シミュレーターでアプリを起動

```
$ flutter run
```


## 2.3 CocoaPodsのインストール

CocoaPodsほiOSのアプリを作成する際のライブラリを管理してくれるもの。
これがないと管理が大変なので入れておきましょう。

```
$ sudo gem install cocoapods
$ pod setup

```

## 2.4 Xcodeのプロビジョニング

Runner > Signing & Capabilities でBubdke identifierを設定します

<img width="786" alt="スクリーンショット 2019-12-06 16.11.23.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/25785/47312932-ed39-a5f7-fbc8-19f44a9f8d9a.png">


変更したらアプリを起動。

```
$ flutter run
```



# 3. VSCodeのセットアップ

## 3.1 VSCodeをインストール

https://code.visualstudio.com/


## 3.2 日本語化

MARKETPLACE (左メニューの四角が4つあるやつ)で
「Japan」と入力すると　Japanese Language Pack が出てくるのでinstall

<img width="1108" alt="スクリーンショット 2019-12-06 16.32.54.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/25785/8de1a47c-22cb-ac82-77bd-66b49f6b40c5.png">



## 3.3 FlutterとDartパッケージをインストール
MARKETPLACE でflutterを検索してインストール

<img width="828" alt="スクリーンショット 2019-12-06 16.32.33.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/25785/f5f1325a-9935-7b12-3537-d8a8e77b2963.png">

これでDartも同時にインストールされます



以上で、開発環境は完成です
OracleDB の Function を使って複数行の SELECT 結果を取得する

# 概要
Function の戻り値に SELECT文での抽出結果を設定したときのメモ

# 環境
- Oracle Database 12c

# 詳細
まずは、抽出結果の型を定義します。

```sql
-- 抽出したいデータの項目をTYPEとして定義する
CREATE OR REPLACE TYPE TYPE_TEST AS OBJECT (
  ID    NUMBER(8,0)
  ,NAME VARCHAR2(256)
);
/

-- 定義したデータ項目のTYPEのTABLEを定義する
CREATE OR REPLACE TYPE TYPE_TEST_TABLE AS TABLE OF TYPE_TEST;
/
```
上記で定義した型を戻り値として、Function を作成していきます。
実際のクエリは以下のものになります。

```sql
CREATE OR REPLACE FUNCTION FETCH_TEST(
  vNAME IN VARCHAR2
) RETURN TYPE_TEST_TABLE PIPELINED
IS
  cursor cTest is 
    SELECT
      ROWNUM ID
      ,vNAME || ROWNUM NAME
    FROM dual 
    CONNECT BY ROWNUM <= 3
;
BEGIN
  for row in cTest loop
    PIPE ROW(
      TYPE_TEST(
        row.ID
        ,row.NAME
      ) 
    );
  end loop;
  return;
END;
/
```
呼び出すときは、以下のような感じで呼び出せます。

```sql
SELECT * FROM table(FETCH_TEST('Q'));
```

ポイントとしては、

- 戻り値の型を ```[戻り値にしたいTABLE型] PIPELINED``` で宣言する
- ```cursor``` の変数を宣言し、SELECT結果を格納する
- ```PIPE ROW ～```の部分でSELECT結果を定義した型で詰め替える

といったところだと思います。

# まとめ
集計データを作成する VIEW を定義しようと思うけど、集計期間は変数で指定できるようにしたい
と思ったときに使った内容でした。
（FUNCTION だとパラメータを渡せるため、条件を変えられるので）
GitHubのPRレビューに便利なhubコマンド

# GitHubのPRレビュー時の確認方法
## 今まで
GitHubでPull Requestが送られてきた時、
今までレビュー用にローカルで該当ブランチを確認するときは以下のようなコマンドで確認していました。

```console
$ git fetch
$ git checkout -b chozetsu_kakkoii_branch_name origin/chozetsu_kakkoii_branch_name
```

ですが、この `chozetsu_kakkoii_branch_name` を指定するのが地味に面倒。
また、どうせローカルのブランチ名もリモートのものに揃えるので、2回指定するのはダルいなと思っていました。


## hub 導入後
同じことをしたい時、 hub なら以下のような入力で一発です。

```console
$ hub checkout https://github.com/kakunin_shitai_PR_URL
```
`https://github.com/kakunin_shitai_PR_URL` には該当のPull RequestのURLをそのまま入れます。
これならいちいちブランチ名を持ってこなくても、URLのコピペで済むのですごく楽。
コマンドを実行すると、リモートのブランチ名と同じ名前でローカルブランチが作られてチェックアウトされます。

# 参考
hubコマンドの導入はMacだとHomebrewなどがお手軽です。
以下の記事などが参考になります。
[Github hubコマンドを使ってみる \- Qiita](https://qiita.com/shizuma/items/eb84c22805c55514e085)
[hubでGithubをちょっと便利に。 \- Qiita](https://qiita.com/ken0nek/items/ce50c6e5b59867c19f79)
【Unityアドカレ2019・冬】Soft Mask でいい感じにマスキングする

## はじめに

この記事は、Unityアセット冬のアドベントカレンダー 2019 Winter！ の、9日目の記事です。

[Unityアセット冬のアドベントカレンダー 2019 Winter！ – Unity公式 Asset Portal](http://assetstore.info/asset-advent-calendar-2019-winter/)

## Soft Mask のご紹介

[Soft Mask - Asset Store](https://assetstore.unity.com/packages/tools/gui/soft-mask-80667?utm_source=jppt&utm_medium20191209)

Soft Mask はUI要素をなめらかにマスキングするためのコンポーネントです。Unity標準の Mask や Mask Rect 2D と似ていますが、それらにはない利点を持っています。

- Mask Rect 2D と違ってマスクの回転をサポートしている。
- Mask と違って透明度をサポートしているので、なめらかなマスキングができる。

![スクリーンショット 2019-12-06 14.01.38.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159849/dfae6fa3-18bf-3075-128b-454aa88487c0.png)

エビフライは、[かわいいフリー素材集 いらすとや](https://www.irasutoya.com/) 様からお借りしました。

## 使い方

Soft Mask をアセットストアからインポートします。
![スクリーンショット 2019-12-06 14.04.04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159849/3b11fb9d-d0d1-2718-b1cc-a55ed6779722.png)

Soft Mask コンポーネントをゲームオブジェクトに追加します。
![スクリーンショット 2019-12-06 14.03.20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159849/a3d0127a-51f4-d99e-2a3a-04913ac713fc.png)


これだけです！非常に簡単。
![スクリーンショット 2019-12-06 15.33.16.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159849/bfd50901-7658-6ad2-39e0-011ae20b2075.png)

ヒエラルキーはこのようになります。
![スクリーンショット 2019-12-06 15.30.31.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159849/a20f0111-0158-d7a0-460a-54487644237a.png)

Unityの標準Maskコンポーネントを使ったことがある人ならお気づきでしょうが、追加するコンポーネントが変わっただけで、基本的な使い方は同じです。とても簡単！

## コンポーネント

コンポーネントのプロパティについて見ていきます。
![スクリーンショット 2019-12-06 15.32.23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159849/57d915e0-fd33-edf5-3f84-940529f5f209.png)

### Source

Graphic, Sprite, Textureから選択します。Graphicを選択した場合、アタッチされているImageコンポーネントかRawImageコンポーネントを参照してマスキングされます。SpriteまたはTextureは、画像を直接指定したいときに使用します。

### Separate Mask

通常はSoftMaskコンポーネントのアタッチされているゲームオブジェクトがマスクとして使われますが、このプロパティをセットした場合は、セットされたゲームオブジェクトをマスクとして使用します。

### Raycast Threshold

レイキャストを通す閾値を指定します。デフォルトは0で、領域のすべての入力を通します。これを0より大きくすることで、指定した値以上の不透明部分でしか入力を受け付けないようにすることができます。

### Invert Mask

マスクが反転できます。
![スクリーンショット 2019-12-06 14.16.05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159849/411f785c-a0bc-34a0-bb3d-e280bd71973d.png)

### Invert Outsides

マスクの外側を反転します。これをチェックすると、上の画像の外側の透明な部分が不透明になります。

### Mask Channel

画像のどの色成分をマスクとして使うか指定できます。普通はデフォルトのAlphaでいいと思いますが柔軟に設定できるようです。
![スクリーンショット 2019-12-06 15.55.31.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/159849/d521d2b7-1333-1800-445b-178a13e1dc63.png)

## スクリプティング

スクリプトは`SoftMasking`ネームスペースに全部入ってます。コメントも書いてありますし、小さいスクリプトなので、簡単に使えるでしょう。

```csharp
using SoftMasking;

public class Something : MonoBehaviour {
    void Start() {
        var mask = gameObject.GetComponent<SoftMask>();
        // なんかやる
    }
}
```

## おわりに

以上、ソフトなマスクを使いたい人におすすめのアセット紹介でした！

紹介し切れていない部分も多いので、興味のある方はアセットストアでチェックしてみてください！
[Soft Mask - Asset Store](https://assetstore.unity.com/packages/tools/gui/soft-mask-80667?utm_source=jppt&utm_medium20191209)

読んでいただき、ありがとうございました。
Swift：HTMLエンティティを含む文字列をデコードする方法

# はじめに
APIなどを介して取得した`< ⇒ &lt;`や`& ⇒ &amp;`のようなHTMLの[エンティティ参照（Entity References）](http://www.shurey.com/js/labo/character.html)を含むStringを普通の文字列にデコードする必要があったため調べたところ，[IBM-Swift/swift-html-entities](https://github.com/IBM-Swift/swift-html-entities)や[alexaubry/HTMLString](https://github.com/alexaubry/HTMLString/tree/master/Sources/HTMLString)などのオープンソースライブラリを見つけた．しかし，本当にこんなに大掛かりな仕掛けが必要なのか疑問に思った．そこで，例のごとくStack Overflowを漁ったところ，`NSAttributeString`を使って一旦`WebKit`を噛ませればいい感じになるというのを見つけた．見つけたソースをExtension化して使いやすくしたものを備忘録しておく．

# ソース

```swift
extension String {
    var htmlDecoded: String {
        guard let data = self.data(using: .utf8) else {
            return self
        }
        let options: [NSAttributedString.DocumentReadingOptionKey : Any] = [
            .documentType : NSAttributedString.DocumentType.html,
            .characterEncoding : String.Encoding.utf8.rawValue
        ]
        guard let attrStr = try? NSAttributedString(data: data, options: options, documentAttributes: nil) else {
            return self
        }
        return attrStr.string
    }
}

```

```swift
let test = "&lt;&amp;&gt;"
Swift.print(test.htmlDecoded) // ⇒ <&>
```

# 参考
- [How do I decode HTML entities in swift?](https://stackoverflow.com/questions/25607247/how-do-i-decode-html-entities-in-swift)
- [NSAttributedString by example](https://www.hackingwithswift.com/articles/113/nsattributedstring-by-example)
エスケープされたJSON文字列からJSON dataに変換する

`JSON.parse`を2回施す。

```js
raw = '"{\\"id\\":\\"123\\"}"'
once = JSON.parse(raw)
twice = JSON.parse(once)
console.log(twice.id) // => "123"
```
> 
https://stackoverflow.com/questions/25721164/how-to-fix-an-escaped-json-string-javascript
【意外とハマる??】Reactで、無限ループに気をつけましょう

例えば、こんなコンポーネント。

```react:App.js
const App = () => {
  const [count, setCount] = useState(0)
  return (
    <>
      <button onClick={setCount(count + 1)}>+1</button>
      {count}
    </>
  )
}

export default App
```
チュートリアルなどでよくある、数字を足していくやつですね。

実は、これ`無限ループ`が起きてしまっているんです。

実際にこれを動かしてみると、
`Too many re-renders. React limits the number of renders to prevent an infinite loop.(直訳: 再レンダリングが多すぎます。 Reactは、無限ループを防ぐためにレンダリングの数を制限します。)`と怒られます。

原因は、onClick内のこの書き方です。

```react:
onClick={setCount(count + 1)}
```
この書き方の場合、onClickでsetCountは呼ばれず、コンポーネントがrenderされたタイミングでsetCountが呼ばれます。

例えば、

```react
onClick={console.log("hello")}
```
とやると、renderされたタイミングで`hello`と表示されるのが確認できると思います。

このようなことから、

`setState`されたタイミングで`render`されるreactコンポーネントの性質上、
render => setState => render => setState => render ....
と無限ループが起きてしまうのです。

これを防ぐためにいくつか方法がありますが、
僕はアロー関数をよく使います。

```react:
onClick={() => setCount(count + 1)}
```

以上です。
Visual Studio 2019 でDeleteやBackspaceなどが使えなくなった時の対処法

## 背景
Visual Studio 2019でC++のコードをかきかいしているとき、
以下のキーが効かなくなった。（汗）
・Delete
・backspace
・Ctrl + v

しかし、動くキーもあった。
・Ctrl + c
・Ctrl + s

初めはすぐ直るだろうとか、安易に思って1週間。
もう我慢の限界がきた。
キーボードを変えたりしたができなかった。
ググってみても見つからなかったので、
ここでシェアしたいとおもいます。

## 解決方法

1. メニューの[ツール]→[オプション]を選択
2. オプション内の[環境]を選択
3. 次の追加キーボードマップ スキームを適応の[リセット]をクリック
4. 実行しますか？　という問いに[はい]を選択

以下、イメージ図。
その１
![無題zx.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/503403/929355c1-ea15-8967-c52c-aa7fbc4ce926.png)
その２
![無題xszdx.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/503403/7109d7ef-5460-32c0-0398-2c6154048c51.png)
その３
![無題fgasd.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/503403/89e07551-92c4-bb7a-d722-605e38ed134e.png)
Re:ゼロから始めるCSS設計

この記事は ウェブクルー Advent Calendar 2019 8日目の記事です。
昨日は@hiro_moriさんの「古い組織にデザイン思考を浸透させる手順」でした。

#概要
弊社が運営するwebサービスの大型改修案件に伴い、改めてCSSの管理と設計について学び直したので、そのことについて書きます。
~~(内容は概ね[Web制作者のためのCSS設計の教科書](https://book.impress.co.jp/books/1113101128)の要約です）~~

#CSSを管理する上での問題点
中〜大規模サイトを長期に渡って運用していると、必ずと言っていい程出てくる「CSSが煩雑になる問題」。
最初は綺麗に整頓された記述でも、後からコンテンツの追加やサイト改修によって膨大な記述&ファイル数になったり、
似た記述が重複したり、修正によって意図しない箇所に影響が出たり、詳細度が高すぎて、最終奥義「！important」を使わざるをえなくなったり...
運営期間が長ければ長いサイトほど、担当者はこれらの問題に頭を抱えているのではないかと思います。
![Qiita用.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/538617/bf683e44-716b-778b-ba58-6c8ea112e142.png)



#良いCSS設計とは？
Googleエンジニアのフィリップ・ウォルトン氏の[CSS Architecture](https://philipwalton.com/articles/css-architecture/)によると、良いCSS設計は下記の通りだそうです。
####予測しやすい
→制作者が思ったとおりのイメージ(表示)になっているか
→意図しない動き(影響)はないか
####再利用しやすい
→汎用的に使えるモジュールやコンポーネント
→それぞれが独立しており、様々な箇所で使い回すことができる
####保守しやすい
→後から機能を追加した際に、既存のルールを壊さない
####拡張しやすい
→サイト規模を拡大し、コードが複雑になっても追加修正がしやすいか
→(サイト規模が増える=担当者が増える)修正者が増えても、メンテナンスしやすいかどうか

#目指すべきところ
上記を踏まえ、理想としては、
・ユニークでわかりやすい命名規則（他に影響しない）
・なるべくhtml構造に依存しない
・どの場所に入れても使いやすい
・CSSの上書きは最小限に
・似たパーツは共通化

のような設計にできたら良さそうだなと思いました。

#有名なCSS設計手法
CSS設計の有名なものとしては下記
・OOCSS
・SMACSS
・BEM
・MCSS
などがあり、詳しい説明はドキュメントや記事が多く存在するので割愛しますが
今回、上記のいいとこ取りをしたFLOCSSを採用しました。
（FLOCSSの手法を取り入れることで、上記目指すべきところ、がある程度叶いそうな感じがしました）
日本語のドキュメントがあり、採用している企業(webサービス)も多く、検索すると記事が多くあるのも採用理由の１つです。

#FLOCCSの概要
webページを
 `Foundation`
 `Layout`
 `Object`
 　┝`Component`
 　┝`Project`
 　┗`Utility`
というレイヤーに分類して管理、記述するという設計手法です。
SASSを使うことによって、上記と同じようなディレクトリ構造にし、common.scssなどにまとめてコンパイルすることによって、モジュールごとに管理でき、読み込むCSSは１つにすることができます。
また、オリジナルルールとして、ページ単位の独自のCSSを記述する`Page`というディレクトリとCSSファイルも用意し、原則として、２つのCSSファイルを読み込むという設計にしました（下記参照）
<font color="FireBrick">(19.12.10 追記　すみません、下記画像の @mixin は@import の間違いです)</font>
![Qiita用2.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/538617/be61514b-fa4f-8c42-eaba-cc37decaaea5.png)

なお、改修案件は現在進行中のため、CSSがこれだけ少なくなった、メンテナンス性が上がった、などの結果については今後に期待です。悪しからず。

現時点での肌感としては、導入のための学習コストはそれなりにかかりますし、初期の策定がかなり大変ですが、
再利用性が高いので、コードを書けば書くほど後から楽になっていくのではないかなと思っています。
ただ、後々担当者が変わった際に、全体の設計を理解してもらう必要があるかなと感じています。

####提唱者の谷拓樹さんのドキュメント
[FLOCSS公式ドキュメント](https://github.com/hiloki/flocss)
[柴犬でもわかるFLOCSS](https://mamehiko.booth.pm/items/1033385)
[みんなが知らないような知ってるようなFLOCSS](https://hiloki.github.io/s/flocss-layout/)

####参考記事
[各CSS設計手法を取り入れる上でのメリット・デメリットをまとめてみた](https://qiita.com/nezurika/items/a964e21d3596b0ee4c9a)
[CSS設計を勉強するならまずこれを見たら良いかも](https://qiita.com/sueshin/items/c80151181d06649e2ff6)
[脱・CSS無法地帯。FLOCSSで指針のある設計を。](https://qiita.com/sueshin/items/dcbaf3d8a0adb6b087db)
[FLOCSSを使ってCSSファイルを20,000行から9,000行にした話](https://qiita.com/Atsss/items/4f9d98fb1d0546539c09)
[FLOCSSを使ったCSS設計での悩みどころと解決案](https://qiita.com/uggds/items/d904b2f9a103c37a25fa)
[【CSS設計】メイクアップなマークアップ♡FLOCSSでどんなときでもキレイにきまるコーディング術!](https://geechs-magazine.com/tag/lifehack/20161219_3)
[CSS設計の目的とFLOCSSの概要 – FLOCSSで始めるCSS設計](https://www.to-r.net/media/flocss-01/)

明日は @wchikarusato さんです。よろしくお願いいたします！
Qlik のピボットテーブルのソート

# Qlikのピボットテーブルのソートの仕組みについて
初めての投稿ですが、今回はQlikのピボットテーブルのソートについてです。

Qlikで以下のようなピボットテーブルを作成したとき
※画像はQlikViewですが、Qlik Senseでも同じです
![WS0000.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/546656/ebcdea1b-5a63-27f0-5663-ce516347460c.png)

各支店毎にカテゴリの売上台数の降順にソートの設定がしたいことありませんか？

支店毎、カテゴリ毎に売上台数の昇順なので、プロパティのソートタブで下記の
ように設定してみました。
![WS0001.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/546656/7a6bc227-09a3-ab26-f860-3b674ad95967.png)

これで良さそうな感じですが結果は下記になりました。
![WS0002.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/546656/680c79dc-344a-1ddd-dc5a-50956d40298f.png)

希望通りにソートされないので、どういう順番なのか確認したところ、下記と同じ結果になりました。
![WS0003.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/546656/92d9ebaa-15f5-c12a-6d85-4a006d425b14.png)

上記のようにQlikではソート定義の時にAggr関数で項目を指定しても、指定した項目ごとにソートされないことが確認できました。
※今回の場合は、第2軸でsumした結果がソート順になります。

Qlikで支店毎にカテゴリの売上台数の降順にするには、支店毎のカテゴリがそれぞれ別々の値として認識させる必要があります。
※東京の車と大阪の車は別々の値として判断させる必要があります。
![WS0007.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/546656/7ceca07e-12fc-1020-3451-e0157764ff21.png)

方法としては見た目の値とは別に内部値をもたせることができるDual値を使った方法になります。
![WS0006.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/546656/4caac611-4ee0-a6d8-3166-ee2107f7e6d6.png)

軸タブでカテゴリをDual関数を使用した計算軸に設定しています。
表示上はカテゴリの値ですが、内部的には支店、カテゴリ毎の売上台数をsumした結果を保持しています。

Dual関数を使用した計算軸に対して、ソートで「sum(売上台数)」の数式で降順を定義すると下記のような結果になります。
![WS0007.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/546656/fe579fda-ec22-a0e1-84ff-249c6cec35b6.png)

ピボットテーブルで直接カテゴリから車を選択した場合、Dual関数を使用してない場合は、各支店の車で絞り込まれますが、Dual関数を使用した場合は選択した支店の車だけになるのでご注意ください
[Linux][初期設定] 目次

#目次
[インストール＆アンインストール](https://qiita.com/osorezugoing/items/720eebad62cb488b458f)

[システム](https://qiita.com/osorezugoing/items/1b7980de52b8e07c9aad)

[開発環境](https://qiita.com/osorezugoing/items/f85f27df9223aed641cd)

[バックアップ＆リカバリー](https://qiita.com/osorezugoing/items/d91beaa5745766bb93c8)
macOS CatalinaでOBS（ウインドウキャプチャ）を使う

# 概要

CatalinaにアップデートしたMacでOBSを使ったらウインドウキャプチャや画面キャプチャが使えなくなったのでメモ

# コンソールから開く

直接アプリアイコンから開くと動かないので、コンソールから開きます

```
open /Applications/OBS.app/Contents/MacOS/OBS --args -picture
```

参考：
https://obsproject.com/forum/threads/macos-10-15-catalina-support-status.111343/

# Macの環境設定を変更

このままだと、OBSでウインドウキャプチャや画面キャプチャが使えないので利用許可の設定を行う

* 「システム環境設定」 -> 「セキュリティとプライバシー」 を開いて、「プライバシー」タブを選択
* 左メニューから画面収録を選択して、ターミナルにチェックを入れる

<img width="678" alt="スクリーンショット 2019-12-06 15.11.27.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/93260/9cdc5e1d-2ed5-fbe3-e828-4bcfac9336c8.png">

これで今まで通り使えました👏
Reactでvideo.jsライブラリを利用

こんにちは。
先週末は奥多摩にソロキャンプ△に出かけました。streampackチームのminsuです。

#概要
Reactで動画プレイヤーのJSライブラリvideo.jsを実装してみます。
https://github.com/videojs/video.js

今回の環境はこちらの記事の環境を流用しています。
https://qiita.com/minsu/items/0ccbafff460e72b13d44

#インストール
まずはnpm,yarnでvideo.jsパッケージを追加します。 

```
$ yarn add video.js
```

#コーディング
Reactでの実装方法は video.js document に記載されているので、これを参考にして次のように実装してみます。
https://docs.videojs.com/tutorial-react.html

次のようにjsファイルを作成します。

```
app/javascript/components
  ├ VideoPlayer.js
  └ VideoTest.js
```

VideoPlayer.js

```js
import React from "react"
import videojs from 'video.js'
import "video.js/dist/video-js.css"

export default class VideoPlayer extends React.Component {
  componentDidMount() {
    // instantiate Video.js
    this.player = videojs(this.videoNode, this.props.options, function onPlayerReady() {
      console.log('onPlayerReady', this)
    });
  }

  componentWillUnmount() {
    if (this.player) {
      this.player.dispose()
    }
  }

  render() {
    return (
      <div>	
        <div data-vjs-player>
          <video ref={ node => this.videoNode = node } className="video-js"></video>
        </div>
      </div>
    )
  }
}
```
video.jsのpluginsを利用する場合は
componentDidMount()onPlayerReady(){}内で適応すればいいようです。

```js

export default class VideoPlayer extends React.Component {
  componentDidMount() {
  this.player = videojs(this.videoNode, this.props.options, function onPlayerReady() {
    console.log('onPlayerReady', this)
    const player = this
    player.someplugin({
      ~~~
    })
  })
}
```

VideoTest.js

```js
import React from "react"
import VideoPlayer from './VideoPlayer'

export default class VideoTest extends React.Component {
  render(){
    const videoJsOptions = {
      autoplay: true,
      controls: true,
      sources: [{
        src: 'http://www.example.com/path/to/video.mp4',
        type: 'video/mp4'
      }]
    }
    
    return(
      <div>
        <h1>test video</h1>
        <VideoPlayer 
          options={videoJsOptions}
        />
      </div>
    )
  }
}
```

実際に表示させてみます。

test.html.haml

```haml
= react_component 'VideoTest'
```

#動作確認
![スクリーンショット 2019-12-06 15.04.07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/399734/d15bf944-4452-c9ef-397a-18439d6a1b3a.png)

#参考
https://github.com/videojs/video.js
https://docs.videojs.com/tutorial-react.html

#利用動画
（c）copyright 2008、Blender Foundation / www.bigbuckbunny.org
強化学習３０　Colaboratory+Acrobot+ChainerRL

強化学習２８まで終了していることが前提です。
標準DQNでAcrobotを学習しようとするとうまく行きません。
最初はうまく学習できても、途中からおかしくなります。
いろいろといじりまわした結果、reward-scale-factorがややこしくなる原因のようです。
reward-scale-factorは報酬を正規化する係数のようですが、1.0にします。
つまり何もしないということのようですが。。。

ノートブックは、chokozainerRLに入れておきました。
acrobot_dqn_chokozainer.ipynb
です。
ゲーム開発で役立つサイトまとめ 

[PONOS Advent Calendar 2019](https://qiita.com/advent-calendar/2019/ponos) の 7 日目の記事です。

技術系の情報をウェブで求めると困らない程度に多くの記事が見つかりますが、ゲーム開発の技術情報はニッチなためかウェブで見つけられるものがまだまだ少ない気がしています。ないわけではないですが、特にゲーム開発系以外から移ってきた人は案外知らなかったりします。

そこで、個人的な忘備録も兼ねてまとめておきます。



# Gamasutra[^gamasutra]

https://www.gamasutra.com/

1997 年からある[^gamasutra-founded]古参サイト。
ゲーム開発でもプログラムの話だけではなく、アート、音楽、ビジネスなど全般に渡った記事があります。カテゴリ分けは Programming, Art, Audio, Design, Production, Biz/Markeging となっていて、ゲーム系の求人情報ページもあったりします。
Post mortem というプロジェクトの事後評価をする記事が非定期にあって、これはみんな大好きなあるある話や失敗ネタです。実際参考にはなるんですが、最近はこの記事は減っている感じがします。 

[^gamasutra]: どうしてこんな名前なんでしょうね。カーマスートラ(インドの性典)にかけてるんでしょうけど。
[^gamasutra-founded]: https://en.wikipedia.org/wiki/Gamasutra

# gamedev.net

https://gamedev.net/

1999 年からある[^2]こちらも古参のサイト。
Gamasutra 同様、記事は全般にわたっていますが技術寄りな記事が多い印象です。

[^2]: https://en.wikipedia.org/wiki/GameDev.net

# CEDiL

https://cedil.cesa.or.jp/

CEDEC での講演資料をまとめたサイト。日本語でまとまっているのはここが一番でしょう。会員登録は必要ですが無料[^cedil-free]で閲覧できます。

[^cedil-free]: GDC Vault や ACM Digital Library の値段を考えるととてもありがたいことです。

# GDC Vault

https://www.gdcvault.com/

GDC での講演資料をまとめたサイト。こちらは講演のビデオもあって、資料を見るだけよりは理解が進みやすいかもしれません。ただし、有料(550USD/1Year)です。結構高い。

# ACM SIGGRAPH Digital Library

https://dl.acm.org/sig.cfm?id=SP932

ACM の CG 分科会の論文を検索できるサイト。なぜこれをここで紹介しているかというと、SIGGRAPH で発表された内容は数年後に(PC)ゲームで採用されていることがあります[^cg-in-game]。要チェック。

[^cg-in-game]: Non-Photorealistic Rendering とか Subsurface Scattering はインパクトありました。

# Unity Blog

https://blogs.unity3d.com/jp/

ゲームエンジン Unity の公式ブログ。Unity 限定の話はさておき、一般的な技術の話や応用できそうな話もあるので見ておくとよいです。

# Game Developer Magazine Archive

https://www.gdcvault.com/gdmag

1994 年から 2013 年まで出版されていた Game Developer という雑誌のデジタルアーカイブです。前述の GDC Vault の中にあります。
内容的には GAMASUTRA と実は変わりません[^cmp]。Post morterm はこちらにもあって、陳腐化する内容でもないですから参考にするといいでしょう。プログラムなどの記事は過去の技術なんでそのまま利用はできないでしょうが、もしかするとスマホなど(PC や据え置きゲーム機と比較して)低スペックなハードでは応用できることもありそうです。

[^cmp]: GDC, GDC Vault, Gamasutra, Game Developer は同じ会社が関わっています。

----
全然まとめきれてませんね。UE もないし、書籍絡み(Game Programming Gems とか)で情報があるはず。
気が向いたらあとで追記します。

明日は [@unemen](https://qiita.com/unemen) さんです。
いろんなパッケージマネージャで使用しているモジュールのライセンスを確認してみたく


毎々お世話になっております、株式会社 日立製作所 OSSソリューションセンタ の 神山直也(hi-naoya) です。
日立グループ OSS Advent Calendar 2019 の９日目、書かせて頂きたく。

私は社内システムの設計、構築、運用、etc …ゆりかごから墓場まで面倒を見ています。
社内システムを作るにもOSSを使うわけですが…このOSSのライセンスって調べるのが本当に大変！！！
なので、備忘録がてら、調べ方を調べてみました。

## Python/pip 編

Pythonの場合は `pip show` コマンドで調べられます。

`$ pip3 show PyYAML` (python3.7.3 / pip18.1)を実行すると、

```
Name: PyYAML
Version: 3.13
Summary: YAML parser and emitter for Python
Home-page: http://pyyaml.org/wiki/PyYAML
Author: Kirill Simonov
Author-email: xi@resolvent.net
License: MIT
Location: /usr/lib/python3/dist-packages
Requires: 
Required-by: 
```

が得られるので、こちらで License を確認できます。
同様の内容は、リポジトリのページから参照できます。

https://pypi.org/project/PyYAML/

多数のモジュールを一気に見たい場合は `pip-licenses` モジュールが便利そうです。
`$ pip-licenses` を実行すると、

```
 Name      Version  License     
 Click     7.0      BSD         
 greenlet  0.4.15   MIT License 
 msgpack   0.6.2    Apache 2.0  
 neovim    0.3.1    Apache      
 pynvim    0.4.0    Apache
```

このような形で一覧で、取れます。便利。

## Ruby/gem 編

Ruby の場合は、gemの情報を返す `gem specification` で調べられます。

`$ gem specification zlib` (ruby2.5.5p157 / gem2.6.7.2)

```
--- !ruby/object:Gem::Specification
name: zlib
version: !ruby/object:Gem::Version
  version: 1.0.0
...(中略)...
licenses:
- BSD-2-Clause
metadata: {}
...(攻略)..
```

pip-licenses のgem版みたいなものがあればよかったのですが、見当たらなかったのでワンライナーを書いてみました。


```gem list | cut -f1 -d' ' | xargs -n 1 gem specification | grep 'licenses:' -A 3 | grep -oP '(?<=^- ).+$' | sort | uniq```

これで、

```
2-clause BSDL
BSD 2-Clause
BSD-2-Clause
MIT
PSFL
Ruby
Ruby's
ruby
```

このような形で、使ってるモジュールのライセンスを集計して表示できます。
実際は、どのモジュールがどのライセンスか等細かく見ていく必要があるかと思いますが、ざっくりと全貌掴むには十分そうです。

## CentOS/yum 編

Yum の場合は、 `yum info` でライセンスを含むパッケージ情報が取得できます。

`$ yum info openssl` (CentOS7.7.1908 / yum3.4.3)

```
読み込んだプラグイン:fastestmirror
Loading mirror speeds from cached hostfile
 * base: centos.usonyx.net
 * epel: epel.dionipe.id
 * extras: download.nus.edu.sg
 * updates: download.nus.edu.sg
インストール済みパッケージ
名前                : openssl
アーキテクチャー    : x86_64
エポック            : 1
バージョン          : 1.0.2k
リリース            : 19.el7
容量                : 814 k
リポジトリー        : installed
提供元リポジトリー  : base
要約                : Utilities from the general purpose cryptography library with TLS implementation
URL                 : http://www.openssl.org/
ライセンス          : OpenSSL
説明                : The OpenSSL toolkit provides support for secure communications between
                    : machines. OpenSSL includes a certificate management tool and shared
                    : libraries which provide various cryptographic algorithms and
                    : protocols.
```

こちらもワンライナーで一覧とってみようと思いましたが、yum コマンド実行するとロックがかかるようで、gem と同じ方法ではできませんでした…残念。

## 最後に

今回調べた方法はほんの一例で、もっと効率的な方法はありそうです。
使うOSSが増えてくると人力で探すのは限界があるので、うまいこと自動化していきたいところです。


## TODO

https://github.com/github/licensed
「OSS」「ライセンス」あたりで調べてると、こちらのツールが見つかりました。
やりたいことに合致してそうなので、調べてみたいと思います。
MACで音が出ない

自分用にメモ
#サウンド設定を確認する
貸し出し用にMAC端末のキッティングをしていたところ、
システム環境設定 >　サウンド > 出力装置
で「出力装置が見つかりませんでした」としれっと言ってくるMAC君[^1]。
「主音量」の右「消音」のチェックもグレーアウトしています。
<img width="512" alt="スクリーンショット 2019-12-06 14.59.22.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/373685/6b96e8f0-34c7-b0ea-ced7-256d0f8e3eac.png">

#Appleのサポート
[Appleのサポートページはこちら](https://support.apple.com/ja-jp/HT203186 "Appleのサポートページ")
「出力」タブをクリックして、「内蔵スピーカー」を選択します。「出力」パネルに「内蔵スピーカー」がオプションとして表示されない場合は、Apple サポートにお問い合わせください。

#NVRAMのリセット
> NVRAM に記憶される設定情報には、音量、画面解像度、選択されている起動ディスク、時間帯、最近起きたカーネルパニックの情報などが該当します。

[Appleのサポートページはこちら](https://support.apple.com/ja-jp/HT204063 "Appleのサポートページ")

1. 電源を入れて
2. 電源を入れた直後に`option`キー、`command`キー、`P`キー、`R`キーを同時に押します
3. 2回ほど起動音がしたらキーを離して構いません、
   音のしない設定にしてある場合は20秒ほど押し続けてからキーを放します

https://support.apple.com/ja-jp/HT204063
#あっさり認識しました
<img width="512" alt="スクリーンショット 2019-12-06 15.04.47.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/373685/a0de8432-c55c-0021-d0af-07b9f17797fe.png">

[^1]: そういえば数日前にユーザーから同じことを聞かれました、わりとよくある現象なのでしょうか？
Notionのスラッシュコマンドを使おう

アルプ株式会社でエンジニアをしています、集約のエンティティ@pictinyです。
これは[Notion Advent Calendar 2019](https://qiita.com/advent-calendar/2019/notion) 6日目のエントリです。
5日目は[Notionのブロックをドラッグ・アンド・ドロップで操作する](https://qiita.com/pictiny/items/11b5ce7fdf203beacfdc)でした。

# コマンド

Notionには**Slash commands**と呼ばれるコマンドのようなショートカットがあります。
ブロック内で`/`を打つと、コマンドの補完ウィンドウが表示されます。
`/`に続けてコマンドを打ち込めば候補リストが絞り込まれていきます。
補完ウィンドウではマウスでスクロールもできます。

<img width="578" alt="Screen Shot 2019-12-04 at 23.38.48.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/427952/e0c38997-53d0-20d3-03aa-83805d9d172d.png">

Notionのショートカットでできることの多くは、コマンドでもできます。
ショートカットを忘れたり、思った通りにショートカットが走らなかったときには、コマンドを使って操作の候補を表示するとよいでしょう。

# コマンドキャンセル

普通に文章を打っていたらコマンドが暴発し、補完ウィンドウが表示されることが時々あります。
`/`に続けてescキーを入力すると補完ウィンドウが消え、コマンドをキャンセルできます。

# まとめ

コマンドのリファレンスは[Learn the shortcuts](https://www.notion.so/Learn-the-shortcuts-66e28cec810548c3a4061513126766b0)のページ中の**Slash commands**の項目にありますので、わからないことがあればそちらをご覧ください。
Railsデータ登録時に制限をかける方法

# Validatesの書き方
 何かをデータベースなどに登録する編集する際に入力規則を設けたい場合は、modelファイルに記載する。

```ruby
#models/post.rb
class Post < ApplicationRecord
	validates :contetnt,{presence:true,length:{maximum:140}}
end
```

上記の例では空白を許可しないvalidatesと最大文字数140文字をcontentに設定している。
この設定を実施するとcontentが未入力の状態でDataBaseを更新することはできない。

```ruby
#controllers/posts/controller.rb

def new
    @post = Post.new()
end

def create
   @post = Post.new(content: params[:contetnt])
   if @post.save
      flash[:notice] = "登録が完了しました" 
      redirect_to("/飛ばしたいページURL")
   else
   	　render("posts/new")
   end
end

```

```rhtml

#posts/new.html.erb

<%= form_tag("/posts/create") do %>

	<% @post.errors.full_message.each do | message| %>
    	<%= message %>
    <% end %>
    
	<input type="text" name="content" value="<%= @post.content %>">
    <input type="submit" value="送信">
        
<% end %>
```
WSL2 の port を Win につなぐワンライナー

wsl2 上で Web サーバを立ち上げても、そのままでは Windows 上のブラウザからアクセスできない。 (WSL1 では出来た。)

`win+x a` で管理者権限で Powershell を開いて、
 
```powershell
$IP = wsl -d Ubuntu-18.04 exec hostname -I; netsh.exe interface portproxy add v4tov4 connectaddress=$IP listenport=1234
```

を実行する。 `Ubuntu-18.04` と `listenport=1234` のとこは適宜変更すべし。
Windows を再起動するとクリアされる。 自動化する場合、 $IP は再起動ごとに変化するので、固定値で書き換えてはいけない。

# 余談
wsl 側から netsh.exe を実行することは出来ますが、 sudo とかしても管理者権限は付与できません。 wsl ターミナル自体を「管理者として実行」すれば、そのターミナル内からは

```bash
netsh.exe interface portproxy add v4tov4 connectaddress=$(hostname -I) listenport=1234
```
とかで実行できる。が、管理者権限つきの wsl ターミナルは危ないのでお勧めしません。
Symbolic Tensor(シンボリックテンソル)ってなんだ？

##経緯
https://keras.io/backend/
上記のサイトを見ていて「symbolic tensor」という言葉が出てきた。いまいち意味が分からないので自分なりにまとめてみようと思い書いた。

##Tensorとは
>A tensor is a generalization of scalars, vectors, and matrices to an arbitrary number of indices.
引用：https://www.wolframalpha.com/input/?i=tensor

要はベクトルやスカラー、行列などのこと

##symbolic Tensorとは
> In the following example, `c`, `d`, and `e` are symbolic `Tensor`
 |  objects, whereas `result` is a numpy array that stores a concrete
 |  value:
 |  
 |  ```python
 |  # Build a dataflow graph.
 |  c = tf.constant([[1.0, 2.0], [3.0, 4.0]])
 |  d = tf.constant([[1.0, 1.0], [0.0, 1.0]])
 |  e = tf.matmul(c, d)

>引用：pythonで`help(model.output)`
レコメンド運用の現在と未来

この記事は[DMMグループ Advent Calendar 2019](https://qiita.com/advent-calendar/2019/dmm)の14日目です。

# はじめに
二年ぶりのアドベントカレンダー参加です。
前回からチームを移動し、現在はレコメンドチームで運用・開発をしている @funa1g です。
今回はDMMサイト内の複数サービスで表示しているレコメンドの現在の運用設計、今後の課題について紹介します。

## この記事でわかること
* DMMレコメンドシステムの運用の雰囲気
* レコメンドのようなバッチ処理に対する運用上の注意点

## この記事でわからないこと
* DMMレコメンドシステムのレコメンド手法(これはまたいずれ)
* モダンなMLOpsの運用実態(数年前から運用されているため、結構泥臭い)

# 現在の運用設計
## パイプライン処理
レコメンド結果を毎日Jenkinsでのバッチ処理で生成しています。
前処理を経て、レコメンド結果を出力し、APIサーバへexportするのが大まかな流れになっています。

この処理は結構時間がかかるため、実行時間の変化には気をつけている必要があります。
レコメンドを増やした時や、システムリソースの状態が変化した時に、完了時間が大幅に後ろ倒しになるなどの形で影響が判明したりします。
そのため、レコメンドの生成時間の推移を可視化しています。
<img width="1054" alt="スクリーンショット 2019-12-06 14.59.23.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/91466/a6948fb0-debd-c803-86ae-4e673d3ac5f0.png">
こちらは全体の一部です。
これにより、バッチ処理時間に異常があった際には、クリティカルパスを探すことができます。

## データ更新の検知
レコメンド生成には、ユーザーの行動ログや商品情報などを利用しています。
これらのデータ(特に商品情報)は定時更新されているため、そちらの更新を検知して、バッチ処理は実施されるようになっています。
何らかの理由でデータが更新されていない場合もあり、その場合には slack に通知を出すようにしています。
パッと見は他のエラーと区別がつかないため、botにJenkins側の状態をチェックさせ、pollingによるエラーであることを検知させています。
通常のエラーと区別し、特別な対応は不要であることがわかるようにしています。
<img width="421" alt="スクリーンショット 2019-12-09 19.23.57.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/91466/d211bc5e-a5ae-c024-cd26-1a996335bb45.png">
チームのマスコット、nagatochanが教えてくれます。かわいいですね。

## レコメンド内容の変化検知
レコメンド作成に利用するユーザーの行動ログは毎日少しずつ変化していきます。
そのため、ある日レコメンドが正しく生成されなくなる場合があります。

この対策として、アイテムベースのレコメンドでは、商品全体の一定割合に対してレコメンドが生成できなかった場合にはエラーを出すようにしています。
大きな対策ではないのですが、以下のようなケースでエラーが出て、その後の問題を回避できました。

* 元データの値の持ち方がいつの間にか変わって、レコメンドの生成割合が減っていた
* ログ取り込み設定にミスがあり、ログが実は取り込まれておらず、レコメンドが正しく生成されていなかった

後者はもっと早く検知できたはずですが、そこは今後の課題ですね。

# 今後の課題
ここまで現在の運用設計を大まかに見てきました。
すでにそれなりの運用実績がある設計なのですが、レコメンド改善に取り組む上で複数の課題があります。
今後、取り組んでいく予定の課題が次のものになります。

## パイプラインの実行時間推移の可視化
現在もパイプライン上のバッチ処理の時間は、可視化されています。
しかし、当日の実行時間を一覧として眺められますが、前日からの実行時間推移などが追いにくい状態にあります。
先ほどの可視化はあくまで1日の中の実行時間を可視化できるだけで、日毎の変化は追えるようになっていません。
<img width="1410" alt="スクリーンショット 2019-12-11 18.14.06.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/91466/5f6bee38-98e4-73ce-f7fb-041b8af0e2d0.png">
また、Jenkinsのパイプラインも実行時間一覧が見られますが、こんな感じでずらっと並んでしまいます。チェックしづらい。

日時変化や全体のボトルネックを探すために、Datadogでの可視化を準備中です。
以下は作りかけのイメージです。今後、もう少し綺麗にして見やすいダッシュボードにする予定です。
![スクリーンショット 2019-12-11 18.11.37.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/91466/b1751dc0-8712-fb84-8ef8-d12b70afbd55.png)

## レコメンドの質の表示
レコメンドチームでは、レコメンドの質を改善するため、各種改善に取り組んでいます。
改善結果をABテストに出す前に評価するため、オフライン評価に取り組んでいます。
その詳細は[こちら](https://logmi.jp/tech/articles/321477)。

現在は開発の段階でしか実施していないオフライン評価ですが、これをプロダクトに対しても実施していきたいと考えています。
毎日のレコメンド結果に実施し、その質の変化を見ていくことで、レコメンドの状態変化を可視化し、今後必要な調整をあぶりだすことが目的です。
例えば、前月よりレコメンド結果のアイテムの網羅率が大きく低下している場合、何かデータに変化が発生していることを意味している可能性があります。
合わせて元データとなる商品データの傾向なども推移を確認できるようにすることで、より価値のあるインサイトを得られるようになるはずです。

# まとめ
運用設計についてざっくり見てきました。
結構泥臭い内容だったかと思いますが、どこか一つでも面白いと思ってもらえる箇所があるとうれしいです。

さらなる詳細やレコメンドの仕組みについても、今後発信していく機会があるかと思います。
その際にはまたよろしくお願いいたします。

次は @k0bya4 さんです。WebRTCで遊んでみるとのことですが、どんな内容なんでしょうか。
MacBookProでイーサネット・インタフェースが認識されないときの対処法

記事にするほどのことか微妙ですが、今のところ情報が見当たらなかったので。
同様の内容で苦しんでいる方がいたら、参考にしていただければ幸いです。

おそらく、2019/12/6現在で最新のOS Xである**Catalinaと[MacBookPro("13-inch,2019,Thunderbolt3x4ポート" モデル)](https://www.apple.com/jp/macbook-pro-13/specs/)との互換性バグ**です。
(本当はAppleにバグレポートした方がいいのか…？)


----
さて、本題です。

```
MacBookPro(13-inch,2019,Thunderbolt3×4ports)
⇔ USBtype-C変換アダプタ
⇔ イーサネットケーブル 
⇔ スイッチングハブ
```
的な感じでイーサネットによる通信を試みる場合、MBPのtype-Cを挿すポートの箇所によって認識されたりされなかったりします。
ifconfigしてインターフェース名にイーサネットが表示されなかったり、pingを飛ばして疎通できなかったりした際には、一度**左側一番上のポート**に挿してみて下さい。
既に3, 4台のMBPで同様の挙動を確認済みです。変換アダプタは純正・サードパーティ製問わずといった感じだったかと思います。
PySparkでscikit-learnの学習済モデルを使った推論をする

# はじめに

PySparkで機械学習を行う際、MLライブラリでは機能が不十分であることもあり、scikit-learnなど他のライブラリを利用したいと思うことがある。

その際の学習は、そもそもSparkのDataFrameが対応していないので別途行う必要があるが、推論についてはUDFを使えばスムーズにできるので、備忘として掲載。

※ここでは推論についてのみ扱い、学習自体は扱わない

# やり方

学習済みのモデル(`model`: scikit-learnのイメージ)がある時、以下のように行えばよい。
`data`が推論データのDataFrameで、`features`は説明変数のリストである。

ここでは、`model.predict(x)`で予測した結果を返しており、作成したモデルの予測関数に適宜入れ替える必要がある。
同様に、返り値が連続値になる場合は、`DoubleType()`などに変更する。

```python:pyspark上で学習済モデルを使った推論
import pandas as pd
from pyspark.sql.functions import pandas_udf
from pyspark.sql.types import IntegerType

@pandas_udf(returnType=IntegerType())
def predict_udf(*cols):
    X = pd.concat(cols, axis=1)
    return pd.Series(model.predict(X))

data.withColumn('predict', predict_udf(*features))
```

# 参考

- [Prediction at Scale with scikit-learn and PySpark Pandas UDFs](https://medium.com/civis-analytics/prediction-at-scale-with-scikit-learn-and-pyspark-pandas-udfs-51d5ebfb2cd8)
Docker で OpenAM をビルドする

今年も Advent Calendar に記事を書くことになったけれど、ネタもないし余裕もない…

ということで普段 [OpenAM コンソーシアム版 OpenAM](https://github.com/openam-jp/openam) のビルドに使っている Docker 環境を公開してお茶を濁すことにします…

```
$ git clone https://github.com/tsujiguchitky/dockerfiles.git
...
$ sudo docker build --tag build-openam-jp \
> dockerfiles/build-openam-jp
...
$ sudo docker run --name ambuild \
> -it build-openam-jp
...
$ sudo docker cp \
> ambuild:/home/builduser/source/openam/openam-server/target/OpenAM-14.0.0-SNAPSHOT.war .
```

で最新の master ブランチからビルドした OpenAM の war をゲットできます。

Dockerfile は大したことをしていないので、詳しく説明しませんが、

* コンテナの OS は CentOS7
* OpenAM のビルドには Maven 3.1 以上が必要なので、Software Collections の Maven 3.3 を使っている(OS 標準は 3.0.5)
* 関連するすべてのリポジトリに対して順番に `git clone` して `mvn install` をする

くらいがポイントでしょうか。

普段はこんな感じ↓でつかっていて、

```
$ sudo docker run --rm \
> --entrypoint '/bin/bash' \
> -p 5005:5005 \
> -v {ソースを配置しているパス}:/home/builduser/source \
> -v {Maven ローカルリポジトリのパス}:/home/builduser/.m2/repository \
> -it build-openam-jp
```

改修したソースコードをビルド対象にしたいのと、Maven キャッシュも使いたいので `-v` オプションで指定してます。
5005 ポートは `mvn test` をデバッグするために指定しています。

おしまい。
🍰【CakePHP2】複数あるデータベース設定ファイル「database.php」を指定して情報読み込み

## 環境

PHP 7.2.21
CakePHP 2.10.18

## 内容

本来のCakePHPは単一のデータベース接続の定義ファイル「database.php」にpublic変数として接続情報を配列で格納しそれを縦に並べて読み込みを行う

色々あって別々のディレクトリに「database.php」を複数置いた環境にて動的にDBを切り替えるため設定ファイルを読み込まなければならない状態になってしまった

## やったこと

読み込み用のBehavorを新規追加し、それもModelに読み込ませる
その後Behaviorを読んだModelにControllerからファイル名を渡して別の「database.php」情報を読み込む

```Model/Behavior/HogeBehavior.php
<?php
/**
 * Hoge behavior
 *
 */
class HogeBehavior extends ModelBehavior {
    /**
     * 別のDB情報を環境database.phpから読込み
     *
     *@param Model  $model
     *@param string $dbFileName 読み込みたいdatabase.phpファイル名
     *@return array 取得情報
     */
    public function readDatabaseValue(Model $model, string $dbFileName) {
        $cnt = 0;
        $flg = false;

        // 読み込みたいdatabase.phpのフルパス
        $filePath = ROOT . DS . 'app' . DS . 'Config' . DS . $dbFileName;
        if (file_exists($filePath)) {
            $fdata = file($filePath, FILE_IGNORE_NEW_LINES | FILE_SKIP_EMPTY_LINES);
            foreach ($fdata as $line) {
                $line = preg_replace("/( |,|')/", "", $line);
                $data = explode('=>', $line);
                if (strpos($line, 'public') !== false) {
                    $cnt++;
                    $flg = false;
                }
                if ($cnt == 1 && $flg == true) {
                    $result[$data[0]] = $data[1];
                }
                $flg = true;
            }
        }

        return [
            'datasource' => $result['datasource'],
            'persistent' => $result['persistent'] === 'true' ? true : false,
            'host'       => $result['host'],
            'login'      => $result['login'],
            'password'   => $result['password'],
            'database'   => $result['database'],
            'prefix'     => $result['prefix'],
            'encoding'   => $result['encoding'],
        ];
    }
}
```

```Model/Hoge.php
<?php
class Hoge extends AppModel {
    public $useTable    = 'hoge';
    public $primaryKey  = 'id';

    // behaviorの指定
    public $actsAs = [
        'Hoge',
    ];
}

```

```Controller/HogeController.php
// 読み込みたいファイル名
$dbFileName = 'database_another.php';

// $modelの引数は自動付加なので指定不要
$dbValue = $this->Hoge->readDatabaseValue($dbFileName);
```

## 結果

任意に指定した「database.php」の情報を読み込むことが出来た
これとDB接続切替を併用することで指定した別のDBへの接続も可能

今回はファイル名のみを渡してreadDatabaseValue()内でフルパスを作成していたが
Controllerで作成したフルパスを渡してやればディレクトリが異なっていても対応可能
【Rails】Ransackのcollection_check_boxesで、checkboxタグに任意のクラスを指定する

チェックボックスでAjax制御しようとして、クラス名を付与しようとしたところ、collection_check_boxesだと普通にやってもクラス指定できなかったので、色々ページを巡回し、ようやく海外ページのフォーラムで手がかりを発見したのでメモ。

やりたいこと。テーブル値@regionsでチェックボックスを作成し、class名、`chkgroup`を付けたい。
#駄目な例
```html.erb
<%= search_form_for(@q , :id=>'city-form', :remote => true ) do |f| %>
 <%= f.collection_check_boxes :regions_in, @regions, :id, :name, class : 'chkgroup' %>
<% end %>
```

Chromeで開発画面を見ても、クラス名は何も表示されていません。そこで色々と巡回していると、[こんなページ](https://stackoverflow.com/questions/24770491/style-rails-collection-check-boxes)を見つけたものの、checkboxならこれで行けるけど、collection_check_boxesでは対応していませんでした。

#collection_check_boxesの構造
あれこれ試行錯誤した末、多分、checkboxとcollection_check_boxesの構造が異なっているのと思い、ページを巡回していると、qiita内にこんなページが。

[collection_check_boxesメソッドの構造確認](https://qiita.com/sho012b/items/3a595fde14516081dff5)

なるほどと思い、これと同じようにループ構造にして、そこにチェックボックスタグを入れたりしてみたのですが、これも失敗。

#解決方法
めげずに、他に巡回していると、GitHubのフォーラムに、大きなヒントとなる方法が。

[collection_check_boxes - set custom class](https://github.com/bootstrap-ruby/bootstrap_form/issues/256)

この方法だと確かにラベル側に任意のクラスを指定できました。ですが、今回自分がやりたいのはcheckboxタグ側にクラス名を付与すること。そこで、labelタグをループさせることができるのなら、checkboxタグもループできるのでないかと試したところ…。

```erb:html.erb
		<%= f.collection_check_boxes(:region_in,@regions, :region, :region,include_hidden: false) do |b| %>
			<label class="checkbox-inline">
			 <%= b.check_box class:"chkgroup" do %>
				 <%= b.check_box + b.text %>
	　　　    <% end %>
				 <%= b.label {b.text} %>

			</label>
		<% end %>
			
```

成功！とりあえずはチェックボックス内にクラスが入りました。あとはラベルを取り付けるだけです。

#ラベルの場所
ですが、このラベルの場所も気をつけないといけません。checkboxタグのループに入れてもエラーとなるので、ループの外側に入れる必要があります。

```erb:index.html.erb
<%= search_form_for(@q , :id=>'city-form', :remote => true ) do |f| %>
     <%= f.collection_check_boxes(:region_in,@regions, :id, :name) do |b| %>
         <%= b.label {b.text} %>
         <%= b.check_box class:"chkgroup" do %>
             <%= b.check_box + b.text %>
　　　    <% end %>
    <% end %>
<% end %>			
```

これで、チェックボックスの値に対してもAjax制御をする準備ができるようになりました。

![SnapCrab_No-0000.jpg](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/272191/81e997c2-2bc1-7dab-719d-8efee61d94ad.jpeg)
ARM 上でdocker を動かしてみる


# ARM でdockerを動かしたり何たりします。

AWSで、ARMのインスタンスが割と安くつかえるようですので、
他の方の記事と内容がおそらく被りますが、今回は簡単にdockerを動かしてみました。

ARMの場合リポジトリが変わる点が注意でしょうか。
色々記事はありますが、公式ページの情報を見たほうが確実です。

https://docs.docker.com/install/linux/docker-ce/ubuntu/


まず必要なパッケージを入れます。

```
sudo apt install apt-transport-https ca-certificates curl gnupg2 software-properties-common
```

gpgキーの設定などします。ここまでは他のアーキテクチャでも同様です。

```
$ curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -
$ sudo apt-key fingerprint 0EBFCD88
    
pub   rsa4096 2017-02-22 [SCEA]
      9DC8 5822 9FC7 DD38 854A  E2D8 8D81 803C 0EBF CD88
uid           [ unknown] Docker Release (CE deb) <docker@docker.com>
sub   rsa4096 2017-02-22 [S]
```

リポジトリだけ変更をします。

```
$ sudo add-apt-repository \
   "deb [arch=arm64] https://download.docker.com/linux/ubuntu \
   $(lsb_release -cs) \
   stable"
$ sudo apt update
$ sudo apt-get install docker-ce docker-ce-cli containerd.io
```


はい、入りました。
後はバージョンの確認と軽い動作確認をしてみます。
別のリポジトリを間違って設定してしまった場合は、/etc/apt/sources.list の編集と
/etc/apt/sources.list.save の削除などを行い、再度手順を実行すれば動くかと思います。

```
$ sudo docker --version
Docker version 19.03.5, build 633a0ea
$ 
$ sudo docker run hello-world
Unable to find image 'hello-world:latest' locally
latest: Pulling from library/hello-world
3b4173355427: Pull complete 
Digest: sha256:4df8ca8a7e309c256d60d7971ea14c27672fc0d10c5f303856d7bc48f8cc17ff
Status: Downloaded newer image for hello-world:latest

Hello from Docker!
This message shows that your installation appears to be working correctly.

To generate this message, Docker took the following steps:
 1. The Docker client contacted the Docker daemon.
 2. The Docker daemon pulled the "hello-world" image from the Docker Hub.
    (arm64v8)
 3. The Docker daemon created a new container from that image which runs the
    executable that produces the output you are currently reading.
 4. The Docker daemon streamed that output to the Docker client, which sent it
    to your terminal.

To try something more ambitious, you can run an Ubuntu container with:
 $ docker run -it ubuntu bash

Share images, automate workflows, and more with a free Docker ID:
 https://hub.docker.com/

For more examples and ideas, visit:
 https://docs.docker.com/get-started/
$ 
```

arm64v8 版のHello worldが動いたようです。
あとはubuntu のイメージをpullしてみます。

```
$ docker run -it ubuntu bash
docker: Got permission denied while trying to connect to the Docker daemon socket at unix:///var/run/docker.sock: Post http://%2Fvar%2Frun%2Fdocker.sock/v1.40/containers/create: dial unix /var/run/docker.sock: connect: permission denied.
See 'docker run --help'.
$ 
$ sudo docker run -it ubuntu bash
Unable to find image 'ubuntu:latest' locally
latest: Pulling from library/ubuntu
6531af355894: Pull complete 
82f7942d2fb7: Pull complete 
fdce94e690d5: Pull complete 
a96a89ada1c3: Pull complete 
Digest: sha256:6e9f67fa63b0323e9a1e587fd71c561ba48a034504fb804fd26fd8800039835d
Status: Downloaded newer image for ubuntu:latest
```

matplotの様にインストールにかなり時間がかかるということはなく、さっくりと導入できました。
お手軽ですね。
JavascriptでAlt+←/Backspaceでのブラウザバックを無効化

# やりたいこと
探せばいくらでも出てきそうな、[Alt]+←とBackspaceでのブラウザバックを無効化する方法です。

# ソース
```js
window.addEventListener("keydown", function(event) {
    let tagName = "";
    let type = "";
    let readOnly = false;
    let disabled = false;

    // イベント発生元要素の情報を取得
    if (typeof event.target.tagName !== "undefined" && event.target.tagName !== false) {
        tagName = event.target.tagName.toLowerCase();
    }
    if (typeof event.target.type !== "undefined" && event.target.type !== false) {
        type = event.target.type.toLowerCase();
    }
    if (typeof event.target.readOnly !== "undefined" && event.target.readOnly !== false) {
        readOnly = event.target.readOnly;
    }
    if (typeof event.target.disabled !== "undefined" && event.target.disabled !== false) {
        disabled = event.target.disabled;
    }

    // [Alt]+←を無効
    if(event.altKey && (event.key === "ArrowLeft" || event.key === "Left")) {
        return false;
    }

    // BackSpaceを無効
    if (event.key === "Backspace") {
        if ((tagName === "input" && (type === "text" || type === "password")) || tagName === "textarea") {
            // テキストボックス・パスワード・テキストエリアの場合
            if (readOnly || disabled) {
                // 入力不可の場合は無効
                return false;
            }
        }
    }
    return true;
});
```
## 解説
`keydown`イベントでは、`false`を返すとキー入力が無効になります。
なので、イベントの発生元を判別して、[Alt]+←は問答無用で`false`、[Backspace]はイベント発生元の要素を判別して入力可能な要素であれば`true`、入力不可能な要素であれば`false`を返してやるようにすればいいです。
入力可能な要素は`input type="text"`,`input type="password"`,`textarea`の3つで、`readOnly`と`disabled`がどちらも`false`である場合のみです。

### `event.target`
イベント発生元の要素を取得します。
要素の属性値取得時は属性自体が存在しない場合もあるので、`undefined`チェックをしてから取得しています。`tagName`まではやらんでもいいかも。

### `event.key`
`event.keyCode`が非推奨になってしまったので、こちらを利用。
注意点としては、一部のキーがブラウザによって違う値を返してくること。
なので、判定の際に返ってくる可能性のある値を全て判定しなければいけません。
(Chrome: `Escape` IE: `Esc` など)
この例ではChrome、Internet Explorer、FireFoxに対応しています。

# 参考にしたサイト
[keyCode が deprecated になってた](http://var.blog.jp/archives/70803410.html)