Skip to content

Commit 4275cdb

Browse files
committed
[MIG] queue_job: migrate + tests
- Migrate queue_job, test_queue_job and base_import_async to 19.0
1 parent b7b20b0 commit 4275cdb

27 files changed

+361
-253
lines changed

.pre-commit-config.yaml

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,10 @@ exclude: |
22
(?x)
33
# NOT INSTALLABLE ADDONS
44
^base_import_async/|
5-
^queue_job/|
65
^queue_job_batch/|
76
^queue_job_cron/|
87
^queue_job_cron_jobrunner/|
98
^queue_job_subscribe/|
10-
^test_queue_job/|
119
^test_queue_job_batch/|
1210
# END NOT INSTALLABLE ADDONS
1311
# Files and folders generated by bots, to avoid loops

base_import_async/models/base_import_import.py

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -158,8 +158,7 @@ def _split_file(
158158
description = _(
159159
"Import %(model)s from file %(file_name)s - "
160160
"#%(chunk)s - lines %(from)s to %(to)s"
161-
)
162-
description = description % {
161+
) % {
163162
"model": translated_model_name,
164163
"file_name": file_name,
165164
"chunk": chunk,

queue_job/README.rst

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -21,13 +21,13 @@ Job Queue
2121
:target: http://www.gnu.org/licenses/lgpl-3.0-standalone.html
2222
:alt: License: LGPL-3
2323
.. |badge3| image:: https://img.shields.io/badge/github-OCA%2Fqueue-lightgray.png?logo=github
24-
:target: https://github.com/OCA/queue/tree/18.0/queue_job
24+
:target: https://github.com/OCA/queue/tree/19.0/queue_job
2525
:alt: OCA/queue
2626
.. |badge4| image:: https://img.shields.io/badge/weblate-Translate%20me-F47D42.png
27-
:target: https://translation.odoo-community.org/projects/queue-18-0/queue-18-0-queue_job
27+
:target: https://translation.odoo-community.org/projects/queue-19-0/queue-19-0-queue_job
2828
:alt: Translate me on Weblate
2929
.. |badge5| image:: https://img.shields.io/badge/runboat-Try%20me-875A7B.png
30-
:target: https://runboat.odoo-community.org/builds?repo=OCA/queue&target_branch=18.0
30+
:target: https://runboat.odoo-community.org/builds?repo=OCA/queue&target_branch=19.0
3131
:alt: Try me on Runboat
3232

3333
|badge1| |badge2| |badge3| |badge4| |badge5|
@@ -661,7 +661,7 @@ Bug Tracker
661661
Bugs are tracked on `GitHub Issues <https://github.com/OCA/queue/issues>`_.
662662
In case of trouble, please check there if your issue has already been reported.
663663
If you spotted it first, help us to smash it by providing a detailed and welcomed
664-
`feedback <https://github.com/OCA/queue/issues/new?body=module:%20queue_job%0Aversion:%2018.0%0A%0A**Steps%20to%20reproduce**%0A-%20...%0A%0A**Current%20behavior**%0A%0A**Expected%20behavior**>`_.
664+
`feedback <https://github.com/OCA/queue/issues/new?body=module:%20queue_job%0Aversion:%2019.0%0A%0A**Steps%20to%20reproduce**%0A-%20...%0A%0A**Current%20behavior**%0A%0A**Expected%20behavior**>`_.
665665
666666
Do not contact contributors directly about support or help with technical issues.
667667
@@ -720,6 +720,6 @@ Current `maintainer <https://odoo-community.org/page/maintainer-role>`__:
720720
721721
|maintainer-guewen|
722722
723-
This module is part of the `OCA/queue <https://github.com/OCA/queue/tree/18.0/queue_job>`_ project on GitHub.
723+
This module is part of the `OCA/queue <https://github.com/OCA/queue/tree/19.0/queue_job>`_ project on GitHub.
724724
725725
You are welcome to contribute. To learn how please visit https://odoo-community.org/page/Contribute.

queue_job/__manifest__.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22

33
{
44
"name": "Job Queue",
5-
"version": "18.0.2.0.2",
5+
"version": "19.0.1.0.0",
66
"author": "Camptocamp,ACSONE SA/NV,Odoo Community Association (OCA)",
77
"website": "https://github.com/OCA/queue",
88
"license": "LGPL-3",
@@ -24,10 +24,10 @@
2424
],
2525
"assets": {
2626
"web.assets_backend": [
27-
"/queue_job/static/src/views/**/*",
27+
"queue_job/static/src/views/**/*",
2828
],
2929
},
30-
"installable": False,
30+
"installable": True,
3131
"development_status": "Mature",
3232
"maintainers": ["guewen"],
3333
"post_init_hook": "post_init_hook",

queue_job/controllers/main.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
from psycopg2 import OperationalError, errorcodes
1212
from werkzeug.exceptions import BadRequest, Forbidden
1313

14-
from odoo import SUPERUSER_ID, _, api, http
14+
from odoo import SUPERUSER_ID, api, http
1515
from odoo.modules.registry import Registry
1616
from odoo.service.model import PG_CONCURRENCY_ERRORS_TO_RETRY
1717

@@ -179,7 +179,7 @@ def create_test_job(
179179
failure_rate=0,
180180
):
181181
if not http.request.env.user.has_group("base.group_erp_manager"):
182-
raise Forbidden(_("Access Denied"))
182+
raise Forbidden(http.request.env._("Access Denied"))
183183

184184
if failure_rate is not None:
185185
try:
@@ -280,7 +280,7 @@ def _create_graph_test_jobs(
280280
priority=priority,
281281
max_retries=max_retries,
282282
channel=channel,
283-
description="%s #%d" % (description, current_count),
283+
description=f"{description} #{current_count}",
284284
)._test_job(failure_rate=failure_rate)
285285
)
286286

queue_job/delay.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -496,7 +496,8 @@ def __del__(self):
496496
def _set_from_dict(self, properties):
497497
for key, value in properties.items():
498498
if key not in self._properties:
499-
raise ValueError(f"No property {key}")
499+
msg = f"No property {key}"
500+
raise ValueError(msg)
500501
setattr(self, key, value)
501502

502503
def set(self, *args, **kwargs):

queue_job/fields.py

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010

1111
from odoo import fields, models
1212
from odoo.tools.func import lazy
13+
from odoo.tools.misc import SENTINEL
1314

1415

1516
class JobSerialized(fields.Json):
@@ -38,13 +39,14 @@ class JobSerialized(fields.Json):
3839
),
3940
}
4041

