Dicas quando o assunto é SQL e PHP.
<?php /* sanitizar: Esta função realiza : - remove espaços no começo e fim do parâmetro - remove os caracteres *?--%'&#@"/,; - remoção de acentos, torna tudo minúsculo, preserva apenas: letras, números, .:-_ */ function sanitizar($parametro=false) { $parametro=stripslashes(trim($parametro)); $parametro=str_replace(array("*","?", "--", "%", "'", "&", "#", "@", "\"", "/", ",", ";"), "", $parametro); $parametro=strtolower(preg_replace('/[^[:alnum:]|_|.|:|-]/', " ",strtr($parametro, "áàãâéêíóôõúüçÁÀÃÂÉÊÍÓÔÕÚÜÇ-:","aaaaeeiooouucAAAAEEIOOOUUC-:"))); return $parametro; } /* anti_sql: Esta função realiza : - remove caracteres e palavras reservadas de SQL. Obs: esta idéia foi retirada de um fórum de discussão. */ function anti_sql($varivel) { $varivel = preg_replace("/(from|union select|select|insert|delete| where|drop table|show tables|#|\*|--|;|=|@|\\\\)/i","",$varivel); $varivel = trim($varivel); return $varivel; } /* Para evitar XSS, ao exibir valores recuperados na tela, utilize a função nativa htmlentities exemplo: */ $str="não encontrei o valor"; echo $str."<br />"; $str="não encontrei o valor <img src='uma_imagem_nao autorizada.png' />"; echo $str."<br />"; echo htmlentities($str)."<br />"; /* Inserir valor de campos numericos não tratados sempre oferecem risco de SQL Injection devido a não utilização da aspa na composição da query ex: SELECT titulo,mensagem FROM noticia WHERE noticia_id=234; já em campos text/string a SQL Injection torna-se dificultada pela existência da aspa ex: SELECT titulo,mensagem FROM noticia WHERE noticia_titulo='Meu titulo'; porém pode ser contornada, se o interpretador não estiver habilitado para escapar aspas logo seguem algumas forma de evitar a SQL Injection: */ //campo numérico: /* ---- ERRADO: ---- */ $numero = $_GET['numero']; $sql= "SELECT titulo,mensagem FROM noticia WHERE noticia_id=".$numero; /* ---- Fazer: ---- */ $numero = (int) $_GET['numero']; //ou $numero = intval($_GET['numero']); $sql= "SELECT titulo,mensagem FROM noticia WHERE noticia_id=".$numero; /* ou então pode-se usar o sprintf */ $sql= sprintf( "SELECT titulo,mensagem FROM noticia WHERE noticia_id = %u",$numero); /* inclusive para casos compostos */ $numero=22; $titulo='Minha noticia'; $sql= sprintf( "SELECT titulo,mensagem FROM noticia WHERE noticia_id = %u OR titulo = '%s'",$numero, $titulo); /* a SQL Injection no meio da string irá exigir a entrada de uma aspa Ex: "SELECT titulo,mensagem FROM noticia WHERE titulo = 'Meu Teste' SQL Injection: "SELECT titulo,mensagem FROM noticia WHERE titulo = 'Meu Teste' OR 1=1 --' a entrada deverá ser: Meu Teste' OR 1=1 -- para resolver esta entrada, usar as funções pertinente conforme o banco de dados Ex: pg_escape_string pg_escape_bytea dbx_escape_string db2_escape_string maxdb_escape_string mysql_escape_string sqlite_escape_string mysqli_escape_string ingres_escape_string maxdb_real_escape_string mysql_real_escape_string */ $titulo = @pg_escape_string($_POST['titulo']); /* o 'arroba' à frente da função é usado para evitar warning oyu fatal error */ $sql="SELECT titulo,mensagem FROM noticia WHERE titulo = '".$titulo."'"; /* o uso das funções de preparação de query também é recomendado pois faz o trabalho de escapar e validar dados antes da execução ex: pg_prepare mysqli_stmt_prepare ingres_prepare pg_send_prepare ovrimos_prepare maxdb_stmt_prepare db2_prepare ifx_prepare odbc_prepare maxdb_prepare swish_prepare ibase_prepare sdo_das_relational_executepreparedquery exemplo retirado de: http://br2.php.net/manual/pt_BR/function.pg-prepare.php $dbconn = pg_connect("dbname=mary"); $result = pg_prepare($dbconn, "my_query", 'SELECT * FROM shops WHERE name = $1'); //---> Execute the prepared query. Note that it is not necessary to escape the string "Joe's Widgets" in any way: $result = pg_execute($dbconn, "my_query", array("Joe's Widgets")); //---> Execute the same prepared query, this time with a different parameter: $result = pg_execute($dbconn, "my_query", array("Clothes Clothes Clothes")); */ /* alguns padrões podem ser verificados com o uso de expressões regulares seguem exemplos para uma máscare de telefone e uma máscara de CPF - mas sem validação dos dados, apenas do padrão. */ /*verdadeiro se o parâmetro for algo como (99)9999-9999 */ function checar_padrao_telefonico($valor=false) { return preg_match('/^\([0-9]{2}\)[0-9]{4}-[0-9]{4}$/',$valor)?true:false; } /*verdadeiro se o parâmetro for algo como 999.999.999-99 */ function checar_padrao_cpf($valor=false) { return preg_match('/^([0-9]{3}\.){2}[0-9]{3}-[0-9]{2}$/',$valor)?true:false; } ?>
Tagged: php, programação, sql