Python flask directory structure for service layer? - python-3.x

I'm an aspnet core developer and trying to do a test project in python using the flask framework. But because of my lack of understanding of the structure of python projects I'm having hard time compiling it. I don't understand why does it care if I keep my python file in another directory. In C# you can access all classes inside the same namespace without importing anything.
Here's my python flask project structure looks like. I can't seem to work it with this way. I'm trying to import my home_service.py inside home.py file where home routes are present (in aspnet's term controller) and the logger doesn't seem to be accessible either.
And home_service.py can't import db_util.py either.
Would any python flask expert please guide me in the right direction?
/../../Projects/flask-test-project
├── test-project/
│ ├── __init__.py
│ └── static/
│ └── site.css
│ ├── templates/
│ │ ├── layout.html
│ │ ├── home.html
│ │ ├── offerings.html
│ │ ├── login.html
│ │ ├── register.html
│ │ ├── 404.html
│ │ ├── 500.html
│ ├── views/
│ │ ├── __init__.py
│ │ ├── home.py
│ │ ├── offerings.py
│ │ ├── login.py
│ │ ├── register.py
│ ├── service/
│ │ ├── home_service.py
│ │ ├── db_util.py
├── flask-venv-for-ubuntu/
├── requirements.txt
└── run.py
**run.py**
from test-project import app
from datetime import datetime
import logging
todays_date = datetime.today().strftime('%Y%m%d')
logging.basicConfig(filename='error'+ todays_date+'.log',level=logging.Trace)
app.run(debug=True)
app.logger.trace(“Inside run.py”)
**__init__.py**
from flask import g, Blueprint, request
from psycopg2
# $ pip install sentry-sdk[flask]
from werkzeug.exceptions import HTTPException
app = Flask(__name__)
#app.errorhandler(404)
def not_found(error):
return render_template('404.html')
#app.errorhandler(HTTPException)
def handle_exception(e):
app.logger.error(e)
return render_template(“500.html”)
#app.teardown_appcontext
def close_connection():
db = getattr(g, '_database', None)
if db is not None:
db.close()
from test-project.views import home
from test-project.views import login
from test-project.views import register
from test-project.views import offerings
app.register_blueprint(home.mod)
app.register_blueprint(login.mod)
app.register_blueprint(register.mod)
app.register_blueprint(offerings.mod)
**db_util.py**
from flask import g
import psycopg2
POSTGRES_CONNECTIONSTRING = “……...”
def get_db():
db = getattr(g, '_database', None)
if db is None:
db = g._database = psycopg2.connect(POSTGRES_CONNECTIONSTRING)
return db
def query_db(query, args=(), one=False):
try:
cur = get_db().execute(query, args)
rv = cur.fetchall()
cur.close()
return (rv[0] if rv else None) if one else rv
finally:
if(cur)
cur.close()
**home_service.py**
import db_util
def get_something
app.logger.Debug(“get_something started”)
return query_db(“select count(*) as myCount from table1;”)
**home.py**
import home_service
mod = Flask(“home”,__name__)
#mod.route(“/something”)
def something():
app.logger.Debug(“get_something started”)
return render_template(“home.html”, count_of_table1=get_something().myCount)
Please don't recommend me to use SQLAlchemy or any other orm. I want to do it my way. Thanks!

Related

How to import routes flask

