Reputation: 9
I create a simple mailer for our updates into client emails, But how can I send the data one by one and process each data on server side
html:
<p class="response"></p>
<form id="send_updates">
{% csrf_token %}
<textarea name="mail-list" class="mails" id="mails"></textarea>
<button type="submit"> start sends </button>
</form>
javascript:
let mails = $('#mails').val().split('\n');
for(let i = 0; i <= cc.length; i++){
$.ajax({
cache: false,
type: 'post',
url: "{% url 'send_mail' %}",
data: {'email': mails[i]},
async: true,
beforeSend:function(xhr, settings){
xhr.setRequestHeader("X-CSRFToken", "{{ csrf_token }}");
};
success: function(data){
if (data.success) == true{
$('.response').append(mails[i] + ' sent!')
}else{
$('.response').append(mails[i] + ' not sent!')
};
}
});
BUT! It Sends All Request without waiting if it Success or Not
EDIT:
We Want to Monitor One By One If That Email is Send Successfully or Not!
Upvotes: 1
Views: 106
Reputation: 125
Try setting
async: false,
as shown below:
let mails = $('#mails').val().split('\n');
for(let i = 0; i <= cc.length; i++){
$.ajax({
cache: false,
type: 'post',
url: "{% url 'send_mail' %}",
data: {'email': mails[i]},
async: false,
beforeSend:function(xhr, settings){
xhr.setRequestHeader("X-CSRFToken", "{{ csrf_token }}");
};
success: function(data){
if (data.success) == true{
$('.response').append(mails[i] + ' sent!')
}else{
$('.response').append(mails[i] + ' not sent!')
};
}
});
Refer What does "async: false" do in jQuery.ajax()?
Upvotes: 1
Reputation: 3237
If you need to update the UI as they happen:
function fetchNextMail(mails) {
const nextMail = mails.shift();
$.ajax({
type: "get",
url:
"https://jsonplaceholder.typicode.com/todos/1"
}).then(res => {
console.log(Object.keys(res));
console.log(mails.length);
mails.length && fetchNextMail(mails);
});
}
fetchNextMail(["x", "y", "z"]);
If you can wait for all of them to finish to update the UI, you can use Promise.all
:
Promise.all(
["x", "y", "z"].map(mail => {
return $.ajax({
type: "get",
url: "https://jsonplaceholder.typicode.com/todos/1"
});
})
).then(results => {
// results[0], results[1] and results[2]
console.log(results.length);
});
A working example can be found here: https://codesandbox.io/s/jquery-playground-i2vb4
Upvotes: 1
Reputation: 7949
You can use the async/await
.
function getData(ajaxurl , mail) {
return $.ajax({
cache: false,
type: 'post',
url: "{% url 'send_mail' %}" /*instead `ajaxurl`*/,
data: {'email': mail},
beforeSend:function(xhr, settings){
xhr.setRequestHeader("X-CSRFToken", "{{ csrf_token }}");
},
success: function(data){
if (data.success == true){
$('.response').append(mails[i] + ' sent!');
}else{
$('.response').append(mails[i] + ' not sent!')
}
}
});
};
async function test(mail){
try {
const res = await getData('https://api.icndb.com/jokes/random' , mail);
console.log(res);
} catch(err) {
console.log(err);
}
}
var mails = $('#mails').val().split('\n');
for(let i = 0; i <= cc.length; i++){
var mail = mails[i];
test(mail);
}
Try out this method . Here the test()
function is async and will await for getData()
function to complete everytime . Through this , you will achieve your goal .
Upvotes: 1