App Store Connect statuses explained: every version state and what you can change in it

Every version of your iOS app carries exactly one status, and that status decides two things: where the version sits in Apple's queue, and what you are still allowed to change. Everything else, the badges, the emails, the yellow dots, is decoration on top of that one value.

Here is the whole set, what each one means, and what you can edit while you are in it.

The table

Status (API value) What Apple is telling you Can you edit metadata?
PREPARE_FOR_SUBMISSION A draft version. Nothing has been sent anywhere. Yes, everything
PROCESSING_FOR_APP_STORE Your binary arrived and Apple is processing it. Build is locked; the version is not editable
WAITING_FOR_REVIEW Submitted. Sitting in the queue. No human has opened it. No
IN_REVIEW A reviewer has it open. No
PENDING_DEVELOPER_RELEASE Approved. Live only when you press the button. No
READY_FOR_SALE Live on the App Store. No, this version is frozen forever
REJECTED Rejected on a guideline. Usually needs a new build. Yes
METADATA_REJECTED Rejected on text or images only. No new build needed. Yes
INVALID_BINARY The binary failed Apple's checks. Upload a fixed one. Yes
DEVELOPER_REJECTED You pulled it out of review. Yes
REPLACED_WITH_NEW_VERSION Superseded by a later version going live. No
REMOVED_FROM_SALE Apple took it off the store. No
DEVELOPER_REMOVED_FROM_SALE You took it off the store. No
ACCEPTED Approved, in the gap before release. Rarely seen. No

Apple's enum has a handful of other values you will almost never meet, states covering pre-orders, export compliance answers and unsigned contracts among them.

The console does not always show you the raw constant. It shows friendlier wording: "Ready for Sale", "Waiting for Review", "Pending Developer Release", and that wording has changed over the years. The API value is the stable thing. If you are debugging, get the API value.

The four editable states: this is the rule that matters

You can only write to a version that is in one of these four states:

  • PREPARE_FOR_SUBMISSION
  • REJECTED
  • METADATA_REJECTED
  • DEVELOPER_REJECTED

That is the whole list. Description, keywords, promotional text, what's new, screenshots, app previews, build attachment, all of it targets a version, and the version has to be in one of those four.

Anything else and the write fails. Not "silently ignores", fails, with a message about the version not being modifiable in its current state. This is the single most common reason an automated metadata push blows up: the tool asks for an editable version, there isn't one, and the whole job stops.

Notice what is not in that list. WAITING_FOR_REVIEW and IN_REVIEW are locked, which is expected. But READY_FOR_SALE is locked too, and that surprises people. A live version is a historical record. To change anything a shopper sees, you create a new version in PREPARE_FOR_SUBMISSION and change it there.

The part nobody tells you: there are two records, not one

Your listing is split across two objects in App Store Connect, and they have separate states.

The App Store Version record holds everything that changes per release: description, keywords, promotional text, what's new, screenshots, and the build.

The App Info record holds the things that describe the app itself: name, subtitle, primary and secondary category, content rights, age rating, privacy policy URL.

A live app carries two App Info records at once: the live one, locked permanently, and an editable one that staged changes flow through. Read the live record and you get what shoppers see today. Write to it and you get a 409 with a message along the lines of "can not be modified in the current state", because you aimed at the wrong record, not because you lack permission.

The App Info record's own editable states are PREPARE_FOR_SUBMISSION, REJECTED and DEVELOPER_REJECTED.

Practical consequence: changing your app's name and changing your app's description are two different operations against two different records, and one can succeed while the other fails. If a tool tells you the description pushed but the title did not, this is why.

The order things actually happen in

For a normal, uneventful release:

  1. PREPARE_FOR_SUBMISSION: you create the version and write the copy
  2. PROCESSING_FOR_APP_STORE: you upload a binary and Apple ingests it
  3. WAITING_FOR_REVIEW: you submit; it queues
  4. IN_REVIEW: a reviewer opens it
  5. PENDING_DEVELOPER_RELEASE: approved, waiting on you (if you chose manual release)
  6. READY_FOR_SALE: live

Choose automatic release instead and step 5 disappears: IN_REVIEW goes straight to READY_FOR_SALE, sometimes within minutes of the approval email.

When it goes wrong, the branch is at step 4. IN_REVIEW becomes REJECTED or METADATA_REJECTED, the version drops back into an editable state, and you fix and resubmit. That resubmission is a new trip through the queue on the same version, the version number does not change, and neither does the version record.

The states that mean something different from what they sound like

METADATA_REJECTED is good news relative to REJECTED. It means the reviewer's objection is to text, images or your review notes, nothing in the binary. You edit, you resubmit, no new build, no App Store Connect upload, no waiting for processing. Treat the two identically and you will waste an afternoon rebuilding an app that was fine.

DEVELOPER_REJECTED means you rejected it. Apple did not. Somebody on your team clicked the button that withdraws a submission from review, often to fix a typo spotted after submitting. The version goes back to editable and you resubmit. If you see this and nobody admits to clicking it, check who has access.

PENDING_DEVELOPER_RELEASE means it is approved and not live. Nothing further happens until a human releases it. Apps sit in this state for weeks because everyone assumed approval meant shipped.

INVALID_BINARY is not a review outcome. It is Apple's processing pipeline rejecting the upload itself, bad entitlements, missing icons, an unsupported architecture. No reviewer was involved. Fix the build and upload again.

REPLACED_WITH_NEW_VERSION is bookkeeping. When 1.4 goes live, 1.3 gets this state. It is not a rejection and there is nothing to do.

Getting the real status

The console shows you a label. If you want the constant, the App Store Version record carries an appStoreState attribute, and listing an app's versions returns it directly. It is the same value the console renders, without the interpretation layer.

That matters when the console and your memory disagree, and they will, because a version's state changes without anyone emailing you. PROCESSING_FOR_APP_STORE to WAITING_FOR_REVIEW is silent. So is PENDING_DEVELOPER_RELEASE to READY_FOR_SALE if someone else pressed release.

What to do with this

Before any metadata change, ask one question: is there a version in one of the four editable states? If yes, edit it. If no, create a new version, that is the only way to get one.

Before assuming you need a new build, read the status carefully. METADATA_REJECTED does not need one. REJECTED usually does. INVALID_BINARY always does.

And before wondering why your approved app is not on the store, check for PENDING_DEVELOPER_RELEASE.

AppSubmit reads these states straight from the API and refuses to offer you an action the state cannot support. It will not show a "push metadata" button for a version that is in review, because that button could only fail. You can do exactly the same check by hand with the table above.

Last reviewed 2026-08-17. Apple and Google change their rules without notice, so check anything decision-critical against their live documentation.