Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(ITC-04): Report GST Job Work Stock Movement #2504

Merged
merged 9 commits into from
Aug 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 4 additions & 2 deletions india_compliance/gst_india/data/test_e_waybill.json
Original file line number Diff line number Diff line change
Expand Up @@ -1090,9 +1090,11 @@
"gst_hsn_code": "61149090",
"s_warehouse": "Finished Goods - _TIRC",
"t_warehouse": "Goods In Transit - _TIRC",
"amount": 100
"amount": 100,
"taxable_value": 100
}],
"company": "_Test Indian Registered Company"
"company": "_Test Indian Registered Company",
"base_grand_total": 100
},
"values": {
"distance": 0.0,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -292,7 +292,7 @@ def validate_for_charge_type(self):

def ignore_gst_validation_for_subcontracting(doc):
if doc.doctype == "Stock Entry" and not doc.subcontracting_order:
return
return True

return ignore_gst_validations(doc)

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
// Copyright (c) 2024, Resilient Tech and contributors
// For license information, please see license.txt

frappe.query_reports["GST Job Work Stock Movement"] = {
filters: [
{
fieldname: "company",
label: __("Company"),
fieldtype: "Link",
options: "Company",
default: frappe.defaults.get_user_default("Company"),
on_change: report => {
report.set_filter_value({
company_gstin: "",
});
report.refresh();
},
get_query: function () {
return {
filters: {
country: "India",
},
};
},
},
{
fieldname: "company_gstin",
label: __("Company GSTIN"),
fieldtype: "Autocomplete",
get_query() {
const company = frappe.query_report.get_filter_value("company");
return india_compliance.get_gstin_query(company);
},
},
{
fieldname: "from_date",
label: __("From Date"),
fieldtype: "Date",
default: india_compliance.last_half_year("start"),
reqd: 1,
},
{
fieldname: "to_date",
label: __("To Date"),
fieldtype: "Date",
default: india_compliance.last_half_year("end"),
reqd: 1,
},
{
fieldname: "category",
label: __("Invoice Category"),
fieldtype: "Select",
options: [
"Sent for Job Work (Table 4)",
"Received back from Job Worker (Table 5A)",
],
reqd: 1,
},
],
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
{
"add_total_row": 1,
"columns": [],
"creation": "2024-08-19 14:40:26.929838",
"disabled": 0,
"docstatus": 0,
"doctype": "Report",
"filters": [],
"idx": 0,
"is_standard": "Yes",
"letterhead": null,
"modified": "2024-08-19 14:40:33.093455",
"modified_by": "Administrator",
"module": "GST India",
"name": "GST Job Work Stock Movement",
"owner": "Administrator",
"prepared_report": 0,
"ref_doctype": "Subcontracting Order",
"report_name": "GST Job Work Stock Movement",
"report_type": "Script Report",
"roles": [
{
"role": "Item Manager"
},
{
"role": "Stock Manager"
},
{
"role": "Stock User"
},
{
"role": "Accounts Manager"
},
{
"role": "Accounts User"
},
{
"role": "Manufacturing Manager"
},
{
"role": "Manufacturing User"
}
]
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,233 @@
# Copyright (c) 2024, Resilient Tech and contributors
# For license information, please see license.txt

import frappe
from frappe import _

from india_compliance.gst_india.utils.itc_04.itc_04_data import ITC04Query


def execute(filters=None):
report = JobWorkMovement(filters)
return report.columns(), report.data()


class JobWorkMovement:
def __init__(self, filters=None):
self.filters = filters
self.validate_filters()

def validate_filters(self):
if not self.filters:
self.filters = frappe._dict()

if not self.filters.category:
frappe.throw(_("Category is mandatory"))

if not self.filters.from_date:
frappe.throw(_("From Date is mandatory"))

if not self.filters.to_date:
frappe.throw(_("To Date is mandatory"))

if self.filters.from_date > self.filters.to_date:
frappe.throw(_("From Date cannot be greater than To Date"))

def data(self):
itc04 = ITC04Query(self.filters)
data = []

if self.filters.category == "Sent for Job Work (Table 4)":
data = itc04.get_query_table_4_se().run(as_dict=True)
data.extend(itc04.get_query_table_4_sr().run(as_dict=True))

elif self.filters.category == "Received back from Job Worker (Table 5A)":
data = itc04.get_query_table_5A_se().run(as_dict=True)
data.extend(itc04.get_query_table_5A_sr().run(as_dict=True))

return data

def columns(self):
if self.filters.category == "Sent for Job Work (Table 4)":
return self.get_columns_table_4()

elif self.filters.category == "Received back from Job Worker (Table 5A)":
return self.get_columns_table_5A()

return []

def get_columns_table_4(self):
return [
*self.gstin_column(),
*self.posting_date_column(),
{
"fieldname": "invoice_no",
"label": _("Invoice No (Challan No)"),
"fieldtype": "Dynamic Link",
"options": "invoice_type",
"width": 180,
},
*self.common_columns(),
{
"fieldname": "taxable_value",
"label": _("Taxable Value"),
"fieldtype": "Currency",
"width": 150,
},
{
"fieldname": "gst_rate",
"label": _("GST Rate"),
"fieldtype": "Percent",
"width": 100,
},
{
"fieldname": "cgst_amount",
"label": _("CGST Amount"),
"fieldtype": "Currency",
"width": 120,
},
{
"fieldname": "sgst_amount",
"label": _("SGST Amount"),
"fieldtype": "Currency",
"width": 120,
},
{
"fieldname": "igst_amount",
"label": _("IGST Amount"),
"fieldtype": "Currency",
"width": 120,
},
{
"fieldname": "total_cess_amount",
"label": _("Cess Amount"),
"fieldtype": "Currency",
"width": 120,
},
{
"fieldname": "total_tax",
"label": _("Total Tax"),
"fieldtype": "Currency",
"width": 120,
},
{
"fieldname": "total_amount",
"label": _("Total Amount"),
"fieldtype": "Currency",
"width": 150,
},
{
"fieldname": "gst_treatment",
"label": _("GST Treatment"),
"fieldtype": "Data",
"width": 120,
},
]

def get_columns_table_5A(self):
return [
*self.gstin_column(),
*self.posting_date_column(),
{
"fieldname": "original_challan_no",
"label": _("Original Challan No"),
"fieldtype": "Dynamic Link",
"options": "original_challan_invoice_type",
"width": 180,
},
{
"fieldname": "invoice_no",
"label": _("Job Worker Invoice No (Challan No)"),
"fieldtype": "Dynamic Link",
"options": "invoice_type",
"width": 180,
},
*self.common_columns(),
]

def gstin_column(self):
return [
{
"fieldname": "company_gstin",
"label": _("Company GSTIN"),
"fieldtype": "Data",
"width": 160,
"hidden": True if self.filters.company_gstin else False,
}
]

def posting_date_column(self):
return [
{
"fieldname": "posting_date",
"label": _("Posting Date"),
"fieldtype": "Date",
"width": 120,
}
]

def common_columns(self):
return [
{
"fieldname": "supplier",
"label": _("Job Worker"),
"fieldtype": "Link",
"options": "Supplier",
"width": 200,
},
{
"fieldname": "supplier_gstin",
"label": _("Job Worker GSTIN"),
"fieldtype": "Data",
"width": 160,
},
{
"fieldname": "place_of_supply",
"label": _("Place of Supply"),
"fieldtype": "Data",
"width": 150,
},
{
"fieldname": "is_return",
"label": _("Is Return"),
"fieldtype": "Check",
"width": 90,
},
{
"fieldname": "item_type",
"label": _("Item Type (Input/Capital Goods)"),
"fieldtype": "Data",
"width": 180,
"hidden": (
False
if self.filters.category == "Sent for Job Work (Table 4)"
else True
),
},
{
"fieldname": "item_code",
"label": _("Item Code"),
"fieldtype": "Link",
"options": "Item",
"width": 180,
},
{
"fieldname": "gst_hsn_code",
"label": _("HSN Code"),
"fieldtype": "Link",
"options": "GST HSN Code",
"width": 100,
},
{
"fieldname": "qty",
"label": _("Qty"),
"fieldtype": "Float",
"width": 90,
},
{
"fieldname": "uom",
"label": _("UOM"),
"fieldtype": "Data",
"width": 90,
},
]
Loading
Loading