Infiniroot Blog: We sometimes write, too.

Of course we cannot always share details about our work with customers, but nevertheless it is nice to show our technical achievements and share some of our implemented solutions.

Implementing Swiss Payments Code (SPC) and QR code invoicing with Invoice Ninja

Published on June 30th 2020


At Infiniroot we asked ourselves a couple of years ago: How can we improve our invoicing mechanism and reduce the time investment in creating invoices? The old method (basically using Excel and Word, creating a PDF of it and sending to the customers) could definitely be improved.

The path to InvoiceNinja

We realized that creating invoices of one-shot projects would still require a certain amount of time, but invoices on recurring services (such as server hosting) could definitely be automated.

But we didn't just want any invoicing solution:

This is when we finally found Invoiceninja! And we were amazed. Working with invoices finally made fun.

Infiniroot loves InvoiceNinja

ESR Next Generation: QR code invoicing

The automatically created PDF invoices contain our payment information at the footer. We've (probably) been lucky so far, that all our customers never requested an "old style" payment slip, also known as "Einzahlungsschein" or "ESR" (containing a reference number), and copied the payment information from the invoice footer directly into their own payment system.

As ESR's are at the end of their life in Switzerland in 2020, a new kind of "invoice coding" emerges: QR codes on invoices.

The Swiss QR Invoice has a standardized data structure which is documented in the Swiss Implementation Guidelines QR-Bill document. With a bit of technical flair and some "thinking outside the box", the automatic creation of such QR codes can be implemented into InvoiceNinja.

Understanding the SPC data

Behind the optical QR code resides the "SPC data", which is short for "Swiss Payments Code". This data basically contains a couple of lines, each line with a value for a certain field, for example the currency. Here's such an example:

SPC
0200
1
CH5800791123000889012
S
Robert Schneider AG
Rue du Lac
1268
2501
Biel
CH
\n           
\n           
\n           
\n           
\n           
\n           
\n           
3949.75
CHF
S
Pia Rutschmann
Marktgasse
28
9400
Rorschach
CH
NON
\n        
Bill no. 3139 for gardening work and disposal of waste material
EPD
\n

Without going too much into details (read the implementation guide for this), the data starts with SPC internal reference codes (SPC, Version 0200, 1) followed by the invoice sender's (Debitor) IBAN bank account and a structured (S) address of the sender. After exactly 7 new lines the amount of the invoice followed by the currency shows up. Adding the invoice recipient's (Kreditor) address is optional. Finally the data ends with an optional reference code or string and "EPD".

Structured address vs. combined address

The example data above use the "S" address format, which is short for structured format. This basically means that the address is split into multiple fields as this:

S
Company Name
Street Name
House Number
ZIP Code
City
Country Code

When using the "K" (combined) address format, certain elements can be put on the same line:

K
Company Name
Street Name House Number
ZIP Code City
Country Code
\n
\n

Street name and house number are merged into one line. The same happens with ZIP code and the city name. The remaining two lines reserved for the structured address format are now optional and should be left empty (new line).

Why is this important? InvoiceNinja does not split the street into structured fields, which can be seen in the Company Details Settings:

Company Detail Adress Settings in InvoiceNinja

For this reason, the combined (K) address format needs to be used in SPC data.

Creating the QR code in a template

In InvoiceNinja's settings, the Invoice Design can be customized. When "Customize Design" tool is opened, the left side shows the backend code while the right side shows live changes on the final PDF design.

As I mentioned before, we're used to show our payment information in the invoice's footer. We wanted to put the QR code right next to this payment information. The trick however is to find the correct variables to use inside the code. InvoiceNinja's core developer Hillel Coren mentioned some of the variables can be found in the code's transformers. This certainly helps to find most of the needed variables but for certain a workaround is needed (more on that later).

Swiss QR Code Invoice with InvoiceNinja

