佳明导出.fit文件
-
选择Data Management-Export Your Data,导出所有数据,数据准备完成后会发送邮件提供下载链接
-
所有.fit活动文件在/DI_CONNECT/DI-Connect-Uploaded-Files/中的压缩包内
解析.fit文件
可以用fitparse
库解析.fit文件,选取自己想上传的文件
例如想获取活动时间在2024-1-20之前的文件:
from fitparse import FitFile
fit = FitFile(fit_filepath)
for record in fit.get_messages('record'):
timestamp = record.get_value('timestamp')
if timestamp and timestamp < cutoff_date:
print(f"File {fit_filepath} has a timestamp before 2024/01/20: {timestamp}")
break
strava导入.fit文件
-
在 Strava 开发者控制台创建应用:
- 创建 Strava 开发者账户并登录 Strava Developer Portal。
- 创建一个新的应用,网站可以设置成
http://localhost:8080
,用于用户授权后传authorization_code - 获取应用的 Client ID 和 Client Secret
-
用户授权:
-
本地起服务:
import http.server import socketserver import urllib.parse PORT = 8080 Handler = http.server.SimpleHTTPRequestHandler class MyHandler(http.server.BaseHTTPRequestHandler): def do_GET(self): parsed_path = urllib.parse.urlparse(self.path) query_params = urllib.parse.parse_qs(parsed_path.query) if 'code' in query_params: authorization_code = query_params['code'][0] print(f"Authorization code received: {authorization_code}") self.send_response(200) self.end_headers() self.wfile.write(b"Authorization code received successfully") else: self.send_response(400) self.end_headers() self.wfile.write(b"Error: Authorization code not found") with socketserver.TCPServer(("", PORT), MyHandler) as httpd: print(f"Serving at port {PORT}") httpd.serve_forever()
-
替换client_id,在浏览器中访问链接:
https://www.strava.com/oauth/authorize?client_id={client_id}&response_type=code&redirect_uri=http://localhost:8080&scope=activity:write,read&state=random_string&approval_prompt=auto -
在浏览器中授权后,本地服务端获得Authorization Code
-
-
OAuth认证:
- 根据Client ID、Client Secret、Authorization Code,获取有读写权限的Access Token
data = { 'client_id': client_id, 'client_secret': client_secret, 'code': authorization_code, 'grant_type': 'authorization_code', 'redirect_uri': 'http://localhost:8080' } response = requests.post('https://www.strava.com/oauth/token', data=data) if response.status_code == 200: token_data = response.json() new_access_token = token_data['access_token'] # 新的 Access Token new_refresh_token = token_data['refresh_token'] # 新的 Refresh Token print(f"New Access Token: {new_access_token}") print(f"New Refresh Token: {new_refresh_token}") else: print(f"Failed to refresh token: {response.text}")
- 根据Client ID、Client Secret、Authorization Code,获取有读写权限的Access Token
-
过期刷新Access Token:
- Refresh Token在Strava创建的应用页面可找到
- 上一步的data改成如下,重新请求获取Access Token
refresh_data = { 'client_id': client_id, 'client_secret': client_secret, 'refresh_token': refresh_token, 'grant_type': 'refresh_token' }
-
批量上传.fit文件
upload_url = 'https://www.strava.com/api/v3/uploads' fit_files = [f for f in os.listdir(source_folder) if f.endswith('.fit')] for fit_file in fit_files: fit_filepath = os.path.join(source_folder, fit_file) print(f"Uploading {fit_filepath}...") with open(fit_filepath, 'rb') as f: files = {'file': (fit_file, f, 'application/octet-stream')} params = { 'access_token': access_token, 'data_type': 'fit', # 上传文件类型为 FIT 'name': fit_file, # 设置上传活动的名称,默认用文件名 } response = requests.post(upload_url, files=files, data=params) if response.status_code == 201: print(f"Successfully uploaded {fit_file} to Strava.") else: print(f"Failed to upload {fit_file}: {response.text}")