[PHP] nieuwssysteem check op veiligheid en correctheid

Pagina: 1
Acties:

Onderwerpen


Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Hallo,

Ik heb even een vraagje voor een nieuwssysteem, zoals iedereen dat zo vaak maakt, in allerlei soorten en maten. Je moet hierin berichten kunnen plaatsen, bewerken verwijderen etc. Ik heb het met php en mysql opgezet en opzich draait het allemaal goed, alleen vraag ik me af of ik nu overal aan heb gedacht m.b.t. hoe ik data opsla en met betrekking tot de veiligheid van mijn scripts. Ik zit namelijk af en toe een beetje te rommelen tussen de functies strip_tags() htmlspecialchars nl2br() en str_replace() voor bepaalde tekens die de weergave kunnen verpesten (zoals " of '). Ook zat ik eerst nog te rommelen met de slashes (add & stripslashes). Op heel veel punten zie je wel uitleg, maar nergens alles lekker bij elkaar...

Ik heb magic quotes runtime en gpc op 0 (uit dus) gezet, en doe alleen addslashes() als gegevens de database in gaan of als ze bewerkt worden en in bewerkte vorm weer opgeslagen worden in de db. Voor de rest doe ik niets met addslashes of stripslashes. Ik neem aan dat dat voldoende is, of is er iets wat ik nu over het hoofd zie?

str_replace(): ik vroeg me af welke tekens allemaal schadelijk zijn. Ik heb nu str_replace gedaan voor de tekens ' en ".
En wat ik dan doe is dmv str_replace ervoor zorgen dat bij formulieren met meer stappen, de single en double quotes (' en ") vervangen worden door html tekens ( & q u o t ; en zo (zonder de spaties, maar k weet niet hoe ik t anders moet weergeven...). (als ik dat niet doe, krijg je halve strings die opgeslagen worden in de db. Zie bijvoorbeeld het volgende:
PHP:
1
2
3
4
<?$tekst='blaatmetdubbelequoteskijkmaar:"hebt" blablabla';
//tekst komt uit de database
?>
<input type="hidden" value="<?echo $tekst;?>"> 


In dit voorbeeld wordt het woord 'hebt' niet opgeslagen. Als ik het spul dan weer in de db opsla (bij een INSERT of bij een UPDATE) doe ik het omgekeerde, zodat de " en ' wel echt worden opgeslagen in de db (en dmv addslashes komt dat goed).

Verder gebruik ik in de weergave nog str_replace voor < > als ik htmlspecialchars niet kan gebruiken. Volgens mij kun je htmlspecialchars() niet gebruiken als je iets op het scherm wilt printen dat uit een textarea komt, waarin ook newlines opgeslagen zijn. Je hebt dan nl2br() nodig om de newlines ook weer te geven, maar htmlspecialchars maakt het specialchars van waardoor de enters niet geprint worden en de tekst dus achter elkaar doorloopt...

Stel in $record['tekst'] staat de tekst uit een textarea met enters erin, dan doe je: echo nl2br($record['tekst']); voor de juiste weergave. Als ik er dan htmlspecialchars in wil verwerken, dan lukt me dat niet. Dan wordt het namelijk echo htmlspecialchars(nl2br($record['tekst'])); wat betekent dat de gemaakte enters, door htmlspecialchars niet doorkomen. Doe je de functie op een andere plek: nl2br(htmlspecialchars($record['tekst'])) dan gaat het volgens mij ook niet goed, want htmlspecialchars maakt van \n, allemaal specialchars, waardoor nl2br niets te vervangen heeft.

Dus de vraag is hoe je nu het beste info uit een textarea (uit een db) kunt weergeven. Moet je dan htmlspecialchars weglaten en het anders oplossen? En hoe precies?
Dmv strip_tags() icm str_replace voor ' " < >?
Of zijn er nog meer zaken waar ik aan moet denken?

Graag zou ik willen weten of ik overal aan heb gedacht bij het verwerken van de input die ik uit formulieren in de database stop en weer weergeef. Ik heb namelijk net een artikel gelezen op phpfreakz (hacking guide) waarin wordt gezegd dat hierin veel fouten gemaakt worden, waardoor gevoelige info gemakkelijk weergegeven kan worden. Dat is nou niet echt mijn bedoeling...

Alvast bedankt voor uw op- en aanmerkingen...

[ Voor 22% gewijzigd door Verwijderd op 23-08-2004 14:57 ]


Acties:
  • 0 Henk 'm!

  • commeric
  • Registratie: November 2002
  • Laatst online: 14-08 22:32
Als je van een tekstfield naar db gaat kan je gewoon
htmlentities();
addslashes();
doen.
En als het uit de db komt
stripslashes();
nl2br();

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Dankjewel, ga ff bij htmlentities kijken....
Stripslashes lijkt me niet nodig voor info uit de db, want er staan als 't goed is geen overbodige slashes in mijn db met mijn configuratie (magic quotes off).

Bedankt i.i.g. en ben benieuwd of er verder nog reacties zijn...

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Als ik het goed begrijp is jouw voorstel om html entities te gebruiken vóórdat de data de database ingaat...

Als ik dan tekst met aanhalingstekens wil opslaan, dan krijg ik in mijn database, allemaal dingen als & q u o t ; (zonder spaties, maar k weet niet hoe ik het anders moet weergeven...) in mijn database, terwijl ik liever gewoon de aanhalingstekens in mijn database wil hebben. Dus dit voorstel vind ik niet echt een mooie, omdat ik het voordeel ervan niet zie.

Iemand andere ideeen of meer uitleg (voor als k 't niet goed heb begrepen)?

[ Voor 36% gewijzigd door Verwijderd op 23-08-2004 14:56 ]


Acties:
  • 0 Henk 'm!

Verwijderd

Verwijderd schreef op 23 augustus 2004 @ 14:13:
Dankjewel, ga ff bij htmlentities kijken....
Stripslashes lijkt me niet nodig voor info uit de db, want er staan als 't goed is geen overbodige slashes in mijn db met mijn configuratie (magic quotes off).

Bedankt i.i.g. en ben benieuwd of er verder nog reacties zijn...
Stripslashes is wel nodig, wat voordat je data in de db zet is het zeer aan te raden er addslashes over te gooien, anders kunnen mensen je query verbouwen :). Zoek maar eens op "sql injections".

Acties:
  • 0 Henk 'm!

  • ixi
  • Registratie: December 2001
  • Laatst online: 27-08 23:59

ixi

Om gegevens in een textveld weer te geven zul je htmlentities() moeten gebruiken. Als je dit niet doet zal de browser immers bij dubbele quotes in de value de value beeindigen.

Bij het opslaan in de database is een addslashes (of mysql_escape_string) genoeg. Je kan ervoor kiezen om voordat je deze laatste stap doet ook nog een htmlentities erover te gooien, zodat de gegevens uit de database direct in HTML kunnen worden gezet. Het is echter netter (in mijn ogen) om htmlentities pas achteraf toe te passen, zodra iemand dus de pagina gaat bekijken.

Acties:
  • 0 Henk 'm!

Verwijderd

Verwijderd schreef op 23 augustus 2004 @ 14:54:
[...]

Stripslashes is wel nodig, wat voordat je data in de db zet is het zeer aan te raden er addslashes over te gooien, anders kunnen mensen je query verbouwen :). Zoek maar eens op "sql injections".
hier heb je toch niet helemaal gelijk hoor slindenau..
addslashes moet je gebruiken zodat er niet iets komt te staan als:
INSERT INTO test(veldje) VALUES('veel auto's')
maar
INSERT INTO test(veldje) VALUES('veel auto\'s')

als je dit daarna weer uit de db haalt zal het "veel auto's" zijn ipv "veel auto\'s"
stripslashes zou alleen maar voor extra lekker kunnen zorgen

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Ik weet wat sql injections zijn, en wil die graag niet.

Toch valt er niets te strippen lijkt mij.
Ik zal het uitleggen:
PHP:
1
2
3
4
5
6
7
8
9
10
11
12
13
<?
//magic quotes staan off, dat had ik in de opening gezegd...
include 'verbinding.php';//db connectie

$tekst='deze tekst " met aanhalingstekens" moet de db in';
$query="INSERT into teksten SET tekst='".addslashes($tekst)."'";
mysql_query($query);

/*
NB: in de db staan geen slashes! 
De slashes heeft sql immers nodig om de spullen goed in te kunnen voeren...
*/
?>

Dus als ik data uit de db wil printen, hoef ik geen stripslashes te gebruiken.

Mijn stelling is dus: met mijn config heb ik geen stripslashes() nodig, of snap ik het niet goed?

En als ik met mijn scripts gevoelig ben voor sql injections, kun je dan aangeven hoe?

#edit: ik zie dat mijn weerlegging ook al door anderen getypt was...

[ Voor 17% gewijzigd door Verwijderd op 23-08-2004 15:05 ]


Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Nog even duidelijk wat ik nu nog onhandig vind. Iets waarvan ik niet weet hoe ik dit nu 'waterdicht' op kan lossen (herhaling).

Het gaat me om tekst uit een textarea. Daarbij kun je niet iets doen als
PHP:
1
2
//$tekst komt uit de db
echo $tekst;

Je mist dan de newlines, en alle tekst wordt achter elkaar geplakt.

Ik wil graag htmlspecialchars of html enities gebruiken, maar ik wil NIET dat er html entities in mijn db komen. Dus geen tekens als
PHP:
1
&quot;
in mijn database...

Hoe is dan mijn weergave?

Ik kom tot zover...

PHP:
1
2
3
4
5
6
7
8
//$tekst is de tekst, opgeslagen in de db, vanuit een textarea,
//met newlines die ook weergegeven moeten worden...

$tekst= str_replace("\"",""", $tekst);
$tekst = str_replace("\'","'", $tekst);
$tekst = str_replace(">","&lsaquo;", $tekst);
$tekst = str_replace("<","&lsaquo;", $tekst);
<?echo '<p>'.strip_tags((nl2br($record['bericht'])),'<br>');?>


Mijn vraag is: is dit de enige manier (gezien de gestelde voorwaarden in deze post), of is er een andere?

En als dit de enige manier is, is deze dan goed uitgevoerd? Of kan ik beter ook een aantal andere tekens verplaatsen?

(simpelweg htmlspecialchars() lukt niet, zie eerdere posts in dit topic of overtuig me dat het wel kan :P).

[ Voor 10% gewijzigd door Verwijderd op 23-08-2004 15:29 ]


Acties:
  • 0 Henk 'm!

  • commeric
  • Registratie: November 2002
  • Laatst online: 14-08 22:32
Verwijderd schreef op 23 augustus 2004 @ 14:51:
Als ik het goed begrijp is jouw voorstel om html entities te gebruiken vóórdat de data de database ingaat...

Als ik dan tekst met aanhalingstekens wil opslaan, dan krijg ik in mijn database, allemaal dingen als & q u o t ; (zonder spaties, maar k weet niet hoe ik het anders moet weergeven...) in mijn database, terwijl ik liever gewoon de aanhalingstekens in mijn database wil hebben. Dus dit voorstel vind ik niet echt een mooie, omdat ik het voordeel ervan niet zie.

Iemand andere ideeen of meer uitleg (voor als k 't niet goed heb begrepen)?
Dan doe je de htmlentities() toch gewoon als het uit de dbase komt...I don't see the problem

Acties:
  • 0 Henk 'm!

  • crisp
  • Registratie: Februari 2000
  • Laatst online: 15:29

crisp

Devver

Pixelated

PHP:
1
echo nl2br(htmlspecialchars($tekstuitjedatabeest));

zou gewoon moeten werken. Bij het terugschrijven naar een inputveld of textarea is enkel htmlspecialchars voldoende. Bij het wegschrijven naar je databeest zou ik mysql_escape_string gebruiken.

Intentionally left blank


Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Ok, ik zie het probleem nu ook niet helemaal meer....

Ik zag het probleem aanvankelijk wel omdat ik dacht dat
PHP:
1
nl2br(htmlspecialchars($record['bericht']))

niet zou werken....

Bedankt i.i.g.

#edit: bedankt crisp... daar zat idd mijn denkfout...

[ Voor 15% gewijzigd door Verwijderd op 23-08-2004 16:32 ]


Acties:
  • 0 Henk 'm!

  • PrisonerOfPain
  • Registratie: Januari 2003
  • Laatst online: 26-05 17:08
crisp schreef op 23 augustus 2004 @ 16:29:
Bij het wegschrijven naar je databeest zou ik mysql_escape_string gebruiken.
En mocht je vreemde talen willen gaan ondersteunen, mysql_real_escape_string ;)

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Hey, dan heb ik addslashes en stripslashes nooit meer nodig, begrijp ik?

Magic quotes staan uit, en voor invoer naar de database gebruik ik mysql_(real)_escape_string();
Pagina: 1