File size: 7,708 Bytes
37185e0 cdbe688 c400028 37185e0 c400028 052a8fc e3f43f3 c400028 77c5125 c400028 77c5125 e3f43f3 77c5125 37185e0 bc5de14 0724750 bc5de14 0724750 bc5de14 0724750 bc5de14 0724750 87ccea1 77c5125 0724750 37185e0 0724750 37185e0 3be9484 77c5125 87ccea1 77c5125 bc5de14 0724750 77c5125 0724750 bc5de14 77c5125 bc5de14 0724750 bc5de14 77c5125 bc5de14 77c5125 87ccea1 c0d54a6 3be9484 37185e0 3be9484 0724750 37185e0 3be9484 37185e0 c0d54a6 37185e0 2bd7b24 09696f6 c400028 77c5125 c400028 bc5de14 77c5125 0724750 bc5de14 2bd7b24 0724750 77c5125 2bd7b24 0724750 c400028 2bd7b24 77c5125 c3d82ad 12d8a5c 87ccea1 2bd7b24 729192c 2bd7b24 729192c 12d8a5c 729192c 12d8a5c 2bd7b24 09696f6 2bd7b24 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 |
import gradio as gr
import requests
import os
# Load API keys securely from environment variables
proxycurl_api_key = os.getenv("PROXYCURL_API_KEY") # Add your Proxycurl API key to your environment variables
groq_api_key = os.getenv("GROQ_CLOUD_API_KEY")
# Function to use Proxycurl API to get the LinkedIn profile data
def get_linkedin_profile_via_proxycurl(linkedin_profile_url):
headers = {
"Authorization": f"Bearer {proxycurl_api_key}",
}
url = f"https://nubela.co/proxycurl/api/v2/linkedin?url={linkedin_profile_url}"
response = requests.get(url, headers=headers)
if response.status_code == 200:
data = response.json()
# Extract relevant skills and experiences from LinkedIn profile
bio = data.get("summary", "No bio available")
skills = data.get("skills", []) # List of skills from the LinkedIn profile
experiences = data.get("experiences", []) # List of experiences from the LinkedIn profile
return bio, skills, experiences
else:
return "Error: Unable to fetch LinkedIn profile", [], []
# Function to get company information via Proxycurl Company API
def get_company_info(company_name):
headers = {
"Authorization": f"Bearer {proxycurl_api_key}",
}
url = f"https://nubela.co/proxycurl/api/v2/linkedin/company?company_name={company_name}"
response = requests.get(url, headers=headers)
if response.status_code == 200:
data = response.json()
company_info = data.get("description", "No detailed company info available.")
return company_info
else:
return "Error: Unable to fetch company information."
# Placeholder for role description; could be enhanced to scrape or fetch real role data
def get_role_description(role_name, company_name):
return f"The role of {role_name} at {company_name} involves..."
# Helper function to call Groq Cloud LLM API to generate and correct the email
def generate_and_correct_email(bio, company_name, role, company_info, role_description, skills, experiences):
url = "https://api.groq.com/openai/v1/chat/completions"
headers = {
"Authorization": f"Bearer {groq_api_key}",
"Content-Type": "application/json",
}
# New, detailed prompt with emphasis on correlating LinkedIn skills and experience to the job role
prompt = f"""
Write a professional email applying for the {role} position at {company_name}.
The candidate’s bio is: {bio}.
The candidate's LinkedIn profile highlights the following skills: {', '.join(skills)}.
The candidate has the following experiences relevant to the job: {', '.join([exp['title'] for exp in experiences])}.
The email should:
- Be professional, engaging, and customized to the company's culture and the role’s requirements.
- Include relevant company details: {company_info}.
- Highlight the candidate’s skills and experiences from LinkedIn, mapping them directly to the job's requirements. The role description is: {role_description}.
- Emphasize how the candidate’s background aligns with the company’s values and mission.
- Attract the company's attention by focusing on how the candidate's background can bring value to the role and the company's future goals.
- Use a tone that is persuasive but not overly promotional.
- End with a strong call to action, encouraging the company to schedule an interview to discuss how the candidate can contribute to their success.
Structure the email as follows:
1. **Introduction**: Briefly introduce the candidate and state the role they are applying for.
2. **Skills & Experience**: Map the candidate’s skills and experience from LinkedIn to the job's key requirements.
3. **Alignment with the Company**: Emphasize how the candidate’s background fits with the company's mission, values, and goals.
4. **Call to Action**: Encourage the company to schedule an interview to further discuss the candidate’s fit for the role.
Ensure that redundant sign-offs like 'Best regards' or 'Sincerely' are not included.
"""
# Construct the data payload for the API request
data = {
"messages": [
{
"role": "user",
"content": prompt
}
],
"model": "llama3-8b-8192"
}
response = requests.post(url, headers=headers, json=data)
if response.status_code == 200:
return response.json()["choices"][0]["message"]["content"].strip()
else:
print(f"Error: {response.status_code}, {response.text}")
return "Error generating email. Please check your API key or try again later."
# Main function to create the email and allow for saving, editing, or copying
def create_email(name, company_name, role, email, phone, linkedin_profile_url):
# Step 1: Fetch LinkedIn profile using Proxycurl API if LinkedIn URL is provided
if linkedin_profile_url:
bio, skills, experiences = get_linkedin_profile_via_proxycurl(linkedin_profile_url)
else:
bio = f"{name} is a professional." # Default bio if no LinkedIn URL is provided
skills, experiences = [], []
# Step 2: Fetch company information and role description
company_info = get_company_info(company_name)
role_description = get_role_description(role, company_name)
# Step 3: Generate the email using Groq Cloud LLM
generated_email = generate_and_correct_email(bio, company_name, role, company_info, role_description, skills, experiences)
# Step 4: Add the user's email, phone number, and LinkedIn profile to the signature
signature = f"\n\nBest regards,\n{name}\nEmail: {email}\nPhone: {phone}\nLinkedIn: {linkedin_profile_url if linkedin_profile_url else 'Not provided'}"
# Ensure the body doesn't include any redundant 'Best regards' or 'Sincerely' and just append our signature
for phrase in ["Best regards", "Sincerely"]:
if phrase in generated_email:
generated_email = generated_email.split(phrase)[0].strip()
# Return the final polished email with the signature
return generated_email + signature
# Define interface with Gradio
def gradio_ui():
# Define inputs
name_input = gr.Textbox(label="Your Name", placeholder="Enter your name")
company_name_input = gr.Textbox(label="Company Name or URL", placeholder="Enter the company name or website URL")
role_input = gr.Textbox(label="Role Applying For", placeholder="Enter the role you are applying for")
email_input = gr.Textbox(label="Your Email Address", placeholder="Enter your email address")
phone_input = gr.Textbox(label="Your Phone Number", placeholder="Enter your phone number")
linkedin_input = gr.Textbox(label="Your LinkedIn URL", placeholder="Enter your LinkedIn profile URL") # New field for LinkedIn URL
# Define output for the generated email
email_output = gr.Textbox(label="Generated Email", placeholder="Your generated email will appear here", lines=10)
# Create the Gradio interface
demo = gr.Interface(
fn=create_email, # Function to call when the user submits
inputs=[name_input, company_name_input, role_input, email_input, phone_input, linkedin_input],
outputs=[email_output],
title="Email Writing AI Agent",
description="Generate a professional email for a job application by providing your basic info.",
allow_flagging="never" # Disable flagging
)
# Launch the Gradio app
demo.launch()
# Start the Gradio app when running the script
if __name__ == "__main__":
gradio_ui()
|