wildflyでのサービス公開手順 CentOS7+Nginx[http2]+JDK1.8+Wildfly10.1+MariaDB10.1.22

■アップデート

yum update

■JDK1.8 install

yum install java-1.8.0-openjdk-devel
java -version

■Wildfly 10

useradd wildfly
passwd wildfly
curl -O http://download.jboss.org/wildfly/10.1.0.Final/wildfly-10.1.0.Final.tar.gz
tar zxvf wildfly-10.1.0.Final.tar.gz -C /opt

cd /opt
chown -R wildfly:wildfly ./wildfly-10.1.0.Final/
cd /opt/wildfly-10.1.0.Final/
./bin/add-user.sh
vi ./standalone/configuration/standalone.xml
(127.0.0.1をgloval IPに変更)

■Nginx
yumの場合は以下。http2に対応するためビルドから(後述)

vi /etc/yum.repos.d/nginx.repo

[nginx]
name=nginx repo
baseurl=http://nginx.org/packages/centos/7/$basearch/
gpgcheck=0
enabled=1


yum -y --enablerepo=nginx install nginx

■Nginx(https2)
ビルドツール・依存関係ライブラリをインストール
ここからOpenSSL最新版取得

yum groupinstall "Development Tools"
yum install pcre pcre-devel zlib zlib-devel

curl -L -O https://www.openssl.org/source/openssl-1.1.0e.tar.gz

ここからNginx(Stable Version)のURLを取得

curl -L -O https://nginx.org/download/nginx-1.12.0.tar.gz
tar zxvf nginx-1.12.0.tar.gz
cd nginx-1.12.0/

下記の内容でconfigure

./configure  \
  --prefix=/etc/nginx \
  --sbin-path=/usr/sbin/nginx \
  --conf-path=/etc/nginx/nginx.conf \
  --error-log-path=/var/log/nginx/error.log \
  --http-log-path=/var/log/nginx/access.log \
  --pid-path=/var/run/nginx.pid \
  --lock-path=/var/run/nginx.lock \
  --http-client-body-temp-path=/var/cache/nginx/client_temp \
  --http-proxy-temp-path=/var/cache/nginx/proxy_temp \
  --http-fastcgi-temp-path=/var/cache/nginx/fastcgi_temp \
  --http-uwsgi-temp-path=/var/cache/nginx/uwsgi_temp \
  --http-scgi-temp-path=/var/cache/nginx/scgi_temp \
  --user=nginx \
  --group=nginx \
  --with-http_ssl_module \
  --with-http_realip_module \
  --with-http_addition_module \
  --with-http_sub_module \
  --with-http_dav_module \
  --with-http_flv_module \
  --with-http_mp4_module \
  --with-http_gunzip_module \
  --with-http_gzip_static_module \
  --with-http_random_index_module \
  --with-http_secure_link_module \
  --with-http_stub_status_module \
  --with-http_auth_request_module \
  --with-threads \
  --with-stream \
  --with-stream_ssl_module \
  --with-http_slice_module \
  --with-mail \
  --with-mail_ssl_module \
  --with-file-aio \
  --with-http_v2_module \
  --with-ipv6 \
  --with-openssl=../openssl-1.1.0e/

■MariaDB

vi /etc/yum.repos.d/MariaDB.repo

[mariadb]
name = MariaDB
baseurl = http://yum.mariadb.org/10.1/centos7-amd64
gpgkey=https://yum.mariadb.org/RPM-GPG-KEY-MariaDB
gpgcheck=1


yum -y install MariaDB-server MariaDB-client
systemctl start mariadb
systemctl enable mariadb

mysql -p

show variables like 'char%';
vi /etc/my.cnf.d/server.cnf

[mysqld]
character-set-server=utf8


mysql -p

show variables like 'char%';
CREATE DATABASE dbname;
SELECT user,host FROM mysql.user;
GRANT ALL PRIVILEGES ON `dbname`.* TO 'username'@'localhost' IDENTIFIED BY 'password';
GRANT ALL PRIVILEGES ON `dbname`.* TO 'username'@'127.0.0.1' IDENTIFIED BY 'password';

update mysql.user set password=password('password') where user = 'root';
flush privileges;

exit

■firewall確認

firewall-cmd --list-all
firewall-cmd --add-port=80/tcp --permanent
firewall-cmd --add-port=8080/tcp --permanent
firewall-cmd --add-port=9990/tcp --permanent
firewall-cmd --reload
firewall-cmd --list-all

■ひとまず動作確認(まだNGINX未設定)

su - wildfly
cd /opt/
http://ipaddress:8080/
http://ipaddress:9990/
(管理画面からJDBCの設定やデプロイなどを設定。面倒なので、standalone.xmlを上書き)

■おまけ
wildfly停止
./jboss-cli.sh –connect command=:shutdown

wildflyの起動 nohup でも良いけど、サービス登録したい
http://www.dimasrio.com/2016/07/setup-wildfly-10-standalone-di-centos-7.html

SPFレコードなどなど 

知り合いから頼まれて、外国にあるサーバを日本のサーバに移管。

