Crunchbase 域名查公司 API:先消歧多个匹配,再补全 CRM

发布于 2026年10月19日

“官网一样,就是同一家公司。”把这条规则写进 CRM 导入脚本,stripe.com 就会让它失效:保存的域名查询样本有四个组织。直接取 items[0],程序虽然能继续跑,却没有解释为什么这条记录属于当前客户,更没有阻止下次把另一个组织覆盖进来。

这篇指南处理的是域名到企业身份的交接,不是给每个候选都补一遍资料。先留下可复核的选择,再允许企业信息补全。

stripe.com 返回四个组织,不能默认选择第一条

company-by-domain 的必填参数是 domain。平台安全示例使用 stripe.com,该次响应的 domain 为 stripe.com、total_count 为 4,items 中的公司 ID 是:

  • stripe:有可供核对的主体身份信息,进入确认环节。
  • stripe-capital:保留为另一个候选,不自动挂到当前账户。
  • stripe-841c:不能仅凭 ID 相似就认定是重复记录。
  • stripe-atlas:也不能只凭名称就认定与客户是同一主体。

这些是一次观测,不是固定名单或排序保证。多个组织可以匹配同一网站;查询结果本身没有证明它们的法律关系,也没有授权你合并。这个接口未提供分页或数量限制参数,不要凭空添加。

官网域名、公司 ID 与 UUID 要分开保存

官网域名是输入线索;id 是选中的组织标识;uuid 是另一个身份字段。三者分列,CRM 自己的账户主键也继续保留。详情请求使用已确认的公司 ID,不要把 stripe.com 填进 company,也不要用显示名替代。

建议本地映射记录至少保存输入域名、全部候选 ID、选定 ID、可用 UUID、审核状态、审核依据与获取时间。它们是应用自建字段,不是 API 返回契约。以后候选集变化时,先重新审核,而不是覆盖已确认映射;同一域名下的不同组织可以分别关联不同账户。

核对官网、创始人与业务描述后再确认主体

主记录的观测信息包括 id=stripe、name=Stripe、website=https://stripe.com,以及创始人 John Collison、Patrick Collison。审核人还要阅读业务描述,与 CRM 客户的业务范围核对。官网相同只是证据之一,创始人重合也不能单独证明两个组织可以合并。

如果当前账户确实对应这条 Stripe 记录,可以确认 stripe;另外三个 ID 仍留在候选历史中,不应成为同一个账户的别名。无法解释差异时就暂停,向业务同事补充主体资料,而不是让排序充当决策。

若还需要同类应用的 API,可通过联系页面提出需求,也可了解源码私有化部署。

确认公司 ID 后再调用 /companies/details 补全 CRM

目录中的 /companies/details 对应平台操作 company-details,不是让你直接拼目录路径。控制台取得的授权密钥只放服务端环境变量;请求形式为 https://api.opendata-api.com/api/project/crunchbase/company-by-domain?key=YOUR_API_KEY&domain=stripe.com。不要把带密钥的完整 URL 写入日志或前端。打开文章、导航和复制示例均不会发送数据请求。

下面先建立待审记录,再提供受保护的详情函数。审核界面必须从候选中填入 selected_company_id、对应的可用 uuid 和 reviewer_context,完成核对后才把 status 改为 confirmed。代码不自动批准,也不直接写 CRM。

import os
from datetime import datetime, timezone

import requests

BASE = "https://api.opendata-api.com/api/project/crunchbase"
KEY = os.environ["OPENDATA_API_KEY"]


def api(operation, **params):
    response = requests.get(
        f"{BASE}/{operation}",
        params={"key": KEY, **params},
        timeout=30,
    )
    if not response.ok:
        raise RuntimeError(f"HTTP failure: {response.status_code}")
    envelope = response.json()
    if not isinstance(envelope, dict) or envelope.get("code") != 200:
        raise RuntimeError("Platform request failed")
    payload = envelope.get("data")
    if not isinstance(payload, dict) or "error" in payload:
        raise RuntimeError("Unexpected or failed data response")
    return payload


