Maintaining an Open Source Package for Six Years Taught Me Contract Law

Jul 15, 2026 By Yusuke Tanaka

Six years ago I published a Swift library called BarcodeKit for handling barcode scanning on iOS. It was a weekend project, a few hundred lines, MIT licensed. I expected maybe a dozen stars on GitHub. Instead the package grew to over 4,000 dependents, and I became a maintainer whether I planned to or not. For most of those six years I thought of open source as a technical problem: merge requests, CI pipelines, semantic versioning. Then a contributor sent a cease-and-desist email claiming I had violated the terms of an old BSD-style license embedded in a dependency. That email taught me something no tutorial ever did: a license is a contract.

The Day I Realized a License Was a Contract

It started with a pull request. A new contributor had submitted a patch that included code from a library with a three-clause BSD license. The file headers were intact, so I merged it. Two weeks later I received a formal letter from an attorney representing the original author of that BSD library. The letter demanded I remove the contributed code because the license included a non-endorsement clause I had allegedly violated by using the author's name in my documentation. I had never read the full BSD text; I just assumed "permissive" meant "safe."

That demand forced me to read the license word by word. Section 2 of the BSD 3-Clause says: Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. My README had thanked the contributor by name and listed the library as an inspiration. I had not sought permission. Technically, I was in breach. We settled by removing the name and adding a disclaimer, but the lesson stuck: license terms are legally enforceable promises.

I am not a lawyer. I never took a contracts class. But after that incident I started treating every LICENSE file as a binding document. I read the fine print of MIT, Apache 2.0, GPLv3, and the lesser-used ones like MPL and AGPL. I discovered that most licenses include sections on warranty disclaimer, limitation of liability, and governing law. These are not boilerplate; they allocate risk. And as a maintainer, you are the party accepting that risk on behalf of your project.

The cease-and-desist email itself was informative: it cited specific clauses, referenced the license version, and demanded action within 14 days. I responded within 48 hours, but the anxiety of potentially facing litigation over a hobby project was real. That experience reshaped how I view every pull request. I now check not just the code but the license of every dependency introduced. It adds minutes to each review, but it beats a legal letter.

How Open Source Governance Mirrors Employment Terms

