From a5a56923abc9738df7471ebe10bd4f0b168e5d06 Mon Sep 17 00:00:00 2001 From: calboo Date: Wed, 11 Feb 2026 13:08:01 +0100 Subject: [PATCH] show currrently running activity in logbook --- app.py | 29 +++- templates/logbook.html | 85 ++++++++++- templates/logbook_detail.html | 264 ++++++++++++++++++++++------------ 3 files changed, 275 insertions(+), 103 deletions(-) diff --git a/app.py b/app.py index aa30d77..77e4770 100644 --- a/app.py +++ b/app.py @@ -518,9 +518,9 @@ def logbook(): total_time_display = "0h" # --- Existing Logbook Logic --- - # Agrregation to join activities and tasks + # Updated: Remove the 'end_time': {'$ne': None} constraint pipeline = [ - {'$match': {'user_id': user_id, 'end_time': {'$ne': None}}}, + {'$match': {'user_id': user_id}}, {'$sort': {'start_time': -1}}, {'$lookup': { 'from': 'activities', @@ -544,8 +544,18 @@ def logbook(): for entry in log: # Filter tasks to only completed ones for display cleanly in list view entry['tasks'] = [t for t in entry['tasks'] if t['status'] == 'completed'] - duration = entry['end_time'] - entry['start_time'] - entry['duration_str'] = str(duration).split('.')[0] # HH:MM:SS + + if entry.get('end_time'): + duration = entry['end_time'] - entry['start_time'] + entry['duration_str'] = str(duration).split('.')[0] # HH:MM:SS + entry['is_running'] = False + else: + # Handle running entry + now = datetime.now() + duration = now - entry['start_time'] + # Format nicely removing microseconds + entry['duration_str'] = str(duration).split('.')[0] + entry['is_running'] = True return render_template('logbook.html', log=log, chart_data=chart_data, current_range=time_range, total_time_display=total_time_display) @@ -578,6 +588,8 @@ def log_entry_detail(entry_id): update_fields['start_time'] = datetime.strptime(start_str, '%Y-%m-%dT%H:%M') if end_str: update_fields['end_time'] = datetime.strptime(end_str, '%Y-%m-%dT%H:%M') + # If end_time was empty in form (running), and user didn't set it, it stays None (running) + # or if it was running and user sets a time, it stops. except ValueError: flash('Invalid date format') return redirect(url_for('log_entry_detail', entry_id=entry_id)) @@ -611,8 +623,15 @@ def log_entry_detail(entry_id): if entry.get('end_time') and entry.get('start_time'): duration = entry['end_time'] - entry['start_time'] entry['duration_str'] = str(duration).split('.')[0] + entry['is_running'] = False + elif entry.get('start_time'): + # Calculate uptime for running entry + duration = datetime.now() - entry['start_time'] + entry['duration_str'] = str(duration).split('.')[0] + " (Running)" + entry['is_running'] = True else: - entry['duration_str'] = "Running..." + entry['duration_str'] = "--:--" + entry['is_running'] = False # Fetch ALL Tasks linked to this entry (completed or not) tasks = list(db.tasks.find({'time_entry_id': ObjectId(entry_id)})) diff --git a/templates/logbook.html b/templates/logbook.html index 0b081f3..00c35ea 100644 --- a/templates/logbook.html +++ b/templates/logbook.html @@ -21,7 +21,8 @@ {% for entry in log %} -
+ +

@@ -31,9 +32,19 @@ {{ entry.subcategory }} {% endif %} + {% if entry.is_running %} + + Running + + {% endif %}

- {{ entry.start_time.strftime('%Y-%m-%d %H:%M') }} - {{ entry.end_time.strftime('%H:%M') }} + {{ entry.start_time.strftime('%Y-%m-%d %H:%M') }} - + {% if entry.is_running %} + Now + {% else %} + {{ entry.end_time.strftime('%H:%M') }} + {% endif %} {% if entry.note %}

"{{ entry.note }}"

@@ -41,8 +52,14 @@ {% endif %}
-
- {{ entry.duration_str }} +
+ + + {{ entry.duration_str }} + + {% if entry.is_running %} +
● Live
+ {% endif %}
@@ -94,7 +111,67 @@ + {% endblock %}