Competitor Documentation¶
Overview¶
The Competitor module (competitor) manages competitor information for competitive analysis in sales opportunities. This master data model enables sales teams to track which competitors are involved in deals, analyze win/loss patterns against specific competitors, and develop competitive strategies based on historical data.
Model Information¶
Model Name: competitor
Display Name: Competitor
Key Fields: None (no unique constraints)
Features¶
- Simple competitor master data
- Contact integration for competitor details
- Opportunity linkage via opport.compet
- Comment tracking
Common Competitor Categories¶
| Competitor Type | Example | Description |
|---|---|---|
| Direct Competitors | Same product/service providers | Companies offering identical solutions |
| Indirect Competitors | Alternative solution providers | Companies solving same problem differently |
| Emerging Competitors | Startups and new entrants | New market players |
| Industry Giants | Established market leaders | Large, well-known competitors |
Field Reference¶
Basic Fields¶
| Field | Type | Required | Description |
|---|---|---|---|
name |
Char | Yes | Competitor name (e.g., "Acme Corporation") |
Relationship Fields¶
| Field | Type | Description |
|---|---|---|
contact_id |
Many2One | Link to contact record for competitor details (address, phone, etc.) |
opports |
One2Many | List of opportunities where this competitor is involved |
comments |
One2Many | Comments and notes about this competitor |
API Methods¶
1. Create Competitor¶
Method: create(vals, context)
Example:
# Create a competitor with contact details
competitor_id = get_model("competitor").create({
"name": "Acme Corporation",
"contact_id": contact_id # Optional: link to contact for details
})
2. Search Competitors¶
# Find competitor by name
comp_ids = get_model("competitor").search([["name", "=", "Acme Corporation"]])
# Find competitors in opportunities
comp_ids = get_model("competitor").search([["opports", "!=", None]])
Related Models¶
| Model | Relationship | Description |
|---|---|---|
opport.compet |
One2Many | Links competitors to specific opportunities |
contact |
Many2One | Stores competitor contact details |
message |
One2Many | Comments about competitors |
Common Use Cases¶
Use Case 1: Initial Competitor Setup¶
# Create standard competitors in your industry
competitors = [
{"name": "Acme Corporation"},
{"name": "GlobalTech Solutions"},
{"name": "Industry Leader Inc"},
{"name": "Startup Disruptor"},
{"name": "Regional Player Co"}
]
for comp in competitors:
get_model("competitor").create(comp)
Use Case 2: Track Competitors in Opportunity¶
# Add competitors to an opportunity
def add_competitor_to_opportunity(opport_id, competitor_name):
# Find or create competitor
comp_ids = get_model("competitor").search([["name", "=", competitor_name]])
if not comp_ids:
comp_id = get_model("competitor").create({"name": competitor_name})
else:
comp_id = comp_ids[0]
# Link to opportunity via opport.compet
get_model("opport.compet").create({
"opport_id": opport_id,
"compet_id": comp_id
})
# Usage
add_competitor_to_opportunity(opportunity_id, "Acme Corporation")
Use Case 3: Win/Loss Analysis by Competitor¶
# Analyze performance against specific competitors
def analyze_competitor_win_loss(competitor_name):
# Find competitor
comp_ids = get_model("competitor").search([["name", "=", competitor_name]])
if not comp_ids:
return None
comp_id = comp_ids[0]
# Find all opportunities where this competitor was involved
opport_comp_ids = get_model("opport.compet").search([
["compet_id", "=", comp_id]
])
opport_comps = get_model("opport.compet").browse(opport_comp_ids)
# Analyze outcomes
total = 0
won = 0
lost = 0
for oc in opport_comps:
opport = oc.opport_id
total += 1
if opport.state == "won":
won += 1
elif opport.state == "lost":
lost += 1
win_rate = (won / total * 100) if total > 0 else 0
return {
"competitor": competitor_name,
"total_opportunities": total,
"won": won,
"lost": lost,
"win_rate": win_rate
}
# Example
analysis = analyze_competitor_win_loss("Acme Corporation")
print(f"Win rate against {analysis['competitor']}: {analysis['win_rate']:.1f}%")
Use Case 4: Competitive Intelligence Database¶
# Store competitive intelligence in comments
def add_competitive_note(competitor_name, note):
# Find competitor
comp_ids = get_model("competitor").search([["name", "=", competitor_name]])
if not comp_ids:
comp_id = get_model("competitor").create({"name": competitor_name})
else:
comp_id = comp_ids[0]
# Add comment
get_model("message").create({
"related_id": f"competitor,{comp_id}",
"body": note,
"type": "comment"
})
# Usage
add_competitive_note("Acme Corporation",
"New pricing model announced: 20% lower than ours for enterprise tier")
add_competitive_note("Acme Corporation",
"Weakness: Poor customer support noted in recent reviews")
Use Case 5: Competitor Frequency Report¶
# Find most frequently encountered competitors
def get_top_competitors(date_from, date_to, limit=10):
results = []
# Get all competitors
comp_ids = get_model("competitor").search([])
competitors = get_model("competitor").browse(comp_ids)
for comp in competitors:
# Count opportunities in date range
opport_comp_ids = get_model("opport.compet").search([
["compet_id", "=", comp.id]
])
# Filter by date
count = 0
for oc_id in opport_comp_ids:
oc = get_model("opport.compet").browse(oc_id)
opport = oc.opport_id
if opport.date and opport.date >= date_from and opport.date <= date_to:
count += 1
if count > 0:
results.append({
"competitor": comp.name,
"encounters": count
})
# Sort by frequency
results.sort(key=lambda x: x["encounters"], reverse=True)
return results[:limit]
# Get top 5 competitors this quarter
top_comps = get_top_competitors("2026-01-01", "2026-03-31", limit=5)
for i, comp in enumerate(top_comps, 1):
print(f"{i}. {comp['competitor']}: {comp['encounters']} opportunities")
Best Practices¶
1. Naming Conventions¶
# Good: Official company names
{"name": "Acme Corporation"}
{"name": "GlobalTech Solutions Inc"}
{"name": "Industry Leader Ltd"}
# Bad: Informal or inconsistent names
{"name": "acme"} # Inconsistent casing
{"name": "That big competitor"} # Not specific
{"name": "Comp 1"} # Generic
Guidelines: - Use official company names - Be consistent with capitalization - Include legal entity type if needed (Inc, Ltd, Corp)
2. Contact Integration¶
# Good: Link competitor to contact for full details
contact_id = get_model("contact").create({
"name": "Acme Corporation",
"type": "org",
"phone": "+1-555-0100",
"email": "info@acme.com",
"website": "www.acme.com",
"address": "123 Main St, City, State 12345"
})
competitor_id = get_model("competitor").create({
"name": "Acme Corporation",
"contact_id": contact_id
})
# Now you have full competitor details available
3. Competitive Intelligence Management¶
Track strengths and weaknesses:
# Use comments to build competitive intelligence
intelligence_categories = [
"Pricing Strategy",
"Product Features",
"Customer Service",
"Market Position",
"Weaknesses",
"Recent News"
]
# Store structured intelligence
def log_competitive_intel(competitor_name, category, details):
add_competitive_note(competitor_name,
f"[{category}] {details}")
4. Regular Review¶
Quarterly competitor review: - Update competitor list - Remove inactive competitors - Review win/loss patterns - Update competitive intelligence - Brief sales team on changes
Performance Tips¶
1. Cache Competitor Lookups¶
_competitor_cache = {}
def get_competitor_by_name(name):
if name not in _competitor_cache:
ids = get_model("competitor").search([["name", "=", name]])
if ids:
_competitor_cache[name] = ids[0]
return _competitor_cache.get(name)
2. Limit Active Competitors¶
- Focus on top 10-15 most frequently encountered competitors
- Archive historical competitors not seen in last 12 months
- Keep list manageable for sales team
Troubleshooting¶
"Duplicate competitors with similar names"¶
Cause: Inconsistent naming (e.g., "Acme Corp" vs "Acme Corporation") Solution:
# Standardize competitor names
def standardize_competitor_name(name):
# Common standardizations
standardizations = {
" Corp": " Corporation",
" Inc": " Incorporated",
" Ltd": " Limited"
}
for old, new in standardizations.items():
name = name.replace(old, new)
return name.title()
"Competitors not showing in reports"¶
Cause: Competitors exist but not linked to opportunities Solution:
# Find unlinked competitors
all_comp_ids = get_model("competitor").search([])
for comp_id in all_comp_ids:
opport_links = get_model("opport.compet").search([
["compet_id", "=", comp_id]
])
if not opport_links:
comp = get_model("competitor").browse(comp_id)
print(f"Competitor '{comp.name}' has no linked opportunities")
Security Considerations¶
Permission Model¶
- All sales users need read access
- Sales managers can create/edit competitors
- Competitive intelligence should be internal only
Data Access¶
- Competitors are company-wide master data
- Competitive intelligence is confidential
- Restrict external access
Integration Points¶
Internal Modules¶
- opport.compet: Links competitors to opportunities
- sale.opportunity: Opportunities track competing against which companies
- contact: Stores detailed competitor information
- message: Comments for competitive intelligence
Competitive Analysis¶
# Used in:
# - Win/Loss Analysis
# - Competitive Positioning
# - Battle Card Development
# - Sales Training
# - Market Intelligence
Version History¶
Last Updated: 2026-01-05 Model Version: competitor.py Framework: Netforce
Additional Resources¶
- Opportunity Competitor Link:
opport.compet - Sales Opportunity:
sale.opportunity - Win/Loss Analysis Guide
- Competitive Intelligence Best Practices
This documentation is generated for developer onboarding and reference purposes.