Why not build fewer, more useful OData services?
Do you ever have the feeling that you are missing something obvious?
It seems to me that the current orthodoxy is that an OData service should be developed for each UI5 app. In other words, each app should only have to call one service. I think we should question whether that is the best approach.
Of course, a UI5 app can use many OData models, so long as each one has a unique name within the app.
In my opinion, when developing OData services (e.g. using Netweaver Gateway or HCI OData Provisioning), we should think of the big picture. We shouldn’t be too focused on the bespoke Fiori-style app we happen to be developing that day. In a few years time we may have a large number of Fiori apps, both standard and bespoke. There may be many other consumers of our OData services both internal (e.g. our own company website or intranet) and external (e.g. customer or supplier systems).
Why not take an ‘API’ approach, and think of our OData services as a way of interacting with the entities in our back end system? Why not organise the services in such a way as to make it easy to navigate for any UI developer working with any technology? For example we could have a service for customers, one for inventory and one for employees. It seems to me that this would be much more in line with the RESTful architecture. Just because we are using an SAP technology, such as Gateway, to deliver our services, it doesn’t mean we should only consider SAP UI-technologies as consumers. A big plus of the modern web-architecture is that the UI-layer is completely de-coupled from the data-provider and I think we should take advantage of that.
If we (SAP and customers) carry on developing new services at a rapid rate, within a few years I fear we will have a large number of overlapping services. It will be so hard to find one to use that developers will simply create another brand new service rather than trying to sort through that long list. There will be much duplication of logic.
Each published service represents a responsibility (does it work as it should?) and a vulnerability (could it facilitate malicious activity?). This isn’t new (the same can be said for a remote-enabled function module) but surely a very large number of services makes it harder to manage these risks.
Pros & Cons
This is my take on the pros and cons of the one-service-per app model:
- ➕ Robust, as development of a service for app #2 does not affect app #1. This helps us get an app live very quickly, and may fit in better with an agile methodology(?). This appeals to those who found the ESOA (Enterprise Service-Orientated Architecture) approach difficult to manage in practice
- ➕ Re-usability can be introduced via ‘Concrete classes’, as described by Leigh Mason here Making your SAP Gateway work smarter not harder and also Service Inclusion
- ➕ Data provider classes are quite small and manageable as there are only a few entities in each service
- ➕ The service can be optimised for the app. However, this can probably be achieved in a generic service by using features such as $select to specify the fields required. Also, there is nothing to say that the ‘customer’ service must only have one, generic ‘customer’ entity
- ➕ An external ‘API’ product could perhaps be used to unify and present the services provided by Gateway (and other OData providers too)
- ➖ Will lead in time to a large number of overlapping services. It will be hard for a UI-developer to find what they need
- ➖ Likely there will be a lot of duplication of logic (across services), leading to greater effort and reduced maintainability. How many times will an employee entity be required, for example, in order to provide employee names?
- ➖ Services are designed for individual apps on one particular platform (UI5/Fiori) and might not be suitable for future apps or other UI platforms
What do you think? What do you do?
So, is there an obvious point that I am missing? Are there advantages of the one-service-per-app approach that I have missed? Am I wrong to call one-service-per-app the orthodoxy?
What is the strategy in your organisation (or at your clients) for OData services? I look forward to your comments.
If you take a UX approach to developing your OData API's then your OData Entities should be fit for purpose and embody the user requirements, because of the different use cases the API requirements for a UI5 application should be different from those of an Android, IOS, Desktop, Analytics application etc.
If we were to produce one "God like" OData service and circulate to the different concerns, the interface of that service would become brittle and prone to change, adding new fields and features to an Entity which is used broadly brings version management, which in turn brings own delivery overheads, not to mention leaky abstractions as the front end developers try to make the OData Entity do the things it wasn't built for, like sorting, filter and paging which do not come out of the box with a Gateway service.
There should be a level of reuse in the back end code, especially on the CUD side but on the Query side to write fit for purpose Queries I believe you would want to get closer to the metal and provide the front end developers with Entities representing the domain and language of the use case. <CDS Queries>
Just to address a couple of the pros and cons
"this can probably be achieved in a generic service by using features such as $select to specify the fields required."
In HANA value fields aggregate by default if you $select a smaller dataset you may get unwanted/unexpected results - I try to give the UI developers what they need, nothing more, data and business logic is not their domain, the service should have as little friction as possible for its consumption.
" It will be hard for a UI-developer to find what they need"
see above, should it be the domain of the UI developer to know what service to use and how to use it, lots of friction and overhead in a one-size-fits-all service.
"Services are designed for individual apps on one particular platform (UI5/Fiori) and might not be suitable for future apps or other UI platforms"
Services like Apps should be disposable, else you end up with BAPIs on the outside too
Nice blog. You have asked exact same questions that I encountered from many project managers/customers. They love code reusability for obvious reasons.
I have always found using "one service for one app" is a new thing for most people who think from SoA or BAPI angle. So I would not think it as a orthodox/traditional approach.
I also found that this (one service-one app) is a very useful approach if you are designing the app in top-down approach. That is, you create the mock-up first, create an OData model that 'suits' the mockup, then you go about implementing this OData model. Top-down approach is also useful if you want to make efficient use of two-way binding.
Rather if you go the API approach( reuse approach), you start with the implementation first (that of the existing service), then you have to go up on how to tailor the existing OData model with the new UI. That is nothing but bottom-up approach of app design which as I have seen results in many work arounds in UI layer. (like converting OData model to json model etc.)
But I completely agree that business logic should be reused as much as possible. I have been doing it by keeping no business logic in DPC, and moving it into reusable classes.
Though I have not yet tried, I think using "Concrete classes" is the middle path between independent service approach and API approach. But concrete classes also makes sense if you are creating a suite of applications (ex: for e-recruitment, ESS etc.), not when you create a single application.
My two cents.
Good article and it is something we try and do. As John has said, it isn't always a good match, but we very much go down the route of using classes, rather than individual BAPI's.
This has worked rather well at one client, where what we built initially for a desktop app, has been re-used on mobile devices. Obviously a mobile first approach helps with this.
To me, I love the API approach and I know that SAP's vision of Gateway is that it is the API layer to SAP, as they've seen how well this has worked with Salesforce (It is something like 60% of calls to Salesforce are via API). This really does open up SAP to not only good UI, but also things like new processes across both SAP and non-SAP systems, all via API's. Suddenly (particularly when you add in a HANA DB), your SAP system can be the system behind a B2C scenario, surfacing millions of requests per hour.
There's actually a company in the marketplace taking advantage of the SAP OData capabilities. Gateway Architects' Meister is doing this, focusing on major areas like Procure to Pay, Order to Cash, Budget/Claims, and so on, producing JSON content in a 'headless' state with no payload limits, making it easier to use with virtually any endpoint application/device. furthermore, GAMeister uses embedded compression techniques reduce payloads by an average of 90% and AI/ML to continuously enhance the payload results for a better user experience when desired.