Amazon Cognito
Authentication
Cloud Computing
Serverless
AWS Services

How to use Amazon Cognito without Amplify

System Design practice on Codemia

Work through 120+ system design problems with detailed solutions, from rate limiters to multi-region storage.

Practice system design

Introduction

Amplify is a convenient wrapper around Amazon Cognito, but it is not required. If you want tighter control over authentication flows, bundle size, or framework integration, you can talk to Cognito directly through the AWS SDK and standard HTTP APIs.

The Pieces You Actually Need

For most applications, Cognito usage without Amplify comes down to four parts:

  • a User Pool for user accounts,
  • an App Client for your application,
  • optional Hosted UI settings if you want OAuth sign-in,
  • direct SDK calls for sign-up, sign-in, token refresh, and password reset.

If you are building a browser or mobile app, do not create the app client with a secret unless you have a backend that can safely hold it. Public clients should avoid secrets because the client code is visible to users.

Direct Sign-In With the AWS SDK

A straightforward pattern is to use the Cognito Identity Provider API directly. The example below signs in a user with username and password using the JavaScript AWS SDK v3.

javascript
1import {
2  CognitoIdentityProviderClient,
3  InitiateAuthCommand,
4} from "@aws-sdk/client-cognito-identity-provider";
5
6const client = new CognitoIdentityProviderClient({ region: "us-east-1" });
7
8async function signIn(username, password) {
9  const command = new InitiateAuthCommand({
10    AuthFlow: "USER_PASSWORD_AUTH",
11    ClientId: process.env.COGNITO_CLIENT_ID,
12    AuthParameters: {
13      USERNAME: username,
14      PASSWORD: password,
15    },
16  });
17
18  const response = await client.send(command);
19  return response.AuthenticationResult;
20}
21
22signIn("[email protected]", "CorrectHorseBatteryStaple1!")
23  .then((tokens) => console.log(tokens.IdToken))
24  .catch((error) => console.error(error));

This returns the token set if the app client allows the chosen auth flow. In many cases, USER_PASSWORD_AUTH is the simplest way to start, especially for server-side code or controlled applications.

Sign-Up and Confirmation

User registration is also a direct API call. You create the user and then confirm the verification code sent by email or SMS.

javascript
1import {
2  CognitoIdentityProviderClient,
3  SignUpCommand,
4  ConfirmSignUpCommand,
5} from "@aws-sdk/client-cognito-identity-provider";
6
7const client = new CognitoIdentityProviderClient({ region: "us-east-1" });
8
9async function register(username, password, email) {
10  await client.send(
11    new SignUpCommand({
12      ClientId: process.env.COGNITO_CLIENT_ID,
13      Username: username,
14      Password: password,
15      UserAttributes: [
16        { Name: "email", Value: email },
17      ],
18    })
19  );
20}
21
22async function confirm(username, code) {
23  await client.send(
24    new ConfirmSignUpCommand({
25      ClientId: process.env.COGNITO_CLIENT_ID,
26      Username: username,
27      ConfirmationCode: code,
28    })
29  );
30}

This direct approach gives you full control over the UI and error handling instead of accepting Amplify's abstraction.

Working With Tokens

After sign-in, Cognito returns an ID token, access token, and usually a refresh token. The ID token describes the user. The access token is used for authorization against Cognito-aware APIs. The refresh token is used to get new short-lived tokens without asking the user to log in again.

In a web app, store tokens carefully. Prefer an HTTP-only cookie strategy if you have a backend. If the app is purely client-side, minimize exposure and be disciplined about expiry and logout handling.

For backend APIs, verify the JWT before trusting it. That step is independent of Amplify. The important rule is simple: Cognito issues the token, but your application is still responsible for validating it.

Hosted UI Without Amplify

If you want social login or OAuth redirect flows, you can still use Cognito's Hosted UI without Amplify. In that setup, Cognito handles the login screen and redirects back to your app with an authorization code or tokens, depending on the flow you configured.

That route is often simpler than building password screens yourself when you need:

  • Google or Apple sign-in,
  • enterprise identity federation,
  • a standard OAuth redirect workflow,
  • less custom password-handling code.

When Going Without Amplify Makes Sense

Direct Cognito integration is useful when:

  • you already have an existing frontend architecture,
  • you want smaller dependencies,
  • you prefer explicit SDK calls,
  • you need custom UI and error handling,
  • you only use Cognito and do not want the rest of Amplify.

The tradeoff is that you must wire more pieces yourself, especially token storage, session refresh, and redirect handling.

Common Pitfalls

The most common problem is using an app client secret in a browser app. Secrets belong on the server, not in client-side JavaScript.

Another issue is enabling the wrong auth flows on the Cognito app client. If USER_PASSWORD_AUTH is not allowed, the sign-in request fails even though the code looks correct.

Teams also forget that Cognito authentication and JWT validation are separate concerns. Getting a token from Cognito is only half the job; your backend still needs to verify it before authorizing requests.

Summary

  • Amplify is optional; Cognito can be used directly through the AWS SDK.
  • The core pieces are a User Pool, an App Client, and the right auth flow settings.
  • Use direct API calls for sign-up, confirmation, sign-in, and token refresh.
  • Avoid app client secrets in public client applications.
  • Validate Cognito-issued tokens in your backend instead of trusting them blindly.

Related reading
Course
Beginner
27 lessons
10 hours
System Design Fundamentals

Build a strong foundation in designing scalable, reliable distributed systems.

View the course
Track what you have practised

A free account saves your progress, solutions and study plan across every problem on Codemia.

System Design practice on Codemia

Work through 120+ system design problems with detailed solutions, from rate limiters to multi-region storage.

Practice system design

All Rights Reserved.