MyInvois XML to PDF — an A4 invoice you can hand over
Read the UBL XML your supplier sent, see exactly what will be printed, then build a printable A4 PDF in this tab. The XML never leaves your browser.
🔒 100% client-side · zero server upload
QR: none. The UUID and long ID are issued at validation and are not in the XML, so no QR is drawn.
PNG, JPEG or WebP, up to 600 px on a side. It is kept in this browser only — saved on this device and never uploaded.
Untick for a plain document — some buyers ask for one. The preview above still shows it.
What will be printed
Supplier
Buyer
Lines
| No. | Description / Perihal | Qty / Kuantiti | Unit price / Harga seunit | Amount / Jumlah |
|---|
Totals
Worth knowing before you print
Chinese text in the document (or this page, in Chinese) fetches a 1.3 MB font subset once, about 705 KB over the wire. Nothing else is downloaded, and nothing is uploaded.
The XML is read in this tab. There is no upload endpoint; the only request the page can make is for its own font file, and only when the document contains Chinese characters.
Malaysian rules & edge cases
What this page does — and what it does not
It reads a MyInvois (LHDN) UBL 2.1 e-Invoice XML file and lays out an A4 page that looks like the invoice a shop would hand a customer. It is a visual representation, not the e-Invoice. LHDN's guidance is that the e-Invoice is the XML or JSON document and not a PDF, JPG or similar; the PDF here is for the customer's file, the delivery note folder, or the person at the counter who wants paper.
- No validation claim, in any language. The page never says a document is valid, approved or accepted by LHDN, prints no green badge, and the footer of every PDF says: “Visual representation generated in your browser from the supplier's XML. Not an LHDN-validated document.”
- The UUID is not in the file. IRBM assigns the UUID and the validation link when it validates a document, and returns them as API metadata. They are not elements of the XML, so this page cannot print them for you — you paste your own, or the page prints none.
- Nothing is uploaded. The XML is read in this tab by static JavaScript. The only request the page can make is for its own Chinese font file, and only when the document contains Chinese characters.
How the XML is read
- By namespace, never by prefix. Issuers write
cbc:,Cbc:orinv:for the same namespaces, so every element is matched by its namespace URI and local name. AUBLExtensionsblock that redeclares the default namespace cannot hijack a field either: the resolver inherits declarations down the tree, so an element inside that block is simply not a UBL element. - The root is always
Invoice. All eight MyInvois types — 01 invoice, 02 credit note, 03 debit note, 04 refund note, and the self-billed 11–14 — are rooted atInvoice. The document type comes fromcbc:InvoiceTypeCode, never from the element name. A file rooted atCreditNoteis a different UBL document and is refused by name. - Numbers are guarded. Every amount is parsed as an integer number of sen. LHDN's own published FX sample carries
PayableAmount=abc; a file like that is refused with the field and the value named, because a PDF that printsabcas a total is worse than no PDF.
The traps this page handles, each visibly
- Two classification codes. A line can carry a
CLASScode and aPTCcode; the CLASS one is printed and the preview says both exist. - Two currencies. When tax is stated in the tax currency, both figures print, each with the currency the file states, and the exchange rate is printed as stated — nothing is converted.
- The general public is not a buyer. TIN
EI00000000010(“Consolidated Buyers”) is LHDN's placeholder for a walk-in customer. It is read, and labelled as a placeholder, instead of being printed as if it were a registered buyer. - Self-billed 11–14. The party issuing the document is the buyer, so the two party headings flip and say which is which.
- Long text. A 300-character description, a 150-character address line, a 50-character city: all wrap inside their column, never past the margin, and a row is never split across pages.
- A malformed file. The error names the tag and the line and column, rather than a blank page.
The QR code, if you have one
Two optional fields take the UUID and the long ID that MyInvois returned when the document was validated. With both, a QR of LHDN's share link is drawn on the PDF. With neither, no QR is drawn at all — a QR that resolves to nothing would be worse than a blank corner. A half-typed UUID is refused by name, so you find out before you print.
Your logo, if you want one
A PNG, JPEG or WebP picture can be added to the header: it is printed at 120 × 30 pt (about 42 × 11 mm), keeps its own proportions, and its transparency is honoured rather than flattened onto a grey box. It is remembered in this browser only — stored on this device, never uploaded — so a returning visitor does not re-upload it for every invoice. A tick box leaves it out of the PDF for buyers who require a plain document, and unticking changes nothing in the preview. An SVG is refused by name: an SVG is a container for markup and script, not a picture. Nothing about the invoice itself is stored, at any time.
Chinese text
A document with Chinese characters downloads a 1.3 MB font subset once (about 705 KB over the wire) and embeds the whole font, so the characters are really drawn rather than silently dropped. A character the subset cannot draw is refused by name. A Latin-only document fetches no font at all.
Before and after
Before
<Invoice xmlns="urn:oasis:names:specification:ubl:schema:xsd:Invoice-2" …>
<cbc:ID>INV-2026-0118</cbc:ID>
<cbc:InvoiceTypeCode>01</cbc:InvoiceTypeCode>
<cbc:DocumentCurrencyCode>MYR</cbc:DocumentCurrencyCode> After
Invoice / Invois (01) · INV-2026-0118
Supplier: Hoelee Trading Sdn Bhd
Lines / Item: 3
TOTAL / JUMLAH: RM 11,050.56 How it works
- Drop the .xml file into the left pane, or paste its text. Nothing is uploaded — the file is read by the page itself.
- Press “Check the file” to see the structured preview: document type, supplier, buyer, every line with its quantity and amount, the tax subtotals and the total. No PDF exists yet.
- Paste the UUID and long ID from MyInvois if you have them, then press “Build the A4 PDF”. The download appears with the invoice number as its file name.
FAQ
Is this PDF the official LHDN e-Invoice?
No. LHDN states the e-Invoice is the XML or JSON document, not a PDF. This page produces a visual representation for a customer file or a printed copy, and its footer says so on every page. The document that counts is the XML or JSON that MyInvois validated.
Why is there no QR code on my PDF?
Because the UUID and validation link are assigned by IRBM at validation and returned as API metadata — they are not inside the XML. When you paste both the UUID and the long ID, a QR of LHDN's share link is drawn. Without them the page prints nothing rather than a QR that resolves to nowhere.
The file was refused. What do the errors mean?
The message names the cause: a different root element, an unknown InvoiceTypeCode, a missing namespace, a field that is not a number, no lines, or a malformed tag with its line and column. Nothing is guessed or repaired silently, because a repaired invoice is not the document your supplier sent.
Does it check whether LHDN would accept the document?
No, and it never says so. It reads the fields the XML states, guards the numbers, and prints them. Whether a document is valid, and what its UUID is, is IRBM's answer, not this page's.
Can I print an invoice with Chinese descriptions?
Yes. A document containing Chinese characters downloads the WenQuanYi subset font once (about 705 KB compressed) and embeds it whole, so the characters really print. A character the subset cannot draw is refused by name instead of appearing as an empty box.