Skip to content
New ✕

Use best card + savings
offers on Purchases

Booking flights or buying snickers,
automatically view best rewards card, activate savings offers –
before you make the payment.

Uthrive

Uthrive

Consumer Business
    • BEST CREDIT CARDS
    • BEST BUSINESS CREDIT CARDS
    • Become a Credit Card Pro
      • Best Credit Cards
      • Best travel credit cards
      • Best Cash Back credit cards
      • Best No Annual Fee Credit Cards
      • Best balance transfer credit cards
      • Best 0% APR Credit Cards
      • Best Rewards Credit Cards
      • Best Airlines Credit Cards
      • Best Hotel Credit Cards
      • Best Credit Cards For groceries
      • Best Credit Cards For Streaming Services
      • Best Credit Cards For Gas
      • Best Credit Cards For Online Shopping
      • Best Credit Cards For Healthcare
      • Best Credit Cards
        • The Platinum Card® From American Express
        • American Express® Gold Card
        • Blue Cash Preferred® Card From American Express
        • Blue Cash Everyday® Card From American Express
        • Hilton Honors American Express Card
        • Chase Sapphire Preferred® Card
        • Chase Sapphire Reserve®
        • Chase Freedom Unlimited®
        • Southwest Rapid Rewards® Plus Credit Card
        • United Quest℠ Card
        • Capital One Venture Rewards Credit Card
        • Capital One Venture X Rewards Credit Card
        • Capital One VentureOne Rewards Credit Card
        • Capital One Quicksilver Cash Rewards Credit Card
        • Capital One SavorOne Cash Rewards Credit Card
      • Best travel credit cards
        • The Platinum Card® from American Express
        • Chase Sapphire Preferred® Card
        • Capital One Venture Rewards Credit Card
        • Citi Premier® Card
        • Capital One Venture X Rewards Credit Card
        Popular reads
        • Best Credit Cards for Travel Insurance
        • Unexpected Travel Expenses
        • Best Places to Travel for Christmas
        • Five Fantastic Ways to Earn Credit Card Points
        • Best Airbnb Credit Cards
      • Best Cash Back credit cards
        • Chase Freedom Unlimited®
        • Blue Cash Preferred® Card from American Express
        • Citi Double Cash® Card
        • Capital One Quicksilver Cash Rewards Credit Card
        Popular reads
        • Maximize Cash Back Rewards
        • Best Credit Cards That Help You Earn More
      • Best No Annual Fee Credit Cards
        • Capital One SavorOne Cash Rewards Credit Card
        • Blue Cash Everyday® Card from American Express
        • Delta SkyMiles® Blue American Express Card
        • United Gateway℠ Card
      • Best balance transfer credit cards
        • Chase Freedom Unlimited®
        • Blue Cash Everyday® Card from American Express
        • Capital One Quicksilver Cash Rewards Credit Card
        • Capital One SavorOne Cash Rewards Credit Card
        Popular reads
        • What Is A Balance Transfer
        • Balance Transfer Credit Card with Bad Credit
        • Balance Transfer Credit Card Mistakes
      • Best 0% APR Credit Cards
        • Chase Freedom Unlimited®
        • Blue Cash Everyday® Card from American Express
        • Citi Double Cash® Card
        • Capital One Quicksilver Cash Rewards Credit Card
      • Best Rewards Credit Cards
        • American Express® Gold Card
        • Chase Sapphire Preferred® Card
        • Capital One Venture Rewards Credit Card
        • Citi Premier® Card
        Popular reads
        • Maximize Your Credit Card Shopping Rewards
        • Things to buy with a Credit Card
        • Five Fantastic Ways to Earn Credit Card Points
      • Best Airlines Credit Cards
        • Delta SkyMiles® Platinum American Express Card
        • Delta SkyMiles® Gold American Express Card
        • United Quest℠ Card
        • United℠ Explorer Card
        • Southwest Rapid Rewards® Plus Credit Card
        Popular reads
        • Best Delta Credit Cards
        • Best American Airlines Credit Cards
        • Best Southwest Airlines Credit Cards
        • Best United Airlines Credit Cards
      • Best Hotel Credit Cards
        • The World of Hyatt Credit Card
        • Marriott Bonvoy Brilliant® American Express® Card
        • IHG One Rewards Premier Credit Card
        • Hilton Honors American Express Card
      • Best Credit Cards For groceries
        • Blue Cash Preferred® Card from American Express
        • Capital One SavorOne Cash Rewards Credit Card
        • Blue Cash Everyday® Card from American Express
      • Best Credit Cards For Streaming Services
        • Blue Cash Preferred® Card from American Express
        • Capital One SavorOne Cash Rewards Credit Card
        • Chase Sapphire Preferred® Card
        Popular reads
        • Best Credit Cards For Netflix
        • Best Disney Credit Cards
      • Best Credit Cards For Gas
        • Blue Cash Preferred® Card from American Express
        • Citi Premier® Card
        • Costco Anywhere Visa® Card By Citi
        • Chase Sapphire Preferred® Card
        • Blue Cash Everyday® Card from American Express
        Popular reads
        • Rewards Programs for Gas
        • Best Gas Credit Cards
      • Best Credit Cards For Online Shopping
        • Blue Cash Everyday® Card from American Express
        Popular reads
        • Best Stores For Holiday Shopping
        • Maximize Your Credit Card Shopping Rewards
      • Best Credit Cards For Healthcare
        • Chase Freedom Unlimited®
        • Capital One Venture Rewards Credit Card
        • Blue Cash Everyday® Card from American Express
      • American Express Business Credit Cards
      • Chase Business Credit Cards
      • Capital One Business Credit Cards
      • Bank Of America Business Credit Cards
      • American Express Business Credit Cards
        • The Business Platinum Card® From American Express
      • Chase Business Credit Cards
        • Ink Business Preferred® Credit Card
        • Ink Business Unlimited® Credit Card
      • Capital One Business Credit Cards
        • Capital One Spark Miles Business
        • Capital One Venture X Business
    • CREDIT CARD REWARD PROGRAMS
    • BEST AIRLINE REWARD PROGRAMS
    • BEST HOTEL REWARD PROGRAMS
    • Become a Credit Card Pro
      • American Express Membership Rewards
      • Chase Ultimate Rewards
      • Capital One Miles
      • Citi ThankYou Points
      • Bank Of America Travel Rewards
      • American Airlines AAdvantage Program
      • United Airlines MileagePlus
      • Delta SkyMiles
      • Southwest Rapid Rewards
      • American Airlines AAdvantage Program
        • Earn & Redeem American Airlines Miles
        • American Airlines Elite Status
        • Best American Airlines Credit Cards
        • American Airlines Baggage Fees
        • American Airlines Flight Credit
      • United Airlines MileagePlus
        • Earn & Use/Redeem United Miles
        • Best United Airlines Credit Cards
        • United Airlines Baggage Fees
        • United Airlines Partners
      • Delta SkyMiles
        • Earn & Redeem Delta Skymiles
        • Best Delta Credit Cards
        • Delta Medallion Status
        • Delta SkyMiles Amex Changes
      • Southwest Rapid Rewards
        • Use & Redeem Southwest Rapid Rewards
        • Southwest Transfer Points & Points Value
        • Best Southwest Airlines Credit Cards
        • Southwest Low Fare Calendar
      • Hyatt Rewards Program
      • Mariott Bonvoy Rewards Program
      • Hilton Rewards Program
      • Best Western Rewards Program
    • CARD OFFERS
    • BEST CARD FOR PURCHASES
    • REFER A FRIEND
    • Become a Credit Card Pro
      • Amex Offers
      • Chase Offers
      • Best Card For Amazon
      • Best Card For AirBnb
      • Best Card For Apple
      • Best Card For Costco
      • Best Card For Uber/Lyft
      • Best Card For Walmart
      • Best Card For Target
      • American Express Refer A Friend Bonuses
      • Capital One Refer A Friend Program
      • Chase Refer A Friend Bonuses
      • Citi Credit Card Refer A Friend
    • TRAVEL BENEFITS
    • SHOPPING BENEFITS
    • OTHER BENEFITS
    • Become a Credit Card Pro
      • Free Airport Lounge
      • Free Travel Insurance
      • No Foreign Transaction Fee
      • Hotel Credits
      • Free TSA PreCheck
      • Free Checked Bags
      • Free Global Entry
      • Free Priority Pass
      • Cash Back Offers
      • Purchase Protection
      • Extended Warranty
      • Buy Now Pay Later
      • Buy Now Pay Later
        • Buy Now, Pay Later Apps
        • Buy Now, Pay Later No Credit Check
      • Netflix/Hulu
      • Disney Bundle
      • Credit Cards With Cellphone Insurance
  • Log in
  • Sign up

