11

ファイルをダウンロードしようとしています。アクションはajax()POST リクエストによってトリガーされます。要求は、データを JSON 形式でコントローラーに送信します。コントローラーはファイル (バイト) を生成し、それを送り返します。

JavaScript:

function getLicenseFile() {
    $.ajax({
        type: 'POST',
        url: '<%=request.getContextPath()%>/licenses/rest/downloadLicenseFile',
        dataType: 'json',
        contentType: 'application/json;charset=UTF-8',
        data: ko.mapping.toJSON(licenseModel),
        success: function (data) {
            console.log("in sucess")
        },
        error:function (xhr, ajaxOptions, thrownError){
            console.log("in error")
        } 
    });
}  

コントローラ:

@RequestMapping(value = "/licenses/rest/downloadLicenseFile", method = RequestMethod.POST)
@ResponseStatus(value=HttpStatus.OK)
@ResponseBody
public void createLicenseFile(@Valid @RequestBody License license, HttpServletResponse response) throws Exception {

    logger.debug("Contoller License in: "+ license);

    byte[] licensedata = licenseEncodeDefaultService.createLicenseFile(license);
    logger.debug("licenseData: " + new String(licensedata));

    response.setHeader("Content-Disposition", "attachment; filename=\"" + license.getCustomer() + ".license\"");
    response.getOutputStream().write(licensedata);
    response.flushBuffer();
}


問題

  • ブラウザはダウンロードボックスを開くはずですが、それは起こりません
  • 応答は、ajax 関数の error: セクションで処理されます (ただし、HTTP ステータスは ですOK) 。

それで、私は何を間違っていますか、またはこれを行う適切な方法は何ですか?

4

5 に答える 5

17

success応答としてファイルのURLを送信し、コールバックでそれを「訪問」するだけです。

function getLicenseFile() {
    $.ajax({
        type: 'POST',
        url: '<%=request.getContextPath()%>/licenses/rest/downloadLicenseFile',
        dataType: 'json',
        contentType: 'application/json;charset=UTF-8',
        data: ko.mapping.toJSON(licenseModel),
        success: function (data) {
            window.open(data.fileUrl);
            // or window.location.href = data.fileUrl;
        },
        error:function (xhr, ajaxOptions, thrownError) {
            console.log("in error");
        } 
    });
}

data.fileUrlサーバーが応答して、ファイルの取得先をクライアントに通知するように設定する必要があります。

したがって、サーバーは次のようなJSONで応答を送信します

{
    "fileUrl": "http://mysite.com/files/0123456789"
}
于 2012-11-22T23:02:47.203 に答える
8

@ will824あなたが尋ねるように、私は自分の解決策を投稿します。

コントローラーで回避策を使用し、ファイルをファイル システム ( /tmp) に一時的に保存しました。機能を2段階に分けました。作成とダウンロード。これはあまり良くありませんが、私には十分です。

コントローラ(ファイルを作成し、サーバー ファイル システムに保存されます):

@RequestMapping(value = "/licenses/rest", method = RequestMethod.PUT)
@ResponseStatus(value=HttpStatus.OK)
@ResponseBody
public String createLicenseFile(@Valid @RequestBody License license) throws Exception {

    // create encrypted license file and send the name back to view
    String fileName =  licenseEncodeDefaultService.createLicenseFile(license);
    return fileName;

}

コントローラー(ファイルをダウンロード):

@RequestMapping(value = "/licenses/downloadFile/{file}", method = RequestMethod.GET)
public void downloadLicenseFile(@PathVariable("file") String file, HttpServletResponse response) throws Exception {

    // create full filename and get input stream
    File licenseFile = new File ("/tmp/" + file);
    InputStream is = new FileInputStream(licenseFile);

    // set file as attached data and copy file data to response output stream
    response.setHeader("Content-Disposition", "attachment; filename=\"" + file + ".license\"");
    FileCopyUtils.copy(is, response.getOutputStream());

    // delete file on server file system
    licenseFile.delete();

    // close stream and return to view
    response.flushBuffer();
}

JavaScript:

function getLicenseFile() {
    //console.log(ko.mapping.toJSON(licenseModel));
    $.ajax({
        type : 'PUT',
        url : '${pageContext.request.contextPath}/licenses/rest',
        dataType : 'text',
        contentType : 'application/json;charset=UTF-8',
        data : ko.mapping.toJSON(licenseModel),
        success : function(data) {
            window.location.href = '${pageContext.request.contextPath}/licenses/downloadFile/'
                    + data;
        },
        error : function(xhr, ajaxOptions, thrownError) {
            // error handling
        }
    });
}
于 2013-08-13T09:51:01.037 に答える