APITT - システム開発分野 - PBL
「開発フェーズ」

content back
参考
気づいた点
STEP1 : S2JDBC-gen で Entity を自動生成しましょう

S2JDBC-genを使うと Entity と Service を自動生成することができます。

DBで外部キーが設定されていると、S2JDBC-genはそれを認識し、結合の設定まで行ってくれます。

  1. PostgreSQL の JDBC Driver を「src/main/webapp/WEB-INF/lib」に配置します。
  2. プロジェクト直下の「s2jdbc-gen-build.xml」をダブルクリックで開きます。
  3. eclipseメニューの「Run」→「External Tools」→「External Tools Configurations」を開きます。
  4. 「And Build」をダブルクリックします。
  5. 「Arguments」に「gen-entity」と入力します。
  6. 「Run」ボタンをクリックします。

STEP2 : 検索画面の準備

とりあえず動作する画面を作ってみましょう。

まず始めに、検索機能のViewを置くフォルダを作成し、JSPファイルを作成します。

Viewを置くフォルダの作成

  1. 「src/main/webapp/WEB-INF/view/」を右クリックし「New」→「Folder」を選択します。
  2. Folder Name に例えば「sisetuSearch」と入力し「Finish」ボタンをクリック。これでフォルダが作成されます。
JSPファイルの作成(コピーして作成する場合)
  1. Scaffoldが自動生成したJSPをコピーし「src/main/webapp/WEB-INF/view/sisetuSearch」フォルダ以下に置きます。
  2. コピーしたファイルを右クリックし「Refactor」→「rename」で名前を「search.jsp」に変更します。
  3. 内容を以下のように書き換えます。
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="ja" lang="ja">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<link rel="stylesheet" type="text/css" href="${f:url('/css/global.css')}"/>

</head>
<body>
<h1>Sisetu Search</h1>

<html:errors/>

<s:form>

<div>
    sisetu : <html:text property="sisetuId"/>
</div>

<div>
    mokuteki : <html:text property="riyomokutekiId"/>
</div>

<div>
    start date : <html:text property="startDate"/>
</div>

<input type="submit" name="doSearch" value="SEARCH" />

</s:form>
<br/><br/>

</body>
</html>

STEP3 : 検索Actionの準備

次に、検索を処理する Action を準備します。

  1. Scaffoldが自動生成したAction「src/main/java/easySearch/action/SisetuAction.java」をコピーし、同じフォルダに配置します。
  2. ファイルの名前は「SisetuSearchAction.java」とします。
  3. 内容を以下のように書き換えます。
package easySearch.action;

import javax.annotation.Resource;

import org.apache.struts.action.ActionMessages;
import org.seasar.extension.jdbc.JdbcManager;
import org.seasar.extension.jdbc.where.SimpleWhere;
import org.seasar.framework.beans.util.Beans;
import org.seasar.struts.annotation.ActionForm;
import org.seasar.struts.annotation.Execute;
import java.util.List;

import easySearch.entity.Riyoumokuteki;
import easySearch.entity.Sisetu;
import easySearch.service.RiyoumokutekiService;
import easySearch.service.SisetuService;
import easySearch.form.SisetuSearchForm;

public class SisetuSearchAction {

    public JdbcManager jdbcManager;
    public List sisetuItems;
    public List riyoumokutekiItems;
    
    @ActionForm
    @Resource
    protected SisetuSearchForm sisetuSearchForm;
    
    @Execute(validator = false)
    public String index() {
        return search();
    }

    @Execute(validator = false)
    public String search() {
        return "search.jsp";
    }

    @Execute(validator = false)
    public String doSearch() {
        return "doSearch.jsp";
    }
        
    public ActionMessages validateInsert() {
        ActionMessages errors = new ActionMessages();
        return errors;
    }
    
    public ActionMessages validateUpdate() {
        ActionMessages errors = new ActionMessages();
        return errors;
    }
}

search.jspの Form とデータをやりとりするための「SisetuSearchForm.java」を作成します。

  1. 「src/main/java/easySearch/form/SisetuSearchForm.java」を作成し、以下のように記述します。
package easySearch.form;
public class SisetuSearchForm {
    public String sisetuId;
    public String riyomokutekiId;
    public String startDate;
}

STEP4 : 検索結果を表示するViewの準備

検索の実行結果を表示するための画面「doSearch.jsp」を作成します。

  1. 「src/main/webapp/WEB-INF/view/sisetuSearch/search.jsp」を、同じフォルダに「doSearch.jsp」という名前でコピーします。
  2. 「doSearch.jsp」の内容を以下のように書き換えます。
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="ja" lang="ja">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<link rel="stylesheet" type="text/css" href="${f:url('/css/global.css')}"/>
</head>
<body>
<h1>Search Result</h1>

<html:errors/>

sisetuId : ${f:h(sisetuId)}
riyomokutekiId : ${f:h(riyomokutekiId)}
startDate : ${f:h(startDate)}

<br/><br/>

<s:link href="/sisetuSearch/">search page</s:link>

<body>
</html>

