PHP:$_SESSION - 임시로 사용된 데이터를 $_SESSION 변수에 저장하는 것의 장단점은 무엇입니까?

StackOverflow https://stackoverflow.com/questions/77826

  •  09-06-2019
  •  | 
  •  

문제

최근에 내가 더 자주 하기 시작한 일은 일부 데이터를 검색하는 중 작업 시작 시 $_SESSION['myDataForTheTask'] 에 저장합니다..

이제 그렇게 하는 것이 매우 편리해 보이지만 이 접근 방식을 사용하면 성능, 보안 위험 또는 이와 유사한 것에 대해 아무것도 모릅니다.더 많은 전문 지식을 갖춘 프로그래머가 정기적으로 수행하는 작업입니까, 아니면 아마추어에 가까운 작업입니까?

예를 들어:

if (!isset($_SESSION['dataentry']))
{
    $query_taskinfo = "SELECT participationcode, modulearray, wavenum FROM mng_wave WHERE wave_id=" . mysql_real_escape_string($_GET['wave_id']);
    $result_taskinfo = $db->query($query_taskinfo);
    $row_taskinfo = $result_taskinfo->fetch_row();

        $dataentry = array("pcode" => $row_taskinfo[0], "modules" => $row_taskinfo[1], "data_id" => 0, "wavenum" => $row_taskinfo[2], "prequest" => FALSE, "highlight" => array());

        $_SESSION['dataentry'] = $dataentry;
}
도움이 되었습니까?

해결책

세션 변수는 실제로 방문자가 웹 사이트에 있는 동안 이러한 변수를 사용할 수 있는 유일한 방법(그리고 아마도 가장 효율적인 방법) 중 하나입니다. 사용자가 이를 편집할 수 있는 실제 방법은 없습니다. 코드 또는 PHP 인터프리터)이므로 상당히 안전합니다.

세션 시작 시 한 번 데이터베이스에서 설정을 읽을 수 있고 해당 전체 세션에 대해 사용할 수 있으므로 사용자가 변경할 수 있는 설정을 저장하는 좋은 방법입니다. 설정이 변경된 경우에만 추가 데이터베이스 호출을 수행하면 됩니다. 물론 코드에 표시된 것처럼 설정이 이미 존재하는지 또는 데이터베이스에서 추출해야 하는지 확인하는 것은 간단합니다.

임시 변수를 안전하게 저장하는 다른 방법은 생각할 수 없습니다(쿠키는 쉽게 수정될 수 있고 대부분의 경우 바람직하지 않기 때문입니다). 따라서 $_SESSION을 사용하는 것이 좋습니다.

다른 팁

$_SESSION 메커니즘이 쿠키를 사용하고 있습니다.

Firefox의 경우(아마도 새로운 IE일 수도 있고 직접 확인하지 않았을 수도 있음) 이는 다음을 의미합니다. 열린 탭 간에 세션이 공유됩니다..이는 기본적으로 기대하는 것이 아닙니다.이는 세션이 더 이상 "단일 창/사용자에게 특정한 것"이 아니라는 것을 의미합니다.

예를 들어 사이트에 액세스하기 위해 두 개의 탭을 열었다면 첫 번째 탭을 사용하여 루트로 로그인한 후 다른 탭에서도 루트 권한을 얻게 됩니다.

이는 정말 불편합니다. 특히 이메일 클라이언트나 다른 것(예: e-shop)을 코딩하는 경우 더욱 그렇습니다.이 경우 세션을 수동으로 관리하거나 URL에 지속적으로 재생성되는 키를 도입하거나 다른 작업을 수행해야 합니다.

저는 항상 세션 변수를 사용하여 사용자 정보를 저장합니다.성능상 문제는 못봤습니다.세션 데이터는 쿠키(또는 PHPSESSID 쿠키가 꺼져 있는 경우).다른 쿠키 기반 인증보다 보안 위험이 더 크지 않으며 사용자 쿠키에 실제 데이터를 저장하는 것보다 더 안전할 것입니다.

하지만 알려드리자면 SQL 문에 보안 문제가 있습니다.

SELECT participationcode, modulearray, wavenum FROM mng_wave WHERE wave_id=".$_GET['wave_id'];

