---
id: refund-payment
title: Refund Payment
description: Guided UI for issuing full or partial refunds with reason codes and audit trails.
sidebar_position: 33
---

import {
  CodeBlock,
  PropsMarkdownTable,
  PartsMarkdownTable,
  getWebcomponentsVersion,
  getComponentParts,
  getPropsFromDocs,
  ComponentBox,
  setUpMocks,
} from '../helpers';
import docsJson from '../docs.json';
import componentTreeJson from '../component-tree.json';
import '@justifi/webcomponents/dist/module/justifi-refund-payment';

{setUpMocks()}

## Overview

Component to render a form for partially or fully refunding a payment based on a provided payment ID.

## Props, Events & Methods

<PropsMarkdownTable
  props={getPropsFromDocs('justifi-refund-payment', docsJson)}
/>

### Events

- `submit-event`: Emits when the refund is created; payload includes `refund_id` and amount.
- `error-event`: Fires when validation or network calls fail.

### Public methods

1. `refundPayment()` – Trigger the refund flow programmatically (useful if the component is inside a modal with custom buttons).

# Authorization

---

<p>
  Authorization is performed by passing a web component token as{' '}
  <code>auth-token</code>.
</p>
<ul>
  <li>
    <strong>Web Component Token</strong>: These tokens are generated by your
    backend services using the [Web Component Tokens
    API](https://docs.justifi.tech/api-spec#tag/Web-Component-Tokens/operation/CreateWebComponentToken).
    Each token can be scoped to perform a set number of actions and is active
    for 60 minutes. When creating a web component token for this specific
    component you'll need to use the role: `write:account:account_id`. Make sure
    the value for `account_id` matches the prop you also pass separately.
  </li>
</ul>

# Example Usage

---

<ComponentBox>
  <justifi-refund-payment
    payment-id="payment_123"
    account-id="acc_123"
    auth-token="web-component-token"
  />
</ComponentBox>

---

<CodeBlock>{`<!DOCTYPE html>
<html dir="ltr" lang="en">

<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="width=device-width, initial-scale=1.0, minimum-scale=1.0, maximum-scale=5.0" />
  <title>justifi-refund-payment</title>

  <script type="module" src="https://cdn.jsdelivr.net/npm/@justifi/webcomponents@${getWebcomponentsVersion()}/dist/webcomponents/webcomponents.esm.js"></script>

<script
  nomodule
  src="https://cdn.jsdelivr.net/npm/@justifi/webcomponents@${getWebcomponentsVersion()}/dist/webcomponents/webcomponents.js"
></script>

  <style>
    ::part(font-family) {
      font-family: georgia;
    }

    ::part(color) {
      color: darkslategray;
    }

    ::part(background-color) {
      background-color: transparent;
    }

    ::part(button) {
      padding: 0.375rem 0.75rem;
      font-size: 16px;
      box-shadow: none;
      border-radius: 0px;
      line-height: 1.5;
      text-transform: none;
    }

    ::part(button-disabled) {
      opacity: 0.5;
    }

    ::part(input) {
      border-color: #555;
      border-width: 1px;
      border-bottom-width: 1px;
      border-left-width: 1px;
      border-right-width: 1px;
      border-top-width: 1px;
      border-radius: 0;
      border-style: solid;
      box-shadow: none;
      font-size: 1rem;
      font-weight: normal;
      line-height: 1.5;
      padding: 0.375rem 0.75rem;
    }

    ::part(input-focused) {
      border-color: #333;
      box-shadow: 0 0 0 0.25rem rgba(0, 0, 0, 0.25);
    }

    ::part(input-invalid) {
      border-color: #8a2a35;
      box-shadow: 0 0 0 0.25rem rgba(244, 67, 54, 0.25);
    }

    ::part(input-invalid-and-focused) {
      box-shadow: 0 0 0 0.25rem rgba(244, 67, 54, 0.25);
      border-color: #8a2a35;
    }

    ::part(button-primary) {
      color: #333;
      background-color: transparent;
      border-color: #333;
    }

    ::part(button-primary):hover {
      background-color: rgba(0, 0, 0, .05);
      border-color: #333;
      color: #333;
    }
    </style>

</head>

<body>
  <justifi-refund-payment
    payment-id="payment_123"
    account-id="acc_123"
    auth-token="web-component-token"
    hide-submit-button="true"
  />

  <!-- Optional external button - this is only needed if the built in button is hidden via the hide-submit-button prop
   and the refund is submitted via provided refundPayment() method - see below. -->

  <button id="submit-refund-button">Submit Refund</button>
</body>

<script>
  (function () {
    var refundForm = document.querySelector("justifi-refund-payment");

    refundForm.addEventListener("submit-event", (event) => {
      /* this event is raised when the server response is received */
      console.log("server response received", event.detail.response);
    });

    refundForm.addEventListener("error-event", (event) => {
      /* here is where you would handle the error */
      console.error('error-event', event.detail);
    });

    /* manually call Refund with provided method, if built-in submit button is hidden */
    document.getElementById("submit-refund-button").addEventListener("click", async () => {
      const refundData = await refundForm.refundPayment();
      console.log('Refund data', refundData);
    });
  })();
</script>

</html>`}</CodeBlock>

## Theming & Layout

<PartsMarkdownTable
  parts={getComponentParts('justifi-refund-payment', componentTreeJson)}
/>
