2013-10-18 7 views
6

Ich habe ein Feld in meinem Registrierungsformular, das zum Beispiel ein name Feld enthält, es wird in der Datenbank in einem Feld namens user_name varchar(20) gespeichert werden. es ist klar, dass ich die Benutzereingabe bestätigen sollte , wenn ich dieses Feld frist unten mit Code validieren:was sollte man zuerst machen? Desinfektion oder Validierung

<?php 
if(emptiy($_pos['name']) || strlen($_post['name'])>20) 
//send an not valid input error 
else{ 
$name=htmlspcialchars($_post['name']); 
//check for sql injection; 
//insert name into database;} 
?> 

, wenn ein Benutzer einen Namen wie <i> some one </i> die Stringlänge 17 einfügen, so dass der sonst Teil wird performe und Name wird die Länge ist 28, die einen Fehler beim Einfügen in db.In dieser Zeit, wenn ich einen Fehler an den Benutzer senden, dass seine/ihre Eingabe ist zu longe wird er verwirrt. was soll ich machen? Was ist der beste Ansatz?

+5

Sie sollten niemals Daten verschlüsseln, bevor Sie sie speichern. Speichere es raw (benutze das richtige Escapen wie mysqli_real_escape_string oder ähnliches) und kodiere es, bevor du es ausgibst. Dies liegt daran, dass es eine andere Kodierung benötigt, wenn Sie es als HTML oder JSON oder irgendetwas anderes ausgeben. –

+3

Die beste Methode, um sql-injection zu stoppen, ist die Verwendung von mysqli oder PDO prepared statement, um Daten in die Datenbank einzufügen. @ [Niet the Dark Absol] (http://stackoverflow.com/users/507674/niet-the-dark-absol) ist Richtig, aber die Funktion mysqli_real_escape_string() ist veraltet. – nurakantech

+0

Ich werde nie Funktionen wie 'mysqli_real escape_string()' für sesurity Gründe verwenden, im Verwenden von PDO ist es sicherer. – naazanin

Antwort

6

In der Regel sollte man zuerst reinigen - "für Ihren Schutz und ihre." Dies schließt das Entfernen von ungültigen Zeichen ein (Zeichencodierung natürlich empfindlich). Wenn ein Feld nur Zeichen und Leerzeichen enthalten soll, dann entferne alles, was nicht das erste ist.

Danach validieren Sie die Ergebnisse - ist der Name bereits verwendet (für eindeutige Felder), ist es die richtige Größe, ist es nicht leer?

Der Grund, den Sie geben, ist genau der richtige - um die Benutzererfahrung zu maximieren. Verwechsle den Benutzer nicht, wenn du es vermeiden kannst. Dies hilft beim Schutz vor dumb copy & einfügen Verhalten, aber Sie müssen vorsichtig sein - wenn ich möchte meinen Namen als "Ke $ h @" aufgezeichnet, kann ich oder nicht ok mit der Änderung zu "Keh".

Zweitens, es ist auch Bugs zu verhindern.

Was passiert, wenn Sie Benutzernamen erstellen möchten, die keine Sonderzeichen zulassen? Wenn ich "Brian" eingebe, und dein System es als den uns bereits verwendeten Namen zurückweist, dann reiche ich "Brian $" ein? Zuerst validierst du es, und es wird nicht benutzt, dann entziehst du Sonderzeichen und du bleibst bei "Brian". Uh oh - jetzt müssen Sie entweder AGAIN validieren, oder Sie erhalten einen merkwürdigen Fehler, dass entweder die Kontoerstellung fehlgeschlagen ist (wenn Ihre Datenbank zum Beispiel eindeutige Benutzernamen erfordert), oder schlimmer noch, es wird erfolgreich sein und überschreiben/Korruption tritt für Benutzer Benutzerkonten auf.

Ein anderes Beispiel sind minimale Feldlängen: Wenn Sie einen Namen benötigen mindestens 3 Buchstaben lang sein und nur Buchstaben akzeptieren, und ich gebe "Nein" ein, würden Sie es ablehnen; aber wenn ich "no @ # $%" eintrage, würde man sagen, dass es gültig war (lange genug), es sterilisieren, und jetzt ist es nicht mehr gültig, etc.

Der einfache Weg, dies zu vermeiden, ist zuerst zu sanieren und dann müssen Sie nicht zweimal über die Validierung nachdenken.

Allerdings hatte Niet Recht, Daten vor der Speicherung nicht zu verschlüsseln; Im Allgemeinen ist es viel einfacher, die Ausgabe in HTML so einzurichten, als wäre sie codiert, wenn es angebracht ist, dann sollte man daran denken, sie zu dekodieren, wenn Sie nur den einfachen Text (zum Eingeben in Textfelder, JSON-Zeichenfolgen usw.) wollen. Die meisten Testfälle, die Sie verwenden, enthalten keine Daten mit HTML-Entities, so dass es leicht ist, dumme Bugs einzuführen, die nicht leicht zu finden sind.

Das große Problem ist, dass wenn ein solcher Fehler eingeführt wird, kann es schnell zu Datenbeschädigung führen, die nicht leicht zu lösen ist. Beispiel: Sie haben einfachen Text, geben ihn falsch als HTML-Entitäten in ein Textfeld aus, das Formular wird zurückgesendet und Sie codieren es neu ... jedes Mal, wenn es geöffnet/erneut gesendet wird, wird es neu codiert. Bei einer stark frequentierten Site/Formular könnten Sie Tausende von unterschiedlich kodierten Einträgen erhalten, ohne dass Sie klar bestimmen könnten, was und was nicht HTML-kodiert sein sollte.

Der Schutz vor der Injektion ist gut, aber HTML-Codierung ist nicht dafür ausgelegt (und muss nicht verlässlich sein), dies zu tun.

+0

ok, angenommen, dass Sie Brian $ eingeweiht haben, zuerst Saniteze das und das Ergebnis wird Brian sein, und validieren Sie das und es ist einzigartig, ok youre wissen registriert und Sie möchten sich einloggen, Sie geben ein Brian und nochmal in Log-in-Form soll ich den Input sanieren? Also, yeah, ich sollte Hallo sagen Brian, und Sie würden verwirrt sein, weil Sie Brian eingegeben haben $ – naazanin

+1

Sie sollten den Benutzer wissen lassen, dass Sie den Eingang sterilisieren mussten - ich würde sogar so weit gehen, in einer Situation wie dieser zu empfehlen Sie geben dem Benutzer einen Fehler, wenn er eingibt, dass er ungültig ist. –

+0

@naazanin Ich würde mit gdscei einverstanden sein, obwohl ich im Allgemeinen solche Nettigkeiten zu vor-posten clientseitige Formularvalidierung speichern. Da bin ich vorsichtiger, den Benutzer über ungültige Ausgaben zu informieren, wobei ich auf der Serverseite eher eines von zwei Modellen wählen würde: 1) es funktionieren lassen und den Benutzer nicht belästigen, wenn es nicht nötig ist wissen oder 2) ungültige Eingaben ablehnen und den Benutzer herausfinden lassen, was zu tun ist. Dies hängt von Ihrem Anwendungsfall ab und ich kann keinen globalen Vorschlag anbieten. Je internationaler Ihre App ist, desto vorsichtiger müssen Sie sein, wenn Sie potenziell gültige Zeichen verbieten. – BrianHall

2

Nein, Sie sollten zuerst validieren. Sanitizing wird durchgeführt, um die Datenspeicherstufe zu handhaben, die der letzte Schritt ist. Es macht keinen Sinn, auf eine Datenspeicherebene zuzugehen, wenn die Geschäftsregeln die Validierungsphase nicht bestehen. Wenn Sie eine Nummer benötigen und Ihnen eine Zeichenfolge zugewiesen wird, ist das ein Fehler, sodass Sie sie zurück an das Formular senden. Sanitizing mit Ausnahme von stripseslashes, falls erforderlich (nicht erforderlich ab 5.4), ist nicht notwendig, wenn Sie SQL mit vorbereiteten Anweisungen verwenden und stattdessen die Eingabe korrumpieren würden.