I am a beginner with Flask and I have created a project with an MVC structure
CODE :
.
├── app
│. │── main.py
│ ├── controllers
│ │ ├── dbscan.py
│ │ ├── home.py
│ │ └── kmeans.py
│ ├── models
│ │ ├── dbscan.py
│ │ └── kmeans.py
│ ├── static
│ │ └── XXXX
│ └── views
│ └── XXXX
└── main.py
File main.py
from flask import Flask
app = Flask(
__name__,
template_folder='app/views',
static_folder='app/static'
)
if __name__ == "__main__":
app.run(debug=True)
File home.py
from flask import render_template
#app.route("/")
def home():
return render_template('home.html')
ISSUE :
I already understood the problem but I don't know how to fix it...
There is no link between the controllers files and the main.py
So, how I can link all routes present in controllers folder and main.py ?
UPDATE :
home.py
from flask import Blueprint, render_template
home_hdl = Blueprint('home_hdl', __name__, template_folder='views')
#home_hdl.route("/")
def home():
return render_template('home.html')
main.py
from flask import Flask
from app.controllers.home import home_hdl
app = Flask(
__name__,
template_folder='app/views',
static_folder='app/static'
)
app.register_blueprint(home_hdl)
if __name__ == "__main__":
app.run(debug=True)
Folders
.
├── app
│ ├── controllers
│ │ ├── __init__.py
│ │ ├── dbscan.py
│ │ ├── home.py
│ │ └── kmeans.py
│ ├── main.py
│ ├── models
│ │ └── XXXX
│ ├── static
│ │ └── XXXX
│ └── views
│ └── XXXX
└── XXXX
Try this
Define a handler in each of the files you have under the controllers folder (the ones that will handle routing).
E.g. for the dbscan.py, you could have
from flask import Blueprint
dbscan_handlers = Blueprint('dbscan_handlers', __name__, template_folder='views')
# Your routes (in the dbscan.py file) will then be something like this
#dbscan_handlers.route('/xyz/'):
.....
#dbscan_handlers.route('/def/'):
....
Then you register the handler in main.py
from controllers.dbscan import dbscan_handlers
app.register_blueprint(dbscan_handlers)
Note that to do from controllers.abc import xyz, you need to have an __init.py__ file in controllers. The file can be empty.
When someone accesses your app, it will go to main.py and if the route is of the pattern /xyz/, it will be handled by dbscan.py file

How to import a module from another package in python3?

Currently i'm having a file structure like below.
├── src
│ ├── common
│ │ ├──constants.py
│ │ └──configs.py
│ ├── utils
│ │ ├──module1.py
│ │ └──module2.py
│ └── service
│ │ ├──module3.py
│ │ └──module24.py
│ └── main.py
├── test
│ ├── utils
│ │ ├──test_module1.py
│ │ └──test_module2.py
My test_module1.py includes
# test_module1.py
import sys
sys.path.append("./.")
from src.utils.module1 import filter_file
from unittest import TestCase, main, mock
utils/module1.py includes
# module1.py
from common.constants import LOG_FORMAT, TIME_FORMAT
...
Here, when i try to run test_module1.py file from root i get an error saying that,
$- python3 test/utils/test_module1.py
$- ModuleNotFoundError: No module named 'common.constants'
what is the issue here
Tested it, works like this on Windows:
├── src
│ └── utils
│ └──lib.py
├── test
│ └── utils
│ └──bla.py
lib.py:
def test():
print("woo")
bla.py:
import os
import sys
sys.path.append(".." + os.sep + "..")
from src.utils.lib import test
test()

Problem with importing a module in a Python3 script

I got this error: ImportError: cannot import name 'admin' from ' admin.blueprint' after I'm in the module blueprint.py imported Post from models.py please help me to understand the structure of the application in order to avoid such errors in the future.
<module main.py>
from flask import Flask
from flask_sqlalchemy import SQLAlchemy
from admin.blueprint import admin
from config import Config
app = Flask(__name__)
app.config.from_object(Config)
db = SQLAlchemy(app)
app.register_blueprint(admin, url_prefix='/admin')
import views
if __name__ == '__main__'
db.create_all()
app.run(debug=True)`
<module blueprint.py>
from flask import Blueprint, redirect, render_template, request, url_for
from config import ConfigAdmin
from models import Post
admin = Blueprint('admin', __name__, template_folder='templates', static_folder='static')
#admin.route('/')
def admin_login():
return render_template('admin/admin-login.html')
#admin.route('/admin-panel', methods=['POST'])
def admin_panel():
if request.form['username'] == ConfigAdmin.ADMIN_NAME and request.form['password'] == ConfigAdmin.ADMIN_PASS:
return render_template('admin/admin-panel.html')
else:
return redirect(url_for('admin.admin_login'))
#admin.route('/create-post')
def create_post():
return render_template('admin/create-post.html')
#admin.route('/add-post', methods=['POST'])
def add_post():
if request.method == 'POST':
body = Post(post_title=request.form['title'], post_text=request.form['article'], post_img=redirect.form['file'])
db.session.add(body)
db.session.commit()
return redirect(url_for('index'))
else:
return "Err"
<module models.py>
from main import db
class Admin(db.Model):
id = db.Column(db.Integer, primary_key=True)
name = db.Column(db.String(20), unique=True)
passw = db.Column(db.String(20), unique=True)
class Post(db.Model):
id = db.Column(db.Integer, primary_key=True)
title = db.Column(db.String(50), unique=True)
text = db.Column(db.String(500), unique=True)
img = db.Column(db.String(50))
[error][1]
[structure][2]
[1]: https://i.stack.imgur.com/cgrbH.png
[2]: https://i.stack.imgur.com/fDr7O.png
Have you tried creating the following app? Flask Tutorial App - Flaskr blog
I highly recommend following this structure if you're starting out.
looks as follows:
/home/user/Projects/flask-tutorial
├── flaskr/
│ ├── __init__.py
│ ├── db.py
│ ├── schema.sql
│ ├── auth.py
│ ├── blog.py
│ ├── templates/
│ │ ├── base.html
│ │ ├── auth/
│ │ │ ├── login.html
│ │ │ └── register.html
│ │ └── blog/
│ │ ├── create.html
│ │ ├── index.html
│ │ └── update.html
│ └── static/
│ └── style.css
├── tests/
│ ├── conftest.py
│ ├── data.sql
│ ├── test_factory.py
│ ├── test_db.py
│ ├── test_auth.py
│ └── test_blog.py
├── venv/
├── setup.py
└── MANIFEST.in
If you would like it to function in your current app I suggest you create a admin.py inside the same folder as your main.py
from flask import Blueprint, redirect, render_template, request, url_for
from config import ConfigAdmin
from models import Post
bp = Blueprint('admin', __name__, template_folder='templates', static_folder='static')
then import it in main.py as follows
from admin import bp as adminbp
app.register_blueprint(adminbp, url_prefix='/admin')

Python ModuleNotFoundError. Probably a simple mistake

I am trying to setup up some test cases using pytest for a project i'm working on and have setup my directory like so.
C:.
│ OpenGLTestCase.py
│ Sprite.py
│ SpriteManager.py
│ SpriteRenderer.py
│ Texture.py
│ __init__.py
│
├───.pytest_cache
│ │ .gitignore
│ │ CACHEDIR.TAG
│ │ README.md
│ │
│ └───v
│ └───cache
│ lastfailed
│ nodeids
│ stepwise
│
├───tests
│ │ colorGrid.png
│ │ OpenGLTestCaseExample.py
│ │ OpenGLTestCaseExample2.py
│ │ test.png
│ │ test.svg
│ │ test2.png
│ │ test3.png
│ │ test_over_colorGrid_at_128left_256_top.png
│ │ test_over_uvGrid_at_128left_256_top.png
│ │ test_render_image_expected.png
│ │ test_render_triangle_expected.png
│ │ test_sprite_manager.py
│ │ test_Texture.py
│ │ uvGrid.png
│ │
│ └───__pycache__
│ test_sprite_manager.cpython-37-pytest-5.0.0.pyc
│ test_sprite_manager.cpython-37-PYTEST.pyc
│ test_Texture.cpython-37-pytest-5.0.0.pyc
│ test_Texture.cpython-37-PYTEST.pyc
│
└───__pycache__
OpenGLTestCase.cpython-37.pyc
Sprite.cpython-37.pyc
SpriteManager.cpython-37.pyc
SpriteRenderer.cpython-37.pyc
Texture.cpython-37.pyc
__init__.cpython-37.pyc
The parent folder that holds all of this is called "pygameOpenGLUtil". I have my main 4 files in the highest directory along with my __init__.py. When I try and run pytest at this level it says throws a "ModuleNotFoundError: No module named 'pygameOpenGLUtil'". This thrown in my test_sprite_manager.py file. I've gotten this to work in other projects before but I can't seem to figure out what is wrong with this one I am sure i'm just forgetting something small.
Here is my __init__.py:
from .OpenGLTestCase import *
from .Sprite import *
from .SpriteManager import *
from .SpriteRenderer import *
from .Texture import *
And here is my test_sprite_manager.py:
import pygame
from OpenGL.GL import *
from pygameOpenGLUtil import *
class SpriteManagerTest(OpenGLTestCase):
def test_add_sprite(self):
test_sprite_map = SpriteManager()
test_sprite_one = Sprite(test_sprite_map)
test_sprite_one = Sprite(test_sprite_map)
if __name__ == "__main__":
unittest.main()
I am running python3.7.3 and pytest version 5.0.0

Cannot find `glutin` in `glium` when using Conrod

I am attempting to add a GUI to a small project of mine using Conrod. I have managed to work my way down to 3 compilation errors:
error[E0433]: failed to resolve. Could not find `glutin` in `glium`
--> src/support/mod.rs:88:53
|
88 | pub fn next(&mut self, events_loop: &mut glium::glutin::EventsLoop) -> Vec<glium::glutin::Event> {
| ^^^^^^ Could not find `glutin` in `glium`
error[E0433]: failed to resolve. Could not find `glutin` in `glium`
--> src/support/mod.rs:88:87
|
88 | pub fn next(&mut self, events_loop: &mut glium::glutin::EventsLoop) -> Vec<glium::glutin::Event> {
| ^^^^^^ Could not find `glutin` in `glium`
error[E0433]: failed to resolve. Could not find `glutin` in `glium`
--> src/support/mod.rs:106:24
|
106 | glium::glutin::ControlFlow::Break
| ^^^^^^ Could not find `glutin` in `glium`
I've studied the examples that ship with Conrod (particularly the text_edit.rs example) and have successfully compiled and run them. As far as I can tell, they use the same techniques (as my code is directly inspired by their examples), yet does not suffer from the unresolved imports of glutin.
Furthermore, I cannot seem to find any reference to glutin in the project directory itself:
$> pwd
~/dev/conrod/src
$> tree.
.
├── backend
│ ├── gfx.rs
│ ├── glium.rs
│ ├── mod.rs
│ ├── piston
│ │ ├── draw.rs
│ │ ├── event.rs
│ │ └── mod.rs
│ └── winit.rs
├── border.rs
├── color.rs
├── cursor.rs
├── event.rs
├── graph
│ ├── algo.rs
│ ├── depth_order.rs
│ └── mod.rs
├── guide
│ ├── chapter_1.rs
│ ├── chapter_2.rs
│ └── mod.rs
├── image.rs
├── input
│ ├── global.rs
│ ├── mod.rs
│ ├── state.rs
│ └── widget.rs
├── label.rs
├── lib.rs
├── position
│ ├── matrix.rs
│ ├── mod.rs
│ ├── range.rs
│ └── rect.rs
├── render.rs
├── tests
│ ├── global_input.rs
│ ├── mod.rs
│ ├── ui.rs
│ └── widget_input.rs
├── text.rs
├── theme.rs
├── ui.rs
├── utils.rs
└── widget
├── bordered_rectangle.rs
├── builder.rs
├── button.rs
├── canvas.rs
├── collapsible_area.rs
├── drop_down_list.rs
├── envelope_editor.rs
├── file_navigator
│ ├── directory_view.rs
│ └── mod.rs
├── graph
│ ├── mod.rs
│ └── node.rs
├── grid.rs
├── id.rs
├── list.rs
├── list_select.rs
├── matrix.rs
├── mod.rs
├── number_dialer.rs
├── plot_path.rs
├── primitive
│ ├── image.rs
│ ├── line.rs
│ ├── mod.rs
│ ├── point_path.rs
│ ├── shape
│ │ ├── circle.rs
│ │ ├── mod.rs
│ │ ├── oval.rs
│ │ ├── polygon.rs
│ │ ├── rectangle.rs
│ │ └── triangles.rs
│ └── text.rs
├── range_slider.rs
├── rounded_rectangle.rs
├── scrollbar.rs
├── scroll.rs
├── slider.rs
├── tabs.rs
├── text_box.rs
├── text_edit.rs
├── title_bar.rs
├── toggle.rs
└── xy_pad.rs
For reference, my Cargo.toml also includes glutin as a dependency:
[features]
default = ["winit", "glium"]
winit = ["conrod/winit"]
glium = ["conrod/glium"]
[dependencies]
conrod = "^0.57"
find_folder = "*"
glutin = "*"
I believe this is a misconception about the module structure of conrod and glium.
The conrod crate has a number of backend modules, containing utility functions for each of the different backends. conrod::backend::glium is this module for glium, and it contains structures and things useful for using conrod with glium.
In your case, however, I think you mistook this module for glium itself.
glium is a separate crate from conrod, and you'll need to depend on it much like you depend on glutin. glium does indeed have a glium::conrod property, so if you do pull it in with extern crate glium; rather than using conrod::backend::glium, it should "just work"!
You'll need to add some line glium = 0.x in your Cargo.toml as well, but that should be trivial.

Resources