SQL database not showing enteries - python

Im trying to develop a simple blog app. With base that for now only has user_name field and text (besedilo). After i run it it shows no errors. But data is not stored in database and does not display later on.
app.py
from flask import Flask, render_template, request
from flask_mysqldb import MySQL
import yaml
from flask_bootstrap import Bootstrap
app=Flask(__name__)
bootstrap = Bootstrap(app)
db = yaml.load(open('db.yaml'))
app.config['MYSQL_HOST'] = db['mysql_host']
app.config['MYSQL_USER'] = db['mysql_user']
app.config['MYSQL_PASSWORD'] = db['mysql_password']
app.config['MYSQL_DB'] = db['mysql_db']
mysql = MySQL(app)
#app.route('/', methods=['GET','POST'])
def index():
if request.method == 'POST':
form = request.form
user_name = form['user_name']
besedilo = form['besedilo']
cur = mysql.connect.cursor()
cur.execute("INSERT INTO post(user_name, besedilo) VALUES(%s, %s)", (user_name, besedilo))
mysql.connection.commit()
return render_template('index.html')
#app.route('/post')
def post():
cur = mysql.connection.cursor()
result_value = cur.execute("SELECT * FROM post")
if result_value > 0:
post = cur.fetchall()
return render_template('post.html', post=post)
if __name__ == '__main__':
app.run(debug=True)
index.html
{% extends 'base.html' %}
{% block content %}
<h1>Hello</h1>
<form method="post">
NAME:<input type="name" name="user_name">
BESEDILO:<input type="text" name="besedilo">
<input type="submit">
</form>
{% endblock %}
</body>
</html>
post.html
{% extends 'base.html' %}
{% block sub_content %}
<table border = 1>
{% for post in posts %}
<tr>
<td>{{post.user_name}}</td>
<td>{{post.besedilo}}</td>
</tr>
{% endfor %}
</table>
{% endblock %}
db.yaml
mysql_host: 'localhost'
mysql_user: 'root'
mysql_password: 'xxxxxxxx'
mysql_db: 'my_blog'
What have i missed. I have installed all packages, field names are matching.
Database that i set up (with the following commands):
CREATE DATABASE my_blog;
CREATE TABLE post(user_name varchar(30), besedilo varchar(150));
and inserts for fine: with
INSERT INTO post(user_name, besedilo) VALUES ('Alex', 'i have a job to do');
mysql> SELECT * FROM post;
+-----------+----------------+
| user_name | besedilo |
+-----------+----------------+
| Peter | some text |
| Alex | i have a job |
+-----------+----------------+
1.) UPDATE :
#app.route('/', methods=['GET','POST'])
def index():
if request.method == 'POST':
form = request.form
user_name = form['user_name']
besedilo = form['besedilo']
conn = mysql.connect()
cur = conn.cursor()
cur.execute("INSERT INTO post(user_name, besedilo) VALUES(%s, %s)", (user_name, besedilo))
conn.commit()
return render_template('index.html')

I have strong suspicion that culprit is if result_value>0.
I suppose it's always returns 0 for SELECT * FROM post not matter if rows exists in table.
Excerpts from MySQL Documentation:
The use of mysql_num_rows() depends on whether you use mysql_store_result() or mysql_use_result() to return the result set. If you use mysql_store_result(), mysql_num_rows() may be called immediately. If you use mysql_use_result(), mysql_num_rows() does not return the correct value until all the rows in the result set have been retrieved.
Try to exclude your result_value check and see results:
#app.route('/post')
def post():
cur = mysql.connection.cursor()
cur.execute("SELECT * FROM post")
# if result_value > 0: ## I suppose that line always returns 0
post = cur.fetchall()
return render_template('post.html', post=post)
As for def index() - I'm not sure there is a problem there.
Inform about your progress.

Related

Display username in base.html in Flask

