programing

Python에서 데몬을 작성하려면 어떻게 해야 하나요?

shortcode 2022. 11. 6. 16:31
반응형

Python에서 데몬을 작성하려면 어떻게 해야 하나요?

구글에서 검색하면 x2 코드 조각이 나타납니다.첫 번째 결과는 이 코드 레시피에 대한 것입니다.이 코드 레시피에는 많은 문서와 설명이 포함되어 있습니다.아래에 있는 유용한 논의도 포함되어 있습니다.

그러나 다른 코드 샘플에는 많은 문서가 포함되어 있지 않지만 start, stop, restart 등의 명령어를 전달하기 위한 샘플코드가 포함되어 있습니다.또한 데몬이 이미 실행 중인지 등을 확인하는 데 편리한 PID 파일도 생성합니다.

이들 샘플 모두 데몬 작성 방법을 설명합니다.추가로 고려해야 할 사항이 있습니까?하나의 샘플이 다른 샘플보다 더 나은가요? 그 이유는 무엇입니까?

현재의 솔루션

PEP 3143(Standard daemon process library)의 레퍼런스 실장은 python-daemon으로 이용할 수 있습니다.

이력 답변

Sander Marechal의 코드 샘플은 원래 2004년에 게시된 원본보다 우수합니다.파이로의 데몬라이저 기고를 한 적이 있지만, 다시 해야 한다면 샌더의 코드를 사용할 거예요.

정상적으로 동작하는 데몬프로세스가 되었을 때는, 많은 주의가 필요합니다.

  • 코어 덤프 방지(많은 데몬이 루트로 실행되며 코어 덤프에는 중요한 정보가 포함될 수 있음)

  • 가올 안에서 올바르게 행동하다

  • UID, GID, 작업 디렉토리, umask 및 기타 프로세스 매개 변수 설정

  • suid,sgid, 특권

  • 사용 사례에 따라 제외를 포함하여 열려 있는 모든 파일 설명자를 닫습니다.

  • 예를 들어 이미 확립된 컨텍스트 내에서 기동했을 경우, 올바르게 동작한다.init,inetd 등등.

  • 적절한 데몬 동작을 위해 신호 핸들러를 설정하지만 사용 사례에 따라 결정된 특정 핸들러도 설정한다.

  • stdin,stdout,stderr 가 없기

  • PID 파일을 공동 어드바이저리 잠금으로 처리한다.이것은 그 자체로 모순되지만 유효한 많은 방법으로 동작하는 웜의 전체 캔이다.

  • 프로세스가 종료되었을 때 적절한 청소가 가능하다

  • 실제로 좀비로 이어지지 않고 데몬 프로세스가 된다

이들 중 일부는 표준 Unix 문헌(고 W. Richard Stevens, Adison-Wesley, 1992년 UNIX 환경에서의 Advanced Programming)에서 기술된 바와 같이 표준입니다.스트림 리다이렉션 및 PID 파일 처리와 같은 다른 것들은 대부분의 데몬 사용자가 예상할 수 있는 일반적인 동작이지만 표준화되지 않았습니다.

이 모든 것은 PEP 3143 "Standard daemon process library" 사양의 적용을 받습니다.Python-daemon 참조 구현은 Python 2.7 이상 및 Python 3.2 이상에서 작동합니다.

새로운 데몬 어플리케이션을 개발할 때 사용하는 기본적인 'Howdy World' Python 데몬입니다.

#!/usr/bin/python
import time
from daemon import runner

class App():
    def __init__(self):
        self.stdin_path = '/dev/null'
        self.stdout_path = '/dev/tty'
        self.stderr_path = '/dev/tty'
        self.pidfile_path =  '/tmp/foo.pid'
        self.pidfile_timeout = 5
    def run(self):
        while True:
            print("Howdy!  Gig'em!  Whoop!")
            time.sleep(10)

app = App()
daemon_runner = runner.DaemonRunner(app)
daemon_runner.do_action()

」가하게 되는 것에 해 주세요.python-daemon이치하다

pip install python-daemon

그냥 럼럼으로 하세요../howdy.py start../howdy.py stop.

