diasporadiaries

a platform for writing stories with personal accounts and messages
git clone git://parazyd.org/diasporadiaries.git
Log | Files | Refs | Submodules | README | LICENSE

commit dc1b890a31f16aa9f0f39bb86617b24d7c86a097
parent 185a8f6034df215ef63199a8e5d7f9306214aba6
Author: parazyd <parazyd@dyne.org>
Date:   Sat, 26 Jan 2019 02:01:21 +0100

Implement wishful semaphore safety.

Diffstat:
Mconfig.py | 5+++++
Mdb.py | 9+++++++--
Mutils.py | 15+++++++++++++++
3 files changed, 27 insertions(+), 2 deletions(-)

diff --git a/config.py b/config.py @@ -17,9 +17,14 @@ """ Configuration file """ +from threading import BoundedSemaphore # The secret key for flask-login. SECRET_KEY = 'super-secret' # Path to the sqlite database. DB_PATH = './stories.db' + +# Set a BoundedSemaphore to 1. Since sqlite can't do async writes, we have to +# control it with something. +sem = BoundedSemaphore(1) diff --git a/db.py b/db.py @@ -19,7 +19,7 @@ Module for sqlite database operations. """ from sqlite3 import connect -from config import DB_PATH +from config import DB_PATH, sem def initdb(dbpath): @@ -90,12 +90,14 @@ def sql_delete_row_where(col, val, table='stories'): """ Executes a DELETE query where col=val. """ + sem.acquire() DB.execute(""" DELETE FROM %s WHERE %s = '%s'; """ % (table, col, val)) DBCTX.commit() + sem.release() def sql_update_row_where(vals, col, val, table='stories'): @@ -104,6 +106,7 @@ def sql_update_row_where(vals, col, val, table='stories'): vals is a list of tuples. """ + sem.acquire() for i in vals: DB.execute(""" UPDATE %s @@ -111,6 +114,7 @@ def sql_update_row_where(vals, col, val, table='stories'): WHERE %s = ?; """ % (table, i[0], col), (i[1], val)) DBCTX.commit() + sem.release() def sql_insert(args): @@ -118,6 +122,7 @@ def sql_insert(args): Executes an sql INSERT query where args are VALUES to insert. """ # TODO: Make this more generic. + sem.acquire() if len(args) == 11: # Story DB.execute(""" @@ -134,5 +139,5 @@ def sql_insert(args): ); """, (args[0], args[1], args[2], args[3], args[4], args[5], args[6])) - DBCTX.commit() + sem.release() diff --git a/utils.py b/utils.py @@ -29,6 +29,7 @@ from time import gmtime, strftime, time from bcrypt import gensalt, hashpw from flask import Markup +from config import sem from db import (sql_select_col_where, sql_select_col, sql_insert, sql_delete_row_where) @@ -312,8 +313,10 @@ def get_messages(user_id, id_from): i['unread'] = 0 messages.append(i) + sem.acquire() with open(msgpath, 'w') as msgfile: json.dump(messages, msgfile) + sem.release() return messages @@ -348,9 +351,11 @@ def send_message(id_to, msg, id_us): with open(our_msgpath) as ourmsgs: ourdata = json.load(ourmsgs) + sem.acquire() ourdata.append(msgdict) with open(our_msgpath, 'w') as ourmsgs: json.dump(ourdata, ourmsgs) + sem.release() if our_msgpath == their_msgpath: return @@ -359,9 +364,11 @@ def send_message(id_to, msg, id_us): with open(their_msgpath) as theirmsgs: theirdata = json.load(theirmsgs) + sem.acquire() theirdata.append(msgdict) with open(their_msgpath, 'w') as theirmsgs: json.dump(theirdata, theirmsgs) + sem.release() def send_shout(id_to, msg, id_us): @@ -394,9 +401,11 @@ def send_shout(id_to, msg, id_us): with open(shoutpath) as shouts_file: theirdata = json.load(shouts_file) + sem.acquire() theirdata.append(msgdict) with open(shoutpath, 'w') as shouts_file: json.dump(theirdata, shouts_file) + sem.release() def delete_shout(id_to, id_shout): @@ -418,8 +427,10 @@ def delete_shout(id_to, id_shout): if i['id'] == id_shout: shouts.remove(i) + sem.acquire() with open(shoutpath, 'w') as shouts_file: json.dump(shouts, shouts_file) + sem.release() def get_shouts(email): @@ -451,9 +462,11 @@ def follow_user(id_us, id_them): with open(our_follow) as follow_file: ourdata = json.load(follow_file) + sem.acquire() ourdata.append(them['email']) with open(our_follow, 'w') as follow_file: json.dump(ourdata, follow_file) + sem.release() def unfollow_user(id_us, id_them): @@ -475,8 +488,10 @@ def unfollow_user(id_us, id_them): while them['email'] in ourdata: ourdata.remove(them['email']) + sem.acquire() with open(our_follow, 'w') as follow_file: json.dump(ourdata, follow_file) + sem.release() def is_following(email_ours, email_them):