Contact Us

Chargeback Agent API

Upload dispute documents and receive a recommendation, recommended actions, and a formal response letter. Requests authenticate by secret key.

Agent Lifecycle

A case moves through these steps:

  1. Initialize agent with a chargeback case (POST)
  2. Attach documents to the case (POST, PUT)
  3. Agent recommendation (GET)
  4. Generate response letter (POST)
  5. Read response letter (GET)

Repeat the attach and recommendation steps until the case is ready. Each recommendation reports its confidence and suggests further evidence to attach.

When the recommendation is ready, download the PDF in two steps:

  1. Request download (GET)
  2. Download document (GET)

Initialize Chargeback Case

Initialize an agent session with chargeback case details. The response carries the case id for later requests. No field is required, and a complete request body gives the best results.

A blank field is treated as omitted. null and an empty string mean the same thing. On initialize the field stays unset, and on update the field is cleared.

Request

POST /chargeback
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn
{
  data: {
    agent: Boolean | Object,
    amount: Number,
    cardNetwork: String,
    cardholderName: String,
    currency: String,
    disputeDate: String,
    dueDate: String,
    maskedCardNumber: String,
    merchantIdentifier: String,
    merchantName: String,
    merchantUrl: String,
    reasonCode: String,
    reasonDescription: String,
    referenceNumber: String,
    transactionDate: String
  }
}
FieldTypeDescription
agent Boolean or Object Chargeback Agent behavior. true follows the organization's settings, false disables agent research, and an object sets each behavior. Default true. Accepted on the request and never returned. See agent settings
amount Number Disputed amount in major units, such as dollars
cardNetwork String Card network of the disputed transaction, such as "visa". Scopes reasonCode matching when maskedCardNumber lacks the leading digits
cardholderName String Name of the disputing cardholder
currency String (ISO 4217) Transaction currency. Default "USD"
disputeDate Date (ISO 8601) Date the dispute was raised
dueDate Date (ISO 8601) Deadline for the merchant response
maskedCardNumber String Masked card number with its leading digits, such as "424242******4242". The leading digits scope reasonCode matching. A number without leading digits, such as "******4242", uses cardNetwork instead
merchantIdentifier String Organization's identifier for the merchant defending the case
merchantName String Merchant trading name
merchantUrl String (URL) Merchant public website. The agent reads the business description and dispute policies on the site for the recommendation. The address is normalized, so the returned value can differ from the value sent
reasonCode String Card network reason code. Matching accepts the code formats processors export when the card network is known from maskedCardNumber or cardNetwork. Without a card network, only a code cataloged exactly as written resolves
reasonDescription String Dispute description in the caller's wording. Confirms which dispute a reasonCode names when the code uses another network's scheme. Never overrides reasonCode
referenceNumber String Dispute reference number from the processor or card network
transactionDate Date (ISO 8601) Date of the disputed transaction

Response

The response returns the submitted details with the case id and status. The reason code defenseRequirements are available immediately. Each requirement changes to satisfied: true as evidence arrives. Meet as many requirements as possible to maximize success.

evidenceSuggested and evidenceProvided describe the evidence types that meet defense requirements, in merchant-friendly terms. recommendedActions lists more specific actions.

{
  data: {
    amount: Number,
    cardNetwork: String,
    cardholderName: String,
    currency: String,
    defenseRequirements: [{ requirement: String, satisfied: Boolean }],
    disputeDate: String,
    dueDate: String,
    evidenceProvided: [String],
    evidenceSuggested: [String],
    id: String,
    maskedCardNumber: String,
    merchantIdentifier: String,
    merchantName: String,
    merchantUrl: String,
    reasonCode: String,
    reasonDescription: String,
    referenceNumber: String,
    status: "pending",
    transactionDate: String
  }
}
FieldTypeDescription
defenseRequirements Array of Objects Proof the reason code requires of the defense. Every item is satisfied: false until the agent assesses attached documents. Empty when the case has no reasonCode or an unrecognized one
evidenceProvided Array of Strings Evidence categories with at least one satisfied requirement. Empty at initialization, until a document is attached or the agent retrieves evidence
evidenceSuggested Array of Strings Evidence categories still to collect, highest impact first. Every category a merchant can supply when reasonCode is absent or unrecognized
id String (uuid) Identifier for the agent session
status String (enum) pending until a document is attached

