python-quickbooks
=================
[![Python package](https://github.com/ej2/python-quickbooks/actions/workflows/python-package.yml/badge.svg)](https://github.com/ej2/python-quickbooks/actions/workflows/python-package.yml)
[![codecov](https://codecov.io/gh/ej2/python-quickbooks/graph/badge.svg?token=AKXS2F7wvP)](https://codecov.io/gh/ej2/python-quickbooks)
[![](https://img.shields.io/badge/License-MIT-yellow.svg)](https://github.com/ej2/python-quickbooks/blob/master/LICENSE)
[![PyPI](https://img.shields.io/pypi/v/python-quickbooks)](https://pypi.org/project/python-quickbooks/)
A Python 3 library for accessing the Quickbooks API. Complete rework of
[quickbooks-python](https://github.com/troolee/quickbooks-python).
These instructions were written for a Django application. Make sure to
change it to whatever framework/method you’re using.
You can find additional examples of usage in [Integration tests folder](https://github.com/ej2/python-quickbooks/tree/master/tests/integration).
For information about contributing, see the [Contributing Page](https://github.com/ej2/python-quickbooks/blob/master/contributing.md).
Installation
------------
```bash
pip install python-quickbooks
```
QuickBooks OAuth
------------------------------------------------
This library requires [intuit-oauth](https://pypi.org/project/intuit-oauth/).
Follow the [OAuth 2.0 Guide](https://developer.intuit.com/app/developer/qbo/docs/develop/authentication-and-authorization/oauth-2.0) for installation and to get connected to QuickBooks API.
Accessing the API
-----------------
Set up an AuthClient passing in your `CLIENT_ID` and `CLIENT_SECRET`.
from intuitlib.client import AuthClient
auth_client = AuthClient(
client_id='CLIENT_ID',
client_secret='CLIENT_SECRET',
access_token='ACCESS_TOKEN', # If you do not pass this in, the Quickbooks client will call refresh and get a new access token.
environment='sandbox',
redirect_uri='http://localhost:8000/callback',
)
Then create a QuickBooks client object passing in the AuthClient, refresh token, and company id:
from quickbooks import QuickBooks
client = QuickBooks(
auth_client=auth_client,
refresh_token='REFRESH_TOKEN',
company_id='COMPANY_ID',
)
If you need to access a minor version (See [Minor versions](https://developer.intuit.com/app/developer/qbo/docs/learn/explore-the-quickbooks-online-api/minor-versions#working-with-minor-versions) for
details) pass in minorversion when setting up the client:
client = QuickBooks(
auth_client=auth_client,
refresh_token='REFRESH_TOKEN',
company_id='COMPANY_ID',
minorversion=69
)
Object Operations
-----------------
List of objects:
from quickbooks.objects.customer import Customer
customers = Customer.all(qb=client)
**Note:** The maximum number of entities that can be returned in a
response is 1000. If the result size is not specified, the default
number is 100. (See [Query operations and syntax](https://developer.intuit.com/app/developer/qbo/docs/learn/explore-the-quickbooks-online-api/data-queries) for details)
**Warning:** You should never allow user input to pass into a query without sanitizing it first! This library DOES NOT sanitize user input!
Filtered list of objects:
customers = Customer.filter(Active=True, FamilyName="Smith", qb=client)
Filtered list of objects with ordering:
# Get customer invoices ordered by TxnDate
invoices = Invoice.filter(CustomerRef='100', order_by='TxnDate', qb=client)
# Same, but in reverse order
invoices = Invoice.filter(CustomerRef='100', order_by='TxnDate DESC', qb=client)
# Order customers by FamilyName then by GivenName
customers = Customer.all(order_by='FamilyName, GivenName', qb=client)
Filtered list of objects with paging:
customers = Customer.filter(start_position=1, max_results=25, Active=True, FamilyName="Smith", qb=client)
List Filtered by values in list:
customer_names = ['Customer1', 'Customer2', 'Customer3']
customers = Customer.choose(customer_names, field="DisplayName", qb=client)
List with custom Where Clause (do not include the `"WHERE"`):
customers = Customer.where("Active = True AND CompanyName LIKE 'S%'", qb=client)
List with custom Where and ordering
customers = Customer.where("Active = True AND CompanyName LIKE 'S%'", order_by='DisplayName', qb=client)
List with custom Where Clause and paging:
customers = Customer.where("CompanyName LIKE 'S%'", start_position=1, max_results=25, qb=client)
Filtering a list with a custom query (See [Query operations and syntax](https://developer.intuit.com/app/developer/qbo/docs/learn/explore-the-quickbooks-online-api/data-queries) for
supported SQL statements):
customers = Customer.query("SELECT * FROM Customer WHERE Active = True", qb=client)
Filtering a list with a custom query with paging:
customers = Customer.query("SELECT * FROM Customer WHERE Active = True STARTPOSITION 1 MAXRESULTS 25", qb=client)
Get record count (do not include the ``"WHERE"``):
customer_count = Customer.count("Active = True AND CompanyName LIKE 'S%'", qb=client)
Get single object by Id and update:
customer = Customer.get(1, qb=client)
customer.CompanyName = "New Test Company Name"
customer.save(qb=client)
Create new object:
customer = Customer()
customer.CompanyName = "Test Company"
customer.save(qb=client)
Batch Operations
----------------
The batch operation enables an application to perform multiple
operations in a single request (See [Intuit Batch Operations Guide](https://developer.intuit.com/docs/api/accounting/batch) for
full details).
Batch create a list of objects:
from quickbooks.batch import batch_create
customer1 = Customer()
customer1.CompanyName = "Test Company 1"
customer2 = Customer()
customer2.CompanyName = "Test Company 2"
customers = [customer1, customer2]
results = batch_create(customers, qb=client)
Batch update a list of objects:
from quickbooks.batch import batch_update
customers = Customer.filter(Active=True)
# Update customer records
results = batch_update(customers, qb=client)
Batch delete a list of objects (only entities that support delete can use batch delete):
from quickbooks.batch import batch_delete
payments = Payment.filter(TxnDate=date.today())
results = batch_delete(payments, qb=client)
Review results for batch operation:
# successes is a list of objects that were successfully updated
for obj in results.successes:
print("Updated " + obj.DisplayName)
# faults contains list of failed operations and associated errors
for fault in results.faults:
print("Operation failed on " + fault.original_object.DisplayName)
for error in fault.Error:
print("Error " + error.Message)
Change Data Capture
-----------------------
Change Data Capture returns a list of objects that have changed since a given time
(see [Change data capture](https://developer.intuit.com/docs/api/accounting/changedatacapture) for more details):
from quickbooks.cdc import change_data_capture
from quickbooks.objects import Invoice
cdc_response = change_data_capture([Invoice], "2017-01-01T00:00:00", qb=client)
for invoice in cdc_response.Invoice:
# Do something with the invoice
Querying muliple entity types at the same time:
from quickbooks.objects import Invoice, Customer
cdc_response = change_data_capture([Invoice, Customer], "2017-01-01T00:00:00", qb=client)
If you use a `datetime` object for the timestamp, it is automatically converted to a string:
from datetime import datetime
cdc_response = change_data_capture([Invoice, Customer], datetime(2017, 1, 1, 0, 0, 0), qb=client)
Attachments
----------------
See [Attachable documentation](https://developer.intuit.com/docs/api/accounting/Attachable)
for list of valid file types, file size limits and other restrictions.
Attaching a note to a customer:
attachment = Attachable()
attachable_ref = AttachableRef()
attachable_ref.EntityRef = customer.to_ref()
attachment.AttachableRef.append(attachable_ref)
attachment.Note = 'This is a note'
attachment.save(qb=client)
Attaching a file to customer:
attachment = Attachable()
attachable_ref = AttachableRef()
attachable_ref.EntityRef = customer.to_ref()
attachment.AttachableRef.append(attachable_ref)
attachment.FileName = 'Filename'
attachment._FilePath = '/folder/filename' # full path to file
attachment.ContentType = 'application/pdf'
attachment.save(qb=client)
Passing in optional params
----------------
Some QBO objects have options that need to be set on the query string of an API call.
One example is `include=allowduplicatedocnum` on the Purchase object. You can add these params when calling save:
purchase.save(qb=self.qb_client, params={'include': 'allowduplicatedocnum'})
Other operations
----------------
Add Sharable link for an invoice sent to external customers (minorversion must be set to 36 or greater):
invoice.invoice_link = true
Void an invoice:
invoice = Invoice()
invoice.Id = 7
invoice.void(qb=client)
Working with JSON data
----------------
All objects include `to_json` and `from_json` methods.
Converting an object to JSON data:
account = Account.get(1, qb=client)
json_data = account.to_json()
Loading JSON data into a quickbooks object:
account = Account.from_json(
{
"AccountType": "Accounts Receivable",
"AcctNum": "123123",
"Name": "MyJobs"
}
)
account.save(qb=client)
Date formatting
----------------
When setting date or datetime fields, Quickbooks requires a specific format.
Formating helpers are available in helpers.py. Example usage:
date_string = qb_date_format(date(2016, 7, 22))
date_time_string = qb_datetime_format(datetime(2016, 7, 22, 10, 35, 00))
date_time_with_utc_string = qb_datetime_utc_offset_format(datetime(2016, 7, 22, 10, 35, 00), '-06:00')
Exception Handling
----------------
The QuickbooksException object contains additional [QBO error code](https://developer.intuit.com/app/developer/qbo/docs/develop/troubleshooting/error-codes#id1) information.
from quickbooks.exceptions import QuickbooksException
try:
# perform a Quickbooks operation
except QuickbooksException as e:
e.message # contains the error message returned from QBO
e.error_code # contains the
e.detail # contains additional information when available
**Note:** Objects and object property names match their Quickbooks
counterparts and do not follow PEP8.
**Note:** This is a work-in-progress made public to help other
developers access the QuickBooks API. Built for a Django project.
Raw data
{
"_id": null,
"home_page": "https://github.com/ej2/python-quickbooks",
"name": "python-quickbooks",
"maintainer": null,
"docs_url": null,
"requires_python": null,
"maintainer_email": null,
"keywords": "quickbooks, qbo, accounting",
"author": "Edward Emanuel Jr.",
"author_email": "edward.emanuel@gmail.com",
"download_url": "https://files.pythonhosted.org/packages/2b/95/bd3fce3e40bc36974a066732cbeaca336b45b7ff2f4d2e142cf52475d116/python_quickbooks-0.9.9.tar.gz",
"platform": null,
"description": "python-quickbooks\n=================\n\n[![Python package](https://github.com/ej2/python-quickbooks/actions/workflows/python-package.yml/badge.svg)](https://github.com/ej2/python-quickbooks/actions/workflows/python-package.yml)\n[![codecov](https://codecov.io/gh/ej2/python-quickbooks/graph/badge.svg?token=AKXS2F7wvP)](https://codecov.io/gh/ej2/python-quickbooks)\n[![](https://img.shields.io/badge/License-MIT-yellow.svg)](https://github.com/ej2/python-quickbooks/blob/master/LICENSE)\n[![PyPI](https://img.shields.io/pypi/v/python-quickbooks)](https://pypi.org/project/python-quickbooks/)\n \nA Python 3 library for accessing the Quickbooks API. Complete rework of\n[quickbooks-python](https://github.com/troolee/quickbooks-python).\n\nThese instructions were written for a Django application. Make sure to\nchange it to whatever framework/method you\u2019re using.\nYou can find additional examples of usage in [Integration tests folder](https://github.com/ej2/python-quickbooks/tree/master/tests/integration).\n\nFor information about contributing, see the [Contributing Page](https://github.com/ej2/python-quickbooks/blob/master/contributing.md).\n\nInstallation\n------------\n\n```bash\npip install python-quickbooks\n```\n\nQuickBooks OAuth\n------------------------------------------------\n\nThis library requires [intuit-oauth](https://pypi.org/project/intuit-oauth/). \nFollow the [OAuth 2.0 Guide](https://developer.intuit.com/app/developer/qbo/docs/develop/authentication-and-authorization/oauth-2.0) for installation and to get connected to QuickBooks API.\n\n\nAccessing the API\n-----------------\n\nSet up an AuthClient passing in your `CLIENT_ID` and `CLIENT_SECRET`.\n\n from intuitlib.client import AuthClient\n\n auth_client = AuthClient(\n client_id='CLIENT_ID',\n client_secret='CLIENT_SECRET',\n access_token='ACCESS_TOKEN', # If you do not pass this in, the Quickbooks client will call refresh and get a new access token. \n environment='sandbox',\n redirect_uri='http://localhost:8000/callback',\n )\n\nThen create a QuickBooks client object passing in the AuthClient, refresh token, and company id:\n\n from quickbooks import QuickBooks\n\n client = QuickBooks(\n auth_client=auth_client,\n refresh_token='REFRESH_TOKEN',\n company_id='COMPANY_ID',\n )\n\nIf you need to access a minor version (See [Minor versions](https://developer.intuit.com/app/developer/qbo/docs/learn/explore-the-quickbooks-online-api/minor-versions#working-with-minor-versions) for\ndetails) pass in minorversion when setting up the client:\n\n client = QuickBooks(\n auth_client=auth_client,\n refresh_token='REFRESH_TOKEN',\n company_id='COMPANY_ID',\n minorversion=69\n )\n\nObject Operations\n-----------------\n\nList of objects:\n\n from quickbooks.objects.customer import Customer\n customers = Customer.all(qb=client)\n\n**Note:** The maximum number of entities that can be returned in a\nresponse is 1000. If the result size is not specified, the default\nnumber is 100. (See [Query operations and syntax](https://developer.intuit.com/app/developer/qbo/docs/learn/explore-the-quickbooks-online-api/data-queries) for details)\n\n**Warning:** You should never allow user input to pass into a query without sanitizing it first! This library DOES NOT sanitize user input! \n\nFiltered list of objects:\n\n customers = Customer.filter(Active=True, FamilyName=\"Smith\", qb=client)\n\nFiltered list of objects with ordering:\n\n # Get customer invoices ordered by TxnDate\n invoices = Invoice.filter(CustomerRef='100', order_by='TxnDate', qb=client)\n\n # Same, but in reverse order\n invoices = Invoice.filter(CustomerRef='100', order_by='TxnDate DESC', qb=client)\n\n # Order customers by FamilyName then by GivenName\n customers = Customer.all(order_by='FamilyName, GivenName', qb=client)\n\nFiltered list of objects with paging:\n\n customers = Customer.filter(start_position=1, max_results=25, Active=True, FamilyName=\"Smith\", qb=client)\n\nList Filtered by values in list:\n\n customer_names = ['Customer1', 'Customer2', 'Customer3']\n customers = Customer.choose(customer_names, field=\"DisplayName\", qb=client)\n\nList with custom Where Clause (do not include the `\"WHERE\"`):\n\n customers = Customer.where(\"Active = True AND CompanyName LIKE 'S%'\", qb=client)\n\n \n\nList with custom Where and ordering\n\n customers = Customer.where(\"Active = True AND CompanyName LIKE 'S%'\", order_by='DisplayName', qb=client)\n\nList with custom Where Clause and paging:\n\n customers = Customer.where(\"CompanyName LIKE 'S%'\", start_position=1, max_results=25, qb=client)\n\nFiltering a list with a custom query (See [Query operations and syntax](https://developer.intuit.com/app/developer/qbo/docs/learn/explore-the-quickbooks-online-api/data-queries) for\nsupported SQL statements):\n\n customers = Customer.query(\"SELECT * FROM Customer WHERE Active = True\", qb=client)\n\nFiltering a list with a custom query with paging:\n\n customers = Customer.query(\"SELECT * FROM Customer WHERE Active = True STARTPOSITION 1 MAXRESULTS 25\", qb=client)\n\nGet record count (do not include the ``\"WHERE\"``):\n\n customer_count = Customer.count(\"Active = True AND CompanyName LIKE 'S%'\", qb=client)\n\nGet single object by Id and update:\n\n customer = Customer.get(1, qb=client)\n customer.CompanyName = \"New Test Company Name\"\n customer.save(qb=client)\n\nCreate new object:\n\n customer = Customer()\n customer.CompanyName = \"Test Company\"\n customer.save(qb=client)\n\nBatch Operations\n----------------\n\nThe batch operation enables an application to perform multiple\noperations in a single request (See [Intuit Batch Operations Guide](https://developer.intuit.com/docs/api/accounting/batch) for\nfull details).\n\nBatch create a list of objects:\n\n from quickbooks.batch import batch_create\n\n customer1 = Customer()\n customer1.CompanyName = \"Test Company 1\"\n\n customer2 = Customer()\n customer2.CompanyName = \"Test Company 2\"\n\n customers = [customer1, customer2]\n\n results = batch_create(customers, qb=client)\n\nBatch update a list of objects:\n\n from quickbooks.batch import batch_update\n customers = Customer.filter(Active=True)\n\n # Update customer records\n \n results = batch_update(customers, qb=client)\n\nBatch delete a list of objects (only entities that support delete can use batch delete):\n\n from quickbooks.batch import batch_delete\n\n payments = Payment.filter(TxnDate=date.today())\n results = batch_delete(payments, qb=client)\n\nReview results for batch operation:\n\n # successes is a list of objects that were successfully updated\n for obj in results.successes:\n print(\"Updated \" + obj.DisplayName)\n\n # faults contains list of failed operations and associated errors\n for fault in results.faults:\n print(\"Operation failed on \" + fault.original_object.DisplayName)\n\n for error in fault.Error:\n print(\"Error \" + error.Message)\n\nChange Data Capture\n-----------------------\nChange Data Capture returns a list of objects that have changed since a given time \n(see [Change data capture](https://developer.intuit.com/docs/api/accounting/changedatacapture) for more details):\n\n from quickbooks.cdc import change_data_capture\n from quickbooks.objects import Invoice\n\n cdc_response = change_data_capture([Invoice], \"2017-01-01T00:00:00\", qb=client)\n for invoice in cdc_response.Invoice:\n # Do something with the invoice\n\nQuerying muliple entity types at the same time:\n\n from quickbooks.objects import Invoice, Customer\n cdc_response = change_data_capture([Invoice, Customer], \"2017-01-01T00:00:00\", qb=client)\n\nIf you use a `datetime` object for the timestamp, it is automatically converted to a string:\n\n from datetime import datetime\n\n cdc_response = change_data_capture([Invoice, Customer], datetime(2017, 1, 1, 0, 0, 0), qb=client)\n\nAttachments\n----------------\nSee [Attachable documentation](https://developer.intuit.com/docs/api/accounting/Attachable) \nfor list of valid file types, file size limits and other restrictions.\n\nAttaching a note to a customer:\n\n attachment = Attachable()\n\n attachable_ref = AttachableRef()\n attachable_ref.EntityRef = customer.to_ref()\n\n attachment.AttachableRef.append(attachable_ref)\n\n attachment.Note = 'This is a note'\n attachment.save(qb=client)\n\nAttaching a file to customer:\n\n attachment = Attachable()\n\n attachable_ref = AttachableRef()\n attachable_ref.EntityRef = customer.to_ref()\n\n attachment.AttachableRef.append(attachable_ref)\n\n attachment.FileName = 'Filename'\n attachment._FilePath = '/folder/filename' # full path to file\n attachment.ContentType = 'application/pdf'\n attachment.save(qb=client)\n\nPassing in optional params\n----------------\nSome QBO objects have options that need to be set on the query string of an API call. \nOne example is `include=allowduplicatedocnum` on the Purchase object. You can add these params when calling save: \n\n purchase.save(qb=self.qb_client, params={'include': 'allowduplicatedocnum'})\n\nOther operations\n----------------\nAdd Sharable link for an invoice sent to external customers (minorversion must be set to 36 or greater):\n\n invoice.invoice_link = true\n\n\nVoid an invoice:\n\n invoice = Invoice()\n invoice.Id = 7\n invoice.void(qb=client)\n\n\nWorking with JSON data\n----------------\nAll objects include `to_json` and `from_json` methods.\n\nConverting an object to JSON data:\n\n account = Account.get(1, qb=client)\n json_data = account.to_json()\n\nLoading JSON data into a quickbooks object:\n\n account = Account.from_json(\n {\n \"AccountType\": \"Accounts Receivable\",\n \"AcctNum\": \"123123\",\n \"Name\": \"MyJobs\"\n }\n )\n account.save(qb=client)\n\nDate formatting\n----------------\nWhen setting date or datetime fields, Quickbooks requires a specific format.\nFormating helpers are available in helpers.py. Example usage:\n\n date_string = qb_date_format(date(2016, 7, 22))\n date_time_string = qb_datetime_format(datetime(2016, 7, 22, 10, 35, 00))\n date_time_with_utc_string = qb_datetime_utc_offset_format(datetime(2016, 7, 22, 10, 35, 00), '-06:00')\n\nException Handling\n----------------\nThe QuickbooksException object contains additional [QBO error code](https://developer.intuit.com/app/developer/qbo/docs/develop/troubleshooting/error-codes#id1) information. \n\n\n from quickbooks.exceptions import QuickbooksException\n\n try:\n # perform a Quickbooks operation\n except QuickbooksException as e:\n e.message # contains the error message returned from QBO\n e.error_code # contains the \n e.detail # contains additional information when available \n\n\n**Note:** Objects and object property names match their Quickbooks\ncounterparts and do not follow PEP8.\n\n**Note:** This is a work-in-progress made public to help other\ndevelopers access the QuickBooks API. Built for a Django project.\n\n\n\n",
"bugtrack_url": null,
"license": "MIT",
"summary": "A Python library for accessing the QuickBooks API.",
"version": "0.9.9",
"project_urls": {
"Homepage": "https://github.com/ej2/python-quickbooks"
},
"split_keywords": [
"quickbooks",
" qbo",
" accounting"
],
"urls": [
{
"comment_text": "",
"digests": {
"blake2b_256": "2b95bd3fce3e40bc36974a066732cbeaca336b45b7ff2f4d2e142cf52475d116",
"md5": "e6ba9ac43b4335a1b9f535ba2f923715",
"sha256": "2c679c77544f451cef92b3c90763abf19e08a9ba5efe6a874c215d823ce15bdd"
},
"downloads": -1,
"filename": "python_quickbooks-0.9.9.tar.gz",
"has_sig": false,
"md5_digest": "e6ba9ac43b4335a1b9f535ba2f923715",
"packagetype": "sdist",
"python_version": "source",
"requires_python": null,
"size": 34100,
"upload_time": "2024-07-09T16:05:51",
"upload_time_iso_8601": "2024-07-09T16:05:51.753248Z",
"url": "https://files.pythonhosted.org/packages/2b/95/bd3fce3e40bc36974a066732cbeaca336b45b7ff2f4d2e142cf52475d116/python_quickbooks-0.9.9.tar.gz",
"yanked": false,
"yanked_reason": null
}
],
"upload_time": "2024-07-09 16:05:51",
"github": true,
"gitlab": false,
"bitbucket": false,
"codeberg": false,
"github_user": "ej2",
"github_project": "python-quickbooks",
"travis_ci": false,
"coveralls": false,
"github_actions": true,
"requirements": [
{
"name": "intuit-oauth",
"specs": [
[
"==",
"1.2.4"
]
]
},
{
"name": "requests_oauthlib",
"specs": [
[
">=",
"1.3.1"
]
]
},
{
"name": "requests",
"specs": [
[
">=",
"2.31.0"
]
]
}
],
"lcname": "python-quickbooks"
}