41-
def __init__(self, string=fields.SENTINEL, base_type=fields.SENTINEL, **kwargs):
42+
def __init__(self, string=SENTINEL, base_type=SENTINEL, **kwargs):
4243
super().__init__(string=string, _base_type=base_type, **kwargs)
4344

4445
def _setup_attrs(self, model, name): # pylint: disable=missing-return
4546
super()._setup_attrs(model, name)
4647
if self._base_type not in self._default_json_mapping:
47-
raise ValueError(f"{self._base_type} is not a supported base type")
48+
msg = f"{self._base_type} is not a supported base type"
49+
raise ValueError(msg)
4850

4951
def _base_type_default_json(self, env):
5052
default_json = self._default_json_mapping.get(self._base_type)

queue_job/job.py

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -209,7 +209,8 @@ def load(cls, env, job_uuid):
209209
"""
210210
stored = cls.db_records_from_uuids(env, [job_uuid])
211211
if not stored:
212-
raise NoSuchJobError(f"Job {job_uuid} does no longer exist in the storage.")
212+
msg = f"Job {job_uuid} does no longer exist in the storage."
213+
raise NoSuchJobError(msg)
213214
return cls._load_from_db_record(stored)
214215

215216
@classmethod
@@ -505,7 +506,7 @@ def perform(self):
505506
# traceback and message:
506507
# http://blog.ianbicking.org/2007/09/12/re-raising-exceptions/
507508
new_exc = FailedJobError(
508-
"Max. retries (%d) reached: %s" % (self.max_retries, value or type_)
509+
f"Max. retries ({self.max_retries}) reached: {value or type_}"
509510
)
510511
raise new_exc from err
511512
raise
@@ -813,7 +814,7 @@ def set_failed(self, **kw):
813814
setattr(self, k, v)
814815

815816
def __repr__(self):
816-
return "<Job %s, priority:%d>" % (self.uuid, self.priority)
817+
return f"<Job {self.uuid}, priority:{self.priority}>"
817818

818819
def _get_retry_seconds(self, seconds=None):
819820
retry_pattern = self.job_config.retry_pattern
@@ -828,7 +829,7 @@ def _get_retry_seconds(self, seconds=None):
828829
break
829830
elif not seconds:
830831
seconds = RETRY_INTERVAL
831-
if isinstance(seconds, (list | tuple)):
832+
if isinstance(seconds, list | tuple):
832833
seconds = randint(seconds[0], seconds[1])
833834
return seconds
834835

@@ -856,8 +857,7 @@ def related_action(self):
856857
funcname = record._default_related_action
857858
if not isinstance(funcname, str):
858859
raise ValueError(
859-
"related_action must be the name of the "
860-
"method on queue.job as string"
860+
"related_action must be the name of the method on queue.job as string"
861861
)
862862
action = getattr(record, funcname)
863863
action_kwargs = self.job_config.related_action_kwargs

queue_job/jobrunner/__init__.py

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,22 +5,32 @@
55
import logging
66
from threading import Thread
77
import time
8+
from configparser import ConfigParser
89

910
from odoo.service import server
1011
from odoo.tools import config
1112

1213
try:
14+
# Preferred source when available: structured [queue_job] section provided
15+
# by OCA's server_environment addon.
1316
from odoo.addons.server_environment import serv_config
1417

1518
if serv_config.has_section("queue_job"):
1619
queue_job_config = serv_config["queue_job"]
1720
else:
1821
queue_job_config = {}
1922
except ImportError:
20-
queue_job_config = config.misc.get("queue_job", {})
23+
# No server_environment: try to read a [queue_job] section from odoo.conf
24+
queue_job_config = {}
25+
cfg_path = config.get("config")
26+
if cfg_path:
27+
cp = ConfigParser(interpolation=None)
28+
cp.read(cfg_path)
29+
if cp.has_section("queue_job"):
30+
queue_job_config = dict(cp["queue_job"])
2131

2232

23-
from .runner import QueueJobRunner, _channels
33+
from .runner import QueueJobRunner, _channels # noqa: E402
2434

2535
_logger = logging.getLogger(__name__)
2636

queue_job/jobrunner/channels.py

Lines changed: 6 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -455,12 +455,9 @@ def get_subchannel_by_name(self, subchannel_name):
455455

456456
def __str__(self):
457457
capacity = "∞" if self.capacity is None else str(self.capacity)
458-
return "%s(C:%s,Q:%d,R:%d,F:%d)" % (
459-
self.fullname,
460-
capacity,
461-
len(self._queue),
462-
len(self._running),
463-
len(self._failed),
458+
return (
459+
f"{self.fullname}(C:{capacity},Q:{len(self._queue)},"
460+
f"R:{len(self._running)},F:{len(self._failed)})"
464461
)
465462

466463
def remove(self, job):
@@ -894,8 +891,7 @@ def parse_simple_config(cls, config_string):
894891
)
895892
if k in config:
896893
raise ValueError(
897-
f"Invalid channel config {config_string}: "
898-
f"duplicate key {k}"
894+
f"Invalid channel config {config_string}: duplicate key {k}"
899895
)
900896
config[k] = v
901897
else:
@@ -996,7 +992,8 @@ def get_channel_by_name(
996992
if channel_name in self._channels_by_name:
997993
return self._channels_by_name[channel_name]
998994
if not autocreate and not parent_fallback:
999-
raise ChannelNotFound(f"Channel {channel_name} not found")
995+
msg = f"Channel {channel_name} not found"
996+
raise ChannelNotFound(msg)
1000997
parent = self._root_channel
1001998
if parent_fallback:
1002999
# Look for first direct parent w/ config.

0 commit comments

Comments
 (0)