|
import spacy
|
|
import logging
|
|
import json
|
|
from utils.fileTotext import extract_text_based_on_format
|
|
import re
|
|
|
|
def is_valid_email(email):
|
|
email_regex = r'^[a-zA-Z0-9_.+-]+@[a-zA-Z0-9-]+\.[a-zA-Z0-9-.]+$'
|
|
return re.match(email_regex, email) is not None
|
|
|
|
def is_valid_contact(contact):
|
|
patterns = [
|
|
r'^\+91[\s\.\-\/]?\(?0?\)?[\s\-\.\/]?\d{5}[\s\-\.\/]?\d{5}$',
|
|
r'^\+91[\s\.\-\/]?\d{5}[\s\-\.\/]?\d{5}$',
|
|
r'^\d{5}[\s\-\.\/]?\d{5}$',
|
|
r'^\+91[\s\.\-\/]?\d{10}$',
|
|
r'^\d{10}$',
|
|
r'^\+91[\s\.\-\/]?\(?\d{5}\)?[\s\-\.\/]?\d{5}[\s\-\.\/]?\d{5}$'
|
|
r'\+1\s\(\d{3}\)\s\d{3}-\d{4} ',
|
|
r'\(\d{3}\)\s\d{3}-\d{4} ',
|
|
r'\(\d{3}\)\s\d{3}\s\d{4} ',
|
|
r'\(\d{3}\)\s\d{3}\s\d{3} ',
|
|
r'\+1\d{10} ',
|
|
r'\d{10} ',
|
|
r'\+44\s\d{4}\s\d{6} ',
|
|
r'\+44\s\d{3}\s\d{3}\s\d{4} ',
|
|
r'0\d{4}\s\d{6} ',
|
|
r'0\d{3}\s\d{3}\s\d{4} ',
|
|
r'\+44\d{10} ',
|
|
r'0\d{10} ',
|
|
r'\+61\s\d\s\d{4}\s\d{4} ',
|
|
r'0\d\s\d{4}\s\d{4} ',
|
|
r'\+61\d{9} ',
|
|
r'0\d{9} ',
|
|
r'\+91\s\d{5}-\d{5} ',
|
|
r'\+91\s\d{4}-\d{6} ',
|
|
r'\+91\s\d{10} ',
|
|
r'0\d{2}-\d{7} ',
|
|
r'\+91\d{10} ',
|
|
r'\+49\s\d{4}\s\d{8} ',
|
|
r'\+49\s\d{3}\s\d{7} ',
|
|
r'0\d{3}\s\d{8} ',
|
|
r'\+49\d{12} ',
|
|
r'\+49\d{10} ',
|
|
r'0\d{11} ',
|
|
r'\+86\s\d{3}\s\d{4}\s\d{4} ',
|
|
r'0\d{3}\s\d{4}\s\d{4} ',
|
|
r'\+86\d{11} ',
|
|
r'\+81\s\d\s\d{4}\s\d{4} ',
|
|
r'\+81\s\d{2}\s\d{4}\s\d{4} ',
|
|
r'0\d\s\d{4}\s\d{4} ',
|
|
r'\+81\d{10} ',
|
|
r'\+81\d{9} ',
|
|
r'0\d{9} ',
|
|
r'\+55\s\d{2}\s\d{5}-\d{4} ',
|
|
r'\+55\s\d{2}\s\d{4}-\d{4} ',
|
|
r'0\d{2}\s\d{4}\s\d{4} ',
|
|
r'\+55\d{11} ',
|
|
r'\+55\d{10} ',
|
|
r'0\d{10} ',
|
|
r'\+33\s\d\s\d{2}\s\d{2}\s\d{2}\s\d{2} ',
|
|
r'0\d\s\d{2}\s\d{2}\s\d{2}\s\d{2} ',
|
|
r'\+33\d{9} ',
|
|
r'0\d{9} ',
|
|
r'\+7\s\d{3}\s\d{3}-\d{2}-\d{2} ',
|
|
r'8\s\d{3}\s\d{3}-\d{2}-\d{2} ',
|
|
r'\+7\d{10} ',
|
|
r'8\d{10} ',
|
|
r'\+27\s\d{2}\s\d{3}\s\d{4} ',
|
|
r'0\d{2}\s\d{3}\s\d{4} ',
|
|
r'\+27\d{9} ',
|
|
r'0\d{9} ',
|
|
r'\+52\s\d{3}\s\d{3}\s\d{4} ',
|
|
r'\+52\s\d{2}\s\d{4}\s\d{4} ',
|
|
r'01\s\d{3}\s\d{4} ',
|
|
r'\+52\d{10} ',
|
|
r'01\d{7} ',
|
|
r'\+234\s\d{3}\s\d{3}\s\d{4} ',
|
|
r'0\d{3}\s\d{3}\s\d{4} ',
|
|
r'\+234\d{10} ',
|
|
r'0\d{10} ',
|
|
r'\+971\s\d\s\d{3}\s\d{4} ',
|
|
r'0\d\s\d{3}\s\d{4} ',
|
|
r'\+971\d{8} ',
|
|
r'0\d{8} ',
|
|
r'\+54\s9\s\d{3}\s\d{3}\s\d{4} ',
|
|
r'\+54\s\d{1}\s\d{4}\s\d{4} ',
|
|
r'0\d{3}\s\d{4} ',
|
|
r'\+54\d{10} ',
|
|
r'\+54\d{9} ',
|
|
r'0\d{7} ',
|
|
r'\+966\s\d\s\d{3}\s\d{4} ',
|
|
r'0\d\s\d{3}\s\d{4} ',
|
|
r'\+966\d{8} ',
|
|
r'0\d{8} ',
|
|
r'\+1\d{10} ',
|
|
r'\+1\s\d{3}\s\d{3}\s\d{4} ',
|
|
r'\d{5}\s\d{5} ',
|
|
r'\d{10} ',
|
|
r'\+44\d{10} ',
|
|
r'0\d{10} ',
|
|
r'\+61\d{9} ',
|
|
r'0\d{9} ',
|
|
r'\+91\d{10} ',
|
|
r'\+49\d{12} ',
|
|
r'\+49\d{10} ',
|
|
r'0\d{11} ',
|
|
r'\+86\d{11} ',
|
|
r'\+81\d{10} ',
|
|
r'\+81\d{9} ',
|
|
r'0\d{9} ',
|
|
r'\+55\d{11} ',
|
|
r'\+55\d{10} ',
|
|
r'0\d{10} ',
|
|
r'\+33\d{9} ',
|
|
r'0\d{9} ',
|
|
r'\+7\d{10} ',
|
|
r'8\d{10} ',
|
|
r'\+27\d{9} ',
|
|
r'0\d{9} ',
|
|
r'\+52\d{10} ',
|
|
r'01\d{7} ',
|
|
r'\+234\d{10} ',
|
|
r'0\d{10} ',
|
|
r'\+971\d{8} ',
|
|
r'0\d{8} ',
|
|
r'\+54\s9\s\d{10} ',
|
|
r'\+54\d{9} ',
|
|
r'0\d{7} ',
|
|
r'\+966\d{8} ',
|
|
r'0\d{8}'
|
|
]
|
|
|
|
|
|
return any(re.match(pattern, contact) for pattern in patterns) is not None
|
|
|
|
|
|
|
|
def Parser_from_model(file_path):
|
|
result = {
|
|
"personal": {
|
|
"name": '',
|
|
"contact": '',
|
|
"email": '',
|
|
"location": '',
|
|
"link": '',
|
|
"invalid_email": '',
|
|
"invalid_contact": ''
|
|
},
|
|
"professional": {
|
|
"technical_skills": [],
|
|
"non_technical_skills": [],
|
|
"tools": [],
|
|
"experience": [
|
|
{
|
|
"company": '',
|
|
"projects": '',
|
|
"role": '',
|
|
"years": '',
|
|
"project_experience": []
|
|
}
|
|
],
|
|
"education": [
|
|
{
|
|
"qualification": '',
|
|
"university": '',
|
|
"course": '',
|
|
"certificate": ''
|
|
}
|
|
]
|
|
}
|
|
}
|
|
|
|
try:
|
|
nlp = spacy.load("Spacy_Models/ner_model_05_3")
|
|
logging.debug("Model loaded successfully.")
|
|
except Exception as e:
|
|
logging.error(f"Error loading model: {e}")
|
|
return {"error": "Model loading failed"}
|
|
|
|
try:
|
|
cleaned_text, hyperlinks = extract_text_based_on_format(file_path)
|
|
if not cleaned_text.strip():
|
|
logging.error("No text extracted from the file.")
|
|
return {"error": "Text extraction failed"}
|
|
except Exception as e:
|
|
logging.error(f"Error extracting text from file: {e}")
|
|
return {"error": "Text extraction failed"}
|
|
|
|
try:
|
|
doc = nlp(cleaned_text)
|
|
except Exception as e:
|
|
logging.error(f"Error processing text with SpaCy: {e}")
|
|
return {"error": "Text processing failed"}
|
|
|
|
|
|
entities = {label: [] for label in ['PERSON', 'EMAIL', 'CONTACT', 'LOCATION', 'SKILL', 'SOFT_SKILL', 'COMPANY', 'PROJECTS', 'JOB_TITLE', 'YEARS_EXPERIENCE', 'EXPERIENCE', 'QUALIFICATION', 'UNIVERSITY', 'COURSE', 'CERTIFICATE']}
|
|
|
|
|
|
for ent in doc.ents:
|
|
if ent.label_ in entities:
|
|
if ent.text not in entities[ent.label_]:
|
|
entities[ent.label_].append(ent.text)
|
|
|
|
|
|
result['personal']['name'] = entities.get('PERSON', [''])[0] if entities.get('PERSON', []) else ''
|
|
|
|
|
|
extracted_email = entities.get('EMAIL', [''])[0] if entities.get('EMAIL', []) else ''
|
|
if is_valid_email(extracted_email):
|
|
result['personal']['email'] = extracted_email
|
|
else:
|
|
logging.warning(f"Invalid email detected: {extracted_email}")
|
|
result['personal']['email'] = "Invalid email"
|
|
result['personal']['invalid_email'] = extracted_email
|
|
|
|
|
|
extracted_contact = entities.get('CONTACT', [''])[0] if entities.get('CONTACT', []) else ''
|
|
if is_valid_contact(extracted_contact):
|
|
result['personal']['contact'] = extracted_contact
|
|
else:
|
|
logging.warning(f"Invalid contact detected: {extracted_contact}")
|
|
result['personal']['contact'] = "Invalid contact"
|
|
result['personal']['invalid_contact'] = extracted_contact
|
|
|
|
result['personal']['location'] = entities.get('LOCATION', [''])[0] if entities.get('LOCATION', []) else ''
|
|
result['personal']['link'] = hyperlinks
|
|
|
|
result['professional']['technical_skills'] = entities.get('SKILL', [])
|
|
result['professional']['non_technical_skills'] = entities.get('SOFT_SKILL', [])
|
|
result['professional']['tools'] = []
|
|
|
|
result['professional']['experience'][0]['company'] = entities.get('COMPANY', [''])[0] if entities.get('COMPANY', []) else ''
|
|
result['professional']['experience'][0]['projects'] = entities.get('PROJECTS', [''])[0] if entities.get('PROJECTS', []) else ''
|
|
result['professional']['experience'][0]['role'] = entities.get('JOB_TITLE', [''])[0] if entities.get('JOB_TITLE', []) else ''
|
|
result['professional']['experience'][0]['years'] = entities.get('YEARS_EXPERIENCE', [''])[0] if entities.get('YEARS_EXPERIENCE', []) else ''
|
|
result['professional']['experience'][0]['project_experience'] = entities.get('EXPERIENCE', [])
|
|
|
|
result['professional']['education'][0]['qualification'] = entities.get('QUALIFICATION', [''])[0] if entities.get('QUALIFICATION', []) else ''
|
|
result['professional']['education'][0]['university'] = entities.get('UNIVERSITY', [''])[0] if entities.get('UNIVERSITY', []) else ''
|
|
result['professional']['education'][0]['course'] = entities.get('COURSE', [''])[0] if entities.get('COURSE', []) else ''
|
|
result['professional']['education'][0]['certificate'] = entities.get('CERTIFICATE', [''])[0] if entities.get('CERTIFICATE', []) else ''
|
|
|
|
print(result)
|
|
return result
|
|
|
|
|