[IMP]mail_activity_done: black, isort, prettier

This commit is contained in:
manu 2021-08-13 12:50:46 +02:00 committed by Bernat Puig Font
parent 49d8235387
commit 88e375f09a
9 changed files with 212 additions and 152 deletions

View File

@ -3,18 +3,17 @@
{ {
"name": "Mail Activity Done", "name": "Mail Activity Done",
"version": "12.0.2.0.0", "version": "12.0.2.0.0",
"author": "Eficent," "author": "Eficent," "Odoo Community Association (OCA)",
"Odoo Community Association (OCA)",
"license": "LGPL-3", "license": "LGPL-3",
"category": "Discuss", "category": "Discuss",
"depends": [ "depends": [
'mail', "mail",
], ],
"data": [ "data": [
'views/templates.xml', "views/templates.xml",
'views/mail_activity_views.xml', "views/mail_activity_views.xml",
], ],
"pre_init_hook": "pre_init_hook", "pre_init_hook": "pre_init_hook",
"post_load": "post_load_hook", "post_load": "post_load_hook",
'uninstall_hook': 'uninstall_hook', "uninstall_hook": "uninstall_hook",
} }

View File

@ -1,23 +1,27 @@
# Copyright 2018 Eficent Business and IT Consulting Services S.L. # Copyright 2018 Eficent Business and IT Consulting Services S.L.
# Copyright 2018 Odoo, S.A. # Copyright 2018 Odoo, S.A.
# License AGPL-3.0 or later (https://www.gnu.org/licenses/lgpl.html). # License AGPL-3.0 or later (https://www.gnu.org/licenses/lgpl.html).
from odoo.addons.mail.models.mail_activity import MailActivity
from odoo import fields from odoo import fields
from odoo.addons.mail.models.mail_activity import MailActivity
def pre_init_hook(cr): def pre_init_hook(cr):
""" The objective of this hook is to default to false all values of field """The objective of this hook is to default to false all values of field
'done' of mail.activity 'done' of mail.activity
""" """
cr.execute("""SELECT column_name cr.execute(
"""SELECT column_name
FROM information_schema.columns FROM information_schema.columns
WHERE table_name='mail_activity' AND WHERE table_name='mail_activity' AND
column_name='done'""") column_name='done'"""
)
if not cr.fetchone(): if not cr.fetchone():
cr.execute( cr.execute(
""" """
ALTER TABLE mail_activity ADD COLUMN done boolean; ALTER TABLE mail_activity ADD COLUMN done boolean;
""") """
)
cr.execute( cr.execute(
""" """
@ -28,12 +32,11 @@ def pre_init_hook(cr):
def post_load_hook(): def post_load_hook():
def new_action_feedback(self, feedback=False): def new_action_feedback(self, feedback=False):
if 'done' not in self._fields: if "done" not in self._fields:
return self.action_feedback_original(feedback=feedback) return self.action_feedback_original(feedback=feedback)
message = self.env['mail.message'] message = self.env["mail.message"]
if feedback: if feedback:
self.write(dict(feedback=feedback)) self.write(dict(feedback=feedback))
for activity in self: for activity in self:
@ -42,23 +45,23 @@ def post_load_hook():
activity.active = False activity.active = False
activity.date_done = fields.Date.today() activity.date_done = fields.Date.today()
record.message_post_with_view( record.message_post_with_view(
'mail.message_activity_done', "mail.message_activity_done",
values={'activity': activity}, values={"activity": activity},
subtype_id=self.env.ref('mail.mt_activities').id, subtype_id=self.env.ref("mail.mt_activities").id,
mail_activity_type_id=activity.activity_type_id.id, mail_activity_type_id=activity.activity_type_id.id,
) )
message |= record.message_ids[0] message |= record.message_ids[0]
return message.ids and message.ids[0] or False return message.ids and message.ids[0] or False
if not hasattr(MailActivity, 'action_feedback_original'): if not hasattr(MailActivity, "action_feedback_original"):
MailActivity.action_feedback_original = MailActivity.action_feedback MailActivity.action_feedback_original = MailActivity.action_feedback
MailActivity.action_feedback = new_action_feedback MailActivity.action_feedback = new_action_feedback
def uninstall_hook(cr, registry): def uninstall_hook(cr, registry):
""" The objective of this hook is to remove all activities that are done """The objective of this hook is to remove all activities that are done
upon module uninstall upon module uninstall
""" """
cr.execute( cr.execute(
""" """
DELETE FROM mail_activity DELETE FROM mail_activity

View File

@ -5,8 +5,10 @@
def migrate(cr, version): def migrate(cr, version):
if not version: if not version:
return return
cr.execute(""" cr.execute(
"""
UPDATE mail_activity SET UPDATE mail_activity SET
active = False active = False
WHERE done=True; WHERE done=True;
""") """
)

View File

@ -5,26 +5,27 @@ from odoo import api, fields, models
class MailActivity(models.Model): class MailActivity(models.Model):
_inherit = 'mail.activity' _inherit = "mail.activity"
active = fields.Boolean(default=True) active = fields.Boolean(default=True)
done = fields.Boolean(default=False) done = fields.Boolean(default=False)
state = fields.Selection(selection_add=[ state = fields.Selection(selection_add=[("done", "Done")], compute="_compute_state")
('done', 'Done')], compute='_compute_state')
date_done = fields.Date( date_done = fields.Date(
'Completed Date', index=True, readonly=True, "Completed Date",
index=True,
readonly=True,
) )
@api.depends('date_deadline', 'done') @api.depends("date_deadline", "done")
def _compute_state(self): def _compute_state(self):
super(MailActivity, self)._compute_state() super(MailActivity, self)._compute_state()
for record in self.filtered(lambda activity: activity.done): for record in self.filtered(lambda activity: activity.done):
record.state = 'done' record.state = "done"
class MailActivityMixin(models.AbstractModel): class MailActivityMixin(models.AbstractModel):
_inherit = 'mail.activity.mixin' _inherit = "mail.activity.mixin"
activity_ids = fields.One2many( activity_ids = fields.One2many(
domain=lambda self: [('res_model', '=', self._name), domain=lambda self: [("res_model", "=", self._name), ("active", "=", True)]
('active', '=', True)]) )

View File

@ -4,7 +4,7 @@ from odoo import api, fields, models, modules
class ResUsers(models.Model): class ResUsers(models.Model):
_inherit = 'res.users' _inherit = "res.users"
@api.model @api.model
def systray_get_activities(self): def systray_get_activities(self):
@ -25,31 +25,38 @@ class ResUsers(models.Model):
AND act.done = False AND act.done = False
GROUP BY m.id, states, act.res_model; GROUP BY m.id, states, act.res_model;
""" """
self.env.cr.execute(query, { self.env.cr.execute(
'today': fields.Date.context_today(self), query,
'user_id': self.env.uid, {
}) "today": fields.Date.context_today(self),
"user_id": self.env.uid,
},
)
activity_data = self.env.cr.dictfetchall() activity_data = self.env.cr.dictfetchall()
model_ids = [a['id'] for a in activity_data] model_ids = [a["id"] for a in activity_data]
model_names = {n[0]: n[1] for n in self.env['ir.model'].browse( model_names = {
model_ids).name_get()} n[0]: n[1] for n in self.env["ir.model"].browse(model_ids).name_get()
}
user_activities = {} user_activities = {}
for activity in activity_data: for activity in activity_data:
if not user_activities.get(activity['model']): if not user_activities.get(activity["model"]):
user_activities[activity['model']] = { user_activities[activity["model"]] = {
'name': model_names[activity['id']], "name": model_names[activity["id"]],
'model': activity['model'], "model": activity["model"],
'icon': modules.module.get_module_icon( "icon": modules.module.get_module_icon(
self.env[activity['model']]._original_module), self.env[activity["model"]]._original_module
'total_count': 0, 'today_count': 0, ),
'overdue_count': 0, 'planned_count': 0, "total_count": 0,
'type': 'activity', "today_count": 0,
"overdue_count": 0,
"planned_count": 0,
"type": "activity",
} }
user_activities[activity['model']][ user_activities[activity["model"]][
'%s_count' % activity['states']] += activity['count'] "%s_count" % activity["states"]
if activity['states'] in ('today', 'overdue'): ] += activity["count"]
user_activities[activity['model']][ if activity["states"] in ("today", "overdue"):
'total_count'] += activity['count'] user_activities[activity["model"]]["total_count"] += activity["count"]
return list(user_activities.values()) return list(user_activities.values())

View File

@ -1,48 +1,48 @@
//Copyright2018 Eficent <http://www.eficent.com> // Copyright2018 Eficent <http://www.eficent.com>
//License LGPL-3.0 or later (http://www.gnu.org/licenses/lgpl.html). // License LGPL-3.0 or later (http://www.gnu.org/licenses/lgpl.html).
odoo.define('mail.Activity.done', function(require) { odoo.define("mail.Activity.done", function (require) {
"use strict"; "use strict";
var mailUtils = require('mail.utils'); var mailUtils = require("mail.utils");
var core = require('web.core'); var core = require("web.core");
var utils = require('mail.utils'); var utils = require("mail.utils");
var time = require('web.time'); var time = require("web.time");
var mail_activity = require('mail.Activity'); var mail_activity = require("mail.Activity");
var QWeb = core.qweb; var QWeb = core.qweb;
var _t = core._t; var _t = core._t;
// We are forced here to override the method, as there is no possibility // We are forced here to override the method, as there is no possibility
// to inherit it. // to inherit it.
var setDelayLabel = function(activities) { var setDelayLabel = function (activities) {
var today = moment().startOf('day'); var today = moment().startOf("day");
_.each(activities, function(activity) { _.each(activities, function (activity) {
var to_display = ''; var to_display = "";
var deadline = moment(activity.date_deadline).startOf('day'); var deadline = moment(activity.date_deadline).startOf("day");
var diff = deadline.diff(today, 'days', true); // true means no rounding var diff = deadline.diff(today, "days", true); // True means no rounding
if(diff === 0){ if (diff === 0) {
to_display = _t('Today'); to_display = _t("Today");
}else{ } else if (diff < 0) {
if(diff < 0){ // overdue // Overdue
if(diff === -1){ if (diff === -1) {
to_display = _t('Yesterday'); to_display = _t("Yesterday");
}else{ } else {
to_display = _.str.sprintf(_t('%d days overdue'), Math.abs(diff)); to_display = _.str.sprintf(_t("%d days overdue"), Math.abs(diff));
} }
}else{ // due } else {
if(diff === 1){ // Due
to_display = _t('Tomorrow'); if (diff === 1) {
}else{ to_display = _t("Tomorrow");
to_display = _.str.sprintf(_t('Due in %d days'), Math.abs(diff)); } else {
} to_display = _.str.sprintf(_t("Due in %d days"), Math.abs(diff));
} }
} }
activity.label_delay = to_display; activity.label_delay = to_display;
}); });
// We do not want to show the activities that have been completed. // We do not want to show the activities that have been completed.
var open_activities = _.filter(activities, function(activity){ var open_activities = _.filter(activities, function (activity) {
return activity.done !== true return activity.done !== true;
}); });
return open_activities; return open_activities;
}; };
@ -54,25 +54,33 @@ odoo.define('mail.Activity.done', function(require) {
*/ */
_render: function () { _render: function () {
_.each(this._activities, function (activity) { _.each(this._activities, function (activity) {
var note = mailUtils.parseAndTransform(activity.note || '', mailUtils.inline); var note = mailUtils.parseAndTransform(
var is_blank = (/^\s*$/).test(note); activity.note || "",
mailUtils.inline
);
var is_blank = /^\s*$/.test(note);
if (!is_blank) { if (!is_blank) {
activity.note = mailUtils.parseAndTransform(activity.note, mailUtils.addLink); activity.note = mailUtils.parseAndTransform(
activity.note,
mailUtils.addLink
);
} else { } else {
activity.note = ''; activity.note = "";
} }
}); });
var activities = setDelayLabel(this._activities); var activities = setDelayLabel(this._activities);
if (activities.length) { if (activities.length) {
var nbActivities = _.countBy(activities, 'state'); var nbActivities = _.countBy(activities, "state");
this.$el.html(QWeb.render('mail.activity_items', { this.$el.html(
activities: activities, QWeb.render("mail.activity_items", {
nbPlannedActivities: nbActivities.planned, activities: activities,
nbTodayActivities: nbActivities.today, nbPlannedActivities: nbActivities.planned,
nbOverdueActivities: nbActivities.overdue, nbTodayActivities: nbActivities.today,
dateFormat: time.getLangDateFormat(), nbOverdueActivities: nbActivities.overdue,
datetimeFormat: time.getLangDatetimeFormat(), dateFormat: time.getLangDateFormat(),
})); datetimeFormat: time.getLangDatetimeFormat(),
})
);
} else { } else {
this.$el.empty(); this.$el.empty();
} }

View File

@ -1,35 +1,41 @@
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
from odoo.tests.common import TransactionCase
from datetime import date from datetime import date
from odoo.tests.common import TransactionCase
class TestMailActivityDoneMethods(TransactionCase): class TestMailActivityDoneMethods(TransactionCase):
def setUp(self): def setUp(self):
super(TestMailActivityDoneMethods, self).setUp() super(TestMailActivityDoneMethods, self).setUp()
self.employee = self.env['res.users'].create({ self.employee = self.env["res.users"].create(
'company_id': self.env.ref("base.main_company").id, {
'name': "Test User", "company_id": self.env.ref("base.main_company").id,
'login': "testuser", "name": "Test User",
'groups_id': [(6, 0, [self.env.ref('base.group_user').id])] "login": "testuser",
}) "groups_id": [(6, 0, [self.env.ref("base.group_user").id])],
activity_type = self.env['mail.activity.type'].search( }
[('name', '=', 'Meeting')], limit=1) )
self.act1 = self.env['mail.activity'].create({ activity_type = self.env["mail.activity.type"].search(
'activity_type_id': activity_type.id, [("name", "=", "Meeting")], limit=1
'res_id': self.env.ref("base.res_partner_1").id, )
'res_model_id': self.env['ir.model']._get('res.partner').id, self.act1 = self.env["mail.activity"].create(
'user_id': self.employee.id, {
'date_deadline': date.today(), "activity_type_id": activity_type.id,
}) "res_id": self.env.ref("base.res_partner_1").id,
"res_model_id": self.env["ir.model"]._get("res.partner").id,
"user_id": self.employee.id,
"date_deadline": date.today(),
}
)
def test_mail_activity_done(self): def test_mail_activity_done(self):
self.act1.done = True self.act1.done = True
self.assertEquals(self.act1.state, 'done') self.assertEquals(self.act1.state, "done")
def test_systray_get_activities(self): def test_systray_get_activities(self):
act_count = self.employee.sudo(self.employee).systray_get_activities() act_count = self.employee.sudo(self.employee).systray_get_activities()
self.assertEqual(len(act_count), 1, self.assertEqual(
"Number of activities should be equal to one") len(act_count), 1, "Number of activities should be equal to one"
)

View File

@ -1,4 +1,4 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8" ?>
<odoo> <odoo>
<!-- <!--
Copyright 2018 Eficent <https://www.eficent.com> Copyright 2018 Eficent <https://www.eficent.com>
@ -7,15 +7,17 @@
<record id="mail_activity_view_form_popup" model="ir.ui.view"> <record id="mail_activity_view_form_popup" model="ir.ui.view">
<field name="name">mail.activity.view.form.popup</field> <field name="name">mail.activity.view.form.popup</field>
<field name="model">mail.activity</field> <field name="model">mail.activity</field>
<field name="inherit_id" ref="mail.mail_activity_view_form_popup"/> <field name="inherit_id" ref="mail.mail_activity_view_form_popup" />
<field name="priority">20</field> <field name="priority">20</field>
<field name="arch" type="xml"> <field name="arch" type="xml">
<field name="activity_type_id" position="after"> <field name="activity_type_id" position="after">
<field name="state"/> <field name="state" />
<field name="date_done"/> <field name="date_done" />
</field> </field>
<button name="action_done" position="attributes"> <button name="action_done" position="attributes">
<attribute name="attrs">{'invisible':[('state', '=', 'done')]}</attribute> <attribute
name="attrs"
>{'invisible':[('state', '=', 'done')]}</attribute>
</button> </button>
</field> </field>
</record> </record>
@ -23,22 +25,31 @@
<record id="mail_activity_view_search" model="ir.ui.view"> <record id="mail_activity_view_search" model="ir.ui.view">
<field name="name">mail.activity.view.search</field> <field name="name">mail.activity.view.search</field>
<field name="model">mail.activity</field> <field name="model">mail.activity</field>
<field name="inherit_id" ref="mail.mail_activity_view_search"/> <field name="inherit_id" ref="mail.mail_activity_view_search" />
<field name="arch" type="xml"> <field name="arch" type="xml">
<field name="res_model_id" position="after"> <field name="res_model_id" position="after">
<field name="done"/> <field name="done" />
<field name="active"/> <field name="active" />
<filter string="Completed Activities" name="activities_completed" <filter
domain="[('active', '=', False), ('state', '=', 'done')]"/> string="Completed Activities"
name="activities_completed"
domain="[('active', '=', False), ('state', '=', 'done')]"
/>
</field> </field>
<filter name="activities_overdue" position="attributes"> <filter name="activities_overdue" position="attributes">
<attribute name="domain">[('date_deadline', '&lt;', context_today().strftime('%Y-%m-%d'))]</attribute> <attribute
name="domain"
>[('date_deadline', '&lt;', context_today().strftime('%Y-%m-%d'))]</attribute>
</filter> </filter>
<filter name="activities_today" position="attributes"> <filter name="activities_today" position="attributes">
<attribute name="domain">[('date_deadline', '=', context_today().strftime('%Y-%m-%d'))]</attribute> <attribute
name="domain"
>[('date_deadline', '=', context_today().strftime('%Y-%m-%d'))]</attribute>
</filter> </filter>
<filter name="activities_upcoming_all" position="attributes"> <filter name="activities_upcoming_all" position="attributes">
<attribute name="domain">[('date_deadline', '&gt;', context_today().strftime('%Y-%m-%d'))]</attribute> <attribute
name="domain"
>[('date_deadline', '&gt;', context_today().strftime('%Y-%m-%d'))]</attribute>
</filter> </filter>
</field> </field>
</record> </record>
@ -46,22 +57,34 @@
<record id="res_partner_view_search_inherit_mail" model="ir.ui.view"> <record id="res_partner_view_search_inherit_mail" model="ir.ui.view">
<field name="name">res.partner.view.search.inherit.mail</field> <field name="name">res.partner.view.search.inherit.mail</field>
<field name="model">res.partner</field> <field name="model">res.partner</field>
<field name="inherit_id" ref="mail.res_partner_view_search_inherit_mail"/> <field name="inherit_id" ref="mail.res_partner_view_search_inherit_mail" />
<field name="arch" type="xml"> <field name="arch" type="xml">
<filter name="activities_my" position="after"> <filter name="activities_my" position="after">
<filter string="Open Activities" name="activities_open" <filter
domain="[('activity_ids.active', '=', True)]"/> string="Open Activities"
<filter string="Completed Activities" name="activities_completed" name="activities_open"
domain="[('activity_ids.active', '=', False), ('activity_ids.state', '=', 'done')]"/> domain="[('activity_ids.active', '=', True)]"
/>
<filter
string="Completed Activities"
name="activities_completed"
domain="[('activity_ids.active', '=', False), ('activity_ids.state', '=', 'done')]"
/>
</filter> </filter>
<filter name="activities_overdue" position="attributes"> <filter name="activities_overdue" position="attributes">
<attribute name="domain">[('activity_ids.date_deadline', '&lt;', context_today().strftime('%Y-%m-%d'))]</attribute> <attribute
name="domain"
>[('activity_ids.date_deadline', '&lt;', context_today().strftime('%Y-%m-%d'))]</attribute>
</filter> </filter>
<filter name="activities_today" position="attributes"> <filter name="activities_today" position="attributes">
<attribute name="domain">[('activity_ids.date_deadline', '=', context_today().strftime('%Y-%m-%d'))]</attribute> <attribute
name="domain"
>[('activity_ids.date_deadline', '=', context_today().strftime('%Y-%m-%d'))]</attribute>
</filter> </filter>
<filter name="activities_upcoming_all" position="attributes"> <filter name="activities_upcoming_all" position="attributes">
<attribute name="domain">[('activity_ids.date_deadline', '&gt;', context_today().strftime('%Y-%m-%d'))]</attribute> <attribute
name="domain"
>[('activity_ids.date_deadline', '&gt;', context_today().strftime('%Y-%m-%d'))]</attribute>
</filter> </filter>
</field> </field>
</record> </record>
@ -69,16 +92,20 @@
<record id="mail_activity_view_tree" model="ir.ui.view"> <record id="mail_activity_view_tree" model="ir.ui.view">
<field name="name">mail.activity.view.tree</field> <field name="name">mail.activity.view.tree</field>
<field name="model">mail.activity</field> <field name="model">mail.activity</field>
<field name="inherit_id" ref="mail.mail_activity_view_tree"/> <field name="inherit_id" ref="mail.mail_activity_view_tree" />
<field name="arch" type="xml"> <field name="arch" type="xml">
<field name="date_deadline" position="after"> <field name="date_deadline" position="after">
<field name="state"/> <field name="state" />
<field name="date_done"/> <field name="date_done" />
</field> </field>
<tree position="attributes"> <tree position="attributes">
<attribute name="decoration-muted">state == 'done'</attribute> <attribute name="decoration-muted">state == 'done'</attribute>
<attribute name="decoration-danger">date_deadline &lt; current_date and state != 'done'</attribute> <attribute
<attribute name="decoration-success">date_deadline == current_date and state != 'done'</attribute> name="decoration-danger"
>date_deadline &lt; current_date and state != 'done'</attribute>
<attribute
name="decoration-success"
>date_deadline == current_date and state != 'done'</attribute>
</tree> </tree>
</field> </field>
</record> </record>
@ -86,12 +113,12 @@
<record id="mail_activity_view_calendar" model="ir.ui.view"> <record id="mail_activity_view_calendar" model="ir.ui.view">
<field name="name">mail.activity.view.calendar</field> <field name="name">mail.activity.view.calendar</field>
<field name="model">mail.activity</field> <field name="model">mail.activity</field>
<field name="inherit_id" ref="mail.mail_activity_view_calendar"/> <field name="inherit_id" ref="mail.mail_activity_view_calendar" />
<field name="priority" eval="2"/> <field name="priority" eval="2" />
<field name="arch" type="xml"> <field name="arch" type="xml">
<field name="summary" position="after"> <field name="summary" position="after">
<field name="state"/> <field name="state" />
<field name="date_done"/> <field name="date_done" />
</field> </field>
</field> </field>
</record> </record>

View File

@ -1,12 +1,19 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8" ?>
<odoo> <odoo>
<!-- <!--
Copyright 2018 Eficent <http://www.eficent.com> Copyright 2018 Eficent <http://www.eficent.com>
License LGPL-3.0 or later (http://www.gnu.org/licenses/lgpl.html). License LGPL-3.0 or later (http://www.gnu.org/licenses/lgpl.html).
--> -->
<template id="assets_backend" name="mail_activity_done assets" inherit_id="web.assets_backend"> <template
id="assets_backend"
name="mail_activity_done assets"
inherit_id="web.assets_backend"
>
<xpath expr="." position="inside"> <xpath expr="." position="inside">
<script type="text/javascript" src="/mail_activity_done/static/src/js/mail_activity.js"/> <script
type="text/javascript"
src="/mail_activity_done/static/src/js/mail_activity.js"
/>
</xpath> </xpath>
</template> </template>
</odoo> </odoo>