Skip to content

Commit 576302f

Browse files
authored
Bug : Fix local timezone display (#195)
* docs: Added code of conduct * Deleted unused function * feat: Added function to convert to local timezone * feat: Updated display fonction to render local tz
1 parent 0723a9c commit 576302f

File tree

3 files changed

+50
-29
lines changed

3 files changed

+50
-29
lines changed

app/callbacks/display_callbacks.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@
1616

1717
import config as cfg
1818
from services import api_client
19-
from utils.display import build_vision_polygon, create_event_list_from_alerts
19+
from utils.display import build_vision_polygon, convert_dt_to_local_tz, create_event_list_from_alerts
2020

2121
logger = logging_config.configure_logging(cfg.DEBUG, cfg.SENTRY_DSN)
2222

@@ -374,7 +374,7 @@ def update_map_and_alert_info(sequence_on_display, cameras):
374374
bboxes=row_with_bboxes["processed_bboxes"],
375375
)
376376

377-
date_val = row_with_bboxes["created_at"].strftime("%Y-%m-%d %H:%M")
377+
date_val = convert_dt_to_local_tz(lat, lon, row_with_bboxes["created_at"])
378378
cam_name = f"{row_cam['name'].values.item()[:-3].replace('_', ' ')} : {int(row_with_bboxes['azimuth'])}°"
379379

380380
camera_info = f"{cam_name}"

app/utils/data.py

-26
Original file line numberDiff line numberDiff line change
@@ -4,35 +4,9 @@
44
# See LICENSE or go to <https://www.apache.org/licenses/LICENSE-2.0> for full license details.
55

66
import ast
7-
from datetime import datetime
87
from typing import List
98

109
import pandas as pd
11-
import pytz
12-
from timezonefinder import TimezoneFinder
13-
14-
tf = TimezoneFinder()
15-
16-
17-
def convert_time(df):
18-
df_ts_local = []
19-
for _, row in df.iterrows():
20-
lat = round(row["lat"], 4)
21-
lon = round(row["lon"], 4)
22-
23-
# Convert created_at to a timezone-aware datetime object assuming it's in UTC
24-
alert_ts_utc = datetime.fromisoformat(str(row["created_at"])).replace(tzinfo=pytz.utc)
25-
26-
# Find the timezone for the alert location
27-
timezone_str = tf.timezone_at(lat=lat, lng=lon)
28-
if timezone_str is None: # If the timezone is not found, handle it appropriately
29-
timezone_str = "UTC" # Fallback to UTC or some default
30-
alert_timezone = pytz.timezone(timezone_str)
31-
32-
# Convert alert_ts_utc to the local timezone of the alert
33-
df_ts_local.append(alert_ts_utc.astimezone(alert_timezone).strftime("%Y-%m-%dT%H:%M:%S"))
34-
35-
return df_ts_local
3610

3711

3812
def process_bbox(input_str):

app/utils/display.py

+48-1
Original file line numberDiff line numberDiff line change
@@ -4,20 +4,61 @@
44
# See LICENSE or go to <https://www.apache.org/licenses/LICENSE-2.0> for full license details.
55

66

7+
from datetime import datetime
78
from io import StringIO
89

910
import dash_leaflet as dl
1011
import pandas as pd
12+
import pytz
1113
import requests
1214
from dash import html
1315
from geopy import Point
1416
from geopy.distance import geodesic
17+
from timezonefinder import TimezoneFinder
1518

1619
import config as cfg
1720

1821
DEPARTMENTS = requests.get(cfg.GEOJSON_FILE, timeout=10).json()
1922

2023

24+
tf = TimezoneFinder()
25+
26+
27+
def convert_dt_to_local_tz(lat, lon, str_utc_timestamp):
28+
"""
29+
Convert a UTC timestamp string to a local timezone string based on latitude and longitude.
30+
31+
Parameters:
32+
lat (float): Latitude of the location.
33+
lon (float): Longitude of the location.
34+
str_utc_timestamp (str): UTC timestamp string in ISO 8601 format (e.g., "2023-10-01T12:34:56").
35+
36+
Returns:
37+
str: Local timezone string in the format "%Y-%m-%d %H:%M" or None if the input timestamp is invalid.
38+
39+
Example:
40+
>>> convert_dt_to_local_tz(48.8566, 2.3522, "2023-10-01T12:34:56")
41+
'2023-10-01 14:34'
42+
"""
43+
lat = round(lat, 4)
44+
lon = round(lon, 4)
45+
46+
# Convert str_utc_timestamp to a timezone-aware datetime object assuming it's in UTC
47+
try:
48+
ts_utc = datetime.fromisoformat(str(str_utc_timestamp)).replace(tzinfo=pytz.utc)
49+
except ValueError:
50+
return None # Handle invalid datetime format
51+
52+
# Find the local timezone
53+
timezone_str = tf.timezone_at(lat=lat, lng=lon)
54+
if timezone_str is None: # If the timezone is not found, handle it appropriately
55+
timezone_str = "UTC" # Fallback to UTC
56+
timezone = pytz.timezone(timezone_str)
57+
58+
# Convert ts_utc to the local timezone
59+
return ts_utc.astimezone(timezone).strftime("%Y-%m-%d %H:%M")
60+
61+
2162
def build_departments_geojson():
2263
"""
2364
This function reads the departments.geojson file in the /data folder thanks to the json module
@@ -191,7 +232,13 @@ def create_event_list_from_alerts(api_events, cameras):
191232
),
192233
style={"fontWeight": "bold"},
193234
),
194-
html.Div(event["started_at"].strftime("%Y-%m-%d %H:%M")),
235+
html.Div(
236+
convert_dt_to_local_tz(
237+
lat=cameras[cameras["id"] == event["camera_id"]]["lat"].values[0],
238+
lon=cameras[cameras["id"] == event["camera_id"]]["lon"].values[0],
239+
str_utc_timestamp=event["started_at"],
240+
)
241+
),
195242
],
196243
n_clicks=0,
197244
className="alert-card",

0 commit comments

Comments
 (0)