Aipo com Upstart - processos estão morrendo inesperadamente

2

Quando eu estou executando o Celery com Upstart, depois de um tempo, o filho processa ou os principais processos morrem sem nenhum traço.

O script Upstart que estou usando ( /etc/init/celery ):

description "celery"

start on runlevel [2345]
stop on runlevel [!2345]

kill timeout 20
# console log
setuid ***
setgid ***

script
chdir /opt/***/project/
exec /opt/***/virtualenvs/***/bin/python manage.py celery worker --settings=settings.staging -B -c 4 -l DEBUG
end script

respawn

Ao executar exatamente o mesmo comando sem o upstart (executando manualmente o exec part), tudo funciona bem.

Com a sub-rotina respawn , o processo mestre morrerá e será recuperado enquanto os processos filhos perdidos ainda existirem, causando sobrecargas de memória. Sem isso, os processos simplesmente desaparecerão até que não haja mais trabalhadores.

O aipo gera um processo mestre e processos de trabalho (4 deles neste caso). Também tentei executá-lo com eventlet em vez de multiprocessamento (1 mestre, 1 processo filho), mas os resultados são semelhantes.

Alguém encontrou tal comportamento antes?

Atualização:

  • O aipo quando executado com -c N começa com N + 2 processos, N dos quais são trabalhadores (quais são os outros 2?).
  • Estou começando a achar que isso está relacionado à estrofe expect , mas não tenho certeza qual deve ser o valor. Com eventlet expect fork faz sentido. Mas e o multiprocessamento?

Update2:

Usar except fork pareceu impedir o processamento de morrer, mas ao tentar parar ou reiniciar o trabalho, ele simplesmente parou.

    
por yprez 25.09.2013 / 18:42

2 respostas

5

Usar o chdir dentro da cláusula script está totalmente errado, e isso significa que você não consegue entender uma idéia muito básica no início (sem ofensa significava). (Como uma nota lateral, a palavra-chave exec é apenas inútil, mas não causa nenhum dano).

Existe uma ideia muito central para entender como funciona o upstart. O Upstart tenta determinar qual processo dos processos gerados pela sub-rotina script é o daemon real desse serviço. Em seguida, ele usa esse processo para determinar se esse trabalho está em execução ou interrompido ou com falha ou o que for. Por esse motivo, é de suma importância garantir que o processo esteja correto.

O algoritmo para determinar o processo é muito simples, depende da estrofe expect . expect fork significa "pegue a segunda bifurcação na sub-rotina script ", expect daemon - mesmo, mas a terceira.

Agora, usar chdir dentro de script significa que ele chama o binário real /bin/chdir e isso conta como uma bifurcação separada. O que você precisa fazer é movê-lo para fora da sub-rotina script e então jogar com a sub-rotina expect até acertar. Você pode verificar se acertou comparando a saída de initctl status celery com ps . Os PIDs devem corresponder.

    
por 06.02.2014 / 23:29
5

A solução não foi para executar a batida de aipo junto com o trabalhador (removendo a parte -B do comando exec).

Aparentemente, esse foi o processo "extra" e, de alguma forma, atrapalhou as coisas.

Aqui está o script final com o qual acabei:

description "celery"

start on started postgresql
stop on runlevel [!2345]

kill timeout 20
setuid ***
setgid ***
respawn

chdir /opt/***/project/
exec /opt/***/virtualenvs/***/bin/python manage.py celery worker --settings=settings.staging -c 4 -l DEBUG

e executando celery beat separadamente:

description "celerybeat"

start on started celery
stop on stopped celery

setuid ***
setgid ***
respawn

chdir /opt/***/project/
exec /opt/***/virtualenvs/***/bin/python manage.py celery beat --settings=settings.staging -l DEBUG
    
por 29.09.2013 / 15:55