diff --git a/frappe/email/doctype/email_account/email_account.js b/frappe/email/doctype/email_account/email_account.js index 5d65a8efe6..9fd9c1a0bf 100644 --- a/frappe/email/doctype/email_account/email_account.js +++ b/frappe/email/doctype/email_account/email_account.js @@ -93,6 +93,7 @@ frappe.ui.form.on("Email Account", { }); } frm.events.show_gmail_message_for_less_secure_apps(frm); + frm.events.toggle_auth_method(frm); }, use_imap: function(frm) { @@ -134,6 +135,7 @@ frappe.ui.form.on("Email Account", { frm.add_child("imap_folder", {"folder_name": "INBOX"}); frm.refresh_field("imap_folder"); } + frm.toggle_display(['auth_method'], frm.doc.service === "GMail"); }, refresh: function(frm) { @@ -150,11 +152,20 @@ frappe.ui.form.on("Email Account", { }, after_save(frm) { - if (frm.doc.use_oauth && !frm.doc.refresh_token) { + if (frm.doc.auth_method === "Oauth" && !frm.doc.refresh_token) { oauth_access(frm); } }, + toggle_auth_method: function(frm) { + if (frm.doc.service !== "GMail") { + frm.toggle_display(['auth_method'], false); + frm.doc.auth_method = "Basic"; + } else { + frm.toggle_display(['auth_method'], true); + } + }, + show_gmail_message_for_less_secure_apps: function(frm) { frm.dashboard.clear_headline(); let msg = __("GMail will only work if you enable 2-step authentication and use app-specific password OR use OAuth."); @@ -166,8 +177,8 @@ frappe.ui.form.on("Email Account", { }, show_oauth_authorization_message(frm) { - let msg = __("Oauth Enabled but not Authorized. Please use `Authorize API Access` Button to do the same."); - if (frm.doc.use_oauth && !frm.doc.refresh_token) { + if (frm.doc.auth_method === "Oauth" && !frm.doc.refresh_token) { + let msg = __("Oauth Enabled but not Authorized. Please use Authorize API Access Button to do the same."); frm.dashboard.clear_headline(); frm.dashboard.set_headline_alert(msg, "yellow"); } diff --git a/frappe/email/doctype/email_account/email_account.json b/frappe/email/doctype/email_account/email_account.json index bd4023d62b..2c42010897 100644 --- a/frappe/email/doctype/email_account/email_account.json +++ b/frappe/email/doctype/email_account/email_account.json @@ -14,12 +14,12 @@ "domain", "service", "authentication_column", + "auth_method", + "authorize_api_access", "password", "awaiting_password", "ascii_encode_password", "column_break_10", - "use_oauth", - "authorize_api_access", "refresh_token", "access_token", "login_id_is_different", @@ -103,6 +103,7 @@ "label": "Email Login ID" }, { + "depends_on": "eval: doc.auth_method === \"Basic\"", "fieldname": "password", "fieldtype": "Password", "hide_days": 1, @@ -111,6 +112,7 @@ }, { "default": "0", + "depends_on": "eval: doc.auth_method === \"Basic\"", "fieldname": "awaiting_password", "fieldtype": "Check", "hide_days": 1, @@ -119,6 +121,7 @@ }, { "default": "0", + "depends_on": "eval: doc.auth_method === \"Basic\"", "fieldname": "ascii_encode_password", "fieldtype": "Check", "hide_days": 1, @@ -583,14 +586,7 @@ "label": "IMAP Details" }, { - "default": "0", - "depends_on": "eval: doc.service === \"GMail\"", - "fieldname": "use_oauth", - "fieldtype": "Check", - "label": "Use OAuth" - }, - { - "depends_on": "eval: doc.service === \"GMail\" && doc.use_oauth && !doc.__islocal && !doc.__unsaved", + "depends_on": "eval: doc.service === \"GMail\" && doc.auth_method === \"Oauth\" && !doc.__islocal && !doc.__unsaved", "fieldname": "authorize_api_access", "fieldtype": "Button", "label": "Authorize API Access" @@ -608,12 +604,19 @@ "hidden": 1, "label": "Access Token", "read_only": 1 + }, + { + "default": "Basic", + "fieldname": "auth_method", + "fieldtype": "Select", + "label": "Method", + "options": "Basic\nOauth" } ], "icon": "fa fa-inbox", "index_web_pages_for_search": 1, "links": [], - "modified": "2022-07-11 15:11:15.196935", + "modified": "2022-07-11 17:29:13.651583", "modified_by": "Administrator", "module": "Email", "name": "Email Account", diff --git a/frappe/email/doctype/email_account/email_account.py b/frappe/email/doctype/email_account/email_account.py index d3273ab89d..a3d4b3ba32 100755 --- a/frappe/email/doctype/email_account/email_account.py +++ b/frappe/email/doctype/email_account/email_account.py @@ -81,10 +81,13 @@ class EmailAccount(Document): if frappe.local.flags.in_patch or frappe.local.flags.in_test: return - if getattr(self, "service", "") != "GMail" and self.use_oauth: - self.use_oauth = 0 + use_oauth = self.auth_method == "Oauth" - if self.use_oauth: + if getattr(self, "service", "") != "GMail" and use_oauth: + self.auth_method = "Basic" + use_oauth = False + + if use_oauth: # no need for awaiting password for oauth self.awaiting_password = 0 @@ -92,7 +95,7 @@ class EmailAccount(Document): # clear access & refresh token self.refresh_token = self.access_token = None - if not frappe.local.flags.in_install and (self.use_oauth or not self.awaiting_password): + if not frappe.local.flags.in_install and (use_oauth or not self.awaiting_password): if self.refresh_token or self.password or self.smtp_server in ("127.0.0.1", "localhost"): if self.enable_incoming: self.get_incoming_server() @@ -102,7 +105,7 @@ class EmailAccount(Document): self.validate_smtp_conn() else: if self.enable_incoming or (self.enable_outgoing and not self.no_smtp_authentication): - if not self.use_oauth: + if not use_oauth: frappe.throw(_("Password is required or select Awaiting Password")) if self.notify_if_unreplied: @@ -155,7 +158,7 @@ class EmailAccount(Document): awaiting_password=self.awaiting_password, email_id=self.email_id, enable_outgoing=self.enable_outgoing, - used_oauth=self.use_oauth, + used_oauth=self.auth_method == "Oauth", ) def there_must_be_only_one_default(self): @@ -210,7 +213,7 @@ class EmailAccount(Document): "email_sync_rule": email_sync_rule, "incoming_port": get_port(self), "initial_sync_count": self.initial_sync_count or 100, - "use_oauth": self.use_oauth or 0, + "use_oauth": self.auth_method == "Oauth", "refresh_token": decrypt(self.refresh_token) if self.refresh_token else None, "access_token": decrypt(self.access_token) if self.access_token else None, } @@ -279,7 +282,9 @@ class EmailAccount(Document): @property def _password(self): - raise_exception = not (self.use_oauth or self.no_smtp_authentication or frappe.flags.in_test) + raise_exception = not ( + self.auth_method == "Oauth" or self.no_smtp_authentication or frappe.flags.in_test + ) return self.get_password(raise_exception=raise_exception) @property @@ -398,7 +403,7 @@ class EmailAccount(Document): "default": 0, }, "name": {"conf_names": ("email_sender_name",), "default": "Frappe"}, - "use_oauth": {"conf_names": ("use_oauth"), "default": 0}, + "auth_method": {"conf_names": ("auth_method"), "default": "Basic"}, "access_token": {"conf_names": ("mail_access_token")}, "refresh_token": {"conf_names": ("mail_refresh_token")}, "from_site_config": {"default": True}, @@ -426,7 +431,7 @@ class EmailAccount(Document): "use_ssl": cint(self.use_ssl_for_outgoing), "use_tls": cint(self.use_tls), "service": getattr(self, "service", ""), - "use_oauth": self.use_oauth or 0, + "use_oauth": self.auth_method == "Oauth", "refresh_token": decrypt(self.refresh_token) if self.refresh_token else None, "access_token": decrypt(self.access_token) if self.access_token else None, } @@ -800,7 +805,7 @@ def pull(now=False): for email_account in frappe.get_list( "Email Account", filters={"enable_incoming": 1}, - or_filters={"awaiting_password": 0, "use_oauth": 1}, + or_filters={"awaiting_password": 0, "auth_method": "Oauth"}, ): if now: pull_from_email_account(email_account.name) @@ -923,7 +928,7 @@ def remove_user_email_inbox(email_account): @frappe.whitelist() def set_email_password(email_account, password): account = frappe.get_doc("Email Account", email_account) - if account.awaiting_password and not account.use_oauth: + if account.awaiting_password and not account.auth_method == "Oauth": account.awaiting_password = 0 account.password = password try: diff --git a/frappe/email/oauth.py b/frappe/email/oauth.py index cb9dcbbc85..140da6afed 100644 --- a/frappe/email/oauth.py +++ b/frappe/email/oauth.py @@ -2,7 +2,6 @@ import base64 from imaplib import IMAP4 from poplib import POP3 from smtplib import SMTP -from typing import Union from urllib.parse import quote import frappe @@ -124,10 +123,6 @@ def oauth_access(email_account: str, service: str): doctype = "Email Account" - # NOTE: setting this here, since we redirect to the service's auth page, - # we lose the use_oauth value in the emal account form - frappe.db.set_value(doctype, email_account, "use_oauth", 1, update_modified=False) - if service == "GMail": return authorize_google_access(email_account, doctype)