jade version of zipcodeapi example - javascript

Trying to create a jade version to do autofill city state from
https://www.zipcodeapi.com/Examples
script(type='text/javascript').
//<![CDATA[
$(function() {
// IMPORTANT: Fill in your client key
console.log("thing")
var clientKey = "js-9qZHzu2Flc59Eq5rx10JdKERovBlJp3TQ3ApyC4TOa3tA8U7aVRnFwf41RpLgtE7";
var cache = {};
var container = $("#example1");
var errorDiv = container.find("div.text-error");
/** Handle successful response */
function handleResp(data)
{
// Check for error
if (data.error_msg)
errorDiv.text(data.error_msg);
else if ("city" in data)
{
// Set city and state
container.find("input[name='city']").val(data.city);
console.log(data.city);
container.find("input[name='state']").val(data.state);
}
}
// Set up event handlers
container.find("input[name='zipcode']").on("keyup change", function() {
// Get zip code
var zipcode = $(this).val().substring(0, 5);
if (zipcode.length == 5 && /^[0-9]+$/.test(zipcode))
{
// Clear error
errorDiv.empty();
// Check cache
if (zipcode in cache)
{
handleResp(cache[zipcode]);
}
else
{
//Build url
var url = "https://www.zipcodeapi.com/rest/"+clientKey+"/info.json/" + zipcode + "/radians";
// Make AJAX request
$.ajax({
"url": url,
"dataType": "json"
}).done(function(data) {
handleResp(data);
// Store in cache
cache[zipcode] = data;
}).fail(function(data) {
if (data.responseText && (json = $.parseJSON(data.responseText)))
{
// Store in cache
cache[zipcode] = json;
// Check for error
if (json.error_msg)
errorDiv.text(json.error_msg);
}
else
errorDiv.text('Request failed.');
});
}
}
}).trigger("change");
});
//]]>
div#example1
label Zip:
input(type='text', name='zipcode', value='')
label City:
input(type='text', name='city', value='')
label State:
input(type='text', name='state', value='')
I am getting the following error and not sure why this is erroring out:
$ is not defined
Any ideas? This is a conversion from the original javascript so I am not sure what I am doing wrong in the conversion. Thanks!

Always listen to your error messages; they're usually right. $ isn't defined. Have you included jQuery (just guessing) in a higher-level template, of which this is a subtemplate? If not, $ is undefined is a valid message from the javascript interpreter.

Related

Javascript Ajax: how to get the Id of something?