result = api("company-by-domain", domain="stripe.com")
mapping = {
    "input_domain": "stripe.com",
    "candidate_ids": [row["id"] for row in result["items"]],
    "selected_company_id": None,
    "uuid": None,
    "status": "needs_review",
    "reviewer_context": None,
    "retrieved_at": datetime.now(timezone.utc).isoformat(),
}


def fetch_confirmed(mapping):
    if mapping["status"] != "confirmed" or not mapping["reviewer_context"]:
        raise ValueError("Identity review required")
    company_id = mapping["selected_company_id"]
    if not company_id or company_id not in mapping["candidate_ids"]:
        raise ValueError("Selected ID is not a candidate")
    profile = api("company-details", company=company_id)
    if profile.get("id") != company_id:
        raise ValueError("Company ID changed")
    if mapping["uuid"] and profile.get("uuid") != mapping["uuid"]:
        raise ValueError("Company UUID changed")
    return profile

平台外层检查 code,业务载荷在 data;详情载荷本身是平铺公司对象,不是 items 或额外的 company 包装。HTTP 成功也不能跳过业务错误检查。通过身份复核后,才按需把官网、创始人、总部位置等资料写回对应账户;返回空值不应直接抹掉已核实的 CRM 字段。

多条匹配、搜索为空和详情 404 要分别处理

给应用定义不同结果,别都记成“查不到”:

  • 多条域名匹配:进入身份审核队列,不自动选择,不反复请求期待顺序改变。
  • 公司搜索为空:search-companies 的有效空结果观测为 HTTP 200、count=0、items=[]、total_pages=0,表示当前搜索条件没有匹配,不证明企业不存在。
  • 详情 404:已知不存在的公司 ID 返回 HTTP 404,表示该精确标识未找到。重新检查映射与标识,不要改抓另一条候选顶替。

尚无证据说明域名查询未命中时的确切结构,因此不能把搜索接口的空结果格式套给它。密钥、权限或请求故障也要另走错误分支,不能降级成“无此公司”。

需要从名字找候选时,公司搜索的 query 是名称前缀;按行业、地区、融资阶段筛选则使用文档支持的 category、location、funding_stage,还可用 investor 限定投资方。名称搜索实测一页 15 条、总数 82、共 6 页;使用 page 和实际页信息继续取,不能只收第一页。文档页码范围为 1—100,且部分排序仅返回一页,不要照搬其他服务的游标规则。

主体匹配成功,不代表融资金额与日期完整

company-funding-rounds 的 Stripe 样本报告 count=24、summary.rounds_count=24,实际只有 15 条。默认 announced 排序下该次只有一页;文档支持 rank 深分页,但没有由此验证完整历史。统计总数和已取行数要分开显示。

轮次有投资方,金额、估值、公告日期仍可能为 null:保留未知,别填零,也别从轮次名称猜日期。需要投资关系时,可查公司投资人、机构对外投资组合,或用 search-investments 的 company 与 lead_only=true 查询收款公司的领投关系;不能把收款公司与投资机构的方向混用。投资人搜索命中只表示候选发现,不证明机构目前仍在投资。

并购、IPO、新闻是独立研究记录:分别查看公司收购、上市搜索和公司新闻操作,并保留各自实体标识与来源,不把公司 ID 当成收购或 IPO ID。本文的平台项目也不等于 Crunchbase 官方 API,鉴权、字段和分页规则不能互套;搜索到“免费 API”不代表已有免费额度,实际可用额度与费用应查看当前定价和账户信息。

域名消歧只能让这次 CRM 关联更可解释,不能认证法律所有权、现任关系或投资活跃度,更不能补出缺失的融资数字。无法确认的主体保持待审,缺失的财务字段保持未知;这比一条看似完整、实际串错公司的客户档案更可靠。