如何在 onchange 函数中使用 promise 获取 json 的文件上传?
How to get json of file upload using promise in onchange function?
我构建了一个将表单转换为 json 的网站,但我需要将上传的图像文件转换为 base64(字符串)并添加到 json,但它只有 return 个 url,它在 console.log() 中成功,但在赋值时没有成功,这是我的代码
<form id="test" action="#" method="post">
<div class="row">
<div class="form-group">
<label>First Name</label>
<input name="namadepan" type="text" placeholder="Enter First Name Here.." class="form-control">
</div>
<div class="form-group">
<label for="gambar">Foto</label>
<input type="file" class="form-control" name ="gambar" id="imagefile" value="Import" onchange="toJSONString(document.getElementById('test'))" />
</div>
<p>
<input type="submit" value="Send" class="btn btn-primary btn-block" />
</p>
</form>
<textarea id="output" class="form-control"></textarea>
这是脚本
function toJSONString(form) {
var obj = {};
var elements = form.querySelectorAll("input, select, textarea");
for (var i = 0; i < elements.length; ++i) {
var element = elements[i];
var name = element.name;
var value = element.value;
if (element.type == "file") {
var p = new Promise(function (resolve) {
var reader = new FileReader();
reader.onload = function () {
code = reader.result;
resolve(code);
console.log(reader.result);
};
reader.readAsDataURL(element.files[0]);
});
p.then(function (result) {
value = result;
})
}
if (name) {
obj[name] = value;
}
}
//return JSON.stringify( obj );
document.getElementById("output").value = JSON.stringify(obj);
}
上面的结果是
{"namadepan":"johndoe","gambar":"C:\fakepath\t2.jpg"}
如我所料
{"namadepan":"johndoe","gambar":"data:image/jpeg;base64,/9j/4AAQSkZJRgABAgAAAQABAAD/2wBDAAUDBAQEAwUE"}
C:\fakepath\t2.jpg
值来自 element.value
。
你看到这个是因为你在 promise 解决之前存储了值。
要正确等待promise,请看下面:
请注意 toJSONString
现在是一个 async
函数
async function toJSONString(form) {
var obj = {};
var elements = form.querySelectorAll("input, select, textarea");
for (var i = 0; i < elements.length; ++i) {
var element = elements[i];
var name = element.name;
// check `name`
if(name) {
// await the Promise here
var value = await new Promise((resolve, reject) => {
if (element.type == "file") {
var reader = new FileReader();
reader.onload = function () {
// resolve to data url
resolve(reader.result);
};
reader.readAsDataURL(element.files[0]);
} else {
// resolve to value
resolve(element.value);
}
});
// store the value after the promise is resolved.
obj[name] = value;
}
}
//return JSON.stringify( obj );
document.getElementById("output").value = JSON.stringify(obj);
}
<form id="test" action="#" method="post">
<div class="row">
<div class="form-group">
<label>First Name</label>
<input name="namadepan" type="text" placeholder="Enter First Name Here.." class="form-control">
</div>
<div class="form-group">
<label for="gambar">Foto</label>
<input type="file" class="form-control" name ="gambar" id="imagefile" value="Import" onchange="toJSONString(document.getElementById('test'))" />
</div>
<p>
<input type="submit" value="Send" class="btn btn-primary btn-block" />
</p>
</form>
<textarea id="output" class="form-control"></textarea>
我构建了一个将表单转换为 json 的网站,但我需要将上传的图像文件转换为 base64(字符串)并添加到 json,但它只有 return 个 url,它在 console.log() 中成功,但在赋值时没有成功,这是我的代码
<form id="test" action="#" method="post">
<div class="row">
<div class="form-group">
<label>First Name</label>
<input name="namadepan" type="text" placeholder="Enter First Name Here.." class="form-control">
</div>
<div class="form-group">
<label for="gambar">Foto</label>
<input type="file" class="form-control" name ="gambar" id="imagefile" value="Import" onchange="toJSONString(document.getElementById('test'))" />
</div>
<p>
<input type="submit" value="Send" class="btn btn-primary btn-block" />
</p>
</form>
<textarea id="output" class="form-control"></textarea>
这是脚本
function toJSONString(form) {
var obj = {};
var elements = form.querySelectorAll("input, select, textarea");
for (var i = 0; i < elements.length; ++i) {
var element = elements[i];
var name = element.name;
var value = element.value;
if (element.type == "file") {
var p = new Promise(function (resolve) {
var reader = new FileReader();
reader.onload = function () {
code = reader.result;
resolve(code);
console.log(reader.result);
};
reader.readAsDataURL(element.files[0]);
});
p.then(function (result) {
value = result;
})
}
if (name) {
obj[name] = value;
}
}
//return JSON.stringify( obj );
document.getElementById("output").value = JSON.stringify(obj);
}
上面的结果是
{"namadepan":"johndoe","gambar":"C:\fakepath\t2.jpg"}
如我所料
{"namadepan":"johndoe","gambar":"data:image/jpeg;base64,/9j/4AAQSkZJRgABAgAAAQABAAD/2wBDAAUDBAQEAwUE"}
C:\fakepath\t2.jpg
值来自 element.value
。
你看到这个是因为你在 promise 解决之前存储了值。
要正确等待promise,请看下面:
请注意 toJSONString
现在是一个 async
函数
async function toJSONString(form) {
var obj = {};
var elements = form.querySelectorAll("input, select, textarea");
for (var i = 0; i < elements.length; ++i) {
var element = elements[i];
var name = element.name;
// check `name`
if(name) {
// await the Promise here
var value = await new Promise((resolve, reject) => {
if (element.type == "file") {
var reader = new FileReader();
reader.onload = function () {
// resolve to data url
resolve(reader.result);
};
reader.readAsDataURL(element.files[0]);
} else {
// resolve to value
resolve(element.value);
}
});
// store the value after the promise is resolved.
obj[name] = value;
}
}
//return JSON.stringify( obj );
document.getElementById("output").value = JSON.stringify(obj);
}
<form id="test" action="#" method="post">
<div class="row">
<div class="form-group">
<label>First Name</label>
<input name="namadepan" type="text" placeholder="Enter First Name Here.." class="form-control">
</div>
<div class="form-group">
<label for="gambar">Foto</label>
<input type="file" class="form-control" name ="gambar" id="imagefile" value="Import" onchange="toJSONString(document.getElementById('test'))" />
</div>
<p>
<input type="submit" value="Send" class="btn btn-primary btn-block" />
</p>
</form>
<textarea id="output" class="form-control"></textarea>