Strutsメモ3

昔 作成
2003/8/8 更新

.doの変更

アクションへのマッピングを変更可能です。 これはweb.xmlの変更で行います。

.do(デフォルト)
hoge.do→hoge
  <servlet-mapping>
    <servlet-name>action</servlet-name>
    <url-pattern>*.do</url-pattern>
  </servlet-mapping>
.ctrl
hoge.ctrl→hoge
  <servlet-mapping>
    <servlet-name>action</servlet-name>
    <url-pattern>*.ctrl</url-pattern>
  </servlet-mapping>
/do/...
/do/hoge→hoge
  <servlet-mapping>
    <servlet-name>action</servlet-name>
    <url-pattern>/do/*</url-pattern>
  </servlet-mapping>
.doから.ctrlへの変更は単に気分の問題でしょう。 /do/への変更は、いろいろと利点があるようです (拡張子を.xlsにしといて、ブラウザにXLSと認識させるとか、 パスが見やすい?とか)。

htmlタグでのリンク

Strutsでリンクを書くとき、<html:link>タグを使います リンク方法の指定は大きく3種類あります。
page Webアプリケーションのルートから指定できます。
href a hrefで指定した場合と同じです。絶対URL(他のサイト)を指定したり、
<html:base/>と一緒に使い、同じディレクトリのJSPを指定します。
forward Global Fowardに指定した値にマッピングさせます。
通常はpageを使い、ちょっと工夫したい時はhrefも使い、 JSPのパスをJSPファイルから完全に分離したいときは、すべてfowardを使う、 といった感じでしょうか?
a href
<a href="hoge.jsp">hoge.jsp</a>baseから相対
<a href="/hoge.jsp">/hoge.jsp</a>ルートから
<a href="http://muimi.com">http://muimi.com</a>完全指定

link
<html:link forward="menu">forward=menu</html:link>global action-forwardの名前
<html:link href="/hoge.jsp">href=/hoge.jsp</html:link>a hrefと同じ。ルート
<html:link href="hoge.jsp">href=hoge.jsp</html:link>a hrefと同じ。相対
<html:link page="/hoge.jsp">page=/hoge.jsp</html:link>Webコンテキストルートから
<html:link page="hoge.jsp">page=hoge.jsp</html:link>誤った用法
html:linkタグを使えないような場面(JavaScriptで遷移先を指定したり)では、 <html:rewite>を使うことができます。 rewriteでも上の3つの遷移方法を指定できます。

フォーム内でネストしたクラス

フォームの中で同じ入力項目が複数出現する場合があります。 そんなときにフォームの中で別のクラスを定義する技がけっこう使えます。

年月日を複数指定するフォームを考えてみましょう。
年月日を表すクラスを作ります。
public class FormDate {
  private String year;	
  private String month;
  private String day;	
  //セッタとゲッタは省略...
}
フォームのフィールドで他のStringフィールド同様にそれを使います。
public class HogeForm extends ActionForm{
  private FormDate date1 = new FormDate();
  private FormDate date2 = new FormDate();
  //セッタとゲッタは省略...
}
指定するネストしたクラスのフィールドは必ず初期化しておく必要があります。 でないと、JSPコンパイル時にvalueがnullだよといったエラーが表示されます (これでちょっとハマった)。

JSPの方はこんな感じ
<html:form action="hoge">
  配達希望日1
  <html:text property="date1.year" size="6" maxlength="4"/>年
  <html:text property="date1.month" size="4" maxlength="2"/>月
  <html:text property="date1.day" size="4" maxlength="2"/>日
  <br>

  配達希望日2
  <html:text property="date2.year" size="6" maxlength="4"/>年
  <html:text property="date2.month" size="4" maxlength="2"/>月
  <html:text property="date2.day" size="4" maxlength="2"/>日
<html:form>
上の太字部分のproperty="date1.year"という書き方が面白いところです。
内部的に
getData1().getYear();
//getData1().setYear(入力値);
といった感じでフィールドが取得、設定されるようです(リフレクションで)。 この.(ドット)区切りでネストしたプロパティーを指定できるのが素敵だと思いました。

コンボボックス

<html:select>タグを使ってコンボボックスを作成できます。 選択肢(option)は、ネストした<html:options>や<html:optionsCollection>タグを利用できます。 optionの値と表示名は、それぞれをリストで指定する方法と、値と表示名を持つビーンを指定する方法があります。 ここでは、optionsCollectionタグとビーンを使う方法を紹介します。こんな感じ↓です。 ここではorg.apache.struts.util.LabelValueBeanを利用しています(その他のビーンも可です)。

select、optionsCollectionタグの記述例

<%
//アプリケーションスコープにListや配列で値を埋めます。
//本来、サーブレットやリスナーで実行します。
LabelValueBean[] data = new LabelValueBean[]{
  new LabelValueBean("赤", "red"),
  new LabelValueBean("青", "blue"),
  new LabelValueBean("黄", "yellow"),
};
application.setAttribute("data", data);
%>

<html:form action="/hoge">
  <html:select property="hoge" size="1">
    <html:optionsCollection name="data" />
    </html:select>
  <html:submit/>
</html:form>

上記を実行した際、表示されるHTMLのソース

<form name="hogeForm" method="post" action="/struts1/hoge.do">
  <select name="hoge" size="1">
    <option value="red" selected="selected">赤</option>
    <option value="blue">青</option>
    <option value="yellow">黄</option></select>
  <input type="submit" value="Submit">
</form>

参考
http://www.techscore.com/tech/Java/Struts/7.html

ファイルアップロード

Strutsではファイルのアップロードは、 <html:file>タグと org.apache.struts.upload.FormFileクラスを使う ことで、簡単に実現できます。 簡単な例が、Strutsのサンプルstruts-upload.warにシンプルな例が載っています。

ここでは、複数ファイルをUploadする例を示します。
まずActionFormクラスのフィールドにFormFileフィールドを定義します。 ここでは複数ファイルをUploadするために、配列で定義しています。
public class UploadForm extends ActionForm {
  private FormFile[] files = new FormFile[3];
  //セッタとゲッタは省略...
}
JSPでは以下のようなフォームを作ります。
<html:form action="upload" enctype="multipart/form-data">
  File1<html:file property="files[0]" /><br>
  File2<html:file property="files[1]" /><br>
  File3<html:file property="files[2]" /><br>
  <html:submit />
</html:form>
submitするとActionクラスが呼ばれます。
public ActionForward perform(
  ActionMapping mapping,
  ActionForm form,
  HttpServletRequest req,
  HttpServletResponse res)
  throws IOException, ServletException {

  UploadForm theForm = (UploadForm) form;

  FormFile[] files = theForm.getFiles();
  
  for(int i=0; i<files.length; i++){
    FormFile file = files[i];
    System.out.println("file" + i + ":"
              + "name=" + file.getFileName()
              + ",size=" + file.getFileSize());
    //...
  }

  //...
}

補足
JSPにcharsetを指定していても日本語ファイル名は文字化けます。 取得したファイル名に対し、いつものやつgetBytes()...new String()... すれば直ります。

次のページへ

(2002/9/12)


もどる