0

我正在向$.postservlet 发送请求,发送一些需要保存在文件中的数据。servlet 保存数据,然后发回文件的路径。我正在尝试导航到response方法回调中所持有的路径,但这是发生了什么:

function saveData(){
    var path;

    $.post("SaveFileServlet", {data : JSON.stringify(jsonPieces)}, function(response) {
        path = response; // setting the path like this does NOT WORK - nothing happens           
        //path="storing/csv_uploads/test.csv"; // setting the path like this WORKS        

        alert (path); // shows: storing/csv_uploads/filename.csv - e.g. WHAT IT SHOULD

        $("body").append("<iframe src='" + path + "' style='display: none;' ></iframe>");       
    });        
}   

如何使它工作,为什么它不工作?谢谢。

更新的编辑

明白了!!!!!!...这是servlet:它可能没有创建文件:真正的路径不是filename.csva System.currentTimeMillis()+".csv",然后我将它写入服务器。但我只是在创建文件后才发送响应(或者我是吗?)......

    protected void processRequest(HttpServletRequest request, HttpServletResponse response)
        throws ServletException, IOException {

    response.setContentType("text/plain");
    response.setCharacterEncoding("UTF-8");
    String filename = "storing/csv_uploads/"+System.currentTimeMillis()+".csv";
    //String filename = "storing/csv_uploads/filename.csv"; //this works since it was previously there
    PrintWriter out = response.getWriter();

    try {
        Type type = new TypeToken<List<PieceFeeder>>(){}.getType();
        ArrayList<PieceFeeder> pieceFeeders = new Gson().fromJson(request.getParameter("data"), type);            

        DataManager dm = new DataManager();
        if (dm.exportPieces(pieceFeeders, filename)) {
            System.out.println("in SaveFileServlet: after exportPieces");
            File f = new File(filename);
            while (!f.exists()) {
                //waiting...I NEVER GET IN HERE
                System.out.println("in SaveFileServlet: waiting for file to exist");
            }
            out.write(filename);
        } else {
            out.write("error at creating file");
        }
    }...
}

DataManager.exportPieces

public void exportPieces(ArrayList<PieceFeeder> pieceFeeders, String filename) {
    BufferedWriter bufferedWriter = null;
    try {
        bufferedWriter = new BufferedWriter(new FileWriter(filename));

        //write first line without "\n"
        if (pieceFeeders.size() > 0) {
            PieceFeeder pf = pieceFeeders.get(0);
            Piece p = pf.getPiece();
            bufferedWriter.write(p.getDescription() + ","
                    + pf.getStock() + ","
                    + p.getLength() + ","
                    + p.getWidth() + ","
                    + p.getLengthEdges() + ","
                    + p.getWidthEdges());
        }
        for (int i = 1; i < pieceFeeders.size(); i++) {
            PieceFeeder pf = pieceFeeders.get(i);
            Piece p = pf.getPiece();
            bufferedWriter.write("\n" + p.getDescription() + ","
                    + pf.getStock() + ","
                    + p.getLength() + ","
                    + p.getWidth() + ","
                    + p.getLengthEdges() + ","
                    + p.getWidthEdges());
        }
        return true;
    } catch (Exception ex) {
        Logger.getLogger(DataManager.class.getName()).log(Level.SEVERE, null, ex);
        return false;
    } finally {
        //Close the BufferedWriter
        try {
            if (bufferedWriter != null) {
                bufferedWriter.flush();
                bufferedWriter.close();
                System.out.println("in exportPieces: finally"); 
            }
        } catch (IOException ex) {
            Logger.getLogger(DataManager.class.getName()).log(Level.SEVERE, null, ex);
        }
    }
}

我总是得到

"in exportPieces: finally"

"in SaveFileServlet: after exportPieces"

并且"in SaveFileServlet: waiting for file to exist"永远不会被调用,因此文件在发送响应之前就存在

但是如果我发送一个旧文件*一个尚未创建的文件),它就可以工作

较新的编辑

只是为了说清楚:如果我这样做:

  • window.location = path
  • $("body").append("<iframe src='" + path + "' ></iframe>");删除display:none 它给出一个404 errorThe requested resource () is not available.但标题显示我正在尝试访问:http://localhost:8080/optimizerwithservlet/storing/csv_uploads/filename.csv所以它就在那里

编辑

正如用户所言,我安装了 Firebug,这就是我得到的:

<iframe style="display: none;" src="storing/csv_uploads/filename.csv">

意思是它有效!但是为什么不显示...?

旧编辑:

万一这可能很重要,尽管我对此表示怀疑:这是来自servlet的相关代码:

    response.setContentType("text/plain");
    response.setCharacterEncoding("UTF-8");
    String filename = "storing/csv_uploads/filename.csv";
    PrintWriter out = response.getWriter();
    out.write(filename);    
4

4 回答 4

3

$.post是异步的。您正试图在值存在之前对其进行警报,仅此而已。

来自jQuery API 文档

Ajax 中的第一个字母代表“异步”,这意味着操作是并行发生的,并且不保证完成的顺序。$.ajax() 的 async 选项默认为 true,表示在发出请求后可以继续执行代码。强烈建议不要将此选项设置为 false(从而使调用不再是异步的),因为它可能导致浏览器无响应。

于 2012-10-26T16:42:02.400 回答
0

克劳迪娅:

您绝对确定您从 servlet 获得的响应是​​带有路径的简单字符串吗?它周围没有任何空白或类似的东西吗?如果不确定,请尝试将您的设置dataTypetext.

我对您的建议是<iframe>在您的页面中放置一个src属性设置为您的文件下载路径的属性。确保您甚至可以访问该文件。这至少可以排除它是否是相对路径问题。

而不是使用alert(),使用console.log()- 作为console.log()将保留数据结构并让您正确查看它。

编辑

function saveData(){
    var path;

    $.post("SaveFileServlet", {dataType: 'text', data : JSON.stringify(jsonPieces)}, function(response) {
        path = response; // setting the path like this does NOT WORK - nothing happens           

        console.log (path); 

        $("body").append("<iframe src='" + path + "' style='display: none;' ></iframe>");       
    });        
}   
于 2012-10-26T17:11:12.227 回答
0

编辑:您可能需要将数据类型指定为“文本”以确保返回字符串。

在回调中,假设response是一个字符串,您可以简单地执行以下操作:

window.location = response;

这会将浏览器重定向到响应指示的路径,假设它是绝对 url 或根相对路径(即以 / 开头)。

于 2012-10-26T16:46:28.737 回答
-1

问题是执行顺序。正如climage 所指出的,ajax 调用是异步的,所以浏览器在等待结果时会继续做一些事情。

最基本的:

function doSomething() {
    $.post("SaveFileServlet", {data : JSON.stringify(jsonPieces)}, function(response) {
      alert('post done');
    }
    alert('doSomething done');
}

几乎 100% 的时间,您将收到的第一个警报将是“doSomething done”而不是“post done”。

这是因为 JavaScript 不会等待 ajax 调用完成以继续进行下一步。

于 2012-10-26T16:46:19.923 回答