Automated Chase Bank Reconciliation to QuickBooks Online (n8n)

Streamline business accounting by syncing Chase transactions to QuickBooks using n8n's self-hosted privacy and advanced logic.

Tools: ChaseQuickBooks Online

Platform: n8n

Short Answer

A fully automated n8n workflow that polls Chase via Plaid (or an email parser), cleans the messy bank descriptions using n8n Expressions, and creates categorized Expenses in QuickBooks Online in real-time, complete with duplicate prevention.

The Problem

Chase does not provide a direct webhook for transaction events, forcing manual CSV imports or expensive third-party aggregators. This delay creates a gap in real-time cash flow visibility and increases the risk of manual data entry errors during month-end reconciliation.

The Outcome

A fully automated n8n workflow that polls Chase via Plaid (or an email parser), cleans the messy bank descriptions using n8n Expressions, and creates categorized Expenses in QuickBooks Online in real-time, complete with duplicate prevention.

Step-by-Step Guide

1. **Establish Credentials**: In n8n, go to 'Credentials' and create a 'Plaid API' account (for Chase access) and a 'QuickBooks Online OAuth2' account. 2. **Set Trigger**: Add a 'Schedule' node. Configure it to run every 6 hours to stay within API rate limits while maintaining near real-time data. 3. **Connect Chase (Plaid)**: Add a 'Plaid' node. Set the Resource to `Transactions` and the Operation to `Get`. Link your Chase account via the Plaid Link portal. 4. **Filter Cleared Transactions**: Use a 'Filter' node to check if `pending` is `false`. Only synced 'cleared' transactions to prevent double-counting when status changes. 5. **Data Transformation**: Add a 'Code' node. Use JavaScript to clean the `name` field (e.g., stripping out transaction IDs like 'SQ *' using `.replace()`). Map the `amount` to a positive value as QBO Expenses expect positive numbers for debits. 6. **Duplicate Check**: Add a 'QuickBooks Online' node. Use the `Find` operation to search for an Expense with the same `Transaction ID` (stored in the QBO 'Memo' or 'Reference' field). 7. **Conditional Logic (If)**: Add an 'If' node. If the 'Find' node returns no results, proceed to create the record. 8. **Create QuickBooks Expense**: Add another 'QuickBooks Online' node. Set the Resource to `Expense`. Map the cleaned name to the 'Account' or 'Entity' and the amount to the 'Total Amount' field. 9. **Category Mapping**: Use a 'Switch' node before the QBO node to map Chase categories (from Plaid) to your QuickBooks Chart of Accounts IDs. 10. **Error Handling**: Create a separate 'Error Trigger' workflow. Use the 'Execute Workflow' node to alert you via Slack if the Chase API token expires or QBO returns a 401 error.

Data Mapping

| Chase/Plaid Field | n8n Expression/Transformation | QuickBooks Online Field | | :--- | :--- | :--- | | `amount` | `{{ Math.abs($json.amount) }}` | Total Amount (Required) | | `date` | `{{ $json.date }}` | Payment Date | | `name` | `{{ $json.name.split('*')[0] }}` | Memo / Reference | | `transaction_id` | `{{ $json.transaction_id }}` | Private Note (for Dup Check) | | `category[0]` | `{{ $json.category == 'Food' ? '12' : '45' }}` | Account ID (Category) | | `Iso_currency_code`| `{{ $json.iso_currency_code }}` | Currency |

Gotchas & Failure Modes

• **Memory/State Management**: n8n doesn't automatically 'remember' the last synced transaction ID like Zapier. You must use the 'Wait' node or a 'Static Data' variable via the `getWorkflowStaticData('node')` function to store the last sync date. • **Rate Limiting**: QuickBooks Online API has strict throttling. If syncing hundreds of historical transactions, use the 'Split In Batches' node (batch size: 10) with a 1-second delay between batches. • **Amount Polarity**: Plaid returns expenses as positive numbers, but some bank export formats use negative. Always verify your source data and use `Math.abs()` in n8n expressions to ensure QBO receives positive values for 'Expense' objects. • **OAuth Token Expiry**: If self-hosting n8n, ensure your `WEBHOOK_URL` is correctly configured in your environment variables, or the QuickBooks OAuth callback will fail.

Verification Checklist

- [ ] **Test Node**: Execute the Plaid node individually to ensure it returns a valid JSON array of transactions. - [ ] **Expression Check**: Use the 'Expression' editor to verify that the Chase 'Description' is correctly parsed into a clean string. - [ ] **Dry Run**: Run the workflow with the QuickBooks node in 'Manual' mode or pointed to a QBO Sandbox environment. - [ ] **Duplicate Filter**: Run the workflow twice in succession to ensure the 'If' node successfully blocks the second run from creating a duplicate. - [ ] **Resource Check**: Verify in n8n 'Execution' logs that the memory usage did not spike during large data fetches.

Ready to Automate?

Build this automation with n8n in minutes.