Skip to content

Commit 70b3ece

Browse files
committed
[IMP] fastapi_log: Adapt to log collection
1 parent 996029a commit 70b3ece

13 files changed

Lines changed: 147 additions & 155 deletions

File tree

fastapi_log/README.rst

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,10 @@ Authors
7171
Contributors
7272
------------
7373

74-
- Florian Mounier florian.mounier@akretion.com
74+
- Florian Mounier florian.mounier@akretion.com
75+
- `PyTech <https://www.pytech.it>`__:
76+
77+
- Simone Rubino <simone.rubino@pytech.it>
7578

7679
Maintainers
7780
-----------

fastapi_log/__manifest__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44

55
{
66
"name": "Fastapi Log",
7-
"version": "16.0.1.0.0",
7+
"version": "16.0.1.1.0",
88
"author": "Akretion, Odoo Community Association (OCA)",
99
"summary": "Log Fastapi requests in database",
1010
"category": "Tools",

fastapi_log/fastapi_dispatcher.py

Lines changed: 8 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,10 @@
11
# Copyright 2025 Akretion (http://www.akretion.com).
22
# @author Florian Mounier <florian.mounier@akretion.com>
3+
# Copyright 2025 Simone Rubino - PyTech
34
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
5+
46
import logging
57

6-
from odoo import registry, tools
78
from odoo.http import _dispatchers
89

910
from odoo.addons.fastapi.fastapi_dispatcher import (
@@ -27,16 +28,8 @@ def dispatch(self, endpoint, args):
2728
._get_endpoint(environ["PATH_INFO"])
2829
)
2930
if fastapi_endpoint.log_requests:
30-
if tools.config["test_enable"]:
31-
cr = getattr(
32-
self.request.env.registry, "test_log_cr", self.request.env.cr
33-
)
34-
else:
35-
# Create an independent cursor
36-
cr = registry(self.request.env.cr.dbname).cursor()
37-
38-
env = self.request.env(cr=cr, su=True)
3931
request = self.request
32+
env = request.env(su=True)
4033
try:
4134
log = env["api.log"].log_request(request)
4235
except Exception as e:
@@ -50,18 +43,17 @@ def dispatch(self, endpoint, args):
5043
log and log.log_exception(response_exc)
5144
except Exception as e:
5245
_logger.warning("Failed to log exception", exc_info=e)
46+
else:
47+
# Be sure to commit/save the exception's log
48+
env.cr.commit()
49+
5350
raise response_exc
5451
else:
5552
try:
5653
log and log.log_response(response)
5754
except Exception as e:
5855
_logger.warning("Failed to log response", exc_info=e)
59-
finally:
60-
if not tools.config["test_enable"]:
61-
try:
62-
cr.commit() # pylint: disable=E8102
63-
finally:
64-
cr.close()
56+
6557
return response
6658
else:
6759
return super().dispatch(endpoint, args)
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
# Copyright 2025 Simone Rubino - PyTech
2+
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).
3+
4+
from openupgradelib import openupgrade
5+
6+
7+
@openupgrade.migrate()
8+
def migrate(env, version):
9+
endpoint_id_column = openupgrade.get_legacy_name("fastapi_endpoint_id")
10+
openupgrade.logged_query(
11+
env.cr,
12+
"""
13+
UPDATE api_log SET
14+
collection_id=%(endpoint_id_column)s,
15+
collection_model='fastapi.endpoint',
16+
collection_ref='fastapi.endpoint,' || %(endpoint_id_column)s
17+
WHERE %(endpoint_id_column)s IS NOT NULL
18+
"""
19+
% {
20+
"endpoint_id_column": endpoint_id_column,
21+
},
22+
)
23+
openupgrade.logged_query(
24+
env.cr,
25+
"""
26+
ALTER TABLE api_log
27+
DROP COLUMN %(endpoint_id_column)s
28+
"""
29+
% {
30+
"endpoint_id_column": endpoint_id_column,
31+
},
32+
)
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
# Copyright 2025 Simone Rubino - PyTech
2+
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl).
3+
4+
from openupgradelib import openupgrade
5+
6+
7+
@openupgrade.migrate()
8+
def migrate(env, version):
9+
openupgrade.copy_columns(
10+
env.cr,
11+
{
12+
"api_log": [
13+
(
14+
"fastapi_endpoint_id",
15+
None,
16+
None,
17+
),
18+
],
19+
},
20+
)

fastapi_log/models/api_log.py

Lines changed: 15 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,24 @@
11
# Copyright 2025 Akretion (http://www.akretion.com).
22
# @author Florian Mounier <florian.mounier@akretion.com>
3+
# Copyright 2025 Simone Rubino - PyTech
34
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
45

56
from starlette.exceptions import HTTPException as StarletteHTTPException
67

7-
from odoo import api, fields, models
8+
from odoo import api, models
89

910

1011
class FastapiLog(models.Model):
1112
_inherit = "api.log"
1213