Download Uthrive App

Scan with your phone camera to download
the Uthrive App.

Get Maximum Rewards + Savings
on Purchases.

Automatic best saving offer.
Use best card at checkout.
Get up to $800* back on online purchases.
Consumer Business
  • Get Uthrive App
  • Sign up
  • Log in
Plaid logo
Docs
Consumer Business
  • Introduction
  • Authentication
  • Endpoints
  • Errors
  • Schema Objects
  • Login
  • Contact Sales
Plaid logo
Docs
Go To Uthrive
Login|Contact Sales

Endpoints

Calculate Earned Rewards

Copy
POST /reward/earned

URL: https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/earned

Calculate earned credit card rewards for a provided list of transactions. Use this endpoint to show users how much reward value they’ve already received based on their spending history.

Authentication
  • Required.
  • Supply client-id and api-key headers with every request.
Request Headers
HeaderTypeRequiredDescription
client-idstringYesYour Uthrive client ID
api-keystringYesYour Uthrive API key
Content-TypestringYesapplication/json
Request Schema

The request body is a JSON object with an array of transaction objects.

FieldTypeRequiredDescription
transactionsarrayYesList of transaction objects

Each transaction object:

FieldTypeRequiredExample
transactionIdstringYes“12345”
transactionAmountnumberYes100.50
transactionDatestringYes“2023-10-01”
merchantstringYes“Amazon”
cardNamestringYes“Chase Sapphire Preferred”

Example Request

Copy
{
  "transactions": [
    {
      "transactionId": "12345",
      "transactionAmount": 100.50,
      "transactionDate": "2023-10-01",
      "merchant": "Amazon",
      "cardName": "Chase Sapphire Preferred"
    },
    {
      "transactionId": "67890",
      "transactionAmount": 250.75,
      "transactionDate": "2023-10-02",
      "merchant": "Walmart",
      "cardName": "American Express Blue Cash EveryDay"
    }
  ]
}
Response

Returns a JSON object with two main fields:

  • data: Contains the rewards breakdown
  • message: Status message
Example Success Response (200 OK)
Copy
{
  "data": {
    "earnedRewards": [
      {
        "transactionId": "67890",
        "transactionAmount": 250.75,
        "transactionDate": "2023-10-02",
        "merchant": "Walmart",
        "cardName": "American Express Blue Cash EveryDay",
        "rewardValue": 0.01,
        "rewardMultiplier": 1,
        "rewardAmount": 2.5075
      },
      {
        "transactionId": "12345",
        "transactionAmount": 100.5,
        "transactionDate": "2023-10-01",
        "merchant": "Amazon",
        "cardName": "Chase Sapphire Preferred",
        "rewardValue": 0.013,
        "rewardMultiplier": 1,
        "rewardAmount": 1.3065
      }
    ],
    "totalEarnedReward": 3.814
  },
  "message": "Success"
}
Response Field Details
FieldTypeDescription
earnedRewardsarrayList of calculated rewards, one per input transaction
totalEarnedRewardnumberSum of all reward values earned across the input transactions
messagestringOperation status message

Each item in earnedRewards:

FieldTypeDescription
transactionIdstringThe transaction’s unique reference
transactionAmountnumberSpend amount for this transaction
transactionDatestringPurchase date (YYYY-MM-DD)
merchantstringMerchant name
cardNamestringThe card used
rewardValuenumberDollar equivalent per point/mile for this card
rewardMultipliernumberMultiplier applied (depends on merchant/category)
rewardAmountnumberTotal reward value earned for the transaction
Error Responses
HTTP CodeMeaningExample Response
400Malformed input or missing fields{ “message”: “Invalid request body” }
401Authentication failed{ “message”: “Unauthorized” }
500Internal server error{ “message”: “Internal error” }
    cURL
    Copy
    curl -X POST "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/earned" \
      -H "Content-Type: application/json" \
      -H "client-id: YOUR_CLIENT_ID" \
      -H "api-key: YOUR_API_KEY" \
      -d '{
        "transactions": [
          {
            "transactionId": "12345",
            "transactionAmount": 100.50,
            "transactionDate": "2023-10-01",
            "merchant": "Amazon",
            "cardName": "Chase Sapphire Preferred"
          }
        ]
      }'
    
    NodeJS
    Copy
    const axios = require('axios');
    
    async function postEarnedRewards() {
      const url = 'https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/earned';
      const headers = {
        'Content-Type': 'application/json',
        'client-id': 'YOUR_CLIENT_ID',
        'api-key': 'YOUR_API_KEY'
      };
      const data = {
        transactions: [
          {
            transactionId: "12345",
            transactionAmount: 100.50,
            transactionDate: "2023-10-01",
            merchant: "Amazon",
            cardName: "Chase Sapphire Preferred"
          }
        ]
      };
    
      try {
        const response = await axios.post(url, data, { headers });
        console.log('Response:', response.data);
      } catch (error) {
        if (error.response) {
          console.error('API Error:', error.response.status, error.response.data);
        } else {
          console.error('Error:', error.message);
        }
      }
    }
    
    postEarnedRewards();
    
    Python
    Async Python example with aiohttp
    Copy
    pip install aiohttp
    import aiohttp
    import asyncio
    
    async def post_earned_rewards():
        url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/earned"
        headers = {
            "Content-Type": "application/json",
            "client-id": "YOUR_CLIENT_ID",
            "api-key": "YOUR_API_KEY"
        }
        data = {
            "transactions": [
                {
                    "transactionId": "12345",
                    "transactionAmount": 100.50,
                    "transactionDate": "2023-10-01",
                    "merchant": "Amazon",
                    "cardName": "Chase Sapphire Preferred"
                }
            ]
        }
    
        async with aiohttp.ClientSession() as session:
            async with session.post(url, json=data, headers=headers) as resp:
                print("Status code:", resp.status)
                response_json = await resp.json()
                print("Response body:", response_json)
    
    # Run the async function
    asyncio.run(post_earned_rewards())
    
    Java
    Using Spring RestTemplate
    Copy
    import org.springframework.http.*;
    import org.springframework.web.client.RestTemplate;
    import java.util.*;
    
    public class UthriveApiSpring {
        public static void main(String[] args) {
            RestTemplate restTemplate = new RestTemplate();
    
            String url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/earned";
    
            HttpHeaders headers = new HttpHeaders();
            headers.setContentType(MediaType.APPLICATION_JSON);
            headers.set("client-id", "YOUR_CLIENT_ID");
            headers.set("api-key", "YOUR_API_KEY");
    
            Map<String, Object> transaction = new HashMap<>();
            transaction.put("transactionId", "12345");
            transaction.put("transactionAmount", 100.50);
            transaction.put("transactionDate", "2023-10-01");
            transaction.put("merchant", "Amazon");
            transaction.put("cardName", "Chase Sapphire Preferred");
    
            Map<String, Object> reqBody = new HashMap<>();
            reqBody.put("transactions", Arrays.asList(transaction));
    
            HttpEntity<Map<String, Object>> entity = new HttpEntity<>(reqBody, headers);
    
            ResponseEntity<String> response = restTemplate.postForEntity(url, entity, String.class);
    
            System.out.println("Status code: " + response.getStatusCodeValue());
            System.out.println("Response body: " + response.getBody());
        }
    }
    
    Java 11+ with Jackson for JSON construction

    If you prefer strong typing and JSON serialization

    Copy
    import com.fasterxml.jackson.databind.ObjectMapper;
    import java.net.URI;
    import java.net.http.*;
    import java.util.*;
    
    public class UthriveApiJackson {
        public static void main(String[] args) throws Exception {
            String url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/earned";
            HttpClient client = HttpClient.newHttpClient();
    
            Map<String, Object> transaction = new HashMap<>();
            transaction.put("transactionId", "12345");
            transaction.put("transactionAmount", 100.50);
            transaction.put("transactionDate", "2023-10-01");
            transaction.put("merchant", "Amazon");
            transaction.put("cardName", "Chase Sapphire Preferred");
    
            Map<String, Object> reqBody = new HashMap<>();
            reqBody.put("transactions", Arrays.asList(transaction));
    
            ObjectMapper mapper = new ObjectMapper();
            String jsonBody = mapper.writeValueAsString(reqBody);
    
            HttpRequest request = HttpRequest.newBuilder()
                    .uri(URI.create(url))
                    .header("Content-Type", "application/json")
                    .header("client-id", "YOUR_CLIENT_ID")
                    .header("api-key", "YOUR_API_KEY")
                    .POST(HttpRequest.BodyPublishers.ofString(jsonBody))
                    .build();
    
            HttpResponse<String> response = client.send(request, HttpResponse.BodyHandlers.ofString());
            System.out.println(response.statusCode());
            System.out.println(response.body());
        }
    }
    
    Android

    Android Example Using OkHttp

    1. Add OkHttp to Your build.gradle (Module):
    Copy
    dependencies {
        implementation 'com.squareup.okhttp3:okhttp:4.10.0'
    }
    1. Android Java code example
    Copy
    import android.os.Bundle;
    import androidx.appcompat.app.AppCompatActivity;
    import okhttp3.*;
    
    import org.json.JSONArray;
    import org.json.JSONObject;
    
    import java.io.IOException;
    
    public class MainActivity extends AppCompatActivity {
    
        private static final String URL = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/earned";
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
    
            // You may wish to run this inside an AsyncTask, background thread, or ViewModel (for production)
            new Thread(this::postUthriveEarnedReward).start();
        }
    
        private void postUthriveEarnedReward() {
            OkHttpClient client = new OkHttpClient();
    
            try {
                JSONObject transaction = new JSONObject();
                transaction.put("transactionId", "12345");
                transaction.put("transactionAmount", 100.50);
                transaction.put("transactionDate", "2023-10-01");
                transaction.put("merchant", "Amazon");
                transaction.put("cardName", "Chase Sapphire Preferred");
    
                JSONArray transactions = new JSONArray();
                transactions.put(transaction);
    
                JSONObject requestBodyJson = new JSONObject();
                requestBodyJson.put("transactions", transactions);
    
                RequestBody body = RequestBody.create(
                    requestBodyJson.toString(),
                    MediaType.get("application/json; charset=utf-8")
                );
    
                Request request = new Request.Builder()
                        .url(URL)
                        .post(body)
                        .addHeader("Content-Type", "application/json")
                        .addHeader("client-id", "YOUR_CLIENT_ID")
                        .addHeader("api-key", "YOUR_API_KEY")
                        .build();
    
                Response response = client.newCall(request).execute();
                if (response.isSuccessful() && response.body() != null) {
                    String responseStr = response.body().string();
                    runOnUiThread(() -> {
                        // Handle the API response (update UI, Toast, Log, etc.)
                        // Example:
                        System.out.println("Response: " + responseStr);
                    });
                } else {
                    runOnUiThread(() -> {
                        System.err.println("Error: " + response.code());
                    });
                }
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
    

    Best Practices

    • transactionId can be any string unique to a transaction in your system.
    • Ensure cardName matches Uthrive’s supported list for best accuracy.
    • The sum of rewardAmount fields will equal totalEarnedReward.

    Calculate Missed Rewards

    Copy
    POST /reward/missed

    URL: https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/missed

    Calculate missed rewards for a batch of transactions, showing how much additional reward value a user could have earned if they had used the optimal card—including both cards they already have and cards they may want to apply for.

    Authentication
    • Required.
    • Supply client-id and api-key headers with every request
    Request Headers
    HeaderTypeRequiredDescription
    client-idstringYesYour Uthrive client ID
    api-keystringYesYour Uthrive API key
    Content-TypestringYesapplication/json
    Request Body Schema
    FieldTypeRequiredDescription
    transactionsarrayYesList of transaction objects (see below)
    yourCardsarrayYesList of card names you currently hold

    Each transaction object:

    FieldTypeRequiredDescription
    transactionIdstringYesUnique ID
    transactionAmountnumberYesSpend amount
    transactionDatestringYesYYYY-MM-DD
    merchantstringYesMerchant name
    cardNamestringYesCard used

    yourCards is an array of card name strings (must match Uthrive’s supported cards list).

    Example Request

    Copy
    {
      "transactions": [
        {
          "transactionId": "12345",
          "transactionAmount": 100.5,
          "transactionDate": "2023-10-01",
          "merchant": "Amazon",
          "cardName": "Chase Sapphire Preferred"
        }
      ],
      "yourCards": [
        "American Express Platinum",
        "Chase Sapphire Preferred"
      ]
    }
    
    
    Success Response (200 OK)

    Returns a breakdown of:

    • missed rewards if a different card in the user’s wallet (yourCards) was used,
    • missed rewards if a potential new card (not in wallet) was used, and summary statistics.
    Copy
    {
      "data": {
        "missedRewards": [
          {
            "transactionId": "12345",
            "transactionAmount": 100.5,
            "transactionDate": "2023-10-01",
            "merchant": "Amazon",
            "cardName": "Chase Sapphire Preferred",
            "rewardAmount": 1.3065,
            "missedRewardYourCards": [
              {
                "cardId": 43,
                "cardName": "Capital One QuickSilver",
                "transactionId": "12345",
                "rewardValue": 0.01,
                "rewardMultiplier": 1.5,
                "missedReward": 0.201
              }
            ],
            "missedRewardNewCards": [
              {
                "cardId": 99,
                "cardName": "Amex Green",
                "transactionId": "12345",
                "rewardValue": 0.02,
                "rewardMultiplier": 2,
                "missedReward": 0.5
              }
            ],
            "bestCard": {
              "cardId": 99,
              "cardName": "Amex Green",
              "transactionId": "12345",
              "rewardValue": 0.02,
              "rewardMultiplier": 2,
              "missedReward": 0.5
            }
          }
        ],
        "overallMissedRewardsExisting": 0.201,
        "overallMissedRewardsNew": 0.5
      },
      "message": "Success"
    }
    Response Fields

    Top-level:

    FieldTypeDescription
    data.missedRewardsarrayList of per-transaction missed reward breakdowns
    data.overallMissedRewardsExistingnumberTotal missed by not using the best card you have
    data.overallMissedRewardsNewnumberTotal missed if you had access to all cards
    messagestringSuccess or error string

    Inside each object in missedRewards:

    FieldTypeDescription
    transactionIdstringThe transaction’s unique ID
    transactionAmountnumberSpend amount
    transactionDatestringPurchase date (YYYY-MM-DD)
    merchantstringMerchant
    cardNamestringThe card actually used for the transaction
    rewardAmountnumberRewards earned with the actual card used
    missedRewardYourCardsarrayMissed rewards for other cards you hold
    missedRewardNewCardsarrayMissed rewards if you had other (potential) cards
    bestCardobjectTheoretical card with maximum possible reward

    Each object in missedRewardYourCards and missedRewardNewCards:

    FieldTypeDescription
    cardIdintegerUthrive-internal card ID
    cardNamestringCard name
    transactionIdstringTransaction ID
    rewardValuenumber$ value per point/mile
    rewardMultipliernumberPoints multiplier
    missedRewardnumberExtra dollars you would have earned
      cURL
      Copy
      curl -X POST "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/missed" \
        -H "Content-Type: application/json" \
        -H "client-id: YOUR_CLIENT_ID" \
        -H "api-key: YOUR_API_KEY" \
        -d '{
          "transactions": [
            {
              "transactionId": "12345",
              "transactionAmount": 100.5,
              "transactionDate": "2023-10-01",
              "merchant": "Amazon",
              "cardName": "Chase Sapphire Preferred"
            }
          ],
          "yourCards": [
            "American Express Platinum",
            "Chase Sapphire Preferred"
          ]
        }'
      
      Node
      1. Install Axios
      Copy
      npm install axios
      1. Async/Await Node.js Script with Error Handling
      Copy
      const axios = require('axios');
      async function postMissedRewards() {
        const url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/missed";
        const headers = {
          'Content-Type': 'application/json',
          'client-id': 'YOUR_CLIENT_ID',
          'api-key': 'YOUR_API_KEY'
        };
        const data = {
          transactions: [
            {
              transactionId: "12345",
              transactionAmount: 100.5,
              transactionDate: "2023-10-01",
              merchant: "Amazon",
              cardName: "Chase Sapphire Preferred"
            }
          ],
          yourCards: [
            "American Express Platinum",
            "Chase Sapphire Preferred"
          ]
        };
      
        try {
          const response = await axios.post(url, data, { headers });
          console.log('Status:', response.status);
          console.log('Response:', JSON.stringify(response.data, null, 2));
        } catch (error) {
          if (error.response) {
            // Server responded with an error status
            console.error('API Error:', error.response.status);
            console.error('Error body:', JSON.stringify(error.response.data, null, 2));
          } else if (error.request) {
            // Request was made but no response
            console.error('No response received:', error.request);
          } else {
            // Error in setting up the request
            console.error('Request setup error:', error.message);
          }
        }
      }
      
      postMissedRewards();
      
      Python
      1. Using Aync/Await with error handling
      Copy
      pip install requests
      import requests
      
      url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/missed"
      
      headers = {
          "Content-Type": "application/json",
          "client-id": "YOUR_CLIENT_ID",
          "api-key": "YOUR_API_KEY"
      }
      
      data = {
          "transactions": [
              {
                  "transactionId": "12345",
                  "transactionAmount": 100.5,
                  "transactionDate": "2023-10-01",
                  "merchant": "Amazon",
                  "cardName": "Chase Sapphire Preferred"
              }
          ],
          "yourCards": [
              "American Express Platinum",
              "Chase Sapphire Preferred"
          ]
      }
      
      try:
          response = requests.post(url, json=data, headers=headers, timeout=10)
          response.raise_for_status()  # Raises HTTPError for bad HTTP status codes
          print("Status:", response.status_code)
          print("Response:", response.json())
      except requests.exceptions.HTTPError as e:
          print(f"HTTP error occurred: {e} - Response body: {response.text}")
      except requests.exceptions.ConnectionError as e:
          print("A connection error occurred:", e)
      except requests.exceptions.Timeout as e:
          print("Request timed out:", e)
      except requests.exceptions.RequestException as e:
          print("An error occurred while making the request:", e)
      
      1. Using Async request with aiohttp
      Copy
      import asyncio
      import aiohttp
      
      async def post_missed_rewards():
          url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/missed"
          headers = {
              "Content-Type": "application/json",
              "client-id": "YOUR_CLIENT_ID",
              "api-key": "YOUR_API_KEY"
          }
          data = {
              "transactions": [
                  {
                      "transactionId": "12345",
                      "transactionAmount": 100.5,
                      "transactionDate": "2023-10-01",
                      "merchant": "Amazon",
                      "cardName": "Chase Sapphire Preferred"
                  }
              ],
              "yourCards": [
                  "American Express Platinum",
                  "Chase Sapphire Preferred"
              ]
          }
          try:
              async with aiohttp.ClientSession() as session:
                  async with session.post(url, json=data, headers=headers, timeout=10) as resp:
                      print("Status:", resp.status)
                      resp_json = await resp.json()
                      print("Response:", resp_json)
                      resp.raise_for_status()
          except aiohttp.ClientResponseError as e:
              print(f"HTTP error occurred: {e.status} - {e.message}")
          except aiohttp.ClientConnectionError as e:
              print("A connection error occurred:", e)
          except asyncio.TimeoutError as e:
              print("Request timed out:", e)
          except Exception as e:
              print("An error occurred while making the request:", e)
      
      asyncio.run(post_missed_rewards())
      
      Java

      Using standard HttpClient API

      Copy
      import java.io.IOException;
      import java.net.URI;
      import java.net.http.HttpClient;
      import java.net.http.HttpRequest;
      import java.net.http.HttpResponse;
      
      public class UthriveMissedRewardExample {
          public static void main(String[] args) {
              String url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/missed";
              String clientId = "YOUR_CLIENT_ID";
              String apiKey = "YOUR_API_KEY";
      
              String jsonBody = """
              {
                "transactions": [
                  {
                    "transactionId": "12345",
                    "transactionAmount": 100.5,
                    "transactionDate": "2023-10-01",
                    "merchant": "Amazon",
                    "cardName": "Chase Sapphire Preferred"
                  }
                ],
                "yourCards": [
                  "American Express Platinum",
                  "Chase Sapphire Preferred"
                ]
              }
              """;
      
              HttpClient client = HttpClient.newHttpClient();
              HttpRequest request = HttpRequest.newBuilder()
                      .uri(URI.create(url))
                      .header("Content-Type", "application/json")
                      .header("client-id", clientId)
                      .header("api-key", apiKey)
                      .POST(HttpRequest.BodyPublishers.ofString(jsonBody))
                      .build();
      
              try {
                  HttpResponse<String> response = client.send(request, HttpResponse.BodyHandlers.ofString());
      
                  int status = response.statusCode();
                  String body = response.body();
      
                  System.out.println("Status: " + status);
                  System.out.println("Response body:\n" + body);
      
                  if (status >= 200 && status < 300) {
                      // Success
                      // Optionally, parse the JSON here using a library like Jackson or Gson
                  } else {
                      System.err.println("API returned an error. Status: " + status);
                  }
              } catch (IOException e) {
                  System.err.println("I/O Exception during API call: " + e.getMessage());
                  e.printStackTrace();
              } catch (InterruptedException e) {
                  System.err.println("Request was interrupted: " + e.getMessage());
                  Thread.currentThread().interrupt();
              } catch (Exception e) {
                  System.err.println("Unexpected error: " + e.getMessage());
                  e.printStackTrace();
              }
          }
      }
      

      Using Spring

      If you are using Maven
      Copy
      <dependency>
          <groupId>org.springframework</groupId>
          <artifactId>spring-web</artifactId>
          <version>5.3.30</version> <!-- or your compatible version -->
      </dependency>
      If you use Gradle
      Copy
      implementation 'org.springframework:spring-web:5.3.30'
      Spring RestTemplate example
      Copy
      import org.springframework.http.*;
      import org.springframework.web.client.RestClientException;
      import org.springframework.web.client.RestTemplate;
      
      import java.util.*;
      
      public class UthriveSpringExample {
      
          public static void main(String[] args) {
              String url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/missed";
      
              // Build the request JSON as Java Maps
              Map<String, Object> transaction = new HashMap<>();
              transaction.put("transactionId", "12345");
              transaction.put("transactionAmount", 100.5);
              transaction.put("transactionDate", "2023-10-01");
              transaction.put("merchant", "Amazon");
              transaction.put("cardName", "Chase Sapphire Preferred");
      
              Map<String, Object> requestBody = new HashMap<>();
              requestBody.put("transactions", Arrays.asList(transaction));
              requestBody.put("yourCards", Arrays.asList("American Express Platinum", "Chase Sapphire Preferred"));
      
              // Set HTTP headers
              HttpHeaders headers = new HttpHeaders();
              headers.setContentType(MediaType.APPLICATION_JSON);
              headers.set("client-id", "YOUR_CLIENT_ID");
              headers.set("api-key", "YOUR_API_KEY");
      
              HttpEntity<Map<String, Object>> entity = new HttpEntity<>(requestBody, headers);
      
              RestTemplate restTemplate = new RestTemplate();
      
              try {
                  ResponseEntity<String> response = restTemplate.exchange(
                      url, HttpMethod.POST, entity, String.class);
      
                  int statusCode = response.getStatusCodeValue();
                  System.out.println("Status: " + statusCode);
                  System.out.println("Body:\n" + response.getBody());
      
                  if (statusCode >= 200 && statusCode < 300) {
                      // Success, parse the JSON if needed (Jackson auto-mapping available)
                  } else {
                      System.err.println("API returned non-success status.");
                  }
              } catch (RestClientException e) {
                  System.err.println("Exception during API request: " + e.getMessage());
              }
          }
      }
      

      Using Spring WebClient with error handling.

      WebClient is a part of Spring WebFlux, suitable for both reactive and non-blocking use cases in modern Spring Boot projects.

      Add dependency

      For maven , add to pom.xml
      Copy
      <dependency>
          <groupId>org.springframework.boot</groupId>
          <artifactId>spring-boot-starter-webflux</artifactId>
      </dependency>
      
      For Gradle:
      Copy
      implementation 'org.springframework.boot:spring-boot-starter-webflux'
      
      import org.springframework.http.HttpHeaders;
      import org.springframework.http.MediaType;
      import org.springframework.web.reactive.function.BodyInserters;
      import org.springframework.web.reactive.function.client.WebClient;
      import reactor.core.publisher.Mono;
      
      import java.util.*;
      
      public class UthriveWebClientExample {
          public static void main(String[] args) {
              String url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/missed";
      
              Map<String, Object> transaction = new HashMap<>();
              transaction.put("transactionId", "12345");
              transaction.put("transactionAmount", 100.5);
              transaction.put("transactionDate", "2023-10-01");
              transaction.put("merchant", "Amazon");
              transaction.put("cardName", "Chase Sapphire Preferred");
      
              Map<String, Object> body = new HashMap<>();
              body.put("transactions", List.of(transaction));
              body.put("yourCards", List.of("American Express Platinum", "Chase Sapphire Preferred"));
      
              WebClient webClient = WebClient.builder()
                      .baseUrl(url)
                      .defaultHeader(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
                      .defaultHeader("client-id", "YOUR_CLIENT_ID")
                      .defaultHeader("api-key", "YOUR_API_KEY")
                      .build();
      
              webClient.post()
                      .body(BodyInserters.fromValue(body))
                      .retrieve()
                      .toEntity(String.class)
                      .doOnSuccess(response -> {
                          System.out.println("Status: " + response.getStatusCode().value());
                          System.out.println("Body:\n" + response.getBody());
                      })
                      .doOnError(error -> {
                          System.err.println("Error during API request: " + error.getMessage());
                      })
                      .block(); // For demo main method usage; in production use subscribe() or chain in reactive flow
          }
      }
      

      Controller/Service WebFlux example with POJO mapping

      Project Setup

      Add to your pom.xml
      Copy
      <dependency>
          <groupId>org.springframework.boot</groupId>
          <artifactId>spring-boot-starter-webflux</artifactId>
      </dependency>
      

      Or with Gradle

      Copy
      implementation 'org.springframework.boot:spring-boot-starter-webflux'
      POJO Model Classes
      Copy
      
      // MissedRewardResponse.java
      public class MissedRewardResponse {
          private Data data;
          private String message;
      
          // getters and setters
      
          public static class Data {
              private double overallMissedRewardsExisting;
              private double overallMissedRewardsNew;
              // Add missedRewards etc. as needed
      
              // getters and setters
          }
      }
      
      Service Layer using WebClient
      Copy
      import org.springframework.beans.factory.annotation.Value;
      import org.springframework.http.HttpHeaders;
      import org.springframework.http.MediaType;
      import org.springframework.stereotype.Service;
      import org.springframework.web.reactive.function.BodyInserters;
      import org.springframework.web.reactive.function.client.WebClient;
      import reactor.core.publisher.Mono;
      
      import java.util.List;
      import java.util.Map;
      
      @Service
      public class UthriveService {
      
          private final WebClient webClient;
      
          public UthriveService(
              @Value("${uthrive.api.client-id}") String clientId,
              @Value("${uthrive.api.api-key}") String apiKey
          ) {
              this.webClient = WebClient.builder()
                      .baseUrl("https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging")
                      .defaultHeader(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
                      .defaultHeader("client-id", clientId)
                      .defaultHeader("api-key", apiKey)
                      .build();
          }
      
          public Mono<MissedRewardResponse> getMissedRewards(List<Map<String, Object>> transactions, List<String> yourCards) {
              Map<String, Object> body = Map.of(
                  "transactions", transactions,
                  "yourCards", yourCards
              );
      
              return webClient.post()
                      .uri("/reward/missed")
                      .body(BodyInserters.fromValue(body))
                      .retrieve()
                      .bodyToMono(MissedRewardResponse.class);
          }
      }
      
      Controller Layer
      Copy
      import org.springframework.beans.factory.annotation.Autowired;
      import org.springframework.web.bind.annotation.*;
      import reactor.core.publisher.Mono;
      import java.util.List;
      import java.util.Map;
      
      @RestController
      @RequestMapping("/api")
      public class UthriveController {
      
          @Autowired
          private UthriveService uthriveService;
      
          @PostMapping("/reward/missed/proxy")
          public Mono<MissedRewardResponse> proxyMissedReward(@RequestBody MissedRewardRequest request) {
              return uthriveService.getMissedRewards(request.getTransactions(), request.getYourCards());
          }
      }
      
      // --- You would also need this request DTO for clean deserialization ---
      class MissedRewardRequest {
          private List<Map<String, Object>> transactions;
          private List<String> yourCards;
      
          public List<Map<String, Object>> getTransactions() { return transactions; }
          public void setTransactions(List<Map<String, Object>> transactions) { this.transactions = transactions; }
      
          public List<String> getYourCards() { return yourCards; }
          public void setYourCards(List<String> yourCards) { this.yourCards = yourCards; }
      }
      
      Android

      Example using OkHttp for the HttpClient and Gson for deserialization

      Add dependencies in build.gradle
      Copy
      implementation 'com.squareup.okhttp3:okhttp:4.10.0'
      implementation 'com.google.code.gson:gson:2.10.1'
      Model classes (POJOs)
      Copy
      public class MissedRewardResponse {
          private Data data;
          private String message;
      
          public Data getData() { return data; }
          public String getMessage() { return message; }
      
          public static class Data {
              private double overallMissedRewardsExisting;
              private double overallMissedRewardsNew;
              // Add other fields as needed
      
              public double getOverallMissedRewardsExisting() { return overallMissedRewardsExisting; }
              public double getOverallMissedRewardsNew() { return overallMissedRewardsNew; }
              // Add other getters/setters...
          }
      }
      
      Make the HTTP request

      Run as a background thread

      Copy
      import android.os.Bundle;
      import androidx.appcompat.app.AppCompatActivity;
      import okhttp3.*;
      import com.google.gson.Gson;
      import java.io.IOException;
      import java.util.*;
      
      public class MainActivity extends AppCompatActivity {
      
          private static final String URL = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/reward/missed";
          private static final Gson gson = new Gson();
      
          @Override
          protected void onCreate(Bundle savedInstanceState) {
              super.onCreate(savedInstanceState);
      
              // Run in a background thread:
              new Thread(this::postMissedReward).start();
          }
      
          private void postMissedReward() {
              OkHttpClient client = new OkHttpClient();
      
              Map<String, Object> transaction = new HashMap<>();
              transaction.put("transactionId", "12345");
              transaction.put("transactionAmount", 100.5);
              transaction.put("transactionDate", "2023-10-01");
              transaction.put("merchant", "Amazon");
              transaction.put("cardName", "Chase Sapphire Preferred");
      
              Map<String, Object> requestBodyMap = new HashMap<>();
              requestBodyMap.put("transactions", Collections.singletonList(transaction));
              requestBodyMap.put("yourCards", Arrays.asList("American Express Platinum", "Chase Sapphire Preferred"));
      
              String requestBodyStr = gson.toJson(requestBodyMap);
      
              RequestBody body = RequestBody.create(
                  requestBodyStr,
                  MediaType.parse("application/json; charset=utf-8")
              );
      
              Request request = new Request.Builder()
                  .url(URL)
                  .post(body)
                  .addHeader("Content-Type", "application/json")
                  .addHeader("client-id", "YOUR_CLIENT_ID")
                  .addHeader("api-key", "YOUR_API_KEY")
                  .build();
      
              try (Response response = client.newCall(request).execute()) {
                  if (response.isSuccessful() && response.body() != null) {
                      String responseBody = response.body().string();
                      MissedRewardResponse missedRewardResponse = gson.fromJson(responseBody, MissedRewardResponse.class);
                      runOnUiThread(() -> {
                          // Use your POJO here (update UI, etc.)
                          System.out.println("Success! Message: " + missedRewardResponse.getMessage());
                          System.out.println("Overall Missed Existing: " + missedRewardResponse.getData().getOverallMissedRewardsExisting());
                      });
                  } else {
                      runOnUiThread(() -> {
                          System.err.println("API error: " + response.code());
                      });
                  }
              } catch (IOException e) {
                  runOnUiThread(() -> {
                      System.err.println("Network or parsing error: " + e.getMessage());
                  });
              }
          }
      }
      

      Use WorkManager/LiveData/Coroutines for modern Android apps. To update the UI, use runOnUiThread only when necessary.

      Error Responses

      HTTP CodeDescriptionExample Response
      400Malformed input, missing fields{ “message”: “Invalid request body” }
      401Authentication failed{ “message”: “Unauthorized” }
      500Internal server error{ “message”: “Internal error” }

      Best Practices

      • Card name values in both transactions.cardName and yourCards must match the supported card list for accurate matching.
      • Use this endpoint after transactions post to help users see real, actionable “missed value.”
      • Use overallMissedRewardsExisting to surface “missed with your current cards” and overallMissedRewardsNew for “missed if you had all available cards.”

      Best card recommendation

      Copy
      POST /recommend/advice

      URL: https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/recommend/advice

      Get the best personalized card usage advice for a specific purchase scenario. This endpoint tells you which of the user’s cards (and optionally, any new/potential cards) will maximize rewards for a given merchant and spend amount.

      Authentication
      • Required: Include client-id and api-key headers in every request
      Request Headers
      HeaderTypeRequiredDescription
      client-idstringYesYour Uthrive client ID
      api-keystringYesYour Uthrive API key
      Content-TypestringYesapplication/json
      Request Body Schema
      FieldTypeRequiredDescription
      merchantstringYesMerchant name (e.g., “Amazon”)
      yourCardsarrayYesList of card names you currently hold
      spendAmountnumberYesAmount (USD) to be spent

      Example Request:

      Copy
      {
        "merchant": "Amazon",
        "yourCards": [
          "American Express Platinum",
          "Chase Sapphire Preferred"
        ],
        "spendAmount": 300
      }
      
      Success Response (200 OK)

      Returns:

      • The best card in the user’s wallet for this merchant/spend amount.
      • Other cards in the wallet, with their respective reward calculations (ordered by reward value).
      Example:
      Copy
      {
        "data": {
          "bestCard": {
            "cardName": "Chase Sapphire Preferred",
            "rewardValue": 0.013,
            "rewardMultiplier": 1,
            "rewardAmount": 3.9,
            "bonus": 0.013
          },
          "otherCards": [
            {
              "cardName": "American Express Platinum",
              "rewardValue": 0.01,
              "rewardMultiplier": 1,
              "rewardAmount": 3,
              "bonus": 0.01
            }
          ]
        },
        "message": "Success"
      }
      
      Response Fields

      Top-level:

      FieldTypeDescription
      dataobjectCard advice data (see below)
      messagestringStatus message

      Inside data:

      FieldTypeDescription
      bestCardobjectCard with the maximum total reward for this scenario
      otherCardsarrayOther cards in wallet, with computed reward amounts

      Each card object:

      FieldTypeDescription
      cardNamestringCard name
      rewardValuenumber$ value per reward point/mile
      rewardMultipliernumberMultiplier for this merchant/amount
      rewardAmountnumberTotal reward earned for spendAmount (in USD)
      bonusnumberBonus reward value, if applicable
        cURL
        Copy
        curl -X POST "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/recommend/advice" \
          -H "Content-Type: application/json" \
          -H "client-id: YOUR_CLIENT_ID" \
          -H "api-key: YOUR_API_KEY" \
          -d '{
            "merchant": "Amazon",
            "yourCards": [
              "American Express Platinum",
              "Chase Sapphire Preferred"
            ],
            "spendAmount": 300
          }'
        
        NodeJS
        1. Install dependencies
        Copy
        npm install axios
        npm install --save-dev typescript @types/node
        1. Create recommendAdvice.ts
        Copy
        import axios from 'axios';
        
        // ---- POJO Type Definitions ----
        interface CardReward {
          cardName: string;
          rewardValue: number;
          rewardMultiplier: number;
          rewardAmount: number;
          bonus: number;
        }
        
        interface AdviceResponse {
          data: {
            bestCard: CardReward;
            otherCards: CardReward[];
          };
          message: string;
        }
        
        async function getRecommendationAdvice(): Promise<void> {
          const url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/recommend/advice";
          const headers = {
            "Content-Type": "application/json",
            "client-id": "YOUR_CLIENT_ID",
            "api-key": "YOUR_API_KEY"
          };
          const body = {
            merchant: "Amazon",
            yourCards: [
              "American Express Platinum",
              "Chase Sapphire Preferred"
            ],
            spendAmount: 300
          };
        
          try {
            const response = await axios.post<AdviceResponse>(url, body, { headers });
            const advice = response.data;
        
            // POJO mapping in action
            console.log("Best Card Advice:", advice.data.bestCard);
            advice.data.otherCards.forEach((card, i) => {
              console.log(`Other Card ${i + 1}:`, card);
            });
            console.log("Message:", advice.message);
        
            // Example individual field access:
            // console.log("Best card name:", advice.data.bestCard.cardName);
        
          } catch (error: any) {
            if (error.response) {
              console.error('API Error:', error.response.status);
              console.error('Error response body:', error.response.data);
            } else if (error.request) {
              console.error('No response received:', error.request);
            } else {
              console.error('Request setup error:', error.message);
            }
          }
        }
        
        // Run the function
        getRecommendationAdvice();
        

        The above example returns a strongly-typed POJO (AdviceResponse and CardReward)—true POJO mapping as in Java.

        Python

        Object oriented approach

        1. Define Python classes for POJO mapping
        Copy
        from typing import List, Optional
        
        class CardReward:
            def __init__(self, cardName: str, rewardValue: float, rewardMultiplier: float, rewardAmount: float, bonus: float):
                self.card_name = cardName
                self.reward_value = rewardValue
                self.reward_multiplier = rewardMultiplier
                self.reward_amount = rewardAmount
                self.bonus = bonus
        
            @classmethod
            def from_dict(cls, data):
                return cls(
                    cardName=data.get("cardName"),
                    rewardValue=data.get("rewardValue"),
                    rewardMultiplier=data.get("rewardMultiplier"),
                    rewardAmount=data.get("rewardAmount"),
                    bonus=data.get("bonus")
                )
        
            def __repr__(self):
                return (f"CardReward(card_name={self.card_name!r}, reward_value={self.reward_value}, "
                        f"reward_multiplier={self.reward_multiplier}, reward_amount={self.reward_amount}, bonus={self.bonus})")
        
        class AdviceResponse:
            def __init__(self, best_card: CardReward, other_cards: List[CardReward], message: str):
                self.best_card = best_card
                self.other_cards = other_cards
                self.message = message
        
            @classmethod
            def from_dict(cls, data):
                best_card = CardReward.from_dict(data["data"]["bestCard"])
                other_cards = [CardReward.from_dict(card) for card in data["data"].get("otherCards", [])]
                message = data.get("message", "")
                return cls(best_card, other_cards, message)
        
            def __repr__(self):
                return (f"AdviceResponse(best_card={self.best_card}, other_cards={self.other_cards}, message={self.message!r})")
        
        1. Request Function With Error Handling
        Copy
        import requests
        
        def get_recommendation_advice(client_id: str, api_key: str) -> Optional[AdviceResponse]:
            url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/recommend/advice"
            headers = {
                "Content-Type": "application/json",
                "client-id": client_id,
                "api-key": api_key
            }
            data = {
                "merchant": "Amazon",
                "yourCards": [
                    "American Express Platinum",
                    "Chase Sapphire Preferred"
                ],
                "spendAmount": 300
            }
            try:
                response = requests.post(url, json=data, headers=headers, timeout=10)
                response.raise_for_status()
                advice = AdviceResponse.from_dict(response.json())
                return advice
            except requests.exceptions.HTTPError as e:
                print(f"HTTP error occurred: {e} - Response body: {getattr(e.response, 'text', '')}")
            except requests.exceptions.ConnectionError as e:
                print("A connection error occurred:", e)
            except requests.exceptions.Timeout as e:
                print("Request timed out:", e)
            except requests.exceptions.RequestException as e:
                print("A general error occurred while making the request:", e)
            except Exception as e:
                print("Unexpected error:", e)
            return None
        
        1. Example Usage
        Copy
        if __name__ == "__main__":
            CLIENT_ID = "YOUR_CLIENT_ID"
            API_KEY = "YOUR_API_KEY"
        
            advice = get_recommendation_advice(CLIENT_ID, API_KEY)
            if advice:
                print("Best Card:")
                print(advice.best_card)
                print("\nOther Cards:")
                for card in advice.other_cards:
                    print(card)
                print("\nMessage:", advice.message)
        

        Using aiohttp async library with DTO validation

        Install prerequisites

        Copy
        pip install aiohttp pydantic
        Copy
        import asyncio
        import aiohttp
        from pydantic import BaseModel, ValidationError, conlist, constr, condecimal
        from typing import List, Optional
        
        # --- DTOs and Response Mapping ---
        
        class AdviceRequest(BaseModel):
            merchant: constr(min_length=1)
            yourCards: conlist(constr(min_length=2), min_items=1)
            spendAmount: condecimal(ge=0)
        
        class CardReward(BaseModel):
            cardName: str
            rewardValue: float
            rewardMultiplier: float
            rewardAmount: float
            bonus: float
        
        class AdviceData(BaseModel):
            bestCard: CardReward
            otherCards: List[CardReward]
        
        class AdviceResponseDTO(BaseModel):
            data: AdviceData
            message: str
        
        # --- Async Function ---
        
        async def get_recommendation_advice(client_id: str, api_key: str, request_body: AdviceRequest) -> Optional[AdviceResponseDTO]:
            url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/recommend/advice"
            headers = {
                "Content-Type": "application/json",
                "client-id": client_id,
                "api-key": api_key,
            }
        
            try:
                async with aiohttp.ClientSession() as session:
                    async with session.post(url, json=request_body.dict(), headers=headers, timeout=10) as resp:
                        print("Status:", resp.status)
                        resp_json = await resp.json()
                        if resp.status >= 200 and resp.status < 300:
                            try:
                                advice = AdviceResponseDTO.parse_obj(resp_json)
                                return advice
                            except ValidationError as ve:
                                print("Response validation error:", ve)
                        else:
                            print('API Error:', resp.status, resp_json)
            except asyncio.TimeoutError:
                print("Request timed out")
            except aiohttp.ClientConnectionError as e:
                print("Connection error:", e)
            except Exception as e:
                print("Error:", e)
            return None
        
        # --- Example usage ---
        
        async def main():
            CLIENT_ID = "YOUR_CLIENT_ID"
            API_KEY = "YOUR_API_KEY"
            try:
                # Validate DTO input before request!
                request_body = AdviceRequest(
                    merchant="Amazon",
                    yourCards=[
                        "American Express Platinum",
                        "Chase Sapphire Preferred"
                    ],
                    spendAmount=300
                )
            except ValidationError as ve:
                print("Input validation error:", ve)
                return
        
            advice = await get_recommendation_advice(CLIENT_ID, API_KEY, request_body)
            if advice:
                print("\nBest Card:")
                print(advice.data.bestCard)
                print("\nOther Cards:")
                for card in advice.data.otherCards:
                    print(card)
                print("\nMessage:", advice.message)
        
        if __name__ == "__main__":
            asyncio.run(main())
        

        How this works:

        • DTO Validation: Input (your request body) is validated with pydantic, ensuring correct schema before the request.
        • HTTP POST with aiohttp, with async/await for maximum efficiency.
        • Response Mapping: JSON result is mapped to a pydantic object (AdviceResponseDTO). Any validation error is clearly printed.
        • Error Handling: Handles timeouts, connection errors, and reports validation errors (both request and response)
        Java

        Spring Boot with WebFlux

        1. Add dependencies for Maven projects
        Copy
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-webflux</artifactId>
        </dependency>
        <!-- Optionally, Lombok for POJOs: -->
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <scope>provided</scope>
        </dependency>
        
        1. POJO (DTO) classes
        AdviceRequest.java
        Copy
        import lombok.Data;
        import java.math.BigDecimal;
        import java.util.List;
        
        @Data
        public class AdviceRequest {
            private String merchant;
            private List<String> yourCards;
            private BigDecimal spendAmount;
        }
        
        CardReward.java
        Copy
        import lombok.Data;
        
        @Data
        public class CardReward {
            private String cardName;
            private double rewardValue;
            private double rewardMultiplier;
            private double rewardAmount;
            private double bonus;
        }
        
        AdviceData.java
        Copy
        import lombok.Data;
        import java.util.List;
        
        @Data
        public class AdviceData {
            private CardReward bestCard;
            private List<CardReward> otherCards;
        }
        
        AdviceResponseDTO.java
        Copy
        import lombok.Data;
        
        @Data
        public class AdviceResponseDTO {
            private AdviceData data;
            private String message;
        }
        

        WebClientServiceBean

        UthriveAdviceService.java
        Copy
        import org.springframework.beans.factory.annotation.Value;
        import org.springframework.http.HttpHeaders;
        import org.springframework.http.MediaType;
        import org.springframework.stereotype.Service;
        import org.springframework.web.reactive.function.client.WebClient;
        import org.springframework.web.reactive.function.client.WebClientResponseException;
        import reactor.core.publisher.Mono;
        
        @Service
        public class UthriveAdviceService {
        
            private final WebClient webClient;
        
            public UthriveAdviceService(
                    @Value("${uthrive.api.client-id}") String clientId,
                    @Value("${uthrive.api.api-key}") String apiKey
            ) {
                this.webClient = WebClient.builder()
                        .baseUrl("https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging")
                        .defaultHeader(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
                        .defaultHeader("client-id", clientId)
                        .defaultHeader("api-key", apiKey)
                        .build();
            }
        
            public Mono<AdviceResponseDTO> getAdvice(AdviceRequest request) {
                return webClient.post()
                        .uri("/recommend/advice")
                        .bodyValue(request)
                        .retrieve()
                        .onStatus(status -> !status.is2xxSuccessful(),
                            response -> response.bodyToMono(String.class)
                                .flatMap(body -> Mono.error(new RuntimeException("Api error: " + body)))
                        )
                        .bodyToMono(AdviceResponseDTO.class)
                        .doOnError(WebClientResponseException.class, ex -> {
                            System.err.println("WebClientResponseException: " + ex.getRawStatusCode() + " " + ex.getResponseBodyAsString());
                        })
                        .doOnError(Exception.class, ex -> {
                            System.err.println("General exception: " + ex.getMessage());
                        });
            }
        }
        
        Controller
        Copy
        import org.springframework.beans.factory.annotation.Autowired;
        import org.springframework.http.ResponseEntity;
        import org.springframework.web.bind.annotation.*;
        import reactor.core.publisher.Mono;
        
        @RestController
        @RequestMapping("/api/uthrive")
        public class UthriveAdviceController {
        
            @Autowired
            private UthriveAdviceService adviceService;
        
            @PostMapping("/recommend/advice")
            public Mono<ResponseEntity<AdviceResponseDTO>> recommendAdvice(@RequestBody AdviceRequest request) {
                return adviceService.getAdvice(request)
                        .map(ResponseEntity::ok)
                        .onErrorResume(e -> Mono.just(ResponseEntity.badRequest().body(null)));
            }
        }
        

        Configure your credentials In application.properties or application.yml

        Copy
        uthrive.api.client-id=YOUR_CLIENT_ID
        uthrive.api.api-key=YOUR_API_KEY
        
        Android
        1. Add dependencies in your build.gradle
        Copy
        implementation 'com.squareup.okhttp3:okhttp:4.10.0'
        implementation 'com.google.code.gson:gson:2.10.1'
        
        1. Create POJO(DTOs) for mapping
        AdviceRequest.java
        Copy
        import java.util.List;
        
        public class AdviceRequest {
            private String merchant;
            private List<String> yourCards;
            private double spendAmount;
        
            public AdviceRequest(String merchant, List<String> yourCards, double spendAmount) {
                this.merchant = merchant;
                this.yourCards = yourCards;
                this.spendAmount = spendAmount;
            }
            // getters and setters (or use Lombok)...
        }
        
        CardReward.java
        Copy
        public class CardReward {
            private String cardName;
            private double rewardValue;
            private double rewardMultiplier;
            private double rewardAmount;
            private double bonus;
        
            // getters and setters...
        }
        AdviceData.java
        Copy
        import java.util.List;
        
        public class AdviceData {
            private CardReward bestCard;
            private List<CardReward> otherCards;
        
            // getters and setters...
        }
        
        AdviceResponseDTO.java
        Copy
        public class AdviceResponseDTO {
            private AdviceData data;
            private String message;
        
            public AdviceData getData() { return data; }
            public String getMessage() { return message; }
        }
        

        Service class

        UthriveAdviceService.java
        Copy
        import android.util.Log;
        
        import com.google.gson.Gson;
        import com.google.gson.JsonSyntaxException;
        
        import java.io.IOException;
        import java.util.concurrent.Executor;
        import java.util.concurrent.Executors;
        
        import okhttp3.*;
        
        public class UthriveAdviceService {
            private final String url = "https://h0n277p4vd.execute-api.us-east-1.amazonaws.com/staging/recommend/advice";
            private final OkHttpClient client = new OkHttpClient();
            private final Gson gson = new Gson();
            private final String clientId;
            private final String apiKey;
            private final Executor executor = Executors.newSingleThreadExecutor();
        
            public UthriveAdviceService(String clientId, String apiKey) {
                this.clientId = clientId;
                this.apiKey = apiKey;
            }
        
            public interface Callback {
                void onSuccess(AdviceResponseDTO advice);
                void onError(Exception e);
            }
        
            public void getRecommendationAdvice(AdviceRequest adviceRequest, Callback callback) {
                executor.execute(() -> {
                    try {
                        RequestBody body = RequestBody.create(
                                gson.toJson(adviceRequest),
                                MediaType.get("application/json; charset=utf-8")
                        );
        
                        Request request = new Request.Builder()
                                .url(url)
                                .post(body)
                                .addHeader("Content-Type", "application/json")
                                .addHeader("client-id", clientId)
                                .addHeader("api-key", apiKey)
                                .build();
        
                        try (Response response = client.newCall(request).execute()) {
                            if (response.isSuccessful() && response.body() != null) {
                                String responseStr = response.body().string();
                                try {
                                    AdviceResponseDTO adviceResp = gson.fromJson(responseStr, AdviceResponseDTO.class);
                                    callback.onSuccess(adviceResp);
                                } catch (JsonSyntaxException je) {
                                    callback.onError(new Exception("Response parsing error: " + je.getMessage()));
                                }
                            } else {
                                callback.onError(new Exception("API Error: Code " + response.code() + " Body: " +
                                        (response.body() != null ? response.body().string() : "")));
                            }
                        }
                    } catch (IOException e) {
                        callback.onError(new Exception("Network error: " + e.getMessage(), e));
                    } catch (Exception e) {
                        callback.onError(e);
                    }
                });
            }
        }
        
        Use in your Activity/Fragment
        Copy
        import android.os.Bundle;
        import androidx.appcompat.app.AppCompatActivity;
        import java.util.Arrays;
        
        public class MainActivity extends AppCompatActivity {
        
            private static final String CLIENT_ID = "YOUR_CLIENT_ID";
            private static final String API_KEY = "YOUR_API_KEY";
        
            @Override
            protected void onCreate(Bundle savedInstanceState) {
                super.onCreate(savedInstanceState);
        
                UthriveAdviceService service = new UthriveAdviceService(CLIENT_ID, API_KEY);
        
                AdviceRequest req = new AdviceRequest(
                    "Amazon",
                    Arrays.asList("American Express Platinum", "Chase Sapphire Preferred"),
                    300.0
                );
        
                service.getRecommendationAdvice(req, new UthriveAdviceService.Callback() {
                    @Override
                    public void onSuccess(AdviceResponseDTO advice) {
                        runOnUiThread(() -> {
                            // Access POJO fields
                            if (advice != null && advice.getData() != null) {
                                CardReward best = advice.getData().getBestCard();
                                if (best != null) {
                                    System.out.println("Best card: " + best.getCardName() + " Reward: " + best.getRewardAmount());
                                }
                                // And so on...
                            }
                        });
                    }
        
                    @Override
                    public void onError(Exception e) {
                        runOnUiThread(() -> {
                            System.err.println("Error: " + e.getMessage());
                        });
                    }
                });
            }
        }
        

        Error Responses

        HTTP CodeDescriptionExample Response
        400Malformed or incomplete input{ “message”: “Invalid request body” }
        401Authentication failed{ “message”: “Unauthorized” }
        500Internal server error{ “message”: “Internal error” }

        Usage

        • The Merchant must match a recognized merchant in Uthrive’s system for best results.
        • yourCards must be an array of the user’s actual card names (must match Uthrive’s supported list).
        • All returned reward calculations assume the provided spend amount and merchant.
        • Use this endpoint for real-time “which card should I use?” advice in apps, widgets, or POS scenarios.
        Uthrive U Log It's Your Money! Uthrive QR

        Download The App

        Point your phone camera to scan the code

        Best Credit Cards

        • Best Cash Back credit cards
        • Best No Annual Fee Credit Cards
        • Best balance transfer credit cards
        • Best 0% APR Credit Cards
        • Best Rewards Credit Cards
        • Best Hotel Credit Cards
        • Best Credit Cards For Groceries
        • Best Credit Cards For Streaming Services
        • Best Credit Cards For Gas
        • Best Credit Cards For Healthcare

        Credit Cards Rewards

        • Credit Card Reward Programs
        • American Express Membership Rewards
        • Chase Ultimate Rewards
        • Capital One Miles
        • Citi ThankYou Points
        • Bank Of America Travel Rewards

        Credit Card Benefits

        • Costco credit card benefits
        • Amazon credit card benefits
        • Apple credit card benefits
        • Southwest credit card benefits
        • United credit card benefits
        • Delta credit card benefits

        Best Airline Reward Programs

        • American Airlines AAdvantage Program
        • United Airlines MileagePlus
        • Delta SkyMiles
        • Southwest Rapid Rewards

        Best Hotel Reward Programs

        • Hyatt Rewards Program
        • Mariott Bonvoy Rewards Program
        • Hilton Rewards Program
        • Best Western Rewards Program

        Best Business Credit Cards

        • American Express Business Credit Cards
        • Capital One Business Credit Cards
        • Chase Business Credit Cards
        • Bank Of America Business Credit Cards

        Best Balance Transfer Credit Cards

        • What Is A Balance Transfer
        • Balance Transfer Credit Card With Bad Credit
        • Balance Transfer Credit Card Mistakes

        Refer A Friend

        • American Express Refer A Friend Bonuses
        • Capital One Refer A Friend Program
        • Chase Refer A Friend Bonuses
        • Citi Credit Card Refer A Friend

        Credit Card Pro Series

        • Credit card management app
        • Credit card referral
        • Best credit card for Airbnb
        • Best credit card for Uber
        • Best credit card for Walmart
        Best Credit Cards Caret Down
        • Best Cash Back credit cards
        • Best No Annual Fee Credit Cards
        • Best balance transfer credit cards
        • Best 0% APR Credit Cards
        • Best Rewards Credit Cards
        • Best Hotel Credit Cards
        • Best Credit Cards For Groceries
        • Best Credit Cards For Streaming Services
        • Best Credit Cards For Gas
        • Best Credit Cards For Healthcare
        Credit Cards Rewards Caret Down
        • Credit Card Reward Programs
        • American Express Membership Rewards
        • Chase Ultimate Rewards
        • Capital One Miles
        • Citi ThankYou Points
        • Bank Of America Travel Rewards
        Credit Card Benefits Caret Down
        • Costco credit card benefits
        • Amazon credit card benefits
        • Apple credit card benefits
        • Southwest credit card benefits
        • United credit card benefits
        • Delta credit card benefits
        Best Airline Reward Programs Caret Down
        • American Airlines AAdvantage Program
        • United Airlines MileagePlus
        • Delta SkyMiles
        • Southwest Rapid Rewards
        Best Hotel Reward Programs Caret Down
        • Hyatt Rewards Program
        • Mariott Bonvoy Rewards Program
        • Hilton Rewards Program
        • Best Western Rewards Program
        Best Business Credit Cards Caret Down
        • American Express Business Credit Cards
        • Capital One Business Credit Cards
        • Chase Business Credit Cards
        • Bank Of America Business Credit Cards
        Best Balance Transfer Credit Cards Caret Down
        • What Is A Balance Transfer
        • Balance Transfer Credit Card With Bad Credit
        • Balance Transfer Credit Card Mistakes
        Refer A Friend Caret Down
        • American Express Refer A Friend Bonuses
        • Capital One Refer A Friend Program
        • Chase Refer A Friend Bonuses
        • Citi Credit Card Refer A Friend
        Credit Card Pro Series Caret Down
        • Credit card management app
        • Credit card referral
        • Best credit card for Airbnb
        • Best credit card for Uber
        • Best credit card for Walmart

        About

        • Our Story
        • Uthrive in Media

        Help

        • Help
        • support@Uthrive.club

        Legal

        • Terms & Conditions
        • Privacy Policy

        All corporate logos and trademarks are for illustrative purposes only and are not a recommendation, an offer to sell, or a solicitation of an offer. Trademarks and logos are the property of their respective owners and do not represent endorsements of any kind. Examples and/or pictures above are for illustrative purposes only and are not real customers. View our Disclaimer for more details.

        © Copyright 2022 Uthrive Inc. All rights reserved.

        Verifying...

        Sign in to Uthrive

        No more passwords to remember. Signing in is fast, simple and secure.

        * I agree with Terms & Conditions and Privacy Policy of Uthrive. View more >
        I understand that I am providing written instructions in accordance with the Fair Credit Reporting Act and other applicable law for Uthrive to request and receive information about me from third parties, including but not limited to a copy of my consumer report and score from consumer reporting agencies, at any time for so long as I have an active Uthrive account. I further authorize Uthrive to retain a copy of my credit information for it’s use and to match with credit products.
        View less
        Always use Best card + Savings Offers on Purchases.
        Don't leave your money on the table.
        Scan to
        Download
        The App.
        Uthrive