Skip to content

MickeyWzt/LoreLens

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

46 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

LoreLens 7.14

LoreLens 是面向全球旅行场景的文化解读 PWA。用户可以拍照或选择本地照片、调整关注区域,并获得与画面相关的文化线索、观察提示和行动建议。

Deploy to Render

7.14 保留了原有的沉浸式深色界面、玻璃卡片和相机体验,同时重构了扫描状态、AI 服务、定位、历史数据、离线能力、国际化、无障碍和生产服务器。

主要能力

  • 扫描状态机:主页、相机、裁剪、分析、结果、错误和待处理状态互斥,离开页面会取消过期分析请求。
  • 多 AI Provider:默认使用 Qwen 识图、DeepSeek 生成文字总结,可配置 Gemini 为备用。
  • 自然朗读:中文和英文使用小米 mimo-v2.5-tts;日、韩、西、法、德、意、葡、俄语使用低延迟的 qwen3-tts-flash;阿拉伯语、离线或云端故障时使用设备语音。
  • 安全服务端:API Key 只保存在服务端环境变量中;包含 10 MB 请求限制、超时、速率限制、安全响应头、请求 ID 和不记录请求正文的结构化日志。
  • 可靠定位:高精度 GPS → 低精度 GPS → 上次有效位置 → 可选 IP 粗略位置 → 明确不可用,不会伪造默认城市。
  • 定位辅助默认开启:相机拍摄时刷新并绑定设备定位;上传 JPEG 优先读取照片自身的 EXIF GPS,没有 EXIF 时不会冒用当前地点。
  • AI 定位交叉验证:完整传递坐标、精度、来源、时间与附近 POI;视觉和定位冲突或疑似仿制品时不生成确定地图链接。
  • 本地优先记录:分析图片经过压缩后保存在浏览器本地;离线裁剪会生成待处理记录,只有用户主动重试才会上传。
  • 版本化备份:支持 V2 JSON 导出、schema 校验导入和按记录 ID/更新时间合并。
  • PWA:字体、样式、脚本和应用壳本地缓存;地图与远程背景图使用受控运行时缓存。
  • 十一种语言:简体中文、英语、日语、韩语、西班牙语、法语、德语、意大利语、葡萄牙语、俄语和阿拉伯语,包含 RTL、键盘操作、减少动效和安全区适配。

运行要求

  • Node.js 20.19+ 或 22.12+
  • npm 10+
  • 现代 Chromium、Safari 或 Firefox 浏览器
  • 至少配置一个图像 AI Provider 才能进行真实图片解读

本地开发

npm install
Copy-Item .env.example .env.local
npm run dev

默认地址为 http://localhost:3000。请在 .env.local 中填入需要的密钥;不要把该文件提交到 Git。

最小推荐配置:

VISION_PROVIDER=qwen
QWEN_API_KEY=your_qwen_key
TEXT_PROVIDER=deepseek
DEEPSEEK_API_KEY=your_deepseek_key
MIMO_API_KEY=your_mimo_key

Qwen 负责单张图片解读;DeepSeek 只在用户主动生成“共鸣回顾”时处理文字记录。未配置 AI 时,应用仍可启动并验证相机、裁剪、离线记录、历史、地图和设置,分析操作会显示明确的“服务尚未配置”状态。

环境变量

完整模板见 .env.example

变量 默认值 用途
PORT 3000 Express/Vite 开发服务器端口
TRUST_PROXY_HOPS 0 可信反向代理跳数;Render 部署设为 1
API_RATE_LIMIT_PER_MINUTE 120 每个来源 IP 的 API 每分钟请求上限
AI_RATE_LIMIT_PER_DAY 30 每个来源 IP 的每日 AI 请求上限
TTS_RATE_LIMIT_PER_DAY 100 每个来源 IP 的每日云端朗读请求上限
VISION_PROVIDER qwen 图像 Provider:qwengemini
QWEN_API_KEY / DASHSCOPE_API_KEY Qwen/DashScope 服务端密钥
QWEN_VISION_MODEL qwen-vl-max-latest Qwen 视觉模型
QWEN_BASE_URL DashScope compatible-mode v1 OpenAI 兼容 Base URL
QWEN_TTS_API_KEY 复用 QWEN_API_KEY 可选独立千问 TTS 密钥
QWEN_TTS_MODEL qwen3-tts-flash 日、韩、西、法、德、意、葡、俄语云端朗读模型
QWEN_TTS_BASE_URL https://dashscope.aliyuncs.com/api/v1 千问原生 TTS API Base URL
QWEN_TTS_VOICE Cherry 千问多语言系统音色
TEXT_PROVIDER deepseek 文字 Provider:deepseekgemini
DEEPSEEK_API_KEY DeepSeek 服务端密钥
DEEPSEEK_TEXT_MODEL deepseek-chat DeepSeek 文字模型
DEEPSEEK_BASE_URL https://api.deepseek.com/v1 DeepSeek Base URL
GEMINI_API_KEY Gemini 主 Provider 或备用 Provider 密钥
VISION_FALLBACK_PROVIDER gemini 图像备用 Provider;仅可恢复错误时最多调用一次
TEXT_FALLBACK_PROVIDER gemini 文字备用 Provider;仅可恢复错误时最多调用一次
AI_TIMEOUT_MS 30000 单次上游请求超时,范围 1000–120000 ms
MIMO_API_KEY 小米 MiMo TTS 服务端密钥;为空时全部使用设备语音
MIMO_TTS_MODEL mimo-v2.5-tts 小米内置精品音色模型
MIMO_BASE_URL https://api.xiaomimimo.com/v1 小米 MiMo API Base URL
MIMO_TTS_TIMEOUT_MS 30000 单次语音生成超时,范围 1000–120000 ms
MIMO_TTS_VOICE_ZH / MIMO_TTS_VOICE_EN 茉莉 / Mia 中英文预设音色
UNSPLASH_ACCESS_KEY 可选动态城市背景图;为空时使用缓存或品牌渐变
IP_LOCATION_URL 可选粗略 IP 定位 JSON 地址,需返回经纬度字段