VPSについてまともに調べたことがなかったけど、
いきなり大きくスケールすることもないと思うので、安さ優先で調査。

最近、調べるとほとんどGMOにつながるなと思う。
とりあえず、SSDにしたかったので、Conohaの900円プランで5年は持つだろうということで契約。
それより安いプランはさすがにPHP動かすなどになるときつそう。

WordPressで作られていて、PHPのバージョンも聞けない雰囲気だったのでとりあえず最新のPHP7を。
せっかくなので以前作った構成をベースにNginxも設定。

Google insight speedで確認。
過去のサーバよりもモバイルは得点は上昇。
パソコンは下降。。。
なので言われるがままに設定。

主にgzip圧縮やcacheの設定を見直し。
それでもパソコンは赤点で、画像圧縮ちゃんとしろとかがメインで怒られる。
これは少しずつ勝手に変えていこう。。
ただ、2,3月頃に一新するようなのでそこまで待つ。

ブラウザからデベロッパーモードで見ると警告やらエラーがわんさか出ているので
これもそのうち解決していく。

で、本題の迷惑メールの件について。
メールの機能は確認してほしいといわれ確認。
特にエラーはなかったので問題ないかなと思ったけど、いくら待ってもメールが届かない。
迷惑メールフォルダを見てみるとそこに入ってた。

あまりこの辺は詳しくなかったので調査。
なりすましのやり方が逆にわかるために、こんなので防げるのか??とか思ってたせいで時間がかかった。。
結局、SPFだけじゃ信頼できないってDKIMと組み合わせたりもするみたい。

独自ドメインのメール送信を SPF に対応させる方法

いくつかのサイトをまわってみても、これを入れればいいとか言って
謎のIPアドレスが出てきたりしてかなり悩まされたので、微力ながら検索上位に来るように良かったサイトをリンク。

あとはnslookupで確認も出来るので確認しましょう。

Qiitaなんかでも簡単にまとめてくれるのは良いんだけど、
本質を知りたい人向けと、とりあえず動けばいいやって人向けになんとか改善できないものか。
厳しいけどlikeだけじゃなくてbadも欲しい。Stack Overflowになっちゃうか。

GoogleCloudPlatform+Wildfly10+JDK9(EARLY) 2

前回の記事

意外と覚えているもんだ。
とりあえずdownloadしてWindowsで確認&開発環境を構築。

・wildfly 10.1.0.Final
http://wildfly.org/downloads/

・Eclipse neon
https://eclipse.org/downloads/

・JDK9 early 64-bit
https://jdk9.java.net/download/

①Wildfly編
1. downloadしたWildflyを解凍。
2. wildfly-10.1.0.Final/bin/add-user.batでManagementユーザを追加。
3. wildfly-10.1.0.Final/bin/standalone.batを実行して確認。
  http://localhost:8080
  http://localhost:9990

2つめのURLは、add-user.batで追加したユーザ/パスワードを設定してログイン。

特に問題なかったので、Eclipse編に。

②Eclipse
1. neonをインストール
2. jboss tools をマーケットプレイスからインストール
  なぜか途中でエラー。Neonだから?
  keep my installation the same and modify the items being installed to be compatibleを選択して進む。
その後も警告とか出るけどとりあえず無視して進む。

③プロジェクト作成
毎回、何から作ってたか忘れてしまう。
Mavenの場合、誰かがこんなパターンおすすめだよみたいなのを登録してくれているので
その組み合わせを選ぶぽい。
よく本とかではKitchen sinkなんかが取り出されてるけど、
毎回ディレクトリ構成とかが気に食わなくてやめてた記憶。

でもMavenお勧めはなんかしっくりこないことが多いので、Java EE Web Projectから作成。
2年前はSeamを選んでた気がするが、CDIに名前変わったんだぜって記事に書いた記憶が復活。
Create blank Projectにチェックいれた?
Wildflyはこの時点ではEAP6、AS7.1、8x/9xとしか出てこない。
使いたいのは10.xなので警告無視して次へ進む。

Mavenと違って見覚えのある形のWorkspaceになったので満足。
Mavenの場合、Wildfly10選んだのにJavaSE1.5みたいな単語が見えて怖かった。
Java EE Web Projectも怪しいのでプロジェクトのプロパティを変更。

Build pathの変更
ぐぬぬ。。jdk9(jre9)が選べない。タイトル詐欺。。。
しょうがないので過去にインストールしてたぽいjdk1.8
JavaCompilerも合わせて変更。

Project Facetsの変更
Dynamic Web Moduleを3.1に。
Javaも1.8に。

JPAの接続先がないとか警告が出るのでPOM.xmlにmysqlのconnectorを追記。
Windowsだと、「%HOMEPATH%\.m2\repository\mysql\mysql-connector-java\」に登録されるのでそこを参照するようにする。
Deploy時に選択できたような記憶があるが、やり方忘れたので残念ながらこの方法で。。

