2010-02-02 9 views
46

पर पहुंचें मेरे पास एक लिंक है जिसे उपयोगकर्ता पीडीएफ प्राप्त करने के लिए क्लिक करता है। JQuery में, मैं पीडीएफ प्राप्त करने के लिए सर्वर पर एक पोस्ट AJAX कॉल बनाते हैं। पीडीएफ सही सामग्री शीर्षलेख आदि के साथ मेरे पास आता है जो आम तौर पर ब्राउज़र को रीडर प्लगइन खोलने का कारण बनता है, या उपयोगकर्ता को पीडीएफ को सहेजने की अनुमति देता है।सर्वर पर पोस्ट करें, पीडीएफ प्राप्त करें, उपयोगकर्ता w/jQuery

चूंकि मुझे पीडीएफ डब्ल्यू/एजेक्स कॉल मिल रहा है, मुझे यकीन नहीं है कि मुझे ऑनस्यूप कॉलबैक में प्राप्त डेटा के साथ क्या करना है। मैं ब्राउज़र में प्राप्त डेटा कैसे दे सकता हूं और इसे पीडीएफ प्रतिक्रिया के साथ अपनी डिफ़ॉल्ट चीज़ करने की अनुमति देता हूं?

+0

'इसकी डिफ़ॉल्ट चीज़' को परिभाषित करें। –

+0

जो ब्राउज़र आमतौर पर पीडीएफ पर सेट सामग्री प्रकार के साथ प्रतिक्रिया के साथ करता है। एक पाठक खोलें, डाउनलोड स्थान आदि – bryanvick

उत्तर

31

आप सब पर jQuery की जरूरत नहीं है की तरह कुछ करना होगा। बस सामान्य रूप से एक फार्म के माध्यम से अपने पोस्ट सबमिट करें, और सर्वर साइड पर, HTTP हेडर

Content-Disposition: attachment; filename="whatever.pdf" 

ब्राउज़र को उसके डिफ़ॉल्ट काम करेंगे जोड़ें।

वैकल्पिक रूप से, यदि आप पीडीएफ पीढ़ी के दौरान होने वाली किसी भी त्रुटि की रिपोर्ट करने के बारे में अधिक सावधान रहना चाहते हैं, तो आप यह कर सकते हैं। JQuery के साथ अपने सर्वर पर अपने पैरामीटर पोस्ट करें। सर्वर पर, द्विआधारी सामग्री उत्पन्न करें और इसे कुछ मिनटों तक कैश करें, जो उपयोगकर्ता के सत्र में रखी गई कुंजी के माध्यम से सुलभ हो, और अपने पृष्ठ पर "सफलता" अजाक्स प्रतिक्रिया लौटाएं (या यदि कोई त्रुटि हुई, तो वापस लौटें "त्रुटि" प्रतिक्रिया)।

window.location = "/get/my/pdf"; 

सर्वर तो कैश्ड पीडीएफ सामग्री प्रस्तुत करती है: पेज को सफल प्रतिक्रिया वापस हो जाता है, इसे तुरंत की तरह कुछ कर सकते हैं। ऊपर के रूप में सामग्री-विस्थापन शीर्षलेख शामिल करना सुनिश्चित करें।

+5

आपको आवश्यकता नहीं हो सकती है लेकिन कभी-कभी आप करते हैं;) –

50

पर एक नजर डालें - jQuery Plugin for Requesting Ajax-like File Downloads

पूरे plugin (टिप्पणियां सहित) कोड का सिर्फ बारे में 30 लाइनों है।

कॉल jquery AJAX कॉल के समान ही है।

$.download('/export.php','filename=myPDF&format=pdf&content=' + pdfData); 

बेशक, आप के रूप में आप किसी भी तरह के डाउनलोड के लिए होगा सर्वर साइड पर सामग्री प्रकार और सामग्री-विन्यास शीर्षलेख सेट करना होगा।

जावा में मैं इस

response.setContentType("application/pdf"); 
response.setHeader("Content-Disposition", "attachment; filename="exported.pdf"); 
+0

के लिए संकेत यह जवाब था, लेकिन मैं इसे वोट अप करने के लिए पर्याप्त प्रतिष्ठा नहीं है। मुझे पता था कि मैं गलत तरीके से समस्या के बारे में सोच रहा था। – bryanvick

+0

धन्यवाद, नया यहाँ। – bryanvick

-1

मुझे लगता है कि सबसे अच्छा डाउनलोड फ़ोल्डर में एक अस्थायी पीडीएफ फाइल बनाने और उसके बाद पॉप अप एक iframe होने .. क्रोम का उपयोग कर इसे तुरंत लोड होगा फ़ाइल लोड करने के लिए किया जाएगा, लेकिन मैं दूसरे के लिए लगता वेरिएंट एक्रोबेट रीडर स्थापित किया जाना चाहिए पीडीएफ देखने के लिए लेकिन फिर भी आप FlashPaper का उपयोग कर सकते हैं :)

+0

