feat: Basic validation for indian PAN No. in Supplier (#24687)

diff --git a/erpnext/hooks.py b/erpnext/hooks.py
index 347da6b..39d3659 100644
--- a/erpnext/hooks.py
+++ b/erpnext/hooks.py
@@ -272,6 +272,9 @@
 	'Address': {
 		'validate': ['erpnext.regional.india.utils.validate_gstin_for_india', 'erpnext.regional.italy.utils.set_state_code', 'erpnext.regional.india.utils.update_gst_category']
 	},
+	'Supplier': {
+		'validate': 'erpnext.regional.india.utils.validate_pan_for_india'
+	},
 	('Sales Invoice', 'Sales Order', 'Delivery Note', 'Purchase Invoice', 'Purchase Order', 'Purchase Receipt'): {
 		'validate': ['erpnext.regional.india.utils.set_place_of_supply']
 	},
diff --git a/erpnext/regional/india/utils.py b/erpnext/regional/india/utils.py
index 09bafdd..5f07863 100644
--- a/erpnext/regional/india/utils.py
+++ b/erpnext/regional/india/utils.py
@@ -55,6 +55,14 @@
 			frappe.throw(_("Invalid GSTIN! First 2 digits of GSTIN should match with State number {0}.")
 				.format(doc.gst_state_number))
 
+def validate_pan_for_india(doc, method):
+	if doc.get('country') != 'India':
+		return
+
+	p = re.compile("[A-Z]{5}[0-9]{4}[A-Z]{1}")
+	if not p.match(doc.pan):
+		frappe.throw(_("Invalid PAN No. The input you've entered doesn't match the format of PAN."))
+
 def validate_tax_category(doc, method):
 	if doc.get('gst_state') and frappe.db.get_value('Tax Category', {'gst_state': doc.gst_state, 'is_inter_state': doc.is_inter_state}):
 		if doc.is_inter_state: