Selling software license keys online: a creator guide

Selling software online is a business. Selling software license keys online is an operational discipline. The license key is the thin layer of trust between your code and the people who paid for it, and almost every painful moment in a software product business (piracy, chargebacks, support tickets about "my key doesn't work anymore") traces back to decisions you made about how that key is generated, activated, and eventually revoked.

This guide is for indie developers, small studios, and solo founders who sell desktop apps, plugins, developer tools, or any software that needs a license check. If you're selling activation codes, gift codes, or download keys (the broader category), our guide to selling codes online covers those patterns at a higher level. This article goes deeper on the software-specific parts: key formats, activation architectures, offline flows, and revocation.

What a software license key actually is

A license key is a string your customer pastes into your app. That's the user-facing definition. Under the hood, a modern license key is one of three things, and the choice you make here shapes every other decision.

A random string tied to a database record. The key itself carries no meaning. Your activation server looks up the string, checks who owns it, what tier it grants, how many devices have activated it, and whether it's been revoked. This is how most cloud-era licensing platforms (Keygen, LicenseSpring, Paddle with Keygen) work by default. The upside is flexibility. The trade-off is that your app has to talk to a server to verify anything.

A cryptographically signed token. The key contains real data (customer ID, tier, expiry, seat count) plus a digital signature your app can verify with a public key baked into the binary. Formats like PASETO v4 or Ed25519-signed payloads are the modern picks. This is what you want when offline verification matters, because your app can validate the key without phoning home.

A legacy hash or checksum key. The old-school 25-character alphanumeric strings from Windows software in the 2000s. A simple algorithm generated them, a simple algorithm verified them, and a simple algorithm cracked them within a week of release. Don't build new products on this pattern. It has one remaining use, which is making keys look familiar to buyers who expect a "proper" serial number, and that cosmetic effect can be preserved on top of modern crypto underneath.

For most indie products in 2026, the right answer is a hybrid. Generate a random key tied to a server record for day-to-day licensing, and issue a cryptographically signed license file for customers who need offline activation. Most licensing platforms give you both patterns without extra engineering.

Key generation: what actually matters

You have three realistic generation strategies, and the one you pick should be driven by the device environment your customers live in.

UUIDs and random strings

The simplest option. Generate a version 4 UUID or a 128-bit random string, format it as groups of uppercase characters (looks like A3F4-B821-9CD0-77EE), and store it in your database. Collision risk is effectively zero at any volume you'll ever hit. Speed of generation is microseconds. Customer perception is that it looks like a "real" software key.

This is what most modern delivery platforms do by default when you tell them to generate a key at checkout. For a one-tier product or a tool where every customer gets the same features, this is all you need.

Cryptographically signed keys with embedded data

When your key needs to carry information your app can verify without a network call, you sign the data instead of looking it up. The payload (customer ID, product tier, expiry date, seat count) gets signed with an Ed25519 or RSA-2048 private key that lives only on your licensing server. Your app ships with the public key and verifies the signature at runtime.

Ed25519 is the modern default because the signatures are small, verification is fast, and the security level is equivalent to AES-128 and NIST P-256. The keys themselves end up around 64 characters after base32 encoding, which is long but tolerable in an email or a copy-paste field.

The tradeoff is rigidity. Once a key is signed, you can't change what it grants. Upgrading a customer from the starter tier to pro means issuing a new key or layering a revocation check on top.

Server-generated keys with rich metadata

The most flexible option and the one most commercial platforms default to. Your checkout triggers an API call that creates a license record on your licensing server, generates a random key as the identifier, and stores the full entitlement (tier, seats, expiry, attached email) against that record. The server is the source of truth. The key is just a pointer.

This is the pattern behind LicenseSpring's key-based activation flow and Keygen's default licensing setup. You can change what a key grants at any point by updating the server record, revoke it in a single API call, and move customers between plans without issuing a new key. The cost is that your app needs a working network connection at least occasionally.

Activation server architecture

Once the key exists, your app needs to prove to your server that it's the rightful holder. This is the activation step, and it's where most licensing bugs live.