ここまでで、まだ検索の機能はりませんが、JSPの検索画面から検索結果画面に遷移する機能が実装できたはずです。

http://localhost:8080/EasySearch/sisetuSearch/で動作確認してみて下さい。


STEP5 : 検索機能の実装

これまで作成したJSPとJavaを以下のように書き換えます。(詳細は研修中に説明します)

SisetuSearchAction.java

package easySearch.action;

import javax.annotation.Resource;

import org.apache.struts.action.ActionMessages;
import org.seasar.extension.jdbc.JdbcManager;
import org.seasar.extension.jdbc.where.SimpleWhere;
import org.seasar.framework.beans.util.Beans;
import org.seasar.struts.annotation.ActionForm;
import org.seasar.struts.annotation.Execute;
import java.util.List;

import easySearch.entity.Riyoumokuteki;
import easySearch.entity.Sisetu;
import easySearch.service.RiyoumokutekiService;
import easySearch.service.SisetuService;
import easySearch.form.SisetuSearchForm;

public class SisetuSearchAction {

    public JdbcManager jdbcManager;
    public List sisetuItems;
    public List riyoumokutekiItems;
    
    @ActionForm
    @Resource
    protected SisetuSearchForm sisetuSearchForm;
    
    @ActionForm
    @Resource
    protected SisetuService sisetuService;
    
    @ActionForm
    @Resource
    protected RiyoumokutekiService riyoumokutekiService;

    @Execute(validator = false)
    public String index() {
        return search();
    }

    @Execute(validator = false)
    public String search() {
        sisetuItems = sisetuService.findAll();
        riyoumokutekiItems = riyoumokutekiService.findAll();
        return "search.jsp";
    }

    @Execute(validator = false)
    public String doSearch() {
        if(sisetuSearchForm.sisetuId.equals("")){
            sisetuSearchForm.sisetuId = null;
        }
        if(sisetuSearchForm.riyomokutekiId.equals("")){
            sisetuSearchForm.riyomokutekiId = null;
        }
        sisetuItems = jdbcManager
            .from(Sisetu.class)
            .leftOuterJoin("riyoumokutekibetusisetuList")
            .leftOuterJoin("riyoumokutekibetusisetuList.riyoumokuteki")
            .leftOuterJoin("yoyakumeisaiList")
            .leftOuterJoin("yoyakumeisaiList.yoyaku","to_date(yoyakumeisaiList.yoyaku.riyouDate,'YYYYMMDD') between to_date(?,'YYYY-MM-DD') and to_date(?,'YYYY-MM-DD') + 7",sisetuSearchForm.startDate,sisetuSearchForm.startDate)
            .where(new SimpleWhere()
               .eq("sisetuid", sisetuSearchForm.sisetuId)  // if sisetuId is not null
               .eq("riyoumokutekibetusisetuList.riyomokutekiid", sisetuSearchForm.riyomokutekiId)
                )
            .getResultList();
        return "doSearch.jsp";
    }
        
    public ActionMessages validateInsert() {
        ActionMessages errors = new ActionMessages();
        return errors;
    }
    
    public ActionMessages validateUpdate() {
        ActionMessages errors = new ActionMessages();
        return errors;
    }
}

search.jsp

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="ja" lang="ja">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<link rel="stylesheet" type="text/css" href="${f:url('/css/global.css')}"/>

<!-- protocalendar -->
<link id="calendar_style" href="${f:url('/protocalendar-js/stylesheets/simple.css')}" media="screen" rel="Stylesheet" type="text/css" />
<script src="${f:url('/protocalendar-js/lib/prototype.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/lib/effects.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/javascripts/protocalendar.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/javascripts/lang_ja.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/javascripts/lang_zh-cn.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/javascripts/lang_zh-tw.js')}" type="text/javascript"></script>

</head>
<body>
<h1>Sisetu Search</h1>

<html:errors/>

<s:form>

<div>
sisetu : 
<html:select property="sisetuId">
<html:option value="">all</html:option>
<c:forEach var="r" varStatus="s" items="${sisetuItems}">
<html:option value="${f:h(r.sisetuId)}">${f:h(r.name)}</html:option>
</c:forEach>
</html:select>
</div>

<div>
mokuteki : 
<html:select property="riyomokutekiId">
<html:option value="">all</html:option>
<c:forEach var="r" varStatus="s" items="${riyoumokutekiItems}">
<html:option value="${f:h(r.riyomokutekiId)}">${f:h(r.name)}</html:option>
</c:forEach>
</html:select>
</div>

<div>
    start date : <input id="startDate" name="startDate" size="30" type="text" />
    <script type="text/javascript">
      InputCalendar.createOnLoaded('startDate', {lang:'ja', format: 'yyyy-mm-dd'});
    </script>
</div>

<input type="submit" name="doSearch" value="SEARCH" />

</s:form>
<br/><br/>

<s:link href="/menu/">menu page</s:link>

</body>
</html>

doSearch.jsp

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="ja" lang="ja">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<link rel="stylesheet" type="text/css" href="${f:url('/css/global.css')}"/>
</head>
<body>
<h1>Search Result</h1>

