implement permanent deletion, make user profile migration reversible

This commit is contained in:
Yusur 2025-11-26 16:50:42 +01:00
parent 536e49d1b9
commit 8369035693
7 changed files with 21 additions and 7 deletions

1
.gitignore vendored
View file

@ -18,3 +18,4 @@ config/
node_modules/ node_modules/
alembic.ini alembic.ini
**.egg-info **.egg-info
.vscode

View file

@ -2,9 +2,12 @@
## 0.10.0 ## 0.10.0
+ Codebase refactor (with breaking changes!) + Codebase refactor (with breaking changes!)
+ Dropped support for Python<=3.9
+ Move ALL config to .env (config.py is NO MORE supported) + Move ALL config to .env (config.py is NO MORE supported)
+ Config SITE_NAME replaced with APP_NAME + Config SITE_NAME replaced with APP_NAME
+ Add CSRF token and flask_WTF + Add CSRF token and flask_WTF
+ Schema changes: biography and website moved to `User`; `UserProfile` table deprecated (and useless fields removed)
+ Posts can now be permanently deleted
## 0.9.0 ## 0.9.0

View file

@ -24,7 +24,7 @@ from flask_wtf import CSRFProtect
import dotenv import dotenv
import logging import logging
__version__ = '0.10.0-dev45' __version__ = '0.10.0-dev47'
# we want to support Python 3.10+ only. # we want to support Python 3.10+ only.
# Python 2 has too many caveats. # Python 2 has too many caveats.
@ -63,7 +63,7 @@ def before_request():
try: try:
g.db.connect() g.db.connect()
except OperationalError: except OperationalError:
logger.error('database connected twice.\n') logger.error('database connected twice')
@app.after_request @app.after_request
def after_request(response): def after_request(response):

View file

@ -23,6 +23,8 @@ from . import BASEDIR
database = connect(os.environ['DATABASE_URL']) database = connect(os.environ['DATABASE_URL'])
class BaseModel(Model): class BaseModel(Model):
id = AutoField(primary_key=True)
class Meta: class Meta:
database = database database = database

View file

@ -16,7 +16,7 @@
</ul> </ul>
<form method="POST"> <form method="POST">
<input type="hidden" name="csrf_token" value="{{ csrf_token() }}" /> <input type="hidden" name="csrf_token" value="{{ csrf_token() }}" />
<input type="submit" value="Delete"> <input type="submit" value="Delete">
</form> </form>
</div> </div>

View file

@ -239,12 +239,15 @@ def edit(id):
@bp.route('/delete/<int:id>', methods=['GET', 'POST']) @bp.route('/delete/<int:id>', methods=['GET', 'POST'])
def confirm_delete(id): def confirm_delete(id):
user = get_current_user() user: User = current_user
message = get_object_or_404(Message, Message.id == id) message: Message = get_object_or_404(Message, Message.id == id)
if message.user != user: if message.user != user:
abort(404) abort(404)
if request.method == 'POST': if request.method == 'POST':
abort(501, 'CSRF-Token missing.') if message.user == user:
message.delete_instance()
flash('Your message has been deleted forever')
return redirect(request.args.get('next', '/'))
return render_template('confirm_delete.html', message=message) return render_template('confirm_delete.html', message=message)
# Workaround for problems related to invalid data. # Workaround for problems related to invalid data.

View file

@ -70,6 +70,11 @@ def rollback(migrator: Migrator, database: pw.Database, *, fake=False):
facebook=pw.TextField(null=True), facebook=pw.TextField(null=True),
telegram=pw.TextField(null=True)) telegram=pw.TextField(null=True))
migrator.sql("""
UPDATE "userprofile" SET biography = (SELECT p.biography FROM user p WHERE p.user_id = id LIMIT 1),
website = (SELECT p.website FROM user p WHERE p.user_id = id LIMIT 1);
""")
migrator.remove_fields('user', 'biography', 'website') migrator.remove_fields('user', 'biography', 'website')
migrator.change_fields('user', username=pw.CharField(max_length=255, unique=True)) migrator.change_fields('user', username=pw.CharField(max_length=255, unique=True))