2014年6月24日火曜日

jmxtermで手軽にJMX経由でmbeanの値を見てみる

ちょっと凝ったことをしたいときは、Javaだったり、JRubyなんかでスクリプト書いたほうがいいと思うんだけど。。。

単純に特定の値を見たい、そんなときはコマンドラインでカジュアルにチェックできると嬉しいよね、ってことで、jmxtermです。

ちなみに、グラフとか見たい時はJConsoleもいいけど、VisualVMのほうが見た目がよいね。最近のJavaならJAVA_HOME/bin配下にjvisualvmってのがあるから、そいつです。

 (閑話休題)

というわけで、チートシート風に。例では、hazelcastの値を取っていますが、別にhazelcastでなくてももちろんかまいません。

JMXを有効にするには、最低4つJVMの起動パラメータに追加してください。
(あたりまえだけど、外に晒される環境でああれば、適切なアクセス制限してください)

-Dcom.sun.management.jmxremote 
-Dcom.sun.management.jmxremote.port=適当に
-Dcom.sun.management.jmxremote.ssl=false
-Dcom.sun.management.jmxremote.authenticate=false

で、JVMを起動させたら、繋いでみる。
インタラクティブシェルとして操作もできるけど、パイプからコマンド投げたほうがなにかと便利。
javaが実行できる環境で叩いてください。これはMacで使用している例。

// ドメイン一覧
echo domains | java -jar ./jmxterm-1.0-alpha-4-uber.jar -l host:port
 
// bean一覧
echo beans -d com.hazelcast | java -jar ./jmxterm-1.0-alpha-4-uber.jar -l host:port
 
// info取得
echo 'info -b instance=sessions,name=hoge,type=IMap -d com.hazelcast' | java -jar ./jmxterm-1.0-alpha-4-uber.jar -l host:port
 
// 対象の値全部
echo 'get -b instance=sessions,name=hoge,type=IMap -d com.hazelcast *' | java -jar ./jmxterm-1.0-alpha-4-uber.jar -l host:port
 
// 特定の値
echo 'get -b instance=sessions,name=hoge,type=IMap -d com.hazelcast localHeapCost' | java -jar ./jmxterm-1.0-alpha-4-uber.jar -l host:port
 
// keyは要らんからvalueだけ
echo 'get -b instance=sessions,name=hoge,type=IMap -d com.hazelcast -s localHeapCost' | java -jar ./jmxterm-1.0-alpha-4-uber.jar -l host:port


らくちんですなー

2014年6月16日月曜日

JavaでUTF-8 with BOMなファイルでBOMを取ってみる

T/O なんだけど、標準APIでなんかいいのないのかね?

import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
public class RemoveBom {
public static void main(String[] args) throws IOException {
String result = "";
boolean first = true;
for (String str : Files.readAllLines(Paths.get(args[1]), StandardCharsets.UTF_8)) {
if (first) {
str = removeBom(str);
first = false;
}
result += str;
}
// resultをなんかする
}
private static String removeBom(String str) {
if (str.startsWith("\uFEFF")) {
str = str.substring(1);
}
return str;
}
}
view raw 2014.06.16.java hosted with ❤ by GitHub

2014年5月16日金曜日

Excelからのcsvをjava.nioで読んだらMalformedInputException

環境

  • Mac OS X Lion
  • Java 7
  • 元ファイルは素性のしれないxlsx
  • Excel 2011

経緯


素性のしれないxlsxをExcelでcsvにした

こんな読み込みをしていて
localPath = "fuga.csv"
List<String> hoge = Files.readAllLines(Paths.get(localPath), Charset.defaultCharset());
view raw 2014.05.16.java hosted with ❤ by GitHub
こんな例外が

java.nio.charset.MalformedInputException: Input length = 1

元のファイルを見てみる

$ file --mime fuga.csv
fuga.csv: text/plain; charset=unknown-8bit

unknownとかいっちゃってる。

sublime Textで、UTF-8 で保存しなおす。

$ file --mime fuga.csv
fuga.csv: text/plain; charset=utf-8

わーい。
これで読み込めた。


追記

そもそもなんだけど、Excelでcsv出力すると、S-JIS(固定)らしい。

別件で、InputStream扱うときに

BufferedReader br = new BufferedReader(new InputStreamReader(hoge.getInputStream(), "SJIS"));

