2025-12-02 18:54:14 +08:00

128 lines
4.1 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# DashScope 本地视频文件路径格式问题 - 根因分析
## 问题描述
调用 DashScope API 时返回错误:
```
<400> InternalError.Algo.InvalidParameter: The provided URL does not appear to be valid. Ensure it is correctly formatted.
```
## 当前实现分析
### 尝试的方法 1直接使用绝对路径
```python
video_path_for_api = str(video_path.absolute())
# 例如:/Users/d-robotics/workSpace/videoSummary/uploads/episode_0_model_input_observation_full_image.mp4
```
**结果**:失败,返回 400 错误
### 尝试的方法 2使用 file:// 格式
```python
file_url = f"file://{absolute_path_str}"
# 例如file:///Users/d-robotics/workSpace/videoSummary/uploads/episode_0_model_input_observation_full_image.mp4
```
**结果**:失败,返回 400 错误
## 根因分析
### 1. 路径格式问题
根据 DashScope 官方文档示例:
```python
local_path = "xxx/test.mp4" # 绝对路径字符串
video_path = f"file://{local_path}"
```
**关键发现**
- 文档示例中 `local_path` 是**绝对路径字符串**,不包含前导斜杠
- 但在 macOS/Linux 系统上,绝对路径通常以 `/` 开头
- 当使用 `file://` 前缀时,如果路径以 `/` 开头,应该使用 `file:///`(三个斜杠)而不是 `file://`(两个斜杠)
### 2. URL 编码问题
路径中可能包含特殊字符(虽然当前路径没有),但 `file://` URL 格式要求路径部分需要进行 URL 编码:
- 空格应该编码为 `%20`
- 其他特殊字符也需要编码
### 3. 可能的解决方案
#### 方案 A使用正确的 file:// 格式(推荐)
根据 RFC 3986 和 file:// URL 规范:
- 在 Unix/macOS 系统上,`file://` URL 应该使用三个斜杠:`file:///`
- 路径应该进行 URL 编码
```python
from urllib.parse import quote, urljoin
import os
absolute_path = video_path.absolute()
absolute_path_str = str(absolute_path)
# 对于 Unix/macOS 系统,使用 file:/// 格式
if os.name != 'nt': # Unix/macOS
# 移除前导斜杠,然后添加 file:///
path_without_leading_slash = absolute_path_str.lstrip('/')
file_url = f"file:///{path_without_leading_slash}"
# 或者直接使用 file:/// 加上完整路径
file_url = f"file://{absolute_path_str}"
else: # Windows
# Windows 路径需要特殊处理
file_url = f"file:///{absolute_path_str.replace('\\', '/')}"
```
#### 方案 B直接使用绝对路径字符串如果 SDK 支持)
根据文档示例,可能 SDK 内部会自动处理 `file://` 前缀,所以应该直接传递绝对路径字符串:
```python
video_path_for_api = str(video_path.absolute())
```
#### 方案 C使用 pathlib 的 as_uri() 方法
Python 的 `pathlib.Path` 提供了 `as_uri()` 方法,可以生成正确的 file:// URL
```python
video_path_for_api = video_path.absolute().as_uri()
# 这会自动生成正确的 file:// URL 格式
```
## 推荐解决方案
**使用 `pathlib.Path.as_uri()` 方法**,这是最可靠的方式,因为:
1. Python 标准库方法,符合 RFC 3986 规范
2. 自动处理不同操作系统的路径格式
3. 自动处理特殊字符编码
4. 生成正确的 file:// URL 格式
### 实现代码
```python
def analyze_video(self, video_path: Path, prompt: str, fps: Optional[int] = None) -> Dict[str, Any]:
# ... existing code ...
# Use pathlib's as_uri() method to generate correct file:// URL
absolute_path = video_path.absolute()
video_path_for_api = absolute_path.as_uri()
# Log for debugging
logger.info(f"Using video path (file:// URI): {video_path_for_api}")
# ... rest of the code ...
```
## 验证步骤
1. 使用 `pathlib.Path.as_uri()` 生成 file:// URL
2. 验证生成的 URL 格式是否正确
3. 测试调用 DashScope API
4. 如果仍然失败,检查 DashScope SDK 文档是否有其他要求
## 注意事项
- DashScope API 可能需要在服务器端能够访问该文件路径
- 如果 API 服务器运行在不同的机器上,本地文件路径将无法访问
- 在这种情况下,可能需要将文件上传到可访问的 URL如 OSS或使用其他方式传递文件内容