당신은해야 절대, 절대 반복하지 않아요, 사용자가 제공한 데이터를 가져와서 먼저 정리하지 않고 SQL 문을 실행하는 데 사용합니다.따옴표로 묶고 함수를 추가하겠습니다. mysql_real_escape_string().그러면 대부분의 공격으로부터 보호받을 수 있습니다.따라서 귀하의 라인은 다음과 같습니다:

$query_taskinfo = "SELECT participationcode, modulearray, wavenum FROM mng_wave WHERE wave_id='".mysql_real_escape_string($_GET['wave_id'])."'";

임시 데이터를 저장할 위치를 결정할 때 고려해야 할 몇 가지 요소가 있습니다.세션 저장소는 단일 사용자와 관련된 데이터에 적합합니다.기본 파일 기반 세션 스토리지 핸들러가 비효율적이라면 데이터베이스나 Memcache 유형의 백엔드를 사용하여 다른 것을 구현할 수 있습니다.보다 session_set_save_handler 더 많은 정보를 위해서.

사용자 세션에 공통 데이터를 저장하는 것은 나쁜 습관입니다.여러 사용자가 자주 액세스하는 데이터를 저장하는 더 좋은 장소가 있으며, 이 데이터를 세션에 저장하면 이 데이터가 필요한 각 사용자에 대해 데이터를 복제하게 됩니다.귀하의 예에서는 사용자 세션에 특별히 연결되지 않은 이 웨이브 데이터(wave_id 기반)에 대해 다른 유형의 스토리지 엔진을 설정할 수 있습니다.이렇게 하면 데이터를 한 번 아래로 가져오고 여러 사용자가 다시 가져오지 않고도 데이터에 액세스할 수 있는 곳에 저장합니다.

자체 서버에서 실행 중이거나 누구도 서버의 파일/메모리를 스누핑할 수 없는 환경에서 실행 중인 경우 세션 데이터는 안전합니다.쿠키는 서버에 저장되며 클라이언트에 전송되는 식별 쿠키일 뿐입니다.문제는 물론 다른 사람이 쿠키를 빼앗아 다른 사람을 사칭할 수 있다는 것입니다.HTTPS를 사용하고 URL에 세션 ID를 넣지 않도록 하면 대부분의 문제로부터 사용자를 안전하게 보호할 수 있습니다.(주의하지 않으면 XSS가 쿠키를 가로채는 데 계속 사용될 수 있습니다. 이에 대한 Jeef Atwoods의 게시물 도.)

세션 변수에 무엇을 저장할지는 장바구니와 같은 다른 페이지에서 다시 참조하려면 데이터를 거기에 두십시오. 그러나 이 결과를 생성하는 데 사용되는 임시 데이터인 경우에는 거기에 넣지 마십시오. 현재 본 게시물의 태그 목록과 같은 페이지입니다.세션은 사용자별 영구 데이터를 위한 것입니다.

입력 유효성 검사를 개선하는 또 다른 방법은 _GET['wave_id'] 변수를 캐스팅하는 것입니다.

$query_taskinfo = "SELECT participationcode, modulearray, wavenum FROM mng_wave WHERE wave_id=".(int)$_GET['wave_id']." LIMIT 1";

나는 wave_id가 정수이고 답은 하나뿐이라고 가정합니다.

할 것이다

세션 사용의 몇 가지 다른 단점:

  1. $_SESSION 데이터는 다음 이후에 만료됩니다. session.gc_maxlifetime 몇 초 동안 활동이 없습니다.
  2. 기억해두고 전화해야 해 session_start() 세션 데이터를 사용할 모든 스크립트에 대해.
  3. 여러 서버에 대한 로드 밸런싱을 통해 웹 사이트를 확장하는 것은 사용자가 매번 동일한 서버로 연결되어야 하기 때문에 문제가 될 수 있습니다."고정 세션"으로 이 문제를 해결하세요.

$_SESSION 항목은 세션에 저장되며 기본적으로 디스크에 보관됩니다.자신만의 배열을 만들어서 이전처럼 '데이터 입력' 배열 항목에 넣을 필요가 없습니다.$_SESSION['pcode'], $_SESSION['modules'] 등을 사용할 수 있습니다.

내가 말했듯이 세션은 디스크에 저장되고 세션에 대한 포인터는 쿠키에 저장됩니다.따라서 사용자는 세션 데이터를 쉽게 얻을 수 없습니다.