List<String> stringList = new ArrayList<>();
while(br.ready()) {
    stringList.add(br.readLine());
}
br.close();

とかで読み込みできた。

ちなみに、hogeはSpringのMultipartFileです。


2014年4月30日水曜日

SpringMVCのform:selectだけど、optionのlabelが使いたい

結論から言うと、妥協してるのでいい方法があったら教えて欲しい。

元のやつ

<form:select class="hoge-form" items="${hogeMap}" path="hogeId" required="required">


hogeMapはSpringMVCのControllerで定義されているMap<Integer,String>である。
上記のようなタグは、実行されるとこんな感じになる。

<select id="hogeId" name="hogeId" class="hoge-form" required="required">
<option value="1">リスト1</option>
<option value="2">リスト2</option>
</select>

このoptionのところにlabelをつけたいんだけど、form:selectだとどうにもうまくいかなくて妥協したのがコレ

<select id="hogeId" name="hogeId" required="required">
<c:forEach var="hoge" items="${hogeMap}" varStatus="hogeStatus">
<option value="${hogeMap.key}" label="${hogeStatus.index}.${hoge.value}" class="hoge-form" />
</c:forEach>
</select>

生成されるのはこんなん

<select id="hogeId" name="hogeId" required="required">
<option value="1" label="0.リスト1" class="hoge-form"></option>
<option value="2" label="1.リスト2" class="hoge-form"></option>
</select>

びみょ

追記

別途modelMapになにかのmodelがあって、form:selectのpathに指定したやつがmodelMapのmodelのプロパティにあると勝手にそれをselectedにしてくれる機能を使ってる場合は別途、<option>にこんな指定が必要です。


