Claude-skill-registry discovery-specialist
Contact discovery specialist - handles contact classification, email verification, GDPR compliance, and opportunity enrichment.
install
source · Clone the upstream repo
git clone https://github.com/majiayu000/claude-skill-registry
Claude Code · Install into ~/.claude/skills/
T=$(mktemp -d) && git clone --depth=1 https://github.com/majiayu000/claude-skill-registry "$T" && mkdir -p ~/.claude/skills && cp -r "$T/skills/data/discovery-specialist" ~/.claude/skills/majiayu000-claude-skill-registry-discovery-specialist && rm -rf "$T"
manifest:
skills/data/discovery-specialist/SKILL.mdsource content
Discovery Specialist
Technical specialist for contact discovery and enrichment in totalaud.io.
Core Responsibility
Help Scout Mode deliver accurate, GDPR-compliant contact information for music industry opportunities.
Key Files
- B2B/B2C classificationapps/aud-web/src/lib/discovery/contactClassifier.ts
- Email validationapps/aud-web/src/lib/discovery/emailVerifier.ts
- GDPR suppressionapps/aud-web/src/lib/discovery/suppressionService.ts
- Domain matchingapps/aud-web/src/lib/discovery/domainPatterns.ts
Expertise Areas
Contact Classification
Distinguish B2B (legitimate business contacts) from B2C (personal contacts):
interface ClassificationResult { type: 'B2B' | 'B2C' | 'UNKNOWN' confidence: number // 0-100 signals: Signal[] reasoning: string } // B2B Signals (increase score) const b2bSignals = [ 'info@', 'press@', 'music@', 'submissions@', // Role-based 'bbc.co.uk', 'spotify.com', // Known industry 'Company page', 'Business account', // Platform indicators 'playlist curator', 'A&R', 'radio DJ' // Job titles ] // B2C Signals (decrease score) const b2cSignals = [ 'gmail.com', 'hotmail.com', 'yahoo.com', // Personal email 'Personal account', 'Fan account', // Platform indicators 'listener', 'music lover' // Personal descriptors ]
Email Verification
interface VerificationResult { isValid: boolean deliverable: boolean reason?: 'invalid_format' | 'domain_not_found' | 'mailbox_not_found' confidence: number } async function verifyEmail(email: string): Promise<VerificationResult> { // Format check if (!isValidEmailFormat(email)) { return { isValid: false, deliverable: false, reason: 'invalid_format', confidence: 100 } } // Domain check (MX records) const hasMX = await checkMXRecords(email.split('@')[1]) if (!hasMX) { return { isValid: false, deliverable: false, reason: 'domain_not_found', confidence: 90 } } // Additional verification via API if available return { isValid: true, deliverable: true, confidence: 80 } }
Domain Pattern Library
// Music industry domains by category const domainPatterns = { radio: [ /bbc\.co\.uk/, /radiox\.co\.uk/, /capitalfm\.com/, /absoluteradio\.co\.uk/ ], streaming: [ /spotify\.com/, /apple\.com/, /deezer\.com/, /tidal\.com/ ], press: [ /nme\.com/, /diymagazine\.com/, /clashmusic\.com/, /thefader\.com/ ], blogs: [ /earmilk\.com/, /thissongissick\.com/, /hypem\.com/ ], pr: [ /libertymusic\.co\.uk/, /musicgateway\.com/ ] } function categoriseDomain(domain: string): string | null { for (const [category, patterns] of Object.entries(domainPatterns)) { if (patterns.some(p => p.test(domain))) { return category } } return null }
GDPR Suppression
import { createHash } from 'crypto' class SuppressionService { private suppressedHashes: Set<string> // Hash email for privacy-preserving suppression private hashEmail(email: string): string { return createHash('sha256') .update(email.toLowerCase().trim()) .digest('hex') } async isSupressed(email: string): Promise<boolean> { const hash = this.hashEmail(email) return this.suppressedHashes.has(hash) } async addToSuppression(email: string, reason: string): Promise<void> { const hash = this.hashEmail(email) this.suppressedHashes.add(hash) // Log for audit trail (without PII) await logSuppressionEvent(hash, reason) } }
Confidence Scoring
interface OpportunityScore { overall: number // 0-100 contactQuality: number relevance: number freshness: number signals: string[] } function scoreOpportunity(opp: Opportunity, artist: Artist): OpportunityScore { let contactQuality = 50 // Email verification if (opp.emailVerified) contactQuality += 30 if (opp.emailType === 'role-based') contactQuality += 10 if (opp.lastContacted && daysSince(opp.lastContacted) < 30) contactQuality += 10 // Relevance scoring const relevance = calculateRelevance(opp, artist) // Freshness const freshness = opp.lastVerified ? Math.max(0, 100 - daysSince(opp.lastVerified)) : 50 return { overall: (contactQuality + relevance + freshness) / 3, contactQuality, relevance, freshness, signals: collectSignals(opp) } }
Common Tasks
Add New Domain Pattern
- Identify new music industry domain
- Add regex to appropriate category
- Test classification accuracy
- Update pattern count metrics
Improve Classification Accuracy
- Analyse misclassifications
- Add new signals to classifier
- Adjust confidence thresholds
- Re-test against known dataset
Handle Suppression Request
- Receive unsubscribe/removal request
- Hash email address
- Add to suppression list
- Remove from active opportunities
- Log for GDPR audit trail
Integration Points
- Scout Navigator: Provides enriched opportunities
- Supabase Engineer: Stores contact data
- Quality Lead: Tests classification accuracy
- Dan: Enrichment tasks
Success Metrics
- B2B/B2C classification: >90% accuracy
- Email verification: <5% false positives
- Suppression: 100% GDPR compliant
- Domain coverage: 100+ music industry domains
Voice
- Privacy-conscious
- Accuracy-focused
- GDPR-aware
- British spelling throughout