
Query the Chart of Accounts by account type and active status (status='all' includes inactive), or with a raw SQL-like query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters. maxresults and start_position apply to both. Paginated.
Retrieve comprehensive account details by ID including name, type, sub-type, classification, current balance, parent account, and account number.
Create Chart of Accounts entry. Specify name, account type (Bank, Other Current Asset, Fixed Asset, etc.), account sub-type, and optional description, account number, or parent account for hierarchy.
Update account with new name, description, account number, or active status. Uses optimistic locking with sync_token. Cannot change account type.
Get one bill payment by ID: vendor, pay type, paying account, the bills it covers (Line.LinkedTxn), total and SyncToken. Use querybillpayments to find IDs. For customer payments received, use get_payment.
List or search payments made against vendor bills. Server filters: vendorid (queryvendors), startdate, enddate, docnumber. paytype and billid (querybills) filter each fetched page, so keep paging with nextstartposition. Or pass a raw query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignored_filters.
Pay one or more of a vendor's bills by check or credit card. Needs vendorid (queryvendors), the bills as lines with txnid (querybills, status 'Payable'), totalamt, and paytype with bankaccountid or creditcardaccountid (queryaccounts). A/P account from queryaccounts, department from querydepartments.
Change a bill payment. Only the fields you pass change; lines, if passed, replace all lines (pass totalamt with them). Needs billpaymentid and the current synctoken from getbillpayment or querybillpayments. To cancel a payment use voidbillpayment or deletebillpayment instead.
Void a bill payment: it stays on record with its total zeroed and lines cleared, and the bills it paid become payable again. Needs billpaymentid and the current synctoken from getbillpayment or querybillpayments. Use deletebill_payment to remove it entirely.
Permanently delete a bill payment; the bills it paid become payable again. Needs billpaymentid and the current synctoken from getbillpayment or querybillpayments. Use voidbill_payment to keep a zeroed record.
Query bills by vendor, payment status (Payable/Paid) and date range, or with a raw SQL-like query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters. maxresults and start_position apply to both. Paginated.
Retrieve comprehensive bill details by ID including vendor info, line items with account/item details, amounts, due date, and balance information.
Create bill record for vendor with line items for expenses or items. Specify vendor, transaction date, line items with account or item details, and optional due date. Line ClassRef, TaxCodeRef and DepartmentRef IDs come from queryclasses, querytaxcodes and querydepartments.
Update bill with new vendor, line items, dates, or amounts. Uses optimistic locking with sync_token.
Delete bill by ID permanently. Uses optimistic locking with sync_token.
Get one class by ID: name, parent, active state and SyncToken. Classes tag transactions or lines (ClassRef) by business segment. Use query_classes to find class IDs.
List or search classes, e.g. to find the ClassRef ID for an invoice, bill or expense line. Filters: namecontains, status (active by default; 'all' includes deactivated). Paginate with startposition and nextstartposition, or pass a raw query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignored_filters.
Create a class, or a subclass when parentclassid is set (use queryclasses to find the parent). Returns the new class ID for ClassRef. QuickBooks has no class delete: deactivate with updateclass active=false.
Rename, re-parent, deactivate (active=false) or reactivate a class. Only the fields you pass change. Needs classid and the current synctoken from getclass or queryclasses. This is also how to remove a class: QuickBooks has no class delete.
Query customers by active status (status='all' includes inactive), or with a raw SQL-like query for name, balance or other filters. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters. maxresults and start_position apply to both. Paginated.
Retrieve comprehensive customer details by ID including contact info, billing and shipping addresses, payment terms, balance info, tax settings, and metadata. Parameters: customer_id (required string). Essential for customer management, invoice creation, and reporting. Requires OAuth 2.0 with accounting scope.
Create customer with contact info, addresses, and settings. Parameters: name (required), companyname, displayname, email, phone, billaddr, shipaddr, taxable, openbalance, openbalancedate, creditlimit. DisplayName must be unique.
Update customer with new contact info, addresses, and settings. Uses optimistic locking with synctoken. Parameters: id (required), synctoken (required), name, companyname, email, phone, addresses, taxable, active, creditlimit.
Soft delete customer by setting status to inactive. Preserves historical data and transaction references. Parameters: customerid (required), synctoken (required). Cannot delete customers with outstanding balances.
Get one department by ID: name, parent, active state and SyncToken. Departments tag transactions (DepartmentRef) by location, such as a store or region. Use query_departments to find department IDs.
List or search departments (locations), e.g. to find the DepartmentRef ID for an invoice, bill or expense. Filters: namecontains, status (active by default; 'all' includes deactivated). Paginate with startposition and nextstartposition, or pass a raw query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignored_filters.
Create a department (location), or a sub-department when parentdepartmentid is set (use querydepartments to find the parent). Returns the new ID for DepartmentRef. QuickBooks has no department delete: deactivate with updatedepartment active=false.
Rename, re-parent, deactivate (active=false) or reactivate a department. Only the fields you pass change. Needs departmentid and the current synctoken from getdepartment or querydepartments. This is also how to remove a department: QuickBooks has no department delete.
Diagnostic tool to check QuickBooks authentication configuration.
List or search employees by name to find an employee ID, e.g. the entityid (entitytype 'Employee') for an expense in createpurchase. Returns IDs and names only. Filters: namecontains, status. Paginate with startposition, or pass a raw query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters.
Query estimates by customer, status (Accepted/Closed/Pending/Rejected/Converted) and date, or with a raw SQL-like query. Use either query or the customer/date filters, not both: those are ignored when query is set and listed in ignoredfilters. status, maxresults and start_position apply to both. Paginated.
Retrieve comprehensive estimate details by ID including customer info, line items with products/services, amounts, transaction date, expiration date, and acceptance status.
Create sales estimate for customer with line items. Specify customer, line items with products/services, transaction date, optional expiration date, and customer memo. Line ClassRef, TaxCodeRef and DepartmentRef IDs come from queryclasses, querytaxcodes and querydepartments.
Update estimate with new line items, dates, customer memo, or addresses. Uses optimistic locking with sync_token.
Delete estimate by ID permanently. Uses optimistic locking with sync_token.
Send estimate via email to customer. Specify estimate ID; email_address is optional -- omit to send to the customer's on-file BillEmail instead of overriding it. QuickBooks Online's send endpoint does not support a custom subject or message body.
Query invoices by customer, email delivery status (NotSet/NeedToSend/EmailSent, not payment status) and date, or with a raw SQL-like query. Use either query or the customer/date filters, not both: those are ignored when query is set and listed in ignoredfilters. status, maxresults and start_position apply to both. Paginated.
Retrieve comprehensive invoice details by ID including customer info, line items with quantities and amounts, payment status, delivery info, tax calculations, and financial totals. Parameters: invoice_id (required string). Essential for invoice management and financial analysis.
Create invoice with line items, customer details, and financial settings. Parameters: customerid (required), lineitems (required array), txndate (YYYY-MM-DD), duedate, docnumber, privatenote, customermemo, emailaddress. Auto-calculates taxes and balances. Line ClassRef, TaxCodeRef and DepartmentRef IDs come from queryclasses, querytaxcodes and querydepartments.
Modify existing invoice with updated line items, financial details, and settings. Supports updating customer refs, line items, dates, invoice numbers, and notes. Uses optimistic locking with synctoken. Parameters: id (required), synctoken (required), customerid, lineitems, txndate, duedate, doc_number. Cannot update paid/voided invoices. Requires OAuth 2.0 with write permissions.
Void invoice while maintaining audit trail. Preserves historical records but removes from accounts receivable. Parameters: id (required), sync_token (required). Cannot void paid invoices.
Send invoice via email to customer. Includes PDF and payment portal links. Parameters: invoiceid (required), emailaddress (optional -- omit to send to the customer's on-file BillEmail instead of overriding it). QuickBooks Online's send endpoint does not support a custom subject or message body.
Query products and services by type (Service/Inventory/NonInventory/Category) and active status (status='all' includes inactive), or with a raw SQL-like query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters. maxresults and start_position apply to both. Paginated.
Retrieve comprehensive item details by ID including name, description, SKU, unit price, purchase cost, income/expense accounts, inventory tracking, and quantity on hand. Parameters: item_id (required string). Essential for invoice line item details, inventory checks, and price lookups. Requires OAuth 2.0 with com.intuit.quickbooks.accounting scope.
Create item for products/services. Requires name, type (Service/Inventory/NonInventory/Category), and type-specific accounts. Inventory needs assetaccountid. Supports inventory tracking, SKU, pricing. Type cannot be changed after creation. Essential for product catalogs and invoices.
Update item name, description, SKU, pricing, accounts, or status. Requires id and sync_token for optimistic locking. Sparse update (only provided fields change). Type cannot change after creation. Use Inventory Adjustments for quantity changes. Essential for price and status updates.
Delete an item by marking it as inactive (soft delete). Items cannot be permanently deleted if they have been used in transactions. Inactive items are hidden from dropdowns but remain in historical records. Parameters: itemid (required), synctoken (required). Essential for item lifecycle management and catalog cleanup. Requires OAuth 2.0 with com.intuit.quickbooks.accounting scope.
List or search payment methods (Cash, Check, Visa) to find the paymentmethodid for createpurchase, updatepurchase, createpayment or updatepayment. Filters: namecontains, type (CREDITCARD or NONCREDITCARD), status. Paginate with startposition, or pass a raw query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters.
Query customer payments by customer and date range, or with a raw SQL-like query for amount or other filters. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters. maxresults and start_position apply to both. Paginated.
Retrieve comprehensive payment details by ID including customer info, payment method, line items showing invoice applications, amounts applied and unapplied.
Create payment record for customer against invoices. Specify total amount, customer, payment method, and line items linking to invoices. Auto-calculates unapplied amounts. Use querypaymentmethods for paymentmethodid.
Update payment with new amount, method, or invoice applications. Uses optimistic locking with synctoken. Use querypaymentmethods for paymentmethod_id.
Delete payment by ID. Uses optimistic locking with sync_token.
Get one expense (purchase) by ID: payment type, paid-from account, payee, lines, total and SyncToken. Use querypurchases to find purchase IDs. Bills paid later are separate: use getbill.
List or search expenses (cash, check and credit-card purchases). Server filters: startdate, enddate, docnumber. paymenttype, accountid and entityid filter each fetched page, so keep paging with nextstartposition. Or pass a raw query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignored_filters.
Record an expense paid by cash, check or credit card (a credit-card refund with credit=true). Needs accountid (queryaccounts) and lines with an expense account (queryaccounts) or item (queryitems). Payee from queryvendors/querycustomers/queryemployees, payment method from querypaymentmethods; class, tax code, department from queryclasses, querytaxcodes, query_departments.
Change an expense. Only the fields you pass change; lines, if passed, replace all lines. Needs purchaseid and the current synctoken from getpurchase or querypurchases. IDs come from the same lookups as create_purchase.
Permanently delete an expense (purchase). Needs purchaseid and the current synctoken from getpurchase or querypurchases.
Run a financial report: ProfitAndLoss, BalanceSheet, CashFlow, TrialBalance, GeneralLedger, AgedReceivables/AgedPayables (aging), CustomerSales, ItemSales, TransactionList and more. A param the report does not take is rejected. Filter IDs: querycustomers, queryvendors, queryitems, queryclasses, querydepartments, queryaccounts. Capped at 400,000 cells; narrow the period if hit.
Get one sales tax code by numeric ID with the tax rates it groups. Pass the ID as TaxCodeRef on invoice, bill, estimate or expense lines. Use querytaxcodes to find IDs; the TAX and NON pseudo codes appear there but cannot be read by ID.
List or search sales tax codes, e.g. to find the TaxCodeRef ID for a line. Filters: namecontains, status; or pass a raw query. Paged client-side with maxresults and startposition (QuickBooks ignores paging on tax codes). Create a new code with createtaxcode. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters.
Create a sales tax code through TaxService, from existing tax rates (taxrateid, see querytaxrates) and/or new ones (name, ratevalue, taxagencyid from querytax_agencies). May be rejected on US companies using Automated Sales Tax. QuickBooks has no API to delete a tax code.
Get one tax rate by ID: percentage, tax agency and active state. Tax rates are grouped into tax codes; use querytaxrates to find rate IDs.
List or search tax rates, e.g. to reuse an existing rate in createtaxcode. Filters: namecontains, agencyid (from querytaxagencies), status. Paginate with startposition and nextstartposition, or pass a raw query. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters.
Get one tax agency (the authority a tax rate is owed to) by ID. Use querytaxagencies to find agency IDs.
List tax agencies, e.g. to find the taxagencyid for a new rate in createtaxcode. QuickBooks filters tax agencies only by Id, so there are no structured filters; paginate with startposition and nextstart_position, or pass a raw query.
Create a tax agency by display name, to receive new tax rates in createtaxcode. US companies show only system-created agencies in the QuickBooks UI. QuickBooks supports no update or delete of a tax agency, so it cannot be removed through the API.
Get one tax classification (an item tax category used by Automated Sales Tax and non-US tax regimes) by ID. Use querytaxclassifications to find IDs.
List tax classifications. The full list runs to thousands of rows, so start with level=1, then pass a row's id as parentid to list its children. Paged client-side with maxresults and start_position.
Get one tax payment or refund made against a filed tax return, by ID. Available on AU, CA and UK companies only; other regions get error 5030. Use querytaxpayments to find IDs.
List tax payments and refunds made against filed tax returns. AU, CA and UK companies only; other regions get error 5030. Paginate with startposition and nextstart_position, or pass a raw query.
Validate QuickBooks Online credentials by making a test API call. Returns success status and message. Use this to verify credentials and realm ID are valid.
Query vendors by active status (status='all' includes inactive), or with a raw SQL-like query for name or other filters. Use either query or the named filters, not both: named filters are ignored when query is set and listed in ignoredfilters. maxresults and start_position apply to both. Paginated.
Retrieve comprehensive vendor details by ID including contact information, addresses, email, phone numbers, tax identifier, balance, and 1099 status.
Create vendor record with display name, contact details, billing address, email, phone, tax identifier, and 1099 settings. Display name is required.
Update vendor with new contact details, address, email, phone, tax info, or active status. Uses optimistic locking with sync_token.
Delete vendor by ID. Uses optimistic locking with sync_token.

In an mcp.json file, add the configuration below, and restart Cursor.
Learn more in the official documentation ↗
1{
2 "mcpServers": {
3 "agent-handler": {
4 "url": "https://ah-api-develop.merge.dev/api/v1/tool-packs/{TOOL_PACK_ID}/registered-users/{REGISTERED_USER_ID}/mcp",
5 "headers": {
6 "Authorization": "Bearer yMt*****"
7 }
8 }
9 }
10}
11Open your Claude Desktop configuration file and add the server configuration below. You'll also need to restart the application for the changes to take effect.
Make sure Claude is using the Node v20+.
Learn more in the official documentation ↗
1{
2 "mcpServers": {
3 "agent-handler": {
4 "command": "npx",
5 "args": [
6 "-y",
7 "mcp-remote@latest",
8 "https://ah-api-develop.merge.dev/api/v1/tool-packs/{TOOL_PACK_ID}/registered-users/{REGISTERED_USER_ID}/mcp",
9 "--header",
10 "Authorization: Bearer ${AUTH_TOKEN}"
11 ],
12 "env": {
13 "AUTH_TOKEN": "yMt*****"
14 }
15 }
16 }
17}Open your Windsurf MCP configuration file and add the server configuration below.
Click on the refresh button in the top right of the Manage MCP server page or in the top right of the chat box in the box icon.
Learn more in the official documentation ↗
1{
2 "mcpServers": {
3 "agent-handler": {
4 "command": "npx",
5 "args": [
6 "-y",
7 "mcp-remote@latest",
8 "https://ah-api.merge.dev/api/v1/tool-packs/<tool-pack-id>/registered-users/<registered-user-id>/mcp",
9 "--header",
10 "Authorization: Bearer ${AUTH_TOKEN}"
11 ],
12 "env": {
13 "AUTH_TOKEN": "<ah-production-access-key>"
14 }
15 }
16 }
17 }In Command Palette (Cmd+Shift+P on macOS, Ctrl+Shift+P on Windows), run "MCP: Open User Configuration".
You can then add the configuration below and press "start" right under servers. Enter the auth token when prompted.
Learn more in the official documentation ↗
1{
2 "inputs": [
3 {
4 "type": "promptString",
5 "id": "agent-handler-auth",
6 "description": "Agent Handler AUTH_TOKEN", // "yMt*****" when prompt
7 "password": true
8 }
9 ],
10 "servers": {
11 "agent-handler": {
12 "type": "stdio",
13 "command": "npx",
14 "args": [
15 "-y",
16 "mcp-remote@latest",
17 "https://ah-api-develop.merge.dev/api/v1/tool-packs/{TOOL_PACK_ID}/registered-users/{REGISTERED_USER_ID}/mcp",
18 "--header",
19 "Authorization: Bearer ${input:agent-handler-auth}"
20 ]
21 }
22 }
23}Whether you're an engineer experimenting with agents or a product manager looking to add tools, you can get started for free now