SpringBootでWebアプリ開発チャレンジ(4~7日目)

色々詰まってしまい更新が滞ってしまった…
4~7日目にやったことをダイジェストでまとめてみる。

4日目:月別一覧を実装しようとして心折れかける

心が折れかけたのでterateilに質問を投げてみる…

SpringBootで特定の年月のデータを一覧表示したい

その結果、ご丁寧なご回答をいただけました…!
JPAでSQLにアクセスするには、JPQLという専門の用語を使うのですね…

5,6日目:編集と更新を実装しようとして詰まる

formタグでのaction属性の指定と、controller側のパスの設定が噛み合わずになかなか実装進まず…
そもそもhtmlでのPOST, PUT送信の実装の仕方に慣れていなかったと痛感…。

/income_outgo/{id}/editへ遷移
{id}/editのパスに対し編集画面に必要なデータを取得
/income_outgo/{id}/editのURLで編集画面(income_outgo/edit.html)表示
/income_outgo/{id}/のパスに対しputメソッドを実行
⑤ ④から送られてきた{id}に該当するデータの更新を実行
/income_outgo/monthのURLで月別一覧(month.html)表示(つまりリダイレクト)

income_outgo/month.html

 <td>
    <a class="btn btn-outline-secondary" th:href="@{/income_outgo/{id}/edit(id=*{id})}">編集</a> <!-- ① -->
</td>

income_outgo/edit.html

<h4>収支の編集</h4>
<form th:object="${incomeOutgo}" th:action="@{/income_outgo/{id}(id=*{id})}" th:method="put"> <!-- ④ -->

IncomeOutgoController.java

@GetMapping("{id}/edit") // ②
 public String edit(@PathVariable Long id, Model model){
    IncomeOutgo incomeOutgo = incomeOutgoService.findById(id);
    model.addAttribute("incomeOutgo", incomeOutgo);
    // 今月(yyyy-MM)の文字列
    Date today = new Date();
    SimpleDateFormat thisMonthPathFormat = new SimpleDateFormat("yyyy-MM");
    String thisMonthPath = thisMonthPathFormat.format(today);
    //今月をリンクに入れる
    model.addAttribute("thisMonthPath", thisMonthPath);
    return "income_outgo/edit"; // ③
   }

@PutMapping("{id}") //⑤
 public String update(@PathVariable Long id, @ModelAttribute IncomeOutgo incomeOutgo){
     incomeOutgo.setId(id);
     incomeOutgoService.save(incomeOutgo);
     return "redirect:/income_outgo/month"; //⑥
}

はじめのうちは、どこがどのように関連しているか分かっておらず、
th:actionのところ、@GetMapping("{id}/edit")のところ、return "income_outgo/edit"のところをあれこれ書き換えていました…


ちなみに削除はすんなり実装できました。。。
/income_outgo/{id}/のパスに対しdeleteメソッドを実行
② ①から送られてきた{id}に該当するデータを削除
/income_outgo/monthにリダイレクト

month.html

<td>
    <form th:action="@{/income_outgo/{id}/(id=*{id})}" th:method="delete"> <!-- ① -->
        <input class="btn btn-outline-secondary" type="submit" value="削除" />
    </form>
</td>

IncomeOutgoController.java

@DeleteMapping("{id}")
public String destroy(@PathVariable  Long id){
    incomeOutgoService.deleteById(id); //②
    return "redirect:/income_outgo/month"; //③
}

7日目(今日):月別一覧と年間一覧の実装

terateilで回答いただいた内容をもとに、今月の一覧を取得することに成功。

今度は「前の月」と「次の月」を表示するようにしたい。

IncomeOutgoControllerで前の月と次の月リンク用の文字列を生成して

// 今月(yyyy-MM)の文字列
Date today = new Date();
SimpleDateFormat thisMonthPathFormat = new SimpleDateFormat("yyyy-MM");
String thisMonthPath = thisMonthPathFormat.format(today);

@GetMapping("month/{thisMonthPath}")
    public String month(Model model) {

    // 前月の一覧のパス取得
    Date prevMonth = incomeOutgoService.prevMonth(today);
    String prevMonthPath = thisMonthPathFormat.format(prevMonth);
    model.addAttribute("prevMonthPath", prevMonthPath);

    // 次月の一覧のパス取得
    Date nextMonth = incomeOutgoService.nextMonth(today);
    String nextMonthPath = thisMonthPathFormat.format(nextMonth);
    model.addAttribute("nextMonthPath", nextMonthPath);

    //今月をリンクに入れる
    model.addAttribute("thisMonthPath", thisMonthPath);
    return "income_outgo/month";
}

htmlのリンクにパスを指定

<div class="month-header">
<ul>
    <li><a class="btn btn-outline-secondary" href="/income_outgo/month" th:href="@{/income_outgo/month/{thisMonthPath}(thisMonthPath=${prevMonthPath})}">前の月</a></li>
    <li><h2 th:text="${thisMonth}"></h2></li>
    <li><a class="btn btn-outline-secondary" href="/income_outgo/month" th:href="@{/income_outgo/month/{thisMonthPath}(thisMonthPath=${nextMonthPath})}">次の月</a></li>
</ul>
</div>

URLは変わるけど画面自体が変わらない…
→マッピングするたびDate today = new Date()が走るから、結局thisMonthParhが今月のまま更新されないのですよ…
Date today = new Date()ではなく、 GETで送られてくるthisMonthPathからいわゆるtodayを作るようにしたい

Date today = thisMonthPathFormat.parse(thisMonthPath);

こう書くとparse部分に赤い波線がでる(すなわちエラー)
どうやら
解釈できない文字列や不正な日付 (例えば 2015-02-31) が指定された場合 NaNを返すらしいので、parseメソッドは不適切(thisMonthPath = “yyyy-MM”だから)

thisMonth の文字列をうまいことDate型にできないものか…
それか、Repositoryクラスから引数をString型に変えるしかないのか…
日付扱うの難しい!!!


とりあえず、最低限のCRUDは実装できたけど、まだまだ道のりが遠い…
しかも本格的に使うにはまだまだ機能が足りない!

  • 登録・更新時のバリデーション
  • 登録・更新・削除後のメッセージ表示
  • 削除時に確認ポップアップ表示
  • 現状ただあるだけのベージングを機能させる

etc…

次回に続く…

SNSでもご購読できます。

コメントを残す

*