pwa-kit
pwa-kit copied to clipboard
[BUG] Reset Password is not working
Summary
When using "Reset Password" the app returns the error "Your access-token is invalid and could not be used to identify the API client.". This happens regardless if the email is known to the system or not.
Steps To Reproduce
- open https://pwa-kit.mobify-storefront.com/en-GB/login
- click "Forgot Password!"
- enter valid email
- click "Reset Password"
- see the error "Your access-token is invalid and could not be used to identify the API client."
Expected result
- no error message
Actual result
- error message "Your access-token is invalid and could not be used to identify the API client."
System Information (as applicable)
Browser: Chrome Version 97.0.4692.99 Node version: pwa-kit version: 1.3 Desktop OS: Mobile Device Info:
Happens on the official test system, on our test system and locally.
Additional information
I tried to trace down this to myself but was not successful.
It seems that the underlying call
https://{{short_code}}.api.commercecloud.salesforce.com/customer/shopper-customers/v1/organizations/{{organization_id}}/customers/password/actions/create-reset-token?siteId={{site_id}}
is executed with the SLAS token and this does not work. I can reproduce the same error in Postman.
The documentation actually says to use the AM based token (https://account.demandware.com/dwsso/oauth2/access_token). But this did also not work for me and returns
"Your access-token is valid, but you have no permissions to access the resource.".
The related OCAPI permission is set but there is no related AuthZ Scope that could be set.
Hi @stm-dschulz! This is a known issue/gap that the SLAS password reset flow currently doesn't work in the PWA.
My understanding is that the SLAS password reset endpoint (/customers/password/actions/create-reset-token?siteId={{site_id}}) doesn't support shopper JWT. This endpoint is for admins to reset password on behalf of shoppers.
I believe SLAS team is actively working on this issue. For now, if you need to implement this feature, you need to create a server side endpoint that grabs AM OAuth token, call the endpoint and create a password reset token, then you use that token to reset password using another endpoint /reset.
To offer an alternative, you can also bridge the current API gap using OCAPI hooks.
https://github.com/SalesforceCommerceCloud/ocapi_hooks_collection shows how to do this.
- It extends the
dw.ocapi.shop.customers.password_reset.afterPOSTto send a password reset email. - It extends
dw.ocapi.shop.auth.beforePOSTto accept the reset token and attempt to set the users password.
You can review the tests for the basic flow:
https://github.com/SalesforceCommerceCloud/ocapi_hooks_collection/blob/main/test/integration/ocapi/04_passwordReset.js
I'm going to leave this issue open until we've resolved it in the default generated PWA.
Hi @kevinxh , @johnboxall , thx for the reply.
We will use the OCAPI solution to fix this. Whats your opinion - makes sense to contribute this fix?
Hey @stm-dschulz,
I don't believe a fix can be contributed in the scope of this repo right now.
Going forward, one of three things will happen:
- SLAS will add a password reset feature which we will adopt in the PWA Kit. When the feature drops, a PR that integrates it would be accepted.
- We'll adopt a DW hooks cartridges that will always be deployed alongside the PWA Kit.
- The underlying SCAPI/OCAPI will change to remove the requirement for a non-shopper OAuth token.
Until one of these three things happen, I believe this issue is blocked.
If yah'll do end up going the OCAPI route, I'd appreciate if you upstreamed any changes to https://github.com/SalesforceCommerceCloud/ocapi_hooks_collection, as if we choose to formally adopt a hooks cartridge for PWA Kit, this will most likely be our starting point.
Hello @stm-dschulz Thank you for the feedback. We will be looking into this in the first half of 2023.
Quick note, the OCAPI Shop /customers/password_reset endpoint has "different" authentication than most other APIs and does not respect SLAS JWTs passed to it.
To call it, you'll need to use regular OCAPI Auth:
https://documentation.b2c.commercecloud.salesforce.com/DOC2/topic/com.demandware.dochelp/content/b2c_commerce/topics/account_manager/b2c_account_manager_add_api_client_id.html
A trick I commonly use is to create a "super" API Client that can be used both for SLAS and OCAPI calls.
To do this:
- Create an API Client in AM, noting it's client ID
- Create an API Client in SLAS, using the AM client ID
Thanks!
A following question is : what OCPI api is to be used to actually reset the password after obtaining the reset token using the afterPOST hook described above ?
Once "Environment Variables" ships in Managed Runtime ~2023 June, our recommended approach will likely to be to use the SLAS Password Reset API with a callback URI to MRT:
https://developer.salesforce.com/docs/commerce/commerce-api/guide/slas-password-reset.html
Then MRT can send the email using a configured email service provider.
Alternatively, you could set a B2C Commerce controller as callback URI, and use its email sending capabilities.
Environment Variables for Managed Runtime has now shipped: https://developer.salesforce.com/docs/commerce/pwa-kit-managed-runtime/guide/managed-runtime-administration.html#environment-variables
You can use environment variables to inject the Client ID + Secret of a SLAS Private client into your code, then create an Express.js handler to forward requests to the relevant password reset APIs and optionally send a password reset email through your ESP.
https://developer.salesforce.com/docs/commerce/commerce-api/guide/slas-password-reset.html
To fix the Password Reset functionality in your Progressive Web App (PWA), follow these steps: Step 1: Generate an Admin token by accessing the following URL: https://account.demandware.com/dw/oauth2/access_token Note: Make sure to set the scope in the request Body to SALESFORCE_COMMERCE_API:<tenantId> sfcc.shopper-customers.login Step 2: Once you have the token generated in Step 1, use it for Authorization and refer to the documentation provided at the following link: https://developer.salesforce.com/docs/commerce/commerce-api/references/shopper-customers?meta=getResetPasswordToken At this step, you will receive a resetToken, which will be used for the password reset process in Step 3. Step 3: Again, use the Token generated in Step 1(or generate a new one) for Authorization and follow the documentation provided at the following link: https://developer.salesforce.com/docs/commerce/commerce-api/references/shopper-customers?meta=resetPassword (edited)
Thanks Anmol Srivastava
Hello,
I am working on correcting the password reset functionality and I have tried implementing the above 3 steps. I am able to get the admin access token from the dwoauth/dwsso/oauth2/access_token call with the scope as mentioned in step one. However, when I try to use this token for authorization for step two /create-reset-token?siteId=SiteExample I am getting a 401 Unauthorized error "Your access-token is invalid and could not be used to identify the API client."
Does anyone know how I can fix this? And am I able to add an authorization header to the SCAPI packages/template-retail-react-app/app/commerce-api/hooks/useCustomer.js getResetPasswordToken call?
Thanks!
@lisa-mcgerr it seems like you may have not set up the access token correctly. But, as per @johnboxall's comment, you should be able to do this by following the SLAS Password Reset guide, which should not require an OCAPI access token.
Hi , still have this problem . does someone has working example how can I fix this 401 unauthorised error during "reset-password" flow ?