The example code that you pointed to from BasicAndroidKeyStore does not log the public key as getPublic() from the KeyPair class only returns a reference the the public key object, not the public key itself.
Log.d(TAG, "Public Key reference is: " + kp.getPublic().toString());
Logs:
D/KeyStoreFragment: Public Key reference is: android.security.keystore.AndroidKeyStoreRSAPublicKey@b8004e8f
The same goes for getPrivate().
Log.d(TAG, "Private Key reference is: " + kp.getPrivate().toString());
Logs:
D/KeyStoreFragment: Private Key reference is
android.security.keystore.AndroidKeyStoreRSAPrivateKey@5da42c27
Now, as you point out in your comment, kp.getPublic().getEncoded()
will return the actual public key, but a public key's original purpose is not meant to be secret.
The private key is meant to be secret and while using a hardware-backed keystore with keys supported in the device's secure hardware, the secret keys are stored safely in the TEE/SE and cannot be extracted by the app itself or another bad actor with root privileges. You can see it in this example:
Log.d(TAG, "Private Key is " + Arrays.toString(kp.getPrivate().getEncoded()));
Logs:
D/KeyStoreFragment: Private Key is null
To verify your keys are supported by your device's secure hardware, you can use some variation of this code to suit your needs. You can paste this snippet after the same Log.d mentioned above in the example app's createKeys() method.
KeyFactory factory = KeyFactory.getInstance(kp.getPrivate().getAlgorithm(), "AndroidKeyStore");
KeyInfo keyInfo = null;
try {
keyInfo = factory.getKeySpec(kp.getPrivate(), KeyInfo.class);
} catch (InvalidKeySpecException e) {
e.printStackTrace();
}
if (keyInfo.isInsideSecureHardware())
Log.d(TAG, "Key is supported in secure hardware");
else
Log.d(TAG, "Key is not supported in secure hardware");