2008年10月25日土曜日

Amazon EC2のWindowsを使ってみた

Amazon AWSのEC2でWindowsが使えるようになったので早速試してみた。
普通に起動して普通にリモートデスクトップで接続できたわけで、普段使っているWindowsと何か違うかというと何も違わない。もちろん、普段使っているのはクライアント版のWindowsでEC2ではサーバ版という違いはあるけど。

ところが、致命的な欠点を発見。

いまのところEC2で使えるイメージ(AMI)は英語版Windowsしかないようで、日本語の表示も入力も一切できない。日本語のキーボードレイアウトすら選択できない。インストールメディアのイメージがどこかにあれば言語の追加インストールもできるが、手元にWindows Serverのメディアはないし、あったとしてもイメージ化してアップロードなんてやっぱりダメだろうな。

EC2でサイトイメージのキャプチャでも作ろうと思ってたのに日本語が表示できないんじゃどうしようもない。頼むから日本語版のイメージ作ってくれ、ほんとに。

-- 追記 (2008/11/3) --

WindowsのインストールメディアはEBSのスナップショットとして用意してあった。AWSのResourcesのArticles&Tutrialsに「Configuring Windows Components on Amazon EC2」という記事に書いてあった。このスナップショットからEBSボリュームを作成してWindowsのインスタンスにアタッチすると各種コンポーネントのインストールが可能になる。

2008年8月23日土曜日

FlashCS3からBlazeDSを呼び出す

FlashCS3にはFlexのようなRemoteObjectがないのでBlazeDSのサービスを呼び出せないのかと思っが、どうやら方法があるようだ。

FlashではNetConnectionを使ってリモートメソッドのcallができる。これを簡単に行う「Strippers Remoting Classes」というライブラリがある。使い方は「Flash | Remoting Classes for Flash CS3 ActionScript 3.0」を参照。



2008年7月2日水曜日

ivy.xmlのconfの使い方

confの基本

Ivyで一番難しいのはconfの使いこなし方だと思う。confは、たとえばコンパイル時と実行時でライブラリのセットを切り替えたい場合などに使う。

configurationsを書かなければデフォルトのconfである"default"が1つ作られる。明示的に書く場合

<configurations>
    <conf name="compile" />
    <conf name="runtime" />
</configurations>

などと書き、コンパイル時とランタイム時に分けることができる。しかし、ただconfigutationsを書いただけでは意味がない。依存性ごとにどのconfに紐付くのかを指定する必要がある。

<depandencies>
    <dependency org="javaee" name="javaee-api" rev="5" conf="compile"/>
    <dependency org="commons-betwixt" name="commons-betwixt" rev="0.8" conf="compile;runtime"/>
</dependencies>

上のように書くと、javaee-apiはコンパイル時だけに必要でbetwixtはコンパイル時、実行時に含まれることになる。

build.xmlのretrieveタスクでパターンを設定するとconf別のライブラリディレクトリが出来上がる。

<ivy:retrieve pattern="${ivy.lib.dir}/[conf]/[artifact].[ext]" sync="true"/>

confのマッピング

でも残念なことに上記のような書き方でantするとjavaee-apiのところで警告が出てその先の依存性が解決できない。 なぜかと言うと自分のプロジェクトに複数のconfがあるように依存相手のプロジェクトにも複数のconfがあるから。上記javaee-apiのconfはこちらのcompile設定に結びつくのと同時に相手のcompile設定にも結びついてしまう。これを実行したときのivysettings.xmlはJava.Netリポジトリのpomを読まない設定なのでローカルリポジトリに自動的にjavaee-api用のivy.xmlができる。このivy.xmlには"default"設定1つだけが定義されているのでcompile設定では依存性が解決できない。

ではどうするかというと

<dependency org="javaee" name="javaee-api" rev="5" conf="compile->default"/>

のように "自分のconf名->相手のconf名" と言う形でconfのマッピングをしてやる。

Mavenのscopeのように標準的な名前があればいいのだけどIvyのconfはそれぞれのプロジェクトで勝手に名前がつけられるので、依存先のivy.xmlを見ないとconfの設定が書けない。でも大抵はMaven2のリポジトリを使うことになるのでpomから生成されたお決まりのconfパターンになる。こういうときはconfigurations要素のdefaultconfmapping属性にマッピングを書いておくことでいちいちdependencyにconfマッピングを書かなくても済む。

マッピングいろいろ

調査中なので以下嘘かも。
詳しくはIvyドキュメントのdependencyのリファレンスに書いてある。

複数のconfを複数のconfにマッピング。A, B, Cのどのconfでもx, y両方が含まれる。
"A,B,C->x,y"

複数のマッピングを書くとき。
"A->x;B->y"

ワイルドカード指定もできる。confがAのとき、依存先のすべてのconfを含む。
"A->*"

confのマッピングを書かなかった場合、すべてのconfに依存先のすべてのconfが含まれる。
"*->*"

除外の指定。A, B以外すべてのときxにマッピング。
"*, !A, !B -> x"

Aのときはx, それ以外のときはyにマッピング。
"A->x;%->y"

フォールバック。Aのときxにマッピングするが、xがなかったら*にマッピング。
"A->x(*)"

Ivyの設定

ivysettings.xml

<ivysettings>
    <settings defaultResolver="default-chain"/>
        <resolvers>
        <chain name="default-chain" returnFirst="true">
            <ibiblio name="ibiblio" m2compatible="true" />
                ... その他のリポジトリ
        </chain>
    </resolvers>
