PHP 스크립트에서 500 내부 서버 오류 오류를 보내는 방법


81

특정 조건에서 PHP 스크립트에서 "500 내부 서버 오류"를 보내야합니다. 스크립트는 타사 앱에서 호출해야합니다. 스크립트에는 일반적인 대신 응답 코드 die("this happend")를 보내야 하는 몇 가지 문이 포함되어 있습니다 . 제 3 자 스크립트는 응답 코드를 받지 않는 것을 포함한 특정 조건에서 요청을 다시 보냅니다 .500 Internal Server Error200 OK200 OK

질문의 두 번째 부분 : 다음과 같이 스크립트를 설정해야합니다.

<?php
    custom_header( "500 Internal Server Error" );

    if ( that_happened ) {
        die( "that happened" )
    }

    if ( something_else_happened ) {
        die( "something else happened" )
    }

    update_database( );

    // the script can also fail on the above line
    // e.g. a mysql error occurred

    remove_header( "500" );
?>

200마지막 줄이 실행 된 후에 만 ​​헤더 를 보내야 합니다.

편집하다

부수적 인 질문 : 다음과 같은 이상한 500 개의 헤더를 보낼 수 있습니까?

HTTP/1.1 500 No Record Found
HTTP/1.1 500 Script Generated Error (E_RECORD_NOT_FOUND)
HTTP/1.1 500 Conditions Failed on Line 23

이러한 오류가 웹 서버에 기록됩니까?


u는 헤더를 보내고 나중에 헤더를 제거 할 때 할 수 없습니다
ajreal

1
다시 질문 : 그것은 전적으로 합법적입니다. 이유 문구는 기계 소비를위한 것이 아니며 무엇이든 될 수 있습니다. 중요한 것은 3 자리 상태 코드뿐입니다. (RFC2616 6.1.1 : "여기에 나열된 이유 문구는 권장 사항 일뿐입니다. 프로토콜에 영향을주지 않고 로컬 등가물로 대체 할 수 있습니다.")
Piskvor는

답변:


171
header($_SERVER['SERVER_PROTOCOL'] . ' 500 Internal Server Error', true, 500);

참고로이 솔루션은 일부 Apache 버전에서 브라우저 버그 헤더를 방지하는 X-Pad를 보냅니다. stackoverflow.com/questions/8711584/... . http_response_code()이 헤더를 생략합니다.
Anthony Rutledge

3
헤더가 처음에 있지 않은 경우에도 작동합니다 (예 : 작업 증명).
나는 나입니다

멋지다. 500 내부 서버 오류 대신 json을 출력하려면 어떻게해야할까요?
tblancog

44

PHP 5.4에는 http_response_code 라는 함수가 있으므로 PHP 5.4를 사용하는 경우 다음을 수행 할 수 있습니다.

http_response_code(500);

5.4에서 PHP 버전을 실행하는 경우이 함수 (Gist)에 대한 polyfill을 작성했습니다 .


후속 질문에 답하기 위해 HTTP 1.1 RFC는 다음과 같이 말합니다.

여기에 나열된 이유 문구는 권장 사항 일 뿐이며 프로토콜에 영향을주지 않고 로컬 등가물로 대체 할 수 있습니다.

즉, 코드 자체 뒤에 원하는 텍스트 (캐리지 리턴 또는 줄 바꿈 제외)를 사용할 수 있으며 작동합니다. 하지만 일반적으로 더 나은 응답 코드를 사용할 수 있습니다. 예를 들어 레코드를 찾을 수없는 경우 500 을 사용하는 대신 404 (찾을 수 없음)를 보낼 수 있고 "조건 실패"(유효성 검사 오류를 추측 함)와 같은 경우에는 422 (처리 할 수 없음)와 같은 메시지를 보낼 수 있습니다. 실재).


출력이 시작되면이 기능도 더 이상 작동하지 않는다는 점을 기억하는 것이 중요합니다!
rob74

@ rob74 True — 일단 PHP가 출력을 보내기 시작하면 모든 헤더 관련 기능이 더 이상 작동하지 않습니다. 출력 전송을 시작하기 전에 응답 코드를 변경해야하는지 확실하지 않은 경우 출력 버퍼링 이 좋은 솔루션입니다.
inxilpro 2015 년

34

다음 기능을 사용하여 상태 변경을 보낼 수 있습니다.

