Examples of scripts¶
You can find examples for scripts (loosely based on the scripts for the official python bindings for gnucash or on questions posted on the mailing list) in the examples subfolder.
Creating and opening gnucash files¶
from __future__ import print_function
import os
import tempfile
from piecash import open_book, create_book, GnucashException
FILE_1 = os.path.join(tempfile.gettempdir(), "not_there.gnucash")
FILE_2 = os.path.join(tempfile.gettempdir(), "example_file.gnucash")
if os.path.exists(FILE_2):
os.remove(FILE_2)
# open a file that isn't there, detect the error
try:
book = open_book(FILE_1)
except GnucashException as backend_exception:
print("OK", backend_exception)
# create a new file, this requires a file type specification
with create_book(FILE_2) as book:
pass
# open the new file, try to open it a second time, detect the lock
# using the session as context manager automatically release the lock and close the session
with open_book(FILE_2) as book:
try:
with open_book(FILE_2) as book_2:
pass
except GnucashException as backend_exception:
print("OK", backend_exception)
os.remove(FILE_2)
Creating an account¶
#!/usr/bin/env python
## @file
# @brief Example Script simple sqlite create
# @ingroup python_bindings_examples
from __future__ import print_function
import os
from piecash import create_book, Account, Commodity, open_book
from piecash.core.factories import create_currency_from_ISO
filename = os.path.abspath('test.blob')
if os.path.exists(filename):
os.remove(filename)
with create_book(filename) as book:
a = Account(parent=book.root_account,
name="wow",
type="ASSET",
commodity=create_currency_from_ISO("CAD"))
book.save()
with open_book(filename) as book:
print(book.root_account.children)
print(book.commodities.get(mnemonic="CAD"))
os.remove(filename)
Creating a transaction¶
#!/usr/bin/env python
# # @file
# @brief Creates a basic set of accounts and a couple of transactions
# @ingroup python_bindings_examples
from decimal import Decimal
import os
import tempfile
from piecash import create_book, Account, Transaction, Split, Commodity
from piecash.core.factories import create_currency_from_ISO
FILE_1 = os.path.join(tempfile.gettempdir(), "example.gnucash")
with create_book(FILE_1, overwrite=True) as book:
root_acct = book.root_account
cad = create_currency_from_ISO("CAD")
expenses_acct = Account(parent=root_acct,
name="Expenses",
type="EXPENSE",
commodity=cad)
savings_acct = Account(parent=root_acct,
name="Savings",
type="BANK",
commodity=cad)
opening_acct = Account(parent=root_acct,
name="Opening Balance",
type="EQUITY",
commodity=cad)
num1 = Decimal("4")
num2 = Decimal("100")
num3 = Decimal("15")
# create transaction with core objects in one step
trans1 = Transaction(currency=cad,
description="Groceries",
splits=[
Split(value=num1, account=expenses_acct),
Split(value=-num1, account=savings_acct),
])
# create transaction with core object in multiple steps
trans2 = Transaction(currency=cad,
description="Opening Savings Balance")
split3 = Split(value=num2,
account=savings_acct,
transaction=trans2)
split4 = Split(value=-num2,
account=opening_acct,
transaction=trans2)
# create transaction with factory function
from piecash.core.factories import single_transaction
trans3 = single_transaction(None,None,"Pharmacy", num3, savings_acct, expenses_acct)
book.save()
Simple changes on a newly created book¶
from __future__ import print_function
from piecash import create_book
# create by default an in memory sqlite version
book = create_book(echo=False)
print("Book is saved:", book.is_saved, end=' ')
print(" ==> book description:", book.root_account.description)
print("changing description...")
book.root_account.description = "hello, book"
print("Book is saved:", book.is_saved, end=' ')
print(" ==> book description:", book.root_account.description)
print("saving...")
book.save()
print("Book is saved:", book.is_saved, end=' ')
print(" ==> book description:", book.root_account.description)
print("changing description...")
book.root_account.description = "nevermind, book"
print("Book is saved:", book.is_saved, end=' ')
print(" ==> book description:", book.root_account.description)
print("cancel...")
book.cancel()
print("Book is saved:", book.is_saved, end=' ')
print(" ==> book description:", book.root_account.description)
Create a book with some accounts and add a transaction¶
from piecash import create_book, Account
# create a book with some account tree structure
with create_book("../gnucash_books/simple_book_transaction_creation.gnucash", overwrite=True) as mybook:
mybook.root_account.children = [
Account(name="Expenses",
type="EXPENSE",
commodity=mybook.currencies(mnemonic="USD"),
placeholder=True,
children=[
Account(name="Some Expense Account",
type="EXPENSE",
commodity=mybook.currencies(mnemonic="USD")),
]),
Account(name="Assets",
type="ASSET",
commodity=mybook.currencies(mnemonic="USD"),
placeholder=True,
children=[
Account(name="Current Assets",
type="BANK",
commodity=mybook.currencies(mnemonic="USD"),
placeholder=True,
children=[
Account(name="Checking",
type="BANK",
commodity=mybook.currencies(mnemonic="USD"))
]),
]),
]
# save the book
mybook.save()
from piecash import open_book, Transaction, Split
from datetime import datetime
from decimal import Decimal
# reopen the book and add a transaction
with open_book("../gnucash_books/simple_book_transaction_creation.gnucash",
open_if_lock=True,
readonly=False) as mybook:
today = datetime.now()
# retrieve the currency from the book
USD = mybook.currencies(mnemonic="USD")
# define the amount as Decimal
amount = Decimal("25.35")
# retrieve accounts
to_account = mybook.accounts(fullname="Expenses:Some Expense Account")
from_account = mybook.accounts(fullname="Assets:Current Assets:Checking")
# create the transaction with its two splits
Transaction(
post_date=today,
enter_date=today,
currency=USD,
description="Transaction Description!",
splits=[
Split(account=to_account,
value=amount,
memo="Split Memo!"),
Split(account=from_account,
value=-amount,
memo="Other Split Memo!"),
]
)
# save the book
mybook.save()
from piecash import ledger
# check the book by exporting to ledger format
with open_book("../gnucash_books/simple_book_transaction_creation.gnucash",
open_if_lock=True) as mybook:
print(ledger(mybook))
Extract Split information as pandas DataFrame¶
from piecash import open_book
# open a book
with open_book("../gnucash_books/simple_sample.gnucash", open_if_lock=True) as mybook:
# print all splits in account "Asset"
asset = mybook.accounts(fullname="Asset")
for split in asset.splits:
print(split)
# extract all split information to a pandas DataFrame
df = mybook.splits_df()
# print for account "Asset" some information on the splits
print(df.loc[df["account.fullname"] == "Asset", ["transaction.post_date", "value"]])
Filtered transaction reports¶
from __future__ import print_function
import datetime
import re
import os.path
from piecash import open_book
if __name__=='__main__':
this_folder = os.path.dirname(os.path.realpath(__file__))
s = open_book(os.path.join(this_folder, "..", "gnucash_books", "simple_sample.gnucash"), open_if_lock=True)
else:
s = open_book(os.path.join("gnucash_books", "simple_sample.gnucash"), open_if_lock=True)
# get default currency
print(s.default_currency)
regex_filter = re.compile("^/Rental/")
# retrieve relevant transactions
transactions = [tr for tr in s.transactions # query all transactions in the book/session and filter them on
if (regex_filter.search(tr.description) # description field matching regex
or any(regex_filter.search(spl.memo) for spl in tr.splits)) # or memo field of any split of transaction
and tr.post_date.date() >= datetime.date(2014, 11, 1)] # and with post_date no later than begin nov.
# output report with simple 'print'
print("Here are the transactions for the search criteria '{}':".format(regex_filter.pattern))
for tr in transactions:
print("- {:%Y/%m/%d} : {}".format(tr.post_date, tr.description))
for spl in tr.splits:
print("\t{amount} {direction} {account} : {memo}".format(amount=abs(spl.value),
direction="-->" if spl.value > 0 else "<--",
account=spl.account.fullname,
memo=spl.memo))
# same with jinja2 templates
try:
import jinja2
except ImportError:
print("\n\t*** Install jinja2 ('pip install jinja2') to test the jinja2 template version ***\n")
jinja2 = None
if jinja2:
env = jinja2.Environment(trim_blocks=True, lstrip_blocks=True)
print(env.from_string("""
Here are the transactions for the search criteria '{{regex.pattern}}':
{% for tr in transactions %}
- {{ tr.post_date.strftime("%Y/%m/%d") }} : {{ tr.description }}
{% for spl in tr.splits %}
{{ spl.value.__abs__() }} {% if spl.value < 0 %} --> {% else %} <-- {% endif %} {{ spl.account.fullname }} : {{ spl.memo }}
{% endfor %}
{% endfor %}
""").render(transactions=transactions,
regex=regex_filter))