Application Development Blog Posts
Learn and share on deeper, cross technology development topics such as integration and connectivity, automation, cloud extensibility, developing at scale, and security.
Showing results for 
Search instead for 
Did you mean: 
I am a member of a team building SAP S/4HANA Cloud applications. I am mainly working on the back-end part (ABAP) but these days I am more involved in automation of our development processes where I often create tools in Python and Bash.

I would like to briefly introduce the Python library providing OData client our team has built while we were working on test automation of OData services providing data for our Fiori applications.

The library has name pyodata and its has three homes:

Why Python?

In the beginning of our Fiori journey, we made the decision to go for BTD and ATTD and since we were experienced Python programmers we took Robot Framework as the test tool.

Our goals

Due to our lack of deep knowledge of OData protocol, our test base started growing by ad-hoc OData URLs builders and results processors. We were aware of the existing Python libraries but no one was willing to tailor them to our needs and some of them looked un-maintained.

In the next step, we created Robot keywords executing basic OData request and were happy until we ran into the need to prepare test data. It was a natural decision to start building the test-data preparation tools in Python too. At the moment we already had a metadata analyzer verifying validity of $metadata document (e.g. checking ValueList annotations points to the existing EntityTypes and EntityProperties).

So, we took the metadata analyzer and used its output to create a OData request builder seamlessly integrated into Python. We want to save us a lot of typing by avoiding the need to use brackets for function calls and providing string literals - instead we rather leverage Python dynamic features to enable writing code as if you had native Python types and functions.


Currently the library supports only

  • OData V2

However, we plan to add support for V4 soon and potentially V3 in future.

Even though we started with Python 2.7 we no longer support this version of Python and focus on

  • Python >= 3.6

We did not want to make the library dependent on any HTTP framework, thus you must provide an object implementing Python Requests Session object's interface. That allows to focus on OData protocol and ignore service vendor implementation details.

However, we have been building the library against SAP Gateway, so the implementation favors this vendor (for example, the library gracefully handle errors reported by SAP Gateway).


For demonstration purposes, I took the backend OData service at which provides data for SAP Fiori Apps Reference Library

List of all OnPremis Releases

import requests
import pyodata


client = pyodata.Client(SERVICE_URL, requests)

query = client.entity_sets.Releases.get_entities()
query = query.filter(query.releaseType == 'SOP')

for rel in query.execute():
print(f'{rel.releaseName} ({rel.releaseId})')

List of all apps in the release SAP S/4HANA 1809 and its FPSes

import requests
import pyodata
from pyodata.v2.service import GetEntitySetFilter as esf


client = pyodata.Client(SERVICE_URL, requests)

rel_query = client.entity_sets.Releases.get_entities().filter("startswith(releaseName, 'S/4HANA 1809')")
sop_releases = rel_query.execute()

apps_query = client.entity_sets.AppsOnSearch.get_entities()
apps_cond = esf.or_(*[apps_query.releaseId == sop.releaseId for sop in sop_releases])

for app in apps_query.filter(apps_cond).execute():
print(f'{app.AppNameAll} ({app.appId})')

Bottom line

PyOData is being developed with Developer Experience in our minds and we have some ideas how to make the library even more comfortable (our Wish List). However, only the developers using the library know which parts are not optimal, so I encourage you to report us your ideas.

I hope I will enjoy the python way of consuming OData services as our team do!
  • SAP Managed Tags:
Labels in this area