I want to add current username in base.html, but I can't understand how make it.
I have got username, which takes from MySQL database
#app/routes
#app.route('/auth', methods=['GET', 'POST'])
def auth():
msg = ''
if request.method == 'POST' and 'username' in request.form and 'password' in request.form:
username = request.form['username']
hash = request.form['password']
salt = b'$2b$12$Mw/92Q0HkYKTR.0.ghNQs.'
password = bytes(hash, encoding='utf-8')
hash_1 = bcrypt.hashpw(password,salt)
cursor = mysql.connection.cursor(MySQLdb.cursors.DictCursor)
cursor.execute('SELECT * FROM user WHERE username = % s AND password = % s', (username, hash_1,))
account = cursor.fetchone()
if account:
session['loggedin'] = True
session['id'] = account['id']
session['username'] = account['username']
msg = 'Logged in successfully !'
return render_template('index.html', msg=msg)
else:
msg = 'Неверное имя пользователя/пароль !'
return render_template('auth.html', msg=msg)
How can I take the username field and get it to the base.html, when user is Loggined in? I tryed to make it with using documentation, but it doesn`t work.
#base.html
{% if g.username %}
<li><span>{{ g.user['username'] }}</span>
{% else %}
<a class="p-2 text-dark" href="/auth">Авторизация</a>
{% endif %}
I make it
{% if session.loggedin %}
<a class="p-2 text-dark" href="/auth">Привет,{{session.username}} </a>
{% else %}
<a class="p-2 text-dark" href="/auth">Авторизация</a>

variable is undefined flask mysql

I need to greet user on the page. F.ex: Hello {{ name }}, but I get the error UnboundLocalError: local variable 'account' referenced before assignment. What is the problem in the code below?
python:
app = Flask(__name__)
mysql = MySQL(app)
#app.route('/', methods=['GET', 'POST'])
def index():
if request.method == 'POST':
name = request.form['name']
email = request.form['email']
cur = mysql.connection.cursor()
cur.execute('INSERT INTO users(name, email) VALUES(%s, %s)', (name, email))
mysql.connection.commit()
cur.close()
return redirect('profile')
return render_template('index.html')
#app.route('/profile', methods=['GET'])
def profile():
if request.method == 'POST':
name = request.form['name']
email = request.form['email']
cur = mysql.connection.cursor()
cur.execute('SELECT * FROM users')
account = cur.fetchone()
return render_template('profile.html', account=account)
index.html:
<form action="" method="POST">
<span style="color: #fff;">Firstname:</span><input type="text" name="name" placeholder="Type your firstname"><br><br>
<input type="submit" name="submit" value="submit">
</form>
profile.html
<h4 style="color: #fff;">Your firstname: is {{ account['name'] }}</h4>
<h4 style="color: #fff;">Your email: is {{ account['email'] }}</h4>
I can connect to database and fetch users data, but on the profile.html page I get the error
How to solve it? Please help.
You haven't passed the account to the template.
Instead of ,
return render_template('profile.html')
you need to write as,
return render_template('profile.html', account=account)
EDIT:
#app.route('/profile', methods=['GET','POST'])
def profile():
if request.method == 'POST':
name = request.form['name']
email = request.form['email']
cur = mysql.connection.cursor()
cur.execute('SELECT * FROM users')
account = cur.fetchone()
return render_template('profile.html', account=account)
Or if you wanted the profile to be a get request you can do this
#app.route('/profile', methods=['GET','POST'])
def profile():
if request.method == 'POST':
name = request.form['name']
email = request.form['email']
cur = mysql.connection.cursor()
cur.execute('SELECT * FROM users')
account = cur.fetchone()
return render_template('profile.html', account=account)

How to avoid the below error in Python Flask

I am using the below 3 html i.e. Index.html , Results.html and Edit.html
and python code file app.py code is also pasted below.
The save to the DB is working fine and when I retrieve the data for editing and click on Submit I am encountering the below error
"_mysql_exceptions.ProgrammingError: (1064, "You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '%s' at line 1")"
Index.html
<h1>Welcome</h1>
<br>
<br>
<form method="POST" action="{{ url_for('index') }}">
Name <input type="text" name="name" />
<br>
Email <input type="email" name="email" />
<br>
CRType <select name = "CRType">
<option value = "New">New</option>
<option value = "Old">Old</option>
</select><br>
<input type="submit" value="Submit">
</form>
Results.html
Add CR
<table border = 1>
{% for user in userDetails %}
<tr>
<td> {{user[3]}} </td>
<td> {{user[0]}} </td>
<td> {{user[1]}} </td>
<td> {{user[2]}} </td>
<td> Edit Profile </td>
</tr>
{% endfor %}
</table>
Edit.html
h1>Welcome to Update Zone</h1>
<br>
<br>
<body>
<form method="POST" action="{{ url_for('Edit') }}">
CR_ID <input type="text" name="CR_ID" value = "{{user[0]}}"/>
<br>
Name <input type="text" name="name" value = "{{user[1]}}"/>
<br>
Email <input type="email" name="email" value = "{{user[2]}}"/>
<br>
<br>
<input type="submit" value="Submit">
</body>
</form>
App.PY
from flask import Flask, render_template, request, redirect
from flask_mysqldb import MySQL
# from flask_table import Table, Col, LinkCol
app = Flask(__name__)
# Configure db
#db = yaml.load(open('db.yaml'))
app.config['MYSQL_HOST'] = 'localhost'
app.config['MYSQL_USER'] = 'root'
#app.config['MYSQL_PASSWORD'] = 'P#$$w0rd'
app.config['MYSQL_DB'] = 'flaskapp'
mysql = MySQL(app)
#app.route('/', methods=['GET', 'POST'])
def index():
if request.method == 'POST':
# Fetch form data
userDetails = request.form
name = userDetails['name']
email = userDetails['email']
CRType = userDetails['CRType']
# CR_ID = userDetails['CR_ID']
cur = mysql.connection.cursor()
# cur.execute("""INSERT INTO users(name, email, CRType) VALUES(%s, %s, % )""",(name, email, CRType)
cur.execute("""INSERT INTO users (name, email, CRType) VALUES (%s, %s, %s)""", (name, email, CRType))
mysql.connection.commit()
cur.close()
return redirect ('/results')
# return redirect('/results')
return render_template('index.html')
#app.route('/results')
def results():
cur = mysql.connection.cursor()
resultValue = cur.execute("SELECT * from users")
if resultValue > 0:
userDetails = cur.fetchall()
# edit = LinkCol('Edit', 'edit', url_kwargs=dict(id='CR_ID'))
return render_template('results.html',userDetails=userDetails)
#app.route('/Edit', methods=['GET', 'POST'])
def Edit():
# request.method == 'GET':
# Fetch form data
# user = request.form
# CR_ID = user['CR_ID']
CR_ID = request.args.get('CR_ID')
name = request.args.get('name')
email = request.args.get('email')
CRType = request.args.get('CRType')
cur = mysql.connection.cursor()
# result= cur.execute("SELECT CR_ID, name, email from users where CR_ID = 1")
result = cur.execute("""SELECT CR_ID, name, email from users where CR_ID = %s""",CR_ID)
# result = cur.execute("Update table users set name=?, email=?, CRType=? where CR_ID = %s", CR_ID)
RV = cur.fetchall()
user = RV[0]
cur.close()
return render_template('Edit.html',user=user)
if __name__ == '__main__':
app.run(debug= True)
Your SQL statements aren't properly formatted. It should be
result = cur.execute("SELECT CR_ID, name, email from users where CR_ID = %s", (CR_ID))

Creating an events manager using Flask and MySQL

I'm a novice Python and Javascript programmer and am currently working on creating an events manager app using Flask and MySQL.
The one page website should allow users to:
Add and view events.
Sort events by date or by category
I can't seem to insert data into my local MySQL database. Each time I open the MySQL workbench to check, the table remains empty.
My questions are:
How do I insert the data from the input tags into MySQL using Flask?
What is the best method to check MySQL if the insertion was successful?
How do I get data from MySQL into the HTML table using Flask on app startup?
The HTML:
<!DOCTYPE html>
<head>
<meta charset="UTF-8">
<link rel = 'stylesheet' href = 'https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css'>
<title>Events and Opportunities</title>
</head>
<body>
<div class = 'container'>
<h1>Events and Opportunities</h1>
<table class="table">
<thead>
<tr id = 'tableHeader'>
<th>Date</th>
<th>Category</th>
<th>Title</th>
<th>Description</th>
</tr>
</thead>
<tbody>
<form action = '/' method = 'post'>
<tr id = 'tableInput'>
<td><input type = 'date' name = 'inputDate' id = 'inputDate'></td>
<td><input type = 'text' name = 'inputCategory' id = 'inputCategory' maxlength = '20'></td>
<td><input type = 'text' name = 'inputTitle' id = 'inputTitle' maxlength = '100'></td>
<td><input type = 'text' name = 'inputDescription' id = 'inputDescription' maxlength = '500'></td>
</tr>
</form>
</tbody>
</table>
<button type = 'button' id = 'addButton' class="btn btn-default">Add</button>
</div>
<script src = 'https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js'></script>
<script
src="https://code.jquery.com/jquery-3.2.1.min.js"
integrity="sha256-hwg4gsxgFZhOsEEamdOYGBf13FyQuiTwlAQgxVSNgt4="
crossorigin="anonymous">
</script>
<script src = 'static/app.js'></script>
</body>
</html>
The Javascript:
$('#addButton').on('click', () => {
if ($('#inputDate').val() === '' || $('#inputCategory') === '' || $('#inputTitle') === '' || $('#inputDescription') === ''){
alert('Please fill in the form.');
}
else{
const valDate = $('<th></th>').text($('#inputDate').val());
const valCategory = $('<th></th>').text($('#inputCategory').val());
const valTitle = $('<th></th>').text($('#inputTitle').val());
const valDescription = $('<th></th>').text($('#inputDescription').val());
const newRow = $('<tr></tr>').append(valDate, valCategory, valTitle, valDescription);
$('#tableInput').before(newRow);
$('#inputDate').val('');
$('#inputCategory').val('');
$('#inputTitle').val('');
$('#inputDescription').val('');
}
})
The Flask code:
from flask import Flask, render_template, request
import mysql.connector
app = Flask(__name__)
cnx = mysql.connector.connect(user='root', password='yunani', host='127.0.0.1', database='test')
cursor = cnx.cursor()
#app.route('/', methods = ['GET', 'POST'])
def index():
return render_template('index.html')
if request.method == 'POST':
date = request.form['inputDate']
category = request.form['inputCategory']
title = request.form['inputTitle']
description = request.form['inputDescription']
cursor.execute('INSERT INTO data (Date, Category, Title, Description) VALUES ({}, {}, {}, {})'.format(date, category, title, description))
cnx.commit()
if __name__ == '__main__':
app.run(debug = True)
The MySQL schema:link to image
Try changing your handler to
def index():
if request.method == 'POST':
date = request.form['inputDate']
category = request.form['inputCategory']
title = request.form['inputTitle']
description = request.form['inputDescription']
cursor.execute('INSERT INTO data (Date, Category, Title, Description) VALUES ({}, {}, {}, {})'.format(date, category, title, description))
cnx.commit()
return render_template('index.html') # don't do this at the top
You are currently returning before checking the call type or talking to the database.

how to add time to html from python method

this is part of a flask application. I would like to get the current time to output anywhere in the form of the html file.
I would like to add the method current_time() in flaskr.py to the anywhere in the from in the attached html file. Thanks!
flaskr.py
import os
import sqlite3
from flask import Flask, request, session, g, redirect, url_for, abort, \
render_template, flash
from datetime import date
import time
app = Flask(__name__)
app.config.from_object(__name__)
app.config.update(dict(
DATABASE = os.path.join(app.root_path, 'flaskr.db'), ##in real world apps use instance folders for databases instead
SECRET_KEY = 'development key',
USERNAME = 'admin',
PASSWORD = 'default'
))
app.config.from_envvar('FLASKR_SETTINGS', silent=True)
def connect_db():
rv = sqlite3.connect(app.config['DATABASE'])
rv.row_factory = sqlite3.Row
return rv
def get_db():
if not hasattr(g, 'sqlite_db'):
g.sqlite_db = connect_db()
return g.sqlite_db
#app.teardown_appcontext
def close_db(error):
if hasattr(g, 'sqlite_db'):
g.sqlite_db.close()
def init_db():
db = get_db()
with app.open_resource('schema.sql', mode = 'r') as f:
db.cursor().executescript(f.read())
db.commit()
#app.cli.command('initdb')
def initdb_command():
init_db()
print('initialized the database.')
#app.route('/')
def show_entries():
db = get_db()
cur = db.execute('select title, text from entries order by id desc')
entries = cur.fetchall()
return render_template('show_entries.html', entries=entries)
#app.route('/add', methods=['POST'])
def add_entry():
if not session.get('logged_in'):
abort(401)
db = get_db()
db.execute('insert into entries (title, text) values (?, ?)',
[request.form['title'], request.form['text']])
db.commit()
flash('New entry was successfully posted')
return redirect(url_for('show_entries'))
#app.route('/login', methods=['POST', 'GET'])
def login():
error = None
if request.method == 'POST':
if request.form['username'] != app.config['USERNAME']:
error = 'Invalid username'
elif request.form['password'] != app.config['PASSWORD']:
error = 'Invalid password'
else:
session['logged_in'] = True
flash('You were logged in')
return redirect(url_for('show_entries'))
return render_template('login.html', error = error)
#app.route('/logout')
def logout():
session.pop('logged_in', None)
flash('You were logged out')
return redirect(url_for('show_entries'))
def current_time():
return date.today()
show_entries.html
{% extends "layout.html" %}
{% block body %}
{% if session.logged_in %}
<form action="{{ url_for('add_entry') }}" method=post class=add-entry>
<dl>
<dt>Title:
<dd><input type=text size=30 name=title>
<dt>Text:
<dd><textarea name=text rows=5 cols=40></textarea>
<dd><input type=submit value=Share>
</dl>
</form>
{% endif %}
<ul class=entries>
{% for entry in entries %}
<li><h2>{{ entry.title }}</h2>{{ entry.text|safe }}
{% else %}
<li><em> No entries so far</em>
{% endfor %}
</ul>
{% endblock %}
You can just use datetime.now() method:
from datetime import datetime
...
return render_template(... current_time = datetime.now())
...

Categories

Resources