diff --git a/addons/website_mass_mailing/__manifest__.py b/addons/website_mass_mailing/__manifest__.py index 57659cb3162..1d6534dc96c 100644 --- a/addons/website_mass_mailing/__manifest__.py +++ b/addons/website_mass_mailing/__manifest__.py @@ -24,6 +24,7 @@ On a simple click, your visitors can subscribe to mailing lists managed in the E 'website.assets_wysiwyg': [ 'website_mass_mailing/static/src/js/website_mass_mailing.editor.js', 'website_mass_mailing/static/src/scss/website_mass_mailing_edit_mode.scss', + 'website_mass_mailing/static/src/snippets/s_popup/options.js', ], 'web.assets_tests': [ 'website_mass_mailing/static/tests/**/*', diff --git a/addons/website_mass_mailing/controllers/main.py b/addons/website_mass_mailing/controllers/main.py index 7f062a4a0a6..4586397c2e6 100644 --- a/addons/website_mass_mailing/controllers/main.py +++ b/addons/website_mass_mailing/controllers/main.py @@ -8,43 +8,58 @@ from odoo.addons.mass_mailing.controllers import main class MassMailController(main.MassMailController): - @route('/website_mass_mailing/is_subscriber', type='json', website=True, auth="public") - def is_subscriber(self, list_id, **post): - email = None - if not request.env.user._is_public(): - email = request.env.user.email - elif request.session.get('mass_mailing_email'): - email = request.session['mass_mailing_email'] - + @route('/website_mass_mailing/is_subscriber', type='json', website=True, auth='public') + def is_subscriber(self, list_id, subscription_type, **post): + value = self._get_value(subscription_type) + fname = self._get_fname(subscription_type) is_subscriber = False - if email: - contacts_count = request.env['mailing.contact.subscription'].sudo().search_count([('list_id', 'in', [int(list_id)]), ('contact_id.email', '=', email), ('opt_out', '=', False)]) + if value and fname: + contacts_count = request.env['mailing.contact.subscription'].sudo().search_count( + [('list_id', 'in', [int(list_id)]), (f'contact_id.{fname}', '=', value), ('opt_out', '=', False)]) is_subscriber = contacts_count > 0 - return {'is_subscriber': is_subscriber, 'email': email} + return {'is_subscriber': is_subscriber, 'value': value} - @route('/website_mass_mailing/subscribe', type='json', website=True, auth="public") - def subscribe(self, list_id, email, **post): + def _get_value(self, subscription_type): + value = None + if subscription_type == 'email': + if not request.env.user._is_public(): + value = request.env.user.email + elif request.session.get('mass_mailing_email'): + value = request.session['mass_mailing_email'] + return value + + def _get_fname(self, subscription_type): + return 'email' if subscription_type == 'email' else '' + + @route('/website_mass_mailing/subscribe', type='json', website=True, auth='public') + def subscribe(self, list_id, value, subscription_type, **post): if not request.env['ir.http']._verify_request_recaptcha_token('website_mass_mailing_subscribe'): return { 'toast_type': 'danger', 'toast_content': _("Suspicious activity detected by Google reCaptcha."), } + ContactSubscription = request.env['mailing.contact.subscription'].sudo() Contacts = request.env['mailing.contact'].sudo() - name, email = Contacts.get_name_email(email) + if subscription_type == 'email': + name, value = Contacts.get_name_email(value) + elif subscription_type == 'mobile': + name = value - subscription = ContactSubscription.search([('list_id', '=', int(list_id)), ('contact_id.email', '=', email)], limit=1) + fname = self._get_fname(subscription_type) + subscription = ContactSubscription.search( + [('list_id', '=', int(list_id)), (f'contact_id.{fname}', '=', value)], limit=1) if not subscription: # inline add_to_list as we've already called half of it - contact_id = Contacts.search([('email', '=', email)], limit=1) + contact_id = Contacts.search([(fname, '=', value)], limit=1) if not contact_id: - contact_id = Contacts.create({'name': name, 'email': email}) + contact_id = Contacts.create({'name': name, fname: value}) ContactSubscription.create({'contact_id': contact_id.id, 'list_id': int(list_id)}) elif subscription.opt_out: subscription.opt_out = False # add email to session - request.session['mass_mailing_email'] = email + request.session[f'mass_mailing_{fname}'] = value return { 'toast_type': 'success', 'toast_content': _("Thanks for subscribing!"), diff --git a/addons/website_mass_mailing/static/src/js/website_mass_mailing.editor.js b/addons/website_mass_mailing/static/src/js/website_mass_mailing.editor.js index 5b300e3b3f5..25b3f049974 100644 --- a/addons/website_mass_mailing/static/src/js/website_mass_mailing.editor.js +++ b/addons/website_mass_mailing/static/src/js/website_mass_mailing.editor.js @@ -40,8 +40,10 @@ options.registry.mailing_list_subscribe = options.Class.extend({ */ cleanForSave() { const previewClasses = ['o_disable_preview', 'o_enable_preview']; - this.$target[0].querySelector('.js_subscribe_btn').classList.remove(...previewClasses); - this.$target[0].querySelector('.js_subscribed_btn').classList.remove(...previewClasses); + const subscribeBtn = this.$target[0].querySelector('.js_subscribe_btn'); + subscribeBtn && subscribeBtn.classList.remove(...previewClasses); + const subscribedBtn = this.$target[0].querySelector('.js_subscribed_btn'); + subscribedBtn && subscribedBtn.classList.remove(...previewClasses); }, //-------------------------------------------------------------------------- diff --git a/addons/website_mass_mailing/static/src/js/website_mass_mailing.js b/addons/website_mass_mailing/static/src/js/website_mass_mailing.js index 7cb2e7e6e83..9be5ea45e30 100644 --- a/addons/website_mass_mailing/static/src/js/website_mass_mailing.js +++ b/addons/website_mass_mailing/static/src/js/website_mass_mailing.js @@ -40,10 +40,12 @@ publicWidget.registry.subscribe = publicWidget.Widget.extend({ return def; } const always = this._updateView.bind(this); + const inputName = this.$target[0].querySelector('input').name; return Promise.all([def, this._rpc({ route: '/website_mass_mailing/is_subscriber', params: { - 'list_id': this.$target.data('list-id'), + 'list_id': this._getListId(), + 'subscription_type': inputName, }, }).then(always).guardedCatch(always)]); }, @@ -68,11 +70,11 @@ publicWidget.registry.subscribe = publicWidget.Widget.extend({ const isSubscriber = data.is_subscriber; const subscribeBtnEl = this.$target[0].querySelector('.js_subscribe_btn'); const thanksBtnEl = this.$target[0].querySelector('.js_subscribed_btn'); - const emailInputEl = this.$target[0].querySelector('input.js_subscribe_email'); + const valueInputEl = this.$target[0].querySelector('input.js_subscribe_value'); subscribeBtnEl.disabled = isSubscriber; - emailInputEl.value = data.email || ''; - emailInputEl.disabled = isSubscriber; + valueInputEl.value = data.value || ''; + valueInputEl.disabled = isSubscriber; // Compat: remove d-none for DBs that have the button saved with it. this.$target[0].classList.remove('d-none'); @@ -80,6 +82,10 @@ publicWidget.registry.subscribe = publicWidget.Widget.extend({ thanksBtnEl.classList.toggle('d-none', !isSubscriber); }, + _getListId: function () { + return this.$target.closest('[data-snippet=s_newsletter_block').data('list-id') || this.$target.data('list-id'); + }, + //-------------------------------------------------------------------------- // Handlers //-------------------------------------------------------------------------- @@ -89,9 +95,9 @@ publicWidget.registry.subscribe = publicWidget.Widget.extend({ */ _onSubscribeClick: async function () { var self = this; - var $email = this.$(".js_subscribe_email:visible"); - - if ($email.length && !$email.val().match(/.+@.+/)) { + const inputName = this.$('input').attr('name'); + const $input = this.$(".js_subscribe_value:visible"); + if (inputName === 'email' && $input.length && !$input.val().match(/.+@.+/)) { this.$target.addClass('o_has_error').find('.form-control').addClass('is-invalid'); return false; } @@ -109,8 +115,9 @@ publicWidget.registry.subscribe = publicWidget.Widget.extend({ this._rpc({ route: '/website_mass_mailing/subscribe', params: { - 'list_id': this.$target.data('list-id'), - 'email': $email.length ? $email.val() : false, + 'list_id': this._getListId(), + 'value': $input.length ? $input.val() : false, + 'subscription_type': inputName, recaptcha_token_response: tokenObj.token, }, }).then(function (result) { @@ -118,7 +125,7 @@ publicWidget.registry.subscribe = publicWidget.Widget.extend({ if (toastType === 'success') { self.$(".js_subscribe_btn").addClass('d-none'); self.$(".js_subscribed_btn").removeClass('d-none'); - self.$('input.js_subscribe_email').prop('disabled', !!result); + self.$('input.js_subscribe_value').prop('disabled', !!result); const $popup = self.$target.closest('.o_newsletter_modal'); if ($popup.length) { $popup.modal('hide'); diff --git a/addons/website_mass_mailing/static/src/snippets/s_popup/000.js b/addons/website_mass_mailing/static/src/snippets/s_popup/000.js index c5eeb158508..fa652326730 100644 --- a/addons/website_mass_mailing/static/src/snippets/s_popup/000.js +++ b/addons/website_mass_mailing/static/src/snippets/s_popup/000.js @@ -16,7 +16,7 @@ PopupWidget.include({ _canShowPopup() { if ( this.$el.is('.o_newsletter_popup') && - this.$el.find('input.js_subscribe_email').prop('disabled') + this.$el.find('input.js_subscribe_value').prop('disabled') ) { return false; } diff --git a/addons/website_mass_mailing/static/src/snippets/s_popup/options.js b/addons/website_mass_mailing/static/src/snippets/s_popup/options.js new file mode 100644 index 00000000000..2b85bc833ab --- /dev/null +++ b/addons/website_mass_mailing/static/src/snippets/s_popup/options.js @@ -0,0 +1,14 @@ +/** @odoo-module **/ + +import options from 'web_editor.snippets.options'; + +options.registry.NewsletterLayout = options.registry.SelectTemplate.extend({ + /** + * @constructor + */ + init() { + this._super(...arguments); + this.containerSelector = '> .container, > .container-fluid, > .o_container_small'; + this.selectTemplateWidgetName = 'newsletter_template_opt'; + }, +}); diff --git a/addons/website_mass_mailing/static/tests/tours/newsletter_block.js b/addons/website_mass_mailing/static/tests/tours/newsletter_block.js index efde36c722c..79d7d051cb6 100644 --- a/addons/website_mass_mailing/static/tests/tours/newsletter_block.js +++ b/addons/website_mass_mailing/static/tests/tours/newsletter_block.js @@ -14,7 +14,7 @@ wTourUtils.registerEditionTour('newsletter_block_edition', { }), { content: 'Wait for the list id to be set.', - trigger: 'iframe .s_newsletter_subscribe_form[data-list-id]:not([data-list-id="0"])', + trigger: 'iframe .s_newsletter_block[data-list-id]:not([data-list-id="0"]) .s_newsletter_subscribe_form', run: () => null, // it's a check }, ...wTourUtils.clickOnSave(), diff --git a/addons/website_mass_mailing/views/snippets_templates.xml b/addons/website_mass_mailing/views/snippets_templates.xml index 46ad954242c..ac37bbdb70c 100644 --- a/addons/website_mass_mailing/views/snippets_templates.xml +++ b/addons/website_mass_mailing/views/snippets_templates.xml @@ -25,9 +25,9 @@ + + + +