Code signing is the cryptographic mechanism that proves your binary was built by you and hasn't been tampered with in transit. Without a valid signing configuration, app stores refuse to accept the binary — there is no workaround or exception. For Android, releasing with only the debug keystore (the default development key) means you cannot update your app once published, because Google Play requires all updates to be signed with the same key. A lost or overwritten keystore permanently orphans your published app, blocking all future updates for every existing user. CWE-798 (hardcoded credentials) applies when keystore passwords appear in committed source — exposing your signing key allows anyone to publish malicious updates impersonating your app.
Critical because unsigned builds are rejected outright by both stores, and a lost Android keystore permanently blocks updates for every existing install.
For Expo projects, use EAS Build which manages credentials automatically. For bare React Native Android, generate a release keystore and reference it via environment variables — never commit the keystore file or its password.
// android/app/build.gradle
signingConfigs {
release {
storeFile file(System.getenv("KEYSTORE_PATH") ?: "../release.keystore")
storePassword System.getenv("KEYSTORE_PASSWORD")
keyAlias System.getenv("KEYSTORE_ALIAS")
keyPassword System.getenv("KEYSTORE_KEY_PASSWORD")
}
}
buildTypes {
release {
signingConfig signingConfigs.release
}
}
Store the keystore file and all four environment variables in your CI secret store (GitHub Actions secrets, EAS secrets, etc.). Back up the keystore in a separate secure location — it cannot be recovered if lost.
mobile-store-readiness.build-config.build-signing-configuredcriticaleas.json under build.ios.production or in Xcode project settings (team ID, provisioning profile, certificate). For Android, check android/app/build.gradle for a signingConfigs block or eas.json for android.production.withoutCredentials: false. Count all signing configuration references found across build files. Verify signing keys/certificates are referenced (not necessarily examining the actual keys themselves, just the configuration)."No iOS signing configuration found in Xcode project — Team ID not set" or "Android signingConfigs references keystore at path that doesn't exist: ./keystore.jks"eas build --platform ios --auto-submit # EAS handles signing
eas build --platform android # EAS handles signing
keytool -genkey -v -keystore my-release.keystore -keyalg RSA -keysize 2048 -validity 10000 -alias my-key-alias
android/app/build.gradle, add signingConfigs:
signingConfigs {
release {
storeFile file("../my-release.keystore")
storePassword System.getenv("KEYSTORE_PASSWORD")
keyAlias System.getenv("KEYSTORE_ALIAS")
keyPassword System.getenv("KEYSTORE_KEY_PASSWORD")
}
}