Node.js周りの学びメモ

node.jsを周りを勉強する上で、すぐあれこれ忘れちゃうので、一応メモ。

##express-generator

###bin/www
applicationのデフォルトのエントリーポイント。server周りの設定が書いてある。

##webpack

###使用準備
・参考：[webpack.config.jsの読み方、書き方](http://dackdive.hateblo.jp/entry/2016/04/13/123000)

・プロジェクトディレクトリのルートに以下を作成。
`webpack.config.js`

minimumと思われる設定。src/app.jsから始めて芋づる式にバンドルした何かをdistに出力する。

```js:webpack.config.js
const path = require('path');

module.exports = {
  context: path.join(__dirname, 'src'),
  entry: './app.js',
  output: {
    path: path.join(__dirname, 'dist'),
    filename: '[name].js'
  },
  target: 'node',
  module: {
    rules: [
      {
      test: /\.js$/,
        loader: 'babel-loader',
        options: {
          presets: [
            ['es2015', { modules: false }]
          ]
        }
      }
    ]
  }
}

```

・context:
entryポイントなどのために設定する。なくてもcurrent directoryを自動で読み込んでくれるが、基本的には明示的に設定して、カッチリ決めておいた方がいいらしい。

・target:
サーバー側をbundleするよと指定している。

・ライブラリ群と頻繁に変更するファイルとを分けてバンドルしたい時
>キャッシュを活用できない。
ライブラリは頻繁に変更しないファイルのため、キャッシュを活用すべきだが、全てのファイルを1つにバンドルするとそれができない。
そのため、頻繁に変更するファイルのバンドルと、ライブラリ群をまとめたバンドルは別にして出力する（CommonsChunkPluginというプラグインが必要）。
参考：[webpack使い方](http://qiita.com/soarflat/items/28bf799f7e0335b68186)

・resolve.extensionsには`''`の空文字を指定してはいけない。
元々はなんでもファインダー的な感じだったと思うんだけど、webpack2からダメになったらしい。

###便利そうなplugin
・UglifyJSPlugin
jsのファイルを圧縮してくれる。

・ProvideJSPlugin
指定したモジュールを全てのファイルで変数として使えるようにしてくれる。

・CommonsChunkPlugin
複数のエントリーポイント間で共有できる、モジュールを出力するためのプラグイン。

##pug
可愛いワンちゃんのアイコンが秀逸。

###注意すべきこと
・属性に変数を渡したい時。

```
span(class="icon-#{item.icon}") //NG
span(class="icon-" + item.icon) //OK
```

参考：[escaping variables, behavior has changed for attributes](https://github.com/pugjs/pug/issues/2302)

##mongodb
###注意すべきこと
・updateOneを作る際
formの方にidをしっかりinput hiddenでつけておく。urlにあって、そのあとでアクセスできていても、サーバーサイドのロジックの際に、うまく動かないことがある。

・ユーザー認証周り
参考：https://stackoverflow.com/questions/41615574/mongodb-server-has-startup-warnings-access-control-is-not-enabled-for-the-dat
参考：http://kidooom.hatenadiary.jp/entry/2015/02/18/112458

###ドキュメントの配列に要素を追加する
`$push`と`$each`を使う。

```:terminal
db.COL.update({name: 'osakabe}, {$push: {comments: {$each: ['hoge', 'wako']}}})
```

###ネストされたプロパティにアクセスする
キーを文字列にして、`.`で繋げば良い。

```:terminal
db.COL.update({sector: {$exists: true}}, {$push: {"sector.sales": {$each: salesID}}},{upsert: false});
```

###内部配列を検索し、マッチしたものを更新する

クエリは内部ドキュメントと同じ方式で出来る。見つかった要素を参照する場合は$で参照する
参考：https://gist.github.com/ykst/d1a024f1d800311744be

```:terminal
db.COL.insert({a:[1,2,3,4]})
db.COL.update({a:1}, {$set: {'a.$': 100}}) // [100,2,3,4]

db.COL.insert({x:[{i:1},{i:2},{i:3},{i:4}]})
db.COL.update({'x.i':1}, {$set: {'x.$.i': 100}}) // [{i:100},{i:2},{i:3},{i:4}]
```

###配列を利用してドキュメントを検索する
`{$in:[]}`を使用する。

```:terminal
salesID
[
  ObjectId("5993e8d4c98e1444a465f55f"),
  ObjectId("5993e8d4c98e1444a465f560")
]
db.employees.find({_id:{$in:salesID}})
{ "_id" : ObjectId("5993e8d4c98e1444a465f55f"), "name" : "osakabe" }
{ "_id" : ObjectId("5993e8d4c98e1444a465f560"), "name" : "cho" }
```

###findOneの返り値を扱うとき
```js
collection(COL).findOne(
  {dct: "categoryTable"},
  {categories: 1},
  function(err, result) {
    cate = result;
  }
);
```

##静的なファイルの扱いについて
多分、3時間x3回くらいハマらせていただいている静的ファイルが404になってしまう事案。
またハマったら以下を参照すべし。
[Expressで静的ファイル(static ファイル)をホスティングする](https://maku77.github.io/nodejs/express/static-file.html)

##要勉強

###lodash
どうもunderscore.js的何からしい。
参考：https://lodash.com/docs/4.17.4