DEV Community

Gig Shield
Gig Shield

Posted on

How to Structure Milestone Payments for Freelance Software Projects

If you've freelanced as a developer for long enough, you've probably had one of these:

  • The client says the feature "isn't finished" three weeks after you shipped it.
  • The last invoice is the one that never gets paid.
  • A "quick change" after sign-off turns into a week of unpaid work.

None of these are really about money. They're about a project structure that left "done" undefined and put all the risk on one side. Here's how to fix that.

1. Milestones should end in something you can run

A milestone is only useful if both sides can check it without an argument. "Backend work" is not a milestone. "API endpoints for auth and orders, deployed to staging, with a Postman collection" is.

A structure that works for most small and mid-size projects:

Milestone Deliverable Share of budget
Spec Agreed scope, user stories, technical approach 10 to 15%
Core build Main features working on staging 35 to 40%
Completion Remaining features, tests passing, bugs fixed 30 to 35%
Handover Production deploy, docs, access transferred 15 to 20%

Keep the final milestone small. It's the one most often delayed, so don't let it hold a third of the budget.

2. Write acceptance criteria like test cases

For every milestone, agree in writing:

  • Which features must work, and in which environment
  • Which tests must pass (unit, integration, or a manual checklist)
  • What's included: docs, migrations, environment setup
  • How long the client has to review, and what happens if they don't

That last one matters. A fixed review window, for example 72 hours, after which the milestone is treated as approved, stops your payment from waiting on someone's holiday.

3. Every change request is a new milestone

Anything outside the agreed scope gets its own price and its own acceptance criteria. It feels formal the first time. After that it saves the relationship, because nobody is doing free work and nobody gets a surprise invoice.

4. Get the money committed before you write code

Asking for full payment upfront scares good clients. Waiting until the end puts all the risk on you. The middle ground is escrow per milestone:

  1. The client funds the milestone before work starts.
  2. A neutral party holds the funds.
  3. You deliver, the client approves, the money is released.
  4. If there's a disagreement, the evidence is checked against the written criteria.

Developers have an advantage here: our evidence is unusually good. Commit history, pull requests, staging URLs, CI results and logs make it easy to show whether a milestone was met.

Disclosure: I'm the founder of GigShield.ai, which does milestone escrow for freelancers and the clients they already work with. There's a longer guide on escrow for software development projects if you want templates for milestone design. The structure in this article works with any escrow method, or even without one.

5. Keep the paper trail as you go

  • The signed agreement, with milestones and criteria
  • Written approval for each milestone (a message is enough)
  • Each change request and its price
  • Links to the commits, releases and test runs for each delivery

Checklist before your next project

  • Every milestone ends in something the client can run or test
  • Acceptance criteria are written, with a review deadline
  • The final milestone is 20% or less of the budget
  • Change requests are priced as new milestones
  • The first milestone is funded before you start
  • Both sides know how a disagreement will be resolved

Get the structure right and most "payment problems" never happen.

Top comments (0)