Newsletter moved to Frappe
diff --git a/erpnext/config/crm.py b/erpnext/config/crm.py
index 52958e3..178ee95 100644
--- a/erpnext/config/crm.py
+++ b/erpnext/config/crm.py
@@ -70,11 +70,6 @@
"items": [
{
"type": "doctype",
- "name": "Newsletter",
- "description": _("Newsletters to contacts, leads."),
- },
- {
- "type": "doctype",
"name": "Communication",
"description": _("Record of all communications of type email, phone, chat, visit, etc."),
},
@@ -116,11 +111,6 @@
"description": _("Manage Sales Person Tree."),
"doctype": "Sales Person",
},
- {
- "type": "doctype",
- "name": "Newsletter List",
- "description": _("Newsletter Mailing List"),
- },
]
},
{
diff --git a/erpnext/crm/doctype/newsletter/__init__.py b/erpnext/crm/doctype/newsletter/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/crm/doctype/newsletter/__init__.py
+++ /dev/null
diff --git a/erpnext/crm/doctype/newsletter/newsletter.js b/erpnext/crm/doctype/newsletter/newsletter.js
deleted file mode 100644
index 9bee9b3..0000000
--- a/erpnext/crm/doctype/newsletter/newsletter.js
+++ /dev/null
@@ -1,63 +0,0 @@
-// Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
-// License: GNU General Public License v3. See license.txt
-
-cur_frm.cscript.onload = function(doc) {
- return frappe.call({
- method: "erpnext.crm.doctype.newsletter.newsletter.get_lead_options",
- type: "GET",
- callback: function(r) {
- set_field_options("lead_source", r.message.sources.join("\n"))
- set_field_options("lead_status", r.message.statuses.join("\n"))
- }
- });
-}
-
-cur_frm.cscript.refresh = function(doc) {
- erpnext.toggle_naming_series();
- if(!doc.__islocal && !cint(doc.email_sent) && !doc.__unsaved
- && inList(frappe.boot.user.can_write, doc.doctype)) {
- cur_frm.add_custom_button(__('Send'), function() {
- return $c_obj(doc, 'send_emails', '', function(r) {
- cur_frm.refresh();
- });
- }, "icon-play", "btn-success");
- }
-
- cur_frm.cscript.setup_dashboard();
-
- if(doc.__islocal && !doc.send_from) {
- cur_frm.set_value("send_from",
- repl("%(fullname)s <%(email)s>", frappe.user_info(doc.owner)));
- }
-}
-
-cur_frm.cscript.setup_dashboard = function() {
- cur_frm.dashboard.reset();
- if(!cur_frm.doc.__islocal && cint(cur_frm.doc.email_sent) && cur_frm.doc.__onload && cur_frm.doc.__onload.status_count) {
- var stat = cur_frm.doc.__onload.status_count;
- var total = frappe.utils.sum($.map(stat, function(v) { return v; }));
- if(total) {
- $.each(stat, function(k, v) {
- stat[k] = flt(v * 100 / total, 2) + '%';
- });
-
- cur_frm.dashboard.add_progress("Status", [
- {
- title: stat["Sent"] + "% Sent",
- width: stat["Sent"],
- progress_class: "progress-bar-success"
- },
- {
- title: stat["Sending"] + "% Sending",
- width: stat["Sending"],
- progress_class: "progress-bar-warning"
- },
- {
- title: stat["Error"] + "% Error",
- width: stat["Error"],
- progress_class: "progress-bar-danger"
- }
- ]);
- }
- }
-}
diff --git a/erpnext/crm/doctype/newsletter/newsletter.json b/erpnext/crm/doctype/newsletter/newsletter.json
deleted file mode 100644
index 2515638..0000000
--- a/erpnext/crm/doctype/newsletter/newsletter.json
+++ /dev/null
@@ -1,281 +0,0 @@
-{
- "allow_copy": 0,
- "allow_import": 0,
- "allow_rename": 1,
- "autoname": "field:subject",
- "beta": 0,
- "creation": "2013-01-10 16:34:31",
- "custom": 0,
- "description": "Create and Send Newsletters",
- "docstatus": 0,
- "doctype": "DocType",
- "document_type": "Other",
- "fields": [
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "newsletter_list",
- "fieldtype": "Link",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "ignore_xss_filter": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "Newsletter List",
- "length": 0,
- "no_copy": 0,
- "options": "Newsletter List",
- "permlevel": 0,
- "precision": "",
- "print_hide": 0,
- "print_hide_if_no_value": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 1,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "subject",
- "fieldtype": "Small Text",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "ignore_xss_filter": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "Subject",
- "length": 0,
- "no_copy": 0,
- "permlevel": 0,
- "print_hide": 0,
- "print_hide_if_no_value": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 1,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "description": "",
- "fieldname": "send_from",
- "fieldtype": "Data",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "ignore_xss_filter": 1,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "Sender",
- "length": 0,
- "no_copy": 1,
- "permlevel": 0,
- "print_hide": 0,
- "print_hide_if_no_value": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 0,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "email_sent",
- "fieldtype": "Check",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "ignore_xss_filter": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "Email Sent?",
- "length": 0,
- "no_copy": 1,
- "permlevel": 0,
- "print_hide": 0,
- "print_hide_if_no_value": 0,
- "read_only": 1,
- "report_hide": 0,
- "reqd": 0,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "newsletter_content",
- "fieldtype": "Section Break",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "ignore_xss_filter": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "",
- "length": 0,
- "no_copy": 0,
- "permlevel": 0,
- "print_hide": 0,
- "print_hide_if_no_value": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 0,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "message",
- "fieldtype": "Text Editor",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "ignore_xss_filter": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "Message",
- "length": 0,
- "no_copy": 0,
- "permlevel": 0,
- "print_hide": 0,
- "print_hide_if_no_value": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 1,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "description": "",
- "fieldname": "test_the_newsletter",
- "fieldtype": "Section Break",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "ignore_xss_filter": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "",
- "length": 0,
- "no_copy": 0,
- "permlevel": 0,
- "print_hide": 0,
- "print_hide_if_no_value": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 0,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "description": "A Lead with this email id should exist",
- "fieldname": "test_email_id",
- "fieldtype": "Data",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "ignore_xss_filter": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "Test Email Id",
- "length": 0,
- "no_copy": 0,
- "permlevel": 0,
- "print_hide": 0,
- "print_hide_if_no_value": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 0,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "test_send",
- "fieldtype": "Button",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "ignore_xss_filter": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "Test",
- "length": 0,
- "no_copy": 0,
- "options": "test_send",
- "permlevel": 0,
- "print_hide": 0,
- "print_hide_if_no_value": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 0,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- }
- ],
- "hide_heading": 0,
- "hide_toolbar": 0,
- "icon": "icon-envelope",
- "idx": 1,
- "in_create": 0,
- "in_dialog": 0,
- "is_submittable": 0,
- "issingle": 0,
- "istable": 0,
- "max_attachments": 0,
- "menu_index": 0,
- "modified": "2016-05-24 16:01:54.675129",
- "modified_by": "Administrator",
- "module": "CRM",
- "name": "Newsletter",
- "owner": "Administrator",
- "permissions": [
- {
- "amend": 0,
- "apply_user_permissions": 0,
- "cancel": 0,
- "create": 0,
- "delete": 1,
- "email": 1,
- "export": 1,
- "if_owner": 0,
- "import": 0,
- "permlevel": 0,
- "print": 1,
- "read": 1,
- "report": 1,
- "role": "Newsletter Manager",
- "set_user_permissions": 0,
- "share": 1,
- "submit": 0,
- "write": 0
- }
- ],
- "quick_entry": 1,
- "read_only": 0,
- "read_only_onload": 0,
- "sort_order": "ASC",
- "title_field": "subject",
- "track_seen": 0
-}
\ No newline at end of file
diff --git a/erpnext/crm/doctype/newsletter/newsletter.py b/erpnext/crm/doctype/newsletter/newsletter.py
deleted file mode 100755
index dbf7dde..0000000
--- a/erpnext/crm/doctype/newsletter/newsletter.py
+++ /dev/null
@@ -1,189 +0,0 @@
-# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
-# License: GNU General Public License v3. See license.txt
-
-from __future__ import unicode_literals
-
-import frappe
-import frappe.utils
-from frappe import throw, _
-from frappe.model.document import Document
-from frappe.email.queue import check_email_limit
-from frappe.utils.verified_command import get_signed_params, verify_request
-from frappe.utils.background_jobs import enqueue
-from frappe.utils.scheduler import log
-from frappe.email.queue import send
-from erpnext.crm.doctype.newsletter_list.newsletter_list import add_subscribers
-
-class Newsletter(Document):
- def onload(self):
- if self.email_sent:
- self.get("__onload").status_count = dict(frappe.db.sql("""select status, count(name)
- from `tabEmail Queue` where reference_doctype=%s and reference_name=%s
- group by status""", (self.doctype, self.name))) or None
-
- def test_send(self, doctype="Lead"):
- self.recipients = frappe.utils.split_emails(self.test_email_id)
- self.queue_all()
- frappe.msgprint(_("Scheduled to send to {0}").format(self.test_email_id))
-
- def send_emails(self):
- """send emails to leads and customers"""
- if self.email_sent:
- throw(_("Newsletter has already been sent"))
-
- self.recipients = self.get_recipients()
-
- if getattr(frappe.local, "is_ajax", False):
- self.validate_send()
-
- # using default queue with a longer timeout as this isn't a scheduled task
- enqueue(send_newsletter, queue='default', timeout=1500, event='send_newsletter', newsletter=self.name)
-
- else:
- self.queue_all()
-
- frappe.msgprint(_("Scheduled to send to {0} recipients").format(len(self.recipients)))
-
- frappe.db.set(self, "email_sent", 1)
-
- def queue_all(self):
- if not self.get("recipients"):
- # in case it is called via worker
- self.recipients = self.get_recipients()
-
- self.validate_send()
-
- sender = self.send_from or frappe.utils.get_formatted_email(self.owner)
-
- if not frappe.flags.in_test:
- frappe.db.auto_commit_on_many_writes = True
-
- send(recipients = self.recipients, sender = sender,
- subject = self.subject, message = self.message,
- reference_doctype = self.doctype, reference_name = self.name,
- unsubscribe_method = "/api/method/erpnext.crm.doctype.newsletter.newsletter.unsubscribe",
- unsubscribe_params = {"name": self.newsletter_list},
- send_priority = 0)
-
- if not frappe.flags.in_test:
- frappe.db.auto_commit_on_many_writes = False
-
- def get_recipients(self):
- """Get recipients from Newsletter List"""
- return [d.email for d in frappe.db.get_all("Newsletter List Subscriber", ["email"],
- {"unsubscribed": 0, "newsletter_list": self.newsletter_list})]
-
- def validate_send(self):
- if self.get("__islocal"):
- throw(_("Please save the Newsletter before sending"))
- check_email_limit(self.recipients)
-
-@frappe.whitelist()
-def get_lead_options():
- return {
- "sources": ["All"] + filter(None,
- frappe.db.sql_list("""select distinct source from tabLead""")),
- "statuses": ["All"] + filter(None,
- frappe.db.sql_list("""select distinct status from tabLead"""))
- }
-
-
-@frappe.whitelist(allow_guest=True)
-def unsubscribe(email, name):
- if not verify_request():
- return
-
- subs_id = frappe.db.get_value("Newsletter List Subscriber", {"email": email, "newsletter_list": name})
- if subs_id:
- subscriber = frappe.get_doc("Newsletter List Subscriber", subs_id)
- subscriber.unsubscribed = 1
- subscriber.save(ignore_permissions=True)
-
- frappe.db.commit()
-
- return_unsubscribed_page(email)
-
-def return_unsubscribed_page(email):
- frappe.respond_as_web_page(_("Unsubscribed"), _("{0} has been successfully unsubscribed from this list.").format(email))
-
-def create_lead(email_id):
- """create a lead if it does not exist"""
- from email.utils import parseaddr
- from frappe.model.naming import get_default_naming_series
- real_name, email_id = parseaddr(email_id)
-
- if frappe.db.get_value("Lead", {"email_id": email_id}):
- return
-
- lead = frappe.get_doc({
- "doctype": "Lead",
- "email_id": email_id,
- "lead_name": real_name or email_id,
- "status": "Lead",
- "naming_series": get_default_naming_series("Lead"),
- "company": frappe.db.get_default("Company"),
- "source": "Email"
- })
- lead.insert()
-
-
-@frappe.whitelist(allow_guest=True)
-def subscribe(email):
- url = frappe.utils.get_url("/api/method/erpnext.crm.doctype.newsletter.newsletter.confirm_subscription") +\
- "?" + get_signed_params({"email": email})
-
- messages = (
- _("Thank you for your interest in subscribing to our updates"),
- _("Please verify your email id"),
- url,
- _("Click here to verify")
- )
-
- content = """
- <p>{0}. {1}.</p>
- <p><a href="{2}">{3}</a></p>
- """
-
- frappe.sendmail(email, subject=_("Confirm Your Email"), content=content.format(*messages))
-
-@frappe.whitelist(allow_guest=True)
-def confirm_subscription(email):
- if not verify_request():
- return
-
- if not frappe.db.exists("Newsletter List", _("Website")):
- frappe.get_doc({
- "doctype": "Newsletter List",
- "title": _("Website")
- }).insert(ignore_permissions=True)
-
-
- frappe.flags.ignore_permissions = True
-
- add_subscribers(_("Website"), email)
- frappe.db.commit()
-
- frappe.respond_as_web_page(_("Confirmed"), _("{0} has been successfully added to our Newsletter list.").format(email))
-
-
-def send_newsletter(newsletter):
- try:
- doc = frappe.get_doc("Newsletter", newsletter)
- doc.queue_all()
-
- except:
- frappe.db.rollback()
-
- # wasn't able to send emails :(
- doc.db_set("email_sent", 0)
- frappe.db.commit()
-
- log("send_newsletter")
-
- raise
-
- else:
- frappe.db.commit()
-
-
-
diff --git a/erpnext/crm/doctype/newsletter/newsletter_list.js b/erpnext/crm/doctype/newsletter/newsletter_list.js
deleted file mode 100644
index e95d295..0000000
--- a/erpnext/crm/doctype/newsletter/newsletter_list.js
+++ /dev/null
@@ -1,10 +0,0 @@
-frappe.listview_settings['Newsletter'] = {
- add_fields: ["subject", "email_sent"],
- get_indicator: function(doc) {
- if(doc.email_sent) {
- return [__("Sent"), "green", "email_sent,=,Yes"];
- } else {
- return [__("Not Sent"), "orange", "email_sent,=,No"];
- }
- }
-};
diff --git a/erpnext/crm/doctype/newsletter/test_newsletter.py b/erpnext/crm/doctype/newsletter/test_newsletter.py
deleted file mode 100644
index 2019b65..0000000
--- a/erpnext/crm/doctype/newsletter/test_newsletter.py
+++ /dev/null
@@ -1,51 +0,0 @@
-# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors
-# License: GNU General Public License v3. See license.txt
-from __future__ import unicode_literals
-
-import frappe, unittest
-
-from erpnext.crm.doctype.newsletter.newsletter import unsubscribe
-from urllib import unquote
-
-class TestNewsletter(unittest.TestCase):
- def setUp(self):
- if not frappe.get_all("Newsletter List Subscriber"):
- for email in ["test_subscriber1@example.com", "test_subscriber2@example.com",
- "test_subscriber3@example.com"]:
- frappe.get_doc({
- "doctype": "Newsletter List Subscriber",
- "email": email,
- "newsletter_list": "_Test Newsletter List"
- }).insert()
- else:
- frappe.db.sql("update `tabNewsletter List Subscriber` set unsubscribed = 0")
-
- def test_send(self):
- self.send_newsletter()
- self.assertEquals(len(frappe.get_all("Email Queue")), 3)
-
- def test_unsubscribe(self):
- # test unsubscribe
- self.send_newsletter()
-
- email = unquote(frappe.local.flags.signed_query_string.split("email=")[1].split("&")[0])
-
- unsubscribe(email, "_Test Newsletter List")
-
- self.send_newsletter()
- self.assertEquals(len(frappe.get_all("Email Queue")), 2)
-
- def send_newsletter(self):
- frappe.db.sql("delete from `tabEmail Queue`")
- frappe.delete_doc("Newsletter", "_Test Newsletting")
- newsletter = frappe.get_doc({
- "doctype": "Newsletter",
- "subject": "_Test Newsletting",
- "newsletter_list": "_Test Newsletter List",
- "send_from": "Test Sender <test_sender@example.com>",
- "message": "Testing my news."
- }).insert(ignore_permissions=True)
-
- newsletter.send_emails()
-
-test_dependencies = ["Newsletter List"]
diff --git a/erpnext/crm/doctype/newsletter_list/__init__.py b/erpnext/crm/doctype/newsletter_list/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/crm/doctype/newsletter_list/__init__.py
+++ /dev/null
diff --git a/erpnext/crm/doctype/newsletter_list/newsletter_list.js b/erpnext/crm/doctype/newsletter_list/newsletter_list.js
deleted file mode 100644
index 7799627..0000000
--- a/erpnext/crm/doctype/newsletter_list/newsletter_list.js
+++ /dev/null
@@ -1,46 +0,0 @@
-frappe.ui.form.on("Newsletter List", "refresh", function(frm) {
- if(!frm.is_new()) {
- frm.add_custom_button(__("View Subscribers"), function() {
- frappe.route_options = {"newsletter_list": frm.doc.name};
- frappe.set_route("Report", "Newsletter List Subscriber");
- }, __("View"));
-
- frm.add_custom_button(__("Import Subscribers"), function() {
- frappe.prompt({fieldtype:"Select", options: frm.doc.__onload.import_types,
- label:__("Import Email From"), fieldname:"doctype", reqd:1}, function(data) {
- frappe.call({
- method: "erpnext.crm.doctype.newsletter_list.newsletter_list.import_from",
- args: {
- "name": frm.doc.name,
- "doctype": data.doctype
- },
- callback: function(r) {
- frm.set_value("total_subscribers", r.message);
- }
- })
- }, __("Import Subscribers"), __("Import"));
- }, __("Action"));
-
- frm.add_custom_button(__("Add Subscribers"), function() {
- frappe.prompt({fieldtype:"Text",
- label:__("Email Ids"), fieldname:"email_list", reqd:1}, function(data) {
- frappe.call({
- method: "erpnext.crm.doctype.newsletter_list.newsletter_list.add_subscribers",
- args: {
- "name": frm.doc.name,
- "email_list": data.email_list
- },
- callback: function(r) {
- frm.set_value("total_subscribers", r.message);
- }
- })
- }, __("Add Subscribers"), __("Add"));
- }, __("Action"));
-
- frm.add_custom_button(__("New Newsletter"), function() {
- frappe.route_options = {"newsletter_list": frm.doc.name};
- frappe.new_doc("Newsletter");
- }, __("Action"));
-
- }
-});
diff --git a/erpnext/crm/doctype/newsletter_list/newsletter_list.json b/erpnext/crm/doctype/newsletter_list/newsletter_list.json
deleted file mode 100644
index 597116f..0000000
--- a/erpnext/crm/doctype/newsletter_list/newsletter_list.json
+++ /dev/null
@@ -1,100 +0,0 @@
-{
- "allow_copy": 0,
- "allow_import": 1,
- "allow_rename": 0,
- "autoname": "field:title",
- "creation": "2015-03-18 06:08:32.729800",
- "custom": 0,
- "docstatus": 0,
- "doctype": "DocType",
- "document_type": "Setup",
- "fields": [
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "title",
- "fieldtype": "Data",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "in_filter": 0,
- "in_list_view": 0,
- "label": "Title",
- "length": 0,
- "no_copy": 1,
- "permlevel": 0,
- "precision": "",
- "print_hide": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 1,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "default": "0",
- "fieldname": "total_subscribers",
- "fieldtype": "Int",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "in_filter": 0,
- "in_list_view": 1,
- "label": "Total Subscribers",
- "length": 0,
- "no_copy": 0,
- "permlevel": 0,
- "precision": "",
- "print_hide": 0,
- "read_only": 1,
- "report_hide": 0,
- "reqd": 0,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- }
- ],
- "hide_heading": 0,
- "hide_toolbar": 0,
- "in_create": 0,
- "in_dialog": 0,
- "is_submittable": 0,
- "issingle": 0,
- "istable": 0,
- "max_attachments": 0,
- "modified": "2015-11-16 06:29:50.643141",
- "modified_by": "Administrator",
- "module": "CRM",
- "name": "Newsletter List",
- "name_case": "",
- "owner": "Administrator",
- "permissions": [
- {
- "amend": 0,
- "apply_user_permissions": 0,
- "cancel": 0,
- "create": 1,
- "delete": 1,
- "email": 1,
- "export": 1,
- "if_owner": 0,
- "import": 1,
- "permlevel": 0,
- "print": 1,
- "read": 1,
- "report": 1,
- "role": "Newsletter Manager",
- "set_user_permissions": 0,
- "share": 1,
- "submit": 0,
- "write": 1
- }
- ],
- "read_only": 0,
- "read_only_onload": 0,
- "sort_field": "modified",
- "sort_order": "DESC"
-}
\ No newline at end of file
diff --git a/erpnext/crm/doctype/newsletter_list/newsletter_list.py b/erpnext/crm/doctype/newsletter_list/newsletter_list.py
deleted file mode 100644
index 68c445f..0000000
--- a/erpnext/crm/doctype/newsletter_list/newsletter_list.py
+++ /dev/null
@@ -1,102 +0,0 @@
-# -*- coding: utf-8 -*-
-# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors and contributors
-# For license information, please see license.txt
-
-from __future__ import unicode_literals
-import frappe
-from frappe.model.document import Document
-from frappe.utils import validate_email_add
-from frappe import _
-from email.utils import parseaddr
-
-class NewsletterList(Document):
- def onload(self):
- singles = [d.name for d in frappe.db.get_all("DocType", "name", {"issingle": 1})]
- self.get("__onload").import_types = [{"value": d.parent, "label": "{0} ({1})".format(d.parent, d.label)} \
- for d in frappe.db.get_all("DocField", ("parent", "label"), {"options": "Email"})
- if d.parent not in singles]
-
- def import_from(self, doctype):
- """Extract email ids from given doctype and add them to the current list"""
- meta = frappe.get_meta(doctype)
- email_field = [d.fieldname for d in meta.fields
- if d.fieldtype in ("Data", "Small Text", "Text", "Code") and d.options=="Email"][0]
- unsubscribed_field = "unsubscribed" if meta.get_field("unsubscribed") else None
- added = 0
-
- for user in frappe.db.get_all(doctype, [email_field, unsubscribed_field or "name"]):
- try:
- email = parseaddr(user.get(email_field))[1]
- if email:
- frappe.get_doc({
- "doctype": "Newsletter List Subscriber",
- "newsletter_list": self.name,
- "email": email,
- "unsubscribed": user.get(unsubscribed_field) if unsubscribed_field else 0
- }).insert(ignore_permissions=True)
-
- added += 1
- except frappe.UniqueValidationError:
- pass
-
- frappe.msgprint(_("{0} subscribers added").format(added))
-
- return self.update_total_subscribers()
-
- def update_total_subscribers(self):
- self.total_subscribers = self.get_total_subscribers()
- self.db_update()
- return self.total_subscribers
-
- def get_total_subscribers(self):
- return frappe.db.sql("""select count(*) from `tabNewsletter List Subscriber`
- where newsletter_list=%s""", self.name)[0][0]
-
- def on_trash(self):
- for d in frappe.get_all("Newsletter List Subscriber", "name", {"newsletter_list": self.name}):
- frappe.delete_doc("Newsletter List Subscriber", d.name)
-
-@frappe.whitelist()
-def import_from(name, doctype):
- nlist = frappe.get_doc("Newsletter List", name)
- if nlist.has_permission("write"):
- return nlist.import_from(doctype)
-
-@frappe.whitelist()
-def add_subscribers(name, email_list):
- if not isinstance(email_list, (list, tuple)):
- email_list = email_list.replace(",", "\n").split("\n")
- count = 0
- for email in email_list:
- email = email.strip()
- valid = validate_email_add(email, False)
-
- if valid:
- if not frappe.db.get_value("Newsletter List Subscriber",
- {"newsletter_list": name, "email": email}):
- frappe.get_doc({
- "doctype": "Newsletter List Subscriber",
- "newsletter_list": name,
- "email": email
- }).insert(ignore_permissions = frappe.flags.ignore_permissions)
-
- count += 1
- else:
- pass
- else:
- frappe.msgprint(_("{0} is not a valid email id").format(email))
-
- frappe.msgprint(_("{0} subscribers added").format(count))
-
- return frappe.get_doc("Newsletter List", name).update_total_subscribers()
-
-def restrict_newsletter_list(doc, method):
- from frappe.limits import get_limits
-
- newsletter_list_limit = get_limits().get('newsletter_recipients')
- if not newsletter_list_limit:
- return
-
- nl = frappe.get_doc("Newsletter List", doc.newsletter_list)
- if nl.get_total_subscribers() >= newsletter_list_limit:
- frappe.throw(_("Please Upgrade to add more than {0} subscribers").format(newsletter_list_limit))
\ No newline at end of file
diff --git a/erpnext/crm/doctype/newsletter_list/test_newsletter_list.py b/erpnext/crm/doctype/newsletter_list/test_newsletter_list.py
deleted file mode 100644
index ebc094e..0000000
--- a/erpnext/crm/doctype/newsletter_list/test_newsletter_list.py
+++ /dev/null
@@ -1,25 +0,0 @@
-# -*- coding: utf-8 -*-
-# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors and Contributors
-# See license.txt
-from __future__ import unicode_literals
-
-import frappe
-import unittest
-
-class TestNewletterList(unittest.TestCase):
- def test_import(self):
- new_list = frappe.get_doc({
- "doctype": "Newsletter List",
- "title": "_Test Newsletter List 1"
- }).insert()
-
- n_leads = frappe.db.sql("select count(distinct email_id) from `tabLead`")[0][0]
-
- added = new_list.import_from("Lead")
- self.assertEquals(added, n_leads)
-
- def tearDown(self):
- frappe.delete_doc("Newsletter List", "_Test Newsletter List 1")
-
-test_dependencies = ["Lead"]
-
diff --git a/erpnext/crm/doctype/newsletter_list/test_records.json b/erpnext/crm/doctype/newsletter_list/test_records.json
deleted file mode 100644
index ed2f89e..0000000
--- a/erpnext/crm/doctype/newsletter_list/test_records.json
+++ /dev/null
@@ -1,6 +0,0 @@
-[
- {
- "doctype": "Newsletter List",
- "title": "_Test Newsletter List"
- }
-]
diff --git a/erpnext/crm/doctype/newsletter_list_subscriber/__init__.py b/erpnext/crm/doctype/newsletter_list_subscriber/__init__.py
deleted file mode 100644
index e69de29..0000000
--- a/erpnext/crm/doctype/newsletter_list_subscriber/__init__.py
+++ /dev/null
diff --git a/erpnext/crm/doctype/newsletter_list_subscriber/newsletter_list_subscriber.json b/erpnext/crm/doctype/newsletter_list_subscriber/newsletter_list_subscriber.json
deleted file mode 100644
index 08208b8..0000000
--- a/erpnext/crm/doctype/newsletter_list_subscriber/newsletter_list_subscriber.json
+++ /dev/null
@@ -1,124 +0,0 @@
-{
- "allow_copy": 0,
- "allow_import": 1,
- "allow_rename": 0,
- "autoname": "hash",
- "creation": "2015-03-18 06:15:59.321619",
- "custom": 0,
- "docstatus": 0,
- "doctype": "DocType",
- "document_type": "Document",
- "fields": [
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "newsletter_list",
- "fieldtype": "Link",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "in_filter": 0,
- "in_list_view": 1,
- "label": "Newsletter List",
- "length": 0,
- "no_copy": 0,
- "options": "Newsletter List",
- "permlevel": 0,
- "precision": "",
- "print_hide": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 1,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "email",
- "fieldtype": "Data",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "in_filter": 0,
- "in_list_view": 1,
- "label": "Email",
- "length": 0,
- "no_copy": 0,
- "permlevel": 0,
- "precision": "",
- "print_hide": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 1,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- },
- {
- "allow_on_submit": 0,
- "bold": 0,
- "collapsible": 0,
- "fieldname": "unsubscribed",
- "fieldtype": "Check",
- "hidden": 0,
- "ignore_user_permissions": 0,
- "in_filter": 0,
- "in_list_view": 1,
- "label": "Unsubscribed",
- "length": 0,
- "no_copy": 0,
- "permlevel": 0,
- "precision": "",
- "print_hide": 0,
- "read_only": 0,
- "report_hide": 0,
- "reqd": 0,
- "search_index": 0,
- "set_only_once": 0,
- "unique": 0
- }
- ],
- "hide_heading": 0,
- "hide_toolbar": 0,
- "in_create": 0,
- "in_dialog": 0,
- "is_submittable": 0,
- "issingle": 0,
- "istable": 0,
- "max_attachments": 0,
- "modified": "2015-11-16 06:29:50.675306",
- "modified_by": "Administrator",
- "module": "CRM",
- "name": "Newsletter List Subscriber",
- "name_case": "",
- "owner": "Administrator",
- "permissions": [
- {
- "amend": 0,
- "apply_user_permissions": 0,
- "cancel": 0,
- "create": 1,
- "delete": 1,
- "email": 1,
- "export": 1,
- "if_owner": 0,
- "import": 1,
- "permlevel": 0,
- "print": 1,
- "read": 1,
- "report": 1,
- "role": "Newsletter Manager",
- "set_user_permissions": 0,
- "share": 1,
- "submit": 0,
- "write": 1
- }
- ],
- "read_only": 0,
- "read_only_onload": 0,
- "sort_field": "modified",
- "sort_order": "DESC",
- "title_field": "email"
-}
\ No newline at end of file
diff --git a/erpnext/crm/doctype/newsletter_list_subscriber/newsletter_list_subscriber.py b/erpnext/crm/doctype/newsletter_list_subscriber/newsletter_list_subscriber.py
deleted file mode 100644
index c036adc..0000000
--- a/erpnext/crm/doctype/newsletter_list_subscriber/newsletter_list_subscriber.py
+++ /dev/null
@@ -1,13 +0,0 @@
-# -*- coding: utf-8 -*-
-# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors and contributors
-# For license information, please see license.txt
-
-from __future__ import unicode_literals
-import frappe
-from frappe.model.document import Document
-
-class NewsletterListSubscriber(Document):
- pass
-
-def after_doctype_insert():
- frappe.db.add_unique("Newsletter List Subscriber", ("newsletter_list", "email"))
diff --git a/erpnext/crm/doctype/newsletter_list_subscriber/test_newsletter_list_subscriber.py b/erpnext/crm/doctype/newsletter_list_subscriber/test_newsletter_list_subscriber.py
deleted file mode 100644
index 24a0788..0000000
--- a/erpnext/crm/doctype/newsletter_list_subscriber/test_newsletter_list_subscriber.py
+++ /dev/null
@@ -1,12 +0,0 @@
-# -*- coding: utf-8 -*-
-# Copyright (c) 2015, Frappe Technologies Pvt. Ltd. and Contributors and Contributors
-# See license.txt
-from __future__ import unicode_literals
-
-import frappe
-import unittest
-
-# test_records = frappe.get_test_records('Newsletter List Subscriber')
-
-class TestNewsletterListSubscriber(unittest.TestCase):
- pass
diff --git a/erpnext/hooks.py b/erpnext/hooks.py
index 047ec8d..2704039 100644
--- a/erpnext/hooks.py
+++ b/erpnext/hooks.py
@@ -137,10 +137,6 @@
"validate": "erpnext.shopping_cart.cart.set_customer_in_address"
},
- "Newsletter List Subscriber": {
- "validate": "erpnext.crm.doctype.newsletter_list.newsletter_list.restrict_newsletter_list"
- },
-
# bubble transaction notification on master
('Opportunity', 'Quotation', 'Sales Order', 'Delivery Note', 'Sales Invoice',
'Supplier Quotation', 'Purchase Order', 'Purchase Receipt',
diff --git a/erpnext/patches/v5_0/newsletter.py b/erpnext/patches/v5_0/newsletter.py
index bd95937..c03664b 100644
--- a/erpnext/patches/v5_0/newsletter.py
+++ b/erpnext/patches/v5_0/newsletter.py
@@ -10,9 +10,9 @@
frappe.reload_doctype("Lead")
frappe.reload_doctype("Contact")
- frappe.reload_doc('crm', 'doctype', 'newsletter_list')
- frappe.reload_doc('crm', 'doctype', 'newsletter_list_subscriber')
- frappe.reload_doc('crm', 'doctype', 'newsletter')
+ frappe.reload_doc('email', 'doctype', 'email_group')
+ frappe.reload_doc('email', 'doctype', 'email_group_member')
+ frappe.reload_doc('email', 'doctype', 'newsletter')
frappe.permissions.reset_perms("Newsletter")
@@ -30,7 +30,7 @@
user.save()
# create default lists
- general = frappe.new_doc("Newsletter List")
+ general = frappe.new_doc("Email Group")
general.title = "General"
general.insert()
general.import_from("Lead")
diff --git a/erpnext/patches/v6_2/remove_newsletter_duplicates.py b/erpnext/patches/v6_2/remove_newsletter_duplicates.py
index 4f25c95..dc5b778 100644
--- a/erpnext/patches/v6_2/remove_newsletter_duplicates.py
+++ b/erpnext/patches/v6_2/remove_newsletter_duplicates.py
@@ -1,12 +1,12 @@
import frappe
def execute():
- duplicates = frappe.db.sql("""select newsletter_list, email, count(name)
- from `tabNewsletter List Subscriber`
- group by newsletter_list, email
+ duplicates = frappe.db.sql("""select email_group, email, count(name)
+ from `tabEmail Group Member`
+ group by email_group, email
having count(name) > 1""")
# delete all duplicates except 1
- for newsletter_list, email, count in duplicates:
- frappe.db.sql("""delete from `tabNewsletter List Subscriber`
- where newsletter_list=%s and email=%s limit %s""", (newsletter_list, email, count-1))
+ for email_group, email, count in duplicates:
+ frappe.db.sql("""delete from `tabEmail Group Member`
+ where email_group=%s and email=%s limit %s""", (email_group, email, count-1))
diff --git a/erpnext/public/js/website_utils.js b/erpnext/public/js/website_utils.js
index b0fc557..b541606 100644
--- a/erpnext/public/js/website_utils.js
+++ b/erpnext/public/js/website_utils.js
@@ -18,7 +18,7 @@
erpnext.subscribe_to_newsletter = function(opts, btn) {
return frappe.call({
type: "POST",
- method: "erpnext.crm.doctype.newsletter.newsletter.subscribe",
+ method: "frappe.email.doctype.newsletter.newsletter.subscribe",
btn: btn,
args: {"email": opts.email},
callback: opts.callback