diff --git a/mass_mailing_custom_unsubscribe/README.rst b/mass_mailing_custom_unsubscribe/README.rst index 568d653..3f62625 100644 --- a/mass_mailing_custom_unsubscribe/README.rst +++ b/mass_mailing_custom_unsubscribe/README.rst @@ -1,96 +1 @@ -.. image:: https://img.shields.io/badge/licence-AGPL--3-blue.svg - :target: http://www.gnu.org/licenses/agpl-3.0-standalone.html - :alt: License: AGPL-3 - -========================================================== -Customizable unsubscription process on mass mailing emails -========================================================== - -This addon extends the unsubscription form to let you: - -- Choose which mailing lists are not cross-unsubscriptable when unsubscribing - from a different one. -- Know why and when a contact has been subscribed or unsubscribed from a - mass mailing. -- Provide proof on why you are sending mass mailings to a given contact, as - required by the GDPR in Europe. - -Configuration -============= - -Unsubscription Reasons ----------------------- - -You can customize what reasons will be displayed to your unsubscriptors when -they are going to unsubscribe. To do it: - -#. Go to *Mass Mailing > Configuration > Unsubscription Reasons*. -#. Create / edit / remove / sort as usual. -#. If *Details required* is enabled, they will have to fill a text area to - continue. - -Usage -===== - -Once configured: - -#. Go to *Mass Mailing > Mailings > Mass Mailings > Create*. -#. Edit your mass mailing at wish, but remember to add a snippet from - *Footers*, so people have an *Unsubscribe* link. -#. Send it. -#. If somebody gets unsubscribed, you will see logs about that under - *Mass Mailing > Mailings > Unsubscriptions*. - -.. image:: https://odoo-community.org/website/image/ir.attachment/5784_f2813bd/datas - :alt: Try me on Runbot - :target: https://runbot.odoo-community.org/runbot/205/10.0 - -Known issues / Roadmap -====================== - -* This module adds a security hash for mass mailing unsubscription URLs, which - disables insecure URLs from mass mailing messages sent before its - installation. This can be a problem, but anyway you'd get that problem in - Odoo 11.0, where https://github.com/odoo/odoo/pull/12040 was merged, so at - least this addon will be forward-compatible with it. So, **this feature must - be removed from here when migrating to v11**. -* This module replaces AJAX submission core implementation from the mailing - list management form, because it is impossible to extend it. When - https://github.com/odoo/odoo/pull/14386 gets merged (which upstreams most - needed changes), this addon will need a refactoring (mostly removing - duplicated functionality and depending on it instead of replacing it). In the - mean time, there is a little chance that this introduces some - incompatibilities with other addons that depend on ``website_mass_mailing``. - -Bug Tracker -=========== - -Bugs are tracked on `GitHub Issues -`_. In case of trouble, please -check there if your issue has already been reported. If you spotted it first, -help us smashing it by providing a detailed and welcomed feedback. - -Credits -======= - -Contributors ------------- - -* Rafael Blasco -* Antonio Espinosa -* Jairo Llopis - -Maintainer ----------- - -.. image:: https://odoo-community.org/logo.png - :alt: Odoo Community Association - :target: https://odoo-community.org - -This module is maintained by the OCA. - -OCA, or the Odoo Community Association, is a nonprofit organization whose -mission is to support the collaborative development of Odoo features and -promote its widespread use. - -To contribute to this module, please visit https://odoo-community.org. +**This file is going to be generated by oca-gen-addon-readme.** diff --git a/mass_mailing_custom_unsubscribe/__init__.py b/mass_mailing_custom_unsubscribe/__init__.py index 434c125..d93811e 100644 --- a/mass_mailing_custom_unsubscribe/__init__.py +++ b/mass_mailing_custom_unsubscribe/__init__.py @@ -1,5 +1,4 @@ -# -*- coding: utf-8 -*- -# Copyright 2016 Jairo Llopis # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). from . import controllers, models +from .hooks import post_init_hook diff --git a/mass_mailing_custom_unsubscribe/__manifest__.py b/mass_mailing_custom_unsubscribe/__manifest__.py index d8bbe90..a069192 100644 --- a/mass_mailing_custom_unsubscribe/__manifest__.py +++ b/mass_mailing_custom_unsubscribe/__manifest__.py @@ -1,11 +1,11 @@ -# -*- coding: utf-8 -*- # Copyright 2016 Jairo Llopis +# Copyright 2018 David Vidal # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). { - 'name': "Customizable unsubscription process on mass mailing emails", - "summary": "Know and track (un)subscription reasons, GDPR compliant", + 'name': 'Customizable unsubscription process on mass mailing emails', + 'summary': 'Know and track (un)subscription reasons, GDPR compliant', 'category': 'Marketing', - 'version': '10.0.2.0.0', + 'version': '11.0.1.0.0', 'depends': [ 'website_mass_mailing', ], @@ -17,9 +17,10 @@ 'views/assets.xml', 'views/mail_unsubscription_reason_view.xml', 'views/mail_mass_mailing_list_view.xml', + 'views/mail_mass_mailing_contact_view.xml', 'views/mail_unsubscription_view.xml', ], - "demo": [ + 'demo': [ 'demo/assets.xml', ], 'images': [ @@ -27,7 +28,8 @@ ], 'author': 'Tecnativa,' 'Odoo Community Association (OCA)', - 'website': 'https://www.tecnativa.com', + 'website': 'https://github.com/OCA/social', 'license': 'AGPL-3', 'installable': True, + 'post_init_hook': 'post_init_hook', } diff --git a/mass_mailing_custom_unsubscribe/controllers/__init__.py b/mass_mailing_custom_unsubscribe/controllers/__init__.py index 6667911..4ca7a1b 100644 --- a/mass_mailing_custom_unsubscribe/controllers/__init__.py +++ b/mass_mailing_custom_unsubscribe/controllers/__init__.py @@ -1,4 +1,3 @@ -# -*- coding: utf-8 -*- # Copyright 2016 Jairo Llopis # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). diff --git a/mass_mailing_custom_unsubscribe/controllers/main.py b/mass_mailing_custom_unsubscribe/controllers/main.py index 3b21572..d2dcac6 100644 --- a/mass_mailing_custom_unsubscribe/controllers/main.py +++ b/mass_mailing_custom_unsubscribe/controllers/main.py @@ -1,12 +1,11 @@ -# -*- coding: utf-8 -*- # Copyright 2015 Antiun IngenierĂ­a S.L. (http://www.antiun.com) # Copyright 2016 Jairo Llopis # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). import logging -from openerp.http import request, route -from openerp.addons.website_mass_mailing.controllers.main \ +from odoo.http import request, route +from odoo.addons.website_mass_mailing.controllers.main \ import MassMailController _logger = logging.getLogger(__name__) @@ -45,24 +44,18 @@ class CustomUnsubscribe(MassMailController): _logger.debug( "Called `mailing()` with: %r", (mailing_id, email, res_id, token, post)) - if res_id: - res_id = int(res_id) mailing = request.env["mail.mass_mailing"].sudo().browse(mailing_id) - mailing._unsubscribe_token(res_id, token) # Mass mailing list contacts are a special case because they have a # subscription management form - if mailing.mailing_model == 'mail.mass_mailing.contact': + if mailing.mailing_model_real == 'mail.mass_mailing.contact': result = super(CustomUnsubscribe, self).mailing( - mailing_id, email, res_id, **post) - # FIXME Remove res_id and token in version where this is merged: - # https://github.com/odoo/odoo/pull/14385 + mailing_id, email, res_id, token=token, **post) result.qcontext.update({ - "token": token, - "res_id": res_id, "contacts": result.qcontext["contacts"].filtered( lambda contact: - not contact.list_id.not_cross_unsubscriptable or - contact.list_id <= mailing.contact_list_ids + not any(contact.list_ids.mapped( + 'not_cross_unsubscriptable')) or + contact.list_ids <= mailing.contact_list_ids ), "reasons": request.env["mail.unsubscription.reason"].search([]), @@ -85,7 +78,7 @@ class CustomUnsubscribe(MassMailController): # You could get a DetailsRequiredError here, but only if HTML5 # validation fails, which should not happen in modern browsers return super(CustomUnsubscribe, self).mailing( - mailing_id, email, res_id, **post) + mailing_id, email, res_id, token=token, **post) @route() def unsubscribe(self, mailing_id, opt_in_ids, opt_out_ids, email, res_id, @@ -107,10 +100,6 @@ class CustomUnsubscribe(MassMailController): if details: extra_context["default_details"] = details request.context = dict(request.context, **extra_context) - # FIXME Remove token check in version where this is merged: - # https://github.com/odoo/odoo/pull/14385 - mailing = request.env['mail.mass_mailing'].sudo().browse(mailing_id) - mailing._unsubscribe_token(res_id, token) _logger.debug( "Called `unsubscribe()` with: %r", (mailing_id, opt_in_ids, opt_out_ids, email, res_id, token, diff --git a/mass_mailing_custom_unsubscribe/exceptions.py b/mass_mailing_custom_unsubscribe/exceptions.py index bc9bbcc..ffff891 100644 --- a/mass_mailing_custom_unsubscribe/exceptions.py +++ b/mass_mailing_custom_unsubscribe/exceptions.py @@ -1,8 +1,7 @@ -# -*- coding: utf-8 -*- # Copyright 2016 Jairo Llopis # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). -from openerp import exceptions +from odoo import exceptions class DetailsRequiredError(exceptions.ValidationError): diff --git a/mass_mailing_custom_unsubscribe/hooks.py b/mass_mailing_custom_unsubscribe/hooks.py new file mode 100644 index 0000000..72fb665 --- /dev/null +++ b/mass_mailing_custom_unsubscribe/hooks.py @@ -0,0 +1,17 @@ +# Copyright 2018 David Vidal +# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). + +from odoo import api, SUPERUSER_ID + + +def post_init_hook(cr, registry): + """Ensure all existing contacts are going to work as v10""" + env = api.Environment(cr, SUPERUSER_ID, {}) + contacts = env['mail.mass_mailing.contact'].search([]) + for contact in contacts: + if len(contact.list_ids) <= 1: + continue + list_1 = contact.list_ids[0] + for list_ in contact.list_ids - list_1: + contact.copy({"list_ids": [(6, 0, list_.ids)]}) + contact.list_ids = list_1 diff --git a/mass_mailing_custom_unsubscribe/models/__init__.py b/mass_mailing_custom_unsubscribe/models/__init__.py index 991b56b..d74e7e1 100644 --- a/mass_mailing_custom_unsubscribe/models/__init__.py +++ b/mass_mailing_custom_unsubscribe/models/__init__.py @@ -1,7 +1,6 @@ -# -*- coding: utf-8 -*- # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). -from . import mail_mail from . import mail_mass_mailing +from . import mail_mass_mailing_contact from . import mail_mass_mailing_list from . import mail_unsubscription diff --git a/mass_mailing_custom_unsubscribe/models/mail_mail.py b/mass_mailing_custom_unsubscribe/models/mail_mail.py deleted file mode 100644 index fb3f1bf..0000000 --- a/mass_mailing_custom_unsubscribe/models/mail_mail.py +++ /dev/null @@ -1,14 +0,0 @@ -# -*- coding: utf-8 -*- -# Copyright 2016 Jairo Llopis -# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). - -from openerp import models - - -class MailMail(models.Model): - _inherit = 'mail.mail' - - def _get_unsubscribe_url(self, email_to): - result = super(MailMail, self)._get_unsubscribe_url(email_to) - token = self.mailing_id._unsubscribe_token(self.res_id) - return "%s&token=%s" % (result, token) diff --git a/mass_mailing_custom_unsubscribe/models/mail_mass_mailing.py b/mass_mailing_custom_unsubscribe/models/mail_mass_mailing.py index 2eec3d4..abd58a3 100644 --- a/mass_mailing_custom_unsubscribe/models/mail_mass_mailing.py +++ b/mass_mailing_custom_unsubscribe/models/mail_mass_mailing.py @@ -1,52 +1,27 @@ -# -*- coding: utf-8 -*- # Copyright 2016 Jairo Llopis # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). -import hmac -import hashlib -from openerp import api, models -from openerp.exceptions import AccessDenied -from openerp.tools import consteq +from odoo import models class MailMassMailing(models.Model): _inherit = "mail.mass_mailing" - @api.multi - def _unsubscribe_token(self, res_id, compare=None): - """Generate a secure hash for this mailing list and parameters. - This is appended to the unsubscription URL and then checked at - unsubscription time to ensure no malicious unsubscriptions are - performed. - - :param int res_id: - ID of the resource that will be unsubscribed. - - :param str compare: - Received token to be compared with the good one. - - :raise AccessDenied: - Will happen if you provide :param:`compare` and it does not match - the good token. - """ - secret = self.env["ir.config_parameter"].sudo().get_param( - "database.secret") - key = (self.env.cr.dbname, self.id, int(res_id)) - token = hmac.new(str(secret), repr(key), hashlib.sha512).hexdigest() - if compare is not None and not consteq(token, str(compare)): - raise AccessDenied() - return token - def update_opt_out(self, email, res_ids, value): """Save unsubscription reason when opting out from mailing.""" self.ensure_one() + model = self.env[self.mailing_model_real].with_context( + active_test=False) action = "unsubscription" if value else "subscription" - records = self.env[self.mailing_model].browse(res_ids) + records = self.env[model._name].browse(res_ids) previous = self.env["mail.unsubscription"].search(limit=1, args=[ ("mass_mailing_id", "=", self.id), ("email", "=", email), ("action", "=", action), ]) + if 'opt_out' not in model._fields: + return super(MailMassMailing, self).update_opt_out( + email, res_ids, value) for one in records: # Store action only when something changed, or there was no # previous subscription record @@ -59,5 +34,7 @@ class MailMassMailing(models.Model): "unsubscriber_id": "%s,%d" % (one._name, one.id), "action": action, }) + if model._name == 'mail.mass_mailing.contact': + pass return super(MailMassMailing, self).update_opt_out( email, res_ids, value) diff --git a/mass_mailing_custom_unsubscribe/models/mail_mass_mailing_contact.py b/mass_mailing_custom_unsubscribe/models/mail_mass_mailing_contact.py new file mode 100644 index 0000000..6f2f927 --- /dev/null +++ b/mass_mailing_custom_unsubscribe/models/mail_mass_mailing_contact.py @@ -0,0 +1,30 @@ +# Copyright 2018 David Vidal +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). + +from odoo import api, fields, models + + +class MailMassMailing(models.Model): + _inherit = "mail.mass_mailing.contact" + + # Recover the old Many2one field so we can set a contact by list + mailing_list_id = fields.Many2one( + 'mail.mass_mailing.list', + string='Mailing List', + ondelete='cascade', + compute="_compute_mailing_list_id", + inverse="_inverse_mailing_list_id", + search="_search_mailing_list_id", + ) + + @api.depends('list_ids') + def _compute_mailing_list_id(self): + for contact in self: + contact.mailing_list_id = contact.list_ids[:1] + + def _inverse_mailing_list_id(self): + for contact in self: + contact.list_ids = contact.mailing_list_id + + def _search_mailing_list_id(self, operator, value): + return [('list_ids', operator, value)] diff --git a/mass_mailing_custom_unsubscribe/models/mail_mass_mailing_list.py b/mass_mailing_custom_unsubscribe/models/mail_mass_mailing_list.py index a80a3fa..1e9cd66 100644 --- a/mass_mailing_custom_unsubscribe/models/mail_mass_mailing_list.py +++ b/mass_mailing_custom_unsubscribe/models/mail_mass_mailing_list.py @@ -1,8 +1,7 @@ -# -*- coding: utf-8 -*- # Copyright 2016 Pedro M. Baeza # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). -from openerp import fields, models +from odoo import fields, models class MailMassMailing(models.Model): diff --git a/mass_mailing_custom_unsubscribe/models/mail_unsubscription.py b/mass_mailing_custom_unsubscribe/models/mail_unsubscription.py index 148ae9d..d2a23e7 100644 --- a/mass_mailing_custom_unsubscribe/models/mail_unsubscription.py +++ b/mass_mailing_custom_unsubscribe/models/mail_unsubscription.py @@ -1,8 +1,9 @@ -# -*- coding: utf-8 -*- # Copyright 2016 Jairo Llopis # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). from odoo import _, api, fields, models +from odoo.addons.mass_mailing.models.mass_mailing import \ + MASS_MAILING_BUSINESS_MODELS from .. import exceptions @@ -35,13 +36,14 @@ class MailUnsubscription(models.Model): lambda self: self._selection_unsubscriber_id(), "(Un)subscriber", help="Who was subscribed or unsubscribed.") - mailing_list_id = fields.Many2one( - "mail.mass_mailing.list", - "Mailing list", + mailing_list_id = fields.Many2many( + comodel_name="mail.mass_mailing.list", + string="Mailing list", ondelete="set null", compute="_compute_mailing_list_id", store=True, help="(Un)subscribed mass mailing list, if any.", + readonly=False, ) reason_id = fields.Many2one( "mail.unsubscription.reason", @@ -57,6 +59,15 @@ class MailUnsubscription(models.Model): help="HTTP request metadata used when creating this record.", ) + def map_mailing_list_models(self, models): + model_mapped = [] + for model in models: + if model == 'mail.mass_mailing.list': + model_mapped.append(('mail.mass_mailing.contact', model)) + else: + model_mapped.append((model, model)) + return model_mapped + @api.model def _default_date(self): return fields.Datetime.now() @@ -64,7 +75,9 @@ class MailUnsubscription(models.Model): @api.model def _selection_unsubscriber_id(self): """Models that can be linked to a ``mail.mass_mailing``.""" - return self.env["mail.mass_mailing"]._get_mailing_model() + model = self.env['ir.model'].search( + [('model', 'in', MASS_MAILING_BUSINESS_MODELS)]).mapped('model') + return self.map_mailing_list_models(model) @api.multi @api.constrains("action", "reason_id") @@ -90,7 +103,7 @@ class MailUnsubscription(models.Model): """Get the mass mailing list, if it is possible.""" for one in self: try: - one.mailing_list_id = one.unsubscriber_id.list_id + one.mailing_list_id |= one.unsubscriber_id.mailing_list_id except AttributeError: # Possibly model != mail.mass_mailing.contact; no problem pass diff --git a/mass_mailing_custom_unsubscribe/readme/CONFIGURE.rst b/mass_mailing_custom_unsubscribe/readme/CONFIGURE.rst new file mode 100644 index 0000000..589e848 --- /dev/null +++ b/mass_mailing_custom_unsubscribe/readme/CONFIGURE.rst @@ -0,0 +1,10 @@ +Unsubscription Reasons +---------------------- + +You can customize what reasons will be displayed to your unsubscriptors when +they are going to unsubscribe. To do it: + +#. Go to *Mass Mailing > Configuration > Unsubscription Reasons*. +#. Create / edit / remove / sort as usual. +#. If *Details required* is enabled, they will have to fill a text area to + continue. diff --git a/mass_mailing_custom_unsubscribe/readme/CONTRIBUTORS.rst b/mass_mailing_custom_unsubscribe/readme/CONTRIBUTORS.rst new file mode 100644 index 0000000..493868e --- /dev/null +++ b/mass_mailing_custom_unsubscribe/readme/CONTRIBUTORS.rst @@ -0,0 +1,4 @@ +* Rafael Blasco +* Antonio Espinosa +* Jairo Llopis +* David Vidal diff --git a/mass_mailing_custom_unsubscribe/readme/DESCRIPTION.rst b/mass_mailing_custom_unsubscribe/readme/DESCRIPTION.rst new file mode 100644 index 0000000..6806342 --- /dev/null +++ b/mass_mailing_custom_unsubscribe/readme/DESCRIPTION.rst @@ -0,0 +1,8 @@ +This addon extends the unsubscription form to let you: + +- Choose which mailing lists are not cross-unsubscriptable when unsubscribing + from a different one. +- Know why and when a contact has been subscribed or unsubscribed from a + mass mailing. +- Provide proof on why you are sending mass mailings to a given contact, as + required by the GDPR in Europe. diff --git a/mass_mailing_custom_unsubscribe/readme/ROADMAP.rst b/mass_mailing_custom_unsubscribe/readme/ROADMAP.rst new file mode 100644 index 0000000..e94b7b8 --- /dev/null +++ b/mass_mailing_custom_unsubscribe/readme/ROADMAP.rst @@ -0,0 +1,11 @@ +* As version 11 has introduced a new relation type between mailing lists and + contacts that has multiple usability issues that are being reworked by Odoo + to land in version 12, this module falls back to the version 10 behaviour in + which one contact belonged to just one list. +* This module replaces AJAX submission core implementation from the mailing + list management form, because it is impossible to extend it. When + https://github.com/odoo/odoo/pull/14386 gets merged (which upstreams most + needed changes), this addon will need a refactoring (mostly removing + duplicated functionality and depending on it instead of replacing it). In the + mean time, there is a little chance that this introduces some + incompatibilities with other addons that depend on ``website_mass_mailing``. diff --git a/mass_mailing_custom_unsubscribe/readme/USAGE.rst b/mass_mailing_custom_unsubscribe/readme/USAGE.rst new file mode 100644 index 0000000..69f31e5 --- /dev/null +++ b/mass_mailing_custom_unsubscribe/readme/USAGE.rst @@ -0,0 +1,8 @@ +Once configured: + +#. Go to *Mass Mailing > Mailings > Mass Mailings > Create*. +#. Edit your mass mailing at wish, but remember to add a snippet from + *Footers*, so people have an *Unsubscribe* link. +#. Send it. +#. If somebody gets unsubscribed, you will see logs about that under + *Mass Mailing > Mailings > Unsubscriptions*. diff --git a/mass_mailing_custom_unsubscribe/static/src/js/partner.tour.js b/mass_mailing_custom_unsubscribe/static/src/js/partner.tour.js index 0d2365d..86bb842 100644 --- a/mass_mailing_custom_unsubscribe/static/src/js/partner.tour.js +++ b/mass_mailing_custom_unsubscribe/static/src/js/partner.tour.js @@ -39,7 +39,7 @@ odoo.define("mass_mailing_custom_unsubscribe.partner_tour", }, { content: "Successfully unsubscribed", - trigger: "body:not(:has(#reason_form)) .alert-success:contains('Your changes have been saved.')", + trigger: "body:not(:has(#reason_form)) .alert-success:contains('You have been successfully unsubscribed!')", }, ] ); diff --git a/mass_mailing_custom_unsubscribe/static/src/js/require_details.js b/mass_mailing_custom_unsubscribe/static/src/js/require_details.js index 6c778c6..4845894 100644 --- a/mass_mailing_custom_unsubscribe/static/src/js/require_details.js +++ b/mass_mailing_custom_unsubscribe/static/src/js/require_details.js @@ -3,7 +3,7 @@ odoo.define("mass_mailing_custom_unsubscribe.require_details", function (require) { "use strict"; - var animation = require("web_editor.snippets.animation"); + var animation = require("website.content.snippets.animation"); animation.registry.mass_mailing_custom_unsubscribe_require_details = animation.Class.extend({ diff --git a/mass_mailing_custom_unsubscribe/static/src/js/unsubscribe.js b/mass_mailing_custom_unsubscribe/static/src/js/unsubscribe.js index 12ec3a0..07c452f 100644 --- a/mass_mailing_custom_unsubscribe/static/src/js/unsubscribe.js +++ b/mass_mailing_custom_unsubscribe/static/src/js/unsubscribe.js @@ -1,4 +1,4 @@ -/* Copyright 2016 Jairo Llopis + /* Copyright 2016 Jairo Llopis * License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). */ /* TODO This JS module replaces core AJAX submission because it is impossible @@ -9,7 +9,7 @@ odoo.define("mass_mailing_custom_unsubscribe.unsubscribe", function (require) { "use strict"; var core = require("web.core"); var ajax = require("web.ajax"); - var animation = require("web_editor.snippets.animation"); + var animation = require("website.content.snippets.animation"); var _t = core._t; animation.registry.mass_mailing_unsubscribe = @@ -24,7 +24,7 @@ odoo.define("mass_mailing_custom_unsubscribe.unsubscribe", function (require) { this.$token = this.$("input[name='token']"); this.$res_id = this.$("input[name='res_id']"); this.$reasons = this.$(".js_unsubscription_reason"); - this.$details = this.$reasons.find("[name='details']") + this.$details = this.$reasons.find("[name='details']"); this.$el.on("submit", $.proxy(this.submit, this)); this.$contacts.on("change", $.proxy(this.toggle_reasons, this)); this.toggle_reasons(); diff --git a/mass_mailing_custom_unsubscribe/templates/mass_mailing_contact_reason.xml b/mass_mailing_custom_unsubscribe/templates/mass_mailing_contact_reason.xml index adc6dc5..21dc91c 100644 --- a/mass_mailing_custom_unsubscribe/templates/mass_mailing_contact_reason.xml +++ b/mass_mailing_custom_unsubscribe/templates/mass_mailing_contact_reason.xml @@ -10,7 +10,7 @@ - diff --git a/mass_mailing_custom_unsubscribe/tests/__init__.py b/mass_mailing_custom_unsubscribe/tests/__init__.py index bc46fde..a599c88 100644 --- a/mass_mailing_custom_unsubscribe/tests/__init__.py +++ b/mass_mailing_custom_unsubscribe/tests/__init__.py @@ -1,4 +1,3 @@ -# -*- coding: utf-8 -*- # Copyright 2016 Jairo Llopis # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). diff --git a/mass_mailing_custom_unsubscribe/tests/test_ui.py b/mass_mailing_custom_unsubscribe/tests/test_ui.py index 0f13f5b..9f8e24b 100644 --- a/mass_mailing_custom_unsubscribe/tests/test_ui.py +++ b/mass_mailing_custom_unsubscribe/tests/test_ui.py @@ -1,9 +1,8 @@ -# -*- coding: utf-8 -*- # Copyright 2016 Jairo Llopis # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). import mock from contextlib import contextmanager -from openerp.tests.common import HttpCase +from odoo.tests.common import HttpCase class UICase(HttpCase): @@ -37,7 +36,7 @@ class UICase(HttpCase): }) self.mailings += Mailing.create({ "name": "test mailing %d" % n, - "mailing_model": "mail.mass_mailing.contact", + "mailing_model_id": self.env["mail.mass_mailing.contact"], "contact_list_ids": [(6, 0, self.lists.ids)], "reply_to_mode": "thread", }) @@ -53,7 +52,7 @@ class UICase(HttpCase): self.contacts += Contact.create({ "name": "test contact %d" % n, "email": self.email, - "list_id": self.lists[n].id, + "mailing_list_id": self.lists[n].id, }) def tearDown(self): @@ -117,7 +116,8 @@ class UICase(HttpCase): # Change mailing to be sent to partner partner_id = env["res.partner"].name_create( "Demo Partner <%s>" % self.email)[0] - self.mailings[0].mailing_model = "res.partner" + self.mailings[0].mailing_model_id = self.env.ref( + "base.model_res_partner") self.mailings[0].mailing_domain = repr([ ('opt_out', '=', False), ('id', '=', partner_id), diff --git a/mass_mailing_custom_unsubscribe/tests/test_unsubscription.py b/mass_mailing_custom_unsubscribe/tests/test_unsubscription.py index b6d7043..660e7ab 100644 --- a/mass_mailing_custom_unsubscribe/tests/test_unsubscription.py +++ b/mass_mailing_custom_unsubscribe/tests/test_unsubscription.py @@ -1,8 +1,7 @@ -# -*- coding: utf-8 -*- # Copyright 2016 Jairo Llopis # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl). -from openerp.tests.common import SavepointCase +from odoo.tests.common import SavepointCase from .. import exceptions diff --git a/mass_mailing_custom_unsubscribe/views/mail_mass_mailing_contact_view.xml b/mass_mailing_custom_unsubscribe/views/mail_mass_mailing_contact_view.xml new file mode 100644 index 0000000..c0517a7 --- /dev/null +++ b/mass_mailing_custom_unsubscribe/views/mail_mass_mailing_contact_view.xml @@ -0,0 +1,30 @@ + + + + + + + mail.mass_mailing.contact + + + + 1 + + + + + + + + + mail.mass_mailing.contact + + + + + + + + + diff --git a/mass_mailing_custom_unsubscribe/views/mail_unsubscription_view.xml b/mass_mailing_custom_unsubscribe/views/mail_unsubscription_view.xml index 177b559..b222728 100644 --- a/mass_mailing_custom_unsubscribe/views/mail_unsubscription_view.xml +++ b/mass_mailing_custom_unsubscribe/views/mail_unsubscription_view.xml @@ -14,7 +14,7 @@ - + - +