Tax: VAT invoices and 1099s

Your legal details, EU VAT on self-billed invoices, the self-billing agreement, and 1099-NEC filing and delivery through your own filing provider.

Embed
Preview of the card
<a href="https://referalli.com/docs/tax"><img src="https://referalli.com/docs/_api/public/orgs/07f432f4-34b9-46a7-aaad-c0e395d2e4f9/spaces/2bf4f614-3630-4fbf-85f9-5ecafa6b7d97/pages/1ae3821a-c5c6-4d01-a00b-0a9db404ce8f/social-card.svg?v=3e7ae33eec8b" alt="Tax: VAT invoices and 1099s" width="600" height="315"></a>

Referalli issues the tax paperwork for the commissions you pay. Every payout comes with a self-billed invoice, which you issue on your partner's behalf. US partners also get a 1099-NEC, filed through a filing provider you connect.

Both documents need your legal identity:

curl -X PUT https://referalli.com/v1/org/tax-profile \
  -H "Authorization: Bearer $KEY" \
  -H "content-type: application/json" \
  -d '{
    "legalName": "Acme GmbH",
    "address": "Hauptstr. 1, 10115 Berlin",
    "country": "DE",
    "vatId": "DE123456789",
    "domesticVatBps": 1900,
    "viesCheck": true
  }'

Field

Meaning

legalName, address, country

Who you are on invoices and 1099s. country is a 2-letter ISO code.

vatId

Your EU VAT number. It's checked against each member state's format and stored normalised (de 123 456 789 becomes DE123456789).

ein

Your US employer identification number: the payer TIN on 1099s. It's stored as 12-3456789, and the audit log records only that it was set.

domesticVatBps

The VAT rate, in basis points (1900 = 19%), you add for VAT-registered partners in your own country.

viesCheck

When true, a partner's VAT number must be listed as registered in the EU's VIES register before it's accepted.

Every field is optional, and a call changes only the fields it sends. GET /v1/org/tax-profile returns them. Both require the owner, admin or finance role.

Self-billed invoices

Every payout carries an invoice that you issue for the partner. It holds:

  • a number that is sequential per merchant per year (SBI-2026-1, SBI-2026-2, …), with no gaps and no duplicates, even when runs are created at the same time;

  • the supplier (the partner: name and address from their tax form, plus their VAT number) and the customer (you, from your tax profile);

  • the commission lines, the net amount, any VAT, and the total;

  • the VAT treatment and the matching wording.

vatTreatment

When

VAT

reverse_charge

You and the partner are VAT-registered in different EU countries

None. The invoice says the customer accounts for VAT (Article 196, Council Directive 2006/112/EC).

domestic

The partner is VAT-registered in your country

Your domesticVatBps, added on top of the commission. The partner is paid the total, and the payout records vatMinor. Without a rate, no VAT is added and the invoice says so.

outside_scope

The partner has no VAT number, or one of you is outside the EU

None.

GET /v1/payouts/{id}/invoice returns the invoice as JSON. Add ?format=html for a printable page: use your browser's "Save as PDF". Partners get the same page from GET /v1/partner/payouts/{id}/invoice?format=html. Invoices issued before these fields existed still render.

Partner VAT numbers

A partner adds their EU VAT number in the portal (PUT /v1/partner/orgs/{orgId}/vat with {"vatId": "FR…"}), or you set it with PUT /v1/partners/{id}/vat. Send null to remove it. A number that doesn't match its country's format returns 400. With viesCheck on, one that VIES doesn't list as registered also returns 400, and an accepted one records vatVerifiedAt.

The self-billing agreement

Self-billing needs the partner's prior agreement. A VAT-registered partner accepts it once per merchant, in the portal or with POST /v1/partner/orgs/{orgId}/self-billing and {"accept": true}. GET on the same path returns the status and the current agreement version. Until a VAT-registered partner accepts, payout runs skip them with self_billing_agreement_missing. Their balance waits; nothing is lost. Partners without a VAT number aren't affected. Each invoice records the agreement version and the date it was accepted.

1099-NEC filing

US persons (partners with a W-9 on file) who were paid $600 or more in a calendar year get a Form 1099-NEC. Referalli works out who needs one, files the forms through your filing provider, and delivers each partner's Copy B.

Connect a filing provider

Filing uses your own provider account (BYOK); Referalli holds no filing credentials of its own.

curl -X PUT https://referalli.com/v1/org/tax-filing \
  -H "Authorization: Bearer $KEY" \
  -H "content-type: application/json" \
  -d '{"provider": "test"}'

provider

What it does

test (default)

Simulates filing. Every well-formed form is accepted at once and nothing reaches the IRS. Use it to try the whole flow.

tax1099

Files through your Tax1099 account. Send credentials: {"apiKey": "…"}; the key is encrypted at rest and never returned. The adapter hasn't been verified against Tax1099's API yet, so it stays switched off until a deployment sets TAX1099_ADAPTER_VERIFIED=on after a sandbox round trip. Until then, file with test for a dry run, or upload the data from GET /v1/tax/1099 to your provider by hand.

Connecting a provider requires the owner or admin role.

Review, then file

GET /v1/tax/1099/preview?year=2026 lists each recipient with Box 1 (nonemployee compensation, in USD cents) and anything that blocks filing them:

issues

Meaning

missing_tin, missing_address

Their W-9 is incomplete.

fx_missing

A payout to them was in a currency with no USD rate on record (see Exchange rates).

already_filed

A form for this partner and year has already been filed.

payerReady is false until your legal details include your legal name, EIN and address; payerIssues lists what's missing.

curl -X POST https://referalli.com/v1/tax/1099/filings \
  -H "Authorization: Bearer $KEY" \
  -H "content-type: application/json" \
  -d '{"year": 2026}'

This files every ready recipient in one batch and returns the filing with its status (submitting, submitted, accepted or rejected) and its documents. A partner is never filed twice for a year, even if two requests arrive at the same time. GET /v1/tax/1099/filings?year=2026 lists filings. For a provider that accepts forms later, POST /v1/tax/1099/filings/{id}/refresh checks the status again.

Filing is safe to interrupt. Referalli records the filing (submitting) and its documents (pending) before it calls your provider, and sends the filing's id as the provider's idempotency key. If the call fails or its answer is lost, the filing stays submitting with the error shown, and an hourly sweep (or refresh) resends the same batch with the same key, so the provider returns its first result instead of filing again. A document that's pending counts as filed, so it can't be filed twice in the meantime.

Delivery to partners

When a form is accepted, Copy B is delivered: the partner finds it under Payouts → Tax forms in the portal (GET /v1/partner/tax-documents, then GET /v1/partner/tax-documents/{id} for the printable form), gets a notification, and, where the provider supports it, an email copy. Copy B shows only the last four digits of the partner's TIN. A tax.form_delivered event is published for each one.

Corrections

If a partner's total for the year changes after filing (a late payout, say), file a corrected form: POST /v1/tax/1099/documents/{id}/correct. It refiles with the current total and marks the form CORRECTED. The original stays on record, and the correction points to it with correctionOf. When the amount on file already matches, the call returns 409.

Filing and corrections require the owner, admin or finance role, and every filing is audited.

Not tax advice

Referalli applies the rules above mechanically. Check the VAT treatment for your situation with your adviser, especially for domestic rates and non-EU partners.

Updated