django-xadmin中APScheduler的啟動初始化


環境: python3.5.x + django1.9.x +  xadmin-for-python3

APScheduler做為一個輕量級和使用量很多的后台任務計划(scheduler)包,可以方便的隨系統啟動/關閉而啟動/關閉,如果整合到django中,啟動APScheduler的代碼該寫在哪里好呢,以下幾個方式供參考:

1. (推薦)自定義Middleware,非常類似Java中的Filter,缺點是要有URL訪問才會觸發啟動,如果系統還沒有啟動完就訪問了URL會觸發__init__多次調用(多次http同時請求造成),可以通過threading的lock同步代碼和狀態限制執行一次

class StartupMiddleware(object):
    def __init__(self):
        #啟動后台任務APScheduler
        init_scheduler()

        from django.core.exceptions import  MiddlewareNotUsed
        raise MiddlewareNotUsed #TIP 拋出此異常,則Django將從 middleware 棧中移出該 middleware,請求就不會經過此middleware

    def process_request(self, request):
        print("*****enter startup middleware")

 

scheduler = None
def init_scheduler():
    global scheduler
    lock = threading.Lock()  # TIP 多線程同步代碼
    with lock:
        if scheduler and scheduler.running:
            print('*****APScheduler is already started, pid:{}, tid:{}'.format(os.getpid(), threading.current_thread().getName()))
            return scheduler
        executors = {
            'default': ThreadPoolExecutor(5),#線程模式下進程池大小
            'processpool': ProcessPoolExecutor(5),#進程模式下進程池大小
        }
        job_defaults = {
            'coalesce': True, #如果有幾次未執行,條件可以時是否只執行一次
            'max_instances': 1, #同一個job同一時間最多有幾個實例再跑
        }

        scheduler = BackgroundScheduler(executors=executors, job_defaults=job_defaults, timezone=timezone(TIME_ZONE))

        scheduler.add_job(...)
        scheduler.start()
        return scheduler

 

2. 應用中的settings.py文件,django在開發環境默認會啟動兩個python進程(對於開發環境還是很實用的,改代碼后會自動重啟),放settings.py中的代碼會被這兩個python進程都調用一次,當然可以通過--reload參數只啟動一個python進程,另外加載settings.py時部分app還未loaded,限制了應用的代碼。

 

3. 頂層的urls文件, 這個不管你django啟動時是一個進程還是兩個進程,urls文件也只會被加載一次,但存在的缺陷就是在執行makemigrations這樣的命令時,會同樣出現app還未loaded的錯...

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM