# Request Proxy (请求代理)

- Summary: `requestProxy` 是 Five 初始化时的关键参数，用于在发起网络请求前对 URL 进行拦截和修改，常用于鉴权、资源重定向或 CDN 域名替换。
- Schema: `(url: string) => string | Promise<string>`
- Concepts: 请求拦截、资源重定向、鉴权签名。
- Configuration: `FiveInitArgs.requestProxy`。
- Examples: CDN 替换、私有化部署鉴权、调试模式。

## Schema

> Definition: FiveInitArgs

    interface FiveInitArgs {
      /**
       * 请求代理函数
       * @description 在 Five 内部发起任何网络请求（如加载图片、模型、配置）之前调用。
       * @param url - 原始请求 URL
       * @returns 修改后的 URL (string) 或异步返回修改后的 URL (Promise<string>)
       */
      requestProxy?: (url: string) => string | Promise<string>;
    }

## Concepts

### 拦截时机

Five 内部加载资源（全景图瓦片、3D 模型、纹理贴图等）时，会通过统一的 Fetcher 层发起请求。`requestProxy` 钩子函数会在每次请求发起前被触发。

### 核心用途

1. 域名替换 (CDN Domain Sharding): 将资源请求分散到多个 CDN 域名以突破浏览器并发限制。
2. 鉴权签名 (Authentication): 针对私有化部署或受保护资源，在 URL 后追加鉴权 Token (如 SAS Token)。
3. 资源重定向 (Redirection): 在开发环境下将线上资源重定向到本地或测试环境。
4. 协议适配: 强制将 `http` 协议升级为 `https`。

## Configuration

`requestProxy` 是 `Five` 构造函数的配置项之一。

参数 | 类型 | 默认值 | 说明
--- | --- | --- | ---
`requestProxy` | `(url: string) => string | Promise<string>` | `undefined` | 代理函数，返回修改后的 URL。支持同步或异步返回。

## Examples

### 1. 基础用法：CDN 域名替换

将图片资源请求分散到不同的 CDN 节点，加速加载。

    const five = new Five({
      requestProxy: (url) => {
        // 简单的字符串替换示例
        return url.replace('//vrlab-public.ljcdn.com/', '//vr-public.realsee-cdn.cn/');
      }
    });

### 2. 进阶用法：异步鉴权 (Async Auth)

对于需要动态获取 Token 的场景，可以使用 `Promise` 异步返回 URL。

    const five = new Five({
      requestProxy: async (url) => {
        // 仅对私有桶资源进行签名
        if (url.includes('private-bucket')) {
          const token = await fetchToken(); // 假设 fetchToken 是一个获取鉴权的异步函数
          const separator = url.includes('?') ? '&' : '?';
          return `${url}${separator}token=${token}`;
        }
        return url;
      }
    });

### 3. 开发调试：本地资源代理

在开发阶段，将特定资源重定向到本地文件。

    const proxyMap: Record<string, string> = {};

    const five = new Five({
      requestProxy: (url) => {
        // 如果该 URL 在映射表中存在（例如通过 <input type="file"> 加载的本地 Blob URL），则使用映射值
        if (proxyMap[url]) {
          console.log(`[Proxy] Redirecting ${url} -> ${proxyMap[url]}`);
          return proxyMap[url];
        }
        return url;
      }
    });

## Common Pitfalls

1. 死循环风险: 不要在 `requestProxy` 内部再次发起会导致 `requestProxy` 触发的 Five 资源请求，否则可能导致递归调用。
2. 性能损耗: `requestProxy` 会在所有资源请求前触发（包括成百上千个瓦片请求）。请确保该函数执行效率极高，避免进行耗时的同步操作。如果是异步操作，应做好缓存。
3. URL 格式: 确保返回的 URL 格式正确。如果原 URL 包含 Query 参数，拼接 Token 时要注意判断是使用 `?` 还是 `&`。
4. 缓存一致性: 如果修改了 URL（例如加了 Token），可能会影响浏览器的缓存命中策略。

## Related

- Parameter: Five 初始化参数总览。
- Load External Model: 加载外部模型时也会触发 requestProxy。

    tags: [请求代理, 鉴权, 域名替换, 私有化, 请求拦截, configuration, network, proxy, authentication, CDN, token, url-rewrite, cors]