API ReferenceChangelog
API Reference

Recurring transaction guide

Understand how we identify recurring tansactions

ⓘ Reading Time: 5 mins

Spade’s recurrence flag leverages transaction history and merchant information to identify recurring spend.

Recurrence flagging is not enabled by default. To request access, please contact us at [email protected]. Please note - enabling this feature may add ~5ms of latency to your enrichment requests.

Overview

Spade defines recurring transactions as spend that happens on a consistent basis to a specific merchant (often via a subscription). Examples of recurring transactions flagged by Spade include subscription payments to Netflix and a Con Edison electricity bill - shopping at the same grocery store on a regular basis is not considered a recurring transaction.

Spade uses a combination of merchant data and user transaction history to determine if a specific transaction is recurring.

Understanding Recurrence Data

Spade’s recurring transaction flag includes the following fields:

  • intervalDays: The number of days between recurring transactions
  • intervalType: The type of recurrence pattern (weekly, biweekly, monthly, quarterly, etc.)
  • nextPaymentExpected: The predicted date of the next payment in this pattern
  • recentRecurrences: An array of up to 5 recent transactions in this pattern, including:
    • amount: The transaction amount
    • occurredAt: Timestamp of when the transaction occurred
    • enrichmentId: Spade's unique identifier for the enrichment
    • transactionId: Your original transaction identifier

Getting started

To get started:

  • Ensure this feature is enabled by contacting [email protected]
  • Verify that your integration includes the following:
    • Unique and consistent ‘userId’ parameters
    • Correct ‘occurredAt’ dates
    • Accurate transaction ‘amount’

In order to get the best results, we recommend sending at least 3 months of backfilled transactions with the correct occurredAt dates (not the date the transaction was backfilled). For historical recurring transactions, Spade needs 3 or more transactions with matching characteristics to establish a recurring pattern. Please contact your account representative to discuss backfill approach.

Testing for Recurring Transactions

Spade's API allows you to detect recurring transactions through our enrichment endpoints. Here's how to get started:

1. Send Transaction Data

First, send your first transaction to our enrichment endpoint:

import requests

raw_transaction = {
   "amount": "22.99",
   "cardId": null,
   "userId": "user_1234",
   "location": {
      "city": "LOS GATOS",
      "region": "CA",
      "country": "USA"
   },
   "occurredAt": "2024-06-01",
   "categoryCode": "4899",
   "categoryType": "MCC",
   "currencyCode": "USD",
   "merchantName": "NETFLIX.COM",
   "transactionId": "transaction_1"
}

response = requests.post("https://east.sandbox.spade.com/transactions/enrich", json=raw_transaction, headers={"X-Api-Key": "<Your API Key Here>"})
enriched_transaction = response.json()

print(enriched_transaction)

2. Check Recurrence Information

As the previous request is one that Spade had predicted to be a recurring transaction (subscription), the enrichment response will include a recurrenceInfo object for transactions that are part of a recurring pattern:

{
	"transactionInfo": {
		"type": "spending",
		"thirdParties": [],
		"spendingInfo": {
			"channel": {
				"value": "digital"
			}
		},
		"transactionId": "5678",
		"recurrenceInfo": {
			"intervalType": "monthly",
			"intervalDays": 30,
			"nextPaymentExpected": "2024-07-01",
			"recentRecurrences": null
		}
	},
  ...
}

Any transaction that is not part of a predicted or historical recurring pattern will have null for the recurrenceInfo object.

3. Send Additional Transaction Data

As you send additional transactions, you will see the recurrenceInfo object update with the new data:

import requests

raw_transaction = {
   "amount": "22.99",
   "cardId": null,
   "userId": "user_1234",
   "location": {
      "city": "LOS GATOS",
      "region": "CA",
      "country": "USA"
   },
   "occurredAt": "2024-07-01",
   "categoryCode": "4899",
   "categoryType": "MCC",
   "currencyCode": "USD",
   "merchantName": "NETFLIX.COM",
   "transactionId": "transaction_2"
}

response = requests.post("https://east.sandbox.spade.com/transactions/enrich", json=raw_transaction, headers={"X-Api-Key": "<Your API Key Here>"})
enriched_transaction = response.json()

print(enriched_transaction)

4. Check Recurrence Information

The enrichment response will now include a recentRecurrences object under the recurrenceInfo object:

{
	"transactionInfo": {
		"type": "spending",
		"thirdParties": [],
		"spendingInfo": {
			"channel": {
				"value": "digital"
			}
		},
		"transactionId": "transaction_2",
		"recurrenceInfo": {
			"intervalType": "monthly",
			"intervalDays": 30,
			"nextPaymentExpected": "2024-07-31",
			"recentRecurrences": [
				{
					"amount": 22.99,
					"enrichmentId": "227dd480-2bd5-4805-b88d-185c306ee9bb",
					"occurredAt": "2024-06-01 00:00:00+00:00",
					"transactionId": "transaction_1"
				}
			]
		}
	},
  ...
}

As you add additional recurring transactions, the recentRecurrences array will be updated with the new transactions, up to a maximum of 5.

In addition to predicting recurring transactions, Spade also uses historical transactions to find recurring patterns. For example, if you send transactions for a user on 2024-07-01, 2024-08-01, 2024-09-01, and 2024-10-01, all with similar amounts, Spade will use the historical data to determine if the transaction is recurring. If so, it will mark the last transaction as recurring, and the intervalType will be set to monthly.

Troubleshooting

Common reasons why transactions might not be recognized as recurring:

  • Transaction amounts that vary significantly between occurrences
  • Irregular timing (varying more than a few days from the expected pattern)
  • Missing or incorrect userId values
  • Insufficient transaction history

If you're not seeing expected recurring patterns, ensure that:

  1. The amount of the transactions are correct
  2. The userId is consistent across transactions
  3. The occurredAt dates reflect the actual transaction dates
  4. You've sent enough transaction history (at least 3 occurrences)