Skip to content

Commit

Permalink
Merge branch 'fix_keep'
Browse files Browse the repository at this point in the history
* fix_keep:
  fix: yihong0618#484 keep gps data decode
  doc: new runner
  upd runner's page url (yihong0618#522)
  fix: cityMatch (yihong0618#521)
  fix: upload to strava type

# Conflicts:
#	README-CN.md
#	README.md
  • Loading branch information
ben-29 committed Oct 19, 2023
2 parents 7c3c05b + 5b381b0 commit c8a5795
Show file tree
Hide file tree
Showing 4 changed files with 51 additions and 40 deletions.
1 change: 1 addition & 0 deletions requirements.txt
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ tzlocal
fit-tool
haversine==2.8.0
garth
pycryptodome


bs4
Expand Down
16 changes: 7 additions & 9 deletions run_page/codoon_sync.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,29 +6,27 @@
import os
import time
import urllib.parse
import xml.etree.ElementTree as ET
from collections import namedtuple
from datetime import datetime, timedelta

import eviltransform
import gpxpy
import numpy as np
import polyline
import requests
import eviltransform
from config import (
BASE_TIMEZONE,
GPX_FOLDER,
TCX_FOLDER,
JSON_FILE,
SQL_FILE,
TCX_FOLDER,
run_map,
start_point,
)
from generator import Generator

from utils import adjust_time_to_utc, adjust_timestamp_to_utc, to_date

import numpy as np
import xml.etree.ElementTree as ET
from tzlocal import get_localzone
from utils import adjust_time_to_utc, adjust_timestamp_to_utc, to_date

# struct body
FitType = np.dtype(
Expand Down Expand Up @@ -238,13 +236,13 @@ def tcx_job(run_data):
if "points" in run_data:
own_points = run_data["points"] # track points
# get single bpm
if own_heart_rate != None:
if own_heart_rate is not None:
for single_time, single_bpm in own_heart_rate.items():
single_time = adjust_timestamp_to_utc(single_time, str(get_localzone()))
# set bpm data
fit_array = set_array(fit_array, single_time, single_bpm, None, None, None)
# get single track point
if own_points != None:
if own_points is not None:
for point in own_points:
repeat_flag = False
# TODO add elevation information
Expand Down
57 changes: 29 additions & 28 deletions run_page/keep_sync.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
import zlib
from collections import namedtuple
from datetime import datetime, timedelta
from Crypto.Cipher import AES

import eviltransform
import gpxpy
Expand All @@ -21,6 +22,10 @@
RUN_DATA_API = "https://api.gotokeep.com/pd/v3/stats/detail?dateUnit=all&type=running&lastDate={last_date}"
RUN_LOG_API = "https://api.gotokeep.com/pd/v3/runninglog/{run_id}"

# AES Decrypt key
key = b"56fe59;82g:d873c"
iv = b"2346892432920300"

# If your points need trans from gcj02 to wgs84 coordinate which use by Mappbox
TRANS_GCJ02_TO_WGS84 = True

Expand Down Expand Up @@ -64,8 +69,12 @@ def get_single_run_data(session, headers, run_id):
return r.json()


def decode_runmap_data(text):
run_points_data = zlib.decompress(base64.b64decode(text), 16 + zlib.MAX_WBITS)
def decode_runmap_data(text, is_geo=False):
_bytes = base64.b64decode(text)
if is_geo:
cipher = AES.new(key, AES.MODE_CBC, iv)
_bytes = cipher.decrypt(_bytes)
run_points_data = zlib.decompress(_bytes, 16 + zlib.MAX_WBITS)
run_points_data = json.loads(run_points_data)
return run_points_data

Expand All @@ -80,33 +89,25 @@ def parse_raw_data_to_nametuple(
keep_id = run_data["id"].split("_")[1]

start_time = run_data["startTime"]
if run_data.get("vendor", {}).get("source", "") == "Keep" and run_data.get(
"rawDataURL"
):
raw_data_url = run_data.get("rawDataURL")
r = session.get(raw_data_url)
if r.ok:
# string strart with `H4sIAAAAAAAA` --> decode and unzip
run_points_data = decode_runmap_data(r.text)
run_points_data_gpx = run_points_data
if TRANS_GCJ02_TO_WGS84:
run_points_data = [
list(eviltransform.gcj2wgs(p["latitude"], p["longitude"]))
for p in run_points_data
]
for i, p in enumerate(run_points_data_gpx):
p["latitude"] = run_points_data[i][0]
p["longitude"] = run_points_data[i][1]
else:
run_points_data = [
[p["latitude"], p["longitude"]] for p in run_points_data
]
if with_download_gpx:
if str(keep_id) not in old_gpx_ids:
gpx_data = parse_points_to_gpx(run_points_data_gpx, start_time)
download_keep_gpx(gpx_data, str(keep_id))
if run_data["geoPoints"]:
run_points_data = decode_runmap_data(run_data["geoPoints"], True)
run_points_data_gpx = run_points_data
if TRANS_GCJ02_TO_WGS84:
run_points_data = [
list(eviltransform.gcj2wgs(p["latitude"], p["longitude"]))
for p in run_points_data
]
for i, p in enumerate(run_points_data_gpx):
p["latitude"] = run_points_data[i][0]
p["longitude"] = run_points_data[i][1]
else:
print(f"ID {keep_id} retrieved gpx data failed")
run_points_data = [[p["latitude"], p["longitude"]] for p in run_points_data]
if with_download_gpx:
if str(keep_id) not in old_gpx_ids:
gpx_data = parse_points_to_gpx(run_points_data_gpx, start_time)
download_keep_gpx(gpx_data, str(keep_id))
else:
print(f"ID {keep_id} no gps data")
heart_rate = None
if run_data["heartRate"]:
heart_rate = run_data["heartRate"].get("averageHeartRate", None)
Expand Down
17 changes: 14 additions & 3 deletions run_page/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -98,17 +98,28 @@ def get_strava_last_time(client, is_milliseconds=True):
return 0


def upload_file_to_strava(client, file_name, data_type):
def upload_file_to_strava(client, file_name, data_type, force_to_run=True):
with open(file_name, "rb") as f:
try:
r = client.upload_activity(activity_file=f, data_type=data_type)
if force_to_run:
r = client.upload_activity(
activity_file=f, data_type=data_type, activity_type="run"
)
else:
r = client.upload_activity(activity_file=f, data_type=data_type)

except RateLimitExceeded as e:
timeout = e.timeout
print()
print(f"Strava API Rate Limit Exceeded. Retry after {timeout} seconds")
print()
time.sleep(timeout)
r = client.upload_activity(activity_file=f, data_type=data_type)
if force_to_run:
r = client.upload_activity(
activity_file=f, data_type=data_type, activity_type="run"
)
else:
r = client.upload_activity(activity_file=f, data_type=data_type)
print(
f"Uploading {data_type} file: {file_name} to strava, upload_id: {r.upload_id}."
)

0 comments on commit c8a5795

Please sign in to comment.