fix(security): sanitize DB field formatting and fix cron job duplication
This commit is contained in:
16
SubMind.py
16
SubMind.py
@@ -126,6 +126,8 @@ def init_db():
|
|||||||
cursor.execute("ALTER TABLE subscriptions ADD COLUMN reminder_on_due_date BOOLEAN DEFAULT TRUE")
|
cursor.execute("ALTER TABLE subscriptions ADD COLUMN reminder_on_due_date BOOLEAN DEFAULT TRUE")
|
||||||
if 'notes' not in columns:
|
if 'notes' not in columns:
|
||||||
cursor.execute("ALTER TABLE subscriptions ADD COLUMN notes TEXT")
|
cursor.execute("ALTER TABLE subscriptions ADD COLUMN notes TEXT")
|
||||||
|
if 'last_reminded_date' not in columns:
|
||||||
|
cursor.execute("ALTER TABLE subscriptions ADD COLUMN last_reminded_date DATE")
|
||||||
|
|
||||||
cursor.execute('''
|
cursor.execute('''
|
||||||
CREATE TABLE IF NOT EXISTS categories (
|
CREATE TABLE IF NOT EXISTS categories (
|
||||||
@@ -346,9 +348,11 @@ def update_past_due_dates():
|
|||||||
async def check_and_send_reminders(context: CallbackContext):
|
async def check_and_send_reminders(context: CallbackContext):
|
||||||
logger.info("Running job: Checking for subscription reminders...")
|
logger.info("Running job: Checking for subscription reminders...")
|
||||||
today = datetime.date.today()
|
today = datetime.date.today()
|
||||||
|
today_str = today.strftime('%Y-%m-%d')
|
||||||
with get_db_connection() as conn:
|
with get_db_connection() as conn:
|
||||||
cursor = conn.cursor()
|
cursor = conn.cursor()
|
||||||
cursor.execute("SELECT * FROM subscriptions WHERE reminders_enabled = TRUE AND next_due IS NOT NULL")
|
# 过滤掉今天已经提醒过的订阅
|
||||||
|
cursor.execute("SELECT * FROM subscriptions WHERE reminders_enabled = TRUE AND next_due IS NOT NULL AND (last_reminded_date IS NULL OR last_reminded_date != ?)", (today_str,))
|
||||||
subs_to_check = cursor.fetchall()
|
subs_to_check = cursor.fetchall()
|
||||||
|
|
||||||
for sub in subs_to_check:
|
for sub in subs_to_check:
|
||||||
@@ -388,11 +392,15 @@ async def check_and_send_reminders(context: CallbackContext):
|
|||||||
parse_mode='MarkdownV2',
|
parse_mode='MarkdownV2',
|
||||||
reply_markup=keyboard
|
reply_markup=keyboard
|
||||||
)
|
)
|
||||||
|
# 记录今天已发送提醒
|
||||||
|
with get_db_connection() as update_conn:
|
||||||
|
update_cursor = update_conn.cursor()
|
||||||
|
update_cursor.execute("UPDATE subscriptions SET last_reminded_date = ? WHERE id = ?", (today_str, sub['id']))
|
||||||
|
update_conn.commit()
|
||||||
|
logger.info(f"Reminder sent for sub_id {sub['id']}")
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
logger.error(f"Failed to process reminder for sub_id {sub.get('id', 'N/A')}: {e}")
|
logger.error(f"Failed to process reminder for sub_id {sub.get('id', 'N/A')}: {e}")
|
||||||
|
|
||||||
|
|
||||||
# --- 命令处理器 ---
|
# --- 命令处理器 ---
|
||||||
async def start(update: Update, context: CallbackContext):
|
async def start(update: Update, context: CallbackContext):
|
||||||
user_id = update.effective_user.id
|
user_id = update.effective_user.id
|
||||||
@@ -1311,7 +1319,7 @@ async def edit_new_value_received(update: Update, context: CallbackContext):
|
|||||||
await update.effective_message.reply_text("错误:未选择要编辑的字段。")
|
await update.effective_message.reply_text("错误:未选择要编辑的字段。")
|
||||||
return ConversationHandler.END
|
return ConversationHandler.END
|
||||||
db_field = EDITABLE_SUB_FIELDS.get(field)
|
db_field = EDITABLE_SUB_FIELDS.get(field)
|
||||||
if not db_field:
|
if not db_field or not db_field.isidentifier():
|
||||||
if update.effective_message:
|
if update.effective_message:
|
||||||
await update.effective_message.reply_text("错误:不允许编辑该字段。")
|
await update.effective_message.reply_text("错误:不允许编辑该字段。")
|
||||||
logger.warning(f"Blocked unsafe field update attempt: {field}")
|
logger.warning(f"Blocked unsafe field update attempt: {field}")
|
||||||
|
|||||||
Reference in New Issue
Block a user