dibi escapovaní konce řádku

Upozornění: Tohle vlákno je hodně staré a informace nemusí být platné pro současné Nette.
zatomik
Člen | 19
+
0
-

Mám takový problém s dibi. Když nahrávám data do databáze, používám následující příkaz:

$result = dibi::query(' UPDATE '.$this->catName.' SET ',
                                $this->data,
                                'WHERE `id`=%i',
                                $this->data['id']);

Některá data, která ukládám beru z html tagu textarea, kde je normálně možné vložit konce řádků a ty bych také chtěl uložit do databáze, aby se při zpětném načtení vše odřádkovalo tak jak bylo. Dibi mi ovšem všechny \r\n změní na \\r\\n, takže se v textboxu zobrazí natvrdo \\r\\n místo toho, aby se text odřádkoval.

Vstup si od uživatele kontroluji sám, takže bych uvítal, jestli jde v dibi celé tyhle ochrany vypnout.

Filip Procházka
Moderator | 4668
+
0
-
  1. dibi má vlastní fórum
  2. vypnout to nejde a ani se o to nesnaž!

Tvým úkolem je předat do dibi surová data a on je uloží do databáze. Z databáze je pak přečteš a ošetřuješ až při vypisování v šabloně!

zatomik
Člen | 19
+
0
-

HosipLan napsal(a):

  1. dibi má vlastní fórum
  2. vypnout to nejde a ani se o to nesnaž!

Tvým úkolem je předat do dibi surová data a on je uloží do databáze. Z databáze je pak přečteš a ošetřuješ až při vypisování v šabloně!

  1. Pardon, za to se omlouvám

To pak ale musím všude v šabloně nahradit \\r\\n za \r\n? Je zajímavé, že než jsem používal dibi, data jsem ošetřoval pomocí fce mysql_real_escape_string, která má v manuálu napsáno, že také ošetřuje \r\n, ale ten problém jsem neměl:)
Spouštět na každé pole z db nahrazování \\r\\n za \r\n, mi přijde dost nepraktické, to snad abych si do db uložil dvě verze dat, jednou s řádkováním pro editaci a jednou ho úplně smazat pro zobrazování.

Filip Procházka
Moderator | 4668
+
0
-

Je vidět, že máš základní neznalosti. Takže mi dovolit ti to vysvětlit.

Dibi nevytváří ze znaků pro zalomení řádků \\r\\n. To je chyba toho, co do něj dáváš.

Buďto ten vstup se snažíš ošetřovat, pomocí mysql_real_escape_string, addslashes, nebo automaticky ti to „ničí“ php, tím ti z řetězce vznikne ošetřený řetězec.

Není důvod, aby dibi jakkoliv kontrolovalo, jestli jsi to ošetřil, protože to ošetřuje samo. Tobě má ušetřit tu práci s tím ošetřením a zabránit SQL injekci a skládat validní SQL dotazy. Tím že ty data ošetříš před tím, než to do něj dáš, je poškodíš a dibi je tudíž neumí správně uložit.

Ty data se totiž ošetřují z jediného důvodu, aby se dala zapsat do SQL. Neošetřený vstup udělá tento dotaz

$promenna = "'\n nějaká data <tag>";
// zde si prosím uvědom, že v normálních závorkách,
// pokud napíšeš lomítko před písmeno n, vznikne jeden znak zalomení řádku

mysql_query("INSERT INTO tabulka (sloupec) VALUES ('" . $promenna . "') ");
INSERT INTO tabulka (sloupec) VALUES (''\n nějaká data <tag>')

Což je určitě špatně, že. Když to proženeš přes mysql_real_escape_string (což je funkce, která escapuje speciálně pro databázi mysql)

$promenna = "'\n nějaká data <tag>";
mysql_query("INSERT INTO tabulka (sloupec) VALUES ('" . mysql_real_escape_string($promenna) . "') ");
INSERT INTO tabulka (sloupec) VALUES ('\'\n nějaká data <tag>')

Což je naprosto správně. A teď jak by jsi to napsal v dibi

$promenna = "'\n nějaká data <tag>";
dibi::insert('tabulka', array('sloupec' => $promenna)->execute();
INSERT INTO tabulka (sloupec) VALUES ('\'\n nějaká data <tag>')

Takže dibi ti pomáhá jednoduše skládat SQL a ošetřovat data. Ty je ošetřovat nemáš. Od toho je tu dibi. A ty děláš toto

$promenna = mysql_real_escape_string("'\n nějaká data <tag>");
dibi::insert('tabulka', array('sloupec' => $promenna)->execute();
INSERT INTO tabulka (sloupec) VALUES ('\\\'\\n nějaká data <tag>')

To je tvůj základní problém.

Taková data, když je pak čteš z databáze, znovu máš ošetřovat při vypisování, aby jsi zabránil XSS. O to se zase stará latte, nebo funkce htmlspecialchars.

Takže správný worflow je:

  • Přijmeš data, nesmíš mít nastaveno magic_quotes_gpc
  • zpracuješ
  • předáš dibi data, která neošetřuješ, protože je ošetřuje dibi
    • dibi je ošetří a vloží do databáze
  • data čteš přes dibi
    • dibi ti vrátí přesně to, co jsi do něj vložil
  • data vypíšeš v šabloně a ošetříš proti XSS (nebo to za tebe udělá latte)

Editoval HosipLan (5. 10. 2011 9:19)

zatomik
Člen | 19
+
0
-

Super, díky moc. Tenhle problém s dvojitým ošetřením mě nenapadl, až se za to skoro stydím:) Teď už je mi to zcela jasné, takže ještě jednou díky za vysvětlení.

Vždycky nás ve škole učili hlavně ošetřovat vstup, až jsem to trochu přehnal.

Editoval zatomik (5. 10. 2011 10:39)