다른 방법으로는 데몬화되지 않은 일반 Python 프로그램을 만든 후 슈퍼바이저를 사용하여 외부에서 데몬화 합니다.이것은 많은 두통을 줄일 수 있고 *nix-language-portable입니다.

python-daemon 패키지는 데몬 뒤에 있는 많은 문제를 즉시 해결합니다.

(Debian 패키지의 설명에서) 를 유효하게 하는 다른 기능:

  • 프로세스를 자체 프로세스 그룹으로 분리합니다.
  • chroot 내에서 실행하기에 적합한 프로세스 환경을 설정합니다.
  • suid 및 sgid 권한을 포기합니다.
  • 열려 있는 모든 파일 기술자를 닫습니다.
  • 작업 디렉토리, uid, gid 및 umask를 변경합니다.
  • 적절한 신호 핸들러를 설정합니다.
  • stdin, stdout 및 stderr의 새 파일 기술자를 엽니다.
  • 지정된 PID 잠금 파일을 관리합니다.
  • at-exit 처리를 위한 정리 기능을 등록합니다.

질문에 대한 직접적인 답변은 아닐 수 있지만 systemd를 사용하여 애플리케이션을 데몬으로 실행할 수 있습니다.다음은 예를 제시하겠습니다.

[Unit]
Description=Python daemon
After=syslog.target
After=network.target

[Service]
Type=simple
User=<run as user>
Group=<run as group group>
ExecStart=/usr/bin/python <python script home>/script.py

# Give the script some time to startup
TimeoutSec=300

[Install]
WantedBy=multi-user.target

많은 작업이 완료되고 데몬 스크립트가 시스템의 나머지 부분과 동일하게 동작하기 때문에 이 방법을 선호합니다.

이 함수는 응용 프로그램을 데몬으로 변환합니다.

import sys
import os

def daemonize():
    try:
        pid = os.fork()
        if pid > 0:
            # exit first parent
            sys.exit(0)
    except OSError as err:
        sys.stderr.write('_Fork #1 failed: {0}\n'.format(err))
        sys.exit(1)
    # decouple from parent environment
    os.chdir('/')
    os.setsid()
    os.umask(0)
    # do second fork
    try:
        pid = os.fork()
        if pid > 0:
            # exit from second parent
            sys.exit(0)
    except OSError as err:
        sys.stderr.write('_Fork #2 failed: {0}\n'.format(err))
        sys.exit(1)
    # redirect standard file descriptors
    sys.stdout.flush()
    sys.stderr.flush()
    si = open(os.devnull, 'r')
    so = open(os.devnull, 'w')
    se = open(os.devnull, 'w')
    os.dup2(si.fileno(), sys.stdin.fileno())
    os.dup2(so.fileno(), sys.stdout.fileno())
    os.dup2(se.fileno(), sys.stderr.fileno())

YapDi는 python 패키지입니다.스크립트 내부에서 python 스크립트를 데몬 모드로 변환하는 데 사용할 수 있습니다.

python-daemon은 아직 python 3.x를 지원하지 않기 때문에 메일링 리스트에서 읽을 수 있는 것을 통해 PEP 3143의 새로운 구현을 작성했습니다.pep3143 daemon

pep3143g는 적어도 python 2.6, 2.7 및 3.x를 지원해야 합니다.

PidFile 클래스도 포함되어 있습니다.

라이브러리는 표준 라이브러리와 6개의 모듈에만 의존합니다.

python-daemon 대체품으로 사용할 수 있습니다.

여기 서류가 있습니다.

유감스럽게도 @Dustin이 말한 데몬 모듈이 작동하지 않았습니다.대신 python-daemon을 설치하고 다음 코드를 사용했습니다.

# filename myDaemon.py
import sys
import daemon
sys.path.append('/home/ubuntu/samplemodule') # till __init__.py
from samplemodule import moduleclass 

with daemon.DaemonContext():
    moduleclass.do_running() # I have do_running() function and whatever I was doing in __main__() in module.py I copied in it.

달리기는 쉽다

> python myDaemon.py

완전성을 위해 여기 샘플모듈 디렉토리의 내용을 나타냅니다.

>ls samplemodule
__init__.py __init__.pyc moduleclass.py

moduleclass.py의 콘텐츠는 다음과 같습니다.