उत्तर प्रश्न के संदर्भ से बहुत दूर है, और आपके कोड पढ़ने के बाद सभी –

3

"अजाक्स जैसी फ़ाइल डाउनलोड के अनुरोध के लिए jQuery प्लगइन" का जवाब देने का जवाब मुझे सही दिशा में ले गया, लेकिन यह पूरी तरह से मेरी स्थिति के लिए काम नहीं करता है मेरे पास मेरे खोज मानदंड/फ़िल्टर डेटा के रूप में पास करने के लिए ऑब्जेक्ट्स की जटिल वस्तु और सरणी है। मैंने सोचा कि अगर कोई और इस स्थिति में भी चलता है तो मैं अपना कोड साझा करूंगा।

$.download = function (url, data, method) { 
    if (url && data) { 
     //convert the data object into input HTML fields 
     var inputs = ''; 
     var convertToInput = function (key, keyStr, obj) { 
      if (typeof obj === 'undefined') { 
       return; 
      } else if (typeof obj === "object") { 
       for (var innerKey in obj) { 
        if (obj.hasOwnProperty(innerKey)) { 
         var innerKeyStr = ''; 
         if (keyStr === '') { 
          innerKeyStr = innerKey.toString(); 
         } else { 
          innerKeyStr = keyStr + "[" + innerKey.toString() + "]"; 
         } 
         convertToInput(innerKey, innerKeyStr, obj[innerKey]); 
        } 
       } 
       return; 
      } else if ($.isArray(obj)) { 
       obj.forEach(function (item) { 
        convertToInput(key, keyStr + "[]", item); 
       }); 
       return; 
      } 

      inputs += "<input type='hidden' name='" + keyStr + "' value='" + obj + "' />"; 
     }; 
     convertToInput(null, '', data); 

     //send request 
     jQuery('<form action="' + url + '" method="' + (method || 'post') + '">' + inputs + '</form>').appendTo('body').submit().remove(); 
    }; 
}; 
$.download('/api/search?format=csv', searchData, 'POST'); 

यह शायद बहुत अधिक अंतर नहीं पड़ता है, लेकिन कुछ संदर्भ प्रदान करने, मैं एक जावास्क्रिप्ट और नॉकआउट यूआई वेबएपीआई, MVC4, और nHibernate में बुला मिल गया है। क्वेरी स्ट्रिंग का 'format = csv' भाग लौटाए गए मॉडल को CSV फ़ाइल प्रकार में परिवर्तित करने के लिए MediaTypeFormatter को ट्रिगर करता है। अगर मैं इसे छोड़ देता हूं, तो मैं मॉडल को एपीआई से वापस प्राप्त करता हूं और प्रदर्शन के लिए स्लिम ग्रिड को पॉप्युलेट कर सकता हूं।

0

मुझे यह समझने में असफल रहा कि आप फ़ाइल डाउनलोड यूआरएल के लिए AJAX अनुरोध क्यों चाहते हैं!लेकिन अगर यह क्लाइंट की तरह अधिक है तो डाउनलोड करने के लिए कुछ सामग्री उत्पन्न करता है - एक डेटा यूरी का उपयोग करें। क्रोम और फ़ायरफ़ॉक्स 20+ के लिए पूरी तरह से काम करता है। सफारी और आईई नहीं! यदि फ्लैश की अनुमति है, तो आप डाउनलोडकर्ता का उपयोग कर सकते हैं।

आह अपने कोड को पढ़ने के बाद, मैं तुम्हें मानकों का एक गुच्छा भेजना चाहते हैं देखते हैं। ठीक है जब तक कि क्वेरी स्ट्रिंग बहुत लंबा न हो (IE8- 2083 की सीमा है) क्यों उचित यूआरएल के साथ एंकर का उपयोग नहीं करते?

$('a.export-csv').click(function (evt){ 
     linkEl.attr('href','/export?' + encodeURIComponent(formQueryString())); 
     return true; 
    }); 

उपर्युक्त डिफ़ॉल्ट घटना (क्लिक) होने से पहले यूआरएल को बदलने की अनुमति देता है।

+0

आह पर कोई विवरण प्रदान नहीं किया गया है, मुझे लगता है कि आप पैरामीटर का एक गुच्छा भेजना चाहते हैं। ठीक है जब तक कि क्वेरी स्ट्रिंग बहुत लंबा न हो (IE8- 2083 की सीमा है) क्यों उचित यूआरएल के साथ एंकर का उपयोग नहीं करते? –

+0

आपका कोड ठीक दिखता है और मैंने कुछ ऐसा करने की कोशिश की और ऐसा लगता है कि यह काम करता है। क्या आप रेखांकित कर सकते हैं कि आपके लिए कौन सा हिस्सा काम नहीं करता है? –

2

मैं एक ही समस्या थी लेकिन शीर्ष उपयोग पर इस के लिए एक RESTFUL webservice और एक जटिल डेटा वस्तु जो मैं पोस्ट करना चाहिए है।

