2018年4月21日土曜日

Java EEで帳票を出すのに色々悩んだ話(2)

今回は、「Java EEで帳票をPDFで発行するのに色々悩んだ話」の二回目です。

Java EE + JSFで画面を作れるようになり、さらにJaspersoft Studioで帳票を開発し、Jasper Report Libraryを自分のプログラム(Mavenプロジェクト)に組み込み、開発した帳票をPDFで出力!!

やったぜ、出来たぜ!!と思ったら、そうは世の中甘くなかった。


PDFをブラウザにレスポンスとして返すと、確かに、PDFの出力は出来るわけです。

ブラウザが、「保存するのか、開くのか?」とか聞いてくれるわけです。

しかし、言ったら当然ですが、HTTPプロトコルの仕様ではレスポンスは1つしか返せない。

つまり、ブラウザにPDFのレスポンスを返してしまったら、その1つを使い切るわけで、画面のレスポンスは破棄されてしまう・・・つまり、画面は更新されない。

たとえば、PDFを発行したら、画面を「発行したよ!!」という状態に書き換える、という事が出来ない。

サーバー上にファイルとして出力して格納し、ダウンロード画面を出してあげて格納ファイルをダウンロード・・・というアイディアもあるけど、サーバー側にファイル書くのはちょっと最終手段としてとっておきたい。

というわけで、また悩んだあげく、処理を二回に分けてしまうのが一番簡単じゃないかな??と思い実行しました。

これでいいのか!?という問題はあるのですが、まぁ行けてる感じ。

二回に分けるとは、こういうことです。

■1回目の処理

(1-1)サーバー側でデータの更新を終わらせる。

(1-2)サーバー側で帳票のデータ作成を終わらせバイナリデータとして出力しておく。

(1-3)(2)のデータをセッションBeanに格納しておく。

(1-4)帳票が出来たよというフラグを立てておく。

(1-5)ブラウザにレスポンスを返し、画面を最新の状態に書き換える。

■2回目の処理

(2-1)ブラウザがロードされたら、JavaScriptで(1-4)のフラグを確認。立っていたら2回目の処理を自動実行。
※JSFの場合は、2回目の処理を実行する隠しボタンを作り、$('.隠しボタンクラス').click();とかするだけ。

(2-2)サーバー側で(1-3)のセッションBeanから作ってた帳票のバイナリを取り出す。

(2-3)取り出したPDFのバイナリを、ブラウザにレスポンスする。

(2-4)画面は書き変わらないが、1回目の処理で画面は書き換えているので問題なし。



という感じですね。

Primefases Extensionとか使えばもっと楽に出来るんでしょうけど、便利ライブラリ系の処理は、何かあると「こんな挙動だとやばい、知らなかった!!」的な事件に遭遇しやすいので、そんな難しい事じゃなければ、素直に自分で作り込みたい。

という感じでちょこちょこやっております。