U api update

pull/22/head
vapao 2020-01-15 16:04:40 +08:00
parent 5632ed1ea7
commit 980bef2d83
8 changed files with 121 additions and 12 deletions

View File

@ -2,10 +2,12 @@ from apscheduler.schedulers.background import BackgroundScheduler
from apscheduler.triggers.interval import IntervalTrigger
from apscheduler import events
from django_redis import get_redis_connection
from django.utils.functional import SimpleLazyObject
from apps.monitor.models import Detection
from apps.alarm.models import Alarm
from apps.monitor.executors import dispatch
from apps.monitor.utils import seconds_to_human
from apps.notify.models import Notify
from django.conf import settings
from libs import AttrDict, human_datetime
import logging
@ -13,6 +15,7 @@ import json
import time
logger = logging.getLogger("django.apps.monitor")
counter = dict()
class Scheduler:
@ -46,16 +49,36 @@ class Scheduler:
logger.info(f'{human_datetime()} notify job_id: {obj.id}')
def _handle_event(self, event):
# TODO: notify to user
obj = SimpleLazyObject(lambda: Detection.objects.filter(pk=event.job_id).first())
if event.code == events.EVENT_SCHEDULER_SHUTDOWN:
logger.info(f'EVENT_SCHEDULER_SHUTDOWN: {event}')
if event.code == events.EVENT_JOB_MAX_INSTANCES:
Notify.objects.create(
title='调度器已关闭',
source='monitor',
content='调度器意外关闭你可以在github上提交issue',
type='1',
)
elif event.code == events.EVENT_JOB_MAX_INSTANCES:
logger.info(f'EVENT_JOB_MAX_INSTANCES: {event}')
if event.code == events.EVENT_JOB_ERROR:
if time.time() - counter.get(event.job_id, time.time()) > 3600:
counter[event.job_id] = time.time()
Notify.objects.create(
title=f'{obj.name} - 达到调度实例上限',
source='monitor',
content='一般为上个周期的执行任务还未结束,请增加调度间隔或减少任务执行耗时',
type='1',
)
elif event.code == events.EVENT_JOB_ERROR:
logger.info(f'EVENT_JOB_ERROR: job_id {event.job_id} exception: {event.exception}')
if event.code == events.EVENT_JOB_MISSED:
logger.info(f'EVENT_JOB_MISSED: job_id {event.job_id}')
if event.code == events.EVENT_JOB_EXECUTED:
if time.time() - counter.get(event.job_id, time.time()) > 3600:
counter[event.job_id] = time.time()
Notify.objects.create(
title=f'{obj.name} - 执行异常',
source='monitor',
content=f'{event.exception}',
type='1',
)
elif event.code == events.EVENT_JOB_EXECUTED:
obj = Detection.objects.filter(pk=event.job_id).first()
old_status = obj.latest_status
obj.latest_status = 0 if event.retval else 1

View File

View File

@ -0,0 +1,28 @@
from django.db import models
from libs import ModelMixin, human_datetime
class Notify(models.Model, ModelMixin):
TYPES = (
('1', '通知'),
('2', '待办'),
)
SOURCES = (
('monitor', '监控中心'),
('schedule', '任务计划'),
)
title = models.CharField(max_length=255)
source = models.CharField(max_length=10, choices=SOURCES)
type = models.CharField(max_length=2, choices=TYPES)
content = models.CharField(max_length=255, null=True)
unread = models.BooleanField(default=True)
link = models.CharField(max_length=255, null=True)
created_at = models.CharField(max_length=20, default=human_datetime)
def __repr__(self):
return '<Notify %r>' % self.title
class Meta:
db_table = 'notifies'
ordering = ('-id',)

View File

@ -0,0 +1,7 @@
from django.urls import path
from .views import *
urlpatterns = [
path('', NotifyView.as_view()),
]

View File

