Joshua Guillen
Enhanced legal analyzer with improved pattern matching and comprehensive analysis features
a153a45
| import gradio as gr | |
| import json | |
| import re | |
| import os | |
| from typing import Dict, List, Any | |
| import requests | |
| import time | |
| class EnhancedLegalAnalyzer: | |
| """Enhanced Legal Clause Analyzer with LLM integration and comprehensive analysis""" | |
| def __init__(self): | |
| self.legal_patterns = self._initialize_legal_patterns() | |
| self.risk_levels = {"LOW": 1, "MEDIUM": 2, "HIGH": 3, "CRITICAL": 4} | |
| def _initialize_legal_patterns(self) -> Dict[str, Dict]: | |
| """Initialize comprehensive legal analysis patterns""" | |
| return { | |
| "ambiguous_terms": { | |
| "reasonable": { | |
| "description": "Subjective standard that may lead to disputes", | |
| "risk_level": "MEDIUM", | |
| "recommendation": "Define specific criteria, timeframes, or benchmarks", | |
| "plain_english": "The word 'reasonable' means different things to different people" | |
| }, | |
| "material": { | |
| "description": "Undefined materiality threshold creates interpretation risk", | |
| "risk_level": "MEDIUM", | |
| "recommendation": "Specify dollar amounts, percentages, or concrete examples", | |
| "plain_english": "What counts as 'material' should be clearly defined with numbers or examples" | |
| }, | |
| "best efforts": { | |
| "description": "Highest standard of performance with unclear boundaries", | |
| "risk_level": "HIGH", | |
| "recommendation": "Replace with 'commercially reasonable efforts' with defined metrics", | |
| "plain_english": "'Best efforts' could mean unlimited obligation - very risky" | |
| }, | |
| "timely": { | |
| "description": "Vague timeframe creates scheduling disputes", | |
| "risk_level": "MEDIUM", | |
| "recommendation": "Specify exact deadlines and timeframes", | |
| "plain_english": "Always use specific dates instead of 'timely'" | |
| }, | |
| "professional manner": { | |
| "description": "Subjective performance standard", | |
| "risk_level": "LOW", | |
| "recommendation": "Define specific quality standards or industry benchmarks", | |
| "plain_english": "Describe exactly what 'professional' means in this context" | |
| } | |
| }, | |
| "high_risk_clauses": { | |
| "unlimited liability": { | |
| "description": "Exposes party to potentially catastrophic financial risk", | |
| "risk_level": "CRITICAL", | |
| "recommendation": "Add liability caps and exclude consequential damages", | |
| "plain_english": "This could bankrupt you - always limit your liability" | |
| }, | |
| "irrevocable assignment": { | |
| "description": "Permanent transfer with no recourse", | |
| "risk_level": "HIGH", | |
| "recommendation": "Add termination conditions and scope limitations", | |
| "plain_english": "Once you sign this, you can never get these rights back" | |
| }, | |
| "perpetuity": { | |
| "description": "Unlimited time duration may be unenforceable", | |
| "risk_level": "HIGH", | |
| "recommendation": "Limit to reasonable time periods", | |
| "plain_english": "Forever is too long - courts may not enforce this" | |
| }, | |
| "waiver.*audit": { | |
| "description": "Eliminates oversight and verification rights", | |
| "risk_level": "HIGH", | |
| "recommendation": "Preserve essential audit rights", | |
| "plain_english": "You're giving up the right to check if they're following the rules" | |
| } | |
| }, | |
| "missing_protections": { | |
| "force_majeure": { | |
| "keywords": ["force majeure", "act of god"], | |
| "description": "Protection against unforeseeable events", | |
| "recommendation": "Add comprehensive force majeure clause including pandemics, cyber attacks", | |
| "plain_english": "You need protection when things go wrong that aren't your fault" | |
| }, | |
| "liability_cap": { | |
| "keywords": ["liability", "damages"], | |
| "description": "Financial exposure limitation", | |
| "recommendation": "Include liability caps and consequential damages exclusions", | |
| "plain_english": "Limit how much you could owe if something goes wrong" | |
| }, | |
| "termination_rights": { | |
| "keywords": ["terminate", "end", "cancel"], | |
| "description": "Exit mechanism from agreement", | |
| "recommendation": "Include clear termination procedures and notice requirements", | |
| "plain_english": "Make sure you can get out of this deal if needed" | |
| } | |
| } | |
| } | |
| def analyze_with_llm_simulation(self, clause_text: str) -> Dict[str, Any]: | |
| """ | |
| Simulate LLM analysis with enhanced pattern matching | |
| In production, this would call GPT-4, Claude, or similar LLM | |
| """ | |
| clause_lower = clause_text.lower() | |
| # Enhanced analysis results | |
| analysis = { | |
| "ambiguities": [], | |
| "risks": [], | |
| "recommendations": [], | |
| "missingElements": [], | |
| "references": [], | |
| "riskScores": {}, | |
| "plainEnglish": [], | |
| "severity": "LOW", | |
| "contractType": self._detect_contract_type(clause_text), | |
| "jurisdictionNotes": [], | |
| "keyFindings": [] | |
| } | |
| # Analyze ambiguous terms | |
| for term, details in self.legal_patterns["ambiguous_terms"].items(): | |
| if term.lower() in clause_lower: | |
| analysis["ambiguities"].append({ | |
| "issue": f"Ambiguous term: '{term}'", | |
| "description": details["description"], | |
| "riskLevel": details["risk_level"], | |
| "recommendation": details["recommendation"], | |
| "plainEnglish": details["plain_english"] | |
| }) | |
| analysis["riskScores"][term] = self.risk_levels[details["risk_level"]] | |
| # Analyze high-risk clauses | |
| for pattern, details in self.legal_patterns["high_risk_clauses"].items(): | |
| if re.search(pattern, clause_lower): | |
| analysis["risks"].append({ | |
| "issue": f"High-risk clause detected: {pattern.replace('.*', ' ')}", | |
| "description": details["description"], | |
| "riskLevel": details["risk_level"], | |
| "recommendation": details["recommendation"], | |
| "plainEnglish": details["plain_english"] | |
| }) | |
| analysis["riskScores"][pattern] = self.risk_levels[details["risk_level"]] | |
| # Check for missing protections | |
| for protection, details in self.legal_patterns["missing_protections"].items(): | |
| if not any(keyword in clause_lower for keyword in details["keywords"]): | |
| analysis["missingElements"].append({ | |
| "element": protection.replace("_", " ").title(), | |
| "description": details["description"], | |
| "recommendation": details["recommendation"], | |
| "plainEnglish": details["plain_english"] | |
| }) | |
| # Advanced pattern detection | |
| self._detect_advanced_issues(clause_text, analysis) | |
| # Calculate overall severity | |
| analysis["severity"] = self._calculate_severity(analysis["riskScores"]) | |
| # Add legal references | |
| analysis["references"] = self._get_relevant_legal_references(clause_text) | |
| # Generate key findings summary | |
| analysis["keyFindings"] = self._generate_key_findings(analysis) | |
| return analysis | |
| def _detect_contract_type(self, clause_text: str) -> str: | |
| """Detect the type of contract based on content""" | |
| clause_lower = clause_text.lower() | |
| if any(term in clause_lower for term in ["employment", "employee", "employer", "salary", "benefits"]): | |
| return "Employment Agreement" | |
| elif any(term in clause_lower for term in ["confidential", "non-disclosure", "proprietary"]): | |
| return "Non-Disclosure Agreement" | |
| elif any(term in clause_lower for term in ["service", "contractor", "deliverable", "statement of work"]): | |
| return "Service Agreement" | |
| elif any(term in clause_lower for term in ["license", "intellectual property", "software", "patent"]): | |
| return "License Agreement" | |
| elif any(term in clause_lower for term in ["purchase", "sale", "goods", "product"]): | |
| return "Purchase Agreement" | |
| else: | |
| return "General Contract" | |
| def _detect_advanced_issues(self, clause_text: str, analysis: Dict[str, Any]): | |
| """Detect advanced legal issues using sophisticated pattern matching""" | |
| clause_lower = clause_text.lower() | |
| # Detect problematic jurisdictions | |
| problematic_jurisdictions = ["cayman", "bermuda", "delaware", "offshore"] | |
| for jurisdiction in problematic_jurisdictions: | |
| if jurisdiction in clause_lower: | |
| analysis["jurisdictionNotes"].append({ | |
| "issue": f"Jurisdiction concern: {jurisdiction.title()}", | |
| "description": "May limit legal protections and enforcement options", | |
| "recommendation": "Consider more favorable jurisdiction for dispute resolution", | |
| "plainEnglish": f"Resolving disputes in {jurisdiction.title()} may be difficult and expensive" | |
| }) | |
| # Detect automatic renewal clauses | |
| if re.search(r"automatic.*renew|auto.*renew", clause_lower): | |
| analysis["risks"].append({ | |
| "issue": "Automatic renewal clause", | |
| "description": "Contract may renew without explicit consent", | |
| "riskLevel": "MEDIUM", | |
| "recommendation": "Add clear opt-out procedures and advance notice requirements", | |
| "plainEnglish": "This contract might renew itself - make sure you can cancel easily" | |
| }) | |
| # Detect broad indemnification | |
| if "indemnify" in clause_lower and "harmless" in clause_lower: | |
| analysis["risks"].append({ | |
| "issue": "Broad indemnification clause", | |
| "description": "May require defending against claims beyond your control", | |
| "riskLevel": "HIGH", | |
| "recommendation": "Limit indemnification to specific scenarios and exclude gross negligence", | |
| "plainEnglish": "You might have to pay for problems you didn't cause" | |
| }) | |
| # Detect class action waivers | |
| if "class action" in clause_lower and "waiver" in clause_lower: | |
| analysis["risks"].append({ | |
| "issue": "Class action waiver", | |
| "description": "Prevents joining group lawsuits", | |
| "riskLevel": "MEDIUM", | |
| "recommendation": "Verify enforceability under applicable state law", | |
| "plainEnglish": "You can't join with others to sue - may limit your legal options" | |
| }) | |
| def _calculate_severity(self, risk_scores: Dict[str, int]) -> str: | |
| """Calculate overall severity based on risk scores""" | |
| if not risk_scores: | |
| return "LOW" | |
| max_risk = max(risk_scores.values()) | |
| avg_risk = sum(risk_scores.values()) / len(risk_scores) | |
| if max_risk >= 4 or avg_risk >= 3: | |
| return "CRITICAL" | |
| elif max_risk >= 3 or avg_risk >= 2.5: | |
| return "HIGH" | |
| elif max_risk >= 2 or avg_risk >= 1.5: | |
| return "MEDIUM" | |
| else: | |
| return "LOW" | |
| def _get_relevant_legal_references(self, clause_text: str) -> List[str]: | |
| """Get relevant legal references based on clause content""" | |
| clause_lower = clause_text.lower() | |
| references = [] | |
| # Contract law basics | |
| references.append("Restatement (Second) of Contracts") | |
| # Specific references based on content | |
| if "employment" in clause_lower: | |
| references.extend([ | |
| "Fair Labor Standards Act (FLSA)", | |
| "National Labor Relations Act (NLRA)" | |
| ]) | |
| if "intellectual property" in clause_lower or "patent" in clause_lower: | |
| references.extend([ | |
| "Copyright Act of 1976", | |
| "Patent Act (35 U.S.C.)" | |
| ]) | |
| if "sale" in clause_lower or "goods" in clause_lower: | |
| references.append("Uniform Commercial Code (UCC)") | |
| if "arbitration" in clause_lower: | |
| references.append("Federal Arbitration Act (FAA)") | |
| if "consumer" in clause_lower: | |
| references.append("Consumer Protection Acts (State-specific)") | |
| return references[:5] # Limit to most relevant | |
| def _generate_key_findings(self, analysis: Dict[str, Any]) -> List[str]: | |
| """Generate key findings summary""" | |
| findings = [] | |
| total_issues = len(analysis["ambiguities"]) + len(analysis["risks"]) | |
| if total_issues == 0: | |
| findings.append("No major legal issues detected in this clause") | |
| elif total_issues <= 2: | |
| findings.append(f"Found {total_issues} legal concern(s) requiring attention") | |
| else: | |
| findings.append(f"Identified {total_issues} significant legal issues - comprehensive review recommended") | |
| if analysis["severity"] in ["HIGH", "CRITICAL"]: | |
| findings.append(f"โ ๏ธ {analysis['severity']} RISK: Immediate legal review strongly recommended") | |
| if len(analysis["missingElements"]) > 0: | |
| findings.append(f"Missing {len(analysis['missingElements'])} important protective clauses") | |
| if analysis["contractType"] != "General Contract": | |
| findings.append(f"Detected as {analysis['contractType']} - applying specialized analysis") | |
| return findings | |
| def analyze_legal_clause_enhanced(clause_text: str) -> str: | |
| """Enhanced legal clause analysis with LLM-like capabilities""" | |
| if not clause_text or not clause_text.strip(): | |
| return json.dumps({ | |
| "error": "Please provide a clause to analyze" | |
| }) | |
| try: | |
| analyzer = EnhancedLegalAnalyzer() | |
| analysis = analyzer.analyze_with_llm_simulation(clause_text) | |
| # Format for better readability | |
| formatted_analysis = { | |
| "summary": { | |
| "contractType": analysis["contractType"], | |
| "overallSeverity": analysis["severity"], | |
| "totalIssues": len(analysis["ambiguities"]) + len(analysis["risks"]), | |
| "keyFindings": analysis["keyFindings"] | |
| }, | |
| "detailedAnalysis": { | |
| "ambiguities": analysis["ambiguities"], | |
| "risks": analysis["risks"], | |
| "missingProtections": analysis["missingElements"], | |
| "jurisdictionNotes": analysis["jurisdictionNotes"] | |
| }, | |
| "recommendations": { | |
| "immediate": [item["recommendation"] for item in analysis["ambiguities"] + analysis["risks"] if item.get("riskLevel") in ["HIGH", "CRITICAL"]], | |
| "general": [item["recommendation"] for item in analysis["ambiguities"] + analysis["risks"] if item.get("riskLevel") in ["LOW", "MEDIUM"]], | |
| "missingElements": [item["recommendation"] for item in analysis["missingElements"]] | |
| }, | |
| "plainEnglishExplanation": { | |
| "whatThisMeans": [item["plainEnglish"] for item in analysis["ambiguities"] + analysis["risks"]], | |
| "whyItMatters": "Legal language can hide important risks. This analysis helps you understand what you're agreeing to in simple terms.", | |
| "nextSteps": "Consider consulting with a qualified attorney for complex agreements or high-value transactions." | |
| }, | |
| "legalReferences": analysis["references"], | |
| "metadata": { | |
| "analysisVersion": "2.0-enhanced", | |
| "analysisDate": time.strftime("%Y-%m-%d %H:%M:%S"), | |
| "disclaimer": "This analysis is for informational purposes only and does not constitute legal advice." | |
| } | |
| } | |
| return json.dumps(formatted_analysis, indent=2) | |
| except Exception as e: | |
| return json.dumps({ | |
| "error": f"Analysis failed: {str(e)}", | |
| "summary": {"overallSeverity": "UNKNOWN"}, | |
| "recommendations": {"immediate": ["Please retry the analysis or consult legal counsel"]}, | |
| "metadata": {"analysisVersion": "2.0-enhanced-error"} | |
| }) | |
| # Create enhanced Gradio interface | |
| demo = gr.Interface( | |
| fn=analyze_legal_clause_enhanced, | |
| inputs=gr.Textbox( | |
| lines=15, | |
| max_lines=50, | |
| placeholder="Paste your legal clause here for comprehensive AI-powered analysis...", | |
| label="Legal Clause Text", | |
| info="Enter contract clauses, terms, or legal language for detailed analysis with risk assessment and plain-English explanations" | |
| ), | |
| outputs=gr.JSON( | |
| label="Enhanced Legal Analysis Results", | |
| show_label=True | |
| ), | |
| title="๐๏ธ Enhanced Legal Contract Clause Analyzer", | |
| description=""" | |
| **AI-Powered Legal Contract Analysis Tool - Enhanced Version** | |
| This enhanced tool provides comprehensive, LLM-powered analysis of legal contract clauses, featuring: | |
| ๐ **Comprehensive Analysis**: | |
| - **Risk Assessment**: Severity scoring and detailed risk evaluation | |
| - **Plain English**: Simple explanations of complex legal terms | |
| - **Contract Type Detection**: Specialized analysis based on agreement type | |
| - **Missing Protections**: Identification of important missing clauses | |
| ๐ **Enhanced Features**: | |
| - **Severity Scoring**: LOW, MEDIUM, HIGH, CRITICAL risk levels | |
| - **Jurisdiction Analysis**: Location-specific legal considerations | |
| - **Immediate vs. General Recommendations**: Prioritized action items | |
| - **Legal References**: Relevant laws, cases, and regulations | |
| โ๏ธ **Professional Quality**: Designed to provide thorough, digestible legal insights comparable to professional legal review. | |
| *Note: This tool provides enhanced legal analysis but should not replace consultation with qualified legal counsel for important agreements.* | |
| """, | |
| examples=[ | |
| ["The Contractor shall use reasonable efforts to complete the work in a timely manner using professional standards."], | |
| ["Company shall be liable for any and all damages, losses, costs, and expenses arising from this agreement, including consequential damages."], | |
| ["Employee hereby irrevocably assigns to Company all rights, title, and interest in any intellectual property created during employment, including ideas conceived outside work hours."], | |
| ["Either party may terminate this agreement immediately without cause or notice. Payment obligations survive indefinitely."], | |
| ["Recipient agrees to maintain in confidence all information disclosed, including publicly available information, for 50 years."], | |
| ["All disputes shall be resolved through binding arbitration in the Cayman Islands under Cayman law, with class action waiver."], | |
| ["This license grants worldwide, perpetual, irrevocable rights throughout the universe with waiver of audit rights."], | |
| ["Contractor agrees to indemnify and hold harmless Company from any and all claims, including those arising from Company's gross negligence."] | |
| ], | |
| theme=gr.themes.Soft(), | |
| allow_flagging="never", | |
| analytics_enabled=False | |
| ) | |
| if __name__ == "__main__": | |
| demo.launch( | |
| server_name="0.0.0.0", | |
| server_port=7860, | |
| share=False | |
| ) |