-
-
Crossbill — AI reads, rules decide, humans approve, PayPal pays
-
How it works: the Japan rule pack is deterministic; the AI only describes facts
-
All five steps on one screen: Read, Review, Decide, Approve, Pay
-
Amount to pay, with the withholding basis shown for every line item
-
Payment settings, Japanese journal entry (freee / Money Forward CSV) and checks before approval
-
Approved and paid through PayPal Payouts — batch ID and status recorded in the audit log
-
The AI quotes the invoice wording behind each classification; approval needs a named approver
Inspiration
I have spent about twenty years in corporate accounting in Japan, and I write Python to automate the parts of the job that software vendors never got around to. One of those parts is paying people overseas.
Japanese companies now hire freelancers and small vendors abroad all the time: a designer in Portland, a video editor in Singapore, a font foundry in London. Japan's invoice-management systems handle the domestic side well, but a foreign invoice still lands on someone's desk with the same four questions nobody automates:
- Is Japanese withholding tax due on this (20.42% on royalties and copyright paid to non-residents)?
- Does a tax treaty remove or reduce it, and was the treaty form filed before payment?
- Is Japanese consumption tax out of scope, domestic, or reverse-charge?
- At which FX rate do I book it, and what is the net amount I actually send?
Getting one of these wrong means a penalty, an angry vendor, or a correction months later. Systems that do get it right are priced for large enterprises. For an SME that pays a few foreign invoices a month, the answer today is a spreadsheet and an experienced person.
Crossbill is my attempt to put that experienced person's checklist into software, and to connect it directly to the payment rail. If PayPal owns the step before the payout, it becomes the natural way for Japanese businesses to pay the world, not just the way the world pays them.
What it does
Crossbill turns a foreign vendor invoice into a Japan-compliant payment and journal entry, with a human approving every decision.
- AI reads. Claude extracts the vendor, amounts and line items from the PDF and classifies each line (service performed abroad, copyright assignment, license, service performed in Japan, digital service, goods), quoting the words on the invoice that justify the classification. The AI describes facts only; it never decides tax.
- Human reviews. The line items appear in an AG Grid where the reviewer sees the AI's reason next to each category and can correct it in place. Every correction is recorded.
- Rules decide. A deterministic Japan rule pack applies FX conversion (TTM when paying in yen, TTB when paying in foreign currency), consumption-tax treatment, non-resident withholding at 20.42% or the treaty limit rate (0% for the US, UK, France, Germany; 10% for Singapore, China, Korea, India; unverified treaties are flagged, never assumed), rounding down to whole yen, the ledger account, and the withholding due date (10th of the next month, rolled to the next business day using the Japanese holiday calendar).
- Human approves. Amount to pay, withholding, review flags and the compound journal entry are shown together. Approval requires a named approver and an explicit confirmation.
- PayPal pays. The approved net amount is sent through PayPal Payouts (sandbox) from the Japanese business account to the vendor's account. The server recomputes the amount from the rules before calling PayPal; if the browser's figure differs, the payout is refused.
- Records. An audit log keeps who approved what, which AI categories were overridden, and the PayPal batch ID. A journal CSV with Japanese headers imports into freee or Money Forward.
A safety switch (PAYOUT_DRY_RUN) simulates payouts on the public demo; the demo video shows a real sandbox payout with a PayPal batch ID.
How I built it
- Claude (Haiku) with a strict tool schema for extraction, so the output is structured data with a quoted reason per line, plus an arithmetic check that lines + tax = total before anything else happens.
- A Python rule pack (
japan_rules.py) that is the only place tax decisions are made. It usesDecimal, rounds down to whole yen, carries a treaty-rate table, and emits awithholding_basis(domestic / treaty / none) so the UI can explain every number. - FastAPI backend with a single-page frontend: AG Grid Community for the editable review grid (category dropdown, highlighted edited cells, AI reason column), Tailwind for layout, no build step.
- PayPal Payouts API (sandbox) through a small client; JPY amounts are integers; the receiver address is validated at startup.
- 51 automated tests covering the acceptance numbers, category overrides, due-date rollover across holidays, dry-run vs. real mode, and API error handling (Claude and PayPal are mocked in tests).
- Deployed on Render; sample invoices are fictional and generated by a script in the repo.
Challenges I ran into
- Keeping the AI out of the tax decision. It is tempting to ask the model "is this taxable?". The answer looks plausible and is sometimes wrong. The design that worked is: the model quotes evidence and classifies, fixed rules compute, a person decides.
- Withholding is not one number. The base differs by payment currency (yen actually paid vs. TTB conversion), the rate differs by treaty and by whether the form was filed in time, and the surtax disappears when a treaty rate applies. Encoding this honestly also meant encoding what I could not verify, so unverified treaties are flagged rather than guessed.
- Sandbox realities. PayPal sandbox balances are capped, so demo amounts are scaled down, and I wrote a small tool that returns each test payout to the paying account so the demo can run repeatedly.
- Making the demo safe in public. Rate limits on AI extraction, upload validation, a dry-run default, server-side recomputation of the payout amount, and never sending to an address printed on an uploaded invoice.
What I learned
Most of the value was not in the AI call but in the shape around it: evidence next to every classification, a reviewer who can override with one click, and a payment that cannot differ from what the reviewer saw. That shape is what an accountant needs before trusting an agent with money.
What's next
- Verify the remaining treaty rates and account treatments with a tax professional and mark them as verified in the UI.
- Pull the paying company's bank-published TTM/TTB rates automatically.
- Add a second country rule pack (EU VAT reverse charge) to show the Japan pack is one plug-in among many.
- Vendor-side treaty-form workflow, so the form is collected before the first invoice arrives.
Disclaimer: the tax rules in this project demonstrate the approach and are not tax advice. Demo amounts are scaled to fit the PayPal sandbox balance limit.
Log in or sign up for Devpost to join the conversation.