Java(Servlet)でファイルダウンロード
台北猫々
台北猫々
ATOMRSS
  • codeなにがしブックマークに追加する 0 users
  • このページを del.icio.us に追加
  • このページをはてなブックマークに追加
  • GoodJob
  • 38

GJGJGJ

GJGJGJGJGJGJGJGJ

説明

サーバにあるファイルをクライアント(ブラウザ)にダウンロードするメソッドです。"Content-Disposition: attachment"により、ブラウザ側ではダウンロードダイアログが表示され、「開く」か「保存」するかをユーザが選択することができます。 

※クライアントから、ダウンロード要求があった場合にサーバ側で行う処理です。


【変更履歴】
2008.03.19 例外処理追加等

ソースコード

コメント

  • ゲスト
  • 1:ゲスト (通りすがり)
  • 2008/03/18 13:00

Javaのダウンロード処理を書くのであれば、以下の説明も欲しいかな。。。

発生する例外種別として、
・IOException
・FileNotFoundException
・SocketException
などなど、、、色々ありますよね?
また、よく見るケースとしては、
----抜粋開始
while((len=in.read(buf))!=-1){
    out.write(buf,0,len);
}
----抜粋終了
の部分が
----NGCode
while((len=in.read(buf)) -1){
    out.write(buf,0,len);
}
----NGCode
となっていたりするケースも見られます。
とか、、、ノウハウならそこまで欲しいかも

  • GoodJob
  • 0

