Javascript Google sheets API提供了未捕获(承诺)类型错误:尝试获取资源时出现NetworkError

Javascript Google sheets API提供了未捕获(承诺)类型错误:尝试获取资源时出现NetworkError,javascript,google-sheets-api,fetch-api,Javascript,Google Sheets Api,Fetch Api,我正在尝试将一个非常基本的web(只有HTML/CSS/JS)与google sheets连接起来。当我提交表格将数据上传到工作表时,我得到: 未捕获(承诺中)类型错误:尝试获取时出现NetworkError 资源 ​我一直在读,这是因为CORS,但我不知道如何解决它。我的代码非常简单,在谷歌脚本中: function doPost(e){ let jsonResponse; const ss = SpreadsheetApp.getActiveSpreadsheet(); con

我正在尝试将一个非常基本的web(只有HTML/CSS/JS)与google sheets连接起来。当我提交表格将数据上传到工作表时,我得到:

未捕获(承诺中)类型错误:尝试获取时出现NetworkError 资源

​我一直在读,这是因为CORS,但我不知道如何解决它。我的代码非常简单,在谷歌脚本中:

function doPost(e){
  let jsonResponse;

  const ss = SpreadsheetApp.getActiveSpreadsheet();
  const ws = ss.getSheetByName('web')
  const headers = ws.getRange(1, 1, 1, ws.getLastColumn()).getValues()[0];

  const body = e.postData.contents;
  const bodyJSON = JSON.parse(body);

  jsonResponse = ws.appendRow([bodyJSON.name, bodyJSON.email])    
  return sendJSON_(jsonResponse) 
}

function sendJSON_(jsonResponse) {
  return  ContentService.createTextOutput(JSON.stringify(jsonResponse)).setMimeType(ContentService.MimeType.JSON);
}
我已将HTML的代码减少到最低限度,并且:

<!DOCTYPE HTML>
<html lang="en">
<head>
    <meta charset="UTF-8">
</head>
<body>
    <div id='form' class="form">
    <form id="customerForm">
        <input type="text" id="name" placeholder="name">
        <input type="email" id="email" placeholder="Email">
        <button type="submit" id="submitButton">Send</button>
    </form>

    <script>
        function afterSubmit(e){
        url = 'https://script.google.com/macros/s/........../exec'
        var name = document.getElementById('name')
        var email = document.getElementById('email')
        var info = {
            name: name.value,
            email: email.value
        };
        console.log(info);

        fetch(url, {
            method: 'POST',
            cache: 'no-cache',
            redirect: 'follow',
            body: JSON.stringify(info)
        })
        .then(res => res.json())
        .then(res => {
            console.log(res)
        })
          }

        document.getElementById('customerForm').addEventListener('submit', afterSubmit);

    </script>

</body>

</html>

发送
后提交函数(e){
url='1〕https://script.google.com/macros/s/........../exec'
var name=document.getElementById('name')
var email=document.getElementById('email'))
变量信息={
name:name.value,
电子邮件:email.value
};
控制台日志(信息);
获取(url{
方法:“POST”,
缓存:“无缓存”,
重定向:“跟随”,
正文:JSON.stringify(info)
})
.then(res=>res.json())
。然后(res=>{
console.log(res)
})
}
document.getElementById('CustomPerform')。addEventListener('submit',提交后);
我还检查了当我将google sheets脚本发布为web应用程序时,是否将选项正确设置为: 以“我”的身份执行应用程序(email@gmail.com) 谁有权访问该应用程序:任何人,甚至匿名

我在控制台中得到错误的方法是用浏览器打开HTML文件,填写数据,然后按send。

Modified Apps Script
函数doPost(e){
让我们来回应;
const ss=SpreadsheetApp.getActiveSpreadsheet();
const ws=ss.getSheetByName('web')
const headers=ws.getRange(1,1,1,ws.getLastColumn()).getValues()[0];
const body=e.postData.contents;
const bodyJSON=JSON.parse(body);
jsonResponse={“name”:bodyJSON.name,“email”:bodyJSON.email}//MODIFIED
ws.appendRow([jsonResponse.name,jsonResponse.email])//修改
}
  • 我相信你的主要问题是这条线

    jsonResponse = ws.appendRow([bodyJSON.name, bodyJSON.email])
    
    如果您看到,它会显示返回类型为
    工作表
    。因此,理论上,没有我的修改,下一行应该返回一个错误。应用程序脚本仪表板中的执行说明了什么?这就是说,它可能仍然能够更新工作表

    修改后,您的HTML成功地更新了脚本,即使它在浏览器控制台中抛出了一系列错误

  • 您也不需要显式返回任何内容,它就可以正常工作,这就是我在这里省略它的原因

修改的HTML
提交后的函数(e){
网址=
"https://script.google.com/macros/s//exec";
var name=document.getElementById(“名称”);
var email=document.getElementById(“电子邮件”);
变量信息={
name:name.value,
email:email.value,
};
控制台日志(信息);
获取(url{
方法:“张贴”,
缓存:“无缓存”,
模式:“无cors”,//防止cors错误
重定向:“跟随”,
正文:JSON.stringify(info),
})
.然后((res)=>console.log(res))
.catch((err)=>console.log(err));
e、 preventDefault();//防止窗体重新加载页面
}
文档.getElementById(“CustomerPerform”).addEventListener(“提交”,提交后);
  • 这里唯一添加的是
    模式:“无cors”
  • 最后的
    e.preventDefault()
    禁止了我收到的“无法获取”错误,因为表单提交自动重新加载了页面。看起来,由于页面重新加载发生在响应返回之前,因此它只会说“失败”,尽管它成功地更新了脚本
  • 由于no cors参数,返回的对象实际上为空,请参阅
如果你想要一个更有意义的回答,@Tanaike在之前的帖子中建议使用async,如下所示:

const fetchData=async(url,info)=>{
var-json;
试一试{
const response=等待获取(url{
方法:“POST”,
正文:JSON.stringify(info),
});
if(response!=“”)json=wait response.json();
log('Success:',JSON.stringify(JSON));
}捕获(e){
console.log('Errors:',e.message)
}
返回json;
}
异步函数main(){
const res=等待获取数据(url、信息);
控制台日志(res);
}
main()
这还需要将以下内容添加到应用程序脚本端:

返回ContentService.createTextOutput(JSON.stringify(e)).setMimeType(ContentService.MimeType.JSON);
工具书类

我有点困惑,因为你提到这是一个web应用程序,这意味着这是一个应用程序脚本项目,但你说你有一个“本地”版本和一个js文件,这个“本地”在哪里?你能澄清一下你是如何设置这个项目的吗?@iansedano我已经编辑过,让它更清楚。当我说“web app”是作为web app发布GoogleSheets脚本的选项时。JS文件对应于我想与Google sheets脚本连接的网页。很抱歉,我仍然很难理解您是如何设置它的。这个远程“网页”在哪里?到底是什么?远程服务器?这可能是因为远程服务器对CORS有某些限制吗?请参阅。@iansedano我已将代码缩减到我能做到的最低限度,我希望现在这是可以理解的,如果您确实遇到了CORS错误(您共享的错误可能是CORS,但我认为您没有共享完整的错误),那么您很可能无法解决此问题。谷歌不会让第三方直接访问他们的端点。