[PHP/MySQL] Select geeft geen slashes ondanks addslashes

Pagina: 1
Acties:
  • 276 views sinds 30-01-2008
  • Reageer

Onderwerpen


Acties:
  • 0 Henk 'm!

  • Speedener
  • Registratie: September 2000
  • Laatst online: 18-09 12:54
Hoi luitjes,

Ik ben al een tijdje aant stoeien met het volgende. Tijdens het maken van een software project waar ik mee bezig ben, kwam ik achter het volgende: als ik een variabele bewerkte met addslashes en die via een mysql_query in de database duwde, dat als ik het daarna opvroeg dat de slashes niet meer in de regel staan.

Nu ben ik al een uur aan het testen met een testscriptje:

PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
<?php
mysql_connect('localhost', 'xxx', 'xxx');
mysql_select_db('test');

$string_een  = "Dit is een teststring, met vreemde tekens ' @ < \" \ €";
$string_twee = addslashes($string_een);

$query_insert = "INSERT INTO test (test) VALUES ('{$string_twee}');";
mysql_query($query_insert);

$result      = mysql_query('SELECT test FROM test ORDER BY id DESC LIMIT 0,1');
$string_drie = mysql_result($result, 0, 'test');

echo 'Orgineel: ' . $string_een  . '<br />';
echo 'Met slashes: ' . $string_twee . '<br />';
echo 'DB Select: ' . $string_drie . '<br />';
echo 'Insert Query: '. $query_insert;
?>


Dit script retourneert dit:
Orgineel: Dit is een teststring, met vreemde tekens ' @ < " \ €
Met slashes: Dit is een teststring, met vreemde tekens \' @ < \" \\ €
DB Select: Dit is een teststring, met vreemde tekens ' @ < " \ €
Insert Query: INSERT INTO test (test) VALUES ("Dit is een teststring, met vreemde tekens \' @ < \" \\ €");
Waarom is het resultaat van $string_drie (c.q: DB Select) niet hetzelfde als $string_twee?

Ik heb gekeken naar magic quotes, maar dat werkt, als ik goed gelezen heb, alleen bij $_POST en $_GET. Ik ben al aardig wat tijd bezig met php en mysql, maar hier kom ik gewoon niet uit.
Wat mis ik?

Misschien nog interessant, op mn dev servertje draait: Windows Server 2003, Apache, PHP 4.4, MySQL 4 (I know, het is beetje oud maar het werkt prima voor het meeste wat ik doe).

LG Therma V Split WP: HU143MA.U33-HN1636M NK5


Acties:
  • 0 Henk 'm!

  • GlowMouse
  • Registratie: November 2002
  • Niet online
Probeer string_een eens te inserten zonder addslashes: dat gaat fout.
Addslashes is een nutteloze functie, en ik snap niet waarom je dit graag op een string wilt doen. Voordat je een string letterlijk in een query wilt stoppen, pas je er mysql_real_escape_string op toe, altijd. Wil je de geaddslashte string dus letterlijk in de database hebben, pas je er eerst mysql_real_escape_string op toe.

Acties:
  • 0 Henk 'm!

  • Speedener
  • Registratie: September 2000
  • Laatst online: 18-09 12:54
@ GM:
Of ik nou addslashes of mysql_real_escape_string gebruik maakt imho niet zoveel uit, tis een test. Ik wil weten waarom, als ik een text met slashes in de database stop, het zonder slashes terugkrijg bij een select.

Eventjes getest, met mysql_real_escape_string krijg ik ook geen slashes terug. De output van het scriptje is exact hetzelfde als in openingspost.

LG Therma V Split WP: HU143MA.U33-HN1636M NK5


Acties:
  • 0 Henk 'm!

  • GlowMouse
  • Registratie: November 2002
  • Niet online
Speedener schreef op dinsdag 20 februari 2007 @ 17:37:
@ GM:
Of ik nou addslashes of mysql_real_escape_string gebruik maakt imho niet zoveel uit, tis een test. Ik wil weten waarom, als ik een text met slashes in de database stop, het zonder slashes terugkrijg bij een select.

Eventjes getest, met mysql_real_escape_string krijg ik ook geen slashes terug. De output van het scriptje is exact hetzelfde als in openingspost.
Dat laatste is niet waar. Vervang jij regel 8 hierdoor:
PHP:
1
$query_insert = "INSERT INTO test (test) VALUES ('" . mysql_real_escape_string($string_twee) . "');";

dan heb je precies wat je wilt. Hier was je vanzelf ook achtergekomen wanneer je $string_een in de database had geprobeerd te stoppen (probeer het alsnog maar en zoek uit waarom het fout gaat).
Het is niet óf addslashes óf mysql_real_escape_string, het is altijd die laatste wanneer je een string in de database wilt hebben. Dus ook een string waar je eerst addslashes mee deed. Addslashes dient trouwens echt geen enkel nut.

Acties:
  • 0 Henk 'm!

  • Shadowman
  • Registratie: Januari 2002
  • Niet online
addslashes is escaping, geld dus hetzelfde voor als hiervoor:
echo 'dit is \'php\'';
of
echo "dit is \"php\"";

Als je dit uitvoert zie je de slashes ook niet meer, zelfde reden (de database doet in feite stripslashes).

