> ## Documentation Index
> Fetch the complete documentation index at: https://docs.synctera.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Card Transactions

> A card transaction is defined as a transaction that occurs on a customer issued card.

## Card Transactions

All Synctera payment types utilize the common `/transactions` resource - see [API reference](/v2/reference/gettransactionsbatchpayments) for details.

### Transaction Flows

The flow of a transaction is split into two major components:

<CardGroup>
  <Card title="Funding request" icon="square-1" iconType="solid" horizontal href="/v2/docs/card-transactions#funding-request" />

  <Card title="Clearing" icon="square-2" iconType="solid" horizontal href="/v2/docs/card-transactions#clearing" />
</CardGroup>

### Funding Request

Funding requests are initiated at the time of card usage. When a cardholder initiates a transaction, the merchant sends a request to the network. The network then sends a funding request to Synctera, expecting an approved or denied response. A [Pending Transaction](/v2/reference/gettransactionsbatchpayments) is created when the funding request is received, which publishes a [webhook](/v2/docs/webhooks-guide)) on the `transaction.pending.created` topic with initial status `PENDING`.

Synctera then makes a determination on whether to approve or decline the funding request. See [declined transactions](#declined-transactions) for more details.

While evaluating the funding request, the [Pending Transaction](/v2/reference/gettransactionsbatchpayments) may be updated with supplemental data gathered during the process. A `transaction.pending.upated` [webhook](/v2/docs/webhooks-guide) is published when the transaction is updated. For example, [enhanced transaction](#enhanced-transactions) information may be added.

#### Funding Request Flow

```mermaid mermaid theme={"system"}
%%{init: {"fontFamily": "sans-serif"}}%%
sequenceDiagram
Customer->>Merchant: Initiate transaction
Merchant->>Network: Request
Network->>Synctera: Funding request
Synctera->>FinTech: Pending transaction created webhook
Synctera->>Synctera: Evaluate funding request
Synctera->>FinTech: Pending transaction updated webhook
Synctera-->>Network: Response
Network-->>Merchant: Response
```

In addition, the FinTech can elect to participate in the funding request authorization flow - see [FinTech in the auth flow](#fintech-in-the-auth-flow) - which adds an additional decision point to the evaluation.

### Clearing

The transaction is not fully complete until it has cleared. The clearing process causes a transaction to change from **pending** to **posted**. This is when money actually moves. Note that **pending** and **posted** transactions are distinct resources - see [API reference](/v2/reference/gettransactionsbatchpayments) for more details.

After the funding request is approved - sometimes hours - the merchant initiates a request to the network for retrieving the funds for all of their pending transactions. Synctera receives the clearing notification, updates the [Pending Transaction](/v2/reference/gettransactionsbatchpayments) and creates a [Posted Transaction](/v2/reference/gettransactionsbatchpayments).

Two [webhooks](/v2/docs/webhooks-guide) are published when clearing is complete. First, `transaction.pending.updated` when [Pending Transaction](/v2/reference/gettransactionsbatchpayments) status is changed to `CLEARED`. Second, `transaction.posted.created` when the [Posted Transaction](/v2/reference/gettransactionsbatchpayments) is created.

#### Clearing Flow

```mermaid mermaid theme={"system"}
%%{init: {"fontFamily": "sans-serif"}}%%
sequenceDiagram
Merchant->>Network: Request
Network->>Synctera: Notification
Synctera->>FinTech: Pending transaction updated webhook
Synctera->>FinTech: Posted transaction created webhook
```

### Declined Transactions

Transactions may be declined for various reasons, including:

* Insufficient funds
* Suspected fraud
* Customer or account in bad standing
* Gateway ([FinTech in the auth flow](#fintech-in-the-auth-flow))
* [Network Stand-In](#network-stand-in-scenario)
* Address Verification Service (AVS) did not match address on file

When a transaction is declined, the status is updated to `DECLINED`. In most cases, a `transaction.pending.updated` will be issued to signal change of status. However, in the case of network declination, there will only be a `transaction.pending.created` webhook with initial status of `DECLINED`.

The `data.reason` field of the [Pending Transaction](/v2/reference/gettransactionsbatchpayments) body contains the reason for why the transaction was declined. Below is a list of reasons and their sources:

Customer/account standing:

* `NO_CHECKING_ACCOUNT`
* `NO_SAVINGS_ACCOUNT`
* `NO_CREDIT_ACCOUNT`
* `CLOSED_ACCOUNT`

Fraud:

* `SUSPECTED_FRAUD`

Ledger:

* `INSUFFICIENT_FUNDS`
* `DISABLED_PAYMENT_TYPE`
* `BALANCE_VIOLATION`
* `DUPLICATE_TRANSACTION`
* `SPEND_CONTROL_VIOLATED` (see [Spend Controls](/v2/docs/spend-controls-guide))

Network stand-in:

* `NETWORK_DECLINED`

<Info>
  For network declined transactions, there will be additional details under `data.user_data.network_decline_details` of the [Pending Transaction](/v2/reference/gettransactionsbatchpayments) body.
</Info>

Gateway:

* `GATEWAY_DECLINED`
* `GATEWAY_ERROR`

Address Verification Service (AVS):

* `ADDRESS_VERIFICATION_FAILED`

General purpose:

* `TRANSACTION_NOT_PERMITTED`

<Info>
  The list of possible decline reasons is subject to grow, so code should be written defensively around processing declined transactions.
</Info>

### Network Stand-In Scenario

Stand-in scenario happens when a funding request from the network is not responded to in time, so the network must *stand in* to be the decision maker. It is intended to be a fallback mechanism and not to be consistently relied upon, as there is less control over the decision which may result in undesired money movement.

In rare cases, Synctera may never recieve a funding request and only be informed that a transaction has taken place after the fact. In this case, there will only be a [Posted Transaction](/v2/reference/gettransactionsbatchpayments), no [Pending Transaction](/v2/reference/gettransactionsbatchpayments).

### Card Transaction Simulations

Synctera provides a variety of endpoints that simulate card transactions. These endpoints mimic how real transaction will look in a production environment. This gives FinTechs the tools to develop and test their application against the different types of card transactions without any real money movement or financial impact.

All card transaction simulation endpoints are found under the `/cards/transaction_simulations` path - see [API reference](/v2/reference/simulateauthorization) for details. These endpoints can only be used in the [Synctera Sandbox](/v2/reference/need-to-know#sandbox) environment.

This guide will explain how to simulate a selection of typical transaction scenarios.

#### Merchant Information Fields

Many of these endpoints require a `card_acceptor` object, which contains merchant information:

<CodeGroup>
  ```json JSON theme={"system"}
  {
    "address": "address",
    "city": "city",
    "country": "country",
    "mcc": "mcc",
    "name": "name",
    "state": "state",
    "zip": "zip"
  }
  ```
</CodeGroup>

The `mcc` (MCC - Merchant Category Code) field is a universal code assigned to merchants for the purpose of classifying the type of goods and services they provide.

In addition, the top level `mid` (MID - Merchant Identification Number) field is sometimes required. This is a unique identifier assigned to all merchants that process card transactions.

For simulations, the content used for `card_acceptor` and `mid` is not neccesarily important. However, merchant information is often crucial for [FinTech in the Auth Flow](#fintech-in-the-auth-flow).

#### 1. Authorization & Clearing

This describes the typical case where a cardholder purchases something from a physical or online merchant. The transaction amount is authorized, then later cleared. To simulate this scenario, an **authorization**, then **clearing** is performed. Note that an **authorization** equates to a [funding request](#funding-request).

To simulate, first call [Simulate authorization](/v2/reference/simulateauthorization), providing the appropriate `card_id`, along with the authorization `amount`. This will generate an **authorization** (funding request), which applies a hold for the given amount of money and creates a [Pending Transaction](/v2/reference/gettransactionsbatchpayments). On a successful call, a transaction `token` is generated. The `token` is needed for clearing.

Next, call [Simulate clearing or refund](/v2/reference/simulateclearing) with the same `amount` as was used in the **authorization** and `original_transaction_id` set to the **authorization** transaction `token`.

#### 2. Authorization Adjustment

In some circumstances, a merchant may want to authorize for a different amount than what is ultimately cleared. For example, at a gas pump, it is common for a customer to pre-authorize up to a certain amount, but only be charged for the amount of gas that was actually pumped. In this case, an initial **authorization** is created for the pre-authorized amount. Once the final sale price is determined, an **authorization advice** is performed to adjust the hold. Like the previous scenario, a final **clearing** is done to capture the funds.

To simulate, first call [Simulate authorization](/v2/reference/simulateauthorization) like in the previous example and retain the transaction `token`.

Next, issue an **authorization advice** with [Simulate authorization advice](/v2/reference/simulateauthorizationadvice), providing the new `amount` and `original_transaction_id` (`token`).

Finally, issue the **clearing** with [Simulate clearing or refund](/v2/reference/simulateclearing), using the final `amount` from the **authorization advice** and `original_transaction_id` set to the transaction `token` from the original **authorization** response.

#### 3. Reversals & Refunds

**Reversals** and **refunds** both refer to the undoing of a previous action, the only difference being the action that is being undone. **Reversals** release an existing **authorization** hold and **refunds** undo a cleared transaction and move funds back to a cardholder's card.

To simulate a **reversal**, an existing **authorization** hold must already exist. To issue the reversal, call [Simulate reversal](/v2/reference/simulatereversal), providing the full **authorization** `amount` and `original_transaction_id` set **authorization** transaction `token` for `original_transaction_id`.

Likewise, to simulate a **refund**, a cleared transaction must already exist. To issue the refund, call [Simulate clearing or refund](/v2/reference/simulateclearing), providing the final `amount` from the **clearing** and the original **authorization** transaction `token` for `original_transaction_id`.

#### 4. Single Message

All above listed scenarios involve **dual message** transactions. Meaning, the transaction occurs in two parts: **authorization**, then **clearing**. However, there are also **single message** transactions, where **authorization** and **clearing** occur in a single action. Common examples include PIN-debit transactions and ATM transactions.

Below are descriptions of the common **single message** simulation endpoint use cases:

* [Simulate financial](/v2/reference/simulatefinancial): This endpoint is used to simulate a PIN-debit transaction - when a cardholder provides their PIN code at the time of purchase. The `amount` and `card_id` must be provided.
* [Simulate ATM withdrawal](/v2/reference/simulatewithdrawal): This endpoint simulates a cash withdrawal from an ATM (Automated Teller Machine). Similarly, `amount` and `card_id` must be provided.

#### 5. L2L3 data

Level 2 and Level 3 card processing data provide detailed information about a transaction. These additional fields within a payment message offer a comprehensive view of the specific items or services being paid for.

To simulate a l2l3, an existing cleared transaction must already exists. Meaning, the transaction occurs in three parts: authorization, clearing then l2l3.

To issue a l2l3, call [Simulate l2l3](/v2/reference/simulatel2l3), providing the clearing transaction token for original\_transaction\_id and the l2l3 data.

### Enhanced Transactions

By default, transaction metadata (merchant name, location, category, etc.) is provided by the network - found in the transaction `data.user_data` object. For the most part, this information is limited and often inconsistently formatted.

If desired, a card product can be configured with a supported third party provider to add enhanced metadata to each transaction. Synctera's current supported enhanced transaction provider is [MX](https://www.mx.com).

For example, given the following network provided merchant name and MCC (merchant category code):

<CodeGroup>
  ```json JSON theme={"system"}
  {
    "mcc": "4816",
    "name": "EIG*HOSTGATOR.COM"
  }
  ```
</CodeGroup>

Enhanced transaction can provide a cleanly formatted name and consistent category:

<CodeGroup>
  ```json JSON theme={"system"}
  {
    "category": "Hosting",
    "enhanced_description": "HostGator"
  }
  ```
</CodeGroup>

Enhanced transaction information is found in the transaction `data.user_data.enhanced_transaction` object. `enhanced_raw` contains the complete set of data received from the enhanced transaction provider.

<CodeGroup>
  ```json JSON theme={"system"}
  {
    "category": "Hosting",
    "enhanced_description": "HostGator",
    "enhanced_raw": [
      {
        "amount": 12.75,
        "categorized_by": 13,
        "category": "Hosting",
        "category_guid": "CAT-b74fdd98-4391-8015-eafa-e9ca0fad3bee",
        "described_by": 6,
        "description": "HostGator",
        "extended_transaction_type": null,
        "id": "2ffa6d90-e4d0-47e3-a290-17240e7a3ae4",
        "is_bill_pay": false,
        "is_direct_deposit": false,
        "is_expense": null,
        "is_fee": null,
        "is_income": false,
        "is_international": null,
        "is_overdraft_fee": false,
        "is_payroll_advance": false,
        "is_subscription": false,
        "memo": "ad0f57f1-f823-4ba7-8563-a1c4aa458371",
        "merchant_category_code": 4816,
        "merchant_guid": "MCH-dae1c6b5-292b-4d3e-ba15-998ab24a79c2",
        "merchant_location_guid": null,
        "original_description": "EIG*HOSTGATOR.COM",
        "type": "DEBIT"
      }
    ]
  }
  ```
</CodeGroup>

### L2/L3 Data

Some transactions contain Level 2 / Level 3 (L2/L3) data, which provides much more detailed information about the transaction. For details on L2/L3 data, see [this article](/v2/docs/level-2-level-3-data).

When available, L2/L3 data is received from the processor as part of card transaction clearing events/webhooks, i.e. as a transaction transitions from authorized/pending to cleared/posted.

<Info>
  On occasion, for a single transaction with Level 2/Level 3 data, we may receive a clearing event followed by the L2/L3 data several hours later. As a result, a transaction might initially be posted without detailed L2/L3 data, only to be subsequently updated when this additional information becomes available.
</Info>

When available, L2/L3 data is found in the transaction user\_data.l2l3 object on a posted transaction. Example:

<CodeGroup>
  ```json JSON theme={"system"}
  {
    "l2l3": {
      "enhanced_data_id": "e3434344d343434dfdf3564645jk4282328032903j323923023u4h434343",
      "financial": {
        "tax_id": "123456789",
        "total_tax_amount_indicator": "D"
      },
      "fleet_emv": {
        "vat_tax_rate": "0",
        "service_type": "S",
        "odometer_reading": "0000000",
        "fuel_net_amount": 1000,
        "fuel_gross_amount": 1000,
        "fuel_unit_price": "358.9",
        "fuel_unit_of_measure": "G",
        "fuel_quantity": "2.786",
        "expanded_fuel_type": "01",
        "type_of_purchase": "3",
        "non_fuel_gross_amount": 1625,
        "non_fuel_item_details": [
          {
            "product_code": "ZC"
          }
        ]
      },
      "inventory_details": [
        {
          "description": "Edelmann 92397 Power Steering Press",
          "item_discount_amount_indicator": "C",
          "item_discount_applied_indicator": "N",
          "item_extended_amount": 5048,
          "item_extended_amount_indicator": "D",
          "product_code": "B00J5W6CZQ",
          "quantity": "1",
          "unit_of_measure": "PCE"
        }
      ]
    }
  }
  ```
</CodeGroup>

### FinTech in the Auth Flow

#### Authorization Gateway

An authorization Gateway enables a FinTech to optionally take part in the funding request decision of a card transaction’s authorization cycle. The FinTech receives an authorization request via the configured Gateway to either approve or decline the card transaction based on the FinTech's own business logic.

If the fintech opts not to participate in the auth flow Synctera will use default authorization logic to authorize the transactions. The fintech does not have to participate unless there is additional approval logic they would like to incorporate into the decision process that is not supported by Synctera or proprietary in nature.

The authorization request must be responded to within a firm timeout window of **1.5 seconds**. Synctera will default to declining the funding request if a response is not received within the timeout window.

The information in the authorization request includes, but is not limited to:

* Customer/Account/Card ID's
* Available balance
* Merchant information

<CodeGroup>
  ```json JSON theme={"system"}
  {
    "customer_id": "2b9cc6f2-d0bd-4d9d-aa20-5e53355f9469",
    "account_id": "0221e0a7-7774-48a4-8521-e678ec09a53a",
    "transaction_id": "9b59fc80-9bf5-4749-8dd2-511f183becf2",
    "card_id": "6128498a-85a9-4bd8-a3ea-bfe3717b64f6",
    "card_format": "PHYSICAL",
    "last_four": "1234",
    "type": "card_transaction",
    "user_transaction_time": "2022-03-25T10:41:01-04:00",
    "settlement_date": "0001-01-01T00:00:00Z",
    "amount": {
      "amount": 100,
      "currency": "USD",
      "currency_conversion": {
        "original_amount": 100,
        "conversion_rate": 1,
        "original_currency_code": "840",
        "original_currency_code_alpha": "USD"
      }
    },
    "balance": {
      "available_balance": 4210000
    },
    "merchant": {
      "mid": "4445001899609",
      "mcc": "5411",
      "name": "WHOLEFDS EGW 101",
      "city": "EDGEWATER",
      "state": "NJ",
      "postal_code": "07020",
      "country_code": "USA",
      "sub_merchant_id": "",
      "payment_facilitator_id": ""
    },
    "user": {},
    "network_fraud": {
      "transaction_risk_score": 18
    },
    "network": "MASTERCARD",
    "subnetwork": "",
    "dc_sign": "debit",
    "pos": {
      "pan_entry_mode": "MAG_STRIPE",
      "pin_present": false,
      "terminal_id": "10000000",
      "cvv_presence": "CVV1"
    },
    "processor": "MARQETA",
    "processor_data": {}
  }
  ```
</CodeGroup>

Addionally, if [enhanced transactions](#enhanced-transactions) are enabled for the FinTech, this information will also be included.

To signal an authorization request decision, the FinTech must reply with the appropriate HTTP code:

* HTTP code `200`: **approve** the funding request
* HTTP code `402`: **decline** the funding request

Note that while HTTP code `402` is conventional, any code other than `200` will also be interpreted as a **decline**.

#### FinTech Included in Funding Request Authorization Flow

```mermaid mermaid theme={"system"}
%%{init: {"fontFamily": "sans-serif"}}%%
sequenceDiagram
Customer->>Merchant: Initiate transaction
Merchant->>Network: Request
Network->>Synctera: Funding request
Synctera->>FinTech: Pending transaction created webhook
Synctera->>Synctera: Evaluate funding request
Synctera->>FinTech: Authorization request
FinTech->>FinTech: Evaluate authorization request
FinTech-->>Synctera: Response
Synctera->>FinTech: Pending transaction updated webhook
Synctera-->>Network: Response
Network-->>Merchant: Response
```

#### Sandbox Implementation

1. Create a new Gateway configuration via [Synctera API](/v2/reference/listcards)
2. Generate an authorization [card transaction simulation](#card-transaction-simulations) and ensure the Gateway endpoint successfully recieves and responds to the request

<Info>
  For local testing, [ngrok](https://ngrok.com) or [beeceptor](https://beeceptor.com) can be used to produce a publicly accesable URL that terminates to a local development endpoint.
</Info>

#### Gateway Endpoint Configuration

To create a Gateway, a valid, publicly accessable URL must be supplied, along with a list of Card Product ID's that will utilize the Gateway. Additionally, customer headers may be supplied that will be included in authorization calls to the Gateway. If not supplied, `active` status is set to `true` by default. Gateways may be turned off by setting this field `false`.

Note that a Card Product may not be configured on more than one active Gateway at a time.

<CodeGroup>
  ```bash Shell theme={"system"}
  curl \
    -X POST \
    -H "Authorization: Bearer $apikey" \
    -H "Content-Type: application/json" \
    $baseurl/v0/cards/gateways \
    --data-binary '
    {
      "active": true,
      "url": "https://example.com",
      "custom_headers": {
        "key": "value"
      },
      "card_products": [
        "41e81dff-05d4-4421-b7f0-149e3a536979",
        "e8361f07-1e7d-440c-91bd-def3e18a907f"
      ]
    }'
  ```
</CodeGroup>
