くりーむわーかー

プログラムとか。作ってて ・試しててハマった事など。誰かのお役に立てば幸いかと。 その他、いろいろエトセトラ。。。

npm

Vue CLI3でコンポーネントをnpmのモジュールにする

随分ひさしぶりに書く気がする。まーなんか寝れないので何となく書こう。

Vueでコンポートネントを色々作って行くんだけど、規模が大きくなったり、別のプロジェクトで使いたくなった場合とか、どうにか簡単にやりたい。イメージ的にはelement-ui的に、Vueプラグインとしてインストールしたらすぐ使える的な感じ。npmのモジュールとして使えるようにしたいわけです。

で、これをやるにはWebPackとかBabelとかもろもろ激しく設定しなきゃいけなさそうで、ちょっとゲンナリしてたんだけど、Vue-cli3を使うと割と簡単にできたので、そのやり方。

あと、作ったモジュールはverdaccio(なんて読むの?)を使ってプライベートリポジトリに登録して、ちんまり使うようにする。自分恥ずかしがり屋なもんで。

2019/2/27追記
verdaccio:ヴェルダッチォって発音してるっぽ。イタリア語で「緑で描く」、「黄、黒、緑の土を混ぜたもの」みたいな意味らしいけど、絵画を描くときに塗る下地?の色ってことっぽ。そんな感じのニュアンスなんでしょか。 で、これはカタカナでなんて書けばいいんだろか、ベルダッチョはカッコ悪いしの。ベルダチオでいいか。。。

今回のサンプルは下記に上げてます。

https://github.com/n79s/vue-npm-module-sample

①Vue-Cli3のインスト

npm install -g @vue/cli

②コンポーネント作るようのプロジェクトを用意

vue create my-hello-module

③コンポーネント作る

# 例えばこんな感じ。
<template>
  <section>
    <h1>Hello World !!!</h1>
    <div>Message : {{ msg }}</div>
  </section>
</template>

<script>
export default {
  name: 'HelloX',
  props: {
    msg: String
  }
}
</script>

<style scoped>
h1 {
  margin: 40px 0 0;
  color:red;
}
</style>

④公開用のindex.js

import Vue from "vue"
import HelloX from "./HelloX.vue"
import HelloY from "./HelloY.vue"
import HelloZ from "./helloz/HelloZ.vue"

const MyComponents = {
    HelloX,
    HelloY,
    HelloZ
}

Object.keys(MyComponents).forEach(name=>{
    Vue.component(name,MyComponents[name])
})

export default MyComponents

⑤ビルドの設定

# package.jsonはこんな感じに変える
・・・
  "private": false,
  "scripts": {
    "serve": "vue-cli-service serve",
    "build": "vue-cli-service build",
    "build-x": "vue-cli-service build --target lib --name my-hello-module src/components/index.js",
    "lint": "vue-cli-service lint"
  },
  "main":"./lib/my-hello-module.common.js",
  "files": [
    "dist/*",
    "lib/*",
    "src/*",
    "public/*",
    "*.json",
    "*.js"
  ],
・・・

# vue.config.js(これは自分で作る

// vue.config.js
module.exports = {
    // options...
    "css":{
        "extract":false
    },
    "outputDir":"lib"
}

package.jsonの"build-x"のところでビルドのコマンド作る。あと、出力先はデフォだとdistだけど、libに変えてる。「vue.config.js」は無くても動くんだけど、細かい設定をしたい場合は必要。で、cssの部分が無いとcssが別ファイルで作成されてしまい、別プロジェクトでインストールしても、cssが適用されず上手くいかないので、上記の感じで書いておかないとダメ。CDN的に公開して、cssは別で読み込んでもらうような場合はいいのかしらね。

⑥ビルド

npm run build-x

ここまでで、libのフォルダが↓の感じになるはず。

sample05

そしたら、verdaccioの準備。

# インストール
npm install --global verdaccio

# 実行
verdaccio

これだけ。デフォで「http://localhost:4873」で動くはず。まず、ユーザ登録する。

npm adduser --registry http://localhost:4873

ID/PASS/Mail入れて終わり。あとは、下記の感じで公開する。

#package.jsonがあるディレクトリで↓を実行
cd my-hello-module
#公開
npm publish --registry http://localhost:4873
#確認
npm info my-hello-module --registry http://localhost:4873

プライベートリポジトリへの登録が終わったので別のプロジェクトを作成して↓の感じの事をやる。

#別プロジェクトを作る
vue create use-hello