Contributor License Agreements, or CLAs, are the open source equivalent of an employment contract. When a contributor signs a CLA, they grant the project a license to use their contributions, and they often agree to represent that the work is original. As a maintainer, I act like a hiring manager: I review the candidate (the code), check references (the contributor's history), and decide whether to accept. But unlike a manager, I have no HR department, no legal team, and no budget for disputes.

Code review becomes a form of performance evaluation. I assess not just correctness but also license compatibility, potential patent issues, and adherence to project governance. A contributor who submits a patch derived from GPL code into an MIT project is, in effect, violating the terms of both licenses. I have to catch that. The trade-off is that governance work eats into coding time. Some weeks I spend more hours reading license headers and drafting contribution guidelines than writing features.

Burnout from unpaid governance work is common. Studies estimate that roughly 60% of open source maintainers are solo or part-time, and many report stress from legal ambiguity. The autonomy of running your own project is real, but so is the exposure. I have no liability insurance, no corporate shield. If a contributor's code infringes a patent, the lawsuit could name me personally. That risk is rarely discussed in beginners' guides to open source.

The parallel to employment goes deeper: just as an employer can be vicariously liable for an employee's actions, a maintainer can inherit liability from a contributor's mistakes. The legal term is "contributory infringement." If I distribute code that I should have known was infringing, I am liable. That is why large projects like Kubernetes require CLAs and run automated license checks. Small projects cannot afford that infrastructure, but they face the same legal exposure.

Reading License Files: One Key Practice, Not a Checklist

After my legal scare, I adopted a single key practice: reading the full license text of every dependency. I do not rely on summaries or package manager labels. For each new dependency, I open the LICENSE file and scan for three things: warranty disclaimer, governing law, and any non-standard clauses. This takes five minutes per dependency. I also check that the license is compatible with my project's MIT license. For example, if a dependency uses GPL, I cannot include it in BarcodeKit without changing the project license or isolating the code.

This diligence has caught several issues. Once, a dependency's license included a clause that required attribution in advertising materials. My project had no advertising, but if a large company used BarcodeKit in a product, that clause could create obligations. I replaced the dependency with an alternative under MIT. Another time, a dependency's license specified that it was governed by the laws of a country with different copyright standards. I decided the risk was acceptable, but I noted it in my records.

Automated license checking tools exist, but they are not perfect. I use a CI step that runs license-checker and flags any non-MIT-compatible licenses. But the tool only knows about common licenses; it cannot catch custom clauses. Human review is still necessary. I also maintain a spreadsheet of direct and transitive dependencies and their licenses. This is tedious, but it prevents the kind of incident that triggered my first cease-and-desist.

The Three Clauses That Bite Maintainers Most

Three clauses in open source licenses cause the most trouble for maintainers. The first is indemnification. Apache 2.0, for example, includes a section where contributors grant a patent license and agree to indemnify the project for claims arising from their contributions. But many contributors never read that section. If a contributor violates a third-party patent, the project may be protected, but the maintainer's personal liability is not always covered.

The second clause is the warranty disclaimer. Almost every open source license states that the software is provided "as is" without warranty. This is not just a courtesy; it is a legal shield. But the disclaimer only works if the license is properly applied. If you distribute the software without the license text, or if you modify the terms, the disclaimer may be invalid. I have seen projects accidentally remove the warranty section when copying a license file. That mistake can expose users to claims.

The third clause is governing law. Most licenses specify a jurisdiction, like California or New York. If your project is governed by the laws of a state you have never visited, you could be sued there. I once received a contribution from a developer in Germany, and the license specified California. If a dispute arose, I would have to defend myself in a foreign court. This is rare, but it happens. Some maintainers now add a choice-of-law clause in their CONTRIBUTING file to avoid this.

A real example: a friend who maintains a GPL library received a demand letter from a company claiming the library violated a patent. The letter cited the GPL's termination clause, which says that anyone who distributes GPL software and violates its terms loses their license. The company argued that the library's use of a patented algorithm without permission triggered termination. The dispute settled quietly, but it cost my friend thousands in legal fees. Most disputes settle without court, but the cost alone can crush a solo maintainer.

What I Learned from the EU Digital Identity Wallet Debate

In mid-2026, a discussion on Hacker News highlighted the EU Digital Identity Wallet's age-verification technical specification. The specification, hosted on GitHub, proposed that wallets must run on either Android or iOS, effectively locking out other platforms. Commenters noted that the license terms of the specification could force implementers to use only those operating systems. This is contract law meeting platform lock-in: by imposing license conditions, the EU could mandate technical choices.

The debate reminded me of a near-miss in my own package. Early on, I considered adding a clause that the library could only be used on Apple platforms. I thought it would protect the user experience. But a contributor pointed out that such a clause would make the license non-standard and potentially unenforceable. I dropped the idea. The EU wallet spec eventually added a clause allowing alternative implementations, but the controversy showed how license terms can become regulatory tools.

Open source is increasingly used as a compliance mechanism. Governments and corporations publish specifications under open licenses, and those licenses carry obligations. For maintainers, this means that the legal context of your project can shift based on who adopts it. A library written for hobbyists might end up powering government infrastructure. The license you choose today affects that future use. I now include a note in my README that the package is intended for general use and not specifically designed for regulatory compliance.

The EU wallet debate also highlighted the tension between open source ideals and practical governance. The specification was open for comments, but the license terms were drafted by lawyers, not developers. As a maintainer, I learned to read proposed license changes with the same scrutiny I apply to code changes. I also learned that the best way to avoid platform lock-in is to keep the license as permissive and neutral as possible. My package uses MIT, which imposes no platform restrictions. That simplicity is a feature.

Practical Contract Hygiene for Solo Maintainers

Disclaimer: I am not a lawyer, and nothing in this section constitutes legal advice. You should consult an attorney for your specific situation.

After my legal scare, I adopted a set of practices that I call contract hygiene. First, every project must have a CONTRIBUTING file that explicitly states the license terms and the process for accepting contributions. I include a line that says: By submitting a pull request, you agree that your contribution is licensed under the project's license and that you have the right to submit it. This creates a simple contract between contributor and maintainer.

Second, I use a standard CLA template. The Apache Individual Contributor License Agreement is widely recognized and covers patent grants and representation. I do not write custom CLAs; they are harder to enforce and scare contributors. A standard CLA signals professionalism. I store signed CLAs in a private repository as a paper trail. So far I have only a dozen signatures, but for critical contributions, it provides legal clarity.

Third, I pin governing law to my home state. In the CONTRIBUTING file, I add a sentence: This project is governed by the laws of Japan, where the maintainer resides. This is not a formal choice-of-law clause, but it establishes a default. If a dispute arises, the jurisdiction is clear. I also include a note that the project is provided "as is" and that the maintainer is not liable for damages. This mirrors the standard warranty disclaimer.

Fourth, I keep a paper trail of all contributor agreements. For significant contributions, I ask the contributor to acknowledge the license terms in the pull request comment. I also run automated license header checks in CI. A simple script verifies that every new file contains a license header matching the project's license. This catches accidental inclusion of incompatible code. The CI step takes seconds but has flagged several problematic contributions.

Finally, I review the license of every dependency added to the project. I maintain a spreadsheet of direct and transitive dependencies and their licenses. If a dependency uses GPL, I do not include it in an MIT project. If it uses Apache 2.0, I ensure the attribution notice is preserved. This diligence is tedious, but it prevents the kind of incident that triggered my first cease-and-desist.

When Offloading Thinking to AI Blurs Liability

An article on Artfish from July 2026 asked whether we are offloading too much of our thinking to AI. For open source maintainers, the question has a legal dimension: who owns AI-generated code contributions? If a contributor uses an AI tool like GitHub Copilot to write a patch, the copyright status of that patch is uncertain. The AI model may have been trained on GPL code, and the output could be considered a derivative work. As a maintainer, I could be distributing code that carries hidden license obligations.

I have a policy: contributions must be human-reviewed and the contributor must attest that they have the right to submit the code. I do not accept AI-generated patches unless the contributor explicitly states that the output is original and not derived from copyrighted training data. This is a conservative stance, and it may be overly cautious. Some projects welcome AI assistance. But until the law clarifies, I prefer to err on the side of legal safety.

The license compatibility of AI training data is a growing concern. If an AI model was trained on code under GPL, its output may be considered a derivative work under the GPL. Lawyers are still debating this. The Free Software Foundation has not issued a definitive opinion. For now, I include a disclaimer in my CONTRIBUTING file: Contributions generated by AI tools must be accompanied by a statement that the output does not infringe any third-party rights. This is not legally binding, but it creates a record.

Contract law has not caught up with AI. The standard CLA templates assume a human author. There is no checkbox for "generated by a neural network." Until the law evolves, maintainers must hedge. I add a note that the project accepts contributions under the terms of the license, and that the contributor bears responsibility for the originality of the code. This shifts some risk back to the contributor, though in practice enforcement is unlikely for small projects.

Six Years In, I'm More Engineer Than Lawyer

Contract law taught me discipline, not fear. I still write code most weekends. The package still ships new releases, and contributors still submit patches. But I now approach each pull request with a legal checklist alongside my technical review. That checklist takes maybe five minutes, but it has prevented at least two potential disputes. The trade-off is that I spend less time on features and more on documentation and governance. For a solo maintainer, that is a real cost.

Good governance reduces friction, not fun. When contributors know the rules, they are more confident. I have seen fewer questions about licensing since I added the CONTRIBUTING file. Technical decisions often have legal or contractual implications, as seen in articles like Service Mesh Overhead and Cross-Platform Library Bans. The same is true for open source governance.

That said, I also recognize that most maintainers never face a legal issue. Over-engineering governance can harm community contribution. If you require a signed CLA for every typo fix, contributors will go elsewhere. There is a balance. For BarcodeKit, I only require CLAs for significant contributions—those that add new features or modify core logic. Small bug fixes and documentation changes are accepted without a CLA, trusting that the contributor has the right to submit. This pragmatic approach has kept the contribution pipeline flowing while still protecting the project's legal interests.

I am still more engineer than lawyer. I do not give legal advice. But I have learned to read contracts the way I read code: looking for edge cases, undefined behavior, and hidden dependencies. The skills transfer. Version control teaches you to track changes; contract law teaches you to track obligations. Both are about managing complexity over time.

Next, I want to mentor other maintainers on legal basics. I have started a small guide on my GitHub profile, covering CLAs, license compatibility, and AI contributions. The goal is not to make everyone a lawyer, but to reduce the number of maintainers who learn about contract law the way I did: through a cease-and-desist email. The open source ecosystem runs on trust, but trust works best when backed by clear terms.

Still, I wonder: as open source becomes more formalized, will we lose the informal, collaborative spirit that made it special? Or can we find a middle ground where legal hygiene supports rather than stifles contribution? I do not have the answer, but I am watching how projects like Rust and Kubernetes handle these tensions. For now, I will keep coding, keep reviewing, and keep reading those license files—one clause at a time.

Recommend Posts
Tech

A Cloud Team Paid Three Different Chip Vendors for the Same SHA-256 Hash

By Sara Park/Jul 14, 2026

A cloud team ran the same SHA-256 hash on Intel, AMD, and AWS Nitro hardware and got three different bills. This is the economics of the hardware-software boundary, where identical computations cost wildly different amounts depending on which chip vendor you choose.
Tech

FPGA Inference Pipeline Paid Per LUT Rewrites a Billion-Token Batch Economy

By Yusuke Tanaka/Jul 14, 2026

How LUT-based FPGA inference cuts per-token cost below GPU for billion-token batches, reshaping LLM deployment economics and API-level design.
Tech

One BGP Session, Three Transit Providers, and a Peering Invoice That Rewrites Latency

By Yusuke Tanaka/Jul 14, 2026

A peering invoice from a single BGP session revealed how transit costs, not fiber distance, dictated latency. A contrarian take on network engineering in 2026.
Tech

Pixel 8a Ships with One DSP Radio Stack as Qualcomm Tunes the Other

By Sara Park/Jul 15, 2026

Google's Pixel 8a ships with one of two DSP radio stacks active while Qualcomm tunes the other post-launch. This dual-stack approach reveals how modem firmware constraints shape Android development.
Tech

Maintaining an Open Source Package for Six Years Taught Me Contract Law

By Yusuke Tanaka/Jul 15, 2026

Six years maintaining an open source package taught a solo developer that license terms are contracts. A practical guide to governance, liability, and legal hygiene for maintainers.
Tech

One Open Source License Rewrote Its Compatibility Clause After Three Corporate Forks

By Yusuke Tanaka/Jul 14, 2026

How three corporate forks of a copyleft license forced its maintainers to rewrite the compatibility clause, closing loopholes and reshaping downstream project choices.
Tech

One SwiftUI App Store Review Bans Five Cross-Platform Libraries Our Team Depended On

By Sara Park/Jul 15, 2026

A single App Store rejection banned five cross-platform libraries our team had relied on for two years, forcing costly rewrites and exposing the fragility of third-party stacks in iOS development.
Tech

Cache Ejections at the European Edge Double a Transit Provider's Per-Region Bill

By Yusuke Tanaka/Jul 14, 2026

European edge nodes eject caches faster due to ISP fragmentation and low TTLs, doubling per-region bills for transit providers. Tuning with Fastly VCL or AWS Origin Shield can cut costs but adds latency or CPU overhead.
Tech

Three Database Engines Claim Linearizable Reads as a Clock Skid Resets One Team's Consensus

By Lucas Mendes/Jul 15, 2026

A fintech incident reveals how clock skew breaks linearizable reads in CockroachDB and YugabyteDB. Analysis of trade-offs, mitigations, and choosing the right engine.
Tech

Ethernet MAC Hardware Offload Exposes a UDP Jitter Bug That Two Kernel Stacks Hide Differently

By Sara Park/Jul 14, 2026

A deep-dive into how Linux and FreeBSD handle UDP jitter differently under hardware MAC offload, revealing a timestamp-ordering bug in Intel XL710 NICs and practical trade-offs for real-time workloads.
Tech

Saga Pattern vs Two-Phase Commit: Two Distributed Transaction Lies That Fail Differently

By Deepa Iyer/Jul 14, 2026

Both Two-Phase Commit and Saga Pattern promise distributed transaction consistency, but each fails in its own way. A pragmatic breakdown of when each works, where they break, and what practitioners actually do in production.
Tech

BGP Hijack Insurance Rewrote One ISP’s Transit Bill in Four Hours

By Sara Park/Jul 15, 2026

How one ISP turned a BGP hijack into a transit insurance payout, rewriting the economics of network reliability and path integrity.
Tech

A Single Signed SBOM Commit Killed a Friday Afternoon’s Production Patch

By Deepa Iyer/Jul 15, 2026

When a signed SBOM commit triggered a production pipeline failure, a team learned the hard way that supply-chain security gating has real operational costs. This is what working with signed attestations looks like in 2026.
Tech

Google Cloud Spanner’s Write Lock Pricing Forces a PostgreSQL Team to Relearn Transaction Visibility

By Deepa Iyer/Jul 14, 2026

A PostgreSQL team migrating to Google Cloud Spanner discovered that per-write-lock pricing can dominate cloud bills. This article compares Spanner, PostgreSQL, and CockroachDB on cost, consistency, and lock behavior.
Tech

Open Source Maintainers Bill the Corporation That Forked Their Stack

By Sara Park/Jul 15, 2026

When corporations fork open source projects and monetize them without contributing back, maintainers are fighting back with new licensing models, foundations, and billing strategies.
Tech

Six Engineers Maintain Two Rendering Engines as One Company Owns the DOM

By Lucas Mendes/Jul 14, 2026

React and Vue both maintain separate virtual DOM implementations, each requiring dedicated teams. This article examines the economic and engineering costs of dual rendering engines, corporate ownership, and what a unified standard might look like.
Tech

Paying a License Fee Every Time an Open Source Maintainer Quits

By Lucas Mendes/Jul 15, 2026

When a critical open-source maintainer quits, downstream users pay a hidden tax. This article explores why licenses stay silent, how corporate users extract value, and what market mechanisms could fix the gap.
Tech

Apple's App Store Commission Rewrites the Cost of a SwiftUI Gesture Handler

By Yusuke Tanaka/Jul 14, 2026

A $0.99 SwiftUI gesture handler reveals how Apple's 30% commission and platform lock-in reshape developer economics compared to Android's more open model.
Tech

Service Mesh Overhead That Bills Per Sidecar Rewrites a Kubernetes Team’s Capacity Budget

By Deepa Iyer/Jul 14, 2026

Per-sidecar billing from service meshes like Istio and Linkerd can inflate Kubernetes costs by 30-40%. This article examines the hidden overhead, real-world case studies, and alternatives like eBPF and ambient mesh.
Tech

One Data Scientist Runs Inference on Three GPU Vendors and Every Bill Differs

By Sara Park/Jul 14, 2026

A data scientist runs identical LLM inference workloads on AWS, GCP, and Azure. The bills differ wildly. Here's why GPU pricing is still a black box in 2026.