最初のサンプルとして、Member.javaがあるがDBにそんなテーブル無い!とエラーを出してくる。
persistence.xmlを見るとcreate-dropになっているので、起動時に作り直すはず。
というわけで、今度はServersタブから「No servers are available. Click this like to create a new server…」をclickしてサーバを追加する。

サクッと登録して、起動!
http://localhost:8080//
うん。動いてる。
mysql で show tables;
あれ。テーブルない。。
そういえば、persistence.xml(?)書き換えてないからテストのデータベース使ってるのか。

この辺から記憶が怪しくなってきた。

ちょっと長くなってきたので次回に続く。。?

GoogleCloudPlatform+Wildfly10+jdk9(early)

Bigdata関係をしばらく書いていたけど、ちょっとしたサイトを作る必要が出てきたので簡単に作成。(したい)

また、GoogleCloudPlatformが日本公開が11月ということでお試し版をつかってみます!
300$分も無料で使えるし、なんといっても気になるのは従量課金だと「実際の」料金がどのくらいになるかなので、この方式はありがたい。

日本のリージョンを選びたいときは、asia-northeastを選ぶっぽいですね。
元のリージョンがasia-eastが台北なので、そこよりは北ってことかな。

でも、やっぱりasia-eastリージョンよりは若干お高めになっているのが残念。
でもレイテンシがくそ高い!
最初にケチってasia-eastにしたけど、コマンドのレスポンスなんかは
普段使ってるcloudよりも良い気がするのは気のせいだろうか。

AWSと料金比較しているサイトを見て、2割くらいは安い印象を受けた。
ただ、実際に作ってみると、そのサイトの情報が古いのか、GCPの計算が間違ってるように見える。
AWS側はわからないので、どちらも同じく間違っていれば別に問題ないですが。。。
ネットワークの従量課金部分を除いてインスタンス作るだけならやっぱりAWSは安いね。

でもさすがGoogleという感じで、設定がものすごくシンプル。
会社員時代に隣でひたすらAWSの設定を考えてたり、打ち合わせで一緒にいたときに聞いてたあほっぽい設定が全然いらない。
ネットワーク周りとか本当に簡単すぎて震える。

そんなわけで過去を振り返りながらWildflyの設定などをしていきたい。
以前構築したEAP7がちょうど一年くらい前ですっかり忘れているのでリハビリにちょうどいい。

本当は別の目的で同じ構成組みたかったから一石二鳥!
そして昔記事を書いたつもりだったのに全然ない。
Excelにまとめたんだっけかな。。

次回へ続く。。

CentOS7.2 + Zeppelin0.7.0 + Spark2.0 + R3.3.1 + RMeCab(再)

前回の9月3日の記事と特に変わりはないはず。
ただし、今現在もZeppelin0.7.0はDeveloper版なのでちょっとは更新されているはず。

経緯としては、AccessLogを読み込むぜー!ってことで、Google先生にアドバイスを求めたら
Parserがお勧めと帰ってきたので取り込んでみた。

参考サイトのまま作り進めていくと、parserは標準からは分離されたということで、
interpreterにorg.scala-lang.modules:scala-parser-combinators_2.12:1.0.4と書いてから挙動がおかしい。

公式にもStatic initialization is deprecated and will be supported until 0.6.0.
ということで、なんとなくの原因はわかるが、解決方法が不明なことと、割と早く復旧しないとまずいので作り直し。
(幸か不幸か作り直しはもう慣れてる)

新バージョンで細かなバグが治っていることを祈りつつ・・・。

ーーーインストール

そして、前回の記事と全く操作変わらずにインストールできた。。
ネタがない!!w

あ、描画速度も体感できるレベルであがってる!
起動時間が長いとgoogleVisが読み込まれなくなる?バグっぽい挙動、
PINGログが出力されまくるのもなおってるぽい。

ついでにgoogleVisの見た目も少し変わってる。

セキュリティも権限がないとそもそも一覧にも出てこないのはナイス修正!
Jobからは見えるけど、Jobからの遷移もバグってるぽくHome画面にいくのでセーフ(?)

今、Import/Exportがちゃんと動いていないようなので、そこが直るのをまったほうがよさそう

Apache Zeppelinがバッチ処理に使える

たまたまバッチ処理をする必要が出てきたので、実装方法を考えたときにApache Zeppelinを使ってDBを更新すればいいじゃんという結論に。
Clone設定と同じように時間指定できるし、Re Runも簡単だし。

ってことを1つのプロジェクトで考えてた時に、
別プロジェクトでsh + python使ってバッチ処理作ってという依頼が。

Webサービスも古臭いなという印象を受けてたので、1ヶ月で見切りをつけた案件をしているチームからの依頼。
やっぱりpythonもすっごく古臭い。

それはともかく、Zeppelinをバッチで使うとなにが嬉しいかまとめてみる。
(大企業でZeppelinのようなものを使ってバッチ処理する世界は5年は先だと思うので)

  1. TeratermなどでのCUI操作が不要になる
  2. テストデータの挿入するなどのSQLを書いたりした場合、Zeppelin上で1元管理できる。実行したいときに再生ボタンを押すだけ!わざわざtxtに書いておかなくても大丈夫だし、それを探す&開く手間が不要。
  3. 接続先の変更が容易(interpreterの設定)
  4. Success/failが簡単に一覧で確認できる
  5. バージョン管理もできる(これちゃんと動いてる?)