#プライベートリポジトリからインストール
npm install my-hello-module --save --registry http://localhost:4873

#main.jsに↓の感じでグローバル登録する
import Vue from 'vue'
import App from './App.vue'

//↓↓↓ここ
import HelloComponents from 'my-hello-module'

Object.keys(HelloComponents).forEach(name=>{
  Vue.component(name,HelloComponents[name])
})
//↑↑↑ここ

Vue.config.productionTip = false

new Vue({
  render: h => h(App),
}).$mount('#app')

グローバル登録しておけば、あとはアプリ側で↓の感じで使える。

<template>
  <div id="app">
    <HelloLocal msg="Local"/>
    <HelloX msg="use-hello X" />
    <HelloY msg="use-hello Y" />
    <HelloZ msg="use-hello Z" />
  </div>
</template>

<script>
import HelloLocal from './components/HelloLocal.vue'

export default {
  name: 'app',
  components: {
    HelloLocal
  }
}
</script>

Vue-cli3はかなりいい感じですね。すごく楽。verdaccioも素晴らしい。

あと、StoryBook使って管理してみよ。チームでの作業とか良さげ。

参考

loadtestで性能確認

性能系の確認をしたい場合に使うやつ。nodeで動くので、node必須。公式?はココ

インストール。CentOS7。nodeとnpm入れてから。入ってない場合はコッチ参照

npm install -g loadtest

で、色々オプションがあるんだけど、とりあえずの使用は↓

loadtest [-n requests] [-c concurrency] URL

ex.
loadtest -n 200 -c 10 http://localhost/hoge

使いそうなオプションは↓

-n requests 送るリクエストの数。-c指定してる場合にリクエストの総数がパラメータよりも大きくなる可能性があるとのこと。その場合は最初のn個だけレポートするらし。
-c concurrency 擬似的にクライアントをここで指定した個数分作って、並列処理するらし。 プロセス的に分けて並列してるわけではない模様。応答が返ってくる前に2個目のリクエストが送信される場合もあるってさ。
-t timelimit リクエスト送り続ける秒数。応答が返ってきてなくても終わらせるってさ。
-C cookie-name=value cookie付けたい場合。複数ある場合は繰り返して書けって事らし。
-H header:value ヘッダーつけたい場合。jwtのテストとかで使えそう?「-h ”Authorization: JWT token-value"」的に。複数ある場合は繰り返して書けってさ。
-P POST-body ポストの中身。「-P '{"key": "a9acf03f"}'」みたいな。
-m method メソッドの指定。デフォはGET。POSTにしたい時⇒「-m POST」
-T content-type content-typeですね。デフォはtext/plain。
--data POST some variables フォーム送信的な事やるときはこれかな?⇒の感じで使えってさ。「--data '{"username": "test", "password": "test"}' -T 'application/x-www-form-urlencoded' -m POST」。これやるときは「-m POST」 と -Tは必須っぽ。
--rps requestsPerSecond これ使いそー。1秒間あたりに何個リクエスト出すかを指定する。「--rps 0.5」は2秒毎に1リクエストらし。-cと合わせる場合、並列の個数毎に効くんじゃなくて、全体としての扱いになる模様。-c 10とかやって場合に一つ一つ毎にrpsが効くわけではないと。で、あまりに並列度低いとrps満たせなくなるからそれなりに考えてねってことらしい。

他にもいろいろあるので詳しくは公式参照

例えば、10個のクライアントで1秒間にトータル100リクエスト(1クライアント10リクエスト/秒想定)出す状態で10秒間動かす場合は↓の感じ。

loadtest -t 10 -c 10 --rps 100 http://localhost/hoge

で、動かすと色々出てくるんだけど見るのは↓あたりかな。

#1秒間に送信できたリクエスト数
Requests per second: 10
#平均待ち時間
Mean latency:        6.4 ms
#待ち時間の分布割合。↓だと50%は5msで帰ってきてるってことかしら?
Percentage of the requests served within a certain time
  50%      5 ms
  90%      10 ms
  95%      12 ms
  99%      23 ms
 100%      23 ms (longest request)

あと↓の感じで(公式サンプル)、javascriptとして普通に組み込めるからテスト用にモジュール化しておけば、自動実行とか組み込めそうですね。。。

const loadtest = require('loadtest');
const options = {
    url: 'http://localhost:8000',
    maxRequests: 1000,
};
loadtest.loadTest(options, function(error, result)
{
    if (error)
    {
        return console.error('Got an error: %s', error);
    }
    console.log('Tests run successfully');
});
問合せ