[IMP] mail: allow creating channels on first visit from token
This commit allows anyone to create a new mail.channel by visiting the URL /chat/<token>[/<channel_name>], providing that the mail.chat_from_token system parameter is set. This is useful in some situations where new channels need to be created quickly as needed by anyone without special permissions (eg, during the Odoo experience) task-2648580 closes odoo/odoo#77010 X-original-commit: 56ddc073213a148579dd72f4a9336bc4d6a11f22 Signed-off-by: Sébastien Theys (seb) <seb@odoo.com> Signed-off-by: Samuel Degueldre <sdegueldre@users.noreply.github.com>
This commit is contained in:
@@ -4,6 +4,8 @@
|
||||
import json
|
||||
from collections import defaultdict
|
||||
from datetime import datetime, timedelta
|
||||
from psycopg2 import IntegrityError
|
||||
from psycopg2.errorcodes import UNIQUE_VIOLATION
|
||||
|
||||
from odoo import http
|
||||
from odoo.http import request
|
||||
@@ -19,6 +21,30 @@ class DiscussController(http.Controller):
|
||||
# Public Pages
|
||||
# --------------------------------------------------------------------------
|
||||
|
||||
@http.route([
|
||||
'/chat/<string:create_token>',
|
||||
'/chat/<string:create_token>/<string:channel_name>',
|
||||
], methods=['GET'], type='http', auth='public')
|
||||
def discuss_channel_from_token(self, create_token, channel_name=None, **kwargs):
|
||||
if not request.env['ir.config_parameter'].sudo().get_param('mail.chat_from_token'):
|
||||
raise NotFound()
|
||||
channel_sudo = request.env['mail.channel'].sudo().search([('uuid', '=', create_token)])
|
||||
if not channel_sudo:
|
||||
try:
|
||||
channel_sudo = channel_sudo.create({
|
||||
'uuid': create_token,
|
||||
'name': channel_name or create_token,
|
||||
'public': 'public',
|
||||
})
|
||||
except IntegrityError as e:
|
||||
if e.pgcode != UNIQUE_VIOLATION:
|
||||
raise
|
||||
# concurrent insert attempt: another request created the channel.
|
||||
# commit the current transaction and get the channel.
|
||||
request.env.cr.commit()
|
||||
channel_sudo = channel_sudo.search([('uuid', '=', create_token)])
|
||||
return request.redirect(f'/chat/{channel_sudo.id}/{channel_sudo.uuid}')
|
||||
|
||||
@http.route('/chat/<int:channel_id>/<string:invitation_token>', methods=['GET'], type='http', auth='public')
|
||||
def discuss_channel_invitation(self, channel_id, invitation_token, **kwargs):
|
||||
channel_sudo = request.env['mail.channel'].browse(int(channel_id)).sudo().exists()
|
||||
|
||||
@@ -79,7 +79,7 @@ class Channel(models.Model):
|
||||
"Note that they will be able to manage their subscription manually "
|
||||
"if necessary.")
|
||||
# access
|
||||
uuid = fields.Char('UUID', size=50, index=True, default=_generate_random_token, copy=False)
|
||||
uuid = fields.Char('UUID', size=50, default=_generate_random_token, copy=False)
|
||||
public = fields.Selection([
|
||||
('public', 'Everyone'),
|
||||
('private', 'Invited people only'),
|
||||
@@ -88,6 +88,11 @@ class Channel(models.Model):
|
||||
help='This group is visible by non members. Invisible groups can add members through the invite button.')
|
||||
group_public_id = fields.Many2one('res.groups', string='Authorized Group',
|
||||
default=lambda self: self.env.ref('base.group_user'))
|
||||
|
||||
_sql_constraints = [
|
||||
('uuid_unique', 'UNIQUE(uuid)', 'The channel UUID must be unique'),
|
||||
]
|
||||
|
||||
# COMPUTE / INVERSE
|
||||
|
||||
@api.depends('channel_type')
|
||||
|
||||
Reference in New Issue
Block a user