API notifications

This commit is contained in:
Ruud
2013-05-03 14:07:23 +02:00
parent 91c45bad71
commit 4cba44fbb1
5 changed files with 108 additions and 45 deletions

View File

@@ -18,6 +18,7 @@ class Notification(Provider):
listen_to = [
'renamer.after', 'movie.snatched',
'updater.available', 'updater.updated',
'core.message',
]
dont_listen_to = []

View File

@@ -1,12 +1,13 @@
from couchpotato import get_session
from couchpotato.api import addApiView, addNonBlockApiView
from couchpotato.core.event import addEvent
from couchpotato.core.event import addEvent, fireEvent
from couchpotato.core.helpers.encoding import toUnicode
from couchpotato.core.helpers.request import jsonified, getParam
from couchpotato.core.helpers.variable import tryInt, splitString
from couchpotato.core.logger import CPLog
from couchpotato.core.notifications.base import Notification
from couchpotato.core.settings.model import Notification as Notif
from couchpotato.environment import Env
from sqlalchemy.sql.expression import or_
import threading
import time
@@ -21,11 +22,6 @@ class CoreNotifier(Notification):
messages = []
listeners = []
listen_to = [
'renamer.after', 'movie.snatched',
'updater.available', 'updater.updated',
]
def __init__(self):
super(CoreNotifier, self).__init__()
@@ -54,7 +50,10 @@ class CoreNotifier(Notification):
addNonBlockApiView('notification.listener', (self.addListener, self.removeListener))
addApiView('notification.listener', self.listener)
fireEvent('schedule.interval', 'core.check_messages', self.checkMessages, hours = 12, single = True)
addEvent('app.load', self.clean)
addEvent('app.load', self.checkMessages)
def clean(self):
@@ -112,6 +111,23 @@ class CoreNotifier(Notification):
'notifications': notifications
})
def checkMessages(self):
prop_name = 'messages.last_check'
last_check = tryInt(Env.prop(prop_name, default = 0))
messages = fireEvent('cp.messages', last_check = last_check, single = True)
last_time = 0
for message in messages:
if message.get('time') > last_check:
fireEvent('core.message', message = message.get('message'), data = message)
if last_time < message.get('time'):
last_time = message.get('time')
Env.prop(prop_name, value = last_time)
def notify(self, message = '', data = {}, listener = None):
db = get_session()

View File

