### 5.1.16 资源组

[](<>)

MySQL 支持资源组的创建和管理，并允许将在服务器中运行的线程分配给特定组，以便线程根据组可用的资源执行。组属性启用对其资源的控制，以启用或限制组中线程的资源消耗。DBA 可以根据不同的工作负载修改这些属性。

目前，CPU时间是一种可管理的资源，以“虚拟CPU”的概念表示，包括CPU内核、超线程、硬件线程等。服务器在启动时确定有多少虚拟 CPU 可用，具有适当权限的数据库管理员可以将这些 CPU 与资源组相关联并将线程分配给组。

例如，为了管理不需要以高优先级执行的批处理作业的执行，DBA 可以创建一个`批`资源组，并根据服务器的繁忙程度上下调整其优先级。（也许分配给组的批处理作业应该在白天以较低的优先级运行，而在夜间以较高的优先级运行。）DBA 还可以调整组可用的 CPU 集。可以启用或禁用组以控制线程是否可分配给它们。

以下部分描述了 MySQL 中资源组使用的各个方面：

-   [资源组元素](resource-groups.html#resource-group-elements)

-   [资源组属性](resource-groups.html#resource-group-attributes)

-   [资源组管理](resource-groups.html#resource-group-management)

-   [资源组复制](resource-groups.html#resource-group-replication)

-   [资源组限制](resource-groups.html#resource-group-restrictions)

重要的

在某些平台或 MySQL 服务器配置上，资源组不可用或有限制。特别是，对于某些安装方法，Linux 系统可能需要手动步骤。有关详细信息，请参阅[资源组限制](resource-groups.html#resource-group-restrictions).

#### 资源组元素

这些功能为 MySQL 中的资源组管理提供了 SQL 接口：

-   SQL 语句可以创建、更改和删除资源组，并可以将线程分配给资源组。优化器提示允许将单个语句分配给资源组。

-   资源组权限提供对哪些用户可以执行资源组操作的控制。

-   这[`INFORMATION_SCHEMA.RESOURCE_GROUPS`](information-schema-resource-groups-table.html)表公开有关资源组定义和性能模式的信息[`线程`](performance-schema-threads-table.html)表显示了每个线程的资源组分配。

-   状态变量提供每个管理 SQL 语句的执行计数。

#### 资源组属性

[](<>)

资源组具有定义组的属性。所有属性都可以在组创建时设置。一些属性在创建时是固定的；之后可以随时修改其他人。

这些属性是在资源组创建时定义的，不能修改：

-   每个组都有一个名称。资源组名称是类似于表名和列名的标识符，不需要在 SQL 语句中引用，除非它们包含特殊字符或保留字。组名不区分大小写，最长可达 64 个字符。

-   每个组都有一个类型，要么是`系统`要么`用户`.资源组类型影响可分配给组的优先级值的范围，如下所述。该属性与允许的优先级差异一起使系统线程能够被识别，从而保护它们免受用户线程对 CPU 资源的争用。

    系统和用户线程对应于性能模式中列出的后台和前台线程[`线程`](performance-schema-threads-table.html)桌子。

    这些属性在资源组创建时定义，之后可以随时修改：

-   CPU 亲和性是资源组可以使用的一组虚拟 CPU。亲和性可以是可用 CPU 的任何非空子集。如果一个组没有亲缘关系，它可以使用所有可用的 CPU。

-   线程优先级是分配给资源组的线程的执行优先级。优先级值范围从 -20（最高优先级）到 19（最低优先级）。系统和用户组的默认优先级均为 0。

    系统组的优先级高于用户组，确保用户线程的优先级永远不会高于系统线程：

    -   对于系统资源组，允许的优先级范围是 -20 到 0。

    -   对于用户资源组，允许的优先级范围是 0 到 19。

-   每个组都可以启用或禁用，让管理员可以控制线程分配。线程只能分配给启用的组。

#### 资源组管理

[](<>)

默认有一个系统组和一个用户组，命名为`SYS_default`和`USR_default`， 分别。不能删除这些默认组，也不能修改它们的属性。每个默认组没有 CPU 关联性和优先级 0。

新创建的系统和用户线程被分配给`SYS_default`和`USR_default`组，分别。

对于用户定义的资源组，所有属性都在组创建时分配。创建组后，可以修改其属性，但名称和类型属性除外。

要创建和管理用户定义的资源组，请使用以下 SQL 语句：

-   [`创建资源组`](create-resource-group.html)创建一个新组。看[第 13.7.2.2 节，“CREATE RESOURCE GROUP 语句”](create-resource-group.html).

-   [`更改资源组`](alter-resource-group.html)修改现有组。看[第 13.7.2.1 节，“ALTER RESOURCE GROUP 语句”](alter-resource-group.html).

-   [`删除资源组`](drop-resource-group.html)删除现有组。看[第 13.7.2.3 节，“DROP RESOURCE GROUP 语句”](drop-resource-group.html).

    这些声明要求[`RESOURCE_GROUP_ADMIN`](privileges-provided.html#priv_resource-group-admin)特权。

    要管理资源组分配，请使用以下功能：

-   [`设置资源组`](set-resource-group.html)将线程分配给一个组。看[第 13.7.2.4 节，“SET RESOURCE GROUP 语句”](set-resource-group.html).

-   这[`RESOURCE_GROUP`](optimizer-hints.html#optimizer-hints-resource-group)优化器提示将单个语句分配给一个组。看[第 8.9.3 节，“优化器提示”](optimizer-hints.html).

    这些操作需要[`RESOURCE_GROUP_ADMIN`](privileges-provided.html#priv_resource-group-admin)要么[`RESOURCE_GROUP_USER`](privileges-provided.html#priv_resource-group-user)特权。

    资源组定义存储在`资源组`数据字典表，以便组在服务器重新启动时保持不变。因为`资源组`是数据字典的一部分，用户不能直接访问。资源组信息可使用[`INFORMATION_SCHEMA.RESOURCE_GROUPS`](information-schema-resource-groups-table.html)表，它被实现为数据字典表的视图。看[第 26.3.26 节，“信息\_架构资源\_组表”](information-schema-resource-groups-table.html).

    最初，[`RESOURCE_GROUPS`](information-schema-resource-groups-table.html)表有这些行描述默认组：


```
mysql> SELECT * FROM INFORMATION_SCHEMA.RESOURCE_GROUPS\G
*************************** 1. row ***************************
   RESOURCE_GROUP_NAME: USR_default
   RESOURCE_GROUP_TYPE: USER
RESOURCE_GROUP_ENABLED: 1
              VCPU_IDS: 0-3
       THREAD_PRIORITY: 0
*************************** 2. row ***************************
   RESOURCE_GROUP_NAME: SYS_default
   RESOURCE_GROUP_TYPE: SYSTEM
RESOURCE_GROUP_ENABLED: 1
              VCPU_IDS: 0-3
       THREAD_PRIORITY: 0
```

这`线程优先级`值为 0，表示默认优先级。这`VCPU_IDS`值显示包含所有可用 CPU 的范围。对于默认组，显示的值因 MySQL 服务器运行的系统而异。

前面的讨论提到了一个涉及名为的资源组的场景`批`管理不需要以高优先级执行的批处理作业的执行。要创建这样的组，请使用类似于以下的语句：

```
CREATE RESOURCE GROUP Batch
  TYPE = USER
  VCPU = 2-3            -- assumes a system with at least 4 CPUs
  THREAD_PRIORITY = 10;
```

要验证资源组是否按预期创建，请检查[`RESOURCE_GROUPS`](information-schema-resource-groups-table.html)桌子：

```
mysql> SELECT * FROM INFORMATION_SCHEMA.RESOURCE_GROUPS
       WHERE RESOURCE_GROUP_NAME = 'Batch'\G
*************************** 1. row ***************************
   RESOURCE_GROUP_NAME: Batch
   RESOURCE_GROUP_TYPE: USER
RESOURCE_GROUP_ENABLED: 1
              VCPU_IDS: 2-3
       THREAD_PRIORITY: 10
```

如果`线程优先级`值为 0 而不是 10，请检查您的平台或系统配置是否限制了资源组能力；看[资源组限制](resource-groups.html#resource-group-restrictions).

将线程分配给`批`组，这样做：

```
SET RESOURCE GROUP Batch FOR thread_id;
```

此后，命名线程中的语句执行`批`群资源。

如果一个会话自己的当前线程应该在`批`组，在会话中执行此语句：

```
SET RESOURCE GROUP Batch;
```

此后，会话中的语句执行`批`群资源。

使用`批`组，使用[`RESOURCE_GROUP`](optimizer-hints.html#optimizer-hints-resource-group)优化提示：

```
INSERT /*+ RESOURCE_GROUP(Batch) */ INTO t2 VALUES(2);
```

分配给的线程`批`group 使用其资源执行，可以根据需要进行修改：

-   对于系统高负载的时候，减少分配给组的 CPU 数量，降低其优先级，或（如图所示）两者：

    ```
    ALTER RESOURCE GROUP Batch
      VCPU = 3
      THREAD_PRIORITY = 19;
    ```

-   对于系统负载较轻的时候，增加分配给组的 CPU 数量，提高其优先级，或（如图所示）两者：

    ```
    ALTER RESOURCE GROUP Batch
      VCPU = 0-3
      THREAD_PRIORITY = 0;
    ```

#### 资源组复制

[](<>)

资源组管理在其所在的服务器上是本地的。资源组 SQL 语句和对`资源组`数据字典表不会写入二进制日志，也不会被复制。

#### 资源组限制

[](<>)[](<>)

在某些平台或 MySQL 服务器配置上，资源组不可用或有限制：

-   如果安装了线程池插件，则资源组不可用。

    [](<>)

-   资源组在 macOS 上不可用，它没有提供用于将 CPU 绑定到线程的 API。

-   在 FreeBSD 和 Solaris 上，资源组线程优先级被忽略。（实际上，所有线程都以优先级 0 运行。）尝试更改优先级会导致警告：

    ```
    mysql> ALTER RESOURCE GROUP abc THREAD_PRIORITY = 10;
    Query OK, 0 rows affected, 1 warning (0.18 sec)

    mysql> SHOW WARNINGS;
    +---------+------+-------------------------------------------------------------+
    | Level   | Code | Message                                                     |
    +---------+------+-------------------------------------------------------------+
    | Warning | 4560 | Attribute thread_priority is ignored (using default value). |
    +---------+------+-------------------------------------------------------------+
    ```

-   在 Linux 上，资源组线程优先级被忽略，除非`CAP_SYS_NICE`能力已设置。授予`CAP_SYS_NICE`进程的能力支持一系列特权；咨询<http://man7.org/linux/man-pages/man7/capabilities.7.html>完整列表。启用此功能时请小心。

    在使用 systemd 和内核支持环境功能（Linux 4.3 或更高版本）的 Linux 平台上，推荐的启用方式`CAP_SYS_NICE`能力是修改 MySQL 服务文件并保留[**mysqld**](mysqld.html)二进制未修改。要调整 MySQL 的服务文件，请使用以下过程：

    1.  为您的平台运行适当的命令：

        -   Oracle Linux、Red Hat 和 Fedora 系统：

            ```
            $> sudo systemctl edit mysqld
            ```

        -   SUSE、Ubuntu 和 Debian 系统：

            ```
            $> sudo systemctl edit mysql
            ```

    2.  使用编辑器，将以下文本添加到服务文件：

        ```
        [Service]
        AmbientCapabilities=CAP_SYS_NICE
        ```

    3.  重启 MySQL 服务。

        如果您无法启用`CAP_SYS_NICE`如刚刚描述的功能，它可以使用手动设置**设置上限**命令，指定路径名[**mysqld**](mysqld.html)可执行文件（这需要**须藤**使用权）。您可以使用检查功能**盖帽**.例如：

    ```
    $> sudo setcap cap_sys_nice+ep /path/to/mysqld
    $> getcap /path/to/mysqld
    /path/to/mysqld = cap_sys_nice+ep
    ```

    作为安全措施，限制执行[**mysqld**](mysqld.html)二进制到`根`用户和用户`mysql`组成员：

    ```
    $> sudo chown root:mysql /path/to/mysqld
    $> sudo chmod 0750 /path/to/mysqld
    ```

    重要的

    如果手动使用**设置上限**是必需的，必须在每次重新安装后执行。

-   在 Windows 上，线程以五个线程优先级之一运行。-20 到 19 的资源组线程优先级范围映射到下表所示的这些级别。

    [](<>)

    **表 5.6 Windows 上的资源组线程优先级**

    | 优先范围 | Windows 优先级 |
    | ---- | ----------- |
    | -20 到 -10 | `THREAD_PRIORITY_HIGHEST` |
    | -9比-1 | `THREAD_PRIORITY_ABOVE_NORMAL` |
    | 0 | `THREAD_PRIORITY_NORMAL` |
    | 1 到 10 | `THREAD_PRIORITY_BELOW_NORMAL` |
    | 11 至 19 | `THREAD_PRIORITY_LOWEST` |
