Article
· Nov 14, 2023 7m read

Example of Flask application with SQLAlchemy-IRIS - Part 2

Why should you connect Flask to InterSystems IRIS?

    The first thing that comes to mind when we think about combining Flask with IRIS is a portal to interact with your clients and partners. A good example would be a website for patients to access their clinical exams. Of course, this case would require a whole new layer of security, which we did not cover in our last article. However, we can effortlessly add it with Werkzeug, for instance.
Websites to bridge the relationship between your products and clients are, indeed, an excellent example of what you can achieve with this connection of technologies since Flask is flexible, and you can easily add and change any features with it or even do more things if you have some experience with CI/CD.
Let's look at some of the tricks you can perform. If you recall the first application shown in the beginning, you will remember that Flask does not need a complex structure to work, meaning you can build it from scratch with only a few minutes of coding. That means you can quickly create multiple user-friendly interfaces and interactive portals to display and analyze data. For example, you can keep track of every single part of a production separately. Also, you can provide any of InterSystems IRIS features that you frequently use on a beautiful no-code platform. 
    I have been working for Innovatium since last year, and that experience helped me encounter many situations where it was practical to acknowledge the memory used in query result sets, requests, and tables from time to time. This issue is easy to fix by making a portal similar to the one created in my previous article about Django. Since developing with Flask is faster than with Django, it would be painless to construct a few different platforms for each project and for each table that we wish to track. Besides, if you have some extra time, you can automate your platform to get live updates with Flask-SocktetIO.
Having a template to start your projects can accelerate development even more. That is why the next section will introduce a Flask-IRIS CRUD template published on OpenExchange (the one we built in Part 1 of this series of articles). What I mean by that is if you don’t have the time to investigate all the details covered in the last article, just download the application and keep on working with your current knowledge about your project without any worries.
 

The OpenExchange Application

I have decided to write this series of articles inspired by the idea mentioned in the Example of Flask application with SQLAlchemy IRIS. However, since you might already be familiar with Python’s web frameworks and the CRUD logic, I will introduce you to an application to get your hands dirty immediately. This way, you will not have to waste your time reading before your project starts to take shape.
    Follow the steps below to download and start using the application, begin to use it, and watch how easy it is. There is a more succinct version of the about-to-be-mentioned tutorial of its usage on the README file on the related GitHub Repository. You can also check out every link related to the app on its Open Exchange page.

 

Installation Guide

    Before developing projects with Python, it is always a good practice to set up a virtual environment. It will help you add all the requirements, configurations, and variables strictly to this project, without affecting your computer and other projects.
    On Windows/Linux/macOS, open the terminal on the directory where you wish to start your project and create a virtual environment there with the following command:
python -m venv .venv-folder
    The above-mentioned command can be broken down like this: “python” will set a Python environment for the following commands, the -m flag will run a module (in this case, venv), and .venv-folder will create a folder called venv-folder in the current directory (referred by the dot), where the venv module will run.
    Your next step will be to activate the created environment before downloading the requirements and properly starting your project.
    If you use macOS or Linux, you should type “. .venv/bin/activate”. On Windows, the similar command “.venv\Scritps\activate” will run the proper file for the task.
    Then, you can clone the repository with git clone.
git clone https://github.com/heloisatambara/flask-iris.git
    Finally, install the requirements with the Python Install Package, and you will be ready to start coding.
pip install -r requirements.txt
    As you can check on the referred file, the command above will install at least 2.3.3 version of Flask, at least 3.1.1 version of Flask-SQLAlchemy, and at least 0.10.5 version of sqlalchemy-iris, by ^CaretDev.

 

Usage Guide

    First, you have to connect the application to the desired database and namespace. As you may have learned in the previous article, this connection is made on the flaskr-iris/database.py file, with the format “iris://username:password@host:port/NAMESPACE”, as specified on SQLALchemy documentation for the create_engine() function. Examine the example below.
    engine = create_engine("iris://_SYSTEM:sys@localhost:1972/SAMPLE")
    Now, you can finally run the web application and see how the example you developed is working, after checking if the instance is running, with the command about-to-be-mentioned.
...\flask-iris> flask --app flaskr-iris run --debug
    To adapt the application to your needs, start with editing the flaskr-iris/models.py to reflect the data you will require to bring from IRIS to Python. The example cloned from GitHub already covers a great number of cases, as you can check in the previous article in the section dedicated to the models. If you need something else, you can review the related Flask-SQLAlchemy or SQLAlchemy documentation, about defining models and declarative tables, respectively.
    Then, it is suggested that you continue developing by editing the files in flaskr-iris/templates, to adapt the display to your data. The Jinja documentation contains all the options for coding your templates.
    Next, you can use the examples from auth.py and blog.py to create your views. Don’t forget to register all new Blueprints on the create_app() factory, in the __init__.py file.
    Finally, the files inside the static folder should give you a head start to add your brand’s style to the web page.
 

Bonus section - Errors I ran into and how to correct them

  • Starting with what may seem like a newbie error but can happen to anyone: if you forgot to initialize the IRIS instance you are connecting to, you might receive the following message:
sqlalchemy.exc.OperationalError: (intersystems_iris.dbapi._DBAPI.OperationalError) [WinError 10061] No connection could be made because the target machine actively refused it.


Of course, all you need to do here is to press “Start InterSystems IRIS” and run your Flask app again.
 

  • The following error might feel a little more challenging:
RuntimeError: Working outside of request context.

This typically means that you attempted to use functionality that
needed an active HTTP request. Consult the documentation on testing
for information about how to avoid this problem.
db.init_app(app)

    This error may occur due to a few different reasons. If you found it when testing, use the test_client to simulate a complete request. Otherwise, you might need to move your code into a view. However, I ran into this error not in a typical situation: I had not initiated the database with the Flask app. To fix that, when you define your database with db = SQLAlchemy() or similar, you can connect the app directly by doing the following:

app = Flask(__name__)
db = SQLAlchemy(app)

Alternatively, if you are working with an application factory, as shown in the previous article, you can connect the app later by calling init_app():

db = SQLAlchemy()

def create_app():
	app = Flask(__name__)
	db.init_app(app)
  • If you choose to follow the approach from Part 1 of this article, you might notice that every time you run your application, it will try to create all databases from the models you have defined. That means you might need to treat this type of error with a “try/except” block. As an option, you can ignore the error if the table already exists but do not forget to fix other issues too. However, if you select this solution, you might need to delete all the tables manually every time you make changes to them.  Another option is to use the “checkfirst” attribute when calling the create_all() function. That will ignore tables that already exist, so changes will not be applied. If that suits your needs, enjoy. Yet, for a larger-scale implementation, you can use SQLAlchemy to drop previously created tables before running create_all(). Be careful: the tables will be created automatically with the name format DefaultSchema_snake_case_model_name. To illustrate my point, in the example we have just explored, the tables were built in IRIS with the names SQLUser_user and SQLUser_post.
try:
    with app.app_context():
        db.create_all()
except DatabaseError as err:
    if 'already exists' in err._sql_message():
        print("Databases already exist.")
    else:
        print(err) 
  • Last but not least, when you place the models in a different file from the one you used to run the create_all() function, you might feel that it does not work. It happens because you must import every model you want to assemble before trying to make them.
from .models import User, Post
db.init_app(app)
try:
    with app.app_context():
        db.create_all()
Discussion (0)1
Log in or sign up to continue