fix: Multiple fixes in subscription

This commit is contained in:
Deepesh Garg 2021-02-09 16:13:45 +05:30
parent 7177579051
commit e56daeb347
4 changed files with 153 additions and 45 deletions

View File

@ -10,6 +10,14 @@ frappe.ui.form.on('Subscription', {
} }
} }
}); });
frm.set_query('cost_center', function() {
return {
filters : {
company: frm.doc.company
}
}
});
}, },
refresh: function(frm) { refresh: function(frm) {

View File

@ -7,9 +7,10 @@
"engine": "InnoDB", "engine": "InnoDB",
"field_order": [ "field_order": [
"party_type", "party_type",
"status",
"cb_1",
"party", "party",
"cb_1",
"company",
"status",
"subscription_period", "subscription_period",
"start_date", "start_date",
"end_date", "end_date",
@ -44,80 +45,107 @@
{ {
"allow_on_submit": 1, "allow_on_submit": 1,
"fieldname": "cb_1", "fieldname": "cb_1",
"fieldtype": "Column Break" "fieldtype": "Column Break",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "status", "fieldname": "status",
"fieldtype": "Select", "fieldtype": "Select",
"label": "Status", "label": "Status",
"no_copy": 1,
"options": "\nTrialling\nActive\nPast Due Date\nCancelled\nUnpaid\nCompleted", "options": "\nTrialling\nActive\nPast Due Date\nCancelled\nUnpaid\nCompleted",
"read_only": 1 "read_only": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "subscription_period", "fieldname": "subscription_period",
"fieldtype": "Section Break", "fieldtype": "Section Break",
"label": "Subscription Period" "label": "Subscription Period",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "cancelation_date", "fieldname": "cancelation_date",
"fieldtype": "Date", "fieldtype": "Date",
"label": "Cancelation Date", "label": "Cancelation Date",
"read_only": 1 "read_only": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"allow_on_submit": 1, "allow_on_submit": 1,
"fieldname": "trial_period_start", "fieldname": "trial_period_start",
"fieldtype": "Date", "fieldtype": "Date",
"label": "Trial Period Start Date", "label": "Trial Period Start Date",
"set_only_once": 1 "set_only_once": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"depends_on": "eval:doc.trial_period_start", "depends_on": "eval:doc.trial_period_start",
"fieldname": "trial_period_end", "fieldname": "trial_period_end",
"fieldtype": "Date", "fieldtype": "Date",
"label": "Trial Period End Date", "label": "Trial Period End Date",
"set_only_once": 1 "set_only_once": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "column_break_11", "fieldname": "column_break_11",
"fieldtype": "Column Break" "fieldtype": "Column Break",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "current_invoice_start", "fieldname": "current_invoice_start",
"fieldtype": "Date", "fieldtype": "Date",
"label": "Current Invoice Start Date", "label": "Current Invoice Start Date",
"read_only": 1 "read_only": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "current_invoice_end", "fieldname": "current_invoice_end",
"fieldtype": "Date", "fieldtype": "Date",
"label": "Current Invoice End Date", "label": "Current Invoice End Date",
"read_only": 1 "read_only": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"default": "0", "default": "0",
"description": "Number of days that the subscriber has to pay invoices generated by this subscription", "description": "Number of days that the subscriber has to pay invoices generated by this subscription",
"fieldname": "days_until_due", "fieldname": "days_until_due",
"fieldtype": "Int", "fieldtype": "Int",
"label": "Days Until Due" "label": "Days Until Due",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"default": "0", "default": "0",
"fieldname": "cancel_at_period_end", "fieldname": "cancel_at_period_end",
"fieldtype": "Check", "fieldtype": "Check",
"label": "Cancel At End Of Period" "label": "Cancel At End Of Period",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"default": "0", "default": "0",
"fieldname": "generate_invoice_at_period_start", "fieldname": "generate_invoice_at_period_start",
"fieldtype": "Check", "fieldtype": "Check",
"label": "Generate Invoice At Beginning Of Period" "label": "Generate Invoice At Beginning Of Period",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"allow_on_submit": 1, "allow_on_submit": 1,
"fieldname": "sb_4", "fieldname": "sb_4",
"fieldtype": "Section Break", "fieldtype": "Section Break",
"label": "Plans" "label": "Plans",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"allow_on_submit": 1, "allow_on_submit": 1,
@ -125,62 +153,84 @@
"fieldtype": "Table", "fieldtype": "Table",
"label": "Plans", "label": "Plans",
"options": "Subscription Plan Detail", "options": "Subscription Plan Detail",
"reqd": 1 "reqd": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"depends_on": "eval:['Customer', 'Supplier'].includes(doc.party_type)", "depends_on": "eval:['Customer', 'Supplier'].includes(doc.party_type)",
"fieldname": "sb_1", "fieldname": "sb_1",
"fieldtype": "Section Break", "fieldtype": "Section Break",
"label": "Taxes" "label": "Taxes",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "sb_2", "fieldname": "sb_2",
"fieldtype": "Section Break", "fieldtype": "Section Break",
"label": "Discounts" "label": "Discounts",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "apply_additional_discount", "fieldname": "apply_additional_discount",
"fieldtype": "Select", "fieldtype": "Select",
"label": "Apply Additional Discount On", "label": "Apply Additional Discount On",
"options": "\nGrand Total\nNet Total" "options": "\nGrand Total\nNet Total",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "cb_2", "fieldname": "cb_2",
"fieldtype": "Column Break" "fieldtype": "Column Break",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "additional_discount_percentage", "fieldname": "additional_discount_percentage",
"fieldtype": "Percent", "fieldtype": "Percent",
"label": "Additional DIscount Percentage" "label": "Additional DIscount Percentage",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"collapsible": 1, "collapsible": 1,
"fieldname": "additional_discount_amount", "fieldname": "additional_discount_amount",
"fieldtype": "Currency", "fieldtype": "Currency",
"label": "Additional DIscount Amount" "label": "Additional DIscount Amount",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"depends_on": "eval:doc.invoices", "depends_on": "eval:doc.invoices",
"fieldname": "sb_3", "fieldname": "sb_3",
"fieldtype": "Section Break", "fieldtype": "Section Break",
"label": "Invoices" "label": "Invoices",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"collapsible": 1, "collapsible": 1,
"fieldname": "invoices", "fieldname": "invoices",
"fieldtype": "Table", "fieldtype": "Table",
"label": "Invoices", "label": "Invoices",
"options": "Subscription Invoice" "options": "Subscription Invoice",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"collapsible": 1, "collapsible": 1,
"fieldname": "accounting_dimensions_section", "fieldname": "accounting_dimensions_section",
"fieldtype": "Section Break", "fieldtype": "Section Break",
"label": "Accounting Dimensions" "label": "Accounting Dimensions",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "dimension_col_break", "fieldname": "dimension_col_break",
"fieldtype": "Column Break" "fieldtype": "Column Break",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "party_type", "fieldname": "party_type",
@ -188,7 +238,9 @@
"label": "Party Type", "label": "Party Type",
"options": "DocType", "options": "DocType",
"reqd": 1, "reqd": 1,
"set_only_once": 1 "set_only_once": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "party", "fieldname": "party",
@ -197,21 +249,27 @@
"label": "Party", "label": "Party",
"options": "party_type", "options": "party_type",
"reqd": 1, "reqd": 1,
"set_only_once": 1 "set_only_once": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"depends_on": "eval:doc.party_type === 'Customer'", "depends_on": "eval:doc.party_type === 'Customer'",
"fieldname": "sales_tax_template", "fieldname": "sales_tax_template",
"fieldtype": "Link", "fieldtype": "Link",
"label": "Sales Taxes and Charges Template", "label": "Sales Taxes and Charges Template",
"options": "Sales Taxes and Charges Template" "options": "Sales Taxes and Charges Template",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"depends_on": "eval:doc.party_type === 'Supplier'", "depends_on": "eval:doc.party_type === 'Supplier'",
"fieldname": "purchase_tax_template", "fieldname": "purchase_tax_template",
"fieldtype": "Link", "fieldtype": "Link",
"label": "Purchase Taxes and Charges Template", "label": "Purchase Taxes and Charges Template",
"options": "Purchase Taxes and Charges Template" "options": "Purchase Taxes and Charges Template",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"default": "0", "default": "0",
@ -219,36 +277,55 @@
"fieldname": "follow_calendar_months", "fieldname": "follow_calendar_months",
"fieldtype": "Check", "fieldtype": "Check",
"label": "Follow Calendar Months", "label": "Follow Calendar Months",
"set_only_once": 1 "set_only_once": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"default": "0", "default": "0",
"description": "New invoices will be generated as per schedule even if current invoices are unpaid or past due date", "description": "New invoices will be generated as per schedule even if current invoices are unpaid or past due date",
"fieldname": "generate_new_invoices_past_due_date", "fieldname": "generate_new_invoices_past_due_date",
"fieldtype": "Check", "fieldtype": "Check",
"label": "Generate New Invoices Past Due Date" "label": "Generate New Invoices Past Due Date",
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "end_date", "fieldname": "end_date",
"fieldtype": "Date", "fieldtype": "Date",
"label": "Subscription End Date", "label": "Subscription End Date",
"set_only_once": 1 "set_only_once": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "start_date", "fieldname": "start_date",
"fieldtype": "Date", "fieldtype": "Date",
"label": "Subscription Start Date", "label": "Subscription Start Date",
"set_only_once": 1 "set_only_once": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "cost_center", "fieldname": "cost_center",
"fieldtype": "Link", "fieldtype": "Link",
"label": "Cost Center", "label": "Cost Center",
"options": "Cost Center" "options": "Cost Center",
"show_days": 1,
"show_seconds": 1
},
{
"fieldname": "company",
"fieldtype": "Link",
"label": "Company",
"options": "Company",
"show_days": 1,
"show_seconds": 1
} }
], ],
"index_web_pages_for_search": 1,
"links": [], "links": [],
"modified": "2020-06-25 10:52:52.265105", "modified": "2021-02-09 15:44:20.024789",
"modified_by": "Administrator", "modified_by": "Administrator",
"module": "Accounts", "module": "Accounts",
"name": "Subscription", "name": "Subscription",

View File

@ -1,3 +1,4 @@
# -*- coding: utf-8 -*- # -*- coding: utf-8 -*-
# Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors # Copyright (c) 2018, Frappe Technologies Pvt. Ltd. and contributors
# For license information, please see license.txt # For license information, please see license.txt
@ -5,12 +6,13 @@
from __future__ import unicode_literals from __future__ import unicode_literals
import frappe import frappe
import erpnext
from frappe import _ from frappe import _
from frappe.model.document import Document from frappe.model.document import Document
from frappe.utils.data import nowdate, getdate, cstr, cint, add_days, date_diff, get_last_day, add_to_date, flt from frappe.utils.data import nowdate, getdate, cstr, cint, add_days, date_diff, get_last_day, add_to_date, flt
from erpnext.accounts.doctype.subscription_plan.subscription_plan import get_plan_rate from erpnext.accounts.doctype.subscription_plan.subscription_plan import get_plan_rate
from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import get_accounting_dimensions from erpnext.accounts.doctype.accounting_dimension.accounting_dimension import get_accounting_dimensions
from erpnext import get_default_company
class Subscription(Document): class Subscription(Document):
def before_insert(self): def before_insert(self):
@ -243,6 +245,7 @@ class Subscription(Document):
self.validate_plans_billing_cycle(self.get_billing_cycle_and_interval()) self.validate_plans_billing_cycle(self.get_billing_cycle_and_interval())
self.validate_end_date() self.validate_end_date()
self.validate_to_follow_calendar_months() self.validate_to_follow_calendar_months()
self.cost_center = erpnext.get_default_cost_center(self.company)
def validate_trial_period(self): def validate_trial_period(self):
""" """
@ -304,6 +307,14 @@ class Subscription(Document):
doctype = 'Sales Invoice' if self.party_type == 'Customer' else 'Purchase Invoice' doctype = 'Sales Invoice' if self.party_type == 'Customer' else 'Purchase Invoice'
invoice = frappe.new_doc(doctype) invoice = frappe.new_doc(doctype)
# For backward compatibility
# Earlier subscription didn't had any subscription field
company = self.company or get_default_company()
if not company:
frappe.throw(_("Company is mandatory was generating invoice. Please set default company in Global Defaults"))
invoice.company = company
invoice.set_posting_time = 1 invoice.set_posting_time = 1
invoice.posting_date = self.current_invoice_start if self.generate_invoice_at_period_start \ invoice.posting_date = self.current_invoice_start if self.generate_invoice_at_period_start \
else self.current_invoice_end else self.current_invoice_end
@ -330,6 +341,7 @@ class Subscription(Document):
# for that reason # for that reason
items_list = self.get_items_from_plans(self.plans, prorate) items_list = self.get_items_from_plans(self.plans, prorate)
for item in items_list: for item in items_list:
item['cost_center'] = self.cost_center
invoice.append('items', item) invoice.append('items', item)
# Taxes # Taxes
@ -380,7 +392,8 @@ class Subscription(Document):
Returns the `Item`s linked to `Subscription Plan` Returns the `Item`s linked to `Subscription Plan`
""" """
if prorate: if prorate:
prorate_factor = get_prorata_factor(self.current_invoice_end, self.current_invoice_start) prorate_factor = get_prorata_factor(self.current_invoice_end, self.current_invoice_start,
self.generate_invoice_at_period_start)
items = [] items = []
party = self.party party = self.party
@ -583,10 +596,13 @@ def get_calendar_months(billing_interval):
return calendar_months return calendar_months
def get_prorata_factor(period_end, period_start): def get_prorata_factor(period_end, period_start, is_prepaid):
diff = flt(date_diff(nowdate(), period_start) + 1) if is_prepaid:
plan_days = flt(date_diff(period_end, period_start) + 1) prorate_factor = 1
prorate_factor = diff / plan_days else:
diff = flt(date_diff(nowdate(), period_start) + 1)
plan_days = flt(date_diff(period_end, period_start) + 1)
prorate_factor = diff / plan_days
return prorate_factor return prorate_factor

View File

@ -13,21 +13,28 @@
"fieldname": "document_type", "fieldname": "document_type",
"fieldtype": "Link", "fieldtype": "Link",
"label": "Document Type ", "label": "Document Type ",
"no_copy": 1,
"options": "DocType", "options": "DocType",
"read_only": 1 "read_only": 1,
"show_days": 1,
"show_seconds": 1
}, },
{ {
"fieldname": "invoice", "fieldname": "invoice",
"fieldtype": "Dynamic Link", "fieldtype": "Dynamic Link",
"in_list_view": 1, "in_list_view": 1,
"label": "Invoice", "label": "Invoice",
"no_copy": 1,
"options": "document_type", "options": "document_type",
"read_only": 1 "read_only": 1,
"show_days": 1,
"show_seconds": 1
} }
], ],
"index_web_pages_for_search": 1,
"istable": 1, "istable": 1,
"links": [], "links": [],
"modified": "2020-06-01 22:23:54.462718", "modified": "2021-02-09 15:43:32.026233",
"modified_by": "Administrator", "modified_by": "Administrator",
"module": "Accounts", "module": "Accounts",
"name": "Subscription Invoice", "name": "Subscription Invoice",