To generate invoices, you need multiple local configurations. Your own
information is declared in self.yaml, client information can be declared in
files clients/<cname>.yaml, where cname is the client selector. Specific
information for this invoice can be configured in details.yaml.
First, you need to install
poetry. If you have nix it is
as simple as nix-env -iA nixpkgs.poetry. After that, create a virtual
environment and install all dependencies.
$ virtualenv -p python3 .venv
$ source .venv/bin/activate
$ poetry install # install dependencies
When you have created all config files, creating an invoice is as simple as:
$ python main.py
There are a few more options available though:
usage: main.py [-h] [--clean] [--clients CLIENTS] [--date DATE] [--directory DIRECTORY]
[--locale LOCALE] [--user USER] [--validate] [-v] [-y] [--nocolor]
[DETAILS]
script to help create invoices based on information from config files. By default, ask for
confirmation on details before creating an invoice. This behavior can be deactivated with
`-y|--yes`.
positional arguments:
DETAILS file with details and content specific to this invoice (default:
details.yml)
optional arguments:
-h, --help show this help message and exit
--clean ignore previous temporary files in build environment. (default:
False)
--clients CLIENTS relative path (folder) in which information about your clients is
stored in `<cname>.yml` files. (default: clients/)
--date DATE datetime formatting string the invoice should be dated at. Can be a
specific day like '2021-09-01'. Defaults to today. (default:
%Y-%m-%d)
--directory DIRECTORY
directory to expect USER, CLIENTS and DETAILS files in. (default: ./)
--locale LOCALE what language the invoice should be in. Ignored if set in
`details.yml` (default: de)
--user USER your contact details and bank information. (default: self.yml)
--validate only validate available information and check available
functionality, do not actually create invoice (default: False)
-v, --verbose make logging output (more) verbose. Default (or 0) is ERROR, -v is
WARN, -vv is INFO and -vvv is DEBUG. Can be passed multiple times.
(default: 0)
-y, --yes do not ask for confirmation before creating the actual invoice
(default: False)
--nocolor deactivate colored log output (default: False)
Have a file called self.yaml with your own information structured like this:
| Field | Type | description |
|---|---|---|
name |
string | Your full name or company name. |
address |
string | Your Address. Both street and number. |
zip |
int | Your area ZIP code. |
city |
string | The city you live in. |
country |
string | Optional. The country you live in. |
IBAN |
string | The IBAN of your bank account. |
BIC |
string | The BIC of your bank account. |
bank |
string | The name of your bank. |
stid |
string | Optional. Your tax number. |
ustid |
string | Optional. Your sales tax identification number. Will not show stid if available. |
phone |
string | Optional. Your phone number. |
email |
string | Optional. Your email address. |
url |
string | Optional. Link to your webpage. |
name: <name>
address: <address>
zip: <zip>
city: <name of city>
IBAN: <IBAN>
BIC: <BIC>
bank: <name of bank>For every clients cname, have a clients/<cname>.yaml file structured
like this:
| Field | Type | description |
|---|---|---|
name |
string | Your clients name or company name. |
address |
string | Your clients business address. Both street and number. |
zip |
int | ZIP code of your clients address. |
city |
string | City correlating to the zip code. |
country |
string | Optional. Country of your clients business address. |
name: <name>
address: <address>
zip: <zip>
city: <city>
country: <country>Specific information is in a file called details.yaml:
| Field | Type | description |
|---|---|---|
title |
string | Title of the invoice. |
timeframe |
string | Timeframe during which you accumulated the given number of hours. |
client |
string | File-Selector (cname, before the .yaml from your clients folder) of your client for this project. |
invoice_id |
int | Unique ID of this invoice. You need to ensure that this id is unique. |
items |
list | Optional. Entries must include description, amount and item_price_cents, can include unit. |
description |
string | Optional. Description of the work you did. |
hours_worked/amount |
int/float | Optional. Number of hours worked for the job. Can be point number with up to two decimal places. |
unit |
string | Optional. Only available in item-lists. Unit of the item, e.g. 'hours'/'h' or 'pieces'/'pcs'. |
hourly_rate_cents/item_price_cents |
int | Optional. The hourly rate you bill for in this invoice, in cents per hour. |
mwst_percent |
int | Optional. If the (global) calculation should include MwSt, and the percentage. |
locale |
string | Optional. de or en. Overrides --locale. Default: de |
title: <invoice title>
timeframe: <timeframe in which you worked>
client: <rname>
invoice_id: <int>
description: <work description>
hours_worked: <hours worked>
hourly_rate_cents: <int>
mwst_percent: 19title: <invoice title>
timeframe: <timeframe in which you worked>
client: <rname>
invoice_id: <int>
items:
- description: <work description 1>
amount: <int/float>
unit: h
item_price_cents: <int>
- description: <piece description 2>
amount: <int/float>
unit: pcs
item_price_cents: <int>
mwst_percent: 19Both styles can be combined, and the lower-level item is then placed first. It is not possible to specify individual mwst-rates, but individual unit types can be specified.