This guide provides a complete, step-by-step integration of Plaid's Transactions product using the Sandbox environment. It is intended to support both frontend and backend implementations in a language-agnostic format with optional language-specific hints. The goal is to enable an AI agent or developer to execute a fully functional Plaid integration, from user bank linking to retrieving transaction data.
Assumptions:
- The developer has a Plaid account and Sandbox
client_idandsecretare available. If not provided, please ask the users for it. - The application is able to make HTTP requests.
This document references Plaid's official documentation using markdown links.
Warning
This guide is designed to be used for the purpose of building a sample Plaid integration with the use of AI coding tools. You are solely responsible for ensuring the correctness, legality, security, privacy, and compliance of your own app and Plaid integration. This guide is provided under the MIT license and is provided as-is and without warranty of any kind.
Before starting the integration, check with the user and make sure:
- You have obtained your client ID and Sandbox secret from the dashboard.
- Your development environment can serve both frontend and backend logic. The backend must be able to securely manage sensitive credentials and handle API calls.
The Link Token is a short-lived token created server-side that configures the Plaid Link flow. This token must be generated on your backend and passed to the frontend.
POST /link/token/create
Send a POST request to Plaid with the following JSON payload:
{
"client_id": "<your-client-id>",
"secret": "<your-sandbox-secret>",
"client_name": "<your-app-name>",
"language": "en",
"country_codes": ["US"],
"user": {
"client_user_id": "unique-user-id"
},
"products": ["transactions"]
}Optional Parameters:
transactions.days_requested: Integer between 1 and 730. Default is 90.webhook: URL to receive transaction webhooks (recommended in production).redirect_uri: Required only for OAuth-based institutions.
{
"link_token": "link-sandbox-xxxxxxx",
"expiration": "2025-05-08T10:00:00Z"
}- Always generate a new Link Token for each session.
- This call must be done from a secure server environment.
Use the link_token generated in Step 1 to initiate the Plaid Link flow on the frontend.
And use the link as follows
<script src="https://cdn.plaid.com/link/v2/stable/link-initialize.js"></script>or React SDK
npm install --save react-plaid-link
const handler = Plaid.create({
token: "<LINK_TOKEN_FROM_BACKEND>",
onSuccess: function (public_token, metadata) {
// Send the public_token to backend
},
onExit: function (err, metadata) {
// Handle user exit or error
},
});
handler.open();user_good/pass_good– Successful linkuser_transactions_dynamic/ any password – Simulates real-time updates
After the user completes the Link flow, your frontend receives a public_token. This must be exchanged on your backend for an access_token, which is used for authenticated Plaid API requests.
POST /item/public_token/exchange
{
"client_id": "<your-client-id>",
"secret": "<your-sandbox-secret>",
"public_token": "<token-from-frontend>"
}{
"access_token": "access-sandbox-xxxxxxx",
"item_id": "item-id-123",
"request_id": "request-id"
}Store
access_tokensecurely on your backend. Never expose it to the frontend.
This endpoint supports incremental updates and efficient polling.
{
"client_id": "<your-client-id>",
"secret": "<your-sandbox-secret>",
"access_token": "<access_token>"
}{
"added": [...],
"modified": [...],
"removed": [...],
"next_cursor": "cursor-value",
"has_more": false
}Save next_cursor to resume syncs. If has_more is true, repeat call with cursor.
cursor = ""
while True:
response = transactions_sync(cursor)
process(response.added)
if not response.has_more:
break
cursor = response.next_cursor- Use
transactions/syncto keep user data fresh. - Retry on
PRODUCT_NOT_READYerrors. - Respect rate limits and add exponential backoff.
- Do NOT log access tokens OR API credentials.
- Store access tokens securely in the backend database, do not save the access token in the frontend.
- If to build a prototype for simplicity, you could maintain an in memory mapping between the access token and user_id. You can create an endpoint
/api/update_access_tokenso that you can update the access token for a specific user id. - Tokens persist indefinitely unless manually removed or revoked.
- Always validate request origin and authenticate client calls.
- Log all errors and exceptions with enough context to debug issues, but never log sensitive credentials or tokens.