Apache 단계적 다시 로드가 완료되면 감지

Apache 단계적 다시 로드가 완료되면 감지

Apache Graceful Reload(apachectl Graceful)는 비동기 작업인 것으로 보입니다. 스크립트에서 호출하면 Apache가 작업을 수행하는 동안 스크립트가 계속 진행됩니다. 이 작업에는 시간이 오래 걸릴 수 있습니다(예: 느린 클라이언트, 긴 다운로드).

다시 로드가 완료되고 Apache가 이제 새 구성으로 실행되는 시기를 프로그래밍 방식으로 감지하고 싶습니다. 즉, Apache가 완료된 후에만 계속되는 동기 호출처럼 처리하는 방법을 찾고 싶습니다.

당신이 나라면 어떻게 그렇게 하시겠습니까?

12/09 추가: Apache는 새 구성으로 유휴 스레드를 다시 시작하지만 열려 있는 연결이 있는 스레드는 연결이 종료될 때까지 이전 구성을 유지하는 것으로 보입니다. 따라서 Apache가 새 구성으로 새로운 연결을 수락하기 시작하는 시기를 결정하는 것에 대해 더 정확하게 질문할 수 있습니다.

답변1

내 문제는 스스로 해결해야 할 것 같아요 ...

여기에 제가 생각해낸 Perl의 일부가 있습니다. 기본적으로 아파치 로그 파일의 끝부분을 찾아 외워두는 편이다. 그런 다음 Apache를 다시 시작/다시 로드하고 이후 로그 파일에 어떤 텍스트가 기록되었는지 확인합니다. 텍스트에 "정상 작업 재개"가 포함되어 있으면 다시 시작/다시 로드가 완료된 것으로 간주합니다. (그게 사실인지는 확실하지 않지만 여기 "중지 및 다시 시작"에 대한 Apache 페이지에서 나온 것처럼 들립니다.http://httpd.apache.org/docs/2.2/stopping.html)

개선이 이루어졌습니다.

my $lastPos;

sub textSinceLast {
    my $logF  = '/var/log/httpd/error_log'; # or wherever your Apache log file is

    open( FH, '<', $logF ) || die( "Cannot open $logF" );
    my $pos  = sysseek( FH, 0, SEEK_END );
    my $ret = "Still at mark";

    if( defined( $lastPos ) && $pos != $lastPos ) {
        sysseek( FH, $lastPos, SEEK_SET );
        sysread( FH, $ret, $pos - $lastPos, 0 );
    }
    close( FH );
    $lastPos = $pos;
    return $ret;
}

textSinceLast();

`systemctl reload httpd`; # or "service restart apache2", or whatever your distro wants

for( my $i=0 ; $i<1000 ; ++$i ) { # give up after 10sec
    select( undef, undef, undef, 0.01 ); # apparently a tricky way of sleeping for 10ms
    my $text = textSinceLast();
    if( $text =~ /resuming normal operations/ ) {
        print "Detected restart on $i\n";
        last;
    }
}

관련 정보