Right now I'm trying to do a simple delete / update / get through the User Id but I'm not getting the data correctly and I don't know if it's because of the ajax function, if it's for my web Api or if it's because of gRPC ,
My question is similar to this link I already asked, so I'll maybe show the simplest part which is the delete and also show the ajax call
Old Link: gRPC and/or WebAPI: How to do a simple Update but using an Id
gRPC Delete:
public override async Task<Empty> Delete(UserFilter requestData,
ServerCallContext context)
{
var data = await _context.Users_5.FindAsync(requestData.UserID);
if(date == null)
{
throw new Exception("User Not Found");
}
_context.Users_5.Remove(data);
await _context.SaveChangesAsync();
return await Task.FromResult(new Empty());
}
WebApi:
[HttpDelete("{Id_user}")]
public async Task<ActionResult<Empty>> DeleteUser([FromBody] UserFilter Id_user)
{
_logger.Log(LogLevel.Information, "Request Received for AuthController::Delete");
/**
if(Id_user == null)
{
return BadRequest("Id not Found idk why");
}
if(Id_user.ToString() != Request.Cookies["LoginUserId"])
{
return BadRequest("Id's is Different");
}
*/
var results = await _userClient.DeleteAsync(Id_user);
_logger.Log(LogLevel.Information, "Sending Response from AuthController::Delete");
return Ok(results);
}
The Javascript Code:
var $users_A = $('#users_A');
var $Id_user = $('#Id_user')
$users_A.delegate('.remove', 'click', function () {
var $li = $(this).closest('li');
var self = this;
debugger;
$.ajax({
url: uri_7 + $Id_user,
type: 'DELETE',
success: function() {
$li.fadeOut(300, function () {
$(this).remove();
});
},
error: function (xhr, textStatus, errorThrown) {
console.log('XHR:' + JSON.stringify(xhr) + '\nTextStatus:' + textStatus + '\nErrorThrown:' + errorThrown);
}
});
});
The stupid error:
XHR:{"readyState":4,"responseText":"{"type":"https://tools.ietf.org/html/rfc7231#section-6.5.1","title" :"One or more validation errors occurred.","status":400,"traceId":"00-82ac37132e06d497f2f7ec082e382273-ba6109fbfa7fd9f8-00","errors":{"$\ ":["The input does not contain any JSON tokens. Expected the input to start with a valid JSON token, when isFinalBlock is true. Path: $ | LineNumber: 0 | BytePositionInLine: 0."],"Id_user":["The Id_user field is required."]}}","responseJSON":{"type":"https://tools.ietf.org/ html/rfc7231#section-6.5.1","title":"One or more validation errors occurred.","status":400,"traceId":"00-82ac37132e06d497f2f7ec082e382273-ba6109fbfa7fd9f8-00","errors":{ "$":["The input does not contain any JSON tokens. Expected the input to start with a valid JSON token, when isFinalBlock is true. Path: $ | LineNumber: 0 | BytePositionInLine: 0."],"Id_user": ["The Id_user field is required."]}},"status":400,"statusText":"error"}
--Conclusion--
Idk what's happening, I have the post and the getAllUsers correct but getting a specific user it gives me a lot of pain, so how to correct this code??
Any Answer/Help is always welcome

How to Auto-Run a Script in Google Sheets when someone's Data Entry to the Sheet?

I want to Auto-Run Script in Google Sheets every time someone registers from my custom form on my website and the Data Entry to the Sheet.
I tried with adding an OnSubmit event on Trigger but it did not work because I don't use Google Forms I use a Script to collect the data from my website.
Here is the Send Emails Script that I want to Auto-Run and send an email each time someone's data comes into the sheet:
function sendMail() {
const emailTemp = HtmlService.createTemplateFromFile("email");
const sh = SpreadsheetApp.getActiveSpreadsheet().getSheetByName("form1");
const startRow = 2;
const data = sh.getRange(startRow, 2, sh.getLastRow() - 1, sh.getLastColumn() - 1).getValues();
data.forEach((row, i) => {
emailTemp.first = row[2];
emailTemp.last = row[3];
emailTemp.phone = row[9];
let htmlMessage = emailTemp.evaluate().getContent();
let emailSent = row[11];
if (emailSent != "EMAIL_SENT") {
GmailApp.sendEmail(
row[1],
"Thank you!",
"Your email doesn't support HTML.",
{ name: "Email App", htmlBody: htmlMessage });
sh.getRange(startRow + i, 13).setValue("EMAIL_SENT");
}
});
}
Here is the Data Collection Script on my website:
// Variable to hold request
var request;
var url = window.location.href;
$( document ).ready(function() {
$('#url').val(url);
});
console.log(url);
// Bind to the submit event of our form
$("#request-form").submit(function(event){
// Abort any pending request
if (request) {
request.abort();
}
// setup some local variables
var $form = $(this);
// Let's select and cache all the fields
var $inputs = $form.find("input, select, button, textarea");
// Serialize the data in the form
var serializedData = $form.serialize();
// Let's disable the inputs for the duration of the Ajax request.
// Note: we disable elements AFTER the form data has been serialized.
// Disabled form elements will not be serialized.
$inputs.prop("disabled", true);
// Fire off the request to /form.php
request = $.ajax({
url: "https://script.google.com/macros/s/AKfycbwa50RJFxZfnBXQX-LBHR4OD6Lzxb0a2tAclBzGV57nT0XY3WU/exec",
type: "post",
data: serializedData
});
// Callback handler that will be called on success
request.done(function (response, textStatus, jqXHR){
// Log a message to the console
console.log("Hooray, it worked!");
console.log(response);
console.log(textStatus);
console.log(jqXHR);
});
// Callback handler that will be called on failure
request.fail(function (jqXHR, textStatus, errorThrown){
// Log the error to the console
console.error(
"The following error occurred: "+
textStatus, errorThrown
);
});
// Callback handler that will be called regardless
// if the request failed or succeeded
request.always(function () {
// Reenable the inputs
$inputs.prop("disabled", false);
console.log("It's running");
window.location.href = 'success.html';
});
// Prevent default posting of form
event.preventDefault();
});
And here is the Script I have used on the Sheet and Deploy it As Web App, and made it accessable to Anyone, even anonymous.
// 1. Enter sheet name where data is to be written below
var SHEET_NAME = "Leads";
// 2. Run > setup
//
// 3. Publish > Deploy as web app
// - enter Project Version name and click 'Save New Version'
// - set security level and enable service (most likely execute as 'me' and access 'anyone, even anonymously)
//
// 4. Copy the 'Current web app URL' and post this in your form/script action
//
// 5. Insert column names on your destination sheet matching the parameter names of the data you are passing in (exactly matching case)
var SCRIPT_PROP = PropertiesService.getScriptProperties(); // new property service
// If you don't want to expose either GET or POST methods you can comment out the appropriate function
function doGet(e){
return handleResponse(e);
}
function doPost(e){
return handleResponse(e);
}
function handleResponse(e) {
// shortly after my original solution Google announced the LockService[1]
// this prevents concurrent access overwritting data
// [1] http://googleappsdeveloper.blogspot.co.uk/2011/10/concurrency-and-google-apps-script.html
// we want a public lock, one that locks for all invocations
var lock = LockService.getPublicLock();
lock.waitLock(30000); // wait 30 seconds before conceding defeat.
try {
// next set where we write the data - you could write to multiple/alternate destinations
var doc = SpreadsheetApp.openById(SCRIPT_PROP.getProperty("key"));
var sheet = doc.getSheetByName(SHEET_NAME);
// we'll assume header is in row 1 but you can override with header_row in GET/POST data
var headRow = e.parameter.header_row || 1;
var headers = sheet.getRange(1, 1, 1, sheet.getLastColumn()).getValues()[0];
var nextRow = sheet.getLastRow()+1; // get next row
var row = [];
// loop through the header columns
for (i in headers){
if (headers[i] == "Timestamp"){ // special case if you include a 'Timestamp' column
row.push(new Date(), "UTC-7");
} else { // else use header name to get data
row.push(e.parameter[headers[i]]);
}
}
// more efficient to set values as [][] array than individually
sheet.getRange(nextRow, 1, 1, row.length).setValues([row]);
// return json success results
return ContentService
.createTextOutput(JSON.stringify({"result":"success", "row": nextRow}))
.setMimeType(ContentService.MimeType.JSON);
} catch(e){
// if error return this
return ContentService
.createTextOutput(JSON.stringify({"result":"error", "error": e}))
.setMimeType(ContentService.MimeType.JSON);
} finally { //release lock
lock.releaseLock();
}
}
function setup() {
var doc = SpreadsheetApp.getActiveSpreadsheet();
SCRIPT_PROP.setProperty("key", doc.getId());
}
Thank you.
If you are sending the data to the web app via POST request from the client, then use the doPost(e) function in your Apps Script to do what you want.
Include the sendMail() function inside your doPost(e) function before it returns.
Example:
before you execute this line
return ContentService.createTextOutput(JSON.stringify({"result":"success", "row": nextRow})).setMimeType(ContentService.MimeType.JSON);
in handleResponse(e) I would have the program execute sendMail(). I would also have 2 different functions for doGet and doPost but that's up to you.

Javascript Variables Not Globally Returning / Adding Together

I'm trying to add both Facebook and Twitter share counters together, however all my efforts have failed.
<script>
tweets = 0;
function getTwitterCount(url){
$.getJSON('http://urls.api.twitter.com/1/urls/count.json?url=' + url + '&callback=?', function(data){
tweets = data.count;
$('#twitterCount').html(tweets);
return true;
});
}
var urlBase='http://abcdfav4.com/About/KickStarterCampaign/Rewards/ThePeaceSensation.html';
getTwitterCount(urlBase);
$.ajax({
type: 'GET',
url: 'https://graph.facebook.com/http://abcdfav4.com/About/KickStarterCampaign/Rewards/ThePeaceSensation.html',
success: function(data) {
showCount(data);
}
});
var fbshares = 0;
function showCount(responseText) {
// Save the parsed JSON
var json = responseText;
// Check if the response contains a 'shares' property
// If it doesn't, we can just exit this function
if (!json.hasOwnProperty('shares'))
return;
// A shares property and value must exist, update
// the span element with the share count
fbshares = json.shares;
$('#fb-share-count').html(fbshares);
}
var TotalShares = tweets + fbshares;
$('#total-share-count').html(TotalShares);
</script>
I could really do with some outside insight as I've been working crazy to get this website up and running ASAP and I'm probably overlooking the most obvious of things...
Console Log Reads:
Uncaught ReferenceError: fbshares is not defined
sdk.js:64 Invalid App Id: Must be a number or numeric string representing the application id.
card.html?v=2:79 Uncaught ReferenceError: I18n is not defined
sdk.js:64 FB.getLoginStatus() called before calling FB.init().
However despite this message, the Facebook and Twitter counters are working 100%, I just cannot get them to add together.
Best Regards,
Tim
Here's a solution:
var tweets;
function getTwitterCount(url) {
$.getJSON('http://urls.api.twitter.com/1/urls/count.json?url=' + url + '&callback=?', function(data) {
tweets = data.count;
$('#twitterCount').html(tweets);
showTotal();
});
}
var urlBase = 'http://abcdfav4.com/About/KickStarterCampaign/Rewards/ThePeaceSensation.html';
getTwitterCount(urlBase);
$.ajax({
type: 'GET',
url: 'https://graph.facebook.com/http://abcdfav4.com/About/KickStarterCampaign/Rewards/ThePeaceSensation.html',
success: showCount
});
var fbshares;
function showCount(responseText) {
// Save the parsed JSON
var json = responseText;
// Check if the response contains a 'shares' property
// If it doesn't, we can just exit this function
if (!json.hasOwnProperty('shares'))
return;
// A shares property and value must exist, update
// the span element with the share count
fbshares = json.shares;
$('#fb-share-count').html(fbshares);
showTotal();
}
function showTotal() {
if (tweets !== undefined && fbshares !== undefined)
$('#total-share-count').html(tweets + fbshares);
}
Basically showTotal attempts to sum the two values after each callback. When both values are defined, it will place the sum into the HTML.

how to validate serialized data in Ajax

I have this particular problem, where I need to validate the data before it is saved via an ajax call. save_ass_rub function is called when user navigates to a different URL.
In my application, I have a custom Window and user is allowed to input data. I am able to capture all the data in this step: var data = $('form').serialize(true);. But I need to loop through this and check if data for some specific elements is empty or not. I can't do it when the user is in the custom window. The Custom window is optional for the user. All I want is to alert the user in case he has left the elements blank before the data is submitted.
We are using Prototype.js and ajax .
<script>
function save_ass_rub() {
var url = 'xxxx';
var data = $('form').serialize(true);
var result;
new Ajax.Request( url, {
method: 'post',
parameters: data,
asynchronous: false, // suspends JS until request done
onSuccess: function (response) {
var responseText = response.responseText || '';
if (responseText.length > 0) {
result = eval('(' + responseText + ')');
}
}
});
if (result && result.success) {
return;
}
else {
var error = 'Your_changes_could_not_be_saved_period';
if (window.opener) { // ie undocked
//Show alert in the main window
window.opener.alert(error);
return;
}
return error;
}
}
// Set up auto save of rubric when window is closed
Event.observe(window, 'unload', function() {
return save_ass_rub();
});
</script>
Can some thing like this be done?
After Line
var data = $('form').serialize(true);
var split_data = data.split("&");
for (i = 0; i < split_data.length; i++) {
var elem = split_data[i];
var split_elem = elem.split('=');
if( split_elem[0].search(/key/) && split_elem[0] == '' ){
console.log( split_elem );
var error = 'Not all the elements are inputted';
window.opener.alert(error);
return;
}
}
Instead of using the serialized form string, I would use the form itself to do the validation. if $('form') is your form element then create a separate function that checks the form element so its compartmentalized.
function checkform(form)
{
var emptytexts = form.down('input[type="text"]').filter(function(input){
if(input.value.length == 0)
{
return true;
}
});
if(emptytexts.length > 0)
{
return false;
}
return true;
}
and in the save_ass_rub() function
//..snip
if(checkform($('form') == false)
{
var error = 'Not all the elements are inputted';
window.opener.alert(error);
return;
}
var data = $('form').serialize(true);
var result;
I only added text inputs in the checkform() function you can the rest of the input types and any other weird handling you would like to that function. As long as it returns false the error will be displayed and the js will stop otherwise it will continue

"this is undefined error" in JS using Google Maps API

I can't seem to figure out this problem where the below code works when the "for loop" is disabled, and the attributes "locations" and "startAddress" are just simple strings. But if they are not, I am getting a "this is undefined" error when the ajax post request is submitted. Do you have any ideas why would this be? Any leads would be appreciated.
// create an event handler for the save route button
$("#saveRouteButton").click(function(){
var saveRouteName = $("#saveRouteNameField").val();
if (!saveRouteName) {
alert("Please supply a proper name to be submitted to the database");
} else {
var routeLength = directionsDisplay.getDirections().routes[0].legs.length;
var returnRoute = {
alias: null,
locations : [], // make this a string - it works!
startAddresses : [], // make this a string - it works!
};
// disable this loop - it works!
for (var i = 0; i < routeLength; i++){
returnRoute.locations[i] = directionsDisplay.getDirections().routes[0].legs[i].start_location
returnRoute.startAddresses[i] = directionsDisplay.getDirections().routes[0].legs[i].start_address
};
route_info = returnRoute;
route_info.alias = saveRouteName;
//test to see if the variables are set, they are!
alert(route_info.alias);
alert(route_info.locations);
alert($.isPlainObject(route_info))
$.ajax({
url: "save_route/",
type: "POST",
data : route_info,
success: function(data){
if (data != "None") {
$("#savedRoutesList").append('<li class="savedRoutesListItem">'
+ data + '</li>');
}
else {alert("You need to enter a route name");}
}
});
}
return false;
});
the error originates from the : google maps main js - line 13
Thanks!
Just check the route Length value,whether it is giving correct value or not?

Categories