jQuery에서 양식 이중 제출 방지
나는 서버가 처리하는 데 시간이 조금 걸리는 양식을 가지고 있습니다.사용자가 기다리면서 단추를 다시 클릭하여 양식을 다시 제출하지 않도록 해야 합니다.다음 jQuery 코드를 사용해 보았습니다.
<script type="text/javascript">
$(document).ready(function() {
$("form#my_form").submit(function() {
$('input').attr('disabled', 'disabled');
$('a').attr('disabled', 'disabled');
return true;
});
});
</script>
Firefox에서 이것을 시도하면 모든 것이 비활성화되지만 폼이 포함되어야 할 POST 데이터와 함께 제출되지 않습니다.여러 개의 제출 버튼이 있고 POST에 어떤 사람의 값이 포함되어 있는지 결정하기 때문에 양식과 함께 제출할 버튼이 필요하기 때문에 jQuery를 사용하여 양식을 제출할 수 없습니다.저는 평소와 같이 양식을 제출해야 하고, 그 이후에는 즉시 모든 것을 비활성화해야 합니다.
감사합니다!
2018년 업데이트: 저는 이 오래된 답변에 대해 몇 가지 포인트를 얻었고, 가장 좋은 해결책은 중복 제출이 무해하도록 작업을 동일하게 만드는 것이라고 덧붙이고 싶습니다.
예를 들어, 양식이 주문을 작성하는 경우 양식에 고유 ID를 입력합니다.서버는 해당 ID의 주문 작성 요청을 처음 볼 때 해당 ID를 작성하고 "성공"으로 응답해야 합니다.이후 제출 시에도 "성공"으로 응답해야 하지만(클라이언트가 첫 번째 응답을 받지 못한 경우) 아무것도 변경해서는 안 됩니다.
중복되는 항목은 데이터베이스의 고유성 검사를 통해 탐지하여 레이스 상태를 방지해야 합니다.
당신의 문제는 다음과 같습니다.
$('input').attr('disabled','disabled');
양식이 제출해야 할 데이터를 포함하여 모든 입력을 비활성화하고 있습니다.
제출 단추만 비활성화하려면 다음 작업을 수행합니다.
$('button[type=submit], input[type=submit]').prop('disabled',true);
하지만 저는 그 버튼들조차 비활성화되어 있다면 IE가 양식을 제출하지 않을 것이라고 생각합니다.저는 다른 접근법을 제안하고 싶습니다.
이를 해결하기 위한 jQuery 플러그인
우리는 방금 아래 코드로 이 문제를 해결했습니다.여기요jQuery를 사용하는 입니다.data()
양식을 이미 제출했는지 여부를 표시합니다.그렇게 하면 제출 버튼을 조작할 필요가 없어 IE를 놀라게 할 수 있습니다.
// jQuery plugin to prevent double submission of forms
jQuery.fn.preventDoubleSubmission = function() {
$(this).on('submit',function(e){
var $form = $(this);
if ($form.data('submitted') === true) {
// Previously submitted - don't submit again
e.preventDefault();
} else {
// Mark it so that the next submit can be ignored
$form.data('submitted', true);
}
});
// Keep chainability
return this;
};
다음과 같이 사용합니다.
$('form').preventDoubleSubmission();
페이지 로드당 여러 번 제출할 수 있는 AJAX 양식이 있는 경우 다음과 같이 클래스를 지정한 다음 셀렉터에서 제외할 수 있습니다.
$('form:not(.js-allow-double-submission)').preventDoubleSubmission();
타이밍 접근 방식이 잘못되었습니다. 클라이언트 브라우저에서 작업이 얼마나 오래 걸릴지 어떻게 알 수 있습니까?
방법
$('form').submit(function(){
$(this).find(':submit').attr('disabled','disabled');
});
양식을 제출하면 양식 내부의 모든 제출 단추가 비활성화됩니다.
Firefox에서 단추를 비활성화하면 이 상태가 기록으로 돌아갈 때 기억됩니다.예를 들어, 페이지 로드 시 단추를 사용 가능으로 설정해야 합니다.
네이선 롱의 대답이 가야 할 길이라고 생각합니다.저는 클라이언트 측 검증을 사용하고 있기 때문에 양식이 유효하다는 조건만 추가했습니다.
편집: 추가하지 않으면 클라이언트 측 유효성 검사에서 오류가 발생할 경우 사용자는 양식을 제출할 수 없습니다.
// jQuery plugin to prevent double submission of forms
jQuery.fn.preventDoubleSubmission = function () {
$(this).on('submit', function (e) {
var $form = $(this);
if ($form.data('submitted') === true) {
// Previously submitted - don't submit again
alert('Form already submitted. Please wait.');
e.preventDefault();
} else {
// Mark it so that the next submit can be ignored
// ADDED requirement that form be valid
if($form.valid()) {
$form.data('submitted', true);
}
}
});
// Keep chainability
return this;
};
event.timeStamp
Firefox에서는 작동하지 않습니다.을 반환하는 이므로, 은 전화를 . 전화하십시오.event.preventDefault()
그리고 우리가 그것을 하는 동안, 항상 제어 구조가 있는 교정기를 사용하세요.
이전의 모든 답변을 요약하면, 이 작업을 수행하고 크로스 브라우저로 작동하는 플러그인이 있습니다.
jQuery.fn.preventDoubleSubmission = function() {
var last_clicked, time_since_clicked;
jQuery(this).bind('submit', function(event) {
if(last_clicked) {
time_since_clicked = jQuery.now() - last_clicked;
}
last_clicked = jQuery.now();
if(time_since_clicked < 2000) {
// Blocking form submit because it was too soon after the last submit.
event.preventDefault();
}
return true;
});
};
Kern3l을 해결하기 위해, 타이밍 방법은 단순히 제출 버튼의 더블 클릭을 멈추려고 하기 때문에 저에게 효과가 있습니다.제출에 대한 응답 시간이 매우 길면 제출 단추나 양식을 스피너로 교체하는 것이 좋습니다.
위의 예 대부분이 그렇듯이 양식의 후속 제출을 완전히 차단하면 한 가지 나쁜 부작용이 있습니다. 네트워크 오류가 발생하여 다시 제출하려고 하면 이를 수행할 수 없고 변경한 내용이 손실됩니다.이것은 분명 사용자를 화나게 할 것입니다.
jquery-safeform 플러그인을 확인하십시오.
사용 예:
$('.safeform').safeform({
timeout: 5000, // disable next submission for 5 sec
submit: function() {
// You can put validation and ajax stuff here...
// When done no need to wait for timeout, re-enable the form ASAP
$(this).safeform('complete');
return false;
}
});
...그러나 양식이 포함되어야 할 POST 데이터와 함께 제출되지 않았습니다.
맞아요.비활성화된 양식 요소 이름/값은 서버로 전송되지 않습니다.읽기 전용 요소로 설정해야 합니다.
또한 앵커는 그렇게 비활성화될 수 없습니다.다음과 같이 HREF를 제거하거나(권장하지 않음) 기본 동작을 방지해야 합니다(더 나은 방법).
<script type="text/javascript">
$(document).ready(function(){
$("form#my_form").submit(function(){
$('input').attr('readonly', true);
$('input[type=submit]').attr("disabled", "disabled");
$('a').unbind("click").click(function(e) {
e.preventDefault();
// or return false;
});
});
</script>
Nathan Long의 접근 방식을 개선할 가능성이 있습니다.이미 제출된 양식의 탐지 논리를 다음과 같은 논리로 대체할 수 있습니다.
var lastTime = $(this).data("lastSubmitTime");
if (lastTime && typeof lastTime === "object") {
var now = new Date();
if ((now - lastTime) > 2000) // 2000ms
return true;
else
return false;
}
$(this).data("lastSubmitTime", new Date());
return true; // or do an ajax call or smth else
Nathan 코드만 jQuery Validate 플러그인용
jQuery Validate 플러그인을 사용하는 경우 이미 제출 처리기가 구현되어 있으므로 둘 이상을 구현할 이유가 없습니다.코드:
jQuery.validator.setDefaults({
submitHandler: function(form){
// Prevent double submit
if($(form).data('submitted')===true){
// Previously submitted - don't submit again
return false;
} else {
// Mark form as 'submitted' so that the next submit can be ignored
$(form).data('submitted', true);
return true;
}
}
});
내부에서 쉽게 확장할 수 있습니다.} else {
-block - 입력 및/또는 제출 버튼을 비활성화합니다.
건배.
이것으로 두 번째 제출을 중지할 수 있습니다.
$("form").submit(function() {
// submit more than once return false
$(this).submit(function() {
return false;
});
// submit once return true
return true; // or do what you want to do
});
});
저는 이 게시물의 아이디어를 사용하여 At Zako 버전과 매우 유사한 해결책을 생각하게 되었습니다.
jQuery.fn.preventDoubleSubmission = function() {
var last_clicked, time_since_clicked;
$(this).bind('submit', function(event){
if(last_clicked)
time_since_clicked = event.timeStamp - last_clicked;
last_clicked = event.timeStamp;
if(time_since_clicked < 2000)
return false;
return true;
});
};
다음과 같이 사용:
$('#my-form').preventDoubleSubmission();
일종의 제한 시간을 포함하지 않고 제출을 비활성화하거나 양식 요소를 비활성화한 솔루션이 문제를 일으킨다는 것을 발견했습니다. 잠금이 트리거되면 페이지를 새로 고칠 때까지 다시 제출할 수 없기 때문입니다.그것은 나에게 아약스 일을 할 때 약간의 문제를 일으킵니다.
이것은 그렇게 화려하지 않기 때문에 아마 조금 더 예쁘게 만들 수 있을 것입니다.
AJAX를 사용하여 양식을 게시하는 경우, 설정async: false
는 양식이 삭제되기 전에 추가 제출을 방지해야 합니다.
$("#form").submit(function(){
var one = $("#one").val();
var two = $("#two").val();
$.ajax({
type: "POST",
async: false, // <------ Will complete submit before allowing further action
url: "process.php",
data: "one="+one+"&two="+two+"&add=true",
success: function(result){
console.log(result);
// do something with result
},
error: function(){alert('Error!')}
});
return false;
}
});
부트스트랩 3을 위해 Nathan의 솔루션을 약간 수정했습니다.텍스트 로드를 제출 단추로 설정합니다.또한 30초 후에는 시간이 초과되고 양식을 다시 제출할 수 있습니다.
jQuery.fn.preventDoubleSubmission = function() {
$('input[type="submit"]').data('loading-text', 'Loading...');
$(this).on('submit',function(e){
var $form = $(this);
$('input[type="submit"]', $form).button('loading');
if ($form.data('submitted') === true) {
// Previously submitted - don't submit again
e.preventDefault();
} else {
// Mark it so that the next submit can be ignored
$form.data('submitted', true);
$form.setFormTimeout();
}
});
// Keep chainability
return this;
};
jQuery.fn.setFormTimeout = function() {
var $form = $(this);
setTimeout(function() {
$('input[type="submit"]', $form).button('reset');
alert('Form failed to submit within 30 seconds');
}, 30000);
};
두 개의 제출 버튼을 사용합니다.
<input id="sub" name="sub" type="submit" value="OK, Save">
<input id="sub2" name="sub2" type="submit" value="Hidden Submit" style="display:none">
그리고 jQuery:
$("#sub").click(function(){
$(this).val("Please wait..");
$(this).attr("disabled","disabled");
$("#sub2").click();
});
제출 시 간단한 카운터를 사용합니다.
var submitCounter = 0;
function monitor() {
submitCounter++;
if (submitCounter < 2) {
console.log('Submitted. Attempt: ' + submitCounter);
return true;
}
console.log('Not Submitted. Attempt: ' + submitCounter);
return false;
}
그리고 전화monitor()
양식을 제출할 때 기능합니다.
<form action="/someAction.go" onsubmit="return monitor();" method="POST">
....
<input type="submit" value="Save Data">
</form>
저도 비슷한 문제를 겪고 있는데 제 해결책은 다음과 같습니다.
클라이언트 측 유효성 검사가 없는 경우 여기에 설명된 대로 jquery one() 메서드를 사용하면 됩니다.
이렇게 하면 핸들러가 호출된 후에 핸들러가 비활성화됩니다.
$("#mysavebuttonid").on("click", function () {
$('form').submit();
});
만약 당신이 나처럼 클라이언트 측 검증을 한다면, 그것은 조금 더 까다롭습니다.위의 예에서는 유효성 검사에 실패한 후 다시 제출할 수 없습니다.대신 이 방법을 사용해 보십시오.
$("#mysavebuttonid").on("click", function (event) {
$('form').submit();
if (boolFormPassedClientSideValidation) {
//form has passed client side validation and is going to be saved
//now disable this button from future presses
$(this).off(event);
}
});
jQuery 유효성 검사 플러그인을 가져오지 않는 한 이러한 모든 솔루션을 사용할 수 있습니다.
예를 들어 클라이언트가 잘못된 입력을 입력하고 양식을 제출하면 jQuery 유효성 검사에서 잘못된 입력을 탐지하는지 여부에 관계없이 단추가 비활성화됩니다.그러면 고객은 입력을 수정한 후에 양식을 다시 제출할 수 없습니다.
이 문제에 대한 해결 방법은 다음과 같은 경우에만 사용되었습니다.
$('form').submit(function () {
if ($(this).valid()) {
$(this).find("input[type='submit']").prop('disabled', true);
}
});
이 코드를 글로벌로 가져온 JavaScript 파일에 추가한 후 웹 사이트에 양식을 두 번 게시하지 못했습니다.
내 솔루션:
// jQuery plugin to prevent double submission of forms
$.fn.preventDoubleSubmission = function () {
var $form = $(this);
$form.find('[type="submit"]').click(function () {
$(this).prop('disabled', true);
$form.submit();
});
// Keep chainability
return this;
};
저의 경우, 제출 시 양식에 유효성 검사 코드가 있으므로 제출 시 체크포인트를 포함하여 Nathan Long 답변을 증분합니다.
$.fn.preventDoubleSubmission = function() {
$(this).on('submit',function(e){
var $form = $(this);
//if the form has something in onsubmit
var submitCode = $form.attr('onsubmit');
if(submitCode != undefined && submitCode != ''){
var submitFunction = new Function (submitCode);
if(!submitFunction()){
event.preventDefault();
return false;
}
}
if ($form.data('submitted') === true) {
/*Previously submitted - don't submit again */
e.preventDefault();
} else {
/*Mark it so that the next submit can be ignored*/
$form.data('submitted', true);
}
});
/*Keep chainability*/
return this;
};
제출 변경 버튼:
<input id="submitButtonId" type="submit" value="Delete" />
일반 버튼의 경우:
<input id="submitButtonId" type="button" value="Delete" />
그런 다음 클릭 기능을 사용합니다.
$("#submitButtonId").click(function () {
$('#submitButtonId').prop('disabled', true);
$('#myForm').submit();
});
필요한 경우 다시 활성화 버튼을 기억하십시오.
$('#submitButtonId').prop('disabled', false);
나는 포인터 이벤트의 좋은 구식 CSS 트릭을 믿을 수 없습니다: 아직 언급되지 않았습니다.비활성화된 속성을 추가하여 동일한 문제가 발생했지만 이 문제는 다시 게시되지 않습니다.아래를 시도하고 #SubmitButton을 제출 단추의 ID로 바꿉니다.
$(document).on('click', '#SubmitButton', function () {
$(this).css('pointer-events', 'none');
})
이것뿐만 아니라 -- 이것은 양식을 제출할 뿐만 아니라 제출 단추도 비활성화할 것입니다.
$('#myForm').on('submit', function(e) {
var clickedSubmit = $(this).find('input[type=submit]:focus');
$(clickedSubmit).prop('disabled', true);
});
를 사용하는 이 두을 "jQueryValidate" 에 둘 수 .if ($('#myForm').valid())
.
이 코드는 버튼 라벨에 로드를 표시하고 버튼을 다음으로 설정합니다.
비활성화 상태, 처리 후 다시 활성화하고 원래 버튼 텍스트를 반환합니다**
$(function () {
$(".btn-Loading").each(function (idx, elm) {
$(elm).click(function () {
//do processing
if ($(".input-validation-error").length > 0)
return;
$(this).attr("label", $(this).text()).text("loading ....");
$(this).delay(1000).animate({ disabled: true }, 1000, function () {
//original event call
$.when($(elm).delay(1000).one("click")).done(function () {
$(this).animate({ disabled: false }, 1000, function () {
$(this).text($(this).attr("label"));
})
});
//processing finalized
});
});
});
// and fire it after definition
});
내가 찾은 가장 좋은 방법은 버튼을 클릭하면 즉시 비활성화하는 것입니다.
$('#myButton').click(function() {
$('#myButton').prop('disabled', true);
});
필요할 때 다시 활성화합니다. 예:
- 유효성 검사 실패
- 서버에서 양식 데이터를 처리하는 동안 오류가 발생한 다음 jQuery를 사용한 오류 응답 후
다음을 사용하여 매우 유사한 문제를 해결했습니다.
$("#my_form").submit(function(){
$('input[type=submit]').click(function(event){
event.preventDefault();
});
});
언급URL : https://stackoverflow.com/questions/2830542/prevent-double-submission-of-forms-in-jquery
'programing' 카테고리의 다른 글
MySQL의 제한된 수의 테이블에 사용자 액세스 허용 (0) | 2023.08.25 |
---|---|
Python 사전의 스레드 안전 (0) | 2023.08.25 |
gitdiff를 stdout에 쓰도록 하는 방법은? (0) | 2023.08.25 |
재료 각도에서 파지네이터를 사용하는 방법은 무엇입니까? (0) | 2023.08.20 |
도커 파일에서 'COPY' 명령과 'ADD' 명령의 차이점은 무엇입니까? (0) | 2023.08.20 |