FastPrepTransaction Fee Calculator — Parts 1–2: Basic Fee Calculation and Conditional Fee Rules

Transaction Fee Calculator — Parts 1–2: Basic Fee Calculation and Conditional Fee Rules

Stripe logoStripe● EasyFULLTIMENEW GRADINTERNPHONE SCREEN

Problem statement

Related part: Continue to Part 3: Volume-Based Discounts.

The Challenge

You need to build a system that calculates fees for a payment platform. You will get transaction data as a long CSV string. You need to read this data and calculate the fee for each payment based on specific rules.

There are three parts to this problem. We start with simple math and add harder rules later.

  • Basic Fees: Read the data and calculate cost based on the payment method.
  • New Rules: Only charge fees for successful payments. Use different rates for different countries.
  • Discounts: Give discounts to merchants who process a lot of payments.

Input Data

The input is a single string in CSV format. The first row lists the column names. The rows after that are the actual transaction records.

id,reference,amount,currency,date,merchant_id,buyer_country,transaction_type,payment_provider,status

What the columns mean:

  • id: The unique ID for the transaction.
  • reference: Reference number.
  • amount: Money involved in cents (e.g., 1000 = $10.00).
  • currency: The money type (e.g., "eur", "usd").
  • date: When it happened (YYYY-MM-DD).
  • merchant_id: ID for the seller.
  • buyer_country: Country code of the buyer.
  • transaction_type: What kind of action it is (e.g., "payment").
  • payment_provider: How they paid (e.g., "card", "klarna").
  • status: Did it work? (e.g., "payment_completed", "payment_failed").

Part 1: Basic Fee Calculation

The Task

Write a function to read the CSV string. Calculate the fee for each transaction based on the payment_provider. Each provider charges a percentage of the amount plus a fixed fee.

Fee Table:

Payment ProviderFee Rate
card2.9% + 30 cents
klarna3.5% + 50 cents
bank_transfer0.8% flat

You must round the final fee down to the nearest whole number (integer).

Example Data

Input:

id,reference,amount,currency,date,merchant_id,buyer_country,transaction_type,payment_provider,status
py_1,1,1000,eur,2024-12-24,acct_1,ie,payment,card,payment_completed
py_2,2,2500,eur,2024-12-24,acct_2,de,payment,card,payment_failed
py_3,3,3400,eur,2024-12-25,acct_2,ie,payment,klarna,payment_completed
py_4,4,5000,eur,2024-12-25,acct_1,fr,payment,bank_transfer,payment_completed

Output:

id,transaction_type,payment_provider,fee
py_1,payment,card,59
py_2,payment,card,102
py_3,payment,klarna,169
py_4,payment,bank_transfer,40

How we got these numbers:

  • py_1: 1000 × 0.029 + 30 = 59
  • py_2: 2500 × 0.029 + 30 = 102.5. Round down to 102.
  • py_3: 3400 × 0.035 + 50 = 169
  • py_4: 5000 × 0.008 = 40

What You Need To Do

  • Read the CSV string properly (ignore the header row after reading it).
  • Use the right math formula for each provider.
  • Return the result as a CSV string.
  • Round fees down (use integer conversion).

Part 2: Conditional Fee Rules

New Rules

Now, update your code to handle status checks and countries.

  • Check Status: Only calculate a fee if status is "payment_completed".
  • Failed Payments: If the status is failed or pending, the fee is 0.
  • Regional Rates: Ireland ("ie") has special, cheaper rates.

Special Rates for Ireland (ie):

Payment ProviderFee Rate
card1.9% + 20 cents
klarna2.5% + 40 cents

All other countries use the standard rates from Part 1.

Example Data

Input:

id,reference,amount,currency,date,merchant_id,buyer_country,transaction_type,payment_provider,status
py_1,1,1000,eur,2024-12-24,acct_1,ie,payment,card,payment_completed
py_2,2,2500,eur,2024-12-24,acct_2,de,payment,card,payment_failed
py_3,3,3400,eur,2024-12-25,acct_2,ie,payment,klarna,payment_completed
py_4,4,5000,eur,2024-12-25,acct_1,fr,payment,bank_transfer,payment_completed
py_5,5,2000,eur,2024-12-26,acct_1,ie,payment,card,payment_pending

Output:

id,transaction_type,payment_provider,fee
py_1,payment,card,39
py_2,payment,card,0
py_3,payment,klarna,125
py_4,payment,bank_transfer,40
py_5,payment,card,0

How we got these numbers:

  • py_1: Ireland rate used. (Cheaper than standard).
  • py_2: Failed, so fee is 0.
  • py_3: Ireland rate used.
  • py_4: France uses standard rate.
  • py_5: Pending, so fee is 0.

What You Need To Do

  • Look at the status column before doing math.
  • Check the buyer_country. If it is "ie", use the special rates.
  • Keep your code clean. Separate the logic for checking status and calculating fees.

Function

calculateFees(csvData: String) → String[]

Examples

Example 1

csvData = "id,reference,amount,currency,date,merchant_id,buyer_country,transaction_type,payment_provider,status\npy_1,1,1000,eur,2024-12-24,acct_1,ie,payment,card,payment_completed\npy_2,2,2500,eur,2024-12-24,acct_2,de,payment,card,payment_failed\npy_3,3,3400,eur,2024-12-25,acct_2,ie,payment,klarna,payment_completed\npy_4,4,5000,eur,2024-12-25,acct_1,fr,payment,bank_transfer,payment_completed\npy_5,5,2000,eur,2024-12-26,acct_1,ie,payment,card,payment_pending"return = ["id,transaction_type,payment_provider,fee","py_1,payment,card,39","py_2,payment,card,0","py_3,payment,klarna,125","py_4,payment,bank_transfer,40","py_5,payment,card,0"]

py_1: Ireland rate used. (Cheaper than standard). py_2: Failed, so fee is 0. py_3: Ireland rate used. py_4: France uses standard rate. py_5: Pending, so fee is 0.

Constraints

  • The CSV follows the ten-column format shown in the source.
  • The fee is charged only when status is payment_completed.
  • Ireland's special rates apply to card and klarna; all other provider-country combinations use the Part 1 standard rates.
  • Round the final fee down using integer conversion.
  • FastPrep adapter: return the source's newline-delimited CSV result as a String[], one CSV line per array element.

More Stripe problems

See Stripe hiring insights
Saved
public String[] calculateFees(String csvData) {
  // write your code here
}
csvData"id,reference,amount,currency,date,merchant_id,buyer_country,transaction_type,payment_provider,status\npy_1,1,1000,eur,2024-12-24,acct_1,ie,payment,card,payment_completed\npy_2,2,2500,eur,2024-12-24,acct_2,de,payment,card,payment_failed\npy_3,3,3400,eur,2024-12-25,acct_2,ie,payment,klarna,payment_completed\npy_4,4,5000,eur,2024-12-25,acct_1,fr,payment,bank_transfer,payment_completed\npy_5,5,2000,eur,2024-12-26,acct_1,ie,payment,card,payment_pending"
expected["id,transaction_type,payment_provider,fee", "py_1,payment,card,39", "py_2,payment,card,0", "py_3,payment,klarna,125", "py_4,payment,bank_transfer,40", "py_5,payment,card,0"]
Checking account…