I have a very simple Google Apps Script which uses showModalDialog() to open an HTML form over a spreadsheet. The popup tries to send an input value back to the sheet and then close itself. The problem is sometimes the popup's POST request (called using google.script.run()) is cancelled and the sheet is not updated.
When I remove the call to google.script.host.close() the request completes successfully and the sheet is updated. EDIT: Arrgh, I swear this used to work, but now I can't get the data written back to the sheet under any circumstances. Removing the close() does allow the callback to be sent successfully, though.
I've tried using async/await or a success handler (see bottom of question) but neither have worked. How do I make the popup self-closing after the data is successfully sent?
Here's the server-side code:
function onOpen() {
var ui = SpreadsheetApp.getUi();
ui.createMenu('Test Menu')
.addItem('Open Test Popup', 'showPopup')
.addToUi();
return false;
}
function showPopup(){
var html = HtmlService.createTemplateFromFile('Popup').evaluate().setWidth(400).setHeight(350);
SpreadsheetApp.getUi().showModalDialog(html, 'Test Title');
return false;
}
function writeCustomValue(valueToWrite) {
var sheet = SpreadsheetApp.getActive().getActiveSheet();
var cell = sheet.getCurrentCell();
cell.setValue(valueToWrite);
return false;
}
Here's the popup client-side code:
<!DOCTYPE html>
<html>
<head>
<base target="_top">
<link rel="stylesheet" href="https://ssl.gstatic.com/docs/script/css/add-ons1.css">
</head>
<body>
<div class="block form-group">
<label for="valueToWrite">Write this value</label>
<input type="text" id="valueToWrite">
</div>
<button id="writeResponse" onclick='writeResponse()' class="action block">Write this value</button>
<script>
function writeResponse(){
document.getElementById('writeResponse').innerHTML = 'Saving ...';
document.getElementById('writeResponse').disabled = true;
//Get the value of the input field
var valueToWrite = document.getElementById('valueToWrite').value;
//Send the value of the text field as an argument to the server side function.
google.script.run.writeCustomValue(valueToWrite);
google.script.host.close();
}
</script>
</body>
</html>
Here's what I've tried:
- Putting
host.close()in a success handler:
google.script.run.withSuccessHandler(google.script.host.close()).writeCustomValue(valueToWrite);
- Async/await:
async function writeResponse(){
document.getElementById('writeResponse').innerHTML = 'Saving ...';
document.getElementById('writeResponse').disabled = true;
//Get the value of the input field
var valueToWrite = document.getElementById('valueToWrite').value;
//Send the value of the text field as an argument to the server side function.
await google.script.run.writeCustomValue(valueToWrite);
google.script.host.close();
}
