Autor Zpráva
Pavel Krach.
Profil *
Jak zabránit vícenásobnému odeslání formuláře? Nesmí se stát, že se do databáze uloží dva naprosto stejné řádky (jenom jinačí id samozřejmě).
Jak zabránit uživateli, například na pomalejším připojení aby nestihl dvakrát stisknout submit?

Napadlo mě v ukládacím skriptu na začátku kontrolovat, jestli stejný řádek již v db není, ale jedním odesláním formuláře se ukládá třeba 40 řádků a kontrolovat každý řádek v tabulce kde je třeba 300 a víc tisíc řádků zabere nemalý čas jestli se nepletu.

Nějaké nápady?
Díky.
Kubo2
Profil
Pavel Krach.:
Napríklad JavaScriptom po odoslaní nastaviť odosielaciemu tlačítku atribút disabled.

document.forms[0].onsubmit = function() {
  for(var el in this.elements) {
    if(this.elements[el].type == 'submit') {
      this.elements[el].disabled = true;
    }
  }
}
                
Str4wberry
Profil
1) DB to může řešit unikátním indexem.
2) Po odeslání formuláře (onsubmit) je možné další odeslání zablokovat. Je vhodné zároveň nějak znázornit, že už se formulář odesílá.
Pavel Krach.
Profil *
Kubo2
Díky. Vyzkouším.

Str4wberry:
Jak znázornit to, že se formulář odesílá? Aby mi vedle tlačítka uložit vždy na nějakou chvíli problikl nějaký text mi moc dobré řešení nepříjde, zvlášť když to uživatel ani nestihne přečíst.


Kubo2:
Nemám to jak ozkoušet, nemám pomalé připojení. Hodím sem kód:
<head>
<script language="JavaScript" type="text/javascript">
document.forms["pridat_neco"].onsubmit = function() {
  for(var el in this.elements) {
    if(this.elements[el].type == 'submit') {
      this.elements[el].disabled = true;
    }
  }
}
</script>
</head>

<body>
<form method="POST" action="..." name="pridat_neco">
.
.
.
<input type="Submit" value="Uložit">
</form>
</body>

Bude to takhle fungovat? V javascriptu se moc nevyznám, pokud jsem do té funkce výše dal místo "onsubmit" "onmouseover" tak to nefungovalo, resp. tlačítko Uložit bylo i při najetí myši pořád aktivní, tak právě nevím jestli to funguje na to onsubmit.
Str4wberry
Profil
Jestli používáte na serveru PHP. Můžete si pomalou odezvu skriptu vytvořit funkcí sleep.

Aby mi vedle tlačítka uložit vždy na nějakou chvíli problikl nějaký text mi moc dobré řešení nepříjde, zvlášť když to uživatel ani nestihne přečíst.
Může probliknout nějaké točící se kolečko nebo tak něco.
Pavel Krach.
Profil *
Str4wberry:
Díky. Takže jsem zjistil, že ten skript nefunguje. Submit není disabled. Může mi někdo poradit kde je chyba. Díky.
Kajman
Profil
Mohla by tam zlobit rozdílná velikost písmene s, zkuste.
this.elements[el].type.toLowerCase() == 'submit'

Další variantou je generace náhodného tokenu při zobrazení formuláře. Ten si na serveru uložíte třeba do tabulky a budete zpracovávat jen takové formuláře, které mají nepoužitý a neprošlý token. To má výhodu, že je kontrola přímo na serveru.
Kcko
Profil
Pavel Krach.:
Dej si ten JS až pod ten formulář
Str4wberry
Profil
Podle mě by bylo lepší blokovat celý onsubmit. Zablokování submit nejspíš nezabrání třeba odeslání klávesou Enter.

Tedy možná něco jako:

<script>
  var odesilaSe = false;
  function odeslatFormular() {
    if (odesilaSe) return false;
    odesilaSe = true;
  }
</script>

<form action="vysledek.php" onsubmit="return odeslatFormular()">
 <input type="text">
 <button>Odeslat</button>
</form>
Pavel Krach.
Profil *
Teď jsem si uvědomil, že se při ukládání hodnot do DB kontroly jestli se v tabulce stejný řádek už nenachází nevyhnu.

Příklad: uživatel si nechá otevřené okno na jednom počítači, přejde k druhému počítači kde zadá do formuláře hodnoty k uložení a uloží je. Vrátí se k druhému počítači kde mu zůstala stránka otevřená před původní uložení dat. Neaktualizuje stránku, bude si myslet, že to co chtěl ještě neudělal a odškrtá políčka a uloží - a stejné hodnoty jsou v DB dvakrát.

Nenapadá Vás někoho jak to řešit a neprocházet obrovské množství záznamů v DB?

PS: jedná se o kalendář, kde se ukládají akce. V jeden den a určitou hodinu může být naplánována jen ! jedna ! akce.
Str4wberry
Profil
Vždyť jsem to už psal. Použít v DB pro příslušné sloupce unikátní index. A v případě duplicity místo vložení dalšího záznamu (insert) provést jenom update.
Pavel Krach.
Profil *
Str4wberry:
Unikátní index použít nemůžu. Pro jednotlivé sloupce se různé kombinace hodnot opakovat můžou. Ale nesmí být vložen přesně ten samý řádek se všemi kombinacemi, který už v DB je.

Př.:
můžu vložit:
2014-03-12 1 2 3 4 5
2014-03-12 1 2 3 4 6
2014-03-12 1 2 3 4 7
2014-03-12 2 2 3 4 5

nemůžu vložit:
2014-03-12 1 2 3 4 5
2014-03-12 1 2 3 4 5
Kajman
Profil
Proto uděláte ten jeden unikátní index na více sloupci - tedy na jejich kombinaci.

Vaše odpověď


Prosím používejte diakritiku a interpunkci.

Ochrana proti spamu. Napište prosím číslo dvě-sta čtyřicet-sedm: