3

我一直试图让 uwsgi python spooler 正常工作很长一段时间。我有一个设置,我在其中运行一个带有两个工作进程的 django 应用程序。我已经尝试设置一个 cron spooler(和一个 timer spooler)以每十分钟运行一次任务,但无论我尝试了何种设置配置,它似乎总是多次注册信号,并多次运行任务。

这就是我运行 uwsgi 的方式:

#!/bin/bash
sudo uwsgi --emperor /etc/uwsgi/vassals --uid http --gid http --enable-threads --pidfile=/tmp/uwsgi.pid --daemonize=/var/log/uwsgi/uwsgi.log

这是我在 /etc/uwsgi/vassals/django.ini 中的 uwsgi vassal 配置:

[uwsgi]

chdir           = /home/user/django
module          = django.wsgi

master          = true
processes       = 2
socket          = /tmp/uwsgi-django.sock
vacuum          = true
pidfile         = /tmp/uwsgi-django.pid
daemonize      = /home/user/django/log.log
env = DJANGO_SETTINGS_MODULE=django.settings
#lazy-apps = false
#lazy = false
spooler = %(chdir)/tasks
#spooler-processes = 1
#import = django-app/spooler.py
#spooler-import = django-app/spooler.py
shared-import = django-app/spooler.py

(出于隐私原因,我更改了一些路径名)。注释掉的行是各种尝试使其不重复我的信号,但每次似乎都注册信号两次,有时甚至三次(大概在工作人员和单个假脱机进程中)。

[uwsgi-signal] signum 0 registered (wid: 0 modifier1: 0 target: default, any worker)
[uwsgi-signal] signum 1 registered (wid: 1 modifier1: 0 target: default, any worker)
[uwsgi-signal] signum 1 registered (wid: 2 modifier1: 0 target: default, any worker)

有谁知道为什么会发生这种情况,以及如何正确预防?

这是 spooler.py 文件:

@cron(-10, -1, -1, -1, -1)
def periodicUpdate(signal):
    print "Running cron job..."
    _getStats()

也试过

@timer(600)
def periodicUpdate(signal):
    print "Running cron job..."
    _getStats()

我也尝试添加target='spooler'到计时器/cron-decorator,但它似乎并没有什么区别。

4

2 回答 2

3

您确定没有在 django.wsgi、settings.py 或其他 django 相关文件中注册其他信号吗?--shared-import 只会加载一次(在主服务器中)。

顺便说一句,我没有得到你想要完成的事情。这不是假脱机程序的工作方式,即使您想将其用作信号处理程序目标,您也必须在注册信号时指定它(在装饰器中使用 target='spooler')

于 2014-01-21T03:21:20.497 回答
0

虽然这是一个老问题,但我在其他地方找不到答案。我将此解决方案与 Flask 一起使用,但它应该与 Django 类似。

在初始化(prefork 模式)期间,您需要注册一个信号。

uwsgi.register_signal(26, "spooler", periodicUpdate)

那么计时器应该是这样的:

@timer(600, target='spooler')
def periodicUpdate(signal):
    print "Running cron job..."
    _getStats()

至于评论:

错误“只有主人和工人可以注册信号处理程序”是正确的,因为您没有注册任何信号。

与问题

'每当我在我的 django 应用程序中加载其中一个页面时,它都会重新注册它'

可能会发生,因为它的工作人员正在调用该方法(periodicUpdate)一次。这就是为什么必须在产生工人之前注册信号的原因。

于 2022-01-12T16:04:04.370 回答