13-
fastapi_endpoint_id = fields.Many2one(
14-
comodel_name="fastapi.endpoint",
15-
string="Endpoint",
16-
ondelete="cascade",
17-
index=True,
18-
)
14+
@api.model
15+
def _selection_collection_ref(self):
16+
collections = super()._selection_collection_ref()
17+
fastapi_endpoint_model = self.env["fastapi.endpoint"]
18+
collections.append(
19+
(fastapi_endpoint_model._name, fastapi_endpoint_model._description)
20+
)
21+
return collections
1922

2023
@api.model
2124
def _get_request_body(self, request):
@@ -42,7 +45,11 @@ def _prepare_log_request(self, request):
4245
.sudo()
4346
._get_endpoint(environ["PATH_INFO"])
4447
)
45-
log_request_values["fastapi_endpoint_id"] = endpoint.id
48+
log_request_values["collection_ref"] = "%s,%s" % (
49+
endpoint._name,
50+
endpoint.id,
51+
)
52+
4653
return log_request_values
4754

4855
def _prepare_log_exception(self, exception):
Lines changed: 7 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,14 @@
11
# Copyright 2025 Akretion (http://www.akretion.com).
22
# @author Florian Mounier <florian.mounier@akretion.com>
3+
# Copyright 2025 Simone Rubino - PyTech
34
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
45

5-
from odoo import api, fields, models
6+
from odoo import models
67

78

89
class FastapiEndpoint(models.Model):
9-
_inherit = "fastapi.endpoint"
10-
11-
log_requests = fields.Boolean(
12-
help="Log requests in database.",
13-
)
14-
15-
fastapi_log_ids = fields.One2many(
16-
comodel_name="api.log",
17-
inverse_name="fastapi_endpoint_id",
18-
string="Logs",
19-
)
20-
21-
fastapi_log_count = fields.Integer(
22-
compute="_compute_fastapi_log_count",
23-
string="Logs Count",
24-
)
25-
26-
@api.depends("fastapi_log_ids")
27-
def _compute_fastapi_log_count(self):
28-
groups = self.env["api.log"].read_group(
29-
[("fastapi_endpoint_id", "in", self.ids)],
30-
["fastapi_endpoint_id"],
31-
["fastapi_endpoint_id"],
32-
)
33-
mapped_data = {
34-
g["fastapi_endpoint_id"][0]: g["fastapi_endpoint_id_count"] for g in groups
35-
}
36-
for endpoint in self:
37-
endpoint.fastapi_log_count = mapped_data.get(endpoint.id, 0)
10+
_name = "fastapi.endpoint"
11+
_inherit = [
12+
"api.log_collection.mixin",
13+
"fastapi.endpoint",
14+
]

fastapi_log/readme/CONTRIBUTORS.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,3 @@
11
- Florian Mounier <florian.mounier@akretion.com>
2+
- [PyTech](https://www.pytech.it):
3+
- Simone Rubino \<<simone.rubino@pytech.it>\>

fastapi_log/static/description/index.html

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -416,6 +416,10 @@ <h2><a class="toc-backref" href="#toc-entry-4">Authors</a></h2>
416416
<h2><a class="toc-backref" href="#toc-entry-5">Contributors</a></h2>
417417
<ul class="simple">
418418
<li>Florian Mounier <a class="reference external" href="mailto:florian.mounier&#64;akretion.com">florian.mounier&#64;akretion.com</a></li>
419+
<li><a class="reference external" href="https://www.pytech.it">PyTech</a>:<ul>
420+
<li>Simone Rubino &lt;<a class="reference external" href="mailto:simone.rubino&#64;pytech.it">simone.rubino&#64;pytech.it</a>&gt;</li>
421+
</ul>
422+
</li>
419423
</ul>
420424
</div>
421425
<div class="section" id="maintainers">

fastapi_log/tests/common.py

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
# Copyright 2025 Akretion (http://www.akretion.com).
2+
# @author Florian Mounier <florian.mounier@akretion.com>
3+
# Copyright 2025 Simone Rubino - PyTech
4+
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl).
5+
6+
from contextlib import contextmanager
7+
8+
from odoo.tests.common import RecordCapturer
9+
10+
from odoo.addons.api_log.tests.common import Common as CommonAPILog
11+
12+
13+
class Common(CommonAPILog):
14+
@classmethod
15+
def setUpClass(cls):
16+
super().setUpClass()
17+
cls.fastapi_demo_app = cls.env.ref("fastapi.fastapi_endpoint_demo")
18+
cls.fastapi_demo_app.root_path += "/test"
19+
cls.fastapi_demo_app._handle_registry_sync()
20+
cls.fastapi_demo_app.write({"log_requests": True})
21+
lang = (
22+
cls.env["res.lang"]
23+
.with_context(active_test=False)
24+
.search([("code", "=", "fr_BE")])
25+
)
26+
lang.active = True
27+
28+
@contextmanager
29+
def log_capturer(self):
30+
app = self.fastapi_demo_app
31+
with RecordCapturer(
32+
self.env[self.log_model._name],
33+
[("collection_ref", "=", "%s,%s" % (app._name, app.id))],
34+
) as capturer:
35+
yield capturer

0 commit comments

Comments
 (0)