Skip to content

7.3 富文本处理 ​

概述

富文本(如文章内容)中的图片/视频也需要处理。使用 [IMG_URL] 占位符机制,支持域名变更场景。

处理流程图 ​

html
┌─────────────────────────────────────────────────────────────────┐
│                      写入流程(add/update)                      │
├─────────────────────────────────────────────────────────────────┤
│                                                                 │
│  前端编辑器插入图片                                              │
│      │                                                          │
│      ▼                                                          │
│  上传到临时目录 temp/日期/                                       │
│      │                                                          │
│      ▼                                                          │
│  提交 HTML 内容到后端                                            │
│      │                                                          │
│      ▼                                                          │
│  BaseLogic::processContentFieldsOnSave()                        │
│      │                                                          │
│      ├─ 解析 <img> 标签的 src                                   │
│      ├─ 解析 <video>/<source>/<embed> 标签的 src                │
│      ├─ 解析 <a> 标签的文件 href                                │
│      │                                                          │
│      ▼                                                          │
│  save_file() 迁移临时文件 → 正式目录                             │
│      │                                                          │
│      ▼                                                          │
│  替换为 [IMG_URL]/相对路径 占位符                                │
│      │                                                          │
│      ▼                                                          │
│  数据库存储含占位符的 HTML                                       │
│                                                                 │
└─────────────────────────────────────────────────────────────────┘

┌─────────────────────────────────────────────────────────────────┐
│                      读取流程(detail/pageList)                 │
├─────────────────────────────────────────────────────────────────┤
│                                                                 │
│  数据库读取含占位符的 HTML                                       │
│      │                                                          │
│      ▼                                                          │
│  BaseLogic::processContentFieldsOnRead()                        │
│      │                                                          │
│      ├─ 替换 [IMG_URL] 为实际域名                                │
│      │   如 https://cdn.example.com                              │
│      │                                                          │
│      ▼                                                          │
│  返回完整 URL 的 HTML 给前端                                     │
│                                                                 │
└─────────────────────────────────────────────────────────────────┘

在 Logic 中配置 ​

php
class ArticleLogic extends BaseLogic
{
    /**
     * 富文本字段
     *
     * @var array
     */
    protected array $contentFields = ['content'];
}

配置后 BaseLogic 自动处理:

  • add/update:调用 save_content() 处理临时文件
  • detail/pageList/allList:调用 processContentFieldsOnRead() 替换占位符

为什么使用占位符? ​

域名变更场景

假设初始配置 FILE.DOMAIN_URL = https://cdn.example.com,文章内容中图片 URL 为: https://cdn.example.com/article/20260920/abc.jpg

存储时替换为:[IMG_URL]/article/20260920/abc.jpg

如果后续域名变更为 https://cdn2.example.com,只需修改 .env 中的 FILE.DOMAIN_URL,已存储的内容无需逐条更新,读取时自动替换为新域名。

处理范围 ​

save_content() 函数处理以下 HTML 标签:

标签属性说明
<img>src图片
<video>src视频
<source>src视频源
<embed>src嵌入内容
<a>href文件链接(仅处理带扩展名的链接)

代码示例 ​

php
// app/common.php 中的 save_content 函数

function save_content(string &$content, string $saveDir = 'article'): bool
{
    $config = config('file');
    $domainUrl = rtrim($config['domain_url'] ?? '', '/');

    if (empty($domainUrl) || empty($content)) {
        return false;
    }

    // 收集所有需要处理的 URL
    $urlMap = [];

    // 1. 匹配 <img> 标签的 src
    save_content_match($content, '/<img[^>]+src=["\']?([^"\'>\s]+)/i', $domainUrl, $saveDir, $urlMap);

    // 2. 匹配 <video>/<source>/<embed> 标签的 src
    save_content_match($content, '/<(?:video|source|embed)[^>]+src=["\']?([^"\'>\s]+)/i', $domainUrl, $saveDir, $urlMap);

    // 3. 匹配 <a> 标签的 href(指向文件的情况)
    save_content_match($content, '/<a[^>]+href=["\']?([^"\'>\s]+\.\w{2,5})["\']?/i', $domainUrl, $saveDir, $urlMap);

    // 批量替换
    if (!empty($urlMap)) {
        $content = str_replace(array_keys($urlMap), array_values($urlMap), $content);
    }

    return true;
}

注意事项 ​

富文本安全

  • 富文本内容可能包含 XSS 攻击代码,建议在前端使用编辑器的安全模式
  • save_content 只处理本站域名下的 URL,外部 URL 不做处理
  • 图片标签的 src 必须是完整 URL(包含域名),否则无法识别

小蚂蚁云团队 · 提供技术支持