function header_status($statusCode) {
    static $status_codes = null;

    if ($status_codes === null) {
        $status_codes = array (
            100 => 'Continue',
            101 => 'Switching Protocols',
            102 => 'Processing',
            200 => 'OK',
            201 => 'Created',
            202 => 'Accepted',
            203 => 'Non-Authoritative Information',
            204 => 'No Content',
            205 => 'Reset Content',
            206 => 'Partial Content',
            207 => 'Multi-Status',
            300 => 'Multiple Choices',
            301 => 'Moved Permanently',
            302 => 'Found',
            303 => 'See Other',
            304 => 'Not Modified',
            305 => 'Use Proxy',
            307 => 'Temporary Redirect',
            400 => 'Bad Request',
            401 => 'Unauthorized',
            402 => 'Payment Required',
            403 => 'Forbidden',
            404 => 'Not Found',
            405 => 'Method Not Allowed',
            406 => 'Not Acceptable',
            407 => 'Proxy Authentication Required',
            408 => 'Request Timeout',
            409 => 'Conflict',
            410 => 'Gone',
            411 => 'Length Required',
            412 => 'Precondition Failed',
            413 => 'Request Entity Too Large',
            414 => 'Request-URI Too Long',
            415 => 'Unsupported Media Type',
            416 => 'Requested Range Not Satisfiable',
            417 => 'Expectation Failed',
            422 => 'Unprocessable Entity',
            423 => 'Locked',
            424 => 'Failed Dependency',
            426 => 'Upgrade Required',
            500 => 'Internal Server Error',
            501 => 'Not Implemented',
            502 => 'Bad Gateway',
            503 => 'Service Unavailable',
            504 => 'Gateway Timeout',
            505 => 'HTTP Version Not Supported',
            506 => 'Variant Also Negotiates',
            507 => 'Insufficient Storage',
            509 => 'Bandwidth Limit Exceeded',
            510 => 'Not Extended'
        );
    }

    if ($status_codes[$statusCode] !== null) {
        $status_string = $statusCode . ' ' . $status_codes[$statusCode];
        header($_SERVER['SERVER_PROTOCOL'] . ' ' . $status_string, true, $statusCode);
    }
}

다음과 같이 사용할 수 있습니다.

<?php
header_status(500);

if (that_happened) {
    die("that happened")
}

if (something_else_happened) {
    die("something else happened")
}

update_database();

header_status(200);

21
몇 바이트의 메모리를 저장하는 것은 웹 애플리케이션 코드를 어떤 식 으로든 작성해야하는 좋은 이유가 아닙니다.
Dan Grossman

1
당신은 ;애프터 를 놓치고 있지 die()않습니까?
henrywright

2
귀하의 목록에 418 누락 => "나는 주전자 해요"를 참조하십시오 en.wikipedia.org/wiki/Hyper_Text_Coffee_Pot_Control_Protocol
루이 Loudog Trottier

16

다음을 넣을 수 있습니다.

header("HTTP/1.0 500 Internal Server Error");

다음과 같은 조건 내에서 :

if (that happened) {
    header("HTTP/1.0 500 Internal Server Error");
}

데이터베이스 쿼리는 다음과 같이 할 수 있습니다.

$result = mysql_query("..query string..") or header("HTTP/1.0 500 Internal Server Error");

html 태그 (또는 출력) 앞에이 코드를 넣어야한다는 것을 기억해야합니다.


11
header ()를 호출 한 후 exit / die / return / something을 확인하십시오. PHP는 코드 실행을 계속할 것입니다. 이것은 아마도 바람직하지 않을 것입니다.
David Goodwin

8

다음과 같이 단순화 할 수 있습니다.

if ( that_happened || something_else_happened )
{
    header('X-Error-Message: Incorrect username or password', true, 500);
    die;
}

다음 헤더를 반환합니다.

HTTP/1.1 500 Internal Server Error
...
X-Error-Message: Incorrect username or password
...

추가됨 : 무엇이 잘못되었는지 정확히 알아야하는 경우 다음과 같이하십시오.

if ( that_happened )
{
    header('X-Error-Message: Incorrect username', true, 500);
    die('Incorrect username');
}

if ( something_else_happened )
{
    header('X-Error-Message: Incorrect password', true, 500);
    die('Incorrect password');
}

5
이제 무엇을 'x'해야합니까?
Core Xii

1
+1의 첫 번째 매개 변수는 header비어 있지 않은 문자열이어야합니다. 그것은 'x'정말로 중요하지 않습니다.
theazureshadow 2010

1
@Core Xii, @theazureshadow가 지적한대로 첫 번째 매개 변수는 null이 아니어야합니다. 간단히 말해 header ( 'something', true, 500)을 호출하면 올바른 헤더 "HTTP / 1.0 500 내부 서버 오류"가 반환됩니다. 나를 lazy라고 부를 수도 있지만 실제 헤더 문자열을 처리하는 것보다 오류 코드를 전달하는 것이 더 쉽습니다. :) 자세한 내용 은 php.net/manual/en/function.header.php 를 참조하십시오.
David Kuridža 2010

매뉴얼은 이것에 대해 명확하지 않습니다. 그래서 상태 코드를 강제하면 PHP가 문자열 인수를 올바른 값으로 자동으로 덮어 씁니다. 그렇다면 매뉴얼에 문자열 비어 있지 않은 경우에만 효과가 있다고 말하는 이유는 무엇입니까?
Core Xii

1
일부 PHP 구성 (내 호스팅 제공 업체가 예제에 사용하지만 로컬 설정에는 사용하지 않음)에서는이 트릭이 작동하지 않습니다. Apache는 "x"를 올바른 헤더 문자열로 인식하지 못하며 "Malformed header"오류와 함께 실패합니다.
mjsarfatti

2

코드는 다음과 같아야합니다.

<?php
if ( that_happened ) {
    header("HTTP/1.0 500 Internal Server Error");
    die();
}

if ( something_else_happened ) {
    header("HTTP/1.0 500 Internal Server Error");
    die();
}

// Your function should return FALSE if something goes wrong
if ( !update_database() ) {
    header("HTTP/1.0 500 Internal Server Error");
    die();
}

// the script can also fail on the above line
// e.g. a mysql error occurred


header('HTTP/1.1 200 OK');
?>

뭔가 잘못되면 실행을 중지한다고 가정합니다.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.