'JAVA Generating a Signature for Apple Promotional Offers
I'm trying to generate a signature to be returned to the mobile application in order to validate a promotional offer with the App Store.
Apple documentation :doc
However, the validation failed in the mobile application with invalid signature error.
Below, the method that aims to generate the signature
public static final String BEGIN_PRIVATE_KEY = "-----BEGIN PRIVATE KEY-----";
public static final String END_PRIVATE_KEY = "-----END PRIVATE KEY-----";
public static final String EC = "EC";
public static final String SHA_256_WITH_ECDSA = "SHA256withECDSA";
public static final String SEPARATOR = "\\u2063";
public static final String P8_KEY_PATH = "classpath:keys/AuthKey.p8";
private void setSignature(SubscriptionDto subscription , String username) {
String productId = subscription.getAppleIdentifier();
UUID nonce = UUID.randomUUID();
Instant instant = Instant.now();
long timestamp = instant.toEpochMilli();
String offerId = getOfferId(subscription);
String payload = buildPayload(productId, nonce, timestamp, offerId, username);
Signature ecdsaSign = Signature.getInstance(SHA_256_WITH_ECDSA);
ecdsaSign.initSign(getPrivateKey());
ecdsaSign.update(payload.getBytes(StandardCharsets.UTF_8));
byte[] signature = ecdsaSign.sign();
String sig = Base64.getEncoder().encodeToString(signature); // returned signature
verify(sig, payload);
}
private String buildPayload(String productId, UUID nonce, long timestamp, String offerId, String username) {
return String.join(SEPARATOR, bundleId,
keyId,
productId,
offerId,
username!=null?username:"",
nonce.toString().toLowerCase(),
Long.toString(timestamp));
}
public PrivateKey getPrivateKey() throws Exception {
String key = FileUtils.readFileToString(ResourceUtils.getFile(P8_KEY_PATH),
Charset.defaultCharset());
String privateKeyPEM = key
.replace(BEGIN_PRIVATE_KEY, "")
.replaceAll(System.lineSeparator(), "")
.replace(END_PRIVATE_KEY, "");
byte[] encoded = Base64.getDecoder().decode(privateKeyPEM);
KeyFactory keyFactory = KeyFactory.getInstance(EC);
PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(encoded);
return keyFactory.generatePrivate(keySpec);
}
Any idea please ?
Solution 1:[1]
You need to update your invisible separator
from this
public static final String SEPARATOR = "\\u2063";
to this
public static final String SEPARATOR = "\u2063";
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | Waleed Hassan |