Instant API Backends
One command to create an API for your database. And a Basic Web App. With spreadsheet-like business logic — 40X more concise. Extensible with Python.
Join the DZone community and get the full member experience.Join For Free
Is backend creation blocking your Mobile App Dev? Or strategic B2B/internal integration?
Imagine that you could...
Create a database API, instantly?
And declare logic, with spreadsheet-like rules?
Plus an instant Web App, to engage Business Users?
Well, you've just imagined API Logic Server! Working software... now!
In this 10-20 minute tutorial, we'll create, explore and customize the 3 main elements of an API Logic Server:
- A JSON:API for a database
- Business Logic
- A Basic Web App
In this step, we'll use the ApiLogicServer CLI to create and run an api_logic_server project (an API and Web App, backed by underlying Logic):
To create the ApiLogicServer:
- Paste the following into a Terminal window:
Accept the default
Database URLparameter to use the supplied sample database.
- After this Tutorial, you can try it with your own database, by specifying a SQLAlchemy URL (see links below).
Quite a lot just happened that substantially accelerates your project. The process is shown in the diagram below, mapping your actions (A, B, C -- you just did step B) onto a classic n-tiered modern software architecture:
|What You do||What System Does||Why It Matters|
|A) Create DB||(Presupplied for demo)||Use existing tools and procedures|
|B) ApiLogicServer run||1) Instant API: From schema, creates an endpoint for each table - CRUD Data Access automation, including filtering. pagination and related data access||Custom UI development is unblocked on API coding (routes, controllers, ORMs...)|
|2) Instant Web App: Multi-page, multi-table||Engage business users with working software, early in the project|
|C) Declare Logic||Executes spreadsheet-like rules that automate the cocktail napkin spec||Business Agility: 40X more concise, customizable with Python|
1. Explore the API
In many projects, User Interface development is blocked by waiting on API creation.
run command not only created the project, but it ran
python api_logic_server/api_logic_server_run.py to start the server. Let's explore it.
Key Takeaway: ApiLogicServer unblocks UI development
with instant API creation.
Your API can be explored with Open API (Swagger). Explore the api at https://localhost:5000, and:
- Click Customer
- Click Get
- Click Try it out
- Click Execute
Swagger is a great way to discover the API, and get copy/paste code for UI app dev.
In addition to Open API, we can use curl.
- Paste this into a terminal window:
- Observe the response in the Terminal window
GET request, observe:
page offset- pagination support
filter- autmatic support for filtering rows
JSON:APIs - automated by safrs - are client configurable. This is valuable because:
- Client Configurable APIs can reduce network traffic - a single call instead of multiple calls on predefined APIs that don't return quite the correct data
- Client Configurable APIs can reduce organizational dependencies - instead of a waiting on creation of a wide number of endpoints from the server team, UI developers can configure their own APIs
In the example below, observe the following in the
fieldsto designate the fields to be returned
includeto designate related data
- Paste this into a Terminal window:
- In the response, observe the
"included": [tag - the list of related
Your API also includes services for insert, update and delete. We can use curl to test the update.
- Paste the following into a Terminal window:
- Observe the update request reports the violation from our predefined constraint rule:
This was entirely intentional, to illustrate the transaction logic underlying the API. Let's explore that.
The classic definition of Business Logic covers 2 aspects:
- Data Access — this was automated in the
ApiLogicServer runstep, which created not only the API, but the data access (based on SQLAlchemy)
- Transaction logic — multi-table derivations, constraints, and actions such as sending mail or messages — is a significant aspect of any database oriented system, nearly half
Logic is the iceberg under the surface of the API.
ApiLogicServer provides a unique
declarative, rules-based approach
for automating transaction logic.
It's striking how a small "cocktail napkin specification" balloons into hundreds of lines of code:
Implementing logic by conventional procedural code is
slow, error prone, and painful to maintain.
Api Logic Server dramatically improves conciseness, quality and maintainability, by introducing a significant innovation for automating transaction logic: Logic Bank. Logic consists of:
- Rules — 40X more concise using a declarative, spreadsheet-like paradigm, and
- Python — control and extensibility, using standard tools and techniques
Note: in this tutorial, the API and Web App were created strictly from the data model. The logic, however, is injected so you can explore it.
Rules are not simply procedural event handlers. They are spreadsheet-like expressions for constraints and derivations, applied on commit. The process is follows:
- Design as you normally would, and specify the behavior - the "cocktail napkin spec" above
- Declare rules to express your design
- You will find that there is a very close mapping from your design to the rule declarations, as shown below
- These 5 rules replace all the Python code shown above — 200 lines
- Extend with Python (shown later):
This table summarizes the key declarative/procedural differences:
|Characteristic||Procedural||Declarative||Why It Matters|
|Reuse||Not Automatic||Automatic - all Use Cases||40X Code Reduction|
|Invocation||Passive - only if called||Active - call not required||Quality|
Unlike code, you do not call the rules directly. The rules engine in Logic Bank listens for SQLAlchemy
before_flushevents, and applies the applicable rules in an order that reflects their dependencies, with chaining.
For more information on rules, see the links at the end.
The constraint rule (line 54, above) is what caused the update error response above - the
Balance exceeded the altered
CreditLimit. The transaction is rolled back.
Let's pause for some perspective: what is 40X more concise?
A jetliner flies 4X the speed of Charles Lindbergh's Spirit of St. Louis. To get to 40X, you need a scram jet.
So, rules mean that for nearly half your system, you are writing one rule instead of nearly a page of code. See the contrast in the links, at the end, for the actual code vs. rules contrast.
The links (at the end) include a complete list of rules, and examples.
Key Takeaway: Logic is 40X more concise, higher quality, and easier to maintain than legacy procedural code.
3. Explore the Basic Web App
UI development takes time. That's a problem since:
- Such effort may not be warranted for admin "back office" screens, and
- Agile approaches depend on getting working software soon, to drive collaboration and iteration.
ApiLogicServer CLI therefore creates working software now: multi-page, multi-table applications as shown below:
- Multi-page: apps include 1 page per table
- Multi-table: pages include
related_viewsfor each related child table, and join in parent data
- Favorite fields first: first-displayed field is "name", or
- Predictive joins: favorite field of each parent is shown (product name - not product id)
- IDs last: such boring fields are not shown on lists, and at the end on other pages
Start the application:
Before running, you must Create Admin Data for Flask App Builder (except for the Northwind sample, which is pre-created).
Customize With Python
Recall using API Logic Server CLI:
created a complete, executable ApiLogicServer project in a directory called
api_logic_server. On your own machine, you could open the project in an IDE (PyCharm, VSCode, etc) or an Editor (Atom, Text Wrangler, etc). It looks like this in PyCharm:
ApiLogicServer CLI introspected your database and created a
database/models.py file (for SQLAlchemy), and files that declare your
ui/basic-web-app. You can edit those files to customize your server, as described below.
You may need to extend the initially created data model classes, to define derived attributes, or to add relationships not defined in the schema. Such extensions are added to a separate file, to avoid merges if you ever need to rebuild the model classes from a changed schema.
Add code like this to
Customize the API
Your API is derived from the database, but it is not restricted to that. You can customize your API, e.g., add new endpoints and services.
For example - an instant API for a database is all well and good - but can we build the "hello world" so desperately sought by enterprises all over the world? We can.
Examine the following code in
You can run this with curl:
You can also create multi-table services as shown below, for adding an
Order and a list of
Service Definition: to define a service:
expose_services.py, and define a decorated method (line 94). The payload (
Orderand a list of
OrderDetails) is passed in as
b. Your first comment (line 98) describes the arguments in YAML, along with sample data, exposed in Swagger.
a. Use standard Python (lines 110-116) for your service code, including SQLAlchemy and other Python packages.
Note the use of
json_to_entities, to transform the json payload into mapped SQLAlchemy model objects. It is generic, so can be used with your own model objects.
b. It's short, since transaction logic is factored out and automatically reused. The rules that fired for changing a Customers' CreditLimit also monitor order processing. If the json argument contains an absurdly high
quantity, the logic detects this and throws an error. This is shown in the log in the bottom pane, where the indentation illustrates the chaining of a multi-table transaction.
On the last few lines of the log:
1. OrderDetail.Amount is derived 2. OrderDetail.Amount adjusts the Order.TotalAmount 3. the Order.TotalAmount adjusts the Customer.Balance 4. which is checked in the constraint
Key Takeaway: Extend API with Python
Your API is not restricted to the database model -
extend it with standard Python
Key Takeaway: Automatic Reuse
In traditional procedural coding, re-use is generally achieved with significant design work. But in this declarative approach, logic is automatically re-used for all transactions. That has a significant impact on conciseness, and quality.
Use Python to customize logic. Let's POST a new Order:
- Paste the following into the a Terminal window:
- Observe the line containing Congratulations in the log (bottom pane), generated by the event declared on line 64, and implemented on line 44:
This illustrates that you can leverage the full power of Python for events, and more complex constraints and formulas, to complement the expressive power of rules.
Key Takeaway: ApiLogicServer spreadsheet-like logic is extensible with standard Python.
The Basic Web App is driven by
ui/basic_web_app/app/views.py, which contains classes like this for each table:
You can edit this file to control what columns are displayed, their display order, and what related data (views) are shown.
Flask AppBuilder has a wide range of capabilities, including charts. For more information, see Flask AppBuilder.
Key Takeaway: ApiLogicServer multi-page, multi-table apps provide instant back-office admin and agile prototyping.
In 20 minutes — instead of weeks or months — you have built and executed an ApiLogicServer, and explored its 3 key elements:
|Element||Key Takeaway||Why It Matters|
|JSON:API||Created instantly, customizable||Unblock UI Development|
|Logic||Spreadsheet-like rules automate the cocktail napkin spec
40X more concise, customizable with Python
|Strategic Business Agility|
|Basic Web App||Multi-page, multi-table - created instantly, customizable||Engage Business Users, early|
That's a significant result.
This combination of an instant API and spreadsheet-like logic - customizable with Python - may mean it's time to take a very close look at this technology, to create database backends with strategic business agility.
Logic - Explore Types, Examples
Logic - Perspective: 40X
- See the logic vs code contrast here
Explore Basic Web App
- Before running, you must Create Admin Data for Flask App Builder (except for Northwind, which is pre-created)
- You can leverage the full power of Python for events, and more complex constraints and formulas
Opinions expressed by DZone contributors are their own.