CoolFace
Apppublic

reddysainath581/placement.activity

sourceHugging Faceupdated 1y agoView on Hugging Face
0likes
app.py459 linesDownload Raw Back to root
1import streamlit as st2import pandas as pd3import gspread4from google.oauth2.service_account import Credentials5import re6import requests7import fitz  # PyMuPDF8import pdfplumber9import logging10from selenium import webdriver11from selenium.webdriver.chrome.options import Options12from datetime import datetime13from dotenv import load_dotenv14from linkedin_api import Linkedin15import os16 17# Configure logging18logging.basicConfig(level=logging.WARNING, format="%(asctime)s - %(levelname)s - %(message)s")19 20# Load environment variables21load_dotenv()22options = Options()23options.add_argument("--headless")24driver = webdriver.Chrome(options=options)25st.title("Placement Report")26# Streamlit input for email and password27EMAIL = st.text_input("## Enter your LinkedIn username or email:")28PASSWORD = st.text_input("## Enter your password:", type="password")29 30# Check if both email and password are provided31if EMAIL and PASSWORD:32    # Proceed with authentication if both fields are filled33    api = Linkedin(EMAIL, PASSWORD, debug=True)34 35 36# Streamlit App Title37 38 39# Google Sheets Connection Setup40SERVICE_ACCOUNT_FILE = r"C:\Users\lopam\Documents\Linkedin interface\newcred.json" 41SCOPES = ['https://www.googleapis.com/auth/spreadsheets', 'https://www.googleapis.com/auth/drive']42 43# Authenticate with Google Sheets44try:45    credentials = Credentials.from_service_account_file(SERVICE_ACCOUNT_FILE, scopes=SCOPES)46    client = gspread.authorize(credentials)47except Exception as e:48    st.error(f"Failed to authenticate Google Sheets API. Error: {e}")49    st.stop()50 51# Function to extract LinkedIn URLs from a given cell (text or HTML)52def extract_hyperlinks(cell):53    linkedin_urls = []54    if isinstance(cell, str):  # Ensure the cell contains a string.55        linkedin_urls = re.findall(r'https?://(?:www\.)?linkedin\.com/in/[^\s]+', cell)56    return linkedin_urls57 58# Function to extract LinkedIn URLs from PDF59def extract_linkedin_from_pdf(pdf_file):60    linkedin_urls = []61    with fitz.open(pdf_file) as my_pdf_file:62        for page_number in range(1, len(my_pdf_file) + 1):63            page = my_pdf_file[page_number - 1]64            for pdf_link in page.links():65                if "uri" in pdf_link:66                    url = pdf_link["uri"]67                    if re.match(r'https?://(?:www\.)?linkedin\.com/in/[^\s]+', url):68                        linkedin_urls.append(url)69    return linkedin_urls70 71def split_experience(row):72    # If no experience data is found, return "No Experience Data" for both companies73    if row['Experience'] == "No experience data found.":74        return {"Company 1": "No Experience Data", "Company 2": "No Experience Data found" }75    76    # Split the experience data by newlines to separate different companies77    companies = row['Experience'].split("\n")78    79    # Create a dictionary to store the company data80    company_dict = {}81    82    # Assign each company data to a Company column83    for i, company in enumerate(companies):84        company_dict[f"Company {i + 1}"] = company.strip()  # Strip any extra spaces85    86    return company_dict87 88# Function to process the DataFrame and split experience columns89def process_data(df, api):90    # Split the experience data and add new columns91    experience_split = df.apply(split_experience, axis=1)92    experience_part = pd.DataFrame(experience_split.tolist())93    94    # Merge the new experience columns into the original DataFrame95    df = pd.concat([df, experience_part], axis=1)96    97    # Fill any NaN values with "No Experience Data found"98    df.fillna("No Experience Data found", inplace=True)99    100    return df101 102# Updated classify_experience function103def classify_experience(row, company_columns):104    # Check if Batch Start Date and Batch End Date are valid105    if pd.isna(row['Batch Start Date']) or pd.isna(row['Batch End Date']):106        return "Invalid Batch Dates"107 108    batch_start_date = datetime.strptime(row['Batch Start Date'], "%m %Y")109    batch_end_date = datetime.strptime(row['Batch End Date'], "%m %Y")110 111    # Loop through the experience columns (e.g., Company 1, Company 2, etc.)112    for company_col in company_columns:113        # If the company column is empty or has 'Not placed' data, classify as "No experience"114        if pd.isna(row.get(company_col, None)) or 'Not placed' in str(row.get(company_col, '')):115            return "No experience"116        117        # Extract the experience data from the company column118        experience_data = row[company_col]119 120        # Try to extract the start date from the experience data121        try:122            start_date_str = experience_data.split("Start Date:")[1].split(",")[0].strip()123            start_date = datetime.strptime(start_date_str, "%m %Y")124        except (IndexError, ValueError):125            return "Not placed"  # If unable to extract the start date, return "Not placed"126 127        # Classify based on the batch dates128        if start_date < batch_start_date:129            return "Pre Imarticus"130        elif start_date > batch_end_date:131            return "Post Imarticus"132        elif batch_start_date <= start_date <= batch_end_date:133            return "Self Placed"134        else:135            return "Unknown"  # In case no condition is met, you can use "Unknown"136 137    # If no valid experience is found after checking all columns138    return "No experience data found"139 140# For Google Sheets input141file_type = st.radio("Choose the source of data:", ("Google Sheets", "Excel File"))142 143# Convert Batch Start Date and Batch End Date to datetime format with only month and year (month as number)144def convert_to_month_year(df, date_column_name):145    try:146        df[date_column_name] = pd.to_datetime(df[date_column_name], errors='coerce').dt.to_period('M').dt.strftime('%m %Y')147    except Exception as e:148        logging.warning(f"Error converting {date_column_name}: {e}")149    return df150 151if file_type == "Google Sheets":152    SHEET_ID = st.text_input("## Enter the Google Sheet URL (found in the sheet URL):")153 154    if SHEET_ID:155        try:156            sheet = client.open_by_key(SHEET_ID).sheet1157            cell_values = sheet.get_all_values()158            data = pd.DataFrame(cell_values[1:], columns=cell_values[0])159            st.dataframe(data)160 161            # LinkedIn URL Extraction Logic162            df = pd.DataFrame(columns=["Unique ID", "Student Name", "Batch Start Date", "Batch End Date", "Link"])163 164            # Process each row for LinkedIn URLs165            for _, row in data.iterrows():166                linkedin_urls_collected = []167                for cell in row:168                    linkedin_urls = extract_hyperlinks(cell)169                    linkedin_urls_collected.extend(linkedin_urls)170 171                # Look for Google Drive links to extract PDFs172                for cell in row:173                    if isinstance(cell, str) and 'drive.google.com' in cell:174                        try:175                            if "id=" in cell:176                                file_id = cell.split("id=")[1].split("&")[0]177                            elif "/d/" in cell:178                                file_id = cell.split("/d/")[1].split("/")[0]179                            else:180                                continue181 182                            download_url = f"https://drive.google.com/uc?export=download&id={file_id}"183                            response = requests.get(download_url)184                            if response.status_code == 200:185                                with open("temp.pdf", "wb") as f:186                                    f.write(response.content)187 188                                linkedin_urls_from_pdf = extract_linkedin_from_pdf("temp.pdf")189                                linkedin_urls_collected.extend(linkedin_urls_from_pdf)190                        except Exception as e:191                            logging.error(f"Error processing Google Drive link: {e}")192 193                linkedin_urls_collected = list(set(linkedin_urls_collected))  # Remove duplicates194 195                # Add LinkedIn URLs to DataFrame196                if linkedin_urls_collected:197                    for linkedin_url in linkedin_urls_collected:198                        temp_df = pd.DataFrame({199                            "Unique ID": [row['Unique ID']],200                            "Student Name": [row['Student Name']],201                            "Batch Start Date": [row['Batch Start Date']],202                            "Batch End Date": [row['Batch End Date']],203                            "Link": [linkedin_url]204                        })205                        df = pd.concat([df, temp_df], ignore_index=True)206                else:207                    temp_df = pd.DataFrame({208                        "Unique ID": [row['Unique ID']],209                        "Student Name": [row['Student Name']],210                        "Batch Start Date": [row['Batch Start Date']],211                        "Batch End Date": [row['Batch End Date']],212                        "Link": ["No LinkedIn URL found"]213                    })214                    df = pd.concat([df, temp_df], ignore_index=True)215 216            # LinkedIn username extraction for the Google Sheets data217            df["Username"] = df["Link"].apply(lambda link: re.search(r'linkedin\.com/in/([^/]+)/?', link).group(1) if pd.notnull(link) and "linkedin.com/in/" in link else "Invalid URL")218 219            # Apply date conversion to 'Batch Start Date' and 'Batch End Date' after LinkedIn extraction220            df = convert_to_month_year(df, "Batch Start Date")221            df = convert_to_month_year(df, "Batch End Date")222 223            # Scrape each LinkedIn profile link for the Google Sheets data224            data1 = []225            for _, row in df.iterrows():226                username = row["Username"]227                url = row["Link"]228                name_text = row["Student Name"]229                batch_start_date = row["Batch Start Date"]230                batch_end_date = row["Batch End Date"]231                unique_id = row["Unique ID"]232 233                if username != "Invalid URL":234                    try:235                        profile = api.get_profile(username)236                        experience_data = profile.get("experience", [])237                        experience_text = "\n".join(238                            [239                                f"Company: {exp.get('companyName', 'N/A')}, Title: {exp.get('title', 'N/A')}, "240                                f"Start Date: {exp.get('timePeriod', {}).get('startDate', {}).get('month', 'N/A')} "241                                f"{exp.get('timePeriod', {}).get('startDate', {}).get('year', 'N/A')}, "242                                f"End Date: {exp.get('timePeriod', {}).get('endDate', {}).get('month', 'Present')} "243                                f"{exp.get('timePeriod', {}).get('endDate', {}).get('year', 'N/A')}"244                                for exp in experience_data245                            ]246                        ) if experience_data else "No experience data found."247                    except Exception as e:248                        logging.warning(f"API failed for {username}: {e}")249                        experience_text = "API Error"250                else:251                    experience_text = "Invalid URL"252 253                data1.append({254                    "Unique ID": unique_id,255                    "Student Name": name_text,256                    "Batch Start Date": batch_start_date,257                    "Batch End Date": batch_end_date,258                    "LinkedIn URL": url,259                    "Experience": experience_text260                })261 262            # Display the scraped data263            scraped_data_df = pd.DataFrame(data1)264            scraped_data_df = process_data(scraped_data_df, api)265 266            # Apply experience classification267            company_columns = ["Company 1", "Company 2"]  # Modify based on your actual column names268            scraped_data_df["Experience Classification"] = scraped_data_df.apply(269                lambda row: classify_experience(row, company_columns), axis=1270            )271 272            st.dataframe(scraped_data_df)273 274        except Exception as e:275            st.error(f"Error accessing Google Sheets: {e}")276 277# For Excel File input278elif file_type == "Excel File":279    excel_file = st.file_uploader("Upload Excel file", type=["xls", "xlsx"])280 281    if excel_file:282        try:283            data = pd.read_excel(excel_file)284            st.dataframe(data)285 286            # LinkedIn URL Extraction Logic287            df = pd.DataFrame(columns=["Unique ID", "Student Name", "Batch Start Date", "Batch End Date", "Link"])288 289            # Process each row for LinkedIn URLs290            for _, row in data.iterrows():291                linkedin_urls_collected = []292                for cell in row:293                    linkedin_urls = extract_hyperlinks(cell)294                    linkedin_urls_collected.extend(linkedin_urls)295 296                # Look for Google Drive links to extract PDFs297                for cell in row:298                    if isinstance(cell, str) and 'drive.google.com' in cell:299                        try:300                            if "id=" in cell:301                                file_id = cell.split("id=")[1].split("&")[0]302                            elif "/d/" in cell:303                                file_id = cell.split("/d/")[1].split("/")[0]304                            else:305                                continue306 307                            download_url = f"https://drive.google.com/uc?export=download&id={file_id}"308                            response = requests.get(download_url)309                            if response.status_code == 200:310                                with open("temp.pdf", "wb") as f:311                                    f.write(response.content)312 313                                linkedin_urls_from_pdf = extract_linkedin_from_pdf("temp.pdf")314                                linkedin_urls_collected.extend(linkedin_urls_from_pdf)315                        except Exception as e:316                            logging.error(f"Error processing Google Drive link: {e}")317 318                linkedin_urls_collected = list(set(linkedin_urls_collected))  # Remove duplicates319 320                # Add LinkedIn URLs to DataFrame321                if linkedin_urls_collected:322                    for linkedin_url in linkedin_urls_collected:323                        temp_df = pd.DataFrame({324                            "Unique ID": [row['Unique ID']],325                            "Student Name": [row['Student Name']],326                            "Batch Start Date": [row['Batch Start Date']],327                            "Batch End Date": [row['Batch End Date']],328                            "Link": [linkedin_url]329                        })330                        df = pd.concat([df, temp_df], ignore_index=True)331                else:332                    temp_df = pd.DataFrame({333                        "Unique ID": [row['Unique ID']],334                        "Student Name": [row['Student Name']],335                        "Batch Start Date": [row['Batch Start Date']],336                        "Batch End Date": [row['Batch End Date']],337                        "Link": ["No LinkedIn URL found"]338                    })339                    df = pd.concat([df, temp_df], ignore_index=True)340 341            # LinkedIn username extraction for the Google Sheets data342            df["Username"] = df["Link"].apply(lambda link: re.search(r'linkedin\.com/in/([^/]+)/?', link).group(1) if pd.notnull(link) and "linkedin.com/in/" in link else "Invalid URL")343 344            # Apply date conversion to 'Batch Start Date' and 'Batch End Date' after LinkedIn extraction345            df = convert_to_month_year(df, "Batch Start Date")346            df = convert_to_month_year(df, "Batch End Date")347 348            # Scrape each LinkedIn profile link for the Google Sheets data349            data1 = []350            for _, row in df.iterrows():351                username = row["Username"]352                url = row["Link"]353                name_text = row["Student Name"]354                batch_start_date = row["Batch Start Date"]355                batch_end_date = row["Batch End Date"]356                unique_id = row["Unique ID"]357 358                if username != "Invalid URL":359                    try:360                        profile = api.get_profile(username)361                        experience_data = profile.get("experience", [])362                        experience_text = "\n".join(363                            [364                                f"Company: {exp.get('companyName', 'N/A')}, Title: {exp.get('title', 'N/A')}, "365                                f"Start Date: {exp.get('timePeriod', {}).get('startDate', {}).get('month', 'N/A')} "366                                f"{exp.get('timePeriod', {}).get('startDate', {}).get('year', 'N/A')}, "367                                f"End Date: {exp.get('timePeriod', {}).get('endDate', {}).get('month', 'Present')} "368                                f"{exp.get('timePeriod', {}).get('endDate', {}).get('year', 'N/A')}"369                                for exp in experience_data370                            ]371                        ) if experience_data else "No experience data found."372                    except Exception as e:373                        logging.warning(f"API failed for {username}: {e}")374                        experience_text = "API Error"375                else:376                    experience_text = "Invalid URL"377 378                data1.append({379                    "Unique ID": unique_id,380                    "Student Name": name_text,381                    "Batch Start Date": batch_start_date,382                    "Batch End Date": batch_end_date,383                    "LinkedIn URL": url,384                    "Experience": experience_text385                })386 387 388 389                # Function to convert DataFrame to CSV390                def convert_df_to_csv(df):391                    return df.to_csv(index=False).encode("utf-8")392 393 394            # Display the scraped data395            scraped_data_df = pd.DataFrame(data1)396            scraped_data_df = process_data(scraped_data_df, api)397 398            # Apply experience classification399            company_columns = ["Company 1", "Company 2"]  # Modify based on your actual column names400            scraped_data_df["Experience Classification"] = scraped_data_df.apply(401                lambda row: classify_experience(row, company_columns), axis=1402            )403 404            st.dataframe(scraped_data_df)405 406            # Convert DataFrame to CSV407            csv_data = convert_df_to_csv(scraped_data_df)408 409            # Add download button410            st.download_button(411            label="Download Scraped Data as CSV",412            data=csv_data,413            file_name="scraped_data.csv",414            mime="text/csv",415            )416 417 418        except Exception as e:419            st.error(f"Error reading Excel file: {e}")420driver.quit()421 422 423# Generate summary report for experience classification424import pandas as pd425import streamlit as st426 427# Generate summary report for experience classification428import pandas as pd429import streamlit as st430 431def generate_summary_report(scraped_data_df):432    """433    Generates and displays a summary report for experience classification with names included.434    """435    if "Experience Classification" in scraped_data_df.columns and "Student Name" in scraped_data_df.columns:436        summary_report = scraped_data_df.groupby(["Experience Classification"])\437                                      .agg({"Student Name": list, "Experience Classification": "count"})\438                                      .rename(columns={"Experience Classification": "Count"})\439                                      .reset_index()440        441        st.subheader("Summary Report: Experience Classification")442        st.dataframe(summary_report)443        444        # Optionally, display a bar chart445        st.bar_chart(summary_report.set_index("Experience Classification")['Count'])446        447        # Prepare CSV data for download448        csv = summary_report.to_csv(index=False).encode('utf-8')449        st.download_button(label="Download Summary Report", 450                           data=csv, 451                           file_name="experience_summary_report.csv", 452                           mime="text/csv")453    else:454        st.warning("Required columns not found in the DataFrame.")455 456# Call the function to generate the summary report457generate_summary_report(scraped_data_df)458 459