IMO, 세션에 항목을 저장하는 것은 완벽하게 허용됩니다.이는 데이터를 지속적으로 유지하는 좋은 방법입니다.또한 많은 경우 모든 것을 쿠키에 저장하는 것보다 더 안전합니다.다음은 몇 가지 우려 사항입니다.

  • 누군가가 세션을 가로채는 것이 가능하므로 이를 사용하여 사용자 인증을 추적하려면 주의하세요.읽다 이것 자세한 내용은.
  • 데이터를 보관하는 것은 매우 게으른 방법일 수 있습니다.나중에 쿼리할 필요가 없도록 세션에 모든 것을 던지지 마십시오.
  • 세션에 개체를 저장하려는 경우 다음 요청 시 세션이 시작되기 전에 해당 클래스 파일을 포함해야 하거나 자동 로더를 구성해야 합니다.

Zend Framework에는 만료 및 보안(보안문자 등)에 도움이 되는 세션 데이터 관리를 위한 유용한 라이브러리가 있습니다.또한 세션에 대한 유용한 설명도 있습니다.보다 http://framework.zend.com/manual/en/zend.session.html

세션이 매우 유용하다고 생각하지만 몇 가지 참고할 사항이 있습니다.

1) PHP는 서버의 다른 사용자가 액세스할 수 있는 tmp 폴더나 기타 디렉토리에 세션을 저장할 수 있습니다.php.ini 파일로 이동하여 세션이 저장된 디렉토리를 변경할 수 있습니다.

2) 매우 엄격한 보안이 필요한 높은 가치의 시스템을 설정하는 경우 세션에 보내기 전에 데이터를 암호화하고 해독하여 사용할 수 있습니다.메모:트래픽/서버 용량에 따라 너무 많은 오버헤드가 발생할 수 있습니다.

3) 나는 session_destroy()를 발견했습니다.세션을 즉시 삭제하지 않으면 PHP 가비지 수집기가 세션을 정리할 때까지 기다려야 합니다.php.ini 파일에서 가비지 수집기가 실행되는 빈도를 변경할 수 있습니다.하지만 여전히 신뢰성이 떨어지는 것 같습니다. 추가 정보 http://www.captain.at/howto-php-sessions.php

이것이 얼마나 REST-ful인지 고려하고 싶을 수도 있습니다.

즉."의 "무상태 통신" 단락을 참조하세요.REST에 대한 간략한 소개"...

"REST는 상태가 자원 상태로 바뀌거나 고객을 유지해야합니다.다시 말해, 서버는 단일 요청을 넘어서 의사 소통하는 클라이언트에 대해 일종의 통신 상태를 유지할 필요가 없습니다. "

(또는 Wikipedia의 다른 링크 중 하나 나머지)

따라서 귀하의 경우 'wave_id'는 GET에 적합한 리소스이지만 실제로 SESSION에 저장하시겠습니까?확실히 멤캐시드 개체 리소스를 캐시하는 솔루션이 있습니까?

저는 이 접근 방식을 꽤 많이 사용하는데 아무런 문제가 없습니다.쿠키와 달리 데이터는 클라이언트 측에 저장되지 않으며 이는 종종 큰 실수입니다.

하지만 다른 것과 마찬가지로, 특히 사용자 입력을 $_SESSION 변수에 넣은 다음 나중에 SQL 쿼리에서 해당 변수를 사용하는 경우에는 항상 사용자 입력을 삭제해야 한다는 점에 주의하세요.

이는 매우 일반적인 작업이며 세션은 일반적으로 지속적인 데이터베이스 적중보다 빠릅니다.또한 PHP 개발자가 세션 하이재킹을 방지하기 위해 열심히 노력했기 때문에 상당히 안전합니다.

유일한 문제는 무언가 변경되면 세션 항목을 다시 작성해야 한다는 것입니다.그리고 세션을 소유한 사용자가 아닌 사용자가 변경하여 이 키를 새로 고쳐야 하는 경우 시스템에 이 세션 키를 새로 고치도록 알리는 쉬운 방법이 없습니다.아마도 큰 문제는 아니지만 알아두어야 할 사항입니다.

$_SESSION은 사용자가 페이지에 활동하는 동안 정보를 저장하는 서버 측 방법이므로 보안에 매우 유용합니다. 따라서 실제 PHP 파일이나 서버에 악용되는 약점이 없으면 해킹하기 어렵습니다.매우 좋은 구현 중 하나는 사용자가 로그인했는지 확인하는 변수를 저장하고 로그인이 확인된 경우에만 작업을 수행하도록 허용하는 것입니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top