Building Powerful Applications with Zapserp: Real-World Use Cases
The power of web search and content extraction APIs extends far beyond simple data collection. When integrated thoughtfully into applications, Zapserp enables developers to build sophisticated solutions that solve real business problems across multiple industries.
In this comprehensive guide, we'll explore real-world applications, provide implementation examples, and share insights from successful integrations.
Market Research and Intelligence Platforms
Use Case: Competitive Analysis Dashboard
Companies need to monitor competitors, track market trends, and stay informed about industry developments. Zapserp enables building comprehensive intelligence platforms.
import { Zapserp, SearchEngine, SearchResponse, Page } from 'zapserp'
class CompetitiveIntelligence {
private zapserp: Zapserp
constructor(apiKey: string) {
this.zapserp = new Zapserp({ apiKey })
}
async trackCompetitorMentions(competitors: string[], timeframe: 'day' | 'week' | 'month' = 'week') {
const results = []
for (const competitor of competitors) {
// Search for recent mentions
const searchQuery = `"${competitor}" ${this.getTimeframeQuery(timeframe)}`
const searchResults: SearchResponse = await this.zapserp.search({
query: searchQuery,
engines: [SearchEngine.GOOGLE, SearchEngine.BING],
limit: 20,
language: 'en',
country: 'us'
})
// Extract content from top results for sentiment analysis
const topUrls = searchResults.results.slice(0, 5).map(result => result.url)
const contentData = await this.zapserp.readerBatch({ urls: topUrls })
// Process and analyze content
const analysis = await this.analyzeContent(contentData.results, competitor)
results.push({
competitor,
mentionCount: searchResults.results.length,
topSources: searchResults.results.slice(0, 5),
contentAnalysis: analysis,
timestamp: new Date().toISOString()
})
}
return results
}
private getTimeframeQuery(timeframe: string): string {
const timeframes = {
day: 'past 24 hours',
week: 'past week',
month: 'past month'
}
return timeframes[timeframe] || timeframes.week
}
private async analyzeContent(pages: Page[], competitor: string) {
const analysis = {
totalContentLength: 0,
keywordDensity: 0,
sentimentScore: 0,
topKeywords: [] as string[]
}
let totalMentions = 0
let totalWords = 0
for (const page of pages) {
if (page.content) {
const content = page.content.toLowerCase()
const words = content.split(/\s+/)
// Count competitor mentions
const mentions = content.split(competitor.toLowerCase()).length - 1
totalMentions += mentions
totalWords += words.length
analysis.totalContentLength += page.contentLength
// Extract metadata insights
if (page.metadata) {
console.log(`Page: ${page.title}`)
console.log(`Author: ${page.metadata.author || 'Unknown'}`)
console.log(`Published: ${page.metadata.publishedTime || 'Unknown'}`)
}
}
}
analysis.keywordDensity = totalWords > 0 ? (totalMentions / totalWords) * 100 : 0
return analysis
}
async generateMarketReport(industry: string, keywords: string[]) {
const report = {
industry,
generatedAt: new Date().toISOString(),
trends: [] as any[],
keyPlayers: [] as any[],
opportunities: [] as any[]
}
// Analyze industry trends
for (const keyword of keywords) {
const trendQuery = `${industry} ${keyword} trends 2024`
const trendResults = await this.zapserp.search({
query: trendQuery,
engines: [SearchEngine.GOOGLE],
limit: 10
})
// Extract content from trend articles
const trendUrls = trendResults.results.slice(0, 3).map(r => r.url)
const trendContent = await this.zapserp.readerBatch({ urls: trendUrls })
report.trends.push({
keyword,
searchVolume: trendResults.results.length,
topSources: trendResults.results.slice(0, 3),
insights: this.extractTrendInsights(trendContent.results)
})
}
return report
}
private extractTrendInsights(pages: Page[]) {
// Simple keyword extraction for trends
const insights = []
for (const page of pages) {
if (page.content && page.content.length > 500) {
insights.push({
title: page.title,
summary: page.content.substring(0, 200) + '...',
contentLength: page.contentLength,
metadata: page.metadata
})
}
}
return insights
}
}
// Usage Example
const intelligence = new CompetitiveIntelligence('YOUR_API_KEY')
// Track competitor mentions
const competitors = ['OpenAI', 'Anthropic', 'Google AI']
const competitorAnalysis = await intelligence.trackCompetitorMentions(competitors, 'week')
console.log('Competitive Analysis Results:')
competitorAnalysis.forEach(result => {
console.log(`${result.competitor}: ${result.mentionCount} mentions`)
console.log(`Top source: ${result.topSources[0]?.title}`)
})
// Generate industry report
const aiReport = await intelligence.generateMarketReport('artificial intelligence', [
'machine learning',
'neural networks',
'automation',
'AI ethics'
])
console.log('AI Industry Report:', aiReport)
Content Aggregation and News Platforms
Use Case: Automated News Aggregator
Building a platform that automatically discovers, extracts, and curates news content from multiple sources.
interface NewsArticle {
title: string
content: string
url: string
source: string
publishedAt?: string
author?: string
category: string
summary: string
}
class NewsAggregator {
private zapserp: Zapserp
private categories: Record<string, string[]>
constructor(apiKey: string) {
this.zapserp = new Zapserp({ apiKey })
this.categories = {
technology: ['AI', 'blockchain', 'cybersecurity', 'startups'],
business: ['economy', 'finance', 'markets', 'enterprise'],
science: ['climate', 'space', 'medicine', 'research'],
politics: ['elections', 'policy', 'government', 'international']
}
}
async aggregateNews(category: string, hours: number = 24): Promise<NewsArticle[]> {
if (!this.categories[category]) {
throw new Error(`Category ${category} not supported`)
}
const articles: NewsArticle[] = []
const keywords = this.categories[category]
for (const keyword of keywords) {
const searchQuery = `${keyword} news latest ${hours} hours`
try {
// Search for recent news
const searchResults = await this.zapserp.search({
query: searchQuery,
engines: [SearchEngine.GOOGLE, SearchEngine.BING],
limit: 15,
language: 'en',
country: 'us'
})
// Filter for news sources
const newsUrls = this.filterNewsUrls(searchResults.results.map(r => r.url))
if (newsUrls.length > 0) {
// Extract article content
const contentResults = await this.zapserp.readerBatch({
urls: newsUrls.slice(0, 5) // Limit to top 5 per keyword
})
// Process articles
for (let i = 0; i < contentResults.results.length; i++) {
const content = contentResults.results[i]
const searchResult = searchResults.results[i]
if (content && content.content.length > 300) { // Minimum content length
const article: NewsArticle = {
title: content.title,
content: content.content,
url: content.url,
source: this.extractDomain(content.url),
publishedAt: content.metadata?.publishedTime,
author: content.metadata?.author,
category,
summary: this.generateSummary(content.content)
}
articles.push(article)
}
}
}
} catch (error) {
console.error(`Error aggregating news for keyword ${keyword}:`, error)
}
}
// Remove duplicates and sort by relevance
const uniqueArticles = this.removeDuplicates(articles)
return this.rankArticles(uniqueArticles)
}
private filterNewsUrls(urls: string[]): string[] {
const newsdomains = [
'reuters.com', 'bbc.com', 'cnn.com', 'techcrunch.com',
'bloomberg.com', 'wsj.com', 'nytimes.com', 'theguardian.com',
'wired.com', 'arstechnica.com', 'venturebeat.com'
]
return urls.filter(url =>
newsdomains.some(domain => url.includes(domain))
)
}
private extractDomain(url: string): string {
try {
return new URL(url).hostname.replace('www.', '')
} catch {
return 'unknown'
}
}
private generateSummary(content: string): string {
// Simple summary generation - first meaningful paragraph
const paragraphs = content.split('\n').filter(p => p.trim().length > 50)
return paragraphs[0]?.substring(0, 250) + '...' || content.substring(0, 250) + '...'
}
private removeDuplicates(articles: NewsArticle[]): NewsArticle[] {
const seen = new Set<string>()
return articles.filter(article => {
const key = `${article.title}-${article.source}`
if (seen.has(key)) return false
seen.add(key)
return true
})
}
private rankArticles(articles: NewsArticle[]): NewsArticle[] {
// Simple ranking by content length and source reliability
const sourceRanking: Record<string, number> = {
'reuters.com': 10,
'bbc.com': 9,
'bloomberg.com': 9,
'wsj.com': 8,
'techcrunch.com': 7,
'wired.com': 6
}
return articles
.map(article => ({
...article,
score: (sourceRanking[article.source] || 1) + (article.content.length / 1000)
}))
.sort((a, b) => b.score - a.score)
.slice(0, 20) // Top 20 articles
}
async generateNewsletterDigest(categories: string[]): Promise<any> {
const digest = {
generatedAt: new Date().toISOString(),
categories: {} as Record<string, NewsArticle[]>
}
for (const category of categories) {
digest.categories[category] = await this.aggregateNews(category, 24)
}
return digest
}
}
// Usage Example
const newsAggregator = new NewsAggregator('YOUR_API_KEY')
// Get latest technology news
const techNews = await newsAggregator.aggregateNews('technology')
console.log(`Found ${techNews.length} technology articles`)
// Generate daily newsletter
const newsletter = await newsAggregator.generateNewsletterDigest([
'technology', 'business', 'science'
])
console.log('Daily Newsletter Generated:', newsletter)
E-commerce and Price Monitoring
Use Case: Product Price and Review Tracker
Monitor product prices, availability, and reviews across multiple e-commerce platforms.
interface ProductData {
name: string
price?: string
availability: string
rating?: number
reviewCount?: number
url: string
source: string
lastChecked: string
}
class EcommerceMonitor {
private zapserp: Zapserp
constructor(apiKey: string) {
this.zapserp = new Zapserp({ apiKey })
}
async trackProduct(productName: string, sites: string[] = []): Promise<ProductData[]> {
const results: ProductData[] = []
// If no specific sites provided, search broadly
const searchQuery = sites.length > 0
? `${productName} site:${sites.join(' OR site:')}`
: `${productName} buy price`
const searchResults = await this.zapserp.search({
query: searchQuery,
engines: [SearchEngine.GOOGLE],
limit: 20
})
// Filter for e-commerce URLs
const ecommerceUrls = this.filterEcommerceUrls(searchResults.results.map(r => r.url))
if (ecommerceUrls.length > 0) {
const contentResults = await this.zapserp.readerBatch({
urls: ecommerceUrls.slice(0, 10)
})
for (const content of contentResults.results) {
const productData = this.extractProductData(content, productName)
if (productData) {
results.push(productData)
}
}
}
return results
}
private filterEcommerceUrls(urls: string[]): string[] {
const ecommerceDomains = [
'amazon.com', 'ebay.com', 'walmart.com', 'target.com',
'bestbuy.com', 'newegg.com', 'shopify.com'
]
return urls.filter(url =>
ecommerceDomains.some(domain => url.includes(domain))
)
}
private extractProductData(page: Page, productName: string): ProductData | null {
if (!page.content || !page.title) return null
const content = page.content.toLowerCase()
const title = page.title.toLowerCase()
// Basic product matching
if (!title.includes(productName.toLowerCase().split(' ')[0])) {
return null
}
return {
name: page.title,
price: this.extractPrice(page.content),
availability: this.extractAvailability(page.content),
rating: this.extractRating(page.content),
reviewCount: this.extractReviewCount(page.content),
url: page.url,
source: this.extractDomain(page.url),
lastChecked: new Date().toISOString()
}
}
private extractPrice(content: string): string | undefined {
// Simple price extraction patterns
const pricePatterns = [
/\$[\d,]+\.?\d*/g,
/USD [\d,]+\.?\d*/g,
/Price: \$[\d,]+\.?\d*/g
]
for (const pattern of pricePatterns) {
const matches = content.match(pattern)
if (matches && matches.length > 0) {
return matches[0]
}
}
return undefined
}
private extractAvailability(content: string): string {
const availabilityKeywords = {
'in stock': 'In Stock',
'available': 'Available',
'out of stock': 'Out of Stock',
'sold out': 'Sold Out',
'backorder': 'Backorder'
}
const lowerContent = content.toLowerCase()
for (const [keyword, status] of Object.entries(availabilityKeywords)) {
if (lowerContent.includes(keyword)) {
return status
}
}
return 'Unknown'
}
private extractRating(content: string): number | undefined {
const ratingPatterns = [
/(\d\.?\d?) out of 5 stars/i,
/rating: (\d\.?\d?)/i,
/(\d\.?\d?)\/5/i
]
for (const pattern of ratingPatterns) {
const match = content.match(pattern)
if (match && match[1]) {
return parseFloat(match[1])
}
}
return undefined
}
private extractReviewCount(content: string): number | undefined {
const reviewPatterns = [
/(\d+) reviews?/i,
/(\d+) customer reviews?/i,
/based on (\d+) reviews?/i
]
for (const pattern of reviewPatterns) {
const match = content.match(pattern)
if (match && match[1]) {
return parseInt(match[1])
}
}
return undefined
}
private extractDomain(url: string): string {
try {
return new URL(url).hostname.replace('www.', '')
} catch {
return 'unknown'
}
}
async compareProducts(products: string[]): Promise<Record<string, ProductData[]>> {
const comparison: Record<string, ProductData[]> = {}
for (const product of products) {
comparison[product] = await this.trackProduct(product)
}
return comparison
}
async generatePriceAlert(productName: string, targetPrice: number): Promise<any> {
const productData = await this.trackProduct(productName)
const alerts = []
for (const product of productData) {
if (product.price) {
const price = parseFloat(product.price.replace(/[^0-9.]/g, ''))
if (price <= targetPrice) {
alerts.push({
product: product.name,
currentPrice: product.price,
targetPrice: `$${targetPrice}`,
savings: `$${(targetPrice - price).toFixed(2)}`,
url: product.url,
source: product.source
})
}
}
}
return {
productName,
targetPrice: `$${targetPrice}`,
alertsFound: alerts.length,
alerts
}
}
}
// Usage Example
const monitor = new EcommerceMonitor('YOUR_API_KEY')
// Track a specific product
const laptopData = await monitor.trackProduct('MacBook Pro M3', ['amazon.com', 'bestbuy.com'])
console.log('Laptop tracking results:', laptopData)
// Compare multiple products
const smartphoneComparison = await monitor.compareProducts([
'iPhone 15 Pro',
'Samsung Galaxy S24',
'Google Pixel 8'
])
console.log('Smartphone comparison:', smartphoneComparison)
// Set up price alert
const priceAlert = await monitor.generatePriceAlert('iPad Air', 500)
console.log('Price alerts:', priceAlert)
Lead Generation and Sales Intelligence
Use Case: Automated Lead Discovery
Find potential customers and gather contact information based on specific criteria.
interface Lead {
companyName: string
website: string
industry: string
description: string
contactInfo?: {
email?: string
phone?: string
linkedin?: string
}
keyPersonnel?: Array<{
name: string
title: string
linkedin?: string
}>
technology?: string[]
size?: string
location?: string
}
class LeadGenerator {
private zapserp: Zapserp
constructor(apiKey: string) {
this.zapserp = new Zapserp({ apiKey })
}
async findLeads(criteria: {
industry: string
location?: string
technology?: string[]
size?: string
}): Promise<Lead[]> {
const leads: Lead[] = []
// Build search query
let searchQuery = `${criteria.industry} companies`
if (criteria.location) {
searchQuery += ` ${criteria.location}`
}
if (criteria.technology) {
searchQuery += ` ${criteria.technology.join(' OR ')}`
}
const searchResults = await this.zapserp.search({
query: searchQuery,
engines: [SearchEngine.GOOGLE, SearchEngine.BING],
limit: 30
})
// Filter for company websites
const companyUrls = this.filterCompanyUrls(searchResults.results.map(r => r.url))
if (companyUrls.length > 0) {
const contentResults = await this.zapserp.readerBatch({
urls: companyUrls.slice(0, 15)
})
for (const content of contentResults.results) {
const lead = this.extractLeadData(content, criteria)
if (lead && this.qualifyLead(lead, criteria)) {
leads.push(lead)
}
}
}
return leads
}
private filterCompanyUrls(urls: string[]): string[] {
// Filter out job boards, directories, and focus on company websites
const excludeDomains = [
'linkedin.com', 'indeed.com', 'glassdoor.com',
'crunchbase.com', 'wikipedia.org'
]
return urls.filter(url =>
!excludeDomains.some(domain => url.includes(domain)) &&
!url.includes('/jobs') &&
!url.includes('/careers')
)
}
private extractLeadData(page: Page, criteria: any): Lead | null {
if (!page.content || !page.title) return null
const content = page.content
const domain = this.extractDomain(page.url)
return {
companyName: this.extractCompanyName(page.title, content),
website: page.url,
industry: criteria.industry,
description: this.extractDescription(content),
contactInfo: this.extractContactInfo(content),
keyPersonnel: this.extractKeyPersonnel(content),
technology: this.extractTechnology(content),
size: this.extractCompanySize(content),
location: this.extractLocation(content)
}
}
private extractCompanyName(title: string, content: string): string {
// Extract company name from title or content
const titleParts = title.split('|')[0].split('-')[0].trim()
return titleParts || 'Unknown Company'
}
private extractDescription(content: string): string {
// Look for about section or meta description
const aboutMatch = content.match(/about us[:\-]?\s*(.{100,300})/i)
if (aboutMatch) {
return aboutMatch[1].trim()
}
// Fallback to first paragraph
const paragraphs = content.split('\n').filter(p => p.trim().length > 50)
return paragraphs[0]?.substring(0, 200) + '...' || 'No description available'
}
private extractContactInfo(content: string): any {
const contact: any = {}
// Email extraction
const emailMatch = content.match(/[\w\.-]+@[\w\.-]+\.\w+/g)
if (emailMatch && emailMatch.length > 0) {
// Filter out generic emails
const validEmails = emailMatch.filter(email =>
!email.includes('noreply') &&
!email.includes('support') &&
!email.includes('info')
)
if (validEmails.length > 0) {
contact.email = validEmails[0]
}
}
// Phone extraction
const phoneMatch = content.match(/[\+]?[1-9]?[\-\.\s]?\(?[0-9]{3}\)?[\-\.\s]?[0-9]{3}[\-\.\s]?[0-9]{4}/g)
if (phoneMatch && phoneMatch.length > 0) {
contact.phone = phoneMatch[0]
}
// LinkedIn extraction
const linkedinMatch = content.match(/linkedin\.com\/company\/[\w\-]+/g)
if (linkedinMatch && linkedinMatch.length > 0) {
contact.linkedin = `https://${linkedinMatch[0]}`
}
return Object.keys(contact).length > 0 ? contact : undefined
}
private extractKeyPersonnel(content: string): any[] {
const personnel: any[] = []
// Look for CEO, CTO, founder mentions
const titlePatterns = [
/(?:CEO|Chief Executive Officer)[:\-\s]*([A-Za-z\s]+)/gi,
/(?:CTO|Chief Technology Officer)[:\-\s]*([A-Za-z\s]+)/gi,
/(?:Founder|Co-founder)[:\-\s]*([A-Za-z\s]+)/gi
]
titlePatterns.forEach(pattern => {
const matches = content.matchAll(pattern)
for (const match of matches) {
if (match[1] && match[1].trim().length > 2) {
personnel.push({
name: match[1].trim(),
title: match[0].split(/[:\-\s]/)[0],
linkedin: undefined
})
}
}
})
return personnel.slice(0, 3) // Limit to 3 key personnel
}
private extractTechnology(content: string): string[] {
const technologies = [
'React', 'Angular', 'Vue', 'Node.js', 'Python', 'Java',
'AWS', 'Azure', 'Docker', 'Kubernetes', 'MongoDB', 'PostgreSQL'
]
const foundTech = technologies.filter(tech =>
content.toLowerCase().includes(tech.toLowerCase())
)
return foundTech.slice(0, 5) // Limit to 5 technologies
}
private extractCompanySize(content: string): string | undefined {
const sizePatterns = [
/(\d+[\-\+]?)\s*employees/i,
/team of (\d+)/i,
/(\d+)\s*person team/i
]
for (const pattern of sizePatterns) {
const match = content.match(pattern)
if (match && match[1]) {
const size = parseInt(match[1])
if (size < 10) return 'Startup (1-10)'
if (size < 50) return 'Small (11-50)'
if (size < 200) return 'Medium (51-200)'
if (size < 1000) return 'Large (201-1000)'
return 'Enterprise (1000+)'
}
}
return undefined
}
private extractLocation(content: string): string | undefined {
// Simple location extraction - could be enhanced with geo-NLP
const locationPatterns = [
/(?:based in|located in|headquarters in)\s*([A-Za-z\s,]+)/i,
/([A-Za-z\s]+),\s*(?:CA|NY|TX|FL|WA|CO|MA)/i
]
for (const pattern of locationPatterns) {
const match = content.match(pattern)
if (match && match[1]) {
return match[1].trim()
}
}
return undefined
}
private qualifyLead(lead: Lead, criteria: any): boolean {
// Basic lead qualification
if (!lead.companyName || lead.companyName === 'Unknown Company') {
return false
}
if (criteria.technology && criteria.technology.length > 0) {
const hasRequiredTech = criteria.technology.some((tech: string) =>
lead.technology?.includes(tech) ||
lead.description.toLowerCase().includes(tech.toLowerCase())
)
if (!hasRequiredTech) return false
}
return true
}
private extractDomain(url: string): string {
try {
return new URL(url).hostname.replace('www.', '')
} catch {
return 'unknown'
}
}
async enrichLead(lead: Lead): Promise<Lead> {
// Enrich lead with additional company information
const enrichQuery = `"${lead.companyName}" company profile funding`
try {
const enrichResults = await this.zapserp.search({
query: enrichQuery,
engines: [SearchEngine.GOOGLE],
limit: 5
})
// Process additional information from search results
// This could include funding info, recent news, etc.
return {
...lead,
// Additional enriched data would go here
}
} catch (error) {
console.error('Error enriching lead:', error)
return lead
}
}
}
// Usage Example
const leadGen = new LeadGenerator('YOUR_API_KEY')
// Find SaaS companies using React
const saasLeads = await leadGen.findLeads({
industry: 'SaaS',
location: 'San Francisco',
technology: ['React', 'Node.js'],
size: 'Small'
})
console.log(`Found ${saasLeads.length} SaaS leads`)
// Enrich the first lead with additional data
if (saasLeads.length > 0) {
const enrichedLead = await leadGen.enrichLead(saasLeads[0])
console.log('Enriched lead:', enrichedLead)
}
Key Success Factors
When building applications with Zapserp, consider these critical factors:
1. Data Quality & Validation
Always validate and clean extracted data before processing or storing it.
2. Rate Limiting & Efficiency
Implement proper batching and caching to optimize API usage and costs.
3. Error Handling
Build robust error handling for network issues, parsing failures, and API limits.
4. User Experience
Design intuitive interfaces that make complex data accessible and actionable.
5. Scalability
Plan for growth with efficient data processing and storage architectures.
Getting Started
Ready to build your own application? Here are some recommended starting points:
- Start Small: Begin with a simple use case and gradually add complexity
- Prototype Quickly: Use Zapserp's flexibility to rapidly test ideas
- Focus on Value: Identify the specific problem you're solving for users
- Iterate Based on Feedback: Use real user data to guide development priorities
The possibilities with Zapserp are vast. Whether you're building market research tools, content platforms, e-commerce solutions, or sales intelligence systems, the key is to start with a clear problem and iterate toward a solution that delivers real value.
Need help with your specific use case? Contact our team for implementation guidance and best practices tailored to your industry.