2010-11-19 6 views
2

제출 된 변수를 안전하게 추출하는 쉬운 방법이 있습니까?

if(isset($_REQUEST['kkld'])) $kkld=mysql_real_escape_string($_REQUEST['kkld']); 
if(isset($_REQUEST['info'])) $info=mysql_real_escape_string($_REQUEST['info']); 
if(isset($_REQUEST['freq'])) $freq=mysql_real_escape_string($_REQUEST['freq']); 

(그리고 :이 상황에서 isset()을 사용?)

+2

얘들 아, 너 모두 더 많은 평판을 얻길 원하지만 왜 아무도 이상한 생각이라고 설명하지 않았다. ?? 그리고 필요한 데이터 만이 전부가 아닌 소독되어야합니다. – zerkms

+0

@zerkms, 글쎄, 나는 이것이 어떤 상황에서 유용 할 수 있기 때문에 이것이 WEIRD IDEA라고 생각하지 않는다. 그러나 나는 또한 누가 쿼리를 작성하는 사람을 제외하고 모든 데이터가 소독되어야한다는 것에 동의한다. – Starx

+2

@Starx : 어떤 종류의 공격으로부터도 데이터를 보호 할 마법 같은 방법을 사용해서는 안됩니다. 각각의 특정 상황에서 필요한 기능을 적용해야합니다. IE : SQL 쿼리를 수행해야하는 경우 (** 만 **) - 쿼리에 사용 된 변수에만 mysql_real_escape_string()을 적용합니다. – zerkms

답변

25

이 한 번에 모든 변수를 탈출 : 현재 네임 스페이스에

$escapedGet = array_map('mysql_real_escape_string', $_GET); 

추출물 모든 변수 (예 : $foo = $_GET['foo']) :

extract($escapedGet); 

마지막 단계는하지 마십시오. 필요가 없습니다. 값을 배열에 그대로 두십시오. 변수를 추출하면 이름 충돌과 기존 변수 덮어 쓰기로 이어질 수 있으며 이는 번거 로움과 버그의 원인 일뿐만 아니라 보안 위험이됩니다. 또한 @BoltClock에서 말한대로 $_GET 또는 $_POST을 고수하십시오. 또한 2, @zerkms 지적한 바와 같이, 데이터베이스 쿼리에 사용되지 않는 변수가 mysql_real_escaping에 없기 때문에 더 많은 문제가 발생할 수도 있습니다. 정말이의 없음 전혀 특히 좋은 생각이다


주, 당신은 단지 나이 과거의 끔찍한 PHP 관행이었다 magic_quotes를하고 global_vars을 reincarnating하고 있습니다. mysqli 또는 PDO를 통해 바인드 된 매개 변수가있는 prepared statement를 사용하고 $_GET 또는 filter_input을 통해 값을 사용하십시오. http://www.phptherightway.com을 참조하십시오.

+0

@ajo 데이터 자체는 결코 위험하지 않습니다. 위험한 데이터를 사용하기 때문에 위험합니다. mysql_real_escape은 SQL 쿼리에서 데이터를 사용할 때만 당신을 보호한다. SQL 쿼리에서 데이터를 사용하지 않는다면 데이터 만 변경할 것이므로 더 이상 저장하지 않을 것입니다. 데이터를 HTML 페이지에 에코하려면 mysql_real_escaping이 도움이되지 않을 것입니다. 대신에'htmlentities'를 사용해야합니다 ... 컨텍스트가 중요합니다! – deceze

+0

글쎄, 그가 대답하기 전에 내가 대답했던 ajo의 코멘트가 있었다. 나는 어쨌든 내 코멘트를 남겨 둘 것이다. – deceze

+1

이제 모든 사람들이'PDO' 나'prepared statements'을 사용해야하지만,'$ _REQUEST' 나 $ _POST 변수가'array' 일 때 넘어지지 않을까요? 예를 들어 동일한 이름의 여러 체크 박스 값을 제출할 때 – wired00

2

또한

function sanitate($array) { 
    foreach($array as $key=>$value) { 
     if(is_array($value)) { sanitate($value); } 
     else { $array[$key] = mysql_real_escape_string($value); } 
    } 
    return $array; 
} 
sanitate($_POST); 
0

은 살균 또는 INPUT_GET, INPUT_POST, INPUT_COOKIE, INPUT_SERVER, 또는 INPUT_ENV, 당신은

  • filter_input_array을 사용할 수 있습니다 확인하려면 있음을 달성하기 위해 다음과 같이 재귀 기능을 사용할 수 있습니다 - 외부 변수를 가져오고 선택적으로 필터링합니다.

필터링은 콜백으로 수행 할 수 있으므로 mysql_real_escape_string을 제공 할 수 있습니다.

이 방법은 $_REQUEST에 대한 필터링을 허용하지 않습니다. 왜냐하면 you should not work with $_REQUEST은 다른 슈퍼 전역에서 데이터를 사용할 수 있기 때문입니다. 잠재적으로 안전하지 않습니다.

또한 입력 키의 이름을 지정해야하므로 일반 일괄 필터링이 아닙니다. 일반 일괄 필터링을 원할 경우이 페이지의 다른 부분에 표시된대로 array_map 또는 array_walk 또는 array_filter을 사용하십시오.

또한, 왜 당신은 mysqli (개선을 위해) 확장자 대신 이전의 mysql 확장자를 사용하고 있습니까? mysqli 확장은 transactions, multiqueriesprepared statements (이스케이프 필요 없음) DB 코드를 훨씬 더 안정적이고 안전하게 만들 수있는 모든 기능을 지원합니다.

-2

대신 SQL 이스케이프에 대한 바로 가기를 제공하는 PHP7 input filters을 사용하는 것이 좋습니다.SQL 쿼리 문자열에 인라인으로 사용하고, 추가로 경고를 줄 수있다

$_REQUEST->sql['kkld'] 

당신이 그것을 잊지해야합니다 :

mysql_query("SELECT x FROM y WHERE z = '{$_REQUEST->sql['kkld']}'"); 

나는 자체 추천하지 않는 게 좋을하지만 지역화 된 변수를 만드는 예비 부품 문법적으로 의문의 여지가 있지만 실제로 필요한 변수 만 이스케이프 할 수 있습니다. 또는 무엇을 요구했는지 에뮬레이트하려면 $_REQUEST->sql->always();

+4

PHP7 프레임 워크는 최악의 프레임 워크 이름이어야합니다 :) – Gordon

0

저는 Starx와 Ryan의 대답이 11 월 19 일부터 10 월 10 일까지의 가장 좋은 해결책이라고 생각합니다.

하나의 이름 (예 : names [])이있는 입력 필드가 여러 개있는 경우 $ _POST 배열의 배열에 저장된다는 의미이므로 배열의 경우 mysql_real_escape_string이 작동하지 않으므로 재귀 함수를 사용해야합니다. .

그래서이 $ _POST 변수를 벗어나는 유일한 해결책입니다.

function sanitate($array) { 
    foreach($array as $key=>$value) { 
     if(is_array($value)) { sanitate($value); } 
      else { $array[$key] = mysql_real_escape_string($value); } 
    } 
    return $array; 
} 
sanitate($_POST);