WebObjects/Web 應用程式/開發/示例/返回檔案
要從超連結返回檔案,最簡單的方法似乎是在 WOComponent 中覆蓋 appendToResponse,以返回該檔案作為響應,而不是讓 WOComponent 從 .html/.wod 檔案生成自己的響應
public void appendToResponse(WOResponse aResponse, WOContext aContext) {
//Use whatever mime-type you need for content-type:
//"text/csv" is just an example.
aResponse.setHeader("text/csv", "content-type");
//Assuming 'data' is a Java byte[] array. But
//You can do whatever you want to wind up with
//an NSData of content.
aResponse.setContent( new NSData( data ) );
aResponse.setHeader("filename=MyFilename.xls", "Content-Disposition");
//or, if you want the link to "force" a SaveAs dialog...
//aResponse.setHeader("attachment;filename=MyFilename.xls", "Content-Disposition");
其他人報告:我們有以下程式碼用於下載生成的 pdf...
public void appendToResponse(WOResponse aResponse, WOContext aContext) {
super.appendToResponse(aResponse, aContext);
//aResponse.setHTTPVersion("HTTP/1.1");
aResponse.disableClientCaching();
aResponse.removeHeadersForKey("Cache-Control");
aResponse.removeHeadersForKey("pragma");
aResponse.setHeader("application/pdf", "content-type");
aResponse.setHeader("inline; attachment; filename=\"" + fileName + ".pdf\"", "content-disposition");
aResponse.setHeader(Integer.toString(resultData.length()), "content-length");
aResponse.setContent(resultData);
}
用於修復 IE 問題(至少對我們來說)的關鍵行是...
aResponse.disableClientCaching();
aResponse.removeHeadersForKey("Cache-Control");
aResponse.removeHeadersForKey("pragma");
您可能想嘗試
public void appendToResponse( WOResponse r, WOContext c ) {
fileName = "test.txt";
r.setHeader( contentType + "; name=\"" + fileName + "\"", "Content-Type" );
r.setHeader( "inline; filename=\"" + fileName + "\"", "Content-Disposition");
r.setContent( data );
}
雖然根據 RFC2183,您的程式碼應該可以正常工作,但我發現來自一個無名壟斷的某些瀏覽器只會檢視 RFC1341 中的舊位置以獲取檔名,該位置位於 Content-Type 標頭中,而不是(或至少僅在)Content-Disposition 標頭中。
如果您主要希望他們下載檔案,您可能希望將其設為
public void appendToResponse( WOResponse r, WOContext c ) {
fileName = "test.txt";
r.setHeader( contentType + "; name=\"" + fileName + "\"", "Content-Type" );
r.setHeader( "attachment; filename=\"" + fileName + "\"", "Content-Disposition");
r.setContent( data );
}
以及來自郵件列表的另一個來回....
我在顯示 PDF 檔案時遇到問題 [....] 我可以透過點選“下載訊息提醒”上的[儲存]來成功儲存檔案,但當我點選[開啟]時,Acrobat 執行並顯示錯誤訊息“沒有這樣的檔案”,無法開啟 PDF 檔案。
發件人:"MacMullin, Jake (DCS)" <MacMullin.Jake@saugov.sa.gov.au>; 收件人:"Lu Yanmei" <lu.yanmei@meta.co.jp>, webobjects-dev@omnigroup.com 主題:RE: 無法開啟 PDF 檔案 日期:2003 年 5 月 30 日星期五 09:06:57 +0930
我遇到了完全相同的問題。結果發現這與您使用的標頭有關。我發現這種組合效果最好
// set the PDF content and header
response.setContent(outData);
response.appendHeader("application/pdf", "Content-Type");
response.appendHeader(outData.length()+"", "Content-Length");
response.appendHeader("inline;filename=\"file.pdf\"", "Content-Disposition");
以及來自郵件列表的另一個來回....
我在瀏覽器中顯示 PDF 檔案時遇到了問題 [....] 我可以傳送簡單的文字檔案以在瀏覽器中開啟,但 pdf 顯示為亂碼。我不能依賴使用者擁有外掛,有沒有辦法在瀏覽器中顯示它?否則是否有辦法將 pdf 轉換為 html 並將其顯示在瀏覽器中。
r.appendHeader("application/pdf", "Content-type");
r.setHeader(Integer.toString(myData.length()), "content-length");
r.appendHeader("application;filename=\"dockconcepts.pdf\"", "Content-Disposition");
r.appendContentCharacter('\n');
r.appendContentData(new NSData(myData));
如果要響應表單提交返回檔案(並在 Windows 上的 IE 中執行),您需要透過在 WOBuilder 中向表單新增“方法”繫結,將表單的“方法”從“POST”更改為“GET”。
我強烈建議使用 setHeader 方法而不是 appendHeader 方法,以確保現有的內容型別將被檔案返回元件覆蓋。如果已存在內容型別,appendHeader 不會更改內容型別值,這會導致不可預測的結果。--Hschottm 2007 年 1 月 16 日 14:24(UTC)
如果您試圖從子元件執行此操作,則需要使用 setContentInputStream 而不是 setContent。前者的文件說“只返回 InputStream 中的資料——任何已新增或設定的資料(作為字串或 NSData)都將被忽略”,而後者可以在頁面生命週期的後期被覆蓋或追加。例如,我有一個通用的元件,它執行一個報表並將該報表作為 PDF 提供給使用者。我想在我的 ListPeople 頁面中包含該元件,如下所示
PrintLink : ReportDownloader {
title = "Download these results";
fileName = "PersonList.pdf";
data = personList.displayedObjects;
definition = "personlist";
}
在 ReportDownloader.java 中,doReport() 處理對“下載這些結果”連結的點選並構建報表。
public void doReport() {
// ...snip...
// Run the report and put the resulting PDF into the byte array pendingResponse
// ...snip...
}
如上所述,覆蓋的 appendToResponse 方法負責將報表實際寫入響應中。
public void appendToResponse(WOResponse aResponse, WOContext aContext) {
super.appendToResponse(aResponse, aContext);
if (pendingResponse != null) {
//aResponse.setContent(pendingResponse);
ByteArrayInputStream in = new ByteArrayInputStream(pendingResponse);
aResponse.setHeader("application/pdf", "Content-type");
aResponse.setHeader("inline; filename=" + fileName, "Content-disposition");
aResponse.setContentStream(in, 512, (long)pendingResponse.length);
}
}
建立 ByteArrayInputStream 並設定響應以使用它可以確保 PDF 內容是響應中唯一返回的內容,無論父頁面(包含 ReportDownloader 的頁面)試圖渲染到響應中的內容是什麼。