Pergunta

Estou tentando usar atexit em um Process, mas infelizmente não parece funcionar. Aqui está algum código de exemplo:

import time
import atexit
import logging
import multiprocessing

logging.basicConfig(level=logging.DEBUG)

class W(multiprocessing.Process):
    def run(self):
        logging.debug("%s Started" % self.name)

        @atexit.register
        def log_terminate():
             # ever called?
             logging.debug("%s Terminated!" % self.name)

        while True:
            time.sleep(10)

@atexit.register
def log_exit():
    logging.debug("Main process terminated")

logging.debug("Main process started")

a = W()
b = W()
a.start()
b.start()
time.sleep(1)
a.terminate()
b.terminate()

A saída deste código é:

DEBUG:root:Main process started
DEBUG:root:W-1 Started
DEBUG:root:W-2 Started
DEBUG:root:Main process terminated

Eu esperaria que o W.run.log_terminate() seria chamado quando a.terminate() e b.terminate() são chamados, e a saída para ser algo gosta (ênfase adicionada)!:

DEBUG:root:Main process started
DEBUG:root:W-1 Started
DEBUG:root:W-2 Started
Debug: raiz: W-1 terminado! Debug: Raiz: W-2 terminou!
DEBUG:root:Main process terminated

Por que isso não está funcionando e existe uma maneira melhor de registrar uma mensagem (do Process contexto) quando um Process Está terminado?

Obrigado por sua opinião - é muito apreciado.

Solução

EDITAR: Com base na solução sugerida por Alex Martelli, os seguintes trabalhos conforme o esperado:

import sys
import time
import atexit
import signal
import logging
import multiprocessing

logging.basicConfig(level=logging.DEBUG)

class W(multiprocessing.Process):
    def run(self):
        logging.debug("%s Started" % self.name)

        def log_terminate(num, frame):
             logging.debug("%s Terminated" % self.name)
             sys.exit()
        signal.signal(signal.SIGTERM, log_terminate)
        while True:
            time.sleep(10)

@atexit.register
def log_exit():
    logging.debug("Main process terminated")

logging.debug("Main process started")
a = W()
b = W()
a.start()
b.start()
time.sleep(1)
a.terminate()
b.terminate()

Vale a pena notar o seguinte comentário no ATEXIT documentação:

Nota: As funções registradas através deste módulo não são chamadas quando o programa é morto por um sinal, quando um erro interno fatal python é detectado ou quando o OS._Exit () é chamado.
Foi útil?

Solução

Eu resolvi o problema sozinho.

Thet Solution foi simples.Depois que eu atualizei o banco de dados manualmente.Eu reiniciei o mago novamente e depois disso ainda funciona.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top