Недавно я попытался развернуть приложение Flask в Heroku, и у меня возникли некоторые проблемы.При локальном тестировании приложения у меня нет проблем с приложением.Все как регистрация пользователя / вход в систему работает отлично, и отправка формы элемента отлично работает.
Однако, когда я захожу в приложение по адресу https://simplify -exp.herokuapp.com При работе возникают странные проблемы.любая задача, связанная с отправкой формы (логин / регистрация пользователя и создание элемента).Когда что-то отправляется, кажется, что веб-страница ничего не делает, но в третий или четвертый раз, когда я нажимаю кнопку отправки, она работает нормально.Форма заявки, кажется, работает только половину времени, и я понятия не имею, почему.Существует просто ошибочное поведение, когда любое из представленных в отношении перенаправления.
Вот пример того, как логин не работает должным образом.Локально работает.
https://streamable.com/ywsj2
Вот пример выхода из системы, когда вы возвращаетесь на страницу входа в систему, когда она должна перейти на главную страницу с кнопками регистрации и входа (один с синим фоном).
https://streamable.com/iblv6
Если вы посетите сайт и используете его в течение нескольких минут, вы увидите проблемы.
Включенониже находится часть кода и логи герои.Буду признателен за любую помощь.
Я попытался повторно развернуть приложение и перезапустил соединение с БД, так как думал, что это была моя первоначальная ошибка.Пробовал погуглить ошибку, но ничего не нашел.
import os
import datetime
from dateutil.parser import parse
from collections import defaultdict, OrderedDict
from flask import Flask, render_template, redirect, url_for, request
from flask_bootstrap import Bootstrap
from flask_wtf import FlaskForm
from wtforms import StringField, PasswordField, BooleanField
from wtforms.validators import InputRequired, Email, Length
from flask_sqlalchemy import SQLAlchemy
from werkzeug.security import generate_password_hash, check_password_hash
from flask_login import LoginManager, UserMixin, login_user, login_required, logout_user, current_user
from flask_migrate import Migrate
from flask_heroku import Heroku
app = Flask(__name__)
app.config['SECRET_KEY'] = os.urandom(32)
# app.config['SQLALCHEMY_DATABASE_URI'] = 'postgres://localhost/simplify'
bootstrap = Bootstrap(app)
heroku = Heroku(app)
db = SQLAlchemy(app)
migrate = Migrate(app, db)
login_manager = LoginManager()
login_manager.init_app(app)
login_manager.login_view = 'login'
class User(UserMixin, db.Model):
id = db.Column(db.Integer, primary_key=True)
username = db.Column(db.String(15), unique=True)
password = db.Column(db.String(100))
items = db.relationship('Item', backref='user', lazy='dynamic')
def __repr__(self):
return "ID: {}, Username: {}, Items: {}".format(self.id,self.username,self.items)
class Item(db.Model):
id = db.Column(db.Integer, unique=True, nullable=False, primary_key=True, autoincrement=True)
date = db.Column(db.DateTime)
name = db.Column(db.String(80))
price = db.Column(db.Float)
category = db.Column(db.String(80))
user_id = db.Column(db.Integer, db.ForeignKey('user.id'))
def __repr__(self):
return "ID: {}, Date: {}, Name: {}, Price: {}, Category: {}, User_id: {}".format(self.id,self.date,self.name,self.price,self.category,self.user_id)
@login_manager.user_loader
def load_user(user_id):
return User.query.get(int(user_id))
class LoginForm(FlaskForm):
username = StringField('username', validators=[InputRequired(), Length(min=1, max=15)])
password = PasswordField('password', validators=[InputRequired(), Length(min=1, max=80)])
remember = BooleanField('remember me')
class RegisterForm(FlaskForm):
username = StringField('username', validators=[InputRequired(), Length(min=1, max=15)])
password = PasswordField('password', validators=[InputRequired(), Length(min=1, max=80)])
@app.route('/')
def index():
return render_template('index.html')
@app.route('/login', methods=['GET', 'POST'])
def login():
form = LoginForm()
if form.validate_on_submit():
user = User.query.filter_by(username=form.username.data).first()
if user:
if check_password_hash(user.password, form.password.data):
login_user(user, remember=form.remember.data)
return redirect(url_for('dashboard'))
return '<h1>Invalid username or password</h1>'
return render_template('login.html', form=form)
@app.route('/signup', methods=['GET', 'POST'])
def signup():
form = RegisterForm()
if form.validate_on_submit():
hashed_password = generate_password_hash(form.password.data)
new_user = User(username=form.username.data, password=hashed_password)
db.session.add(new_user)
db.session.commit()
login_user(new_user)
return redirect(url_for('dashboard'))
return render_template('signup.html', form=form)
@app.route('/dashboard', methods=['GET', 'POST'])
@login_required
def dashboard():
add_item()
items = query_and_format_items()
categories,c_spending = get_category_spending(items)
months, m_spending = get_monthly_spending(items)
past_month_total_spending, past_month_categories, past_month_spending = get_past_30_days_spending(items)
return render_template('dashboard.html', items=items[:10], categories=categories, c_spending=c_spending, months=months, m_spending=m_spending, past_month_total_spending=past_month_total_spending, past_month_categories=past_month_categories, past_month_spending=past_month_spending)
@app.route('/history/', endpoint='history', methods=['GET', 'POST'])
@login_required
def history():
add_item()
items = query_and_format_items()
return render_template('history.html', items=items)
@app.route('/delete/<int:id>', methods=['POST'])
def remove(id):
item = current_user.items.filter(Item.id == id)
item.delete()
db.session.commit()
return redirect(url_for('history'))
# Adds item into db
def add_item():
if request.form:
item = Item(date=parse(request.form.get('date')), name=request.form.get('item_name'),price=request.form.get('price'),category=request.form.get('category').capitalize(),user_id=current_user.username,user=current_user)
db.session.add(item)
db.session.commit()
# Formats the date of all items
def query_and_format_items():
items = current_user.items.all()[::-1]
items.sort(key=lambda x: x.date, reverse=True)
for item in items:
item.date = item.date.strftime('%m-%d-%y')
return items
def get_category_spending(items):
category_amount = defaultdict(int)
for item in items:
category_amount[item.category] += item.price
return list(category_amount.keys()), list(category_amount.values())
def get_monthly_spending(items):
monthly_amount = OrderedDict()
for item in reversed(items):
item_date = get_month_year(item)
if item_date in monthly_amount:
monthly_amount[item_date] += item.price
else:
monthly_amount[item_date] = item.price
return list(monthly_amount.keys()), list(monthly_amount.values())
def get_month_year(item):
return item.date[:2] + '-' + item.date[6:]
def get_past_30_days_spending(items):
total_spending = 0
category_amount = defaultdict(int)
for item in items:
date_range = datetime.datetime.now() - parse(item.date)
if date_range.days <= 30:
category_amount[item.category] += item.price
total_spending += item.price
return total_spending, list(category_amount.keys()), list(category_amount.values())
@app.route('/logout')
@login_required
def logout():
logout_user()
return redirect(url_for('index'))
if __name__ == '__main__':
app.run(debug=True)
Это логи heroku, когда я пытаюсь отправить форму либо при входе / регистрации пользователя, либо во время создания предмета.
019-06-23T20:48:34.666717+00:00 app[web.1]: 10.5.168.154 - - [23/Jun/2019:20:48:34 +0000] "POST /signup HTTP/1.1" 302 227 "https://simplify-exp.herokuapp.com/signup" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.157 Safari/537.36"
2019-06-23T20:48:34.666688+00:00 heroku[router]: at=info method=POST path="/signup" host=simplify-exp.herokuapp.com request_id=7f74da1c-4dc4-4034-9126-f59781f0258c fwd="96.255.28.103" dyno=web.1 connect=0ms service=301ms status=302 bytes=760 protocol=https
2019-06-23T20:48:34.833489+00:00 heroku[router]: at=info method=GET path="/dashboard" host=simplify-exp.herokuapp.com request_id=43955edb-f83c-4982-a2da-af9cea9a071c fwd="96.255.28.103" dyno=web.1 connect=0ms service=41ms status=200 bytes=7610 protocol=https
2019-06-23T20:48:34.833497+00:00 app[web.1]: 10.5.168.154 - - [23/Jun/2019:20:48:34 +0000] "GET /dashboard HTTP/1.1" 200 7434 "https://simplify-exp.herokuapp.com/signup" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.157 Safari/537.36"
2019-06-23T20:48:34.889270+00:00 app[web.1]: 10.5.168.154 - - [23/Jun/2019:20:48:34 +0000] "GET /static/dashboard.css HTTP/1.1" 200 0 "https://simplify-exp.herokuapp.com/dashboard" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.157 Safari/537.36"
2019-06-23T20:48:34.941411+00:00 app[web.1]: 10.5.168.154 - - [23/Jun/2019:20:48:34 +0000] "GET /resources/demos/style.css HTTP/1.1" 404 232 "https://simplify-exp.herokuapp.com/dashboard" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.157 Safari/537.36"
2019-06-23T20:48:34.889105+00:00 heroku[router]: at=info method=GET path="/static/dashboard.css" host=simplify-exp.herokuapp.com request_id=f5c6337e-6785-480a-968a-f6b4c1680ffd fwd="96.255.28.103" dyno=web.1 connect=1ms service=3ms status=200 bytes=2282 protocol=https
2019-06-23T20:48:34.940746+00:00 heroku[router]: at=info method=GET path="/resources/demos/style.css" host=simplify-exp.herokuapp.com request_id=7d0454ca-d38d-4b44-8de9-152c14496ed5 fwd="96.255.28.103" dyno=web.1 connect=1ms service=28ms status=404 bytes=385 protocol=https
2019-06-23T20:48:36.137821+00:00 heroku[router]: at=info method=GET path="/favicon.ico" host=simplify-exp.herokuapp.com request_id=5c917639-4275-4269-b254-4d64e47a3eda fwd="96.255.28.103" dyno=web.1 connect=0ms service=13ms status=404 bytes=385 protocol=https
2019-06-23T20:48:36.138430+00:00 app[web.1]: 10.5.168.154 - - [23/Jun/2019:20:48:36 +0000] "GET /favicon.ico HTTP/1.1" 404 232 "https://simplify-exp.herokuapp.com/dashboard" "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_3) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.157 Safari/537.36"