<html:errors/>

sisetuId : ${f:h(sisetuId)}
riyomokutekiId : ${f:h(riyomokutekiId)}
startDate : ${f:h(startDate)}

<table border="1">
<tr>
<th>sisetu</th><th>exists yoyaku</th><th>mokuteki</th>
</tr>
<c:forEach var="e" varStatus="s" items="${sisetuItems}">
    <tr style="background-color:${s.index %2 == 0 ? 'white' : 'lightgreen'}">
        <td>
            ${f:h(e.name)}
        </td>
        <td>
            <c:forEach var="yoyakumeisai" varStatus="s" items="${e.yoyakumeisaiList}">
                ${f:h(yoyakumeisai.yoyaku.riyouDate)}
                (${f:h(yoyakumeisai.yoyaku.starttime)} : ${f:h(yoyakumeisai.yoyaku.endtime)})
            </c:forEach>
        </td>
        <td>        
            <c:forEach var="riyoumokutekibetusisetu" varStatus="s" items="${e.riyoumokutekibetusisetuList}">
                ${f:h(riyoumokutekibetusisetu.riyoumokuteki.name)}
            </c:forEach>
        </td>
    </tr>
</c:forEach>
</table>

<br/><br/>

<s:link href="/sisetuSearch/">search page</s:link>
<s:link href="/menu/">menu page</s:link>

<body>
</html>

STEP6 : カレンダーを表示しましょう

protocalendar.jsを利用すると、簡単にカレンダーを使った日付選択機能が実現できます。

  1. protocalendar.jsを提供しているページから「protocalendar-js-1.1.0.zip」をダウンロードします。
  2. eclipseで「src/main/webapp」を右クリックし「Import」→「General」→「Archive File」を選択し、「Next」ボタンをクリックします。
  3. 「From archive file」にさきほどダウンロードした「protocalendar-js-1.1.0.zip」を指定し、「Finish」ボタンをクリックします。
  4. eclipse パッケージで「protocalendar-js-1.1.0」を右句リックし「Refactor」→「rename」で名前を「protocalendar-js」に変更して下さい。

以上でprotocalendar.jsの設定は完了です。

protocalendar.jsを利用したJSPで以下のように記述すると、カレンダーで日付を入力することができます。

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="ja" lang="ja">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<link rel="stylesheet" type="text/css" href="${f:url('/css/global.css')}"/>

<!-- protocalendar -->
<link id="calendar_style" href="${f:url('/protocalendar-js/stylesheets/simple.css')}" media="screen" rel="Stylesheet" type="text/css" />
<script src="${f:url('/protocalendar-js/lib/prototype.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/lib/effects.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/javascripts/protocalendar.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/javascripts/lang_ja.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/javascripts/lang_zh-cn.js')}" type="text/javascript"></script>
<script src="${f:url('/protocalendar-js/javascripts/lang_zh-tw.js')}" type="text/javascript"></script>

</head>

(略)

<div>
    start date : <input id="startDate" name="startDate" size="30" type="text" />
    <script type="text/javascript">
      InputCalendar.createOnLoaded('startDate', {lang:'ja', format: 'yyyy-mm-dd'});
    </script>
</div>

(略)

</body>
</html>

S2JDBCのテスト環境を作成しましょう

S2JDBCのテスト環境を作成しましょう。

テスト環境を用意しておくと、気軽にS2JDBCの機能を試すことができます。是非、活用して下さい。

  1. eclipseで「src/test/java/easySearch/action」を右クリックし「New」→「JUnit Test Case」を選択します。
  2. 「Name:」を例えば「SisetuSearchTest」等とします。
  3. 「Superclass:」に「org.seasar.extension.unit.S2TestCase」と入力します。
  4. 「SetUp()」チェックボックスにチェックを入れます。
  5. 「Finish」ボタンをクリックします。
  6. 出来上がった「SisetuSearchTest.java」を以下のように記述して下さい。
package easySearch.action;

import java.util.List;

import org.seasar.extension.jdbc.JdbcManager;
import org.seasar.extension.unit.S2TestCase;

import easySearch.entity.Sisetu;

public class SisetuSearchTest extends S2TestCase {
    private JdbcManager jdbcManager;
    protected void setUp() throws Exception {
        include("app.dicon");
    }
    
    public void testSisetuSearchAll() throws Exception {
        List results = jdbcManager.from(Sisetu.class).getResultList();
    }
}

テストを追加したい場合は「public void test」から始まるメソッドを定義すればOKです。
例えば「public void testSearchCondition throws Exception」。


content
  1. 参考
  2. 気づいた点
  3. STEP1 : S2JDBC-gen で Entity を自動生成しましょう
  4. STEP2 : 検索画面の準備
  5. STEP3 : 検索Actionの準備
  6. STEP4 : 検索結果を表示するViewの準備
  7. STEP5 : 検索機能の実装
  8. STEP6 : カレンダーを表示しましょう
  9. S2JDBCのテスト環境を作成しましょう