2011-10-04 23 views
18

DownloadLink, अच्छा और एक फाइल डाउनलोड करने के लिए एक बटन/लिंक बनाने के लिए उपयोगी है इन पंक्तियों के साथ:फ्लाई पर जेनरेट की गई फ़ाइल के साथ विकेट के डाउनलोड लिंक का उपयोग कैसे करें?

add(new DownloadLink("downloadButton", getReportFile(), "report.pdf")); 

और

<input type="button" wicket:id="downloadButton" value="Download" /> 
हालांकि

, मैं करने के लिए ट्रिगर फ़ाइल की पीढ़ी चाहते हैं केवल तभी डाउनलोड करें जब बटन/लिंक पर क्लिक किया जाता है। दूसरे शब्दों में, क्लिक करने पर, मैं एक विधि को कॉल करता हूं जो फ़ाइल (हमारे मामले में एक पेंटाहो रिपोर्ट) उत्पन्न करता है, इसे एक अस्थायी जगह में रखता है और File को इंगित करता है। तो मैं उस File का उपयोग करने के लिए DownloadLink बता दूंगा। प्रश्न है, क्या यह संभव है?

वर्तमान में हमारे पास नीचे दिए गए कोड की तरह कुछ है, जो काम करता है, लेकिन मुझे इसमें दिलचस्पी है कि DownloadLink इसके बजाय उपयोग किया जा सकता है या नहीं।

add(new Link<Void>("downloadButton") { 
    @Override 
    public void onClick() { 
    IResourceStream resourceStream = new AbstractResourceStreamWriter() { 
     @Override 
     public void write(OutputStream output) { 
     try { 
      reportService.generateReport(output, report); 
     } catch (IOException e) { 
      // ... 
     } 
     } 

     @Override 
     public String getContentType() {       
     return CONTENT_TYPE_PDF; 
     } 
    }; 

    getRequestCycle() 
     .setRequestTarget(new ResourceStreamRequestTarget(resourceStream) 
     .setFileName("report.pdf")); 
    } 
}); 

(विकेट 1.4.18, अगर यह एक फर्क नहीं पड़ता।)

उत्तर

15

आप निर्माता है कि एक Model तर्क के रूप में लेता है का उपयोग नहीं कर सकते हैं? और ModelFile को getObject() में बनाएं। LoadableDetachableModel एक अच्छा विकल्प है, load(), और इसलिए फाइल जनरेशन, केवल एक बार लागू किया जाएगा।

यदि लिंक क्लिक होने पर हर बार फ़ाइल को ताज़ा रूप से जेनरेट किया जाता है, तो यह सुनिश्चित करने के लिए फ़ाइल को स्वचालित रूप से हटा दिए जाने के बाद DownloadLink.setDeleteAfterDownload(true) का उपयोग करें।

मैं 1.4 का उपयोग नहीं करते हैं, लेकिन 1.3 में स्रोत कोड से पता चलता है कि FileLink की onClick() विधि में getModelObject() के माध्यम से लिया गया है। बजाय DownloadLink.onClick()

public void onClick() 
{ 
    final File file = (File)getModelObject(); 
      ... 
    IResourceStream resourceStream = new FileResourceStream(
      new org.apache.wicket.util.file.File(file)); 
    getRequestCycle().setRequestTarget(.../* uses resourceStream */...); 
} 
+2

आप डाउनलोड लिंक पर क्लिक ओवरराइड भी कर सकते हैं और सुपर विधि को कॉल करने से पहले 'setModelObject()' कर सकते हैं। हालांकि, ज़वी का सुझाव बहुत साफ है। – jbrookover

+4

1. इसके बजाय 'लोड करने योग्यडेटाबल मॉडल' का उपयोग करें। अनुरोध के दौरान getObject() 'को कई बार बुलाया जा सकता है, लेकिन 'लोड()' नहीं होगा; 2. अगर फ़ाइल हमेशा जेनरेट की जाती है, तो आप 'downloadLink.setDeleteAfterDownload (true)' कॉल कर सकते हैं, इसलिए आपको बाद में temp फ़ाइल को हटाने के बारे में चिंता करने की आवश्यकता नहीं है। – tetsuo

+0

@tetsuo आपकी बहुमूल्य टिप्पणियों के लिए धन्यवाद। मैंने आपकी सिफारिशों के साथ उत्तर अपडेट किया है। –

10

उपयोग org.apache.wicket.markup.html.link.ResourceLink

IModel fileModel = new AbstractReadOnlyModel(){ 
    public Object getObject() { 
     return generateFile(); 
    } 
}; 

DownloadLink link = new DownloadLink(linkId, fileModel, "report.pdf"); 

स्रोत कोड।

+0

डाउनलोडलिंक के बजाय संसाधन लिंक का उपयोग करने का क्या फायदा है (जैसा कि [ज़वी लोपेज़ द्वारा दिखाया गया है] (http://stackoverflow.com/questions/7646270/using-wickets-downloadlink-so-that-the-file-is- जनरेटेड- जब-लिंक-है-clicke/7646332 # 7646332))?(यह सुनिश्चित नहीं है कि यह प्रासंगिक है, लेकिन ध्यान दें कि यहां डाउनलोड करने के लिए फ़ाइल एक स्थिर संसाधन नहीं है, लेकिन एक गतिशील रिपोर्ट जो हमेशा उत्पन्न होती है।) – Jonik

+0

डाउनलोड लिंक java.io.File के साथ काम करता है, जबकि संसाधन लिंक आईरसोर्स के साथ काम करता है। विकेट डिस्ट्रो के साथ आने वाले आईरसोर्स के कई कार्यान्वयन हैं जिनमें से अधिकांश गतिशील डेटा उत्पन्न करते हैं। –

संबंधित मुद्दे