@@ -44,14 +44,19 @@ var NotificationBase = new Class({
result.el = App.getBlock('notification').addLink(
new Element('span.'+(result.read ? 'read' : '' )).adopt(
new Element('span.message', {'text': result.message}),
new Element('span.message', {'html': result.message}),
new Element('span.added', {'text': added.timeDiffInWords(), 'title': added})
)
, 'top');
self.notifications.include(result);
if(!result.read)
if(result.data.important !== undefined && !result.read){
var sticky = true
App.fireEvent('message', [result.message, sticky, result])
}
else if(!result.read){
self.setBadge(self.notifications.filter(function(n){ return !n.read}).length)
}
},
@@ -61,20 +66,26 @@ var NotificationBase = new Class({
self.badge[value ? 'show' : 'hide']()
},
markAsRead: function(){
var self = this;
markAsRead: function(force_ids){
var self = this,
ids = force_ids;
var rn = self.notifications.filter(function(n){
return !n.read
})
if(!force_ids) {
var rn = self.notifications.filter(function(n){
return !n.read && n.data.important === undefined
})
var ids = []
rn.each(function(n){
ids.include(n.id)
})
var ids = []
rn.each(function(n){
ids.include(n.id)
})
}
if(ids.length > 0)
Api.request('notification.markread', {
'data': {
'ids': ids.join(',')
},
'onSuccess': function(){
self.setBadge('')
}
@@ -140,26 +151,41 @@ var NotificationBase = new Class({
self.startPoll()
},
showMessage: function(message){
showMessage: function(message, sticky, data){
var self = this;
if(!self.message_container)
self.message_container = new Element('div.messages').inject(document.body);
var new_message = new Element('div.message', {
'text': message
}).inject(self.message_container);
var new_message = new Element('div', {
'class': 'message' + (sticky ? ' sticky' : ''),
'html': message
}).inject(self.message_container, 'top');
setTimeout(function(){
new_message.addClass('show')
}, 10);
setTimeout(function(){
var hide_message = function(){
new_message.addClass('hide')
setTimeout(function(){
new_message.destroy();
}, 1000);
}, 4000);
}
if(sticky)
new_message.grab(
new Element('a.close.icon2', {
'events': {
'click': function(){
self.markAsRead([data.id]);
hide_message();
}
}
})
);
else
setTimeout(hide_message, 4000);
},

View File

@@ -2,6 +2,7 @@ from couchpotato import get_session
from couchpotato.core.event import addEvent, fireEvent
from couchpotato.core.helpers.encoding import tryUrlencode
from couchpotato.core.helpers.request import jsonified, getParams
from couchpotato.core.helpers.variable import tryInt
from couchpotato.core.logger import CPLog
from couchpotato.core.providers.movie.base import MovieProvider
from couchpotato.core.settings.model import Movie
@@ -20,6 +21,7 @@ class CouchPotatoApi(MovieProvider):
'eta': 'https://couchpota.to/api/eta/%s/',
'suggest': 'https://couchpota.to/api/suggest/',
'updater': 'https://couchpota.to/api/updater/?%s',
'messages': 'https://couchpota.to/api/messages/?%s',
}
http_time_between_calls = 0
api_version = 1
@@ -32,6 +34,15 @@ class CouchPotatoApi(MovieProvider):
addEvent('movie.is_movie', self.isMovie)
addEvent('cp.source_url', self.getSourceUrl)
addEvent('cp.messages', self.getMessages)
def getMessages(self, last_check = 0):
data = self.getJsonData(self.urls['messages'] % tryUrlencode({
'last_check': last_check,
}), headers = self.getRequestHeaders(), cache_timeout = 10)
return data
def getSourceUrl(self, repo = None, repo_name = None, branch = None):
return self.getJsonData(self.urls['updater'] % tryUrlencode({

View File

@@ -160,6 +160,7 @@ body > .spinner, .mask{
.icon2.eye-open:before { content: "\e09d"; }
.icon2.search:before { content: "\e03e"; }
.icon2.return-key:before { content: "\e111"; }
.icon2.close:before { content: "\e04e"; }
.icon2.menu:before {
content: "\e076 \e076 \e076";
line-height: 6px;
@@ -715,43 +716,51 @@ body > .spinner, .mask{
position: fixed;
right: 0;
bottom: 0;
padding: 2px;
width: 240px;
width: 320px;
z-index: 20;
overflow: hidden;
font-size: 14px;
font-weight: bold;
}
@media all and (max-width: 480px) {
.messages {
width: 100%;
}
}
.messages .message {
text-align: center;
border-radius: 2px;
margin: 2px 0 0 0;
height: 0;
overflow: hidden;
transition: all .6s cubic-bezier(0.9,0,0.1,1);
box-shadow: 0 1px 1px rgba(0,0,0,0.35), inset 0 1px 0px rgba(255,255,255,0.20);
background-image: linear-gradient(
180deg,
#5b9bd1 0%,
#406db8 100%
);
background: #5b9bd1;
width: 100%;
padding: 0 5px;
visibility: hidden;
position: relative;
margin: 1px 0 0;
max-height: 0;
padding: 0 30px 0 20px;
font-size: 1.1em;
font-weight: normal;
transform: scale(0);
}
.messages .message.sticky {
background-color: #c84040;
}
.messages .message.show {
visibility: visible;
height: auto;
padding-top: 3px;
padding-bottom: 3px;
min-height: 1px;
max-height: 400px;
max-height: 100px;
padding: 15px 30px 15px 20px;
transform: scale(1);
}
.messages .message.hide {
margin-left: 240px;
opacity: 0;
max-height: 0;
padding: 0 20px;
margin: 0;
transform: scale(0);
}
.messages .close {
position: absolute;
padding: 10px 8px;
top: 0;
right: 0;
color: #FFF;
}
/* Fonts */