Handler for counting notifications statuses added
For calculation of notifications statuses we made requests in the UI and fetch all notifications data and process them on the UI side. We want to replace a polling of the whole notification collection by a polling of unread notifications number. This dramatically decrease Fuel UI load in case of a big amount of notifications. Change-Id: I8f83d4e2d7f58beaf06c489b2264ccb69f9927ce Partial-Bug: #1657348
This commit is contained in:
parent
0cabf795b5
commit
d4bf85957e
|
@ -59,3 +59,33 @@ class NotificationCollectionHandler(CollectionHandler):
|
|||
self.collection.single.update(notif, nd)
|
||||
notifications_updated.append(notif)
|
||||
return self.collection.to_list(notifications_updated)
|
||||
|
||||
|
||||
class NotificationCollectionStatsHandler(CollectionHandler):
|
||||
|
||||
collection = objects.NotificationCollection
|
||||
validator = NotificationValidator
|
||||
|
||||
@handle_errors
|
||||
@validate
|
||||
@serialize
|
||||
def GET(self):
|
||||
"""Calculates notifications statuses
|
||||
|
||||
Counts all presented notifications in the DB and returns dict
|
||||
with structure {'total': count, 'unread': count, ...}
|
||||
|
||||
:returns: dict with notifications statuses count
|
||||
|
||||
:http: * 200 (OK)
|
||||
"""
|
||||
return self.collection.single.get_statuses_with_count()
|
||||
|
||||
@handle_errors
|
||||
@validate
|
||||
def POST(self):
|
||||
"""Update notification statuses is not allowed
|
||||
|
||||
:http: * 405 (Method not allowed)
|
||||
"""
|
||||
raise self.http(405)
|
||||
|
|
|
@ -86,6 +86,8 @@ from nailgun.api.v1.handlers.plugin_link import PluginLinkCollectionHandler
|
|||
from nailgun.api.v1.handlers.plugin_link import PluginLinkHandler
|
||||
|
||||
from nailgun.api.v1.handlers.notifications import NotificationCollectionHandler
|
||||
from nailgun.api.v1.handlers.notifications import \
|
||||
NotificationCollectionStatsHandler
|
||||
from nailgun.api.v1.handlers.notifications import NotificationHandler
|
||||
|
||||
from nailgun.api.v1.handlers.orchestrator import DefaultDeploymentInfo
|
||||
|
@ -336,6 +338,8 @@ urls = (
|
|||
NotificationCollectionHandler,
|
||||
r'/notifications/(?P<obj_id>\d+)/?$',
|
||||
NotificationHandler,
|
||||
r'/notifications/stats/?$',
|
||||
NotificationCollectionStatsHandler,
|
||||
|
||||
r'/dump/(?P<snapshot_name>[A-Za-z0-9-_.]+)$',
|
||||
SnapshotDownloadHandler,
|
||||
|
|
|
@ -16,17 +16,17 @@
|
|||
|
||||
from datetime import datetime
|
||||
|
||||
from nailgun.db.sqlalchemy import models
|
||||
from sqlalchemy import func
|
||||
|
||||
from nailgun import consts
|
||||
from nailgun.db import db
|
||||
from nailgun.db.sqlalchemy import models
|
||||
from nailgun import errors
|
||||
from nailgun.logger import logger
|
||||
|
||||
from nailgun.objects import NailgunCollection
|
||||
from nailgun.objects import NailgunObject
|
||||
|
||||
from nailgun.objects import Task
|
||||
|
||||
from nailgun.objects.serializers.notification import NotificationSerializer
|
||||
from nailgun.objects import Task
|
||||
|
||||
|
||||
class Notification(NailgunObject):
|
||||
|
@ -87,6 +87,24 @@ class Notification(NailgunObject):
|
|||
notif_dict['date'] = instance.datetime.strftime('%d-%m-%Y')
|
||||
return notif_dict
|
||||
|
||||
@classmethod
|
||||
def get_statuses_with_count(cls):
|
||||
"""Counts notifications statuses in DB
|
||||
|
||||
Calculates number of notifications and adds total count to the
|
||||
result. All notifications statuses described in the
|
||||
consts.NOTIFICATION_STATUSES will be present in the result.
|
||||
|
||||
:return: dict with structure {'total': count, 'unread': count, ...}
|
||||
"""
|
||||
result = dict.fromkeys(consts.NOTIFICATION_STATUSES, 0)
|
||||
query = db().query(cls.model.status, func.count(cls.model.status)).\
|
||||
group_by(cls.model.status)
|
||||
for status, num in query.all():
|
||||
result[status] = num
|
||||
result['total'] = sum(result.values())
|
||||
return result
|
||||
|
||||
|
||||
class NotificationCollection(NailgunCollection):
|
||||
|
||||
|
|
|
@ -101,3 +101,42 @@ class TestHandlers(BaseIntegrationTest):
|
|||
expect_errors=True
|
||||
)
|
||||
self.assertEqual(404, resp.status_code)
|
||||
|
||||
def test_get_notification_status(self):
|
||||
resp = self.app.get(
|
||||
reverse(
|
||||
'NotificationCollectionStatsHandler',
|
||||
),
|
||||
headers=self.default_headers
|
||||
)
|
||||
self.assertEqual({'total': 0, 'read': 0, 'unread': 0}, resp.json_body)
|
||||
self.assertEqual(200, resp.status_code)
|
||||
|
||||
self.env.create_notification()
|
||||
resp = self.app.get(
|
||||
reverse(
|
||||
'NotificationCollectionStatsHandler',
|
||||
),
|
||||
headers=self.default_headers
|
||||
)
|
||||
self.assertEqual({'total': 1, 'read': 0, 'unread': 1}, resp.json_body)
|
||||
|
||||
self.env.create_notification(status='read')
|
||||
self.env.create_notification(status='read')
|
||||
resp = self.app.get(
|
||||
reverse(
|
||||
'NotificationCollectionStatsHandler',
|
||||
),
|
||||
headers=self.default_headers
|
||||
)
|
||||
self.assertEqual({'total': 3, 'read': 2, 'unread': 1}, resp.json_body)
|
||||
|
||||
def test_notification_statuses_post_not_allowed(self):
|
||||
resp = self.app.post(
|
||||
reverse(
|
||||
'NotificationCollectionStatsHandler',
|
||||
),
|
||||
headers=self.default_headers,
|
||||
expect_errors=True
|
||||
)
|
||||
self.assertEqual(405, resp.status_code)
|
||||
|
|
Loading…
Reference in New Issue