- PR -

Struts Actionクラスでのダウンロード

投稿者投稿内容
せんせ
会議室デビュー日: 2005/09/08
投稿数: 12
投稿日時: 2005-09-09 11:10
はじめまして。
WEB開発の案件で、DBから取得したデータをCSV,XMLでのダウンロードを行う。というものがあるのですが、ちょっとわからない動作をするので何か情報をお持ちの方がいらっしゃいましたらご教授願いたいです。

動作として
・抽出したデータをStringに変換、それをresponseのバッファに格納する
・アクションクラスにてダウンロード用のメソッドを呼び出す。
・メソッドが呼ばれた後アクションクラスでフラッシュし、フォワードはnullを返す。

現象として
・2kぐらいのデータならCSV,XMLでダウンロードできる。(ダウンロードダイアログにてダウンロード可能)
・30kぐらいのデータの場合、ダウンロードできない。(ダウンロードダイアログは表示しますが、ダウンロードを行うときに「このインターネットのサイトを開くことが・・・」のメッセージが表示されます)

今まで行ったこと
・response.setBufferSize()でダウンロードファイル分のサイズを指定
・レスポンスヘッダにもダウンロードファイル分のバッファのサイズを指定
・ヘッダでキャッシュを使用するように変更
・ヘッダのコンテントタイプをそれぞれ指定(text/csv,text/xml)

なにをやっても結果は一緒でした。
何か見落としている部分でもあるのでしょうか?申し訳ありませんがよろしくお願いします。

環境は以下のとおりです
IE6.0 SP2
WindowsXP Professional SP2
J2SE 1.4.2_07
J2EE 1.3.1
Apach

以下にソースコードを抜粋しました。

//下記はアクションクラスでダウンロードを呼び出す部分です

writeToStream("CSV", output, "test", response);
response.getOutputStream().flush();
response.getOutputStream().close();
return null;

//ダウンロードメソッド
void writeToStream(String format, String output, String fileName, HttpServletResponse response)
{
try
{
String fileNameExt = "";

if("CSV".equals(format))
{
fileNameExt = ".csv";
} else
if("XML".equals(format))
{
fileNameExt = ".xml";
}

response.setContentType("application/octet-stream");
response.setHeader("Content-Disposition", "attachment; filename=\"" + fileName + fileNameExt + "\"");
response.setHeader("Cache-Control", "no-cache");

if(output != null)
{
OutputStream os = response.getOutputStream();
OutputStreamWriter w = new OutputStreamWriter(os);
BufferedWriter writer = new BufferedWriter(w);
writer.write(output);
writer.close();
w.close();
}
}
catch(Exception e){}
}
山本 裕介
ぬし
会議室デビュー日: 2003/05/22
投稿数: 2415
お住まい・勤務地: 恵比寿
投稿日時: 2005-09-09 11:22
>catch(Exception e){}
これで何か例外が握りつぶされているってことはないでしょうか?
例外をキャッチしたら常に適切なフォローをいれるか、最低限スタックトレースを出力するようにしましょう。
uk
ぬし
会議室デビュー日: 2003/05/20
投稿数: 1155
お住まい・勤務地: 東京都
投稿日時: 2005-09-09 11:35
さらにいうと、

引用:

OutputStream os = response.getOutputStream();
OutputStreamWriter w = new OutputStreamWriter(os);
BufferedWriter writer = new BufferedWriter(w);
writer.write(output);
writer.close();
w.close();


この部分は

コード:
      PrintWriter writer = response.getWriter();
      writer.write(output);


でいいのではないですか? それからレスポンスの出力ストリームに対するフラッシュや
クローズは、原則としてサーブレット内で行うものではないです。
せんせ
会議室デビュー日: 2005/09/08
投稿数: 12
投稿日時: 2005-09-09 11:36
引用:

インギさんの書き込み (2005-09-09 11:22) より:
>catch(Exception e){}
これで何か例外が握りつぶされているってことはないでしょうか?
例外をキャッチしたら常に適切なフォローをいれるか、最低限スタックトレースを出力するようにしましょう。


インギ様
返答ありがとうございます。説明不足で申し訳ないです^^;
例外に関してはログ出力専用のクラスで管理を行っています。
ここでは例外をスローしている様子が見られないため困ってます(ToT)

以下修正

catch(Exception e)
{
//ログ出力を行うクラスを使用し、例外を出力
log.debug("An exception occurred ProcessOrderDownload ", e);
}
せんせ
会議室デビュー日: 2005/09/08
投稿数: 12
投稿日時: 2005-09-09 11:43
引用:

ukさんの書き込み (2005-09-09 11:35) より:
さらにいうと、

引用:

OutputStream os = response.getOutputStream();
OutputStreamWriter w = new OutputStreamWriter(os);
BufferedWriter writer = new BufferedWriter(w);
writer.write(output);
writer.close();
w.close();


この部分は

コード:
      PrintWriter writer = response.getWriter();
      writer.write(output);


でいいのではないですか? それからレスポンスの出力ストリームに対するフラッシュや
クローズは、原則としてサーブレット内で行うものではないです。




uk様
返答ありがとうございます。
フォワードにnullを返しているのでフラッシュやクローズを行わないといけないのかな?と思い記述したものです^^;
早速上記のことを試してみたいと思います。
ありがとうございます
せんせ
会議室デビュー日: 2005/09/08
投稿数: 12
投稿日時: 2005-09-09 12:21
uk様から指摘を受けた部分を参考に修正を行い確認しましたが、現象は変わりませんでした。。。
uk様ありがとうございました。解決できなくて申し訳ないです(ToT)

こちらでももう少し調べてみますが、みなさんのご助力よろしくお願いします。
せんせ
会議室デビュー日: 2005/09/08
投稿数: 12
投稿日時: 2005-09-09 16:05
途中経過ですが、現状報告まで。

レスポンスヘッダのContent-Dispositionにinline;を指定して実行しました。

データ件数が少なければダイアログが表示される(ファイルの拡張子は.csv)のですが、データ件数が多いと画面にデータを表示してしまいます(ファイルの拡張子がない)。
データ件数の大小に関わらずダイアログを表示し、CSV(もしくはXML)としてダウンロードさせたいです。
よろしくお願いします
枠上コンドル
会議室デビュー日: 2005/09/09
投稿数: 1
投稿日時: 2005-09-09 22:42
私も似たような現象になったことがあります。

http://support.microsoft.com/default.aspx?scid=kb;ja;896219

web等で調査した結果、私の環境では以下のようにすることで
正常ダウンロードができるようになりました。

response.setContentType("application/octet-stream;charset=Windows-31J");
response.setHeader("Pragma", "");
response.setHeader("Cache-Control", "");
response.setHeader("Content-Disposition", "attachment; filename=xxx.csv");

参考になれば幸いです。

スキルアップ/キャリアアップ(JOB@IT)