From 0cecf918a68c18bc3b11e7bd22290088bbecb977 Mon Sep 17 00:00:00 2001 From: Romeo Fragomeli Date: Thu, 21 Oct 2021 13:35:59 +0000 Subject: [PATCH] [FIX] auth_totp,mail,web: TOTP authentication with JSON-RPC Since [1] and [2], the mobile app gets this error when trying to login on v15, while it was working fine in v14 with TOTP enabled. The 'authenticate' JSON-RPC route tries to authenticate the user and then call `session_info()`. As no UID is defined, some methods in `session_info()` raise an exception and an unexpected error is sent: * `_is_public()` -> "Expected singleton: res.users()" * `get_web_translations_hash()` -> "lang" In this fix, this exception is avoided and the proper result is sent, allowing the authentication process to continue. Steps to reproduce: * Try to connect to an account with TOTP on the mobile app (v15+) => BUG Refs: [1] odoo/odoo@80d74e7ee0eab83dc5100e0776df09d04b882fec [2] odoo/odoo@401fc7efe90fb99ebeef33db5d44d8b97be94ed5 X-original-commit: 65dca67ecdcc2228d90781a9f5ccd99f290ada6c Part-of: odoo/odoo#79182 --- addons/auth_totp/tests/test_totp.py | 29 +++++++++++++++++++++++++++++ addons/mail/models/ir_http.py | 2 +- addons/web/models/ir_http.py | 2 +- 3 files changed, 31 insertions(+), 2 deletions(-) diff --git a/addons/auth_totp/tests/test_totp.py b/addons/auth_totp/tests/test_totp.py index 438ef6d142e..f3874fddd81 100644 --- a/addons/auth_totp/tests/test_totp.py +++ b/addons/auth_totp/tests/test_totp.py @@ -1,3 +1,4 @@ +import json import time from xmlrpc.client import Fault @@ -84,3 +85,31 @@ class TestTOTP(HttpCase): self.start_tour('/web', 'totp_tour_setup', login='demo') self.start_tour('/web', 'totp_admin_disables', login='admin') self.start_tour('/', 'totp_login_disabled', login=None) + + def test_totp_authenticate(self): + """ + Ensure that JSON-RPC authentication works and don't return the user id + without TOTP check + """ + + self.start_tour('/web', 'totp_tour_setup', login='demo') + self.url_open('/web/session/logout') + + headers = { + "Content-Type": "application/json", + } + + payload = { + "jsonrpc": "2.0", + "method": "call", + "id": 0, + "params": { + "db": get_db_name(), + "login": "demo", + "password": "demo", + "context": {}, + }, + } + response = self.url_open("/web/session/authenticate", data=json.dumps(payload), headers=headers) + data = response.json() + self.assertEqual(data['result']['uid'], None) diff --git a/addons/mail/models/ir_http.py b/addons/mail/models/ir_http.py index 893533f96e7..af118ec8385 100644 --- a/addons/mail/models/ir_http.py +++ b/addons/mail/models/ir_http.py @@ -18,7 +18,7 @@ class IrHttp(models.AbstractModel): assets_discuss_public_hash = HomeStaticTemplateHelpers.get_qweb_templates_checksum(debug=request.session.debug, bundle='mail.assets_discuss_public') result['cache_hashes']['assets_discuss_public'] = assets_discuss_public_hash guest = self.env.context.get('guest') - if self.env.user._is_public() and guest: + if not request.session.uid and guest: user_context = {'lang': guest.lang} mods = odoo.conf.server_wide_modules or [] lang = user_context.get("lang") diff --git a/addons/web/models/ir_http.py b/addons/web/models/ir_http.py index 212fb0c64c0..bf764741aea 100644 --- a/addons/web/models/ir_http.py +++ b/addons/web/models/ir_http.py @@ -34,7 +34,7 @@ class Http(models.AbstractModel): )) mods = odoo.conf.server_wide_modules or [] lang = user_context.get("lang") - translation_hash = request.env['ir.translation'].sudo().get_web_translations_hash(mods, lang) + translation_hash = request.env['ir.translation'].sudo().get_web_translations_hash(mods, lang) if request.session.uid else None session_info = { "uid": request.session.uid, "is_system": user._is_system() if request.session.uid else False,