A healthy activation flow has four moving parts:

  1. Machine fingerprint. A hash derived from stable hardware attributes (CPU, motherboard, MAC address) plus the OS identifier. The goal is a value that stays constant across reboots but changes when the user moves to a new machine. Most licensing SDKs collect this automatically using platform APIs, so you don't have to write it yourself.
  2. Activation request. Your app sends the license key plus the machine fingerprint to the server over HTTPS. The server checks that the key is valid, hasn't been revoked, and that the customer hasn't hit their activation limit (most indie products allow three to five machines per license).
  3. Signed response. The server responds with a signed payload confirming the activation, the entitlement details, and an optional offline grace window. Your app stores this locally, encrypted or signed.
  4. Periodic heartbeat. Every few days or weeks, your app silently checks in with the server to confirm the license is still valid. This catches cases where the customer was refunded, the license was revoked, or a backup restored an old license file.

The periodic heartbeat matters more than most first-time builders realize. Without it, a customer who refunds, takes a backup of the license file, and then restores it keeps their access indefinitely. A light check every two weeks closes that loophole without annoying legitimate users.

Offline activation for customers who can't phone home

A surprising portion of software buyers need offline activation. Government environments, regulated industries, and anyone deploying to air-gapped networks. Pretending this isn't a real use case will cost you the most valuable customers in most B2B niches.

The standard offline flow is:

  1. The user runs your app offline and it generates an activation request file containing the machine fingerprint and the license key
  2. The user emails that file to you (or uploads it through a web portal on a different machine)
  3. Your licensing server produces a signed license file bound to that specific fingerprint
  4. The user transfers the license file back to the offline machine, where your app verifies the signature and unlocks

Every mature licensing platform supports this flow now. What you build yourself is the policy: how often (if ever) offline licenses expire, whether you automate the signing step with a web form, and how you handle hardware changes when the machine can't deactivate online.

Revocation and refund handling

Revocation is the operation everyone forgets until they need it. The first time a customer charges back, your licensing system should do three things automatically.

First, mark the license record as revoked on the server. The next heartbeat from the customer's app will fail validation and the software will refuse to launch (or drop into a locked trial state, depending on how you want to handle it).

Second, log the event with the original purchase reference and the machine fingerprints that activated under that license. If you ever dispute a chargeback, this timeline is your evidence.

Third, free up the seat count on any shared-seat licenses so the legitimate customers on the same account aren't locked out.

A clean refund policy makes revocation less adversarial. The honest play is a short no-questions window (14 days is standard, covered in detail in our guide to selling software online) where refund equals revocation. Outside that window, handle disputes case by case. The PayPal and Stripe rules on digital goods disputes are strict; our PayPal seller protection guide for digital products covers the evidence trail that actually holds up.

Which licensing tool to pick

If you want to skip building any of this yourself, the realistic options in 2026 are:

  • Keygen for developer-friendly, self-hostable licensing with a generous free tier. Strong on cryptographic keys and offline activation. Best fit for indie developers who want API-first control.
  • LicenseSpring for more polished dashboards and native SDKs across Windows, macOS, and Linux. Leans commercial, aimed at teams that want drop-in clients.
  • Paddle, Lemon Squeezy, or FastSpring with a licensing add-on. Useful when you want the merchant-of-record tax handling and licensing together. Paddle recently integrated Keygen directly for this purpose.
  • Rolling your own on top of a delivery platform. Generate UUIDs at checkout, store entitlements in your own database, verify with a small server you control. Practical if you only need one tier and your product can tolerate the maintenance cost.

Pair any of these with a checkout and delivery layer that handles the purchase, tax, and post-purchase email. SendOwl's secure downloads and code delivery covers the delivery side, with license keys pulled from inventory or generated on demand via API.

Build the minimum that protects the business

The goal of your licensing system isn't to defeat piracy. A determined attacker will crack any license system given time, and optimizing for that case costs legitimate customers real friction. The goal is to make casual sharing inconvenient, give you a clean way to revoke access when a refund or chargeback happens, and generate the evidence trail you need when a dispute goes to mediation.

Start with server-generated random keys, a simple activation limit, and a periodic heartbeat. Add cryptographic signing and offline activation when a paying customer asks for it. Skip anything else until you have real revenue to protect.

SendOwl makes selling software license keys online simple. Connect your licensing system, set your prices, and share the checkout link anywhere you connect with your audience. Get started selling digital products for free today.

Join the
community

Join our newsletter for the latest tips, updates,
and exclusive offers to supercharge your digital product sales.

Join

Related posts