class moduleclass():
    ...

def do_running():
    m = moduleclass()
    # do whatever daemon is required to do.

python에서 데몬화할 때 고려해야 할 또 다른 사항:

에서 python 로깅을 사용하고 있으며 데몬화 후에도 계속 사용하고 싶은 경우에는 반드시 다음 주소로 문의해 주십시오.close()핸들러(특히 파일핸들러)에 접속합니다.

이렇게 하지 않으면 핸들러는 파일이 열려 있다고 생각할 수 있으며, 메시지는 단순히 사라집니다. 즉, 로거가 파일이 닫혀 있는지 확인하십시오.

이 경우 열려 있는 모든 파일 기술자를 무차별적으로 닫을 때 로그 파일을 제외한 모든 파일을 닫을 수 있다고 가정합니다(단, 일반적으로 원하는 파일을 모두 닫은 후 다시 여는 것이 더 쉽습니다).

python-daemon 모듈에 의해 제공되는 순수 Python 솔루션을 선호할 수 있지만,daemon(3)에서 기능하다.libc적어도 BSD나 Linux 에서는요.그렇게 하면, 올바르게 동작합니다.

python에서 호출하는 것은 간단합니다.

import ctypes

ctypes.CDLL(None).daemon(0, 0) # Read the man-page for the arguments' meanings

이제 해야 할 일은 PID 파일의 작성(및 잠금)뿐입니다.하지만 네가 알아서 할 수 있다는 건...

Sander Marechal의 코드 샘플에서 몇 줄을 수정했습니다(승인된 답변에서 @JeffBauer에 의해 언급됨).quit()데몬이 정지하기 전에 실행되는 메서드.이것은 때때로 매우 유용합니다.

여기 있어요.

주의: 설명서가 아직 없고(다른 SO 질문도 많이 참조) 불분명하기 때문에(이 모듈에서 데몬을 올바르게 시작/정지하는 방법) "python-daemon" 모듈을 사용하지 않습니다.

몇 년 동안 여러 번 시도해 본 결과(여기서 제시한 모든 답변을 시도해 보았지만, 모두 마지막에 사소한 결점이 있었습니다) 이제 Python에서 직접 데몬을 시작, 중지, 재시작하는 것보다 더 나은 방법이 있다는 것을 알게 되었습니다. 대신 OS 도구를 사용하십시오.

예를 들어 리눅스의 경우python myapp start그리고.python myapp stop앱을 기동하려면 , 다음과 같이 합니다.

screen -S myapp python myapp.py    
# CTRL+A, D to detach

또는screen -dmS myapp python myapp.py명령어 하나로 시작분리할 수 있습니다.

그 후, 다음과 같이 입력합니다.

screen -r myapp

이 단말기에 다시 접속합니다.터미널에 들어가면 CTRL+C를 사용하여 중지할 수 있습니다.

Python으로 데몬을 만드는 가장 쉬운 방법은 Twisted 이벤트 구동 프레임워크를 사용하는 것입니다.데몬화에 필요한 모든 작업을 처리합니다.Reactor Pattern을 사용하여 동시 요청을 처리합니다.

80%의 경우, 「실행」이라고 하면, 서버만을 필요로 합니다.이 점에 대한 질문은 완전히 불분명하기 때문에, 가능한 답의 영역이 무엇이라고 말하는 것은 어렵다.서버는 충분하므로 거기서부터 시작합니다.드문 경우), 「대몬」으로 .nohup서버를 데몬화하는 방법으로 사용됩니다.

실제 데몬이 실제로 필요할 때까지 단순한 서버를 작성합니다.

, WSGI 레퍼런스 실장에 대해서도 설명합니다.

Simple HTTP Server도 확인합니다.

"또 고려해야 할 사항이 있습니까?네, 백만 가지 정도요무슨 프로토콜?몇 명이나 요청하셨죠?각 요청에 대한 서비스 기간은 얼마나 됩니까?얼마나 자주 도착합니까?전용 프로세스를 사용하시겠습니까?스레드?서브프로세스?데몬을 쓰는 것은 큰 일이다.

언급URL : https://stackoverflow.com/questions/473620/how-do-you-create-a-daemon-in-python

반응형