Javascript 如何使用fetch正确等待成功上传?
我目前正在尝试使用fetch将大量照片(约150-200张)作为Base64一次上传到Cloudinary API。这是我在Expo(SDK 35)不支持Blob和Firebase不接受Base64图像后痛苦的解决方法 在我的应用程序中,照片存储在子目录中。我想要的结果是有一个函数,它获取目录列表并分别上传每个目录中的每个图像。当前,当我运行此函数时,它会适当地查看目录内部,并返回目录中所有文件的数组。但它并没有调用uploadImage并在尝试下一次上载之前等待完成,而是尝试一次上载所有照片 理想情况下,该函数将在移动到下一个子目录之前逐个上载子目录中的所有照片。下面列出了我的代码Javascript 如何使用fetch正确等待成功上传?,javascript,react-native,async-await,es6-promise,fetch-api,Javascript,React Native,Async Await,Es6 Promise,Fetch Api,我目前正在尝试使用fetch将大量照片(约150-200张)作为Base64一次上传到Cloudinary API。这是我在Expo(SDK 35)不支持Blob和Firebase不接受Base64图像后痛苦的解决方法 在我的应用程序中,照片存储在子目录中。我想要的结果是有一个函数,它获取目录列表并分别上传每个目录中的每个图像。当前,当我运行此函数时,它会适当地查看目录内部,并返回目录中所有文件的数组。但它并没有调用uploadImage并在尝试下一次上载之前等待完成,而是尝试一次上载所有照片
const hardDirs = [
{
photoDirectory: "exampleDir1",
},
{
photoDirectory: "exampleDir2",
},
{
photoDirectory: "exampleDir3",
},
{
photoDirectory: "exampleDir4",
},
];
//Parse through directories
async function _directoryNavigator(documentId) {
//TODO: SWITCH TO ASYNCSTORAGE KEY FOR DIRECTORIES
for (let i = 0; i < hardDirs.length; i++) {
let localDir = FileSystem.documentDirectory + hardDirs[i].photoDirectory;
//supply both appropriate path format and name of directory to retrieve files and supply new folder name
let directoryFolder = hardDirs[i].photoDirectory;
//documentId is auto-generated string supplied by Firebase Cloud Firestore for associated scope JSON schema
let firebaseDoc = documentId;
console.log("getting directory " + directoryToUpload);
await _uploadFromDirectory(localDir, directoryFolder, firebaseDoc);
}
}
//Return list of each file in directory, create upload
_uploadFromDirectory = async (localDir, directoryFolder, firebaseDoc) => {
console.log("enumerate from directory");
let directoryContents = await FileSystem.readDirectoryAsync(localDir);
for (let i = 0; i < directoryContents.length; i++) {
let uri = directoryContents[i];
console.log("getting image inside directory" + imageFile);
await createFileUpload(imageFile, localDir, directoryFolder, firebaseDoc);
}
}
createFileUpload = async (uri, localDir, directoryFolder, firebaseDoc) => {
console.log("create base64 file for upload");
let imagePath = `${localDir}/${uri}`;
//console.log("uploadAsFile", imagePath);
const response = await FileSystem.readAsStringAsync(
imagePath,
{
encoding: FileSystem.EncodingType.Base64,
});
let base64Img = `data:image/jpg;base64,${response}`;
let apiUrl = 'https://api.cloudinary.com/v1_1/USERNAME/image/upload';
let data = {
"file": base64Img,
"upload_preset": "PRESET",
"folder": `${directoryFolder}`,
"public_id": `${firebaseDoc}/${directoryFolder}/${uuid.v4()}`
};
const upload = await uploadImage(apiUrl, data);
}
async function uploadImage(apiUrl, data) {
try {
console.log("upload image")
let response = await fetch(apiUrl, {
body: JSON.stringify(data),
headers: {
'content-type': 'application/json'
},
method: 'POST',
});
let data = await response.json();
return data.secure_url;
console.log(data.secure_url);
} catch(err) {
console.error(err);
}
}
常数hardDirs=[
{
光电定向:“exampleDir1”,
},
{
光电定向:“exampleDir2”,
},
{
光电定向:“exampleDir3”,
},
{
光电定向:“exampleDir4”,
},
];
//通过目录解析
异步函数directoryNavigator(documentId){
//TODO:切换到目录的异步存储密钥
for(设i=0;i{
log(“从目录枚举”);
让directoryContents=await FileSystem.readdirectoryanc(localDir);
for(设i=0;i{
log(“创建用于上载的base64文件”);
让imagePath=`${localDir}/${uri}`;
//log(“uploadAsFile”,imagePath);
const response=await FileSystem.readAsStringAsync(
imagePath,
{
编码:FileSystem.EncodingType.Base64,
});
让base64Img=`data:image/jpg;base64,${response}`;
让我们来看看https://api.cloudinary.com/v1_1/USERNAME/image/upload';
让数据={
“文件”:base64Img,
“上传预设”:“预设”,
“文件夹”:“${directoryFolder}”,
“public_id”:`${firebaseDoc}/${directoryFolder}/${uuid.v4()}`
};
const upload=等待上传图像(APIRL,数据);
}
异步函数上载映像(apiUrl,数据){
试一试{
console.log(“上传图像”)
let response=等待获取(APIRL{
正文:JSON.stringify(数据),
标题:{
“内容类型”:“应用程序/json”
},
方法:“POST”,
});
让data=wait response.json();
返回data.secure\u url;
console.log(data.secure_url);
}捕捉(错误){
控制台错误(err);
}
}
我还是一个比较新的人,会用母语做出反应,并尽可能最好地理解ES6。任何指导都将不胜感激。提前谢谢 它看起来像是一次上传一个东西给我;你没有承诺。所有的承诺或诸如此类的东西。你怎么知道它试图一次上传所有的文件呢?我已经读到console.log在跟踪wait函数的执行时可能是一个错误的标志。。。但是我的终端输出和上面的日志给了我很多信息:
上传图像在目录1572387353651内获取图像。jpg创建base64文件用于上传图像在目录1572548413671内获取图像。jpg创建base64文件用于上传图像
我会将其解释为每次调用uploadImage时都会忽略不计上次上传时没有返回资产URL?哦,哈,我明白你的意思了。这只是因为您正在执行返回数据.secure\u url
在console.log(data.secure\u url)
之前,因此如果您希望看到该控制台日志,它将永远不会发生,因为return语句将绕过以下语句。我想它正在做你期望的事情,你的日志记录只是有点不正确。@Jacob意外并发更可能是因为忘记了await
,而不是因为明确的承诺。所有的,但我同意代码似乎是按原样工作的。@Thismyclevername我可以问一下,你为什么要写await response.json()代码>而不是response.json()
?。响应是否已从等待获取(…
)解析??