limpiar - PHP MySQLI Prevención de Inyección SQL
sql injection ejemplos reales (2)
Esta pregunta ya tiene una respuesta aquí:
- ¿Cómo puedo prevenir la inyección SQL en PHP? 28 respuestas
Construí un sitio web que se lanzará pronto y solo tengo un par de preguntas sobre la prevención de la inyección SQL, entiendo cómo usar mysqli_real_escape_string
pero me pregunto si tengo que usar eso en todas las variables que mysqli_real_escape_string
para mi declaración SQL y ¿tengo que usarla cuando estoy haciendo sentencias select también o solo en Insertar actualización y eliminar? Además, ¿qué otra seguridad me recomendaría implementar antes de poner el sitio en funcionamiento, gracias de antemano por cualquier ayuda?
Cualquier consulta puede ser inyectada ya sea de lectura o escritura, persistente o transitoria. Las inyecciones se pueden realizar al finalizar una consulta y ejecutar una consulta separada (posible con mysqli
), lo que hace que la consulta deseada sea irrelevante.
Cualquier entrada a una consulta desde una fuente externa, ya sea desde usuarios o incluso interna, debe considerarse un argumento para la consulta y un parámetro en el contexto de la consulta. Cualquier parámetro en una consulta necesita ser parametrizado. Esto lleva a una consulta parametrizada correctamente de la que puede crear una instrucción preparada y ejecutarla con argumentos. Por ejemplo:
SELECT col1 FROM t1 WHERE col2 = ?
?
es un marcador de posición para un parámetro. Usando mysqli
, puede crear una declaración preparada usando prepare
, enlazar una variable (argumento) a un parámetro usando bind_param
, y ejecutar la consulta con execute
. No tiene que desinfectar el argumento en absoluto (de hecho, es perjudicial hacerlo). mysqli
hace eso por ti. El proceso completo sería:
$stmt = mysqli->prepare("SELECT col1 FROM t1 WHERE col2 = ?");
$stmt->bind_param("s", $col2_arg);
$stmt->execute();
También hay una distinción importante entre consulta parametrizada y declaración preparada . Esta declaración, mientras está preparada, no está parametrizada y, por lo tanto, es vulnerable a la inyección:
$stmt = mysqli->prepare("INSERT INTO t1 VALUES ($_POST[user_input])");
Para resumir:
- Todas las consultas deben estar parametrizadas correctamente (a menos que no tengan parámetros)
- Todos los argumentos a una consulta deben ser tratados como hostiles como sea posible sin importar su origen
Se cerrará en segundos, pero solo para aclarar las cosas
Entiendo cómo usar mysqli_real_escape_string
Me temo que no lo eres.
si tengo que usar eso en todas las variables que obtengo para mi declaración de SQL
definitivamente no.
esta función tiene que ser utilizada para formatear cadenas de SQL solamente
¿Tengo que usarlo cuando estoy haciendo declaraciones selectas también o solo en Insertar actualización y eliminar?
CUALQUIER declaración SQL. Pero, de nuevo, no "usando mysqli_real_escape_string" sino formateando sus literales completa y apropiadamente
Además, ¿qué otra seguridad recomendaría usted?
con respecto a la seguridad de SQL, debe formatear correctamente no solo cadenas, sino literales de cualquier tipo. Y cada uno requiere un conjunto distinto de reglas de formato