Unable to pass SECRET_HASH value to cognito user pool from Gen 2 auth library signIn() method
Environment information
System:
OS: macOS 14.4.1
CPU: (8) arm64 Apple M1 Pro
Memory: 154.64 MB / 16.00 GB
Shell: /bin/zsh
Binaries:
Node: 20.15.0 - /usr/local/bin/node
Yarn: 1.22.22 - /usr/local/bin/yarn
npm: 10.7.0 - /usr/local/bin/npm
pnpm: undefined - undefined
NPM Packages:
@aws-amplify/backend: 1.0.4
@aws-amplify/backend-cli: 1.1.0
aws-amplify: 6.3.8
aws-cdk: 2.147.3
aws-cdk-lib: 2.147.3
typescript: 5.5.3
AWS environment variables:
AWS_STS_REGIONAL_ENDPOINTS = regional
AWS_NODEJS_CONNECTION_REUSE_ENABLED = 1
AWS_SDK_LOAD_CONFIG = 1
No CDK environment variables
Description
An Amazon Cognito user pool enabled with Client secret is imported to Amplify Gen 2 project.
import { defineBackend } from '@aws-amplify/backend';
import { auth } from './auth/resource';
import { data } from './data/resource';
/**
* @see https://docs.amplify.aws/react/build-a-backend/ to add storage, functions, and more
*/
const backend = defineBackend({
});
backend.addOutput({
auth: {
aws_region: "REGION",
user_pool_id: "USER_POOL_ID",
user_pool_client_id: "CLIENT_ID",
identity_pool_id: "IDENTITY_POOL_ID",
username_attributes: ["email"],
standard_required_attributes: ["email"],
user_verification_types: ["email"],
unauthenticated_identities_enabled: true,
password_policy: {
min_length: 8,
require_lowercase: true,
require_uppercase: true,
require_numbers: true,
require_symbols: true,
}
}
})
Unable to find any way to pass Secret_hash value to cognito using auth library signIn() or signUp() method.
Sample signIn()
import type { FormEvent } from "react"
import { Amplify } from "aws-amplify"
import { signIn } from "aws-amplify/auth"
import outputs from "../amplify_outputs.json"
Amplify.configure(outputs)
interface SignInFormElements extends HTMLFormControlsCollection {
email: HTMLInputElement
password: HTMLInputElement
}
interface SignInForm extends HTMLFormElement {
readonly elements: SignInFormElements
}
export default function App() {
async function handleSubmit(event: FormEvent<SignInForm>) {
event.preventDefault()
const form = event.currentTarget
// ... validate inputs
await signIn({
username: [form.elements.email](http://form.elements.email/).value,
password: form.elements.password.value,
options: {
authFlowType: "CUSTOM_WITH_SRP",
clientMetadata: {
secretHash: "IyW/XXX+pvk="
}
}
})
}
return (
<form onSubmit={handleSubmit}>
<label htmlFor="email">Email:</label>
<input type="text" id="email" name="email" />
<label htmlFor="password">Password:</label>
<input type="password" id="password" name="password" />
<input type="submit" />
</form>
)
}
Using above signUp() method, can see in browser console that the secretHash value is passed. However, still getting :
400 Bad Request :: Client is configured with secret but SECRET_HASH was not received".
Can you please advise if we can use Amplify Gen 2 with Cognito user pool having client enabled client secret ?
Hey👋 thanks for raising this! I'm going to transfer this over to our JS repository for better assistance 🙂
Hello, @sagshar5 and thanks for creating this issue. To address the question on Gen 2 support, this is NOT currently supported out of the box at this time. As such, we'll mark this as a feature request.
We'll follow up with any additional questions or updates we have on this from here, but feel free to add any additional context for use cases or implementations you're looking for in Gen 2 as well. Thanks!
@sagshar5, did you run into this only after upgrading to v6 or using Gen2?
Having same issue, does anyone know a workaround?
You have to disable the client secret when you create the userPool. Unfortunately you cannot disable the client secret for a created userPool as far as I can see.
This is very frustrating! Can't believe that amplify doesn't support the SECRET_HASH. With modern frameworks like NEXT.js that have a FE servers where the auth interactions occur.
The workaround we used was to use
import {
CognitoIdentityProviderClient,
InitiateAuthCommand,
} from "@aws-sdk/client-cognito-identity-provider"
@cwomack is there an update this on this? I'm running into the same issue. This just feels like a half baked solution. Pretty poor for AWS standards.
@zammitjames don't have any updates yet, but appreciate the feedback and additional comment on this. The more upvotes, followers, and comments we get from the community on feature requests like this help us gauge the interest.
I'll bring it back through to the team and if there's any further updates I'll follow up with another comment (likely after the holidays).
I recently encountered the same issue while integrating AWS Cognito with an Elastic Load Balancer (ELB). ELB requires the use of a client secret, but our ReactJS client cannot leverage Amplify to send this information directly with signIn(). This presents another use case for supporting SECRET_HASH, which I hope your team can take into consideration.
@Vinci08, thanks for adding this context to the issue. We're reviewing this internally as a feature request and will update with another comment on any progress or news regarding this.
I just encountered this and had to patch locally to get it working. It's also missing from sendCustomChallengeAnswer. For my purposes, I've overloaded clientMetadata to avoid changing the signature of the functions
https://github.com/wavey-ai/amplify-js/commit/a0fba1d1e01809592e1c0541cf37fdd885b9a1f6
I found this issue too, Why can't add the secret_hash into the signIn and confirmSignIn methods. Obviously, there need the param in some situations. And change it is so easy. Why don't change it?
Is there another workaround other than to create a new user-pool without client secret, and from a security stand point of view is that fine?
Hi @root-daemon,
We don't have enough knowledge for the difference yet. I have filed a ticket internally to consult with the service team. I'll keep you post for any updates.
ok so my approach above was wrong. It seems like client apps (of the public, mobile app sort) should not send a SECRET_HASH at all (as they need a client secret to be able to generate it). Instead, the recommended workaround seems @root-daemon to use an edge lambda to inject the SECRET_HASH (so, amplify would talk to your CloudFront proxy rather than Cognito directly). https://aws.amazon.com/blogs/security/protect-public-clients-for-amazon-cognito-by-using-an-amazon-cloudfront-proxy/
This still has some benefits to help ensure logins are from your own client and not a fraudulent one, as it can be combined with WAF, being a Cloudfront proxy.
Thanks @jbrough for sharing the information.
Hi @root-daemon Besides the doc shared above, you can also find the information you are looking for in this doc: https://docs.aws.amazon.com/cognito/latest/developerguide/user-pool-settings-client-apps.html
So, if you use their CFN to deploy the WAF application to Edge via the link above, you will need to modify it to use nodejs16.x as the lambda runtime. Above that will not work. Node 16 is deprecated and will be blocked on AWS in October - I'll create a new lambda template when I have time but I'm rolling with Node 16 atm. Btw, it works great once you use node 16.
https://aws-security-blog-content.s3.amazonaws.com/public/sample/876-Protect-unauthenticated-APIs-Cognito/CloudFront-WAF.yaml
Thanks for sharing this information and CFN template @jbrough!
If using SPA type then client secret for a created userPool is not seen and In hosted ui if Login pages unavailable. Please contact an administrator. The Cognito UI is a bit confusing sometimes. This is just one of the quirks. Click the left nav bar "Overview" (above "Applications") . This is the "overview" of the user pool where your app client is in. On the right side under "Recommendations", there is an icon for "Apply branding to your managed login pages" , click "Configure styles". I think you use Managed Login, click [Create a Style] button to create a new style and assign it to your 2nd app.
No further action from our side needed. Please refer to this document for more information. Thanks!
Hello @cwomack, just checking if this feature update has been pushed yet. I’m currently facing the same issue.