File size: 5,664 Bytes
8bab08d
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
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
# file: agents/hunter.py
"""
Hunter Agent - Discovers companies dynamically
Now uses web search to find company information instead of static files
"""
import json
from typing import List, Optional
from app.schema import Company, Prospect
from app.config import COMPANIES_FILE, SKIP_WEB_SEARCH
from services.company_discovery import get_company_discovery_service
import logging

logger = logging.getLogger(__name__)


class Hunter:
    """
    Discovers companies and creates prospects dynamically

    NEW: Can now discover companies from user input (company names)
    LEGACY: Still supports loading from seed file for backwards compatibility
    """

    def __init__(self, mcp_registry):
        self.mcp = mcp_registry
        self.store = mcp_registry.get_store_client()
        self.discovery = get_company_discovery_service()

    async def run(
        self,
        company_names: Optional[List[str]] = None,
        company_ids: Optional[List[str]] = None,
        use_seed_file: bool = False
    ) -> List[Prospect]:
        """
        Discover companies and create prospects

        Args:
            company_names: List of company names to discover (NEW - dynamic mode)
            company_ids: List of company IDs from seed file (LEGACY - static mode)
            use_seed_file: If True, load from seed file instead of discovery

        Returns:
            List of Prospect objects
        """
        prospects = []

        # Mode 1: Dynamic discovery from company names (NEW)
        if company_names and not use_seed_file:
            logger.info(f"Hunter: Dynamic discovery mode - discovering {len(company_names)} companies")

            for company_name in company_names:
                try:
                    logger.info(f"Hunter: Discovering '{company_name}'...")

                    # Discover company information from web (or use fallback if configured)
                    company = await self.discovery.discover_company(company_name, skip_search=SKIP_WEB_SEARCH)

                    if not company:
                        logger.warning(f"Hunter: Could not discover company '{company_name}'")
                        # Create a minimal fallback company
                        company = self._create_fallback_company(company_name)

                    # Create prospect
                    prospect = Prospect(
                        id=company.id,
                        company=company,
                        status="new"
                    )

                    # Save to store
                    await self.store.save_prospect(prospect)
                    prospects.append(prospect)

                    logger.info(f"Hunter: Successfully created prospect for '{company_name}'")

                except Exception as e:
                    logger.error(f"Hunter: Error discovering '{company_name}': {str(e)}")
                    # Create fallback and continue
                    company = self._create_fallback_company(company_name)
                    prospect = Prospect(
                        id=company.id,
                        company=company,
                        status="new"
                    )
                    await self.store.save_prospect(prospect)
                    prospects.append(prospect)

        # Mode 2: Legacy mode - load from seed file (BACKWARDS COMPATIBLE)
        else:
            logger.info("Hunter: Legacy mode - loading from seed file")

            try:
                # Load from seed file
                with open(COMPANIES_FILE) as f:
                    companies_data = json.load(f)

                for company_data in companies_data:
                    # Filter by IDs if specified
                    if company_ids and company_data["id"] not in company_ids:
                        continue

                    company = Company(**company_data)

                    # Create prospect
                    prospect = Prospect(
                        id=company.id,
                        company=company,
                        status="new"
                    )

                    # Save to store
                    await self.store.save_prospect(prospect)
                    prospects.append(prospect)

                logger.info(f"Hunter: Loaded {len(prospects)} companies from seed file")

            except FileNotFoundError:
                logger.error(f"Hunter: Seed file not found: {COMPANIES_FILE}")
                # If no seed file and no company names provided, return empty
                if not company_names:
                    return []
            except Exception as e:
                logger.error(f"Hunter: Error loading seed file: {str(e)}")
                return []

        return prospects

    def _create_fallback_company(self, company_name: str) -> Company:
        """Create a minimal fallback company when discovery fails"""
        import re
        import uuid

        # Generate ID
        slug = re.sub(r'[^a-zA-Z0-9]', '', company_name.lower())[:20]
        company_id = f"{slug}_{str(uuid.uuid4())[:8]}"

        # Create minimal company
        company = Company(
            id=company_id,
            name=company_name,
            domain=f"{slug}.com",
            industry="Technology",
            size=100,
            pains=[
                "Customer experience improvement needed",
                "Operational efficiency challenges"
            ],
            notes=[
                "Company information discovery in progress",
                "Limited data available"
            ]
        )

        logger.info(f"Hunter: Created fallback company for '{company_name}'")
        return company