你的业余项目刚刚突破 500 颗星,一个陌生人提交了第一个正经的拉取请求:2000 行代码,修复了一个你回避了好几个月的问题。你想直接点合并。但在动手之前,先问自己一个不太舒服的问题:你真的有法律权利发布这些代码吗——并且无论那个贡献者为哪家公司工作,都能永远以你的许可证持续发布吗?
如果你的仓库没有贡献政策,诚实的答案是:你不确定。贡献者仍然拥有他们写下的每一行代码的版权,而你项目的许可证本身并不总能厘清谁授予了谁什么。这种不确定性会一直隐形,直到某一天它突然变得重要:重新许可、收购、企业用户做许可证尽职调查,或者贡献者的雇主声称这些成果一直都是他们的。
有两种机制能解决这个问题,几乎每个开源项目都会选其中之一:贡献者许可协议(CLA)和开发者原创声明(DCO)。两者的存在都是为了确立贡献者有权做出贡献,以及项目有权分发它。它们在分量、摩擦和后续能做什么上差异巨大。本指南解释每种机制如何运作、何时该选哪个,以及如何在一个下午内把你的选择配置好。
为什么你的项目无论如何都需要一份贡献政策
版权是自动产生的。某个人写下代码的那一刻,他们就拥有了它——无需注册,无需版权声明。当他们把它提交给你的项目时,你的开源许可证覆盖了很多东西,但留下了只有贡献政策才能填补的缺口:
- 内向授权。 你的外向许可证(MIT、Apache-2.0、GPL)告诉用户他们可以对你的代码做什么。贡献政策明确表明,进来的贡献是在兼容条款下到达的,这样你就能分发合并后的作品,而不必手动追踪每个文件的来源。
- 雇主主张。 大多数雇佣合同会把业余项目的知识产权归属给雇主,至少对于与员工工作相关的成果是这样。一份要求贡献者确认自己有权提交的政策,把这份责任——以及书面记录——放在了贡献者身上。
- 重新许可的选择空间。 如果你将来想更换许可证、增加商业版本,或者把项目捐给某个基金会,你需要每一位贡献者的授权。事后从几十位过去的贡献者那里追讨许可,介于痛苦和不可能之间。第一天就选好的政策,决定了这扇门是否保持敞开。
- 专利保护。 代码贡献可能附带专利权。有些政策包含明确的专利授权;有些则不包含,这一点比大多数维护者意识到的更重要。
这些都不需要常驻律师事务所。它需要的是在 CLA 和 DCO 之间做出选择,写在你的仓库里,并自动执行。以下是每种选择的具体内容。
什么是贡献者许可协议(CLA)?
贡献者许可协议是贡献者与项目(或其背后的公司或基金会)之间签署的法律文件。贡献者签署一次,那次签名就覆盖他们未来所有的贡献。
与开源许可证不同,CLA 没有标准化。每个项目写自己的,但大多数都落入两种熟悉的形态:
个人 CLA 与企业 CLA
- 个人 CLA(ICLA): 由个人以自己名义贡献时签署。它通常授予项目广泛的版权许可,往往还包括专利许可,同时贡献者保留自己的版权。
- 企业 CLA(CCLA): 由公司签署,授权其员工贡献。公司为其人员提交的成果授予同样的权利。接受企业贡献却没有 CCLA 的项目,是在信任每位员工的经理都知情——并且批准了——而这恰恰是那种在尽职调查中会蒸发的信任。
许可授权 vs. 版权转让
大多数现代 CLA 是许可授权:贡献者保留所有权,授予项目一份永久、全球、免版税的许可——通常足够广泛,允许重新许可。Apache 软件基金会的 ICLA 就是典型例子。
少数项目采用版权转让,贡献者直接转让所有权(自由软件基金会的做法)。转让给予项目最大的执行和重新许可自由,但它对贡献者要求最多,在社区驱动的项目中已经失宠。
CLA 让你和贡献者付出什么代价
权衡之处在于摩擦。第一次贡献的人必须离开拉取请求,阅读一份法律文件,签署它(通常是电子方式),然后等待状态检查变绿,维护者才会审查他们的代码。工具已经让这件事几乎无痛——像 CLA Assistant 这样的机器人会在拉取请求下评论一个签署链接,并自动记录签名——但它仍然是"I 修好了你的 bug"和"你可以合并我的修复"之间的一道关卡。一些顺手的贡献者会因此打退堂鼓。
作为交换,项目得到了一份签名的、可审计的记录:这个人,在这个日期,授予了这些权利。对于企业支持的项目、双许可项目,以及任何可能有一天被收购的项目,这份书面记录值真金白银。
什么是开发者原创声明(DCO)?
开发者原创声明由 Linux 基金会于 2004 年为 Linux 内核引入,正是为了避免 CLA 的沉重负担。它不是贡献者签署并存档的合同。它是一份简短的证明——五段话,1.1 版本——贡献者通过每次提交时在提交信息中添加 Signed-off-by 行来确认:
Fix off-by-one error in retry backoff calculation
The retry delay doubled one extra time because the loop counter
started at 1 instead of 0.
Signed-off-by: Alex Rivera <[email protected]>添加这一行只需一个标志:git commit -s 会使用你配置的 Git 身份自动追加它。通过签署,贡献者证明:
- 他们创作了该贡献(全部或部分),并有权在项目的开源许可证下提交它,或者
- 他们的贡献基于已有的、处于允许此提交的适当开源许可证下的先前成果,或者
- 他们从其他人那里收到该贡献,而那人证明了上述之一,并且他们没有修改它,并且
- 他们理解该贡献及其记录——包括他们的签署——是公开的,并被无限期保留。
这就是全部机制。没有单独的文件,没有账户关联,没有针对每个项目的入门流程。执行方式是一个状态检查:DCO 应用或等效检查验证拉取请求中的每次提交是否带有有效的签署,维护者只在绿灯时合并。
DCO 有意为之的局限
注意 DCO 不做什么。它不授予超出项目外向许可证已传达范围之外的任何许可——它依赖贡献在项目的许可条款下到达。它不包含专利授权。而且由于没有按贡献者签署和存档任何东西,就没有谁同意了什么的中枢登记;git 历史本身就是记录。
支持者认为这是特性:DCO 的低门槛正是重点。Linux 内核、GitLab(2017 年从 CLA 切换)和 Chef(2016 年切换)都得出结论:每次提交的证明给了他们所需的来源可信度,而不用向每位贡献者征税。OpenStack 技术委员会在 2025 年决议用 DCO 取代其 CLA,适用于所有贡献。行业趋势毫无疑问——但趋势不是对你项目的判决,接下来几节会解释。
CLA vs. DCO 逐项对比
| 维度 | CLA | DCO |
|---|---|---|
| 法律机制 | 签署的协议,每位贡献者归档一次 | 提交信息中的每次提交证明 |
| 贡献者做什么 | 签署一份文件(通常通过机器人链接) | 用 git commit -s 添加 Signed-off-by |
| 版权处理 | 对项目的明确许可授权(或转让) | 贡献在项目许可证下到达;无单独授权 |
| 专利授权 | 通常包含 | 无 |
| 重新许可自由 | 广泛的授权通常允许 | 无额外权利;重新许可需要每位贡献者同意 |
| 贡献者摩擦 | 更高:阅读、签署、等待检查 | 极小:一个 Git 标志 |
| 执行工具 | CLA Assistant、EasyCLA、自定义机器人 | DCO 应用、提交信息检查 |
| 同意记录 | 签名数据库 | git 历史本身 |
| 雇主覆盖 | 企业 CLA 明确覆盖员工 | 贡献者自我证明有权提交 |
| 最佳匹配 | 企业支持、双许可或与收购相关的项目 | 贡献摩擦最要紧的社区项目 |
什么时候 CLA 是正确选择
当项目的未来可能依赖于 DCO 无法捕获的权利时,选择 CLA:
- 你计划双许可或重新许可。 如果商业版本、许可证变更,或从 copyleft 转向宽松许可哪怕有一丝可能性,一份带广泛回授的 CLA 是保持这个选项敞开唯一轻量做法。多年后重建同意是噩梦场景。
- 有公司站在项目背后。 企业赞助商、收购方,以及做知识产权尽职调查的企业客户想要签名登记册,而不是考古挖掘。Google、Apache 项目以及 Canonical 都出于这个原因使用 CLA。
- 专利在你的领域要紧。 编解码器、无线协议、ML 模型架构——在专利密集的领域,CLA 明确的专利授权在做实实在在的工作,而 DCO 默默跳过了。
- 某个基金会要求它。 一些基金会把他们的 CLA 作为托管或毕业的条件。在你假定 DCO 足够之前先确认。
如果你走这条路,让 CLA 本身保持标准而无聊:从 Apache ICLA 或 Harmony 模板开始,而不是从头起草,同时发布个人和企业版本,并在第一天就接好签署机器人,让摩擦只是一次点击,而不是一个 PDF 来回。
什么时候 DCO 胜出
当贡献是命脉而摩擦是敌人时,选择 DCO:
- 有许多随手贡献者的社区项目。 文档修复、错字纠正、小 bug 补丁——最可能在签署关卡前打退堂鼓的贡献,恰恰是 DCO 能优雅处理的那些。
- 宽松许可证,没有重新许可计划。 如果项目将永远保持 MIT 或 Apache-2.0,路线图上也没有商业版本,CLA 的额外权利对你帮助不大。
- 独立维护者和小团队。 DCO 不需要签名基础设施,不需要持有协议的法律实体,也不需要会签企业表格的流程。这是你可以从一个
CONTRIBUTING.md文件和一个状态检查运行起来的治理。 - 最大兼容姿态。 一些贡献者——尤其是那些受雇于知识产权政策严格的大公司的人——可以签署 DCO,但未经法律审查无法签署外部 CLA。DCO 让那扇门保持敞开。
无论你选哪个,把决定写下来。一份说明政策、展示确切的签署或签名流程,并链接完整文本的 CONTRIBUTING.md,能消除最常见的困惑来源:贡献者从失败的状态检查中猜测要求。
5 个会破坏任一选择的错误
1. 两个都要。 现实中最常见的失败是一份 CONTRIBUTING.md,在一段里要求 DCO 签署,在另一段里要求 CLA 签名——通常是在一次半途而废的迁移之后。贡献者遵循其中一条指令,另一个检查失败,维护者还是合并了,这让两者的意义都失效。选一种机制,执行它,删除另一种的每一丝痕迹。
2. 没有自动执行。 只在散文里陈述的政策是建议。把检查接入你的拉取请求工作流,作为必需的状态检查——签署用 DCO 应用,签名用 CLA Assistant 或 EasyCLA——这样未经同意的贡献就不会因意外或维护者疲劳而被合并。
3. 忽视企业贡献者。 如果公司使用并修补你的项目,员工会在工作时间提交代码。在 CLA 政策下,这意味着趁关系还热时尽早让 CCLA 签署。在 DCO 政策下,这意味着确保签署要求足够显眼,没有人的第一次贡献变成知识产权事件。
4. 假定雇佣合同允许贡献。 同一枚硬币的另一面:如果你向其他项目贡献,先检查你自己的雇佣协议。许多默认把与工作相关的业余项目知识产权归属给雇主。DCO 的证明("我有权提交这个")只有在那些文件如此说明时才成立。
5. 没有针对 AI 辅助代码的政策。 机器生成的贡献提出了 2004 年时代的 DCO 文本和大多数 CLA 模板都没有预见到的来源问题。决定你的立场——经审查允许、需要披露,还是禁止——并在 CONTRIBUTING.md 中与你的 CLA/DCO 政策一起说明,要在第一个 AI 生成的拉取请求到来之前,而不是之后。
别忘了你项目的财务一面
这是维护者会拖到报税季的部分:你的项目赚到第一块钱的那一刻——GitHub Sponsors 打款、Open Collective 捐赠、因为你的 README 而来的一次咨询合作——它就有了财务,而财务需要账本。
让贡献来源可审计的同一套纪律,也让项目资金变得可管理。把赞助收入与你的工资分开追踪,这样你就知道什么是应纳税的自雇收入。把项目开支——域名续费、CI 分钟数、律师审阅你的 CLA 花掉的那个下午——记在它们自己的账户里,这样扣除项就不会蒸发进个人信用卡账单。如果项目成长为 LLC 或加入财务托管方,干净的历史记录会让过渡变得无聊,而不是像法医鉴定。
纯文本记账与这个工作流契合得格外好:你的账本与代码一起放在版本控制里,每一笔记录都有历史,没有什么藏在专有格式里。我们的文档会带你几分钟内跑起第一个账本。
让你的项目账本和它的 Git 历史一样干净
在 CLA 和 DCO 之间做选择只需一个下午;多年后理清来源或项目财务要花几周。现在就做出贡献决策,自动化它的执行,并给项目的钱投入你给提交同样的用心。Beancount.io 提供纯文本记账,让你对自己的财务数据拥有完全的透明和控制——没有黑箱,没有供应商锁定。免费开始,看看为什么开发者和财务专业人士正在转向纯文本记账。





