Skip to content

Commit

Permalink
[FIX]mail_activity_done: Fix activity_state search.
Browse files Browse the repository at this point in the history
  • Loading branch information
jesusVMayor committed Nov 21, 2024
1 parent f00dd76 commit df64eed
Show file tree
Hide file tree
Showing 2 changed files with 97 additions and 11 deletions.
78 changes: 78 additions & 0 deletions mail_activity_done/models/mail_activity.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
# Copyright 2018-22 ForgeFlow <http://www.forgeflow.com>
# License LGPL-3.0 or later (http://www.gnu.org/licenses/lgpl.html).
from datetime import datetime

import pytz

from odoo import api, fields, models
from odoo.osv import expression

Expand Down Expand Up @@ -92,3 +96,77 @@ def _read_progress_bar(self, domain, group_by, progress_bar):
"""
domain = expression.AND([domain, [("activity_ids.done", "=", False)]])
return super()._read_progress_bar(domain, group_by, progress_bar)

def _search_activity_state(self, operator, value):
# Totally override the method.
all_states = {"overdue", "today", "planned", False}
if operator == "=":
search_states = {value}
elif operator == "!=":
search_states = all_states - {value}

Check warning on line 106 in mail_activity_done/models/mail_activity.py

View check run for this annotation

Codecov / codecov/patch

mail_activity_done/models/mail_activity.py#L106

Added line #L106 was not covered by tests
elif operator == "in":
search_states = set(value)

Check warning on line 108 in mail_activity_done/models/mail_activity.py

View check run for this annotation

Codecov / codecov/patch

mail_activity_done/models/mail_activity.py#L108

Added line #L108 was not covered by tests
elif operator == "not in":
search_states = all_states - set(value)

Check warning on line 110 in mail_activity_done/models/mail_activity.py

View check run for this annotation

Codecov / codecov/patch

mail_activity_done/models/mail_activity.py#L110

Added line #L110 was not covered by tests

reverse_search = False
if False in search_states:
# If we search "activity_state = False", they might be a lot of records
# (million for some models), so instead of returning the list of IDs
# [(id, 'in', ids)] we will reverse the domain and return something like
# [(id, 'not in', ids)], so the list of ids is as small as possible
reverse_search = True
search_states = all_states - search_states

Check warning on line 119 in mail_activity_done/models/mail_activity.py

View check run for this annotation

Codecov / codecov/patch

mail_activity_done/models/mail_activity.py#L118-L119

Added lines #L118 - L119 were not covered by tests

# Use number in the SQL query for performance purpose
integer_state_value = {
"overdue": -1,
"today": 0,
"planned": 1,
False: None,
}

search_states_int = {integer_state_value.get(s or False) for s in search_states}

query = """
SELECT res_id
FROM (
SELECT res_id,
-- Global activity state
MIN(
-- Compute the state of each individual activities
-- -1: overdue
-- 0: today
-- 1: planned
SIGN(EXTRACT(day from (
mail_activity.date_deadline - DATE_TRUNC(
'day', %(today_utc)s AT TIME ZONE res_partner.tz)
)))
)::INT AS activity_state
FROM mail_activity
LEFT JOIN res_users
ON res_users.id = mail_activity.user_id
LEFT JOIN res_partner
ON res_partner.id = res_users.partner_id
WHERE mail_activity.res_model = %(res_model_table)s
and mail_activity.done=False
GROUP BY res_id
) AS res_record
WHERE %(search_states_int)s @> ARRAY[activity_state]
"""

self._cr.execute(
query,
{
"today_utc": pytz.utc.localize(datetime.utcnow()),
"res_model_table": self._name,
"search_states_int": list(search_states_int),
},
)
return [
(
"id",
"not in" if reverse_search else "in",
[r[0] for r in self._cr.fetchall()],
)
]
30 changes: 19 additions & 11 deletions mail_activity_done/tests/test_mail_activity_done.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,6 @@
class TestMailActivityDoneMethods(TransactionCase):
def setUp(self):
super(TestMailActivityDoneMethods, self).setUp()

self.employee = self.env["res.users"].create(
{
"company_id": self.env.ref("base.main_company").id,
"name": "Test User",
"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
)
Expand All @@ -26,18 +17,29 @@ def setUp(self):
"res_id": self.env.ref("base.res_partner_1").id,
"res_model": "res.partner",
"res_model_id": self.env["ir.model"]._get("res.partner").id,
"user_id": self.employee.id,
"user_id": self.env.user.id,
"date_deadline": date.today(),
}
)
self.act2 = self.env["mail.activity"].create(
{
"activity_type_id": activity_type.id,
"res_id": self.env.ref("base.res_partner_1").id,
"res_model": "res.partner",
"res_model_id": self.env["ir.model"]._get("res.partner").id,
"user_id": self.env.user.id,
"date_deadline": date.today(),
}
)
self.act2._action_done()

def test_mail_activity_done(self):
self.act1._action_done()
self.assertTrue(self.act1.exists())
self.assertEqual(self.act1.state, "done")

def test_systray_get_activities(self):
act_count = self.employee.with_user(self.employee).systray_get_activities()
act_count = self.env.user.systray_get_activities()
self.assertEqual(
len(act_count), 1, "Number of activities should be equal to one"
)
Expand All @@ -56,3 +58,9 @@ def test_read_progress_bar(self):
self.assertEqual(self.act1.state, "done")
result = res_partner._read_progress_bar(**params)
self.assertEqual(len(result), 0)

def test_activity_state_search(self):
today_activities = self.env["res.partner"].search(
[("activity_state", "=", "today")]
)
self.assertEqual(len(today_activities), 1)

0 comments on commit df64eed

Please sign in to comment.