odoo-addon-mail-gateway-whatsapp 17.0.1.1.1__py3-none-any.whl → 18.0.1.0.1__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- odoo/addons/mail_gateway_whatsapp/README.rst +6 -6
- odoo/addons/mail_gateway_whatsapp/__manifest__.py +1 -1
- odoo/addons/mail_gateway_whatsapp/i18n/es.po +12 -273
- odoo/addons/mail_gateway_whatsapp/i18n/it.po +12 -273
- odoo/addons/mail_gateway_whatsapp/i18n/mail_gateway_whatsapp.pot +1 -302
- odoo/addons/mail_gateway_whatsapp/models/mail_gateway.py +1 -1
- odoo/addons/mail_gateway_whatsapp/models/mail_gateway_whatsapp.py +14 -13
- odoo/addons/mail_gateway_whatsapp/models/mail_whatsapp_template.py +20 -544
- odoo/addons/mail_gateway_whatsapp/security/ir.model.access.csv +0 -4
- odoo/addons/mail_gateway_whatsapp/static/description/index.html +4 -4
- odoo/addons/mail_gateway_whatsapp/static/src/components/message/message_patch.esm.js +0 -1
- odoo/addons/mail_gateway_whatsapp/static/src/components/phone_field/phone_field.esm.js +2 -3
- odoo/addons/mail_gateway_whatsapp/static/src/components/send_whatsapp_button/send_whatsapp_button.esm.js +3 -5
- odoo/addons/mail_gateway_whatsapp/static/src/components/send_whatsapp_button/send_whatsapp_button.xml +5 -2
- odoo/addons/mail_gateway_whatsapp/tests/test_mail_gateway_whatsapp.py +22 -182
- odoo/addons/mail_gateway_whatsapp/tests/test_mail_whatsapp_template.py +2 -72
- odoo/addons/mail_gateway_whatsapp/tools/const.py +0 -2
- odoo/addons/mail_gateway_whatsapp/views/mail_gateway.xml +23 -24
- odoo/addons/mail_gateway_whatsapp/views/mail_whatsapp_template_views.xml +4 -60
- odoo/addons/mail_gateway_whatsapp/wizards/mail_compose_gateway_message.py +3 -9
- odoo/addons/mail_gateway_whatsapp/wizards/mail_compose_gateway_message.xml +0 -1
- odoo/addons/mail_gateway_whatsapp/wizards/whatsapp_composer.py +2 -3
- odoo/addons/mail_gateway_whatsapp/wizards/whatsapp_composer.xml +1 -4
- {odoo_addon_mail_gateway_whatsapp-17.0.1.1.1.dist-info → odoo_addon_mail_gateway_whatsapp-18.0.1.0.1.dist-info}/METADATA +10 -10
- {odoo_addon_mail_gateway_whatsapp-17.0.1.1.1.dist-info → odoo_addon_mail_gateway_whatsapp-18.0.1.0.1.dist-info}/RECORD +27 -27
- {odoo_addon_mail_gateway_whatsapp-17.0.1.1.1.dist-info → odoo_addon_mail_gateway_whatsapp-18.0.1.0.1.dist-info}/WHEEL +0 -0
- {odoo_addon_mail_gateway_whatsapp-17.0.1.1.1.dist-info → odoo_addon_mail_gateway_whatsapp-18.0.1.0.1.dist-info}/top_level.txt +0 -0
|
@@ -1,8 +1,7 @@
|
|
|
1
|
-
/** @odoo-module **/
|
|
2
|
-
|
|
3
1
|
import {PhoneField} from "@web/views/fields/phone/phone_field";
|
|
4
|
-
import {SendWhatsappButton} from "
|
|
2
|
+
import {SendWhatsappButton} from "../send_whatsapp_button/send_whatsapp_button.esm";
|
|
5
3
|
import {patch} from "@web/core/utils/patch";
|
|
4
|
+
|
|
6
5
|
patch(PhoneField, {
|
|
7
6
|
components: {
|
|
8
7
|
...PhoneField.components,
|
|
@@ -1,13 +1,11 @@
|
|
|
1
|
-
/** @odoo-module **/
|
|
2
|
-
|
|
3
1
|
import {useService} from "@web/core/utils/hooks";
|
|
4
2
|
import {_t} from "@web/core/l10n/translation";
|
|
5
|
-
|
|
3
|
+
import {user} from "@web/core/user";
|
|
4
|
+
import {Component, status} from "@odoo/owl";
|
|
6
5
|
|
|
7
6
|
export class SendWhatsappButton extends Component {
|
|
8
7
|
setup() {
|
|
9
8
|
this.action = useService("action");
|
|
10
|
-
this.user = useService("user");
|
|
11
9
|
this.title = _t("Send Whatsapp Message");
|
|
12
10
|
}
|
|
13
11
|
get phoneHref() {
|
|
@@ -23,7 +21,7 @@ export class SendWhatsappButton extends Component {
|
|
|
23
21
|
res_model: "whatsapp.composer",
|
|
24
22
|
views: [[false, "form"]],
|
|
25
23
|
context: {
|
|
26
|
-
...
|
|
24
|
+
...user.context,
|
|
27
25
|
default_res_model: this.props.record.resModel,
|
|
28
26
|
default_res_id: this.props.record.resId,
|
|
29
27
|
default_number_field_name: this.props.name,
|
|
@@ -1,13 +1,16 @@
|
|
|
1
1
|
<?xml version="1.0" encoding="UTF-8" ?>
|
|
2
2
|
<templates xml:space="preserve">
|
|
3
3
|
|
|
4
|
-
<t t-name="mail_gateway_whatsapp.SendWhatsappButton"
|
|
4
|
+
<t t-name="mail_gateway_whatsapp.SendWhatsappButton">
|
|
5
5
|
<a
|
|
6
6
|
t-att-title="title"
|
|
7
7
|
t-att-href="phoneHref"
|
|
8
8
|
t-on-click.prevent.stop="onClick"
|
|
9
9
|
class="ms-3 d-inline-flex align-items-center o_field_phone_whatsapp"
|
|
10
|
-
|
|
10
|
+
>
|
|
11
|
+
<i class="fa fa-whatsapp" />
|
|
12
|
+
<small class="fw-bold ms-1">Whatsapp</small>
|
|
13
|
+
</a>
|
|
11
14
|
</t>
|
|
12
15
|
|
|
13
16
|
</templates>
|
|
@@ -8,7 +8,6 @@ from unittest.mock import MagicMock, patch
|
|
|
8
8
|
|
|
9
9
|
from markupsafe import Markup
|
|
10
10
|
|
|
11
|
-
from odoo import Command
|
|
12
11
|
from odoo.exceptions import UserError
|
|
13
12
|
from odoo.tests import Form, RecordCapturer
|
|
14
13
|
from odoo.tests.common import tagged
|
|
@@ -158,14 +157,12 @@ class TestMailGatewayWhatsApp(MailGatewayTestCase):
|
|
|
158
157
|
data = json.dumps(message)
|
|
159
158
|
headers_dict = {"Content-Type": "application/json"}
|
|
160
159
|
if headers:
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
).hexdigest()
|
|
168
|
-
)
|
|
160
|
+
hex_dig = hmac.new(
|
|
161
|
+
self.gateway.webhook_secret.encode(),
|
|
162
|
+
data.encode(),
|
|
163
|
+
hashlib.sha256,
|
|
164
|
+
).hexdigest()
|
|
165
|
+
headers_dict["x-hub-signature-256"] = f"sha256={hex_dig}"
|
|
169
166
|
self.url_open(
|
|
170
167
|
f"/gateway/{self.gateway.gateway_type}/{webhook}/update",
|
|
171
168
|
data=data,
|
|
@@ -210,6 +207,7 @@ class TestMailGatewayWhatsApp(MailGatewayTestCase):
|
|
|
210
207
|
get_mock.return_value = GetImageResponse()
|
|
211
208
|
self.receive_message(self.message_02)
|
|
212
209
|
|
|
210
|
+
@mute_logger("odoo.addons.mail_gateway.controllers.gateway")
|
|
213
211
|
def test_post_no_signature_no_message(self):
|
|
214
212
|
self.gateway.webhook_key = self.webhook
|
|
215
213
|
self.gateway.set_webhook()
|
|
@@ -219,21 +217,20 @@ class TestMailGatewayWhatsApp(MailGatewayTestCase):
|
|
|
219
217
|
self.env["discuss.channel"].search([("gateway_id", "=", self.gateway.id)])
|
|
220
218
|
)
|
|
221
219
|
|
|
220
|
+
@mute_logger("odoo.addons.mail_gateway.controllers.gateway")
|
|
222
221
|
def test_post_wrong_signature_no_message(self):
|
|
223
222
|
self.gateway.webhook_key = self.webhook
|
|
224
223
|
self.gateway.set_webhook()
|
|
225
224
|
self.integrate_webhook()
|
|
226
225
|
data = json.dumps(self.message_01)
|
|
226
|
+
hex_dig = hmac.new(
|
|
227
|
+
self.gateway.webhook_secret.encode(),
|
|
228
|
+
data.encode(),
|
|
229
|
+
hashlib.sha256,
|
|
230
|
+
).hexdigest()
|
|
227
231
|
headers = {
|
|
228
232
|
"Content-Type": "application/json",
|
|
229
|
-
"x-hub-signature-256":
|
|
230
|
-
"sha256=1234%s"
|
|
231
|
-
% hmac.new(
|
|
232
|
-
self.gateway.webhook_secret.encode(),
|
|
233
|
-
data.encode(),
|
|
234
|
-
hashlib.sha256,
|
|
235
|
-
).hexdigest()
|
|
236
|
-
),
|
|
233
|
+
"x-hub-signature-256": f"sha256=1234{hex_dig}",
|
|
237
234
|
}
|
|
238
235
|
self.url_open(
|
|
239
236
|
f"/gateway/{self.gateway.gateway_type}/{self.webhook}/update",
|
|
@@ -326,9 +323,10 @@ class TestMailGatewayWhatsApp(MailGatewayTestCase):
|
|
|
326
323
|
("model", "=", channel._name),
|
|
327
324
|
("res_id", "=", channel.id),
|
|
328
325
|
]
|
|
329
|
-
with
|
|
330
|
-
"
|
|
331
|
-
|
|
326
|
+
with (
|
|
327
|
+
RecordCapturer(self.env["mail.message"], message_domain) as capture,
|
|
328
|
+
patch("requests.post") as post_mock,
|
|
329
|
+
):
|
|
332
330
|
post_mock.return_value = MagicMock()
|
|
333
331
|
composer.action_send_whatsapp()
|
|
334
332
|
self.assertEqual(len(capture.records), 1)
|
|
@@ -348,9 +346,10 @@ class TestMailGatewayWhatsApp(MailGatewayTestCase):
|
|
|
348
346
|
("model", "=", channel._name),
|
|
349
347
|
("res_id", "=", channel.id),
|
|
350
348
|
]
|
|
351
|
-
with
|
|
352
|
-
"
|
|
353
|
-
|
|
349
|
+
with (
|
|
350
|
+
RecordCapturer(self.env["mail.message"], message_domain) as capture,
|
|
351
|
+
patch("requests.post") as post_mock,
|
|
352
|
+
):
|
|
354
353
|
post_mock.return_value = MagicMock()
|
|
355
354
|
composer.action_send_whatsapp()
|
|
356
355
|
self.assertEqual(len(capture.records), 1)
|
|
@@ -383,162 +382,3 @@ class TestMailGatewayWhatsApp(MailGatewayTestCase):
|
|
|
383
382
|
post_mock.assert_called()
|
|
384
383
|
channel.invalidate_recordset()
|
|
385
384
|
self.assertTrue(channel.message_ids)
|
|
386
|
-
|
|
387
|
-
def test_send_message_with_variable(self):
|
|
388
|
-
ctx = {
|
|
389
|
-
"default_res_model": self.partner._name,
|
|
390
|
-
"default_res_id": self.partner.id,
|
|
391
|
-
"default_number_field_name": "mobile",
|
|
392
|
-
"default_composition_mode": "comment",
|
|
393
|
-
"default_gateway_id": self.gateway.id,
|
|
394
|
-
}
|
|
395
|
-
tmpl_with_vars = self.env["mail.whatsapp.template"].create(
|
|
396
|
-
{
|
|
397
|
-
"name": "Partner Vars",
|
|
398
|
-
"category": "utility",
|
|
399
|
-
"language": "es",
|
|
400
|
-
"header": "Hi {{1}}",
|
|
401
|
-
"body": "Name: {{1}} · Tel: {{2}}",
|
|
402
|
-
"gateway_id": self.gateway.id,
|
|
403
|
-
"variable_ids": [Command.clear()],
|
|
404
|
-
"state": "approved",
|
|
405
|
-
"is_supported": True,
|
|
406
|
-
"model_id": self.env["ir.model"]._get("res.partner").id,
|
|
407
|
-
}
|
|
408
|
-
)
|
|
409
|
-
self.env["mail.whatsapp.template.variable"].create(
|
|
410
|
-
{
|
|
411
|
-
"name": "{{1}}",
|
|
412
|
-
"line_type": "header",
|
|
413
|
-
"template_id": tmpl_with_vars.id,
|
|
414
|
-
"field_name": "name",
|
|
415
|
-
}
|
|
416
|
-
)
|
|
417
|
-
self.env["mail.whatsapp.template.variable"].create(
|
|
418
|
-
{
|
|
419
|
-
"name": "{{1}}",
|
|
420
|
-
"line_type": "body",
|
|
421
|
-
"template_id": tmpl_with_vars.id,
|
|
422
|
-
"field_name": "name",
|
|
423
|
-
}
|
|
424
|
-
)
|
|
425
|
-
self.env["mail.whatsapp.template.variable"].create(
|
|
426
|
-
{
|
|
427
|
-
"name": "{{2}}",
|
|
428
|
-
"line_type": "body",
|
|
429
|
-
"template_id": tmpl_with_vars.id,
|
|
430
|
-
"field_name": "mobile",
|
|
431
|
-
}
|
|
432
|
-
)
|
|
433
|
-
self.env["mail.whatsapp.template.button"].create(
|
|
434
|
-
{
|
|
435
|
-
"name": "mobile",
|
|
436
|
-
"button_type": "phone_number",
|
|
437
|
-
"template_id": tmpl_with_vars.id,
|
|
438
|
-
"call_number": "+34666555444",
|
|
439
|
-
}
|
|
440
|
-
)
|
|
441
|
-
self.assertEqual(len(tmpl_with_vars.variable_ids), 3)
|
|
442
|
-
self.assertEqual(len(tmpl_with_vars.button_ids), 1)
|
|
443
|
-
self.gateway.whatsapp_account_id = "123456"
|
|
444
|
-
form_composer = Form(self.env["whatsapp.composer"].with_context(**ctx))
|
|
445
|
-
form_composer.template_id = tmpl_with_vars
|
|
446
|
-
self.assertTrue(form_composer.is_required_template)
|
|
447
|
-
self.assertTrue(form_composer._get_modifier("template_id", "required"))
|
|
448
|
-
composer = form_composer.save()
|
|
449
|
-
channel = self.partner._whatsapp_get_channel(
|
|
450
|
-
composer.number_field_name, composer.gateway_id
|
|
451
|
-
)
|
|
452
|
-
message_domain = [
|
|
453
|
-
("gateway_type", "=", "whatsapp"),
|
|
454
|
-
("model", "=", channel._name),
|
|
455
|
-
("res_id", "=", channel.id),
|
|
456
|
-
]
|
|
457
|
-
with RecordCapturer(self.env["mail.message"], message_domain) as capture, patch(
|
|
458
|
-
"requests.post"
|
|
459
|
-
) as post_mock:
|
|
460
|
-
post_mock.return_value = MagicMock()
|
|
461
|
-
composer.action_send_whatsapp()
|
|
462
|
-
# Assertions
|
|
463
|
-
self.assertEqual(len(capture.records), 1)
|
|
464
|
-
channel.invalidate_recordset()
|
|
465
|
-
self.assertTrue(channel.message_ids)
|
|
466
|
-
|
|
467
|
-
def test_send_message_with_dynamic_button(self):
|
|
468
|
-
ctx = {
|
|
469
|
-
"default_res_model": self.partner._name,
|
|
470
|
-
"default_res_id": self.partner.id,
|
|
471
|
-
"default_number_field_name": "mobile",
|
|
472
|
-
"default_composition_mode": "comment",
|
|
473
|
-
"default_gateway_id": self.gateway.id,
|
|
474
|
-
}
|
|
475
|
-
tmpl_with_vars_dynamic = self.env["mail.whatsapp.template"].create(
|
|
476
|
-
{
|
|
477
|
-
"name": "Dynamic Button",
|
|
478
|
-
"category": "utility",
|
|
479
|
-
"language": "es",
|
|
480
|
-
"body": "Name: {{1}} · Tel: {{2}}",
|
|
481
|
-
"gateway_id": self.gateway.id,
|
|
482
|
-
"variable_ids": [Command.clear()],
|
|
483
|
-
"state": "approved",
|
|
484
|
-
"is_supported": True,
|
|
485
|
-
"model_id": self.env["ir.model"]._get("res.partner").id,
|
|
486
|
-
}
|
|
487
|
-
)
|
|
488
|
-
self.assertEqual(len(tmpl_with_vars_dynamic.variable_ids), 0)
|
|
489
|
-
self.env["mail.whatsapp.template.variable"].create(
|
|
490
|
-
{
|
|
491
|
-
"name": "{{1}}",
|
|
492
|
-
"line_type": "body",
|
|
493
|
-
"template_id": tmpl_with_vars_dynamic.id,
|
|
494
|
-
"field_name": "name",
|
|
495
|
-
}
|
|
496
|
-
)
|
|
497
|
-
self.env["mail.whatsapp.template.variable"].create(
|
|
498
|
-
{
|
|
499
|
-
"name": "{{2}}",
|
|
500
|
-
"line_type": "body",
|
|
501
|
-
"template_id": tmpl_with_vars_dynamic.id,
|
|
502
|
-
"field_name": "mobile",
|
|
503
|
-
}
|
|
504
|
-
)
|
|
505
|
-
self.env["mail.whatsapp.template.button"].create(
|
|
506
|
-
{
|
|
507
|
-
"name": "1",
|
|
508
|
-
"button_type": "url",
|
|
509
|
-
"url_type": "dynamic",
|
|
510
|
-
"template_id": tmpl_with_vars_dynamic.id,
|
|
511
|
-
"website_url": "https://www.odoo.com",
|
|
512
|
-
}
|
|
513
|
-
)
|
|
514
|
-
self.assertEqual(len(tmpl_with_vars_dynamic.variable_ids), 3)
|
|
515
|
-
button = tmpl_with_vars_dynamic.variable_ids.search(
|
|
516
|
-
[
|
|
517
|
-
("line_type", "=", "button"),
|
|
518
|
-
("template_id", "=", tmpl_with_vars_dynamic.id),
|
|
519
|
-
]
|
|
520
|
-
)
|
|
521
|
-
button.field_name = "name"
|
|
522
|
-
self.gateway.whatsapp_account_id = "123456"
|
|
523
|
-
form_composer = Form(self.env["whatsapp.composer"].with_context(**ctx))
|
|
524
|
-
form_composer.template_id = tmpl_with_vars_dynamic
|
|
525
|
-
self.assertTrue(form_composer.is_required_template)
|
|
526
|
-
self.assertTrue(form_composer._get_modifier("template_id", "required"))
|
|
527
|
-
composer = form_composer.save()
|
|
528
|
-
channel = self.partner._whatsapp_get_channel(
|
|
529
|
-
composer.number_field_name, composer.gateway_id
|
|
530
|
-
)
|
|
531
|
-
message_domain = [
|
|
532
|
-
("gateway_type", "=", "whatsapp"),
|
|
533
|
-
("model", "=", channel._name),
|
|
534
|
-
("res_id", "=", channel.id),
|
|
535
|
-
]
|
|
536
|
-
with RecordCapturer(self.env["mail.message"], message_domain) as capture, patch(
|
|
537
|
-
"requests.post"
|
|
538
|
-
) as post_mock:
|
|
539
|
-
post_mock.return_value = MagicMock()
|
|
540
|
-
composer.action_send_whatsapp()
|
|
541
|
-
# Assertions
|
|
542
|
-
self.assertEqual(len(capture.records), 1)
|
|
543
|
-
channel.invalidate_recordset()
|
|
544
|
-
self.assertTrue(channel.message_ids)
|
|
@@ -6,7 +6,6 @@ from unittest.mock import patch
|
|
|
6
6
|
|
|
7
7
|
import requests
|
|
8
8
|
|
|
9
|
-
from odoo import Command
|
|
10
9
|
from odoo.exceptions import UserError
|
|
11
10
|
from odoo.tests.common import tagged
|
|
12
11
|
|
|
@@ -122,7 +121,7 @@ class TestMailWhatsAppTemplate(MailGatewayTestCase):
|
|
|
122
121
|
template_2 = self.gateway.whatsapp_template_ids.filtered(
|
|
123
122
|
lambda t: t.template_uid == "0987654321"
|
|
124
123
|
)
|
|
125
|
-
self.
|
|
124
|
+
self.assertFalse(template_2.is_supported)
|
|
126
125
|
self.assertEqual(template_2.template_name, "test_with_buttons")
|
|
127
126
|
self.assertEqual(template_2.category, "marketing")
|
|
128
127
|
self.assertEqual(template_2.language, "es")
|
|
@@ -130,6 +129,7 @@ class TestMailWhatsAppTemplate(MailGatewayTestCase):
|
|
|
130
129
|
self.assertEqual(template_2.header, "Header 2")
|
|
131
130
|
self.assertEqual(template_2.body, "Body 2")
|
|
132
131
|
self.assertFalse(template_2.footer)
|
|
132
|
+
self.assertFalse(template_2.is_supported)
|
|
133
133
|
|
|
134
134
|
def test_export_template(self):
|
|
135
135
|
def _patch_request_post(url, *args, **kwargs):
|
|
@@ -168,73 +168,3 @@ class TestMailWhatsAppTemplate(MailGatewayTestCase):
|
|
|
168
168
|
with patch.object(requests, "get", _patch_request_get):
|
|
169
169
|
new_template.button_sync_template()
|
|
170
170
|
self.assertEqual(new_template.footer, "Footer changed")
|
|
171
|
-
|
|
172
|
-
def test_prepare_values_template_send(self):
|
|
173
|
-
partner = self.env["res.partner"].create(
|
|
174
|
-
{
|
|
175
|
-
"name": "Ada Lovelace",
|
|
176
|
-
"mobile": "+34900111222",
|
|
177
|
-
}
|
|
178
|
-
)
|
|
179
|
-
ctx = {
|
|
180
|
-
"default_res_model": partner._name,
|
|
181
|
-
"default_res_id": partner.id,
|
|
182
|
-
}
|
|
183
|
-
tmpl = self.env["mail.whatsapp.template"].create(
|
|
184
|
-
{
|
|
185
|
-
"name": "Test Render",
|
|
186
|
-
"category": "utility",
|
|
187
|
-
"language": "es",
|
|
188
|
-
"header": "Hi {{1}}",
|
|
189
|
-
"body": "Name: {{1}} · Tel: {{2}}",
|
|
190
|
-
"gateway_id": self.gateway.id,
|
|
191
|
-
"variable_ids": [Command.clear()],
|
|
192
|
-
"state": "approved",
|
|
193
|
-
"is_supported": True,
|
|
194
|
-
"model_id": self.env["ir.model"]._get("res.partner").id,
|
|
195
|
-
}
|
|
196
|
-
)
|
|
197
|
-
self.env["mail.whatsapp.template.variable"].create(
|
|
198
|
-
{
|
|
199
|
-
"name": "{{1}}",
|
|
200
|
-
"line_type": "header",
|
|
201
|
-
"template_id": tmpl.id,
|
|
202
|
-
"field_name": "name",
|
|
203
|
-
}
|
|
204
|
-
)
|
|
205
|
-
self.env["mail.whatsapp.template.variable"].create(
|
|
206
|
-
{
|
|
207
|
-
"name": "{{1}}",
|
|
208
|
-
"line_type": "body",
|
|
209
|
-
"template_id": tmpl.id,
|
|
210
|
-
"field_name": "name",
|
|
211
|
-
}
|
|
212
|
-
)
|
|
213
|
-
self.env["mail.whatsapp.template.variable"].create(
|
|
214
|
-
{
|
|
215
|
-
"name": "{{2}}",
|
|
216
|
-
"line_type": "body",
|
|
217
|
-
"template_id": tmpl.id,
|
|
218
|
-
"field_name": "mobile",
|
|
219
|
-
}
|
|
220
|
-
)
|
|
221
|
-
self.env["mail.whatsapp.template.button"].create(
|
|
222
|
-
{
|
|
223
|
-
"name": "mobile",
|
|
224
|
-
"button_type": "phone_number",
|
|
225
|
-
"template_id": tmpl.id,
|
|
226
|
-
"call_number": "+34666555444",
|
|
227
|
-
}
|
|
228
|
-
)
|
|
229
|
-
components = tmpl.with_context(**ctx).prepare_value_to_send()
|
|
230
|
-
|
|
231
|
-
header = next(c for c in components if c["type"].upper() == "HEADER")
|
|
232
|
-
self.assertEqual([p["type"] for p in header.get("parameters", [])], ["text"])
|
|
233
|
-
self.assertEqual(header["parameters"][0]["text"], partner.name)
|
|
234
|
-
|
|
235
|
-
body = next(c for c in components if c["type"].upper() == "BODY")
|
|
236
|
-
self.assertEqual(
|
|
237
|
-
[p["type"] for p in body.get("parameters", [])], ["text", "text"]
|
|
238
|
-
)
|
|
239
|
-
self.assertEqual(body["parameters"][0]["text"], partner.name)
|
|
240
|
-
self.assertEqual(body["parameters"][1]["text"], partner.mobile or "")
|
|
@@ -55,21 +55,21 @@
|
|
|
55
55
|
<div>
|
|
56
56
|
<h2>First steps</h2>
|
|
57
57
|
<span>Define the values of the fields <b>Webhook Key</b> and <b
|
|
58
|
-
|
|
58
|
+
>Whatsapp Security Key</b>.
|
|
59
59
|
You should set some random value of your choice for this fields.
|
|
60
60
|
Ensure that facebook will be able to comunicate with your server.</span>
|
|
61
61
|
<h2>Creating the Application from meta developer</h2>
|
|
62
62
|
<ol>
|
|
63
63
|
<li>Access
|
|
64
64
|
<a
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
65
|
+
href="https://developers.facebook.com/apps/?show_reminder=true"
|
|
66
|
+
target="_blank"
|
|
67
|
+
rel="noopener noreferrer"
|
|
68
|
+
>
|
|
69
69
|
Meta developer platform</a>.</li>
|
|
70
70
|
<li>Create a new application.</li>
|
|
71
71
|
<li>Select the <b>Other</b> option, then <b
|
|
72
|
-
|
|
72
|
+
>Business</b> in order to create Whatsapp manager</li>
|
|
73
73
|
<li>Select a name and create it</li>
|
|
74
74
|
<li
|
|
75
75
|
>Select the Whatsapp API on the products of the application</li>
|
|
@@ -77,27 +77,27 @@
|
|
|
77
77
|
<li>Go to <b>Whatsapp / API Configuration</b> menú.</li>
|
|
78
78
|
<li>Add a new number.</li>
|
|
79
79
|
<li>Copy the phone identification number to the field <b
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
80
|
+
>Whastapp From phone</b> field.</li>
|
|
81
|
+
<li>Access the menu <b
|
|
82
|
+
>Configuration / Basic information</b>.</li>
|
|
83
|
+
<li
|
|
84
84
|
>Show the secret key of the application and copy it to the <b
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
85
|
+
>Webhook secret</b> field.</li>
|
|
86
|
+
<li>Access the menu <b
|
|
87
|
+
>Configuration / Advanced Options</b>.</li>
|
|
88
|
+
<li>Copy the API Version on the <b
|
|
89
|
+
>Whastapp Version</b> field.</li>
|
|
90
90
|
</ol>
|
|
91
91
|
<h2>Creating a permanent token</h2>
|
|
92
92
|
<ol>
|
|
93
93
|
<li>Access your <a
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
94
|
+
href="https://business.facebook.com/"
|
|
95
|
+
target="_blank"
|
|
96
|
+
rel="noopener noreferrer"
|
|
97
|
+
>meta business site.</a></li>
|
|
98
98
|
<li>Access your business settings menu</li>
|
|
99
99
|
<li>Go to <b
|
|
100
|
-
|
|
100
|
+
>Users / System Users</b> and create a new one with administrator</li>
|
|
101
101
|
<li
|
|
102
102
|
>Once it is created, Generate a new token related to the created app with no expiry and give access to all whatsapp permissions.</li>
|
|
103
103
|
<li>Copy the token value to token field in this page.</li>
|
|
@@ -108,11 +108,11 @@
|
|
|
108
108
|
<li>Press the button Integrate webhook.</li>
|
|
109
109
|
<li
|
|
110
110
|
>On Facebook Develpment, return to the app menu and go to <b
|
|
111
|
-
|
|
111
|
+
>Whatsapp / Configuration</b>.</li>
|
|
112
112
|
<li>Click on <b>Edit Button</b> on the webhook area.</li>
|
|
113
113
|
<li>On the wizard, fill the URL field with <b
|
|
114
|
-
|
|
115
|
-
|
|
114
|
+
>Webhook URL</b> field of the gateway. For the verification identifier, use the <b
|
|
115
|
+
>Whatsapp Security Key</b> field.</li>
|
|
116
116
|
<li>Verify and save the wizard.</li>
|
|
117
117
|
<li
|
|
118
118
|
>If no error is raised, refresh this gateway data, and you should see that it is integrated.
|
|
@@ -120,7 +120,6 @@
|
|
|
120
120
|
If an error is raised, check that the fields are filled properly and that facebook server is able to access your server.</li>
|
|
121
121
|
</ol>
|
|
122
122
|
</div>
|
|
123
|
-
|
|
124
123
|
</page>
|
|
125
124
|
</notebook>
|
|
126
125
|
</field>
|
|
@@ -1,11 +1,10 @@
|
|
|
1
1
|
<?xml version="1.0" encoding="utf-8" ?>
|
|
2
2
|
<odoo>
|
|
3
|
-
|
|
4
3
|
<record id="view_mail_whatsapp_template_tree" model="ir.ui.view">
|
|
5
4
|
<field name="name">view.mail.whatsapp.template.tree</field>
|
|
6
5
|
<field name="model">mail.whatsapp.template</field>
|
|
7
6
|
<field name="arch" type="xml">
|
|
8
|
-
<
|
|
7
|
+
<list decoration-danger="not is_supported and template_uid">
|
|
9
8
|
<field name="name" />
|
|
10
9
|
<field name="template_name" />
|
|
11
10
|
<field name="template_uid" optional="show" />
|
|
@@ -24,7 +23,7 @@
|
|
|
24
23
|
widget="badge"
|
|
25
24
|
/>
|
|
26
25
|
<field name="is_supported" optional="show" />
|
|
27
|
-
</
|
|
26
|
+
</list>
|
|
28
27
|
</field>
|
|
29
28
|
</record>
|
|
30
29
|
|
|
@@ -65,7 +64,7 @@
|
|
|
65
64
|
invisible="is_supported or not template_uid"
|
|
66
65
|
>
|
|
67
66
|
This template is not supported because has <strong
|
|
68
|
-
|
|
67
|
+
>variables</strong> or <strong>buttons</strong>.
|
|
69
68
|
</div>
|
|
70
69
|
<sheet>
|
|
71
70
|
<div class="oe_title">
|
|
@@ -85,7 +84,6 @@
|
|
|
85
84
|
readonly="state != 'draft'"
|
|
86
85
|
options="{'no_create': True}"
|
|
87
86
|
/>
|
|
88
|
-
<field name="model_id" />
|
|
89
87
|
<field name="category" readonly="state != 'draft'" />
|
|
90
88
|
<field name="language" readonly="state != 'draft'" />
|
|
91
89
|
</group>
|
|
@@ -106,59 +104,6 @@
|
|
|
106
104
|
<page name="body" string="Body">
|
|
107
105
|
<field name="body" readonly="state != 'draft'" />
|
|
108
106
|
</page>
|
|
109
|
-
<page name="buttons" string="Buttons">
|
|
110
|
-
<field name="button_ids" readonly="state != 'draft'">
|
|
111
|
-
<tree editable="bottom">
|
|
112
|
-
<field name="sequence" widget="handle" />
|
|
113
|
-
<field name="button_type" />
|
|
114
|
-
<field
|
|
115
|
-
name="url_type"
|
|
116
|
-
readonly="button_type != 'url'"
|
|
117
|
-
required="button_type == 'url'"
|
|
118
|
-
invisible="button_type != 'url'"
|
|
119
|
-
/>
|
|
120
|
-
<field name="name" required="1" />
|
|
121
|
-
<field
|
|
122
|
-
name="website_url"
|
|
123
|
-
readonly="button_type != 'url'"
|
|
124
|
-
required="button_type == 'url'"
|
|
125
|
-
invisible="button_type != 'url'"
|
|
126
|
-
placeholder="e.g. https://www.example.com"
|
|
127
|
-
/>
|
|
128
|
-
<field
|
|
129
|
-
name="call_number"
|
|
130
|
-
readonly="button_type != 'phone_number'"
|
|
131
|
-
required="button_type == 'phone_number'"
|
|
132
|
-
invisible="button_type != 'phone_number'"
|
|
133
|
-
/>
|
|
134
|
-
</tree>
|
|
135
|
-
</field>
|
|
136
|
-
</page>
|
|
137
|
-
<page name="variables" string="Variables">
|
|
138
|
-
<field name="variable_ids">
|
|
139
|
-
<tree editable="bottom" create="0" delete="0">
|
|
140
|
-
<field name="display_name" string="Name" />
|
|
141
|
-
<field name="sample_value" required="1" />
|
|
142
|
-
<field
|
|
143
|
-
name="field_name"
|
|
144
|
-
widget="DynamicModelFieldSelectorChar"
|
|
145
|
-
required="1"
|
|
146
|
-
options="{'model': 'model'}"
|
|
147
|
-
/>
|
|
148
|
-
<field name="model" column_invisible="True" />
|
|
149
|
-
<field
|
|
150
|
-
name="line_type"
|
|
151
|
-
column_invisible="True"
|
|
152
|
-
force_save="1"
|
|
153
|
-
/>
|
|
154
|
-
<field
|
|
155
|
-
name="name"
|
|
156
|
-
column_invisible="True"
|
|
157
|
-
force_save="1"
|
|
158
|
-
/>
|
|
159
|
-
</tree>
|
|
160
|
-
</field>
|
|
161
|
-
</page>
|
|
162
107
|
</notebook>
|
|
163
108
|
</sheet>
|
|
164
109
|
</form>
|
|
@@ -185,9 +130,8 @@
|
|
|
185
130
|
<field name="name">WhatsApp Templates</field>
|
|
186
131
|
<field name="type">ir.actions.act_window</field>
|
|
187
132
|
<field name="res_model">mail.whatsapp.template</field>
|
|
188
|
-
<field name="view_mode">
|
|
133
|
+
<field name="view_mode">list,form</field>
|
|
189
134
|
<field name="domain">[('gateway_id', '=', active_id)]</field>
|
|
190
135
|
<field name="context">{'default_gateway_id': active_id}</field>
|
|
191
136
|
</record>
|
|
192
|
-
|
|
193
137
|
</odoo>
|
|
@@ -13,22 +13,16 @@ class MailComposeGatewayMessage(models.TransientModel):
|
|
|
13
13
|
"mail.whatsapp.template",
|
|
14
14
|
domain="""[
|
|
15
15
|
('state', '=', 'approved'),
|
|
16
|
-
('is_supported', '=', True)
|
|
17
|
-
('model', '=', model)
|
|
16
|
+
('is_supported', '=', True)
|
|
18
17
|
]""",
|
|
19
18
|
)
|
|
20
19
|
|
|
21
20
|
@api.onchange("whatsapp_template_id")
|
|
22
21
|
def onchange_whatsapp_template_id(self):
|
|
23
22
|
if self.whatsapp_template_id:
|
|
24
|
-
self.body = markupsafe.Markup(
|
|
25
|
-
self.whatsapp_template_id.render_body_message()
|
|
26
|
-
)
|
|
23
|
+
self.body = markupsafe.Markup(self.whatsapp_template_id.body)
|
|
27
24
|
|
|
28
25
|
def _action_send_mail(self, auto_commit=False):
|
|
29
26
|
if self.whatsapp_template_id:
|
|
30
|
-
self = self.with_context(
|
|
31
|
-
whatsapp_template_id=self.whatsapp_template_id.id,
|
|
32
|
-
res_id=int(self.res_ids.strip("[]")),
|
|
33
|
-
)
|
|
27
|
+
self = self.with_context(whatsapp_template_id=self.whatsapp_template_id.id)
|
|
34
28
|
return super()._action_send_mail(auto_commit=auto_commit)
|