Google Apps Script: Workflow approval Selecting approval broken - javascript

I'm working to expand on the workflow script posted here...
James Ferreira Workflow video.
I've expanded the script and all is working fine regarding email, but I'm running into an issue with the doGet() function not working corretly.
Here is the code from the video: (mycode for the sendEmail is different and works fine, as it uses and document template.
function sendEmail(e) {
var email = e.values[1];
var Item = e.values[2];
var cost = e.values[3];
var url = '<ENTER YOUR PUBLISHED URL>';
var approve = url + '&approval=true'+'&reply='+email;
var reject = url + '&approval=false'+'&reply='+email;
var html = "<body>"+
"<h2>Please review</h2><br />"+
Item +": " + cost+ "<br />"+
"Approve<br />"+
"Reject<br />"+
"</body>";
MailApp.sendEmail("jjones#beaconcloudsolutions.com", "Approval Request",
"What no html?", {htmlBody: html});
}
function doGet(e){
var answer = (e.parameter.approval == 'true') ? 'Buy it!' : 'Not this time, Keep saving';
MailApp.sendEmail(e.parameter.reply, "Purchase Request",
"Your manager said: "+ answer);
var app = UiApp.createApplication();
app.add(app.createHTML('<h2>An email was sent to '+ e.parameter.reply + ' saying: '+ answer + '</h2>'))
return app
}
So when the script runs, i get the email that shows the links for approval / rejected, but when I select the link for approval or / rejected i get
"Sorry, the page (or document) you have requested does not exist." " Please check the address and try again."
This link should be redirect to the published webapp, noted in the var URL and append either the var approve or reject to it and then just display a basic HTML page.
Any suggestions on what is wrong? the script is authorized..

What does the address bar say when you click on the link from the email? Perhaps something is malformed or not properly encoded.
My gut feeling right now is that there is a missing '?' before you append any params.
Perhaps try this -
//note the ? instead of &
var approve = url + '?approval=true'+'&reply='+email;
var reject = url + '?approval=false'+'&reply='+email;

Related

In Sheet, Send email to a specific recipient when a cell is filled

I am trying to create a sheet for project management to collaborate easily among many interlocutor (I know there are free tools outhere working with a public organization is hellish to insert new procedures into the project).
Here is the sample file created : Google Sheet for Test
The ideais everytime a new question is input, the author can select the menu "Question" > "Send Question".
And it should sent automatic email to the Recipient email address (column C)... under the condition that the Question cell is filled (condition checked in "I2").
But currently, the script does not work as expected.
Note: I am currently learning JS.
Here is the code :
function onOpen() {
var ui = SpreadsheetApp.getUi();
ui.createMenu('Question')
.addItem('Send Question', 'sendQuestion')
.addSeparator()
.addItem('Send Answer', 'sendAnswer')
.addToUi();
}
function sendQuestion() {
var sheet = SpreadsheetApp.getActiveSpreadsheet().getSheetByName("Questions");
var range = sheet.getRange("A22:L2");
var emailvalid = range.getCell(1,7).getValue();
var question = range.getCell(1,5).getValue();
var answer = range.getCell(1,6).getValue();
var qvalid = range.getCell(1,8).getValue();
var ansvalid = range.getCell(1,10).getValue();
if(qvalid == "Nope"){
Browser.msgBox("Please, write a question !");
}
else {
return false};
if(emailvalid == "Nope"){
Browser.msgBox("Please, input a valid email address !");
}
else {
return false};
var from = range.getCell(1,1).getValue();
var recipient = range.getCell(1,2).getValue();
var emailTo = range.getCell(1,3).getValue();
var subject = "Project Management | Your received a new question" + question;
var link = "https://docs.google.com/spreadsheets/d/1QUbw0WNju55h5pk3l8QqVCYa_jSCzrIzMjf0N4v-z8c/edit?usp=sharing"
var options = {}
options.htmlBody = "Hi" + recipient +"," + "<br />"+ "<br />" + "You received a new question from " + from + "<br />" + "<br />" + "You can answer directly into the table here: "<"br />"+"<br />" + link + "<br />" + "<br />"+ "Thank you";
GmailApp.sendEmail(emailTo, subject, " ", options);
}
function emailSent(){
var ui = SpreadsheetApp.getUi();
var sent = sendQuestion("Send Email ?",ui.ButtonSet.YES_NO);
if(sent == ui.Button.YES) {
ui.alert("Your Message has been sent.");
} else {
ui.alert("Email canceled");
}
}
You're main error there is this else return false statement you have, which is basically terminating the function if your validation passes, where it should be the other way around, exiting the function if the validation fails, after you popup informing the problem.
if(qValid == 'Nope') {
Browser.msgBox('etc...');
return; //return here, not in the else clause
}
//same for email valid
There are quite a few other "improvements" I'd do on such function. But I guess it's beyond the point here, you're learning as you go and the most important is that it works now.

Acrobat JavaScript mailDoc operation failing

Goal: I have a fillable PDF form that collects data required to send an email. In the PDF, I have a button to send the PDF, using the mailDoc function on mouse up.
if(app.viewerVersion < 11 )
app.alert("Please download the latest version of Reader",1);
var cToAddr = "email#yahoo.com";
var cBCCAddr = "email#yahoo.com";
var cCCAddr = this.getField("ClientEmail").value;
var cBenAddr = this.getField("BennyEmail").value;
if(cBenAddr != "") {
cCCAddr += ";" + cBenAddr;
}
var cSubLine = "Service Proposal " + this.getField("ServiceAddress").value + " " + this.getField("Text1").value;
var cBody = "Thank you for the opportunity. Please see attached proposal.\n" + "Save the filled form attachment for your own records";
this.mailDoc({
bUI: true,
cTo: cToAddr,
cCc: cCCAddr,
cBcc: cBCCAddr,
cSubject: cSubLine,
cMsg: cBody
});
Error Message:
GeneralError: Operation failed.
Doc.mailDoc:22:AcroForm:Email Quote:Annot1:MouseUp:Action1
I've followed this guide and added a cBcc as they did in this community post, but it had no impact.
The fields are accurately named, and it prompts me to sign into my email account when I press the button, so I'm not sure what is causing the issue, and can't find documentation for mailDoc to help.
Your code is correct. This seems to be a bug when using Yahoo! to send the email. When I try to send it via Outlook or Gmail it works for me (and fails on Yahoo!).
You can find the javascript documentation here: http://www.adobe.com/content/dam/Adobe/en/devnet/acrobat/pdfs/js_api_reference.pdf#G5.2237013

Google Script send form values by email, error: cannot read property "namedValues"

Project key: MyvPlY2KvwGODjsi4szfo389owhmw9jII
I am trying to run a script that sends the contents of my form by email each time the form is submitted. I was following the instructions from this link below exactly until I started getting errors and I received advice to change my script to open spreadsheets by id:
http://www.snipe.net/2013/04/email-contents-google-form/
When I complete the form, it is supposed to email the contents to my email.
The problem I am now having is that the function which goes through the form values doesn't work. It's returning the error
TypeError: Cannot read property "namedValues" from undefined. (line 15, file "Code")"
in regards to the piece of code below:
for(var i in headers)
message += headers[i] + ': '+ e.namedValues[headers[i]].toString() + "\n\n";
I am not too familiar with Google Apps Scripts so I'm not sure how to work around this issue either. Is there anything you recommend? I have included the entire script below.
function sendFormByEmail(e)
{
// Remember to replace this email address with your own email address
var email = "sample#email.com";
var s = SpreadsheetApp.openById("1hOqnK0IVa2WT6-c-MY0jyGGSpIJIV2yzTXdQYX4UQQA").getSheets()[0];
var headers = s.getRange(1,1,1,s.getLastColumn()).getValues()[0];
var message = "";
var subject = "New User Form";
// The variable e holds all the form values in an array.
// Loop through the array and append values to the body.
for(var i in headers)
message += headers[i] + ': '+ e.namedValues[headers[i]].toString() + "\n\n";
// Insert variables from the spreadsheet into the subject.
// In this case, I wanted the new hire's name and start date as part of the
// email subject. These are the 3rd and 16th columns in my form.
// This creates an email subject like "New Hire: Jane Doe - starts 4/23/2013"
subject += e.namedValues[headers[2]].toString() + " - starts " + e.namedValues[headers[15]].toString();
// Send the email
MailApp.sendEmail(email, subject, message);
}
The function appears to be undefined as 'e' is not received as part of the function context. You'll need to set a trigger for the submission of the form, and send the information to the function. You can use the following code:
/* Send Confirmation Email with Google Forms */
function Initialize() {
var triggers = ScriptApp.getProjectTriggers();
for (var i in triggers) {
ScriptApp.deleteTrigger(triggers[i]);
}
ScriptApp.newTrigger("SendConfirmationMail")
.forSpreadsheet(SpreadsheetApp.getActiveSpreadsheet())
.onFormSubmit()
.create();
}
function SendConfirmationMail(e) {
try {
var ss, cc, sendername, subject, columns;
var header, message, value, textbody, sender, itemID, url;
// This is your email address and you will be in the CC
cc = "name#email.com";
// This will show up as the sender's name
sendername = "name to be displayed as sender";
// Optional but change the following variable
// to have a custom subject for Google Docs emails
subject = "Choose an approppiate subject";
// This is the body of the auto-reply
message = "";
ss = SpreadsheetApp.getActiveSheet();
columns = ss.getRange(1, 1, 1, ss.getLastColumn()).getValues()[0];
// This is the submitter's email address
sender = e.namedValues["Username"].toString();
// Only include form values that are not blank
for ( var keys in columns ) {
var key = columns[keys];
//Use this to look for a particular named key
if ( e.namedValues[key] ) {
if ( key == "Username" ) {
header = "The user " + e.namedValues[key] + " has submitted the form, please review the following information.<br />";
} else {
message += key + ' ::<br /> '+ e.namedValues[key] + "<br />";
}
}
}
}
textbody = header + message;
textbody = textbody.replace("<br>", "\n");
Logger.log("Sending email");
GmailApp.sendEmail(cc, subject, textbody,
{cc: cc, name: sendername, htmlBody: textbody});
} catch (e) {
Logger.log(e.toString());
}
}
I have the same error and it took me some time to figure out how to solve it.
The problem is that you are writing your code in the form, and you should do it in your spreadsheet.
When I created the function inside the form and registered the event, it was called but the parameter didn't have the same structure (and didn't have the field namedValues, so the error "Cannot read property "namedValues" from undefined"). A better way to check this is to log the object as a JSON string:
Logger.log("e: " + JSON.stringify(e));
So, the steps I have made to correct this issue:
Create a spreadsheet
Create the form through the spreadsheet (inside the spreadsheet select Tools->Create a form), and create your form
Go back to your spreadsheet, and create the script (Tools->Script Editor)
Write your function
Register the function (Edit->Current Project's Triggers): function sendFormByEmail, Event: From Spreadsheet -> On form submit
Hope this helps
There is an error in this line of code:
message += headers[i] + ': '+ e.namedValues[headers[i]].toString() + "\n\n";
it's this part:
e.namedValues[headers[i]].toString()
I'm just guessing that you want:
e.namedValues + [headers[i]].toString()
You're missing a plus sign if you want to concatenate the values.

Expense approval workflow + hierarchy approval

I'm working to expand on the workflow script posted here:
James Ferreira Workflow video.
function sendEmail(e) {
var email = e.values[1];
var Item = e.values[2];
var cost = e.values[3];
var vendor = e.values[4];
var url = '<SPREADSHEET>';
var approve = url + '?approval=true'+'&reply='+email;
var reject = url + '?approval=false'+'&reply='+email;
var html = "<body>"+
"<h3>Please review</h3><br />"+
Item +": " + cost+ ": " + vendor+ "<br />"+
"Approve<br />"+
"Reject<br />"+
"</body>";
MailApp.sendEmail("<MY EMIAL>", "Approval Request",
"What no html?", {htmlBody: html});
}
function doGet(e){
var answer = (e.parameter.approval == 'true') ? 'Buy it!' : 'Not this time, Keep saving';
MailApp.sendEmail(e.parameter.reply, "Purchase Request",
"Your manager said: "+ answer);
var app = UiApp.createApplication();
app.add(app.createHTML('<h3>An email was sent to '+ e.parameter.reply + ' saying: '+ answer + '</h3>'))
return app
}
Question 1) How do you build in an additional approval flow dependent on the cost?
Question 2) Depending on the approval amount how can I adjust the manager emaill?
For example: if the cost is above £500 I would like to send the approval email to another email account / manager. Would be amazing if the script could automatically recognise this.
Any support of this is much appreciated,
Andrew