[ Voor 6% gewijzigd door Shadowman op 20-02-2007 17:44 ]


Acties:
  • 0 Henk 'm!

  • CodeCaster
  • Registratie: Juni 2003
  • Niet online

CodeCaster

Can I get uhm...

De escape-characters worden er bij het uitvoeren een query afgesloopt, het is alleen zodat de tekst letterlijk in de database komt zoals je wil.

Als je een enkele quote insert (" ' ") dus, gaat het mis, want "insert into test (test) values (' ' ') " geeft een syntaxisfout omdat er drie enkele quotes in staan. Daarom moet je hem escapen, (" \' "), waardoor hij correct door MySQL gelezen kan worden.

[ Voor 4% gewijzigd door CodeCaster op 20-02-2007 17:51 ]

https://oneerlijkewoz.nl
Op papier is hij aan het tekenen, maar in de praktijk...


Acties:
  • 0 Henk 'm!

  • Speedener
  • Registratie: September 2000
  • Laatst online: 18-09 12:54
Bedankt voor jullie reacties!
Ik snap nu wat ik verkeerd deed/dacht.

Dan heb ik hierover nog één vraag. Is het aan te raden zowel addslashes als mysql_real_escape_string of is enkel mysql_real_escape_string (meer dan) genoeg?

Edit: ik zie dat hier GM al antwoord op gegeven heeft.

[ Voor 11% gewijzigd door Speedener op 20-02-2007 17:55 ]

LG Therma V Split WP: HU143MA.U33-HN1636M NK5


Acties:
  • 0 Henk 'm!

  • ACM
  • Registratie: Januari 2000
  • Niet online

ACM

Software Architect

Werkt hier

(jarig!)
Voor de zekerheid nog een wat vollediger antwoord. Zoals je ziet wordt je insert-query uiteindelijk:
INSERT INTO test (test) VALUES ("Dit is een teststring, met vreemde tekens \' @ < \" \\ €");

(wat overigens heel bijzonder is want je omsluit de string in je code met ' ipv " ... )

Bij het parsen van de query in mysql worden o.a. string-elementen opgesteld aan de hand van je query. En daarbij wordt rekening gehouden met het feit dat je mogelijk ook een ' wilt gebruiken als karakter binnen een string. Daarvoor moet je dus escaping gebruiken (net zo als je \" moet schrijven om een " tussen twee "" te krijgen in php), en binnen mysql worden karakters ook met een \ escaped.
Je toegevoegde \-es worden dus gebruikt als escape-character bij het parsen van de query in mysql. En om die reden wordt de voor mysql interne string-representatie dus voordat de data uberhaupt intern verwerkt wordt al dit:
Dit is een teststring, met vreemde tekens ' @ < " \ €

Dat is dus zo binnen gekomen nadat jouw query-string is omgezet in een daadwerkelijk uitvoerbare representatie. Bij het fysiek opslaan is dus niet eens meer bekend dat er ooit extra \ in hebben gezeten.

Een stuk tekst hoor je overigens altijd door mysql_escape_string te halen (nouja tegenwoordig de nog beroerder genoemde mysql_real_escape_string :X ), die anders werkt dan addslashes. De laatste is eigenlijk een compleet waardeloze functie, want vziw is er geen enkele toepassing die alle slashes vereist die het toevoegt. Voor correct invoeren van de data moet je overigens alleen de functie mysql_real_escape_string gebruiken, zeker geen mix van net niet overlappende functies. :)

Op het moment dat je die data dus opvraagt is er al lang niet meer bekend wat dat die escape-slashes er ooit voor gestaan hebben en dus kunnen ze niet eens getoond worden.

Desalniettemin, als je die extra slashes wilt hebben moet je dus eerst je string door addslashes halen om daadwerkelijk de extra slashes te krijgen en daarna nog een keer door mysql_real_escape_string (of desnoods addslashes, maar die is dus niet correct) om de string zodanig aan mysql te kunnen voeren dat ie weet dat de extra slashes niet als escape-character zijn bedoeld, maar domweg als slashs.

De toegevoegde waarde ervan, waarom je een string na addslashes zou willen opslaan ontgaat me overigens. Zoals gezegd ken ik zelf iig geen toepassing die alle toegevoegde slashes vereist en in veel gevallen is het daardoor juist irritant dat er net te veel slashes worden toegevoegd of juist sommige karakters niet van een extra slash worden voorzien (zoals de / die in javascript escaped moet worden).

Acties:
  • 0 Henk 'm!

Verwijderd

als het je vooral om de weergave van quoutes gaat kun je mischien ook gebruik maken van htmlentities en evt html_entity_decode. dan hoef je je helemaal niet meer druk te maken over vreemde tekens in je string omdat deze zijn vervangen door hun html variant. dit ruimt ook meteen euro tekens enzo op.

zie ook:
http://nl2.php.net/manual/en/function.htmlentities.php
http://nl2.php.net/manual/en/function.html-entity-decode.php

daarnaast zou ik addslashes niet gaan mixen met mysql_escape_string of mysql_real_escape_string.

[ Voor 13% gewijzigd door Verwijderd op 21-02-2007 06:49 ]

Pagina: 1