Javascript 使用AJAX将base64图像作为类似文件输入并使用文件名上传
在服务器端,我有一个SpringMVC(JAVA)项目,它使用Javascript 使用AJAX将base64图像作为类似文件输入并使用文件名上传,javascript,jquery,ajax,Javascript,Jquery,Ajax,在服务器端,我有一个SpringMVC(JAVA)项目,它使用MultipartFile @RequestMapping(value = { "/uploadImg/**" }, method = RequestMethod.POST) public void uploadImg(Model model, HttpServletRequest request,HttpServletResponse response,MultipartFile file ) { S
MultipartFile
@RequestMapping(value = { "/uploadImg/**" }, method = RequestMethod.POST)
public void uploadImg(Model model, HttpServletRequest request,HttpServletResponse response,MultipartFile file )
{
String originalFileName = file.getOriginalFilename();
//some cases on based on file name and storing the file into the server
}
以前,我使用
和
上传文件。但现在我有了base64格式的图像数据,并希望使用AJAX将其上传到相同的请求映射
我遇到了这一点,还有很多这样的解决方案。但所有的都只是上传文件数据,但在我的例子中,我想上传带有数据和名称的图像,因为在服务器端,一些逻辑是基于文件名编写的
一个选项可能是,在参数中发送图像数据,在另一个参数中发送文件名,但我无权访问(或者说我不能更改)服务器端代码来执行此操作
那么,使用AJAX如何上传base64图像数据和文件名呢?我用PHP服务器测试了以下代码。我没有访问SpringMVC服务器的权限,但是这两个服务器的JS代码应该是相同的。代码主要基于本文:
//我缩短了base64数据以保持此答案的简短。有关完整数据,请参阅链接文章
让ImageURL=“data:image/gif;base64,R0lGODlhPQBEAPeoAJosM…”;
let block=ImageURL.split(“;”);
让contentType=block[0]。拆分(“:”[1];//在本例中为“image/gif”
让realData=block[1]。拆分(“,”[1];//在本例中,“R0lGODlhPQBEAPeoAJosM…”
设blob=b64toBlob(realData,contentType);
设formDataToUpload=newformdata();
formDataToUpload.append(“image”,blob,“filename.gif”);//您可以在这里设置文件名
$.ajax({
url:“/upload.php”,
数据:formDataToUpload,
键入:“POST”,
contentType:false,
processData:false
});
/**
*根据数据和内容类型转换Blob中的base64字符串。
*
*@param b64Data{String}纯base64字符串,不带contentType
*@param contentType{String}文件的内容类型,即(image/jpeg-image/png-text/plain)
*@param sliceSize{int}sliceSize处理字节字符
*@见http://stackoverflow.com/questions/16245767/creating-a-blob-from-a-base64-string-in-javascript
*@return Blob
*/
函数b64toBlob(b64Data、contentType、sliceSize){
contentType=contentType | |“”;
切片大小=切片大小| | 512;
let byteCharacters=atob(b64Data);
let ByteArray=[];
for(让offset=0;offset
最好是更改生成此base64版本的内容,使其直接返回Blob
如果没有这样的选项,您仍然可以自己将base64字符串转换为Blob。
拥有Blob后,您就可以使用XMLHttpRequest
或fetch
将其发布到服务器上,就像html
一样,这要感谢
//作为base64的1x1px png图像
const b64=“ivborw0kgoaaaansuhueugaaaaaaaaaaabababababababababaaafaffcsjaaaduleqvqimwngygbgaaabqhabh6fo1aaabjru5erkjggg=”;
//将其设置为用户的“name”属性
const上一个文件的\u name\u\u\u input=“file”;
//将其设置为所需的任何文件名
const the_file_name=“pixel.png”;
const blob=新blob([base64ToArrayBuffer(b64)]);
const form=new FormData();
append(上一个文件输入的文件名,blob,文件名);
console.log(…表单);
/*由于无法在StackSnippets中工作,上载将被注释
//对于现代浏览器,可以使用fetchapi
fetch(您的服务器URL,{method:“post”,body:form});
//或者对于较旧的浏览器
const xhr=new XMLHttpRequest();
打开(“POST”,即您的服务器URL);
发送(表格);
*/
函数base64到ArrayBuffer(base64){
const binary_str=atob(base64);
const arr=新的Uint8Array(base64.length);
对于(让i=0;i可能这有帮助:@ahendwh2不,这没有帮助。正如我说的,它将在两个请求参数中发送文件数据和文件名。这将需要更改服务器代码。对吗?我写评论时没有太多时间。我在下面发布了完整的答案
// I've shortend the base64 data to keep this answer short. See the linked article for the complete data
let ImageURL = "data:image/gif;base64,R0lGODlhPQBEAPeoAJosM....";
let block = ImageURL.split(";");
let contentType = block[0].split(":")[1];// In this case "image/gif"
let realData = block[1].split(",")[1];// In this case "R0lGODlhPQBEAPeoAJosM...."
let blob = b64toBlob(realData, contentType);
let formDataToUpload = new FormData();
formDataToUpload.append("image", blob, 'filename.gif'); // Here you can set the filename
$.ajax({
url: '/upload.php',
data: formDataToUpload,
type: 'POST',
contentType: false,
processData: false
});
/**
* Convert a base64 string in a Blob according to the data and contentType.
*
* @param b64Data {String} Pure base64 string without contentType
* @param contentType {String} the content type of the file i.e (image/jpeg - image/png - text/plain)
* @param sliceSize {int} SliceSize to process the byteCharacters
* @see http://stackoverflow.com/questions/16245767/creating-a-blob-from-a-base64-string-in-javascript
* @return Blob
*/
function b64toBlob(b64Data, contentType, sliceSize) {
contentType = contentType || '';
sliceSize = sliceSize || 512;
let byteCharacters = atob(b64Data);
let byteArrays = [];
for (let offset = 0; offset < byteCharacters.length; offset += sliceSize) {
let slice = byteCharacters.slice(offset, offset + sliceSize);
let byteNumbers = new Array(slice.length);
for (let i = 0; i < slice.length; i++) {
byteNumbers[i] = slice.charCodeAt(i);
}
let byteArray = new Uint8Array(byteNumbers);
byteArrays.push(byteArray);
}
return new Blob(byteArrays, {type: contentType});
}