Every Tappa app uses calendar versioning (CalVer) in the form YY.M.patch — for example, 26.4.2 means the second patch of the April 2026 release. We switched from SemVer in 2023 and have not looked back. Here is why.

SemVer was designed for libraries

The semantic versioning spec is a contract between a library and its consumers: major.minor.patch tells you whether an upgrade can break your code. That contract is meaningful when humans (and dependency managers) read it.

An app has no consumers in that sense. The user does not know or care whether 2.4.1 is a major or minor change. They want to know whether the app is recent, whether they have the latest, and whether bug X is fixed.

What CalVer gives you

Built-in freshness signal. Open any Tappa app's About screen. The user sees 26.4.x. They know it shipped this month. That communicates more than 2.41.0 ever could.

A natural release cadence. We ship at least monthly. The CalVer scheme makes this rhythm visible internally. Missing a month is loud — 26.4 followed by 26.6 is hard to ignore.

No more bike-shedding about "is this minor or major?" The decision is gone. The version is the date. The energy goes back into the changelog, where it belongs.

What it does not solve

CalVer does not magically remove the need for a clear changelog. We still write user-facing release notes for every shipped version, and we keep an internal CHANGELOG.md with the engineering details. The version number tells you when. The notes tell you what.

How we map this to App Store Connect

Apple's CFBundleShortVersionString accepts the YY.M.patch format directly. The build number (CFBundleVersion) is a monotonically increasing integer; we do not encode information into it.

In Info.plist:

MARKETING_VERSION = 26.4.2
CURRENT_PROJECT_VERSION = 1247

The build number is set by CI, never by hand.

Edge cases we hit

Two cases needed thinking through:

A small recommendation

If you ship apps regularly, switch to CalVer at the next major release. Document the format in your repo's README. Update your CI. Forget about it. The decision is permanent and the upside is steady.

Libraries — keep using SemVer. They are different animals. Different versions.