${(model.hogeId eq hoge.key)?'selected="selected"' : ''


2014年4月22日火曜日

Basic認証ついてるAPIをSpringのRestTemplateでPOSTするサンプル

タイトルまんま。例えばcurlで


curl http://example.com/hoget -X POST -u shase:p@$$w0rd

こんな感じで使えるAPIをRestTemplateで使おうと思った時はこんなコードでOK


package hoge;
import org.apache.commons.codec.binary.Base64;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.http.ResponseEntity;
import org.springframework.web.client.RestTemplate;
public class SampleUtil {
public static void main(String[] args) {
samplePost("http://example.com/hoget","shase", "p@$$w0rd");
}
public static void samplePost(String url,Strring user, String password) {
String plainCreds = user + ":" + password;
byte[] plainCredsBytes = plainCreds.getBytes();
byte[] base64CredsBytes = Base64.encodeBase64(plainCredsBytes);
String base64Creds = new String(base64CredsBytes);
HttpHeaders headers = new HttpHeaders();
headers.add("Authorization","Basic " + base64Creds);
HttpEntity<String> request = new HttpEntity<String>(headers);
RestTemplate restTemplate = new RestTemplate();
ResponseEntity<String> model = restTemplate.exchange(url, HttpMethod.POST, request, String.class);
// modelの中にいろいろ入っとる
}
}

こちら参考にしました(リンク先はGETの例)
http://springinpractice.com/2013/10/02/quick-tip-basic-authentication-with-spring-resttemplate

2014年4月10日木曜日

骨の折れる話

案外インターネット上に情報が少なく感じたので、親指の骨折(母指基節骨骨折)から治療までの記録を簡単に残しておこうと思います。

今丁度2回目の手術(固定ワイヤーの抜針)が終わったところです。

時間のない人向けまとめ


  • スノーボードは油断するとすぐ怪我をするので気をつけよう
  • 手の外科は専門性が高いので、「手外科専門医」がいる病院を選ぼう
  • やっぱり保険は大切
  • 手術室のBGMは先生の趣味


ま、ふつーのことなんですが。。。
こっから語り入ります。


骨折〜診断

2月のとある日曜日に、会社の同僚とスノボに行き、誰も見てないところでふつーにこけました。

こけた時に、思わず左手をついてしまったらしく、親指の付け根のあたりから腫れていて、突き指をしたような痛みがありました。

痛みはあったものの、そんな大したこともないかな〜という感じで、自力で下山してその日は新幹線で東京の自宅に帰りました。

翌日、市販の湿布をして寝て起きて、それでもやはり腫れが引いておらず、これはヒビでも入ってるかなぁ、と思い、ネットで調べて家から近い整形外科のA診療所に向かいました。

そこで撮ったレントゲンを見ながら

「折れてますねー。これは手術しないとだめですねー」

という、宣告を受けたのでした。

ひと駅隣に、手の専門医がいる病院があるとのこと。

特に手の外科手術をしてくれそうな病院に心当たりがなかったので(普通無いですよね)、紹介状を書いてもらい、午後の診察に間に合わせる感じで、その専門医のいるB病院に行ったのでした。

手外科専門医

あとから知ったのですが、手という器官はとても難しいらしく、整形外科の中でも、更に専門性が高いそうです。

手外科学会というところが、「手外科専門医」認定制度を行っていて、そこに登録されている人は一応手外科の専門医として、認められているそうです。

こちらにリストがあります。

http://www.jssh.or.jp/ippan/senmon/senmoni-meibo.html

首都圏には多い気がしますが、やっぱり地方には少ないですよねぇ。

この話もずいぶん後になってから知ったんですが、わたしを担当していただいた先生もリストにいました。
さて、その病院に行き、レントゲンを撮って、速攻で

「明日は祝日だから、明後日手術できます?」 

という話になり、ずーん、と落ち込んだのを覚えています。

なんでもやっぱり手術以外の解決方法がないとのことで、放置しておくと握力無くなる、という話でした。

セカンドオピニオンも一瞬だけ考えたんですが、最初に行ったA診療所の先生が、

「ウチでは手の骨折はこの病院を毎回紹介しているし、このへんの病院の間でも手ならB病院だね」

なーんてゆってたので、めんどくさくなってじゃあ明後日手術します。ということになりました。

その日は手術の為の血液検査とか、事前のブリーフィングとかして帰りました。

手術


人生で手術なんてしたことなかったのでガクブルだったんですが、事前の説明で

  • 日帰り手術
  • 麻酔は左腕一本(伝達麻酔?)
  • 時間は1時間ぐらい

ということだったので、まぁ、そこまででも無いのかなぁ、と思いました。

実際やってみるとしんどかったんですが。

日帰り手術なので、まず、入院して、手術着に着替え、熱を測ったり、血圧を測ったりします。

時間は結局前の患者さんの手術が押したりするとズレするので、だいたいO時ぐらい、という感じです。

ガクブルしながら暇を潰します。

そして、いざ呼ばれると、まぁ、手以外は元気なので、徒歩で手術室に向かいます。

手術室に入ると、まず患部を洗うように言われます。これも看護師さんに言われながら自分で洗います。

その後、手術台に横たわり手術。。。という流れなのですが、わたしが行った手術室では東京FMがずーっと手術中も流れていました


手術室のBGM

これもあとから知ったんですが、手術室のBGMって、先生の趣味、らしいですね。

先生によってはお気に入りのBGMを持ち込む人もいるとか、いないとか。。。

開腹のようなガチの奴はBGM無しだったりもするようです。

手術の流れとしては、麻酔〜執刀〜縫合、って感じでしょうか。

全身麻酔ではないので手術されている間意識があるんですが、金属製のワイヤーとかを扱っている関係で、

キーン、とか、バチッ(ニッパーで切る)とか金属加工音

がいちいち気になりますが、どうしようもないですよね。。。

都合2時間ほどかかったのですが、憔悴してるわたしに先生が一言

「靭帯も切れてたから縫っておいたよ」

と軽い感じで言われたのが印象的です。骨折に加えて靭帯も切れていたみたいでした(靭帯はレントゲンに映らないので開けないとわからない)。

この手術では結果ワイヤーを4本埋め込む事になりました。

術後

手術した当日の夜がしんどかったです。

麻酔が切れた途端、激しい痛みが押し寄せました

ま、切ってるから当たり前なんですが、耐えかねて痛み止めを2回分飲んだんですがそれでも痛くて、その夜は悶絶しながら寝ました

ちなみに、処方された薬は、


  • 鎮痛剤
  • 抗生物質
  • 胃薬


でした。これを5日ぐらい飲み続けます。痛みは2〜3日目からずいぶん良くなりました。
この時はギブス固定されています。

抜糸

術後一週間ぐらいで、抜糸が行われます。ハサミでチョキチョキってかんじです。まだギブスは取れません。

ワイヤーを1本抜く

術後三週間ぐらいで、1本ワイヤーを抜きました。といっても手術ではなく、

ワイヤー1本は外に露出してる

という状態でした。それをペンチでエイヤーって抜く感じですね。これはこれで痛い。

このタイミングでギブスも外れました。

リハビリ(指を動かせ)と言われるのもこの辺りから。


保険について

手術の費用としては、3割負担のおかげで、1回数万円程度でした(痛い出費ですが。。。)

スノーボード用の簡易な保険とかに入っておくのも良いかも、と今回の事件を振り返って思いました。

旅行代理店のパック旅行中の怪我だったので、通院が終わって総額が算出され次第、保険適用の申請をする予定です。

最初に通院した時に、旅行代理店に電話したところ、「事故発生報告」のような書類の提出を求められ、返信すると、各種手続きの書類が送られてきました。

通院時の領収書等を残しておいたほうが良いとの事だったので、一応全部残してあります。

再手術の日程決まる

術後六週間ぐらいで、そろそろ再手術できるかな、という話になりました。指にワイヤー3本残っており、それを撤去する手術になります。

ちょうど年度初めにかぶっていたので、わたしは1周間だけずらしました。

再手術

術後八週間ぐらいで、再手術と相成りました。今回の手術も

  • 日帰り手術
  • 局部麻酔(今度は腕ではなく、手だけ)
  • 時間は1時間ぐらい

という話でした。

基本的な流れは前回の手術と一緒なんで、端折りますけど

  • 時間はすぐ終わった(手術時間自体は10分程度)
  • 手だけの麻酔なので逆に痛い(麻酔の注射自体の痛みとか、腕に感覚があることによる痛みとか)
  • やっぱり手術室は東京FMだった
という感じで、とりあえず無事終わりました。

術後の痛みも前回に比べれば全然マシでした。でも、やっぱり憔悴してはいます。。。

最後に

今後の流れとしては
  • 抜糸
  • リハビリ
  • 術後1ヶ月ぐらいに先生の最後のチェック
  • 終了
という感じだそうです。(もちろん、予後次第というのはありますが)。

今回のことで、多くの人にご迷惑をお掛けして申し訳ないと思いつつ、また多くの人に心配して頂いて感謝の気持ちでいっぱいでした。

一気には難しいかもしれませんが、ちょっとずつ恩返しができたらなぁ、と思っています。

2014年4月3日木曜日

Springockitoのメモ(一部だけMockitoのモックに)

要旨

Spring+Mockitoを使った環境で、DIしてテストしたいときに、一部だけMockitoのモックに置き換えたい、という話。

Mockito単体だとなんかうまくいかなくて。
もしかしたら、Mockitoでも、やりかた間違ってんのか、もしくは、PowerMockとか使えばいけんのかも。

説明

このコードは、Service1の中で、Service2のメソッドが呼ばれています。
で、Service1のテストをしたいんだけど、Service2のメソッドだけモックにしたい。 しかし、Service1の他の処理はモックにしたくない。

そんなとき。
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.MockitoAnnotations;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath:applicationContext.xml")
public class SampleTest{
// error code
@InjectMocks
@Autowired
private Service1 Service1;
@Mock
@Autowired
private Service2 Service2;
@Test
public void test1() throws Exception {
MockitoAnnotations.initMocks(this);
doReturn(false).when(service2).isHoge();
service1.execute();
}
}

こんなコードで動くかなーと書いてみます。 残念ながら、このコードは動きません。

ここで、Springockitoです。
 https://bitbucket.org/kubek2k/springockito/overview


package hoge;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.kubek2k.springockito.annotations.ReplaceWithMock;
import org.kubek2k.springockito.annotations.SpringockitoContextLoader;
import org.mockito.MockitoAnnotations;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath:applicationContext.xml",
loader = SpringockitoContextLoader.class)
public class SampleTest{
//
@Autowired
private Service1 Service1;
@ReplaceWithMock
@Autowired
private Service2 Service2;
@Test
public void test1() throws Exception {
doReturn(false).when(service2).isHoge();
service1.execute();
}
}
こんな書き方ができます。

使い方

Mavenの人はpomにこんな感じで追加しといてください。
<dependency>
<groupId>org.kubek2k</groupId>
<artifactId>springockito-annotations</artifactId>
<version>1.0.9</version>
<scope>test</scope>
</dependency>

Javaでテストと言えばコレ