मेरे समाधान: jQuery प्लगइन की तरह मैं एक अस्थायी फ़ॉर्म्यूलर का निर्माण और सबमिट करें। सर्वर साइड पर

$('<form target="_blank" action="' + appConstants.restbaseurl + '/print/pdf" method="POST">' + 
    "<input name='data' value='" + angular.toJson($scope.versicherung) + "' />" + 
    '</form>').appendTo('body').submit().remove(); 

हम एक JACKSON के साथ एक CXF REST Service का उपयोग करें: लेकिन मैं json सामग्री के साथ एक पैरामीटर के रूप में डेटा ऑब्जेक्ट (। मैं यहाँ का उपयोग AngularJS लेकिन यह jQuery.param() साथ भी काम करना चाहिए)

जावास्क्रिप्ट भेज प्रदाता:

स्प्रिंग कॉन्फ़िग:

<jaxrs:server id="masterdataService" address="/"> 
    <jaxrs:serviceBeans> 
     <ref bean="printRestServiceBean" /> 
    </jaxrs:serviceBeans> 
    <jaxrs:providers> 
     <bean class="org.codehaus.jackson.jaxrs.JacksonJsonProvider" /> 
     <bean class="de.controller.ExceptionHandler" /> 
    </jaxrs:providers> 
</jaxrs:server> 

नियंत्रक मैं निकालने में PrintService में

package de.controller; 

import javax.ws.rs.Consumes; 
import javax.ws.rs.FormParam; 
import javax.ws.rs.POST; 
import javax.ws.rs.Path; 
import javax.ws.rs.Produces; 
import javax.ws.rs.core.MediaType; 
import javax.ws.rs.core.Response; 

import org.codehaus.jackson.map.ObjectMapper; 
import org.springframework.beans.factory.annotation.Autowired; 


@Path(Constants.PRINT_PATH) 
@Consumes({ MediaType.APPLICATION_JSON, "application/x-www-form-urlencoded"}) 
@Produces("application/pdf; charset=UTF-8") 
public class PrintRestController { 

    @Autowired 
    private PrintService printService; 

    @POST 
    @Produces("application/pdf") 
    @Path("/pdf") 
    public Response getPDF(@FormParam("data") String data) { 
     return printService.getPDF(json2Versicherung(data)); 
    } 

    private Versicherung json2Versicherung(String data) { 
     Versicherung lVersicherung = null; 
     try { 
      ObjectMapper mapper = new ObjectMapper(); 
      lVersicherung = mapper.readValue(data, Versicherung.class); 
     } catch(Exception e) { 
      LOGGER.error("PrintRestController.json2Versicherung() error", e); 
     } 
     return lVersicherung; 
    } 
} 

मैं पीडीएफ द्विआधारी और प्रतिक्रिया का निर्माण: एड परम और इसे वापस परिवर्तित एक जावा POJO को

@Override 
public Response getPDF(Versicherung pVersicherung) { 
    byte[] result = ... //build the pdf from what ever 


    ResponseBuilder response = Response.ok((Object) result); 
    response.header("Content-Disposition", "inline; filename=mypdf.pdf"); 
    return response.build(); 
} 

यह समाधान सभी ब्राउज़रों के लिए काम करता है (IE9 के लिए भी कर सकते हैं जो डेटा यूआरएल को संभाल नहीं लेते हैं) और टैबलेट और स्मार्टफोन पर और इसमें पॉपअपब्लॉकर्स

+0

आपके पास उपयोगकर्ता को यह बताने का कोई तरीका नहीं है कि डाउनलोड पूरा हो गया है, यद्यपि, क्या आप? – crush

+0

नहीं, जब तक आप कुछ अतिरिक्त चाल का उपयोग नहीं करते हैंकुकीज़ सेट करना –

1

अजाक्स जैसी फ़ाइल डाउनलोड का अनुरोध करने के लिए jQuery प्लगइन है - अनिवार्य रूप से - एक फॉर्म बनाना, पोस्ट डेटा को छिपे हुए फ़ील्ड के रूप में जोड़ना , इसे पृष्ठ के शरीर में जोड़कर, इसे सबमिट करना और इसे हटा रहा है।

मेरे मामले में मैं एक रूप है, केवल डेटा का एक हिस्सा नहीं था के रूप में यह था तैनात किया जाना है। यह निम्नलिखित समाधान के लिए बनाया गया है। सर्वर की ओर से मैं अनुरोध से "डेटा" पैरामीटर और यूआरआई-डीकोडिंग को बस पढ़कर डेटा प्राप्त कर सकता हूं।

function postAndDownload(url, data) { 

    encodedData = encodeURIComponent(data); 

    $("<form>") 
     .attr("action", url) 
     .attr("method", "post") 
     .append(
      $("input") 
       .attr("type", "hidden") 
       .attr("name", "data") 
       .attr("value", encodedData) 
     ) 
     .appendTo("body") 
     .submit() 
     .remove(); 
}; 
संबंधित मुद्दे