Agent Settings

The agent field controls agent behavior for the case. The field is accepted on the request and never returned.

ValueDescription
Omitted or true Every setting keeps its default
false Every setting is false
Object Named settings take the posted value, and the rest keep their defaults
Agent settings object

Settings are fixed when the case is created. An agent field posted to update answers 400 Bad Request.

Defaults vary by organization. Contact Findustry AI to discuss customizations.

{
  data: {
    agent: {
      researchTransactionDetails: Boolean,
      submitDisputeToProcessor: Boolean,
      useMerchantMemories: Boolean,
      writeResponseLetter: Boolean
    }
  }
}
SettingTypeDescription
researchTransactionDetails Boolean Agent research of transaction details beyond the case and its attached documents
submitDisputeToProcessor Boolean Agent filing of the response with the issuer or processor. When false, the agent provides the response for the organization to file
useMerchantMemories Boolean Agent use of past research and interactions for the case. By default, the agent remembers which evidence types a merchant can or cannot provide
writeResponseLetter Boolean Agent writing of a response letter for the case. When false, POST /chargeback/:id/letter answers 400 Bad Request

Evidence Categories

evidenceProvided and evidenceSuggested use the lowercase values below.

ValueDescription
cardholder communication Correspondence with the cardholder, such as email conversations or post-payment agreements
cardholder transaction history Cardholder's prior undisputed transactions with the merchant
delivery confirmation Proof the order reached the cardholder, such as signed delivery confirmation or courier tracking
evidence of product quality Evidence the goods were as described, such as condition photographs or a certificate of authenticity
order confirmation Records of the order as placed, such as the confirmation email sent to the cardholder
proof of cardholder non-contact / non-return Proof the cardholder neither contacted the merchant nor returned the merchandise
proof of digital goods usage Proof digital content was delivered, such as purchase and download timestamps or access logs
proof of services provided Proof services were provided and used, such as an invoice or a service confirmation
recurring billing records Subscription billing and cancellation records, such as the billing notice sent to the cardholder
refund and return policies Merchant's published policies and their acceptance, such as a checkout acceptance screenshot
refund receipt Refund and credit records, such as proof a credit was already issued
transaction authorization Payment platform's record of the transaction and its authorization, such as the sales slip, AVS and CVV results, or device fingerprints

Update Case Details

Post only the fields to change. Fields omitted from data stay unchanged. The request accepts the same fields as initialize, except agent, which answers 400 Bad Request.

A blank field clears the value on the case. null and an empty string mean the same thing. Every field can be cleared except referenceNumber. Clearing referenceNumber answers 400 Bad Request.

Request

POST /chargeback/:id
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn
{
  data: {
    dueDate: String,
    merchantUrl: String
  }
}

Response

The response returns the updated case in the same shape as initialize.

Delete Case

Delete a case and its attached documents. Deleted cases and their documents cannot be retrieved.

Request

DELETE /chargeback/:id
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn

Response

{
  data: {
    id: String,
    status: "deleted"
  }
}

Attach Documents to Case

Post the uploadFilenames, then send each file's contents to its signed putUrl, as in document upload. The next recommendation assesses each attached document.

Attach documents to cases initialized with POST /chargeback. A session initialized with direct upload takes its documents at initialization, and this endpoint answers 400 Bad Request for it.

Request

POST /chargeback/:id/upload
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn
{
  data: {
    uploadFilenames: [String]
  }
}

Response

{
  data: {
    id: String,
    putUrls: [
      {
        evidenceId: String,
        putUrl: String,
        uploadFilename: String
      }
    ]
  }
}

Each signed putUrl is valid for five minutes. Each evidenceId identifies the attached document for evidence deletion.

Delete Evidence from Case

Delete a single attached document by its evidenceId. The case and its remaining documents are unchanged. Deleted documents cannot be retrieved.

The agent reassesses the case about thirty seconds after the last deletion, so a burst of deletions is assessed once. The recommendation shows status: "processing" during reassessment and completes with the remaining evidence.

