Metadata-Version: 2.4
Name: huace-aigc-oss-proxy-client
Version: 0.1.6
Summary: 华策 AIGC OSS Proxy Client - 统一 RustFS / 阿里云 OSS / 七牛云上传，支持内网/公网默认上传网络
Author-email: Huace <support@huace.com>
License: MIT
Project-URL: Homepage, https://github.com/huace/huace-aigc-oss-proxy-client
Project-URL: Repository, https://github.com/huace/huace-aigc-oss-proxy-client
Keywords: aigc,oss,huace,sdk,rustfs,aliyun,s3
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Requires-Python: >=3.10
Description-Content-Type: text/markdown
Provides-Extra: aliyun
Requires-Dist: oss2>=2.18.0; extra == "aliyun"
Provides-Extra: rustfs
Requires-Dist: boto3>=1.34.0; extra == "rustfs"
Provides-Extra: qiniu
Requires-Dist: qiniu>=7.12.0; extra == "qiniu"
Requires-Dist: requests>=2.20.0; extra == "qiniu"
Provides-Extra: all
Requires-Dist: oss2>=2.18.0; extra == "all"
Requires-Dist: boto3>=1.34.0; extra == "all"
Requires-Dist: qiniu>=7.12.0; extra == "all"
Requires-Dist: requests>=2.20.0; extra == "all"
Provides-Extra: dev
Requires-Dist: pytest>=7.0.0; extra == "dev"
Requires-Dist: pytest-env>=1.0.0; extra == "dev"
Requires-Dist: moto[s3]>=5.0.0; extra == "dev"
Requires-Dist: build>=1.0.0; extra == "dev"
Requires-Dist: twine>=5.0.0; extra == "dev"

# AIGC OSS Proxy Python SDK