With the following code snipped, almost all of the needed data can be dynamically inserted into the QR code:

    {
      "qr": "SPC\n0200\n1\nHard-Coded-IBAN\nK\n$account.name\n$account.address1\n$account.postal_code $account.city\n\n\nCH\n\n\n\n\n\n\n\n$balance\nCHF\n\n\n\n\n\n\nNON\n\n$invoice_number\nEPD\n",
      "fit": "100",
      "eccLevel": "H",
      "alignment": "right"
    }

Workaround for the invoice's currency

Although there is a $client.currency_id available according to the source code, it never showed any value. And even if it would show a value, it is not certain that the "ID" would actually show the international known currency string, such as USD, EUR or CHF. 

To circumvent this, a custom field can be created. InvoiceNinja supports two custom fields per category (products, clients, invoices, etc) which can then be used in the template. Under Settings -> Advanced Settings -> Invoice Settings, Custom Fields can be defined. Here a custom field called "Currency" is defined under the "Clients" category:

InvoiceNinja custom field

When a Client is now edited (or added), this new custom field shows up in the form:

InvoiceNinja custom field in Clients

Here the value "CHF" was added into this custom field.

The QR code was adjusted accordingly to retrieve the invoices currency dynamically from this custom field (using $client.custom_value1):

    {
      "qr": "SPC\n0200\n1\nHard-Coded-IBAN\nK\n$account.name\n$account.address1\n$account.postal_code $account.city\n\n\nCH\n\n\n\n\n\n\n\n$balance\n$client.custom_value1\n\n\n\n\n\n\n\nNON\n\n$invoice_number\nEPD\n",
      "fit": "100",
      "eccLevel": "H",
      "alignment": "right"
    }

This solution was also shared in the official InvoiceNinja community forums.

Creating an invoice with QR code

Now that everything is in place, a new invoice can be created and its QR code tested.

InvoiceNinja create invoice

And in the PDF view of the invoice, the QR code shows up:

InvoiceNinja QR Code Invoice

With a simple QR Code App this can now be read and the SPC data should be shown:

InvoiceNinja Invoice QR Code read by QR Code Reader

Official validation of the Swiss QR-bill code

An official Swiss QR bill code validator exists and a generated invoice can be uploaded to the validator. If no errors show up, the code is validated and can be used.

Swiss QR Bill Validator

VoilĂ ! The validator scanned the QR code from the uploaded PDF invoice and could not detect any errors. Mission accomplished!

InvoiceNinja has once again proven to us, why we decided for it in the first place!

Final step: Adjusting the QR code design

The integrated custom design editor uses the pdfmake syntax. By using this syntax, the QR Bill design can be implemented as part of the invoice. Note that the footer doesn't hold enough space for the QR Bill - it needs to be placed into the content of the main invoice.

In order to add the Swiss cross in the middle of the QR code as an SVG image, pdfmake needs to be manually updated in Invoice Ninja. This can unfortunately only be done by manually building Invoice Ninja from the source code, using bower, npm and gulp commands.

Hint: use pdfmake's playground to create the design.

Swiss QR Code in invoice PDF, created by Invoice Ninja

Swiss QR Bill in Invoice Ninja v5

Update March 2022: Infiniroot is currently working and testing on a Swiss QR Bill implementation on the newer Invoice Ninja v5! Our first tests were successful and look promising. We are confident that we can roll this out and offer this as a service in the coming weeks! Here's a preview of the v5 with the Swiss QR Code as payment slip:

Swiss QR Bill payment slip in Invoice Ninja v5

To get a "feeling" of the new Invoice Ninja version, we created a Getting Started Guide to Invoice Ninja v5, which is publicly available.

Update May 2022: Infiniroot offers hosted Invoice Ninja v5 in Switzerland since April 2022. The server setup fee also includes a template adjustment to enable the Swiss QR-Bill in invoices.

Your own Invoice Ninja server - data hosted in Switzerland

Since July 2020 Infiniroot offers dedicated InvoiceNinja servers in Switzerland. This allows you to run your own billing application using InvoiceNinja in a secure server environment and data in Switzerland, even with a low budget!