メールを飛ばすなどする場合にはまだまだ作りこみが必要かもしれない。
ここは、自分が勉強不足なのか、そもそもバッチ用に作ってないからコンセプトとしてないのかもしれない。
ただ、当たり前にログ監視もできるので、Zeppelinにアクセスすればだいたいわかるとなると便利。

。。。メモリ2Gが最低要件でさえなければ。。。

AngularJs on Apache Zeppelin

よく読んだら公式情報でもわかるのかもしれないが、結構詰まったのであとで思い出せるように記事にする。
ここまではまったのは結構久しぶりかもしれない。

やりたかったことは、SELECTタグからひとつの値を選択。
選択した値を利用して、別のParagraphにて結果を出力していくというもの。
恐らく一般的な使い方になっていくのだろうが、あまりにもこの辺の情報が薄すぎる。

まずは最終的なソースから。

// scala
import org.apache.zeppelin.display.angular.paragraphscope._
import AngularElem._

// clear previously created angular object.
AngularElem.disassociate

// z.runでInterpreterが切り替わってしまうので保持
val interpreterContext = z.getInterpreterContext()

// db(dataframe から RowのListへ変換。SCALA<==>AngularはJSONでやり取りしているようなのでJSONも組み込みたい)
val location = sqlContext.sql("SELECT location FROM selectLocation")
var locationList = location.collect()

var selectList = org.apache.spark.sql.Row("")

// scala -> angular
z.angularBind("locationList", locationList)

///////////////// display /////////////////
<div>
<select ng-model="selectList" ng-options="list.values for list in {{locationList}}"></select>
<!-- <p>{{{{debug}}}}</p> -->
</div>.model("selectList",selectList).display

<div class="btn btn-primary">reference</div>.onClick(() => {
    val selectOne = AngularModel("selectList")()
    // AngularModel("debug", selectOne)
    z.put("selectOne", selectOne)
    z.run(24,interpreterContext)
}).display

<div class="btn btn-default">reference</div>.display
<div class="btn btn-info">reference</div>.display
<div class="btn btn-warning">reference</div>.display
<div class="btn btn-danger">reference</div>.display
<div class="btn btn-primary">reference</div>.display

上から順に説明すると、最初の数行はおまじない。
AngularElem.disassociateって本当に効果あるのだろうか?
これ以外にもParagraph実行するたびに遅くなっているのでまだまだ改善の余地ありということなのか、能動的にメモリ管理する必要があるのか。

interpreterに関しては、コメントにある通り、別のParagraphを実行してしまうとInterpreterContextが切り替わってしまう。
そうなると2回目の実行が出来ない。Errorlogを見てみると下記のように出ているはず。

ERROR [2016-10-03 01:57:21,622] ({pool-27-thread-2} AngularObject.java[run]:191) - Exception on watch
org.apache.zeppelin.interpreter.InterpreterException: Can not run current Paragraph

次に、SQLContextを利用して、Dataframeを取得。
そのままでは使い勝手が悪かったので、collectでListを取得。
最初はcollectAsListでjava.util.Listを取得していたが、こちらのほうが使い勝手悪かったのでArrayで取得。
どういう使い分けをするのが良いのだろうか。
取得した内容をangularBindでangularにBind。

.displayと書けばangularContextだと認識するようなことを公式に書いてあったので
//// display ////以下はAngularの話。

ng-modelには選択した値が入る(と思っている)

ng-optionsにはBindした値を設定。Arrayにはvaluesという値で入っているのでvalueにはvaluesを設定するように指定。
list.key as list.values for list in {{}}というような指定をすればkeyも設定できる。今回は無視。

pタグで囲まれているのはデバッグ用。BackendのAngularを使って変数を表示する場合、Escapeは2重に書くのかな。

で、<div>.model(・・・)で、AngularContextに値を設定。
公式情報見ているとScala to Angularのために書いているように見える。
実際にはClient to Serverってイメージかな?
公式情報にある、watchとrunも、どっちも+1しているせいで、runとwatchが同じ値を共有しているのかと思ったし。。。

最後にボタンの挙動。
AngularModel(str)()でAngularContextの内容を読み込み。
名前にListってあるのは最初はmultipleにしていたから。

AngularModel(str, obj)でAngularContextの内容をUpdate。

とりあえず、sparkContextにて使いたかったので、ZeppelinContext.putで保持。
その後、ZeppelinContext.runで実行。この際、コメントに書いてある通りinterpreterを指定しないとContextが変わる可能性があるので注意。
24はNotebook内にあるParagraphの順番。0始まり?

おまけで、cssを探った結果、buttonのclassに設定できるもの。
cssの情報はもうちょっとまとめてほしいし、JSFのようなshow case も欲しい。

ちなみにrunで実行した結果を、z.get(str)で取得するだけで終わってます。
z.angular(str)では思うように取得できなかった。

