I'm currently trying to use jQuery to collect information from a HTML form, but I'm stuck.
Every time I console.log payload its empty and didn't capture the input values.
Questions:
Why is payload empty at the end, after I input values into the form?
how to correct it?
Should I use document.ready for this or window.onload?
Please any help is appreciated.
Here is my last attempt jQuery:
$(document).ready(function() {
const ApplyOpeningPayloadBuilder = function() {
let payload = {
"fields": []
};
return {
withKeyValue: function(key, value) {
let param = {};
param.key = key;
param.value = value;
payload.fields.push(param);
return this;
},
withFile: function(key, encoded_data, filename) {
let value = {};
value.encoded_data = encoded_data;
value.file_name = filename;
this.withKeyValue(key, value);
return this;
},
build: function() {
return payload;
}
}
}
let encoded_file = "aGVsbG8gd29ybGQ=";
let apply_for_an_opening_payload_builder = new ApplyOpeningPayloadBuilder();
$(".applicantForm input[type=text]").each(function() {
apply_for_an_opening_payload_builder.withKeyValue(this.name, this.value);
});
$(".applicantForm input[type=email]").each(function() {
apply_for_an_opening_payload_builder.withKeyValue(this.name, this.value);
});
$(".applicantForm input[type=tel]").each(function() {
apply_for_an_opening_payload_builder.withKeyValue(this.name, this.value);
});
$(".applicantForm input[type=url]").each(function() {
apply_for_an_opening_payload_builder.withKeyValue(this.name, this.value);
});
apply_for_an_opening_payload_builder.withFile("resume", encoded_file, "resume.txt");
let payload = apply_for_an_opening_payload_builder.build();
console.log("Log payload:", payload)
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="container" id="json-response">
<div class="form-container">
<div class="header">
<h1>Application form</h1>
</div>
<form action="#" class="applicantForm">
<div class="form-group">
<div class="input-group">
<label for="First Name">First Name <span>*</span></label>
<input type="text" name="First Name">
</div>
<div class="input-group">
<label for="Last Name">Last Name <span>*</span></label>
<input type="text" name="Last Name">
</div>
</div>
<div class="form-group">
<div class="input-group">
<label for="Email">Email <span>*</span></label>
<input type="email" name="Email">
</div>
<div class="input-group">
<label for="Phone">Phone <span>*</span></label>
<input type="tel" name="Phone">
</div>
</div>
<div class="form-group">
<div class="input-group">
<label for="Resume">Resume <span>*</span></label>
<input class="form-control" type="file" name="Resume">
</div>
<div class="input-group">
<label for="LinkedIn Profile">LinkedIn Profile<span>*</span></label>
<input type="url" name="LinkedIn Profile">
</div>
<div class="input-group">
<label for="Website link">Website Link <span>*</span></label>
<input type="url" name="Website link">
</div>
<div class="input-group">
<label for="In lieu of a cover letter, please tell us more about why you are interested in joining the Compass Fellowship?"> In lieu of a cover letter, please tell us more about why you are interested in joining the Compass Fellowship?<span>*</span></label>
<input type="text" name="In lieu of a cover letter, please tell us more about why you are interested in joining the Compass Fellowship?">
</div>
</div>
<button class="submit" type="submit">Apply Now</button>
</form>
</div>
</div>
Here is the structure of how the payload object should look like in the end:
let payload = {
"fields": [
{ "key" : "candidate_first_name", "value" : "John"},
{ "key" : "candidate_last_name", "value" : "Doe"},
{ "key" : "candidate_email", "value" : "john.doe#gmail.com"},
{ "key" : "candidate_phone", "value" : "1234567890"},
{ "key" : "resume", "value": {
"encoded_data" : "aGVsbG8gd29ybGQ=",
"file_name" : "resume.txt"
}
}
]
};
Note the payload structure is from this link, specifically the "Apply for a Opening" section.
You are running all the code at once (document.ready()), instead you need to run it inside form submit, like $('.applicantForm').on('submit', function(e){}).
Check the updated fiddle
var $ = jQuery;
$(document).ready(function() {
const ApplyOpeningPayloadBuilder = function() {
let payload = {
"fields": []
};
return {
withKeyValue: function(key, value) {
let param = {};
param.key = key;
param.value = value;
payload.fields.push(param);
return this;
},
withFile: function(key, encoded_data, filename) {
let value = {};
value.encoded_data = encoded_data;
value.file_name = filename;
this.withKeyValue(key, value);
return this;
},
build: function() {
return payload;
}
}
}
let encoded_file = "aGVsbG8gd29ybGQ=";
$('.applicantForm').on('submit', function(e) {
e.preventDefault();
let apply_for_an_opening_payload_builder = new ApplyOpeningPayloadBuilder();
$(".applicantForm input[type=text]").each(function() {
apply_for_an_opening_payload_builder.withKeyValue(this.name, this.value);
});
$(".applicantForm input[type=email]").each(function() {
apply_for_an_opening_payload_builder.withKeyValue(this.name, this.value);
});
$(".applicantForm input[type=tel]").each(function() {
apply_for_an_opening_payload_builder.withKeyValue(this.name, this.value);
});
$(".applicantForm input[type=url]").each(function() {
apply_for_an_opening_payload_builder.withKeyValue(this.name, this.value);
});
apply_for_an_opening_payload_builder.withFile("resume", encoded_file, "resume.txt");
let payload = apply_for_an_opening_payload_builder.build();
console.log("Log payload:", payload);
})
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<div class="container" id="json-response">
<div class="form-container">
<div class="header">
<h1>Application form</h1>
</div>
<form action="#" class="applicantForm">
<div class="form-group">
<div class="input-group">
<label for="First Name">First Name <span>*</span></label>
<input type="text" name="First Name">
</div>
<div class="input-group">
<label for="Last Name">Last Name <span>*</span></label>
<input type="text" name="Last Name">
</div>
</div>
<div class="form-group">
<div class="input-group">
<label for="Email">Email <span>*</span></label>
<input type="email" name="Email">
</div>
<div class="input-group">
<label for="Phone">Phone <span>*</span></label>
<input type="tel" name="Phone">
</div>
</div>
<div class="form-group">
<div class="input-group">
<label for="Resume">Resume <span>*</span></label>
<input class="form-control" type="file" name="Resume">
</div>
<div class="input-group">
<label for="LinkedIn Profile">LinkedIn Profile<span>*</span></label>
<input type="url" name="LinkedIn Profile">
</div>
<div class="input-group">
<label for="Website link">Website Link <span>*</span></label>
<input type="url" name="Website link">
</div>
<div class="input-group">
<label for="In lieu of a cover letter, please tell us more about why you are interested in joining the Compass Fellowship?"> In lieu of a cover letter, please tell us more about why you are interested in joining the Compass Fellowship?<span>*</span></label>
<input type="text" name="In lieu of a cover letter, please tell us more about why you are interested in joining the Compass Fellowship?">
</div>
</div>
<button class="submit" type="submit">Apply Now</button>
</form>
</div>
</div>
Related
I don't quite understand why when I go to the second entry and then to the others(input), my conditions are not taken into account. Did I make a wrong statement in terms of conditions?
In my code, I assigned rules with regex before sending it to the server. Only condition 1 works.
Thank you for your help.
let inputFirstname = document.querySelector('#firstName');
let inputLastname = document.querySelector('#lastName');
let inputEmail = document.querySelector('#email');
let inputAddress = document.querySelector('#address');
let inputCity = document.querySelector('#city');
const regexName = /^[a-zA-Z-\s]+$/;
const regexMail = new RegExp('^[a-zA-Z0-9.-_]+[#]{1}[a-zA-Z0-9.-_]+[.]{1}[a-z]{2,10}$');
const regexNumber = /^[0-9]{5}$/;
const regexAdress = /^(([a-zA-ZÀ-ÿ0-9]+[\s\-]{1}[a-zA-ZÀ-ÿ0-9]+)){1,20}$/;
document.querySelector('#formContact').addEventListener('change', function (e) {
e.preventDefault();
//Test FIRSTNAME //
if (regexName.test(inputFirstname.value)){
inputFirstname.style.border = " #7EEA5E solid 2px";
return true;
}
//Test LASTNAME //
if (regexName.test(inputLastname.value)) {
inputLastname.style.border = " #7EEA5E solid 2px";
return true;
}
//Test EMAIL //
if (regexMail.test(inputEmail.value)) {
inputEmail.style.border = " #7EEA5E solid 2px";
return true;
}
// Test ADRESS //
if (regexAdress.test(inputAddress.value)) {
inputAddress.style.border = " #7EEA5E solid 2px";
return true;
}
// Test CITY //
if (regexName.test(inputCity.value)) {
inputCity.style.border = " #EA6B5E solid 2px";
return true;
}
else {
alert('Good !');
}
});
<form action="/" method="post" class="row gy-4" id="formContact">
<div class=" form-group">
<label for="firstName">Firstname *</label>
<input type="text" class="form-control" placeholder="" name="firstName" id="firstName"
value="">
<span class="error"></span>
</div>
<div class="form-group">
<label for="lastName" class="form-label">Lastname *</label>
<input type="text" class="form-control" name="lastName" id="lastName" placeholder=""
value="">
<span class="error"></span>
</div>
<div class="form-group">
<label for="email" class="form-label">Email *</label>
<input type="email" class="form-control" name="email" id="email"
placeholder="mail#example.com" value="">
<span class="error"></span>
</div>
<div class="form-group">
<label for="address" class="form-label">Adress *</label>
<input type="text" class="form-control" name="address" id="address"
placeholder="Rue, avenue" value="">
<span class="error"></span>
</div>
<div class="form-group">
<label for="city" class="form-label">City *</label>
<input type="text" class="form-control" id="city" name="city" placeholder="" value="">
<span class="error"></span>
</div>
<div class=" form-group my-4 text-center ">
<button class="btn btnSubmit fw-bold btn-secondary" type="submit"
value="">Order</button>
</div>
</form>
The return calls in your checks exit the whole function on first met condition.
I played a bit around and reworked your code.
Your initial problem was, that you had one function, testing everything even if only one thing changed. On top of that, you wanted to return within each check. The return will exit the function entirely when called. Therefore nothing but your first check came through.
You could avoid this by using a switch case and checking depending on your event.target.id which check you want to run.
I introduced a "global" error variable which defaults to true.
After each check this variable is being updated accordingly.
I added a eventListener with Click on your Order Button, which will only send if error = false, otherwise show an alert. Even though I wouldn't use an altert in production code, since it will HALT your entire code, which might cause problems if you're about to work with async calls.
A message for the user to inform him that everything is ready to be sent seems a bit over the top, since you want to color every field as its updated.
let error = true;
const regexName = /^[a-zA-Z-\s]+$/;
const regexMail = new RegExp('^[a-zA-Z0-9.-_]+[#]{1}[a-zA-Z0-9.-_]+[.]{1}[a-z]{2,10}$');
const regexNumber = /^[0-9]{5}$/;
const regexAdress = /^(([a-zA-ZÀ-ÿ0-9]+[\s\-]{1}[a-zA-ZÀ-ÿ0-9]+)){1,20}$/;
document.querySelector('#formContact').addEventListener('change', function (e) {
e.preventDefault();
const borderCode = " #7EEA5E solid 2px";
switch (e.target.id) {
case 'firstName':
if(regexName.test(e.target.value)) {
error = false;
} else {
error = true;
}
break;
case 'lastName':
if(regexName.test(e.target.value)) {
error = false;
} else {
error = true;
}
break;
case 'email':
if(regexMail.test(e.target.value)) {
error = false;
} else {
error = true;
}
break;
case 'address':
if(regexMail.test(e.target.value)) {
error = false;
} else {
error = true;
}
break;
case 'city':
if(regexName.test(e.target.value)) {
error = false;
} else {
error = true;
}
break;
}
if (!error) {
e.target.style.border = borderCode;
}
});
document.querySelector('#submitButton').addEventListener('click', function (e) {
if(error) {
e.preventDefault();
alert('Some Inputs are not valid.');
}
});
<form action="/" method="post" class="row gy-4" id="formContact">
<div class=" form-group">
<label for="firstName">Firstname *</label>
<input type="text" class="form-control" placeholder="" name="firstName" id="firstName"
value="">
<span class="error"></span>
</div>
<div class="form-group">
<label for="lastName" class="form-label">Lastname *</label>
<input type="text" class="form-control" name="lastName" id="lastName" placeholder=""
value="">
<span class="error"></span>
</div>
<div class="form-group">
<label for="email" class="form-label">Email *</label>
<input type="email" class="form-control" name="email" id="email"
placeholder="mail#example.com" value="">
<span class="error"></span>
</div>
<div class="form-group">
<label for="address" class="form-label">Adress *</label>
<input type="text" class="form-control" name="address" id="address"
placeholder="Rue, avenue" value="">
<span class="error"></span>
</div>
<div class="form-group">
<label for="city" class="form-label">City *</label>
<input type="text" class="form-control" id="city" name="city" placeholder="" value="">
<span class="error"></span>
</div>
<div class=" form-group my-4 text-center ">
<button class="btn btnSubmit fw-bold btn-secondary" type="submit"
id="submitButton" value="">Order</button>
</div>
</form>
I have a form which has various input field with a common name(input array field). I tried to access the value of all elements once the form gets submitted. I able to access all the input field apart from the radio button.
$(document).ready(function() {
function getValue(elem) {
let val = $(elem).val();
if (val === "video") {
let other = $("#videoLink").val();
return other;
}
if (val === "youtube") {
let other = $("#youtubeLink").val();
return other;
}
}
$("#submit").on("click", function() {
$("#form").trigger("submit");
})
$("#form").on("submit", function(e) {
e.preventDefault();
var firstNameValues = $("input[name='firstName[]']").map(function() {
return $(this).val();
}).get();
var lastNameValues = $("input[name='lastName[]']").map(function() {
return $(this).val();
}).get();
var linkValues = $("input[name='link[]']:checked").map(function() {
return getValue(this)
}).get();
})
$("#add-more").on("click", function() {
$("#form > .container").clone().insertAfter("#form");
})
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="col-md-12">
<form name="form" id="form" class="form" method="post">
<div class="container">
<div class="col-md-12 form-group">
<input type="text" name="firstName[]" class="form-control" placeholder="First name" />
</div>
<div class="col-md-12 form-group">
<input type="text" name="lastName[]" class="form-control" placeholder="Last Name" />
</div>
<div class="col-md-12 form-group">
<input type="email" name="email[]" class="form-control" placeholder="Email" />
</div>
<div class="col-md-12 form-group">
<input type="radio" name="link[]" value="youtube">Youtube:<input type="text" id="youtubeLink" name="youtubeLink[]" placeholder="Youtube" />
<input type="radio" name="link[]" value="video">Video<input type="text" id="videoLink" name="videoLink[]" placeholder="Video" />
</div>
</div>
</form>
<button type="button" id="add-more">Add</button>
<button type="button" id="submit" name="submit">Submit</button>
</div>
I have a new auction form. The user has to insert all the requested field , then by clicking on a button "Invite People" can invite other saved users or can invite people by e mail. The email part works fine. But the users part give me some problem.
The html part:
<div ng-show="showBid" class="panel panel-default" ng-controller="NewAuctionController">
<div class="panel-heading">Invite Members</div>
<div class="panel-body">
<ul class="list-group" ng-repeat="user in users">
<li class="col-md-4" id="userlist" ng-hide="user.name == profile">
<img ng-src="{{user.img}}" class="userImage">
<div class="username"> {{user.name}}</div>
<div class="userrole"> {{user.role}} </div>
<div class="usercompany">{{user.company}}</div>
<input type="checkbox" ng-model="user.isChecked" ng-click="insertinvited(user)">
</li>
</ul>
The above part i tried also with ng-change, but it's the same.
The insertinvited() is:
$scope.invitations=[];
$scope.insertinvited= function (user) {
if(user.isChecked) {
$scope.invitations.push(user.name);
} else {
var toDel = $scope.invitations.indexOf(user.name);
$scope.invitations.splice(toDel,1);
}
console.log($scope.invitations);
};
In the console this works, cause when i check the box the array is pushed correctly
But when i try to use that array here:
<div ng-show="showBid" class="panel panel-default" >
<div class="panel-heading">Members Selected:</div>
<div class="panel-body">
<ul class="list-group">
<li class="list-group-item" ng-repeat="invitation in invitations">
<div class="listmail"> {{invitation}}</div>
</li>
</ul>
</div>
</div>
The array seems to be empty, infact when i pass the array to the controller and i try to do a console.log the array is empty.
Anyone could me help?
Edited
This is all my html code:
<form ng-controller="NewAuctionController"
name="myform">
<div>
<div ng-hide="showBid">
<div ng-show="uploading" class="progress">
</div>
<label class="btn" style="background-color: #858892">
Browse
<input type="file" ng-disabled="uploading" file-model="file.upload" name="myfile" style="display: none;" onchange="angular.element(this).scope().photoChanged(this.files)">
</label>
<br>
<br>
<br>
<img class="mythumbnail" ng-src="{{ thumbnail.dataUrl || default }}">
<br>
<br>
<div ng-show="message">
<div ng-class="alert">{{ message }}</div>
</div>
<div class="form-group" id="productname">
<label for="exampleInputName1">Product Name</label>
<input type="text" class="form-control" id="exampleInputName1" placeholder="Enter Product" ng-model="productTitle" >
</div>
<br>
<div class="form-group">
<label for="exampleInputdescription1"> Description:</label>
<input type="text" class="form-control" id="exampleInputdescription1" placeholder="Enter Description" ng-model="productDescription" >
</div>
<div class="form-group">
<label> Expiration Date:</label><br>
<input type="date" class="form-control" name="expiration date" ng-model="endtime" ><br>
</div>
<div class="quantity">
<label>Quantity:</label><br>
<input type="number" name="quantity" ng-model="quantity" placeholder="u" class="form-control" ><br>
</div>
<div class="Warranty">
<label>Warranty (days):</label><br>
<input type="number" name="warranty" class="form-control" ng-model="warranty" placeholder="days" ><br>
</div>
<div class="form-group">
<label>Minimum Price:</label><br>
<input type="number" name="minimum price" id="min" ng-model="minPrice" placeholder="€" class="form-control" ><br>
</div>
<div class="form-group">
<label>Buy-Now Price:</label><br>
<input type="number" name="minimum price" id="min" ng-model="productbuynow" placeholder="€" class="form-control" ><br>
</div>
<div class="form-group">
<label>Location of the goods:</label><br>
<input type="text" name="location" id="country" ng-model="Country" placeholder="Country" class="form-control" ><br>
<input type="text" name="Town" id="town" ng-model="Town" placeholder="Town" class="form-control" ><br>
<input type="text" name="address" id="address" ng-model="Address" placeholder="Address" class="form-control" ><br>
<input type="text" name="Postal code" id="postalCode" ng-model="PostalCode" placeholder="Postal Code" class="form-control" ><br>
</div>
<div class="form-group">
<label>Terms of payment: </label><br>
<select ng-model="payment">
<option value="Letter of credit">Letter of credit</option>
<option value="Cash in advance">Cash in advance</option>
<option value="Confirmed Irrevocable Credit">Confirmed irrevocable Credit</option>
</select><br>
</div>
<div class="form-group">
<label>Terms of Delivery: </label><br>
<select ng-model="delivery">
<option value="Carriage Paid To">Carriage Paid To</option>
<option value="Free Carrier">Free Carrier</option>
<option value="Confirmed Irrevocable Credit">Ex Works</option>
</select><br>
</div>
<input class="savebutton" type="submit" value="Invite People" ng-click="clickToOpen5()"><br>
<div ng-show="showBid" class="panel panel-default" ng-controller="NewAuctionController">
<div class="panel-heading">Invite Members</div>
<div class="panel-body">
<ul class="list-group" ng-repeat="user in users">
<li class="col-md-4" id="userlist" ng-hide="user.name == profile">
<img ng-src="{{user.img}}" class="userImage">
<div class="username"> {{user.name}}</div>
<div class="userrole"> {{user.role}} </div>
<div class="usercompany">{{user.company}}</div>
<input type="checkbox" ng-model="user.isChecked" ng-change="insertinvited(user)">
</li>
</ul>
</div>
<div class="panel-heading">Members Selected:</div>
<div class="panel-body">
<ul class="list-group">
<li class="list-group-item" ng-repeat="invitation in invitations">
<div class="listmail"> {{invitation}}</div>
</li>
</ul>
</div>
<div class= "insertmail" ng-show=" showBid ">
Or Insert E-mail:<br>
<input type="email" name="emailaddress" ng-model="emailaddress">
<div ng-show="showBid" class="panel panel-default" >
<div class="panel-heading">Mail Inserted:</div>
<div class="panel-body">
<ul class="list-group">
<li class="list-group-item" ng-repeat="mail in mails">
<div class="listmail"> {{mail}}</div>
</li>
</ul>
</div>
</div>
<button ng-show="showBid" class="savebutton" ng-click="saveauction(profile)">SAVE</button><br>
</div>
</form>
And this is all my controller:
angular.module('NewAuctionCtrl', ['ngDialog', 'fileModelDirective', 'uploadFileService']).controller('NewAuctionController', ['$scope','$http' ,'ngDialog','uploadFile', '$timeout' , function($scope, $http, ngDialog, uploadFile, $timeout){
$scope.file = {};
$scope.message = false;
$scope.alert = '';
$scope.photoChanged = function (files) {
if (files.length > 0 && files[0].name.match(/\.(png|jpeg|jpg|pdf)$/)) {
$scope.uploading = true;
var file = files[0];
var fileReader = new FileReader();
fileReader.readAsDataURL(file);
fileReader.onload = function(e) {
$timeout(function() {
$scope.thumbnail = {};
$scope.thumbnail.dataUrl = e.target.result;
$scope.uploading = false;
$scope.message = false;
});
};
} else {
$scope.thumbnail = {};
$scope.message = false;
}
};
$http.get('/api/users').then(function(Users) {
$scope.users = Users.data;
});
$scope.mails = [];
$scope.emailaddress = '';
$scope.insertmail = function () {
$scope.mails.push($scope.emailaddress);
$scope.emailaddress = '';
};
$scope.invitations = [] ;
$scope.insertinvited= function (user) {
if(user.isChecked) {
$scope.invitations.push(user.name);
} else {
var toDel = $scope.invitations.indexOf(user.name);
$scope.invitations.splice(toDel,1);
}
console.log($scope.invitations);
};
$scope.saveauction = function (user) {
console.log($scope.invitations);
var array = {
param1: $scope.productTitle,
param2: $scope.productDescription,
param3: $scope.endtime,
param4: $scope.minPrice,
param5: $scope.productbuynow,
param6: user,
param7: $scope.quantity,
param8: $scope.warranty,
param9: $scope.Country,
param10: $scope.Town,
param11: $scope.Address,
param12: $scope.PostalCode,
param13: $scope.payment,
param14: $scope.delivery,
param15:$scope.invitations
};
$scope.uploading = true;
uploadFile.upload($scope.file).then(function (data) {
if (data.data.success) {
$scope.uploading = false;
$scope.alert = 'alert alert-success';
$scope.message = data.data.message;
$scope.file = {};
$http.post('/api/newauction', array)
.then(
function () {
swal(
'Good job!',
'New Auction is created',
'success'
)
});
$scope.sendmail();
}
else {
$scope.uploading = false;
$scope.message = data.data.message;
swal(
'Oops...!',
$scope.message,
'error'
);
$scope.file = {};
}
});
};
$scope.clickToOpen5 = function () {
$scope.showBid = !$scope.showBid;
};
$scope.sendmail = function (){
var address = $scope.mails;
console.log(address);
if(address[0]) {
$http.post('/api/sendmail/', {address: address}).then(function (err) {
if (err)
console.log(err);
});
}
};
});
You should change ng-click to ng-change
<input type="checkbox" ng-model="user.isChecked" ng-change="insertinvited(user)">
And in del of you , i think it should
var todel =$scope.invitations.indexOf(user.name);
$scope.invitations.splice(toDel,1);
This can be the problem of scope inheritance in angular JS.
try to do following changes:
In controller save this to some parameter like:
var vm = this;
now use vm.invitations instead of $scope.invitations.
and in ng-repeat use:
ng-repeat="invitation in vm.invitations"
You are clearing the array with each click.
Remove this statement:
$scope.invitations = [];
and move it to controller's main body; then it should work(especially if you're using ng-change).
this is due to the prototypical inheritance in javascript.
using var vm= this inside controller and
renaming $scope.invitations to vm.invitations in controller and invitations in html to vm.invitations.
will resolve the issue
I am trying to create a webapp that uses angularjs and a backend api build in flask and sqlalchemy. The problem is that some keys in the json contain a dot and angularjs can't handle this. The problem is with the location.name field.
This is the json from the api
{
"brand": "Unknown",
"id": 6,
"location.name": "USB",
"name": "Usb verlengkabel 0.5m",
"uri": "http://localhost:5000/items/6"
}
And this is my angular controller:
angular
.module('inventory')
.controller('Item.ItemEditController', Controller);
function Controller($stateParams,$http) {
var ctrl = this;
$http.get(config.API_URL+'/items'+'/'+$stateParams.itemId ).success(function(data) {
ctrl.item = data;
}).error(function(data){ctrl.errormsg = data});
ctrl.updateItem = function () {
$http({
method: 'PUT',
url: config.API_URL +'/items/' + $stateParams.itemId,
data : this.item
})
.then(function successCallback(response) {
ctrl.result = { class:'alert alert-success', message:'Opgeslagen!'};
console.log(ctrl.result);
}, function errorCallback(response) {
console.log("error")
ctrl.result = { class:'alert alert-danger', message:'Er is iets fout gegaan bij het opslaan'};
});
}
}
And the html page
<div ng-if="ctrl.result.class" ng-class="ctrl.result.class">
{{ctrl.result.message}}
</div>
<form class="form-horizontal" role="form" ng-submit="ctrl.updateItem()">
<div class="form-group">
<label for="name" class="col-sm-2 control-label">Name</label>
<div class="col-sm-10">
<input type="text" ng-model="ctrl.item.name" class="form-control" id="name" placeholder="name"/>
</div>
</div>
<div class="form-group">
<label for="brand" class="col-sm-2 control-label">Brand</label>
<div class="col-sm-10">
<input type="text" ng-model="ctrl.item.brand" class="form-control" id="brand" placeholder="brand" />
</div>
</div>
<div class="form-group">
<label for="location" class="col-sm-2 control-label">Location</label>
<div class="col-sm-10">
<input type="text" ng-model="ctrl.location.name" class="form-control" id="location" placeholder="location" />
</div>
</div>
<div class="form-group">
<div class="col-sm-offset-2 col-sm-10">
<input type="submit" class="btn btn-primary" value="Save"/>
</div>
</div>
</form>
use ctrl.item['location.name'] instead of ctrl.location.name
<input type="text"
class="form-control"
id="location"
placeholder="location"
ng-model="ctrl.item['location.name']" />
plunker: http://plnkr.co/edit/V2LsFL7SNMV8n5nkLQWa?p=preview
The html inside contact_info div is appended dynamically using jquery append function (multiple contact person can exist). How can I produce following json format from the input using jquery?
{
"Company":[
{
"company_name":"ABC Company",
"contact_info":[
{
"contact_person":"Mr. ABC",
"email":"abc#def.com"
},
{
"contact_person":"Mr. XYZ",
"email":"xyz#def.com"
}
]
}
]
}
<div class="form-group">
<label>Company Name
</label>
<div class="col-md-5">
<input name="company_name" id="company_name" type="text" class="form-control">
</div>
</div>
<div id="contact_info">
<div class="row">
<div class="form-group">
<div class="row">
<label>Contact Person
</label>
<input name="contact_person" id="contact_person" type="text" class="form-control" maxlength="100">
<label>Email
</label>
<input type="email" name="cp_email" id="cp_email" class="form-control" maxlength="100">
</div>
</div>
</div>
</div>
<button onclick="addCompany()">Add Company</button>
-----------Script------------
var company=[];
function addCompany()
{
var pushed=0;
$.each(company, function(i, data) {
if(data.company_name===$('#company_name').val())
{
company[i].contact_info.push({
"contact_person":$('#contact_person').val(),
"email":$('#cp_email').val()
});
pushed++;
return false;
}
});
if(pushed==0)
{
var obj={
"company_name":$('#company_name').val(),
"contact_info":[
{
"contact_person":$('#contact_person').val(),
"email":$('#cp_email').val()
}
]
};
company.push(obj);
}
alert(JSON.stringify(company));
}