# 写入文件

{% hint style="warning" %}
实验性功能
{% endhint %}

在某些情况下，UFS 的性能和带宽可能不能满足大量数据写入的需求。为了解决这个问题，Alluxio 提供了 CACHE\_ONLY 的写入方式： Alluxio 支持将数据只写入到 Alluxio 集群，由于整个过程不与 UFS 交互，写入性能和带宽完全取决于 Alluxio 集群本身的性能和带宽。这个功能被称为 **CACHE\_ONLY。**

推荐的使用场景如下：

* AI 训练过程中临时保存 checkpoint 文件；
* 大数据计算中产生的 shuffle 文件。

在这些场景中，文件仅仅只是临时写入，并不需要长期存储。

> 此外，对于需要最终将 CACHE\_ONLY 文件持久化的场景，Alluxio 支持异步持久化功能选项，可按照[启用异步持久化](#qi-yong-yi-bu-chi-jiu-hua)部分中的说明进行配置。

## 启用 CACHE\_ONLY

要使用 CACHE\_ONLY 功能，应单独部署 CACHE\_ONLY 存储组件。需注意的是，Alluxio 客户端会直接与 CACHE\_ONLY 存储进行交互，而不会与 Alluxio Worker 通信。CACHE\_ONLY 存储中的数据和元数据由其自身独立管理。由于文件是独立管理的，CACHE\_ONLY 中的文件无法与由 Alluxio Worker 提供服务的其他文件进行交互。

<figure><img src="/files/21uraSl6lOAQCwpe1zSF" alt=""><figcaption></figcaption></figure>

### 在 Kubernetes 上部署 CACHE\_ONLY Storage

CACHE\_ONLY 存储的部署已集成到 Alluxio Operator 中。只需在 Alluxio 部署文件中配置 `cacheOnly` 字段即可启用该功能。

```yaml
apiVersion: k8s-operator.alluxio.com/v1
kind: AlluxioCluster
metadata:
  name: alluxio
spec:
  image: <PRIVATE_REGISTRY>/alluxio-enterprise
  imageTag: <TAG>
  properties:

  worker:
    count: 2

  pagestore:
    size: 100Gi

  cacheOnly:
    enabled: true
    mountPath: "/cache-only"
    image: <PRIVATE_REGISTRY>/alluxio-cacheonly
    imageTag: <TAG>
    imagePullPolicy: IfNotPresent

    # Replace with base64 encoded license generated by
    # cat /path/to/license.json | base64 |  tr -d "\n"
    license:

    properties:

    journal:
      storageClass: "gp2"

    worker:
      count: 2
    tieredstore:
      levels:
        - level: 0
          alias: SSD
          mediumtype: SSD
          path: /data1/cacheonly/worker
          type: hostPath
          quota: 10Gi
```

**注意：**&#x43;ACHE\_ONLY Worker 需要本地磁盘存储 CACHE\_ONLY 类型的数据，这部分的磁盘空间与 Alluxio Worker 的缓存完全独立，所以需要提前预估 CACHE\_ONLY 的使用容量，预留磁盘空间。

### 配置资源使用量

类似 coordinator 和 worker，我们可以使用类似的字段来配置 CACHE\_ONLY Master 和 Worker 使用的资源 `cacheOnly.master.resources` 和 `cacheOnly.worker.resources`。

```yaml
apiVersion: k8s-operator.alluxio.com/v1
kind: AlluxioCluster
metadata:
  name: alluxio
spec:
  cacheOnly:
    enabled: true
    master:
      count: 1
      resources:
        limits:
          cpu: "8"
          memory: "40Gi"
        requests:
          cpu: "8"
          memory: "40Gi"
      jvmOptions:
        - "-Xmx24g"
        - "-Xms24g"
        - "-XX:MaxDirectMemorySize=8g"
    worker:
      count: 2
      resources:
        limits:
          cpu: "8"
          memory: "20Gi"
        requests:
          cpu: "8"
          memory: "20Gi"
      jvmOptions:
        - "-Xmx8g"
        - "-Xms8g"
        - "-XX:MaxDirectMemorySize=8g"
```

推荐的内存计算方式为：

```
(${Xmx} + ${MaxDirectMemorySize}) * 1.1 <= ${requests} = ${limit}
```

### 访问 CACHE\_ONLY

在 CACHE\_ONLY Storage 部署完成后，所有访问 `/cache_only` 挂载点的请求都是 CACHE\_ONLY 类型的请求，我们可以以多种形式来访问 CACHE\_ONLY 的数据。

使用 Alluxio Cli 访问：

```shell
bin/alluxio fs ls /cache_only
```

使用 Alluxio FUSE 接口访问：

```shell
cd ${fuse_mount_path}/cache_only
echo '123' > test.txt
cat test.txt
```

## 启用异步持久化

对于需要将 Alluxio 中的临时数据最终持久化的场景，Alluxio 提供了异步持久化机制。该机制允许写入 CACHE\_ONLY 挂载点的数据，异步上传到配置好的对应 UFS 路径中。

此功能特别适用于无需立即持久化但需要实现最终一致性的环境。

### 局限性

1. **元数据操作受限**：仅支持基本的文件持久化，重命名等操作无法可靠处理
2. **UFS清理缺失**：从 Alluxio 删除文件不会自动清除UFS中的对应数据。
3. **恢复机制较弱**：如果某个文件在 UFS 和 Alluxio 中的版本出现差异，Alluxio 当前无法对其进行一致性修复。
4. **文件修改会重新触发持久化**：在 Alluxio 中修改文件会调度新的异步持久化任务，可能导致 Alluxio 和 UFS 间版本不一致。
5. **缓存隔离**：通过 `CACHE_ONLY` 写入并最终持久化到 UFS 的文件，在写入 UFS 后也不会从`CACHE_ONLY` 中移除。通过原始的`CACHE_ONLY` 路径读取会命中 `CACHE_ONLY` 缓存，而通过 UFS 路径读取则会走标准的 Alluxio Worker 读取流程——这两种缓存相互隔离，不共享数据。

### 功能启用

需完成以下配置：

1. 启用 CACHE\_ONLY（作为异步持久化的前提条件）
2. 配置`alluxio.gemini.master.async.upload.local.file.path`及对应的 JSON 路径（需在 Alluxio 和 Alluxio CACHE\_ONLY 节点上同时设置，详见下文说明）。
3. 启用 Alluxio Coordinator（异步持久化依赖 job 服务）。
4. 确保 CACHE\_ONLY Master 可连接 ETCD。
5. 如果通过 Operator 部署，请确保在 Alluxio CACHE\_ONLY 组件的配置中同步设置 Alluxio 全局参数。由于当前 Operator 的限制，部分操作生成的属性需要手动在 CACHE\_ONLY 组件中指定。

### 配置选项

| 属性                                                     | 描述                  | 默认    |
| ------------------------------------------------------ | ------------------- | ----- |
| `alluxio.gemini.master.async.upload.local.file.path`   | 异步上传路径映射JSON文件的存储路径 | *N/A* |
| `alluxio.gemini.master.persistence.checker.interval`   | 检查并更新异步持久化状态的时间间隔   | `1s`  |
| `alluxio.gemini.master.persistence.scheduler.interval` | 调度新的异步持久化任务的时间间隔    | `1s`  |

#### 异步上传路径映射配置文件

在 `alluxio.gemini.master.async.upload.local.file.path` 中指定的文件路径应为 JSON 格式。示例如下：

```json
{
  "cacheOnlyMountPoint": "/cache-only",
  "asyncUploadPathMapping": {
    "/cache-only/a": "/s3/a",
    "/cache-only/b": "/local/c"
  },
  "blackList": [
    ".tmp"
  ]
}
```

#### 支持的配置键

| 键名                       | 是否必填  | 描述                                             |
| ------------------------ | ----- | ---------------------------------------------- |
| `cacheOnlyMountPoint`    | 是     | CACHE\_ONLY 存储的挂载点路径                           |
| `asyncUploadPathMapping` | 是     | 键为 CACHE\_ONLY 子路径，值为要持久化的 Alluxio 路径（通过挂载表解析） |
| `blackList`              | 否（可选） | 简单的文件名模式排除列表（非正则表达式）                           |

***

### 容错机制

1. **Worker 故障**: 如果某个 `CACHE_ONLY` Worker 下线， Alluxio 可从其他存有副本的 CACHE\_ONLY Worker 获取数据（需启用副本机制）
2. **Master 故障切换**：异步持久化所需的元数据存储于 Alluxio Master 日志中。当一个 Master 故障时，备用 Master 可通过读取日志恢复元数据。
3. **Coordinator 重启**：异步持久化任务由 Alluxio Coordinator 管理，其 job 状态存储于本地 RocksDB。Coordinator 重启后可通过读取 RocksDB 状态恢复进行中的任务。
4. **Worker 重分配**：如果负责 UFS 上传的 Worker 故障，Coordinator 会将任务重新调度至其他 Worker。

***

### 从 UFS 恢复丢失数据

当文件从 `CACHE_ONLY` 中丢失时，Alluxio 支持通过以下机制从 UFS 恢复数据：

#### 恢复触发条件

1. **打开文件时发现数据块缺失**：通过 `CACHE_ONLY` 路径打开的文件若存在缺失块，客户端会自动从 UFS 拉取缺失内容并缓存。
2. **文件读取错误**：如果 Alluxio 在读取 `CACHE_ONLY` 中的文件时遇到错误，客户端将回退为直接从 UFS 读取该文件，**不会重新缓存到 Alluxio**。

#### 恢复所需前提条件

* 文件之前已经通过异步持久化写入到了 UFS；
* UFS中的文件修改时间**晚于** Alluxio 中的记录；
* UFS 中的文件长度与 Alluxio 元数据中记录的长度一致。

## 高级配置

### 启用多副本

CACHE\_ONLY 支持写入多副本，需要在部署文件里增加配置 `alluxio.gemini.user.file.replication`：

```yaml
apiVersion: k8s-operator.alluxio.com/v1
kind: AlluxioCluster
metadata:
  name: alluxio
spec:
  properties:
    "alluxio.gemini.user.file.replication": "2"
```

### 启用 multipart-upload

Alluxio 支持将写入的数据暂存到内存，在后台使用 multipart-upload 多线程上传到 CACHE\_ONLY 集群，这能够有效提高写入的性能。要开启此功能，需要增加以下配置：

```yaml
apiVersion: k8s-operator.alluxio.com/v1
kind: AlluxioCluster
metadata:
  name: alluxio
spec:
  properties:
    "alluxio.gemini.user.file.cache.only.multipart.upload.enabled": "true"
    "alluxio.gemini.user.file.cache.only.multipart.upload.threads": "16"
    "alluxio.gemini.user.file.cache.only.multipart.upload.buffer.number": "16"
```

| 配置项                                                                | 默认值   | 描述                                 |
| ------------------------------------------------------------------ | ----- | ---------------------------------- |
| alluxio.gemini.user.file.cache.only.multipart.upload.enabled       | false | 是否启用 multipart upload 功能           |
| alluxio.gemini.user.file.cache.only.multipart.upload.threads       | 16    | multipart upload 可使用的最大线程数         |
| alluxio.gemini.user.file.cache.only.multipart.upload.buffer.number | 16    | multipart upload 可使用的内存 buffer 的数量 |

**注意：**&#x5F00;启 multipart-upload 会显著增加 Alluxio Client 的内存使用量，内存使用量计算如下：

```
${alluxio.gemini.user.file.cache.only.multipart.upload.buffer.number} * 64MB 
```

### 缓存驱逐

以 CACHE\_ONLY 模式存储的文件不会被自动驱逐。 如果存储容量接近满载，可以手动删除这些文件以释放空间。 比如在 Alluxio FUSE 里使用 `rm ${file_path}` 或者在命令行里使用 `bin/alluxio fs rm ${file_path}`。


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://documentation.alluxio.io/ee-ai-cn/ai-3.6/data-access/performance/file-writing.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