Google forms auto-email not showing up

My company has a google form that we use to submit requests for data pulls. I created a script that auto emails form responses to myself, as well as a copy to the submitter. The script is:
function Initialize() {
var triggers = ScriptApp.getScriptTriggers();
for(var i in triggers) {
ScriptApp.deleteTrigger(triggers[i]);
}
ScriptApp.newTrigger("SendGoogleForm")
.forSpreadsheet(SpreadsheetApp.getActiveSpreadsheet())
.onFormSubmit()
.create();
}
function SendGoogleForm(e)
{
try
{
// You may replace this with another email address
var email = "My Email Goes here"
var Owner = e.namedValues["Owner:"].toString();
cc = email + "," + Owner
Adv = e.namedValues["Advertiser Name:"].toString();
IO = e.namedValues["IO Name:"].toString();
Tog = "Pixel Request " + Adv + " " + IO;
// Optional but change the following variable
// to have a custom subject for Google Form email notifications
var subject = Tog;
var s = SpreadsheetApp.getActiveSheet();
var columns = s.getRange(1,1,1,s.getLastColumn()).getValues()[0];
var message = "";
// Only include form fields that are not blank
for ( var keys in columns ) {
var key = columns[keys];
if ( e.namedValues[key] && (e.namedValues[key] != "") ) {
message += key + ' :: '+ e.namedValues[key] + "\n\n";
}
}
// This is the MailApp service of Google Apps Script
// that sends the email. You can also use GmailApp for HTML Mail.
MailApp.sendEmail(cc, subject, message);
} catch (e) {
Logger.log(e.toString());
}
}
The script sends the emails without a problem. However, while the email sent to myself shows up in my sent mail, no copy is delivered to my inbox and it is marked as read; this is a problem because then I do not know that requests have been submitted which was the point of this creation. This seems anomalous as normally emails to yourself will typically show up in the inbox as unread. Does anyone know a way I might be able to fix this?
This is not an issue with the Google Script. This is probably how Gmail handles email where the sender and recipient is you.

Categories

Resources