장기 실행 독립 프로세스를 생성하는 시스템 서비스를 실행하는 "올바른" 방법은 무엇입니까?

장기 실행 독립 프로세스를 생성하는 시스템 서비스를 실행하는 "올바른" 방법은 무엇입니까?

새로운 이벤트가 감지될 때마다 ffmpeg 프로세스를 생성하는 시스템 서비스가 있습니다. 이러한 프로세스는 서비스가 다시 시작되더라도 유지되고 완료될 때까지 실행되어야 합니다(그래서 가능한 한 빨리 분리됩니다).

현재 다음 서비스 단위 파일을 사용하여 설정했습니다.

[Unit]
Description=My Service

[Service]
Environment="VAR1=val1" "VAR2=val2"
Type=exec
KillMode=process
ExecStart=/path/to/service/executable
Restart=on-failure

[Install]
WantedBy=default.target

이것이 작동하는 동안 로그의 systemd 경고에 따르면 "올바른" 것은 아닙니다.

systemd[1]: Found left-over process 789794 (ffmpeg) in control group while starting unit. Ignoring.
systemd[1]: This usually indicates unclean termination of a previous run, or service implementation deficiencies.

그렇다면 systemd에서 상위 프로세스보다 오래 지속되는 분리된 프로세스를 처리하는 올바른 방법은 무엇입니까?

답변1

다른 시스템 장치에서 장기 실행 프로세스를 실행하는 것이 좋습니다. 이렇게 하려면 두 번째 시스템 장치를 생성해야 합니다.템플릿 단위. 이렇게 하면 다양한 매개변수를 사용하여 다양한 인스턴스를 시작할 수 있습니다. 일반적으로 systemd는 각 장치를 한 번만 실행합니다(실행 중에 시작하면 아무 일도 일어나지 않습니다). 템플릿 단위는 로 끝나므로 @뒤에 @오는 다른 문자열이 있는 다른 인스턴스가 @동시에 실행될 수 있습니다.

단위 1은 새로운 흐름을 감지하도록 설계되었습니다.

[Unit]
Description=My Service

[Service]
Environment="VAR1=val1" "VAR2=val2"
Type=exec
# KillMode=process  # don't do this read the man page about it
ExecStart=/path/to/service/executable
Restart=on-failure

[Install]
WantedBy=default.target

프로그램에서 /path/to/service/executable새 이벤트/라이브 스트림이 감지되면 라이브 스트림 이름을 인스턴스 매개변수로 사용하여 템플릿 서비스를 시작할 수 있습니다.systemctl start [email protected]

서비스 파일은 [email protected]다음과 같습니다.

[Unit]
Description=Process one live stream

[Service]
# the string "%i" is substituted by systemd with the stuff you give it after the @ in the unit name.
ExecStart=/usr/bin/ffmpeg --some-args --live-stream=%i

편집하다:

매개변수가 많은 경우 다음을 통해 임시 파일에 쓰고 템플릿 서비스에서 읽을 수 있습니다 EnvironmentFile.

[Service]
EnvironmentFile=/my/folder/%i
ExecStart=/usr/bin/ffmpeg --some-args $ARGS_FROM_ENV_FILE

답변2

서비스 단위 파일을 일부 변경할 수 있습니다.

  1. 로 변경 . Type=exec이는Type=simple 서비스가 포크나 백그라운드 작업 없이 ffmpeg 프로세스를 직접 시작함을 나타냅니다.

  2. RemainAfterExit=yes이 섹션에 추가하세요 [Service]. 이는 주 프로세스가 종료된 후에도 서비스를 계속 살아있는 것으로 처리하도록 systemd에 지시합니다.

업데이트된 서비스 단위 파일은 다음과 같습니다.

[Unit]
Description=My Service

[Service]
Environment="VAR1=val1" "VAR2=val2"
Type=simple
KillMode=process
ExecStart=/path/to/service/executable
Restart=on-failure
RemainAfterExit=yes

[Install]
WantedBy=default.target

systemd는 더 이상 남은 프로세스에 대해 불평하지 않습니다. ffmpeg 프로세스가 의도적으로 분리되었음을 인식하고 서비스가 다시 시작되더라도 완료될 때까지 실행되도록 허용합니다. 도움이 되었기를 바랍니다!

관련 정보