vícenásobné uložení do databáze
- Bertram
- Člen | 75
Zdravíčko,neznáte někdo způsob zamezení vícenásobného vložení
údajů do databáze?
Pokud totiž omylem a nebo úmyslně poklepu odesílací tlačítko několikrát
po sobě,
tak se záznam zduplikuje,nebo se vyhodí vyjímka jeli v databázi na
nějakém slopci unikátní klíč.
O nutnosti přesměrování vím a doufám,že jsem to napsal správně.
Posuďte mám to takto:
// Mám pouze jedno odesílací tlačítko
// V dokumentaci v tomto případě doporučená volba
$form->addSubmit('odesli','ulož');
$form->onSubmit[] = callback($this,'formSubmitted');
// Zde jeho zpracování
function formSubmitted ($form)
{
$trafo = ($form->values);
$this->model->vlozit($trafo);
$this->flashMessage('Transformátor uložen.');
$this->redirect('Transformatory:vypis');
}
Je mi také jasné,že budu muset doplnit validaci tak či tak,jen bych
potřeboval trochu nakopnout jak to s tou vlastní validací vlastně je.
Dohledal jsem si tyto varianty,jen v nich trochu tápu.
//varianta 1
//Tady to chápu tak,že si musím vytvořit vlastní třidu s metodou myValidátor
//Pokud mi vrátí true tak to neprojde
//Otázka zní: Kde má být tato třída definována?
$form = new Form();
$form->addText('name', 'Text:', 10)
->addRule('MyClass::myValidator', 'Value %d is not allowed!', 11)
//varianta 2
//U této variandy jsem se dočetl,že se jedná o anonymní funkci
//První $control je parametr předávaný funkci
//A ten druhý je už jenom operace s jeho hodnotou uvnitř funkce
// A nebo jsu vedle jak ta jedle?
$form->addText('oddNumber', 'Liché číslo')
->addRule($form::INTEGER)
->addRule(function (Nette\Forms\IFormControl $control) {
return (bool) ($control->getValue() % 2);
}, 'Musíte uvést liché číslo');
//varianta 3
//nemohl by mi někdo po lopatě vysvětlit co to ten callback je?
//opravte mě:
// 'MyApplication\Models\Users' - je cesta ke třídě User v Modelu
// 'isUsernameAvailable' - je metoda v této třídě dotazující se databáze
$form->addText('username', 'Uživatelské jméno')
->addRule($form::FILLED, 'Vyplňte své uživatelské jméno')
->addRule(callback('MyApplication\Models\Users', 'isUsernameAvailable'),
'Toto uživatelské jméno je již registrováno');
- dakota
- Člen | 148
https://forum.nette.org/…iewtopic.php?…
Problém robi hlavne prehliadač Opera. Nešlo by ochranu proti viacnásobnému odoslaniu formulára implementovať priamo do Nette?
- westrem
- Člen | 398
Co sa tyka viacnasobneho odoslania, tak kolega uz odkazal na spravny thread, ja by som len pripomenul, ze dalsia moznost je zobrazit overlay effect s loading image, ktory zamedzi dalsim kliknutiam.
V pripade, ze sa naozaj nieco seklo, ide vecsinou takyto overlay vypnut pomocou esc.
Ku callbacku:
- callback je obecne pseudotyp v PHP a vetsinou ide o nejaku funkciu/metodu, ktoru je mozne zavolat
- to co mas sam napisane v kode tzn.
callback( .. )
je interna funkcia nette, ktora ujednocuje zapis callbacku, kedze existuju 3 sposoby ako ho pisat
K variantam:
V podstate to co si popisal, su totozne moznosti, len zakazdym predavas
callback inak
- odkazujes sa na triedu MyClass a jej staticku metodu myValidator.
Umiestnenie triedy je lubovolne na tebe. Nette robot loader ju dohlada (ak ho
mas spravne nastaveny). Dolezite je aby existovala a aby sa dala zavolat. Tiez
treba mat na zreteli, ze ako argument sa jej predava
IFormComtrol
a nie samotna hodnota. - Toto je closure, resp. anonymna funkcia, funguje to od PHP 5.3 takze sa
uisti, ze ho mas na hostingu. Tam ako pises, nie su dva parametry ale len jeden
a to ten
IFormControl
- Zase raz len iny zapis callbacku, principialne to iste.
MyApplication\Models\Users
vsak nie je cesta ale nazov triedy spolu s namespaces, v tomto pripade to ani ne je full qualified, pretoze je to odkazovane relativne.
V principe teda mozes mat ako validator hocico co sa da zavolat – staticku metodu, metodu nejakeho objektu, funkciu alebo anonymnu funkciu (closure).
Dufam, ze je to uz jasnejsie.
- Bertram
- Člen | 75
Díky ka radu,ale ještě bych tě poprosil mě trochu nakopnout.
Jak funkuje ten callback jen tuším,protože bohužel neumím anglicky a
překladač mi moc nepomohl.
Když vezmu tu první variantu,tak nemůžu přijít na to jakým způsobem mám
ten parametr získat a předat.
Funkce která by tento parametr mohla přijímat by mohla vypadat např takto:
public static function overPolozku($ozn)
{
$radek = dibi::fetch('SELECT [id] FROM [trafa] WHERE [ozn]=%s', $ozn);
return (bool) $radek;
}
Nemohl by jsi mi prosím napsat,jak by měla být ta validace formulována?
Jak už jsem psal,nevím,kde ten parametr napsat a jak ho získat.
zkoušel jsem různé varianty na různých místech,ale bez úspěchu.
edit:Zkrátka potřebuji ověřit,zda daný název,který se zadá ve formuláři už není uložen v databázi.
Editoval Bertram (20. 10. 2010 15:28)
- westrem
- Člen | 398
public static function overPolozku(IFormControl $ozn)
{
return (bool) dibi::fetchSingle('SELECT COUNT(*) FROM [trafa] WHERE [ozn]=%s', $ozn->getValue());
}
Ako som uz spominal a upozornoval, do callbacku sa predava
IFormControl
nie hodnota sama, preto musis na ziskanie hodnoty
volat getValue()
.
- Bertram
- Člen | 75
Dík za pomoc,už jsem to rozchodil.
Jenom jsem tam musel vyhodit to IFormControl
Jinak mám totiž tuto chybu:
Argument 1 passed to Pokus::overPolozku() must be an instance of IFormControl, instance of Nette\Forms\TextInput given
Což mě právě pořád dokola vrací k otázce validačního pravidla a
k tomu jak zde docílím toho,
že budu předávat argument IFormControl.
ověřovací metoda:
public static function overPolozku($control)
{
return !(bool) dibi::fetchSingle('SELECT COUNT(*) FROM [trafa] WHERE [ozn]=%s', $control->getvalue());
}
validační pravidlo:
$form->addText('ozn','Název:')
->addRule(Form::FILLED, 'Zadejte název!')
->addRule('Pokus::overPolozku','Tento transformátor je již evidován');
Nemá tedy tady být někde uvedeno jaký argument předávám do ověřovací metody?
- Bertram
- Člen | 75
Tady se není zač omlouvat,moc jsi mi pomohl a navíc jsem to měl asi
uvést.
Moje situace se má tak,že se neučím jen Nette ale PHP vůbec.
Moje zdroje jsou pouze knihy a internet a to ještě pouze česky psané.
A pochopit o co vlastně jde,bez toho aby mi to někdo vysvětlil bývá
někdy pěkně velký ořech
a tak si to čtu většinou pořád dokola a doufám že mi to docvakne.
Potřebuji si nějakým způsobem přivlastnit správné programátorské
návyky,tak to zkouším s Nette,
což neznamená,že ovládám PHP.
- westrem
- Člen | 398
No som rad, ze som pomohol :)
Kazdopadne, ak sa ucis aj PHP, Nette moze byt zo zaciatku tazky oriesok v niektorych pripadoch, nie preto, ze by bolo zle napisane, ale skor preto, ze uz pouziva hodne pokrocilych technik a sam som pri citani zdrojakov musel niektore pasaze citat opakovane aby som stravil ich myslienku.
Je to vsak zaroven dobra prirucka ako sa naucit pisat veci cistejsie a lepsie, uz len preto, ze sa na vyvoji podiela aj hlas komunity a za nou je David, ktory v tomto sakra vie co robi.
Kedze vravis, ze ako zdroj mas najme ceske veci, mozno by som ti odporucil serial na linuxsofte – je sice uz starsieho data ale co som kukal prebera sa tam uz PHP 5ka a veci ako Namespaces a closures su aj tak novinky v PHP 5.3, pre teba je asi dolezitejsie plne podchytit PHP a potom zvysne novinky.