ZeppelinはContextが複数扱えて、その状況に合わせて最適な言語を選択できることは面白いけど
やっぱりそれを考えながら使うのは結構難しいっていうか、なんちゃってSEはついていけない気がする

Apache ZeppelinとAngularJS(Selectタグ,tags-input)の試行錯誤

全然、理解できていないけど、たまたま動いたので試行錯誤した内容を記載。
この記事は読んでも何も解決しないし余計混乱するだけの可能性が高いので要注意。

やりたかったことは、Apache Zeppelin上で条件を変更しながらデータを参照したかった。
なので、AngularJSを使ってHTMLを生成し、検索条件を選べるようにしたかった。
理想はこんなの

参考
AngularJS で select タグを思い通りに作る
spark2.0.0 API(Dataset)
Back-end Angular API in Apache Zeppelin

前提知識
AngularJSはFramework。Client側で動くものではなくて、Server側でも動きます。

とりあえず、お試しでいろんなサイトのごちゃまぜ版

import org.apache.zeppelin.display.angular.paragraphscope._
import AngularElem._

val pj_list = Map[Int,String](
    (1, "プロジェクトA")
    ,(2, "プロジェクトB")
    ,(3, "プロジェクトC")
)

val pj_list2 = List("プロジェクトA", "プロジェクトB", "プロジェクトC")

z.angularBind("pj_list", pj_list)
z.angularBind("pj_list2", pj_list2)

println("""%angular {{pj_list}}""")
// {"key1":1,"value1":"プロジェクトA","key2":2,"value2":"プロジェクトB","key3":3,"value3":"プロジェクトC"}
// mapではない。。。オブジェクトのままで良いのに、なぜか変なListに置換される。これはバグじゃないかと思ってる。

println("""%angular 
<select ng-model="select" ng-options="data for (num, data)  in {{pj_list}}" multiple="multiple">

""")

println(“””%angular {{pj_list}}”””)の結果を見てもらえばわかるが、
key1というkeyに1、value1というkeyにプロジェクトAが割り当てられている。
なので、表示は「プロジェクトA」「プロジェクトB」「プロジェクトC」にはならず、「1」「プロジェクトA」「2」「プロジェクトB」「3」「プロジェクトC」となる。

ここまでも結構時間がかかったので、これがバグだったらちょっと殺意が湧くレベル。

でも、思ったよりもやりたいことはできそうだったので、思い切ってこの状態からBindするデータをDBから取得するように変更。
なんとなくダメだろうと思いつつ、上記のソースを書き換えてみた。

// scala
import org.apache.zeppelin.display.angular.paragraphscope._
import AngularElem._

// user Tableについては、別でDBから抽出済み。
val location = sqlContext.sql("SELECT location from user GROUP BY location")
val a = location.collectAsList()

z.angularBind("a", a)

println("""%angular 
<select ng-model="select" ng-options="b.values for b  in {{a}}" multiple="multiple">

""")

あれ?なぜかObjectでBindできてるし。。
Map[Int,String]がわるいのかと思いつつも、StringはObject型じゃないん?とか考えつつも、key,valueにこだわりは今のところ無いので深追いせずに終了。
ちなみに、aの型はjava.util.List[org.apache.spark.sql.Row]。
もしかして、Mapを直接Bindするんじゃなくて、ListのMapをBindすればよかったのか。

<select ng-model=”select” ng-options=”data for (num, data) in {{pj_list}}” multiple=”multiple”>
ここも後で見直すと分からなくなりそうなので補足。
ng-modelにある値が同じ場合、そのタグは別のタグの操作を反映して連動する。
ng-optionはSelectタグのoption。最初のdataが最終的にvalueに入る変数。(num, data)は{{pj_list}}配列の1データ。key,value形式なので(key, value)のように書いている。
どこかのサイトを見る限り、keyの値は勝手に振られるらしい。

zeppelin7.0から手順からなくなっているけど、npmインストールしたらtags-inputも使えるようになるのかな。

ZeppelinでNotebookを開くと別サイトにリダイレクトされちゃう問題

angularを使ったりなどで、Webサイトを丸ごと生成しようとするとハマってしまう。

一度生成してしまったらWeb画面から削除できなくなってしまうので、正直バグじゃないかと思うが対処法。
適当に調べてみても見つからなかった。
この時期にZepplinを使うような人はさすがに自己解決できるのかな。

cd ./zeppelin/notebook/
ll ./**/*

-rw-r--r-- 1 15437 Sep 17 19:31 ./2A94M5J1Z/note.json
-rw-r--r-- 1 39530 Sep 17 19:31 ./2BQA35CJZ/note.json
-rw-r--r-- 1 5922 Sep 17 14:07 ./2BVW41M8Q/note.json
-rw-r--r-- 1 311701 Sep 17 11:54 ./2BWVKB8MT/note.json
-rw-r--r-- 1 106937 Sep 17 19:29 ./2BWYU34J7/note.json
-rw-r--r-- 1 48399 Sep 17 12:11 ./2BX45R6Q9/note.json
-rw-r--r-- 1 43073 Sep 17 15:42 ./2BX54X9C4/note.json