う~ん。例外処理はノウハウとして欲しいところですよね~(ちょっと、はしょっちゃいました(^^;)

ところで、アップしているソースで考慮すべき例外としては、
・IOException
・FileNotFoundException
の2つですよね?(異常系の組み方によっては、IllegalStateExceptionが発生するかなと思いますが)
・SocketException
は、IOExceptionにマッピングされてしまうのでは?

それと、
----NGCode
while((len=in.read(buf)) -1){
   out.write(buf,0,len);
}
----NGCode
という判定方法については問題無いような気がするのですが、具体的にどのようにNGなのかご教示いただけませんか?

  • GoodJob
  • 0

  • ゲスト
  • 3:ゲスト (1です。)
  • 2008/03/19 16:39

回答のみ
・SocketException
は、IOExceptionにマッピングされてしまうのでは?
拾い方によりけりです。
FileのIO例外とResponseのSocket例外は両方共にIOExceptionで拾えますが、ユーザがダウンロードの途中キャンセル等を拾うケースではSocket例外で拾うほうが正確になります。
ユーザキャンセル等は例外をキャッチはしてもプログラムとしての異常には落とすと変ですよね?

----NGCode
while((len=in.read(buf)) -1){
  out.write(buf,0,len);
}
----NGCode 
に関しては誤記です。
失礼いたしました。「動作」としては正常に動くけど「論理的」な意味合いでのNGでしかないですね^^;

----NGCode
while((len=in.read(buf)) 0){
  out.write(buf,0,len);
}
----NGCode 
としたつもりが[0]が[-1]のままになってしまいました。
while((len=in.read(buf)) 0){
の部分で、0の場合まだデータが残っていることを示すため、、、のつもりだったのですが、誤記してしまいました。

  • GoodJob
  • 0

>ユーザがダウンロードの途中キャンセル等を拾うケースではSocket
>例外で拾うほうが正確になります。
なるほどです。

##############################
#↓以下は、この記事の読み手に、ダウンロードのクライアントユ
#ーザのキャンセルをサーバ側で「常に」検知できるという誤解を
#与えないために書いています。
##############################
ただ、サーバ→ブラウザのダウンロード処理は、ダウンロードダイアログ表示のバックグラウンドで行われているため、ユーザキャンセルをいつもSocket例外で拾えるわけではないという、条件付きですね。
(例えば、サイズの小さいファイルでは、ダイアログが表示される時には、ダウンロード処理は完了し、サーブレットは終了してしまっており、SocketExceptionも発生しない)。
##############################

>失礼いたしました。「動作」としては正常に動くけど「論理的」
>な意味合いでのNGでしかないですね^^;
なんとなく、そんな気もしていたのですが、念のためお聞きしてしまいました(^^)


  • GoodJob
  • 0

  • ゲスト
  • 5:ゲスト (1です。)
  • 2008/03/23 04:17

蛇足なんだろうなというのはイヤというほど解かっていますし、しつこくて申し訳ないですが、乗りかかった船なのでついでです。
ノウハウに補足します。

byte buf[]=new byte[1024];
の[1024]はパフォーマンスを見たものです。
よく知られてるチューニングだと、サーバ上のファイルIOに時間がかかる場合(Webサーバとは別のハードのファイルにアクセスする等)これはwhileの周期よりバッファ読み込みが遅くなるケースです。このチューニングは主にバッファの読み込みサイズとwhile文を遅延させることで行います。

以下のメソッドを確認すると、
http://sdc.sun.co.jp/java/docs/j2se/1.4/ja/docs/ja/api/ja...(byte[],%20int,%20int)
----抜粋
できるだけ多くのバイト数を読み込もうとします。
----終了
とあるため、そのときの「できるだけ」が0byteである場合無駄にwhile文がCPU時間をとりCPUフル現象が発生します。
原因がIO時間によるのであれば、スリープをはさむことで解決します。
また、メモリ容量が少ない環境(昨今そんなことは少ないでしょうけど)では、例えば元のファイルのサイズを拾ってきてbyte配列のサイズにしてしまうと、そのファイルが大きい場合、かなり無駄なメモリ空間を取ってしまうというケースも過去に見たことがあります。(私が見たケースは極端で1.5Gのファイルでした。そんなファイルのダウンロードなんてWebでしないで欲しいものですが。。。)なので、固定サイズで発行してあることそのものにも意味があります。

GJGJ

  • ゲスト
  • 6:ゲスト (ヒロ)
  • 2008/10/22 19:50

attachment部分をinlineに変更して、ファイルをダウンロードし別ウィンドウで開くようにしましたが、ウィンドウが元ウィンドウの裏側に表示されてしまうことがあります。
ダウンロードして、開くウィンドウが常に最上位になるようにするには、どうすれば良いでしょうか?
ちなみに、ダウンロードするファイルはPDFで、AcrobatReaderにて開いています。

  • GoodJob
  • 0

JavaScriptでwindow.openして子ウインドウを開いて、その子ウインドウ内でPDFファイルを開くということですか?

親ウインドウから、(子ウインドウのハンドル).focus()して強制的に最前面にしても駄目ということでしょうか?

GJ

前へ 1 次へ

コメントする

[block]から[/block]までの範囲はブロック表示されます。
部分的に目立たせたい時や、引用などにお使いください。

[code]から[/code]までの範囲は等幅表示されます。
ソースコードや設定ファイルの記述などにお使いください。

ゲスト投稿者:ゲスト:

PDFLib | A library for processing PDF on the fly プレゼン公開・共有サイト handsOut.jp オープンタイプ株式会社 チーム・マイナス6% - みんなで止めよう温暖化

ソースコードのブログパーツ

デフォルトのフォントサイズ
修飾
表示サイズ
px px
プレビュー (表示する)
下のプレビュー領域をクリックすると、ポップアップで全体を見ることができます。
パラメータが不正です

    GoodJobしたユーザ

    ブックマークコメント

    関連するなにがし

    前へ 1 次へ

    タグ

    dyndnsbytearrayinputstreamobjectinputstreambytearrayoutputstreamobjectoutputstreamディープコピーdeepcopyarraylistiteratorチェックボックス複数multibytexencentos文字エンコーディングinit_connectcharacter-set-servercollation-serverdefault-character-setf:label動的メソッド呼び出しヘルパーメソッドwsse2重登録防止prototype.js位置positionpositionedoffsetscrolltoスクロールlink_tocyclecheck_box_tagチュートリアルactive_formerror_messages_forハイライトバリデーションvalidate便利リストデコレーションメールデコメ非対応機種tilestext_field_tag一括複数情報etherealrtphexテキストデータ抽出validwhenリセット一括更新plop置換replacepcoslogmixisregソケットnet::telnetfopenmutexサンプルcalendar[linux][bash][シェルスクリプト][大容量]mobilerorrails2.1clipboardクリップボード横向きピラミッドs2jdbc-genjsonicお絵かきフルパス名抽出サブドメインサブドメイン名s2jdbc自動生成エンティティドコモxhtmlrestdoltengspidering背景変更グラデーションiso一括登録xトークンチェックevalmonitorslavereplication画像処理

    前へ 1 2 3 ... 8 次へ