[![Python Version](https://img.shields.io/pypi/pyversions/huace-aigc-oss-proxy-client.svg)](https://pypi.org/project/huace-aigc-oss-proxy-client/)

面向华策 AIGC 插件的上传代理 SDK：上传网络 **`local`（内网 RustFS）** 或 **`public`（公网）**。`public` 按 `HUACE_AIGC_OSS_ALIYUN_ENABLED` / `HUACE_AIGC_OSS_QINIU_ENABLED` 自动选择公网后端，二者均启用时优先阿里云。代码可传 `route=` 覆盖；未传时读取 `HUACE_AIGC_OSS_DEFAULT_UPLOAD_NETWORK`。

**Python 版本**：`>= 3.10`（与 `pyproject.toml` 中 `requires-python` 一致；已声明兼容 **3.10 / 3.11 / 3.12**）。

## 安装

```bash
# 全量后端（RustFS + 阿里云 + 七牛）
pip install huace-aigc-oss-proxy-client[all]

# 仅阿里云 OSS
pip install huace-aigc-oss-proxy-client[aliyun]

# 仅 RustFS / S3 兼容内网（boto3）
pip install huace-aigc-oss-proxy-client[rustfs]

# 仅七牛云
pip install huace-aigc-oss-proxy-client[qiniu]
```

## 环境变量

`OssClient.from_env()` 从进程环境读取配置，变量名统一加前缀 **`HUACE_AIGC_`**（例如 `HUACE_AIGC_OSS_RUSTFS_KEY_PREFIX`）。

可复制 [env.example](./env.example) 为 `.env` 后填入真实值。

按存储对象分组的必填性与默认值如下：

### 全局

| 变量 | 字段含义 | 是否必填 | 默认值 |
|------|----------|----------|--------|
| `HUACE_AIGC_OSS_DEFAULT_UPLOAD_NETWORK` | 见下方说明 | 与代码 `route` 至少填一处 | 无 |

**`HUACE_AIGC_OSS_DEFAULT_UPLOAD_NETWORK`** — 默认上传网络

- **作用**：`upload()` 未传 `route` 时，决定走内网还是公网。
- **取值**：`local` \| `public`
  - `local` → 内网 RustFS
  - `public` → 公网对象存储，由 `HUACE_AIGC_OSS_ALIYUN_ENABLED` / `HUACE_AIGC_OSS_QINIU_ENABLED` 决定具体后端
- **优先级**：`upload(..., route=...)` 高于本变量；二者都未设置则报错。

配置示例：

```bash
# 内网 Worker：upload 可省略 route
HUACE_AIGC_OSS_DEFAULT_UPLOAD_NETWORK=local

# 公网发布（阿里云）
HUACE_AIGC_OSS_DEFAULT_UPLOAD_NETWORK=public
HUACE_AIGC_OSS_ALIYUN_ENABLED=true
HUACE_AIGC_OSS_QINIU_ENABLED=false
```

**`route=public` 时的公网后端选择**（无需单独配置 provider 变量）：

- `HUACE_AIGC_OSS_ALIYUN_ENABLED=true` → 使用阿里云 OSS
- `HUACE_AIGC_OSS_QINIU_ENABLED=true` → 使用七牛云
- 二者均启用 → **优先阿里云**
- 均未启用 → 上传报错

上传超时在代码中写死（不可通过环境变量配置），各 provider 不一致：

- **RustFS**：建连 `10` 秒（`UPLOAD_CONNECT_TIMEOUT_SEC`），传输读取 `3600` 秒（`UPLOAD_TRANSFER_TIMEOUT_SEC`）
- **阿里云 OSS** / **七牛云**：连接/请求超时均为 `3600` 秒（`UPLOAD_TRANSFER_TIMEOUT_SEC`）

### RustFS（内网）

| 变量 | 字段含义 | 是否必填 | 默认值 |
|------|----------|----------|--------|
| `HUACE_AIGC_OSS_RUSTFS_ACCESS_KEY` | RustFS 访问 AK | RustFS 启用时必填 | 无 |
| `HUACE_AIGC_OSS_RUSTFS_SECRET_KEY` | RustFS 访问 SK | RustFS 启用时必填 | 无 |
| `HUACE_AIGC_OSS_RUSTFS_BUCKET` | RustFS 桶名 | RustFS 启用时必填 | 无 |
| `HUACE_AIGC_OSS_RUSTFS_KEY_PREFIX` | RustFS 对象 key 前缀 | 否 | `tmp` |

以下 RustFS 参数在 SDK 首版中为代码写死默认值，不支持通过环境变量覆盖：
- `enabled=true`（固定开启）
- `region=us-east-1`
- `use_ssl=false`
- `max_retries=2`

RustFS 内网 endpoint（代码写死）：
- `http://oss.aigc-transdubbing.huacemedia.com:9000`

### 阿里云 OSS（外网）

| 变量 | 字段含义 | 是否必填 | 默认值 |
|------|----------|----------|--------|
| `HUACE_AIGC_OSS_ALIYUN_ENABLED` | 是否启用阿里云后端 | 否 | `true` |
| `HUACE_AIGC_OSS_ALIYUN_ACCESS_KEY_ID` | 阿里云 AK | 阿里云启用时建议必填 | 无 |
| `HUACE_AIGC_OSS_ALIYUN_ACCESS_KEY_SECRET` | 阿里云 SK | 阿里云启用时建议必填 | 无 |
| `HUACE_AIGC_OSS_ALIYUN_BUCKET` | 阿里云桶名 | 阿里云启用时必填 | 无 |
| `HUACE_AIGC_OSS_ALIYUN_KEY_PREFIX` | 阿里云对象 key 前缀 | 否 | `tmp` |

以下阿里云参数在 SDK 首版中为代码写死默认值，不支持通过环境变量覆盖：
- `endpoint=https://oss-cn-hangzhou.aliyuncs.com`
- `max_retries=3`

### 七牛云（可选）

| 变量 | 字段含义 | 是否必填 | 默认值 |
|------|----------|----------|--------|
| `HUACE_AIGC_OSS_QINIU_ENABLED` | 是否启用七牛后端 | 否 | `false` |
| `HUACE_AIGC_OSS_QINIU_ACCESS_KEY` | 七牛 AK | 七牛启用时必填 | 无 |
| `HUACE_AIGC_OSS_QINIU_SECRET_KEY` | 七牛 SK | 七牛启用时必填 | 无 |
| `HUACE_AIGC_OSS_QINIU_BUCKET` | 七牛空间名 | 七牛启用时必填 | 无 |
| `HUACE_AIGC_OSS_QINIU_DOMAIN` | 七牛访问域名 | 七牛启用时必填 | 无 |
| `HUACE_AIGC_OSS_QINIU_KEY_PREFIX` | 七牛对象 key 前缀 | 否 | `tmp` |

以下七牛参数在 SDK 首版中为代码写死默认值，不支持通过环境变量覆盖：
- `max_retries=3`

### 最小示例


```python
from huace_aigc_oss import OssProxy

proxy = OssProxy.from_env()
proxy.upload("/tmp/output.wav", "output.wav", route="local")
proxy.upload("/tmp/output.wav", "output.wav", route="public")
```

超时、重试等进阶项见 [env.example](./env.example)。

## 快速开始

上传时必须传 `download_name`，SDK 会对本地文件做分块 SHA256 计算，并自动生成对象 key：`<sha256><source_ext>`；`download_name` 仅用于下载响应头。

```python
from huace_aigc_oss import OssProxy

proxy = OssProxy.from_env()

# route 可显式传；不传时读取 HUACE_AIGC_OSS_DEFAULT_UPLOAD_NETWORK
proxy.upload("/tmp/output.wav", "output.wav", route="local")
proxy.upload("/tmp/output.wav", "output.wav")
```

## 内网转公网

内网 RustFS 上传返回的 URL 前缀在代码中固定为：

`http://oss.aigc-transdubbing.huacemedia.com:9000/`

若传入 URL 匹配该前缀，SDK 会从内网下载对象、上传至**阿里云 OSS**（须 `HUACE_AIGC_OSS_ALIYUN_ENABLED=true`），并返回公网 URL；否则原样返回。

```python
from huace_aigc_oss import OssProxy

proxy = OssProxy.from_env()

# 内网 URL → 下载后上传阿里云，返回 https://...aliyuncs.com/...
public_url = proxy.local_to_public_url(
    "http://oss.aigc-transdubbing.huacemedia.com:9000/huace-shortmovie/tmp/abc.mp4"
)

# 已是公网 URL → 直接返回
same = proxy.local_to_public_url("https://cdn.example.com/out.mp4")
```

## Docker Compose 配置说明

所有使用本 SDK client 的容器，都需要增加以下主机名映射，确保内网域名可解析：

```yaml
extra_hosts:
  - "oss.aigc-transdubbing.huacemedia.com:192.168.1.18"
```

即：只要容器内会调用 `huace-aigc-oss-proxy-client`，就必须配置该项。

## 插件集成示例

```python
from huace_aigc_oss import OssProxy

_client = None

def get_client() -> OssProxy:
    global _client
    if _client is None:
        _client = OssProxy.from_env()
    return _client

def upload_file(local_path: str, download_name: str, route: str) -> str:
    result = get_client().upload(local_path, download_name, route=route)
    return result.url or result.key
```
