Html文件保存-如何克服GET的2K限制.(注意POST不起作用)


Html File Save - How to overcome the 2K limit on GET. (Note POST does not work)

我正在将一个用javascript构建的文件保存到本地互联网下载目录中。

这项工作:

javascript

var filename = "mysave.txt"
var contents = "xyz";
document.location = "htmlsave.php?filename=" + filename + "&contents=" + contents;

htmlsave.php:

if(!isset($_GET)) {
    exit(0);
}
$filename = $_GET['filename'];
$contents = $_GET['contents'];
header("Pragma: public"); // required
header("Expires: 0");
header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
header("Cache-Control: private", false); // required for certain browsers
header("Content-Type: application/octet-stream");
header("Content-Disposition: attachment; filename='"" . $filename . "'";" );
header("Content-Transfer-Encoding: binary");
header("Content-Length: " . strlen($contents));
header("Connection: close");
echo $contents;

这不是:

javascript:

var i;
var filename = "mysave.txt"
var contents = "";
for(i=0, contents = "";i<10000;i++){
    contents += "x";
}
document.location = "htmlsave.php?filename=" + filename + "&contents=" + contents;

由于url的2K限制,这显然不起作用。

错误为:

Request-URI Too Long
The requested URL's length exceeds the capacity limit for this server.

显然,您需要使用POST,但是如何使用POST呢?如何对POST数据执行"document.location="位?您无法执行ajax POST(见下文),我已经尝试过了,但它不起作用。

失败的POST方法:

javascript:

var filename = "mysave.txt"
var contents = "";
for(i=0, contents = "";i<10000;i++){
    contents += "x";
}
dataARR = {
    filename: filename,
    contents: contents
};
var dataJSON = JSON.stringify(dataARR);
$.ajax({
    type: "POST", // This for array
    url: "htmlsave.php",
    async: true,
    cache: false,
    crossDomain: false, // This needs to be true for other people
    data: { myJson: dataJSON },
    success: function (data) {
    },
    error: function (XMLHttpRequest, textStatus, errorThrown) {
    }
});

htmlsave.php

if(!isset($_POST) || !isset($_POST['myJson'])) {
    exit(0);
}
$dataTotal = json_decode($_POST['myJson'], true);
$filename = $dataTotal['filename'];
$contents = $dataTotal['contents'];
header("Pragma: public"); // required
header("Expires: 0");
header("Cache-Control: must-revalidate, post-check=0, pre-check=0");
header("Cache-Control: private", false); // required for certain browsers
header("Content-Type: application/octet-stream");
header("Content-Disposition: attachment; filename='"" . $filename . "'";" );
header("Content-Transfer-Encoding: binary");
header("Content-Length: " . strlen($contents));
header("Connection: close");
echo $contents;

那么,如何保存大于2K的文件呢?

php不需要创建,提示用户保存在javascript创建的文件。您可以使用包含文件数据的Blobdownload属性设置为filenamehref设置为objectURL<a>元素来启动提示用户保存文件。

如果要使用php,可以使用php://inputfile_get_contents()echoPOST ed BlobFile对象。

var i;
var filename = "mysave.txt"
var contents = "";
for(i=0, contents = "";i<10000;i++){
    contents += "x";
}
var data = new Blob([contents], {type:"text/plain"});
var file = URL.createObjectURL(data);
var a = document.createElement("a");
a.download = filename;
a.href = file;
a.click();


使用file_ge_contents()php://input

javascript

var i;
var filename = "mysave.txt"
var contents = "";
for(i=0, contents = "";i<10000;i++){
    contents += "x";
}
var data = new Blob([contents], {type:"text/plain"});
var request = new XMLHttpRequest();
request.open("POST", "/path/to/server");
request.setRequestHeader("x-file-name", filename);
request.reponseType = "blob";
request.onload = function() {
  console.log(this.response); // `echo`ed file
};
request.send(data);

php

echo file_get_contents("php://input");

另请参阅从通过ajax发送的dataURI生成带有php的png文件;尽管注意request.setRequestHeader("x-file-name", filename);本应包含在php$tmpFilename = $_SERVER["HTTP_X_FILE_NAME"];的应答的javascript部分