@ -0,0 +1,17 @@
from django.views.generic import View
from apps.notify.models import Notify
from libs import json_response, JsonParser, Argument
class NotifyView(View):
def get(self, request):
notifies = Notify.objects.filter(unread=True)
return json_response(notifies)
def patch(self, request):
form, error = JsonParser(
Argument('id', type=int, help='参数错误')
).parse(request.body)
if error is None:
Notify.objects.filter(pk=form.id).update(unread=False)
return json_response(error=error)

View File

@ -3,15 +3,19 @@ from apscheduler.triggers.interval import IntervalTrigger
from apscheduler.triggers.date import DateTrigger
from apscheduler import events
from django_redis import get_redis_connection
from django.utils.functional import SimpleLazyObject
from apps.schedule.models import Task
from apps.notify.models import Notify
from apps.schedule.executors import dispatch
from apps.alarm.utils import auto_clean_records
from django.conf import settings
from libs import AttrDict, human_datetime
import logging
import json
import time
logger = logging.getLogger("django.apps.scheduler")
counter = dict()
class Scheduler:
@ -31,16 +35,36 @@ class Scheduler:
raise TypeError(f'unknown schedule policy: {trigger!r}')
def _handle_event(self, event):
# TODO: notify to user
obj = SimpleLazyObject(lambda: Task.objects.filter(pk=event.job_id).first())
if event.code == events.EVENT_SCHEDULER_SHUTDOWN:
logger.info(f'EVENT_SCHEDULER_SHUTDOWN: {event}')
if event.code == events.EVENT_JOB_MAX_INSTANCES:
Notify.objects.create(
title='调度器已关闭',
source='schedule',
content='调度器意外关闭你可以在github上提交issue',
type='1',
)
elif event.code == events.EVENT_JOB_MAX_INSTANCES:
logger.info(f'EVENT_JOB_MAX_INSTANCES: {event}')
if event.code == events.EVENT_JOB_ERROR:
if time.time() - counter.get(event.job_id, 0) > 3600:
counter[event.job_id] = time.time()
Notify.objects.create(
title=f'{obj.name} - 达到调度实例上限',
source='schedule',
content='一般为上个周期的执行任务还未结束,请增加调度间隔或减少任务执行耗时',
type='1',
)
elif event.code == events.EVENT_JOB_ERROR:
logger.info(f'EVENT_JOB_ERROR: job_id {event.job_id} exception: {event.exception}')
if event.code == events.EVENT_JOB_MISSED:
logger.info(f'EVENT_JOB_MISSED: job_id {event.job_id}')
if event.code == events.EVENT_JOB_EXECUTED:
if time.time() - counter.get(event.job_id, 0) > 3600:
counter[event.job_id] = time.time()
Notify.objects.create(
title=f'{obj.name} - 执行异常',
source='schedule',
content=f'{event.exception}',
type='1',
)
elif event.code == events.EVENT_JOB_EXECUTED:
if event.retval:
score = 0
for item in event.retval:
@ -50,6 +74,14 @@ class Scheduler:
latest_run_time=human_datetime(event.scheduled_run_time),
latest_output=json.dumps(event.retval)
)
if score != 0 and time.time() - counter.get(event.job_id, 0) > 3600:
counter[event.job_id] = time.time()
Notify.objects.create(
title=f'{obj.name} - 执行失败',
source='schedule',
content='请在任务计划中查看失败详情',
type='1',
)
def _init_builtin_jobs(self):
self.scheduler.add_job(auto_clean_records, 'cron', hour=0, minute=0)

View File

@ -41,6 +41,7 @@ INSTALLED_APPS = [
'apps.config',
'apps.app',
'apps.deploy',
'apps.notify',
]
MIDDLEWARE = [

View File

@ -27,5 +27,6 @@ urlpatterns = [
path('app/', include('apps.app.urls')),
path('deploy/', include('apps.deploy.urls')),
path('home/', include('apps.home.urls')),
path('notify/', include('apps.notify.urls')),
path('apis/', include('apps.apis.urls')),
]