systemd가 로그를 파일에 직접 쓰도록 지시하는 다음과 같은 systemd 구성을 가진 systemd가 관리하는 서비스가 있습니다(syslog 또는 기타 항목 없음).
StandardOutput=file:/var/log/foo/my.log
로그 회전 규칙이 있습니다
/var/log/foo/*.log
{
rotate 31
daily
missingok
notifempty
compress
delaycompress
sharedscripts
}
무슨 일이 일어나고 있는지는 로그가 순환되고 있지만 서비스가 여전히 이전에 순환된 파일에 쓰고 있는 반면 새 로그 파일은 여전히 비어 있다는 것입니다.
서비스가 syslog에 기록하는 유사한 작업 설정이 있습니다. logrotate 구성이
postrotate
invoke-rc.d rsyslog rotate > /dev/null
, 로그가 교체되었음을 syslog에 알립니다.
문제는 문제가 있는 경우 로그가 파일로 직접 전송되므로 비슷한 신호를 systemd에 보내야 하는지 또는 실제 서비스 프로세스에 보내야 하는지 알 수 없다는 것입니다.
나는 copytruncate
logrotate에서 이 옵션을 찾았고 그것이 내 문제를 해결할 것이라고 확신하지만 이것이 이상적인 접근 방식이 아니며 copytruncate
그렇지 않으면 logrotate의 기본 동작이 될 것 같습니다.
이 문제를 어떻게 해결할 수 있나요? systemd에 신호를 보내야 합니까? 서비스 프로세스에 신호를 보내야 합니까? copytruncate
logrotate에서 사용해야 합니까 ?
중요한 경우 서비스는 로그백을 사용하여 stdout에 쓰는 Java 프로세스입니다.
답변1
copytruncate
이 경우에는 정답입니다. 로그 파일을 다시 열도록 신호를 보낼 수 있는 데몬이 있으므로 거의 필요하지 않기 때문에 기본값이 아닙니다.
또 다른 접근 방식은 교체 후 스크립트에서 서비스를 다시 시작하는 것이지만 이는 편리하지 않거나 이상적이지 않을 수 있습니다.
답변2
systemd를 통해 열린 로그는 StandardOutput=file:
이 서비스에 의해 열립니다. 이를 통해 확인할 수 있습니다.lsof /var/log/mylog.log
따라서 회전은 서비스에 따라 다릅니다. 서비스가 특정 신호를 받은 후 로그 파일 다시 열기를 지원하는 경우 간단히 서비스에 신호를 보낼 수 있습니다.아니요시스템에
예를 들어 Apache는 USR1 또는 HUP를 받은 후 로그 파일을 다시 엽니다. 따라서 다음 신호 중 하나를 보내야 합니다.
서비스의 단위 파일에 서비스에 적절한 신호를 보내는 ExecReload 줄이 있는 경우 다음 명령을 사용하여 이를 수행할 수 있습니다.
systemctl reload $service
그렇지 않으면 다른 방법을 사용해야 합니다.
kill -$signal $pid