Deleting evidence also retires any response letter already written, because the letter argued from the deleted document. GET /chargeback/:id/letter answers 404 Not Found until the next response letter request, which rewrites the letter from the remaining evidence. To replace a letter and keep the evidence, discard the letter instead.

Request

DELETE /chargeback/:id/evidence/:evidenceId
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn
ParameterTypeDescription
evidenceId String (uuid) Identifier for the attached document, returned by attach
id String (uuid) Identifier for the agent session

Response

{
  data: {
    id: String,
    status: "deleted"
  }
}
FieldTypeDescription
id String (uuid) Identifier for the deleted evidence
status String (enum) Value deleted

Agent Recommendation

After each document upload, the agent assesses the case and provides a recommendation and recommended actions. The response shows status: "processing" while the agent works. Assessment takes several minutes.

Every status returns the submitted case fields and the current status. On completion, the response adds the recommendation fields.

Request

GET /chargeback/:id
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn

Response

Processing

{
  data: {
    amount: Number,
    cardNetwork: String,
    currency: String,
    // ...the case fields as submitted...
    defenseRequirements: [{ requirement: String, satisfied: Boolean }],
    evidenceProvided: [String],
    evidenceSuggested: [String],
    id: String,
    status: "processing"
  }
}

Complete

{
  data: {
    amount: Number,
    cardNetwork: String,
    currency: String,
    // ...the case fields as submitted...
    confidence: Number,
    defenseRequirements: [{ requirement: String, satisfied: Boolean }],
    evidenceProvided: [String],
    evidenceSuggested: [String],
    id: String,
    merchantAttachments: [{ evidenceId: String, uploadFilename: String }],
    merchantIdentifier: String,
    priority: String,
    recommendation: String,
    recommendedActions: [String],
    referenceNumber: String,
    status: String
  }
}
FieldTypeDescription
confidence Number Confidence in the recommendation, 0 to 100
defenseRequirements Array of Objects requirement and its satisfied flag, set by the assessment from the attached documents. The set stays stable for the life of the case. Evidence matching no known requirement is appended
evidenceProvided Array of Strings Satisfied evidence categories
evidenceSuggested Array of Strings Unsatisfied evidence categories that would strengthen the defense. Updated with each attachment or deletion
id String (uuid) Identifier for the agent session
merchantAttachments Array of Objects Current case documents, after deletions. Each object carries the evidenceId for evidence deletion and the uploadFilename
merchantIdentifier String merchantIdentifier posted on the case. Absent when the case has none
priority String (enum) normal, high
recommendation String respond, accept, hold. accept means the merchant accepts the chargeback, and the agent writes no response letter
recommendedActions Array of Strings Actions that can strengthen the merchant defense
referenceNumber String Dispute reference number from the processor or card network
status String (enum) pending, queued, processing, complete, error

When processing fails, the response carries a message in place of the recommendation.

{
  data: {
    id: String,
    message: String,
    status: "error"
  }
}

Generate Response Letter

When the recommendation is satisfactory, request a formal response letter. The response shows status: "processing" while the agent works. Writing takes several minutes. Read the letter until it is ready, or register a web hook.

The agent writes a letter once, and only on request. A repeat request returns the existing letter. To replace a letter, discard it first.

This request takes no body. A request with a body answers 400 Bad Request.

Request

POST /chargeback/:id/letter
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn

Response

First request

{
  data: {
    id: String,
    status: "processing"
  }
}

Requested again, letter ready

{
  data: {
    id: String,
    responseLetter: String,
    status: "complete"
  }
}

Read Response Letter

Poll the requested letter until it is ready. The request answers 404 Not Found when the letter was never requested, or was retired by discarding it or by deleting evidence.

Request

GET /chargeback/:id/letter
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn

Response

Processing

{
  data: {
    id: String,
    status: "processing"
  }
}

Complete

{
  data: {
    id: String,
    responseLetter: String,
    status: "complete"
  }
}
FieldTypeDescription
id String (uuid) Identifier for the agent session
responseLetter String (markdown) Complete rebuttal letter for the acquirer and card networks

Not requested

HTTP 404
{
  errors: [
    {
      status: 404,
      title: String,
      detail: String
    }
  ]
}

Discard Response Letter

