/** * ─────────────────────────────────────────────────────────────────────────────────────────────────┐ * This web service class handle the custom respons which we send while authenticate user * Insert the user refresh token into the configuration custom settings. * Saved refresh token into installer User's org. * Shopify API Documentation: https://shopify.dev/docs/admin-api/rest/reference * Create Shopify Store: https://www.shopify.com/signup?itcat=identity&itterm=create-new-store * Shopify API Release 2020: https://www.shopify.in/partners/blog/shopify-api-release-january-2020 * What is Person Account in Salesforce ? https://help.salesforce.com/articleView?id=account_person.htm&type=5 * ────────────────────────────────────────────────────────────────────────────────────────────────── * @author Sumit * ────────────────────────────────────────────────────────────────────────────────────────────────── */ @RestResource(UrlMapping='/UpdateRefreshToken/*') global with sharing class UpdateRefreshToken { /** * Rotated-token write-back endpoint (the second of two; the other is * AuthenticateAllApexClass?objectname=UpdateRefreshToken). Both now share ONE implementation — * AuthenticateAllApexClass.persistRotatedToken — so they cannot drift apart or disagree about whether * a token was stored. * * What was wrong here: the write sat behind a chain of Schema/CheckAccessibility permission gates and * a CheckAccessibility-built dynamic SOQL string. This endpoint is reachable through the public Site * as the Guest User, for whom CheckAccessibility.isAccessible() returns an EMPTY STRING * (CheckAccessibility.cls:94-113). Any gate evaluating false, or the collapsed query, skipped the * write entirely — and because the method returned void with a swallowed catch, the caller still got * HTTP 200. Under mandatory Refresh Token Rotation the caller has already consumed the old token at * that point, so a dropped write silently strands the org on a superseded token. */ @HTTPPost global static void updatetoken(){ Restrequest request = restContext.request; Restresponse response = restContext.response; String JSONResponseBody = (request != null && request.requestBody != null) ? request.requestBody.toString().trim() : null; if (String.isBlank(JSONResponseBody)) { if (response != null) response.statusCode = 400; return; } Boolean stored = AuthenticateAllApexClass.persistRotatedToken(JSONResponseBody); if (response != null) { // Fail LOUD so the caller retries while its freshly rotated token is still the live one. response.statusCode = stored ? 200 : 500; response.addHeader('Content-Type', 'application/json'); response.responseBody = Blob.valueOf(stored ? '{"status":"ok"}' : '{"error":"token_not_stored","error_description":"rotated refresh token could not be persisted"}'); } } }