0
\$\begingroup\$

I am working on a Flask application (side-project) to send text-messages to customers using Twilio. There is two different list of customers, 1 for testing and for production (stored in MongoDB). Current functionalities:

  • user login/ logout
  • Add, remove or search a user in both test and production collections
  • Send a text message to a given list (using Twilio API)
  • Get the current credit amount left on Twilio
  • (to-do): get an overview of the past messages sent / the cost of the campaign and the date

enter image description here

I used to have everything under main.py but I recently refactored most of my code to make it more readable. I am now using blueprints and initializing my app using the factory design pattern. So far, I only have a single blueprint (user) but I am trying to split logic between user blueprint (login/logout) and messaging (send messages).

On my navbar, I display the amount left of Twilio (81 euros in the image). I am using the Flask context_processor to inject the value on the navbar. However, the point of having a blueprint is that it encapsulates everything. And if I have multiple blueprints, I would need to duplicate that context_processor.

web_messaging/templates/layouts/base.html (where the credit amount is injected)

<!DOCTYPE html>
<html lang="en">
<body>
  <nav class="navbar navbar-expand-md bg-dark navbar-dark fixed-top">
    ...
      <ul class="navbar-nav ml-auto">
            {% if current_user.is_authenticated %}
            <li class="nav-item">
              <a class="nav-link">{{credit}} €</a>
          </li>
            <li class="nav-item">
                <a class="nav-link" href="{{url_for('user.logout')}}">Déconnection</a>
            </li>
            {% else %}
            <li class="nav-item">
            <a class="nav-link" href="{{url_for('user.login')}}">Connection</a>
            </li>

            {% endif %}
      </ul>
    </div>
  </nav>

  {% block body %}{% endblock %}
</html>

web_messaging/blueprints/user/routes.py (where the credit is generated)

user = Blueprint('user', __name__, template_folder='templates')

...

def get_current_credits():    
    balance_data = client.api.v2010.balance.fetch()
    balance = float(balance_data.balance)
    currency = balance_data.currency
    return balance, currency  


@user.context_processor
def inject_credit():
    credit, currency = get_current_credits()
    if currency != "EUR":
        credit = c.convert(credit, currency, 'EUR')
    return dict(credit=(round(credit,2)))

What I am thinking about is to create a web_messaging/context_manager.py file to manage all contexts. The issue I see here is I will have to import Twilio library on context.py

def get_current_credits():    
    balance_data = client.api.v2010.balance.fetch()
    balance = float(balance_data.balance)
    currency = balance_data.currency
    return balance, currency  

def inject_credit():
    credit, currency = get_current_credits()
    if currency != "EUR":
        credit = c.convert(credit, currency, 'EUR')
    return dict(credit=(round(credit,2)))

web_messaging/app.py

from context import inject_credit

def create_app(settings_override=None):
    app = Flask(__name__, instance_relative_config=True)

    app.config.from_object('config.settings')
    app.config.from_pyfile('settings.py', silent=True)
    app.register_blueprint(user)
    app.register_blueprint(texting)
    extensions(app)
    configure_context_processors(app) # here
    return app

def configure_context_processors(app):
    processors = [inject_credit]
    for processor in processors:
        app.context_processor(processor)
\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.