Discard the response letter for a case, then request a letter to write a new one. The attached documents stay attached to the case.

Discarding a letter in progress abandons it, and the agent delivers no letter from that work. A case with no letter to discard answers 404 Not Found, as reading the letter does. This request takes no body. A request with a body answers 400 Bad Request.

Request

DELETE /chargeback/:id/letter
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn

Response

{
  data: {
    id: String,
    status: "deleted"
  }
}

Direct Upload and Download

Initialize with Direct Upload

Direct upload reads chargeback details from an existing file. Chargeback Agent requires configuration to recognize upload formats before use. Contact support@findustryai.com to configure formats.

Details

Initialize an agent session by posting the uploadFilename of the document to upload. Filenames may be repeated across sessions. The response provides the signed putUrl for the file contents.

A direct-upload session carries one document. To assess several documents together, initialize a case with POST /chargeback and attach each document to it.

Request

POST /chargeback/upload
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn
{
  data: {
    uploadFilename: String
  }
}
FieldTypeRequiredDescription
uploadFilename String (filename) Yes Name of the file to upload. A filename, never a path

Response

{
  data: {
    id: String,
    putUrls: [
      {
        evidenceId: String,
        putUrl: String,
        uploadFilename: String
      }
    ]
  }
}
FieldTypeDescription
id String (uuid) Identifier for the agent session
putUrls Array of one Object uploadFilename, its signed putUrl for the document PUT, and the evidenceId for evidence deletion. The putUrl is valid for five minutes

Document Upload

After initialization, send the file's contents to its signed putUrl. The URL is valid for five minutes.

PUT ${putUrl}
Content-Type: ${contentType}

Example using curl:

curl -X PUT -T file.pdf
"https://bucket.s3.amazonaws.com/file.pdf?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Expires=300&X-Amz-Signature=..."

Document Export

Document export assembles case files in custom formats, such as PDF or XLSX. Chargeback Agent requires configured export formats before use. Contact support@findustryai.com to configure formats.

Details

The agent produces an export in the requested format. The response shows status: "processing" while the agent works. Export takes several minutes. When the download is ready, the response returns a getUrl.

Request

GET /chargeback/:id/download
Authorization: sk_findustryai_kkkkkkkkkkkk_nnnnn
Multiple Formats

When several formats are configured, the format query parameter selects one. Without format, the response returns the default format.

Response

Processing

{
  data: {
    id: String,
    status: "processing"
  }
}

Complete

{
  data: {
    id: String,
    getUrl: String
  }
}
FieldTypeDescription
getUrl String (URL) Signed URL for the document
id String (uuid) Identifier for the agent session

Document Download

The download request returns a signed getUrl. The URL is valid for five minutes.

Example using curl:

curl -L -o file.pdf
"https://bucket.s3.amazonaws.com/file.pdf?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Expires=300&X-Amz-Signature=..."

Web Hooks

Register a web hook in place of polling the agent status. The event body carries the same data as the HTTP response, plus metadata. Security headers authenticate each delivery.

Event Metadata

{
  metadata: {
    attempt: Number,
    event: String,
    id: String,
    timestamp: Number,
    type: "webhook",
    webhook: String
  },
  data: {
    // …
  }
}
FieldTypeDescription
attempt Number (integer) Delivery attempt count, starting at 1
event String chargeback:copilot for the agent result, chargeback:letter for the response letter
id String (uuid) Event identifier, unchanged across attempts. Idempotency token
timestamp Number (milliseconds) Attempt time. Changes with each attempt
type String Value webhook
webhook String (uuid) Endpoint receiving delivery

Acknowledgment

CodeDescriptionResultRetried
2XX Success Delivered No
401 Unauthorized Failed authentication No
429 Too many requests Rate limited Yes, with backoff
5XX Server error Receiver failed Yes, with backoff
504 Gateway Timeout No response after 15 seconds, or unreachable host Yes, with backoff
* Unknown error Client error, including 3XX No

Undeliverable Messages

Findustry AI retries an undeliverable message for up to one hour. When a message still fails after one hour, Findustry AI contacts the organization to discuss delivery rates.

Authentication

Each web hook delivery carries an HMAC signature in the X-Webhook-Signature header. See Web Hooks authentication.