Skip to content

Commit bdf32d0

Browse files
authored
Merge pull request #5 from cmw-creator/wcm
Wcm
2 parents 276eab1 + 449070d commit bdf32d0

25 files changed

Lines changed: 1407 additions & 439 deletions

android/app/build.gradle.kts

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ android {
1313
compileOptions {
1414
sourceCompatibility = JavaVersion.VERSION_17
1515
targetCompatibility = JavaVersion.VERSION_17
16+
isCoreLibraryDesugaringEnabled = true
1617
}
1718

1819
kotlinOptions {
@@ -21,7 +22,7 @@ android {
2122

2223
defaultConfig {
2324
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
24-
applicationId = "com.example.testapp"
25+
applicationId = "com.example.testapp.v200"
2526
// You can update the following values to match your application needs.
2627
// For more information, see: https://flutter.dev/to/review-gradle-config.
2728
minSdk = flutter.minSdkVersion
@@ -48,4 +49,8 @@ repositories {
4849
maven { url = uri("https://maven.aliyun.com/repository/google") }
4950
google()
5051
mavenCentral()
52+
}
53+
54+
dependencies {
55+
coreLibraryDesugaring("com.android.tools:desugar_jdk_libs:2.0.4")
5156
}

android/app/src/main/AndroidManifest.xml

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,10 @@
11
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
2+
<uses-permission android:name="android.permission.INTERNET"/>
23
<application
34
android:label="testapp"
45
android:name="${applicationName}"
5-
android:icon="@mipmap/ic_launcher">
6+
android:icon="@mipmap/ic_launcher"
7+
android:usesCleartextTraffic="true">
68
<activity
79
android:name=".MainActivity"
810
android:exported="true"

dog.zip

1.15 MB
Binary file not shown.

dog/assets/community.json

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,13 +6,19 @@
66
"content": "我的父亲经常忘记吃早饭后的药,大家有什么实用的方法?",
77
"author": "小李",
88
"timestamp": "2025-10-01T08:30:00",
9-
"likes": 5,
9+
"likes": 12,
1010
"comments": [
1111
{
1212
"id": 1,
1313
"author": "阿姨",
1414
"text": "可以把药和饭放在一起,吃完饭顺手拿药",
1515
"timestamp": "2025-10-01T09:00:00"
16+
},
17+
{
18+
"id": 2,
19+
"author": "家庭成员",
20+
"text": "Heng",
21+
"timestamp": "2026-01-03T19:52:49.279086"
1622
}
1723
]
1824
},
@@ -22,7 +28,7 @@
2228
"content": "想在午休时放一些轻柔音乐,有推荐吗?",
2329
"author": "小王",
2430
"timestamp": "2025-09-28T14:12:00",
25-
"likes": 6,
31+
"likes": 10,
2632
"comments": []
2733
}
2834
]
15.6 KB
Loading

dog/assets/photo_info.json

Lines changed: 32 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,38 @@
11
{
22
"photo_00001": {
3+
"title": "社区书法一等奖",
34
"description": "这是您参加社区书法比赛获得一等奖的作品和照片。您的楷书写得工整有力,评委们都说很有颜真卿的风骨。您从六十岁开始学习书法,每天坚持练习两个小时,这份坚持和毅力真是令人敬佩。",
5+
"event_date": "2025-10-01",
46
"update_time": "2025-10-01 18:20:00",
5-
"audio_file": "assets/voice/photo/photo_00001.wav"
7+
"image_file": "photo_detector/photo_00001.jpg",
8+
"audio_file": "",
9+
"location": "社区文化中心",
10+
"people": ["本人", "书法老师"],
11+
"tags": ["书法", "比赛", "获奖"],
12+
"emotion": "自豪"
13+
},
14+
"photo_00002": {
15+
"title": "全家秋日郊游",
16+
"description": "那天阳光正好,大家一起在公园里野餐、放风筝,还帮着拍了很多照片。",
17+
"event_date": "2024-10-15",
18+
"update_time": "2024-10-15 17:30:00",
19+
"image_file": "photo_detector/photo_00002.jpg",
20+
"audio_file": "",
21+
"location": "人民公园",
22+
"people": ["本人", "爱人", "孙女"],
23+
"tags": ["家庭", "郊游", "秋天"],
24+
"emotion": "温馨"
25+
},
26+
"photo_00003": {
27+
"title": "生日蛋糕惊喜",
28+
"description": "家人提前准备的生日惊喜,还有孙子亲手做的小卡片。",
29+
"event_date": "2024-11-20",
30+
"update_time": "2024-11-20 20:10:00",
31+
"image_file": "photo_detector/photo_00003.jpg",
32+
"audio_file": "",
33+
"location": "家中客厅",
34+
"people": ["本人", "家人"],
35+
"tags": ["生日", "家人", "庆祝"],
36+
"emotion": "快乐"
637
}
738
}

dog/dog/assets/family_info.json

Lines changed: 0 additions & 3 deletions
This file was deleted.

dog/dog_server.py

Lines changed: 71 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
from flask import Flask, request, jsonify, send_from_directory, stream_with_context, Response
1+
from flask import Flask, request, jsonify, send_from_directory, stream_with_context, Response, abort
22
from flask_cors import CORS
33
import threading
44
import time
@@ -24,9 +24,15 @@ def __init__(self):
2424
# 配置跨域请求
2525
CORS(self.app)
2626

27+
# 使用绝对路径以避免 CWD (当前工作目录) 不同导致的问题
28+
# .../DogApp2/dog
29+
current_dir = os.path.dirname(os.path.abspath(__file__))
30+
# .../DogApp2
31+
root_dir = os.path.dirname(current_dir)
32+
2733
# 服务器配置
28-
self.UPLOAD_FOLDER = 'uploads'
29-
self.ASSETS_FOLDER = os.path.join('dog', 'assets')
34+
self.UPLOAD_FOLDER = os.path.join(root_dir, 'uploads')
35+
self.ASSETS_FOLDER = os.path.join(current_dir, 'assets')
3036
self.ALLOWED_IMAGE_EXTENSIONS = {'png', 'jpg', 'jpeg', 'gif', 'bmp'}
3137
self.MAX_FILE_SIZE = 16 * 1024 * 1024 # 16MB
3238

@@ -80,8 +86,8 @@ def __init__(self):
8086
self.notification_history_lock = Lock()
8187
self.notification_next_id = 1
8288

83-
# 简单账号存储(明文,保存在 uploads/users.json)
84-
self.users_filename = 'users.json'
89+
# 简单账号存储(明文,保存在 dog/users.json)
90+
self.users_file_path = os.path.join(current_dir, 'users.json')
8591

8692
# 日程提醒推送相关
8793
self.schedule_notifier_stop = threading.Event()
@@ -152,17 +158,28 @@ def save_assets_json(self, data, filename):
152158

153159
# ========== 简易账号存储(明文,仅演示用途) ==========
154160
def load_users(self):
155-
data = self.load_json_data(self.users_filename)
156-
if not data:
157-
return {'users': []}
158-
if isinstance(data, list):
159-
return {'users': data}
160-
if isinstance(data, dict) and 'users' in data:
161-
return {'users': data.get('users', [])}
161+
try:
162+
with self.file_lock:
163+
if os.path.exists(self.users_file_path):
164+
with open(self.users_file_path, 'r', encoding='utf-8') as f:
165+
data = json.load(f)
166+
if isinstance(data, list):
167+
return {'users': data}
168+
if isinstance(data, dict) and 'users' in data:
169+
return {'users': data.get('users', [])}
170+
except Exception as e:
171+
logger.error(f"加载用户数据失败: {e}")
162172
return {'users': []}
163173

164174
def save_users(self, users):
165-
return self.save_json_data(users, self.users_filename)
175+
try:
176+
with self.file_lock:
177+
with open(self.users_file_path, 'w', encoding='utf-8') as f:
178+
json.dump(users, f, ensure_ascii=False, indent=4)
179+
return True
180+
except Exception as e:
181+
logger.error(f"保存用户数据失败: {e}")
182+
return False
166183

167184
def get_video_stream_generator(self, video_path):
168185
"""生成视频流,循环播放"""
@@ -616,6 +633,17 @@ def get_image(filename):
616633
return send_from_directory(self.app.config['UPLOAD_FOLDER'], filename)
617634
except FileNotFoundError:
618635
return jsonify({'message': '图片未找到'}), 404
636+
637+
# 访问 assets 下的静态资源(含记忆库图片)
638+
@self.app.route('/assets/<path:filename>')
639+
def get_asset(filename):
640+
try:
641+
safe_path = os.path.normpath(filename)
642+
if safe_path.startswith('..'):
643+
return abort(400)
644+
return send_from_directory(self.app.config['ASSETS_FOLDER'], safe_path)
645+
except FileNotFoundError:
646+
return jsonify({'message': '资源未找到'}), 404
619647

620648
# GPS数据上传路由
621649
@self.app.route('/upload_gps', methods=['POST'])
@@ -876,18 +904,38 @@ def update_photo_info():
876904
photo_id = data.get('photo_id')
877905
description = data.get('description', '')
878906
audio_file = data.get('audio_file', '')
907+
title = data.get('title', '')
908+
event_date = data.get('event_date', '')
909+
image_file = data.get('image_file', '')
910+
location = data.get('location', '')
911+
tags = data.get('tags', [])
912+
people = data.get('people', [])
913+
emotion = data.get('emotion', '')
914+
915+
if isinstance(tags, str):
916+
tags = [t.strip() for t in tags.split(',') if t.strip()]
917+
if isinstance(people, str):
918+
people = [p.strip() for p in people.split(',') if p.strip()]
879919

880920
if not photo_id:
881921
return jsonify({'message': '缺少photo_id字段'}), 400
882922

883923
# 加载现有数据
884924
photo_info = self.load_assets_json('photo_info.json')
925+
existing = photo_info.get(photo_id, {})
885926

886927
# 更新或添加
887928
photo_info[photo_id] = {
888-
'description': description,
929+
'title': title or existing.get('title', ''),
930+
'description': description or existing.get('description', ''),
931+
'event_date': event_date or existing.get('event_date', ''),
889932
'update_time': datetime.now().strftime('%Y-%m-%d %H:%M:%S'),
890-
'audio_file': audio_file
933+
'image_file': image_file or existing.get('image_file', ''),
934+
'audio_file': audio_file or existing.get('audio_file', ''),
935+
'location': location or existing.get('location', ''),
936+
'tags': tags or existing.get('tags', []),
937+
'people': people or existing.get('people', []),
938+
'emotion': emotion or existing.get('emotion', '')
891939
}
892940

893941
if self.save_assets_json(photo_info, 'photo_info.json'):
@@ -960,7 +1008,8 @@ def upload_photo_image():
9601008
return jsonify({
9611009
'message': '照片上传成功!',
9621010
'photo_id': photo_id,
963-
'file_path': filename
1011+
'file_path': filename,
1012+
'asset_path': f"photo_detector/{filename}"
9641013
}), 200
9651014
else:
9661015
return jsonify({'message': '不支持的文件类型'}), 400
@@ -1700,21 +1749,21 @@ def internal_error(e):
17001749

17011750

17021751

1703-
def run_server(self):
1752+
def run_server(self, port=5000):
17041753
"""运行Flask服务器"""
17051754
print("启动机器狗控制服务器...")
17061755
print(f"上传目录: {os.path.abspath(self.app.config['UPLOAD_FOLDER'])}")
1707-
print("服务器地址: http://0.0.0.0:5000")
1756+
print(f"服务器地址: http://0.0.0.0:{port}")
17081757

17091758
# 使用多线程模式运行
1710-
self.app.run(host='0.0.0.0', port=5000, debug=False, threaded=True)
1759+
self.app.run(host='0.0.0.0', port=port, debug=False, threaded=True)
17111760

1712-
def start(self):
1761+
def start(self, port=5000):
17131762
"""启动服务器线程"""
1714-
server_thread = threading.Thread(target=self.run_server)
1763+
server_thread = threading.Thread(target=self.run_server, kwargs={'port': port})
17151764
server_thread.daemon = True
17161765
server_thread.start()
1717-
print("机器狗API服务器已启动在端口5000")
1766+
print(f"机器狗API服务器已启动在端口{port}")
17181767

17191768
# 集成到现有的机器狗主程序
17201769
def main():

dog/main.py

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -20,15 +20,17 @@ class AppLauncher:
2020
def __init__(self):
2121
self.dog_server = DogServer()
2222
self.webrtc_server = WebRTCServer()
23+
self.api_port = 5000
2324

2425
def start(self):
2526
def start_dog():
26-
self.dog_server.start()
27+
self.dog_server.start(port=self.api_port)
2728

2829
# 启动 webrtc_server(内部已管理 asyncio 线程循环)
2930
def start_webrtc():
30-
logger.info("启动 webrtc_server on 0.0.0.0:5001")
31-
self.webrtc_server.run(host='0.0.0.0', port=5001, debug=False)
31+
webrtc_port = self.api_port + 1
32+
logger.info(f"启动 webrtc_server on 0.0.0.0:{webrtc_port}")
33+
self.webrtc_server.run(host='0.0.0.0', port=webrtc_port, debug=False)
3234

3335
start_dog()
3436
import threading
File renamed without changes.

0 commit comments

Comments
 (0)