grep -R "/test\"" ./*

Zeppelinの仕様として、
一度生成したものはサーバ上にデータを確保しておくことで、サーバを再起動してもコマンドをキックすることなく過去の結果が表示される。
なので、デバッグ中にリダイレクトされてしまうような結果が保持されてしまった場合にはWeb画面上からはどうにもできない。
なので、直接サーバ上に保持されているファイルを修正する。

上記の結果を見ていただければわかるが、notebook単位で分かれているものの、notebookの名前で保持されているわけではない。
今回は、/xxx/test/というnotebookを作っていたため、最後にgrepを行って対象のnotebookを特定している。

拡張子から見てわかる通り、notebookの内容は全てnote.jsonで保持されている。
結果は”msg”というkeyで保持されているので、そこの内容を削除する。

vi ./xxxxx/note.json
/msg
削除したい先頭位置からd$で末尾まで削除する。(””で囲まれているため、最後に”を追加しましょう。)

最後に、メモリ上に展開されている内容をクリアするためにzeppelinの再起動。

これで何とか復旧。。。

CentOS7.2 + Zeppelin0.7.0 + Spark2.0 + R3.3.1 + RMeCab

3度目のZeppelinインストール。なぜこんなことに。
毎回、はまるポイントが異なって色々気づけることが多いのは良いことかもしれない。

今回はZeppelin上でRのtable関数がうまく動かないので、SparkのVersionを1.6から2.0にあげる。
という名目。
Zeppelinがわかってきたので無駄なインストールたちも省いていく。
色々ごにょごにょやればtable関数もうまく動くようだけど、新しいのに乗り換えてうまくいくならそれでいいよね。
Overviewにそれっぽいことかいているし。
※この記事がUPされるころにはうまくいってるのは確認済みです。

過去記事
CentOS7.2へZeppelin0.7.0のインストール

過去記事にもあるけど、参考にした公式
Spark2.0が出たばかりの頃はなかったのに、いつの間にかSpark2.0も反映されている。

■事前準備

yum update
yum install git
yum install java-1.8.0-openjdk-devel
yum install npm
yum install fontconfig-devel

curl -O http://www.eu.apache.org/dist/maven/maven-3/3.3.9/binaries/apache-maven-3.3.9-bin.tar.gz
sudo tar -zxf apache-maven-3.3.9-bin.tar.gz -C /usr/local/
sudo ln -s /usr/local/apache-maven-3.3.9/bin/mvn /usr/local/bin/mvn

mavenは8Mくらいだけど遅い。
と思ったけど、さくらのクラウドの問題だったぽい。
Cloud環境によってはイメージが異なるので、一部インストールが要らなかったりなど微妙な違いがあるのが許せない。

■Rインストール
毎回ここでハマるのと、Rをめっちゃ使うことがわかってきたので今回は解決させる。

yum --enablerepo=epel -y install R R-devel libcurl-devel openssl-devel

+ devtools with `R -e "install.packages('devtools', repos = 'http://cran.us.r-project.org')"`
+ knitr with `R -e "install.packages('knitr', repos = 'http://cran.us.r-project.org')"`
+ ggplot2 with `R -e "install.packages('ggplot2', repos = 'http://cran.us.r-project.org')"`
+ Other vizualisation librairies: `R -e "install.packages(c('devtools','mplot', 'googleVis'), repos = 'http://cran.us.r-project.org'); require(devtools); install_github('ramnathv/rCharts')"`

一時的にリポジトリを有効にしてインストールするっていうのが、イマイチわかりにくい。
名前の重複を避けるためだとか、公式にサポートしていないなど事情はあるんだろうけど、もうちょっとわかりやすくならないものか。

■Rの”evavlute”をインストール
インストールしないと、Zeppelinビルド時に後述のエラーが発生する。
せっかくなので公式サイトが推奨しているのも何も考えず突っ込む。
RMeCabは後程。

`R -e "install.packages(c('evaluate','glmnet','pROC','data.table','caret','sqldf','wordcloud'), repos = 'http://cran.us.r-project.org')"`

なんか失敗している。。。でも関係なさそうだから無視。

Making 'packages.html' ... done

The downloaded source packages are in
        ‘/tmp/RtmprxNFFF/downloaded_packages’
Updating HTML index of packages in '.Library'
Making 'packages.html' ... done
ERROR: option '-g' requires an argument

■Zeppelinインストール
Hadoopに関してはSparkだけで使ってた時からハマってまともに解消するきがないので、とりあえず簡単に動くCDH版を使う。

git clone https://github.com/apache/zeppelin.git
cd zeppelin/

mvn clean package -Pspark-2.0 -Pr -Dhadoop.version=2.6.0-cdh5.5.0 -Pyarn -Ppyspark -Psparkr -Pvendor-repo -Pmapr51 -DskipTests

“evavlute”をインストールしていないと発生するエラー

[INFO] --- exec-maven-plugin:1.2.1:exec (default) @ zeppelin-zrinterpreter_2.10 ---
+++ dirname R/install-dev.sh
++ cd R
++ pwd
+ FWDIR=/root/zeppelin/r/R
+ LIB_DIR=/root/zeppelin/r/R/../../R/lib
+ mkdir -p /root/zeppelin/r/R/../../R/lib
+ pushd /root/zeppelin/r/R
+ R CMD INSTALL --library=/root/zeppelin/r/R/../../R/lib /root/zeppelin/r/R/rzeppelin/
ERROR: dependency 'evaluate' is not available for package 'rzeppelin'
* removing '/root/zeppelin/R/lib/rzeppelin'
[INFO] ------------------------------------------------------------------------
[INFO] Reactor Summary:
[INFO]
[INFO] Zeppelin ........................................... SUCCESS [ 13.457 s]
[INFO] Zeppelin: Interpreter .............................. SUCCESS [ 27.633 s]
[INFO] Zeppelin: Zengine .................................. SUCCESS [ 14.334 s]
[INFO] Zeppelin: Display system apis ...................... SUCCESS [ 33.765 s]
[INFO] Zeppelin: Spark dependencies ....................... SUCCESS [01:32 min]
[INFO] Zeppelin: Spark .................................... SUCCESS [01:09 min]
[INFO] Zeppelin: Markdown interpreter ..................... SUCCESS [  1.031 s]
[INFO] Zeppelin: Angular interpreter ...................... SUCCESS [  0.644 s]
[INFO] Zeppelin: Shell interpreter ........................ SUCCESS [  1.079 s]
[INFO] Zeppelin: Livy interpreter ......................... SUCCESS [  1.440 s]
[INFO] Zeppelin: HBase interpreter ........................ SUCCESS [  8.939 s]
[INFO] Zeppelin: PostgreSQL interpreter ................... SUCCESS [  1.323 s]
[INFO] Zeppelin: JDBC interpreter ......................... SUCCESS [  2.281 s]
[INFO] Zeppelin: File System Interpreters ................. SUCCESS [  3.271 s]
[INFO] Zeppelin: Flink .................................... SUCCESS [ 13.398 s]
[INFO] Zeppelin: Apache Ignite interpreter ................ SUCCESS [  1.843 s]
[INFO] Zeppelin: Kylin interpreter ........................ SUCCESS [  1.182 s]
[INFO] Zeppelin: Python interpreter ....................... SUCCESS [  1.048 s]
[INFO] Zeppelin: Lens interpreter ......................... SUCCESS [  7.611 s]
[INFO] Zeppelin: Apache Cassandra interpreter ............. SUCCESS [01:47 min]
[INFO] Zeppelin: Elasticsearch interpreter ................ SUCCESS [  7.592 s]
[INFO] Zeppelin: BigQuery interpreter ..................... SUCCESS [  1.544 s]
[INFO] Zeppelin: Alluxio interpreter ...................... SUCCESS [  4.551 s]
[INFO] Zeppelin: web Application .......................... SUCCESS [02:08 min]
[INFO] Zeppelin: Server ................................... SUCCESS [ 42.821 s]
[INFO] Zeppelin: Packaging distribution ................... SUCCESS [  5.805 s]
[INFO] Zeppelin: R Interpreter ............................ FAILURE [ 43.638 s]
[INFO] ------------------------------------------------------------------------
[INFO] BUILD FAILURE
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 10:39 min
[INFO] Finished at: 2016-08-27T19:33:15+09:00
[INFO] Final Memory: 232M/591M
[INFO] ------------------------------------------------------------------------
[WARNING] The requested profile "Scala-2.11" could not be activated because it does not exist.
[ERROR] Failed to execute goal org.codehaus.mojo:exec-maven-plugin:1.2.1:exec (default) on project zeppelin-zrinterpreter_2.10: Command execution failed. Process exited with an error: 1 (Exit value: 1) -> [Help 1]
org.apache.maven.lifecycle.LifecycleExecutionException: Failed to execute goal org.codehaus.mojo:exec-maven-plugin:1.2.1:exec (default) on project zeppelin-zrinterpreter_2.10: Command execution failed.
        at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:212)
        at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:153)
        at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:145)
        at org.apache.maven.lifecycle.internal.LifecycleModuleBuilder.buildProject(LifecycleModuleBuilder.java:116)
        at org.apache.maven.lifecycle.internal.LifecycleModuleBuilder.buildProject(LifecycleModuleBuilder.java:80)
        at org.apache.maven.lifecycle.internal.builder.singlethreaded.SingleThreadedBuilder.build(SingleThreadedBuilder.java:51)
        at org.apache.maven.lifecycle.internal.LifecycleStarter.execute(LifecycleStarter.java:128)
        at org.apache.maven.DefaultMaven.doExecute(DefaultMaven.java:307)
        at org.apache.maven.DefaultMaven.doExecute(DefaultMaven.java:193)
        at org.apache.maven.DefaultMaven.execute(DefaultMaven.java:106)
        at org.apache.maven.cli.MavenCli.execute(MavenCli.java:863)
        at org.apache.maven.cli.MavenCli.doMain(MavenCli.java:288)
        at org.apache.maven.cli.MavenCli.main(MavenCli.java:199)
        at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
        at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
        at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
        at java.lang.reflect.Method.invoke(Method.java:498)
        at org.codehaus.plexus.classworlds.launcher.Launcher.launchEnhanced(Launcher.java:289)
        at org.codehaus.plexus.classworlds.launcher.Launcher.launch(Launcher.java:229)
        at org.codehaus.plexus.classworlds.launcher.Launcher.mainWithExitCode(Launcher.java:415)
        at org.codehaus.plexus.classworlds.launcher.Launcher.main(Launcher.java:356)
Caused by: org.apache.maven.plugin.MojoExecutionException: Command execution failed.
        at org.codehaus.mojo.exec.ExecMojo.execute(ExecMojo.java:362)
        at org.apache.maven.plugin.DefaultBuildPluginManager.executeMojo(DefaultBuildPluginManager.java:134)
        at org.apache.maven.lifecycle.internal.MojoExecutor.execute(MojoExecutor.java:207)
        ... 20 more
Caused by: org.apache.commons.exec.ExecuteException: Process exited with an error: 1 (Exit value: 1)
        at org.apache.commons.exec.DefaultExecutor.executeInternal(DefaultExecutor.java:377)
        at org.apache.commons.exec.DefaultExecutor.execute(DefaultExecutor.java:160)
        at org.codehaus.mojo.exec.ExecMojo.executeCommandLine(ExecMojo.java:610)
        at org.codehaus.mojo.exec.ExecMojo.execute(ExecMojo.java:352)
        ... 22 more
[ERROR]
[ERROR] Re-run Maven using the -X switch to enable full debug logging.
[ERROR]
[ERROR] For more information about the errors and possible solutions, please read the following articles:
[ERROR] [Help 1] http://cwiki.apache.org/confluence/display/MAVEN/MojoExecutionException
[ERROR]
[ERROR] After correcting the problems, you can resume the build with the command
[ERROR]   mvn  -rf :zeppelin-zrinterpreter_2.10

■簡単に動作確認

./bin/zeppelin-daemon.sh start
systemctl status firewalld
firewall-cmd --list-all
firewall-cmd --add-port=8080/tcp --zone=public --permanent
firewall-cmd --reload

■設定変更するファイルのバックアップなど

cp -p ./conf/zeppelin-site.xml.template ./conf/zeppelin-site.xml
cp -p ./conf/zeppelin-env.sh.template ./conf/zeppelin-env.sh
cp -p ./conf/shiro.ini ./conf/shiro.ini.org

Login機能の有効化

shiro.ini

[users]
#admin = password1, admin
#user1 = password2, role1, role2
#user2 = password3, role3
#user3 = password4, role2

[urls]
/api/version = authc
/api/interpreter/** = authc, roles[admin]
/api/configurations/** = authc, roles[admin]
/api/credential/** = authc, roles[admin]
/** = authc

[users]領域
デフォルトのユーザをコメントアウト。
その後独自のユーザパスワード、Roleを設定。

[urls]領域
全部承認が必要なように修正。
interpreter,configureations,credentialなどいじられると困るのでadmin権限がないとダメなように設定。
※この設定だと外部へのLink Paragraphができないのでもったいない。

zeppelin-site.xml

<property>
  <name>zeppelin.anonymous.allowed</name>
  <value>false</value>
  <description>Anonymous user allowed by default</description>
</property>

anonymousの許可を無効化(valueをtrue→false)

RMeCabのインストール(日本語形態素解析)

公式情報

以下、mecab-0.996.tar.gz,mecab-ipadic-2.7.0-20070801.tar.gzダウンロードした前提で手順を記載

tar zxfv mecab-0.996.tar.gz
cd mecab-0.996
./configure --with-charset=utf8
make
make install
cd ..
tar zxfv mecab-ipadic-2.7.0-20070801.tar.gz
cd mecab-ipadic-2.7.0-XXXX
./configure --with-charset=utf8
make
/usr/local/libexec/mecab/mecab-dict-index -f euc-jp -t utf-8
make install
cd ..

上記手順でMeCabをサーバにインストールする。

RとMeCabを連携させる

echo "/usr/local/lib"  >> /etc/ld.so.conf.d/R-x86_64.conf
ldconfig
R
Sys.getlocale()
Sys.setlocale("LC_ALL", 'en_US.UTF-8')
install.packages("RMeCab", repos = "http://rmecab.jp/R")
RMeCabC("すもももももももものうち")
q()

R言語おまけ

R言語の設定

listenファイルのメッセージ列から情報を取得し、名詞だけを取り出す。


listen <- read.table("listen.sql", header=T, sep=";")
listen["message"]

library(RMeCab)

b <- RMeCabDF(listen, "message", 1)
b2 = unlist(b)
b2[names(b2) == "名詞"]

これで、下記の問題は解消。
http://stackoverflow.com/questions/33311240/using-sparkr-jvm-to-call-methods-from-a-scala-jar-file