</ivysettings>

主なリポジトリ

Maven2用のリポジトリは、なぜかUrl resolverでは直接指定したライブラリだけがダウンロードされ、その先の依存性の解決をしてくれない。Ibiblio resolverを使うとpomを読んで依存性を解決してくれる。

■ibiblio

まず、これが基本

<ibiblio name="ibiblio" m2compatible="true" />

■ibiblioミラー

ミラーのほうが遅い気がする。

<ibiblio name="ibiblio-mirror" m2compatible="true" root="http://mirrors.ibiblio.org/pub/mirrors/maven2/" />

■Java.Net (JavaEE APIの取得用)

<url name="java-net">
    <artifact pattern="http://download.java.net/maven/1/[module]/jars/[artifact]-[revision].[ext]"/>
</url>

ivy.xmlで

<dependency org="javaee" name="javaee-api" rev="5" />

と書くと、javaee-api.jarがダウンロードできる。

■Seasar

<ibiblio name="seasar" m2compatible="true" root="http://maven.seasar.org/maven2/" />

■JBoss

<ibiblio name="jboss" m2compatible="true" root="http://repository.jboss.com/maven2/" />

2008年6月29日日曜日

IvyはMavenアレルギーの特効薬かもしれない

Apache AntプロジェクトにIvyというものが統合されるらしい。

IvyはMaven2のライブラリ依存関係の解決部分だけを抜き出したようなもの。Ivyの特徴は

  • Maven2のリポジトリが使える
  • ライブラリのJarはプロジェクトのlibディレクトリにコピーされる
  • Antタスクのひとつとして実行されるので今まで作ったAntスクリプトが無駄にならない

MavenのようにすべてをMavenにあわせてプロジェクトを作る必要がないので自由度が高い。

参考記事

万人のためのオートメーション: Ivy による依存関係の管理



2008年6月22日日曜日

Joda Time

Javaの日付ライブラリ。JSR310はこれを参考にしているらしい。

ISO8601形式の文字列とDateTimeオブジェクトの相互変換

DateTimeFormatter fmt = ISODateTimeFormat.dateTime();

パース

DateTime dt = fmt.parseDateTime(strInputDateTime);

文字列にするときは

String strOutputDateTime = fmt.print(dt);



2008年6月10日火曜日

EJB3.0のセッションBeanをJNDIで取得する方法

ここにいろいろ書いてある
https://glassfish.dev.java.net/javaee5/ejb/EJB_FAQ.html


ローカルEJBの場合

クライアントコンテナがインジェクションしてくれる場合、@EJBアノテーションを書く。@EJBのname属性は<ejb-ref-name>に相当。指定しなければルールに従って自動的につけられる。

@EJB(beanInterface=FooLocal.class)

Webフレームワークなどを使っていてServletに自分のアノテーションをつけられない場合はweb.xmlで参照名の定義をする。

<ejb-local-ref>
    <ejb-ref-name>ejb/fooejb</ejb-ref-name>
    <local>abc.def.FooLocal</local> <!-- ローカルインターフェイスの完全修飾名 -->
    <ejb-link>FooBean</ejb-link> <!-- EJBのJNDI名 -->
</ejb-local-ref>

Contextから取得

InitialContext ctx = new InitialContext();
FooLocal foo = (FooLocal)ctx.lookup("java:comp/env/ejb/fooejb");



リモートEJBの場合

クライアントコンテナを使う場合は@EJBアノテーションでインジェクションされる

@EJB(beanInterface=FooRemote.class)

クライアントコンテナを使わない場合JNDIから自前でルックアップする。

props = JNDIリモート参照の設定。後述。
InitialContext ctx = new InitialContext(props);
FooRemote foo = (FooRemote)ctx.lookup("com.example.FooRemote");

JNDIの設定

クラスパスにjndi.propertiesファイルを含めるか、InitialContextの引数にPropertiesを渡す。また、クライアント側プログラムのCLASSPATHにサーバ製品に対応するライブラリを含める。

設定するプロパティ

GrassFishの場合

org.omg.CORBA.ORBInitialHost=hostname
org.omg.CORBA.ORBInitialPort=3700
ホスト、ポートのデフォルトはlocalhost:3700

ライブラリ

appserv-rt.jar
javaee.jar

CLASSPATHに明示的に書く場合は上記の2つだけでいいが、appserv-rt.jarのMANAFEST.MFでさらに以下のファイルが指定されているのでappserv-rt.jarと同じディレクトリに入れておく

appserv-ext.jar
appserv-deployment-client.jar
jmxremote_optional.jar
appserv-rt_ja.jar
appserv-rt_zh.jar
appserv-rt_fr.jar
appserv-rt_de.jar
appserv-rt_es.jar
appserv-rt_it.jar
appserv-rt_sw.jar
appserv-rt_ko.jar
appserv-rt_zh_TW.jar
appserv-rt_zh_CN.jar


JNDI名の定義

EJB3.0のデフォルトのJNDI名はリモートインターフェイスの完全修飾名。
JNDI名を指定する場合は@Stateless, @Statefullの引数に書く
@Stateless(mappedName="FooEJB")

参考記事

Java EE 5チュートリアル:EJB3 セッション・ビーン編(2) 〜EJBクライアント〜