备用 Provider 只会在超时、HTTP 429 或可恢复的 5xx 错误时尝试一次。参数错误、内容错误和 schema 错误不会自动重复计费。

生产构建

npm run typecheck
npm test
npm run build
npm start

npm run build 会生成前端资源、Service Worker 和 dist/server.cjsnpm startdist 提供生产静态资源与 API;可以通过 PORT 更改监听端口。

反向代理需保留 HTTPS、X-Request-ID 和正常的流式请求语义。相机、定位、Service Worker 和剪贴板等能力在非 localhost 环境通常要求 HTTPS。

Render 公开测试版

仓库根目录的 render.yaml 定义了完整的 Node Web Service。点击上方 Deploy to Render,在创建 Blueprint 时填写四个 Secret:

  • QWEN_API_KEY
  • DEEPSEEK_API_KEY
  • MIMO_API_KEY
  • UNSPLASH_ACCESS_KEY

Render 会执行 npm ci --include=dev && npm run build,随后以 npm start 启动,并使用 /api/health 进行健康检查。生产环境启用一层可信代理、90 秒 AI 上游超时、每分钟 API 限流以及 AI/TTS 每日额度;修改额度只需调整 Render 环境变量。

免费 Render Web Service 适合公开测试,但闲置后会休眠。正式推广时应改为常驻实例,并在 AI 服务商后台配置余额提醒与消费上限。

API

方法与路径 说明
GET /api/health 返回可用能力,不返回密钥或模型凭据
POST /api/ai/decipher 解读一张 data URL 图片,返回标准 LoreLens 结果
POST /api/ai/recap 根据本地记录生成旅行回顾
POST /api/tts/speech 使用服务端小米 MiMo 为中英文生成 WAV 朗读音频
GET /api/location/reverse 将坐标转换为可读地点标签
GET /api/location/ip 使用已配置的 IP 定位服务返回粗略位置
GET /api/background 获取按“地点 + 时间段”缓存的 Unsplash 背景
POST /api/background/download 按 Unsplash 规则记录下载事件

错误响应统一为:

{
  "error": {
    "code": "UPSTREAM_UNAVAILABLE",
    "message": "The service is temporarily unavailable.",
    "retryable": true,
    "requestId": "..."
  }
}

本地数据与隐私

  • 设置键:lorelens_settings_v2
  • 记录键:IndexedDB/localForage 中的 lorelens_records_v2
  • 定位缓存键:lorelens_location_v2
  • 背景缓存前缀:lorelens_background_v2:
  • AI Key 不会写入浏览器、本地历史、导出文件或日志。
  • 照片只在用户主动开始分析时发送;开启定位后,位置会随照片发送以提高识别准确率。
  • 离线照片不会自动上传;联网后必须由用户点击“重试”。
  • JSON 导出可能包含用户选择保存的压缩照片和地点,因此应按私人备份处理。

从 7.13 升级时的数据兼容和 API 变更见 MIGRATION.md

项目结构

components/            页面与交互组件
domain/                Zod schema、状态机、裁剪与记录逻辑
services/              浏览器端 AI、定位、背景图和朗读服务
server/                Express API、Provider、缓存和定位服务
store/                 设置、历史与应用上下文状态
public/locales/        十一种语言资源
tests/                 Vitest、RTL 和 API 集成测试

常用命令

命令 作用
npm run dev 启动开发服务器和 Vite 中间件
npm run typecheck 运行 TypeScript 检查
npm test 运行全部 Vitest 测试
npm run test:watch 监听模式运行测试
npm run build 构建生产客户端、PWA 和服务端
npm start 启动已构建的生产服务

验收基线

  • TypeScript 检查通过
  • 24 个测试文件、92 项测试通过
  • 生产主入口 chunk 约 280 KB,地图、历史和设置按需加载
  • npm audit --audit-level=high 无 high/critical 漏洞
  • 已在 390×844、430×932 和 1440×900 的真实 Chromium 浏览器中验证核心流程

About

Transform your perspective with Lorelens. A modern lens designed to capture, explore, and connect the world’s most fascinating lore.

Topics

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages