## 9.6 查询属性

[](<>)

SQL 语句最明显的部分是语句的文本。从 MySQL 8.0.23 开始，客户端还可以定义查询属性，以应用于发送到服务器执行的下一条语句：

-   属性是在发送语句之前定义的。

-   属性存在直到语句执行结束，此时属性集被清除。

-   虽然存在属性，但可以在服务器端访问它们。

    可以使用查询属性的方式示例：

-   Web 应用程序生成生成数据库查询的页面，并且对于每个查询都必须跟踪生成它的页面的 URL。

-   应用程序通过每个查询传递额外的处理信息，以供插件使用，例如审计插件或查询重写插件。

    MySQL 支持这些功能，而无需使用变通方法，例如查询字符串中包含的特殊格式的注释。本节的其余部分描述如何使用查询属性支持，包括必须满足的先决条件。

-   [定义和访问查询属性](query-attributes.html#using-query-attributes)

-   [使用查询属性的先决条件](query-attributes.html#query-attributes-prerequisites)

-   [查询属性可加载函数](query-attributes.html#query-attribute-functions)

### 定义和访问查询属性

使用 MySQL C API 的应用程序通过调用[`mysql_bind_param()`](https://dev.mysql.com/doc/c-api/8.0/en/mysql-bind-param.html)功能。看[mysql\_绑定\_参数（）](https://dev.mysql.com/doc/c-api/8.0/en/mysql-bind-param.html).其他 MySQL 连接器也可能提供查询属性支持。请参阅各个连接器的文档。

这[**mysql**](mysql.html)客户有一个`查询属性`最多可以定义 32 对属性名称和值的命令。看[第 4.5.1.2 节，“mysql 客户端命令”](mysql-commands.html).

查询属性名称使用由[`character_set_client`](server-system-variables.html#sysvar_character_set_client)系统变量。

要访问已定义属性的 SQL 语句中的查询属性，请安装`查询属性`组件如中所述[使用查询属性的先决条件](query-attributes.html#query-attributes-prerequisites).该组件实现了一个[`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string)可加载函数，它接受属性名称参数并将属性值作为字符串返回，或者`空值`如果属性不存在。看[查询属性可加载函数](query-attributes.html#query-attribute-functions).

以下示例使用[**mysql**](mysql.html)客户`查询属性`命令来定义属性名称/值对，以及[`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string)按名称访问属性值的函数。

这个例子定义了两个名为`n1`和`n2`.首先`选择`展示了如何检索这些属性，还演示了检索不存在的属性 (`n3`) 返回`空值`.第二`选择`表明属性不会跨语句持续存在。

```
mysql> query_attributes n1 v1 n2 v2;
mysql> SELECT
         mysql_query_attribute_string('n1') AS 'attr 1',
         mysql_query_attribute_string('n2') AS 'attr 2',
         mysql_query_attribute_string('n3') AS 'attr 3';
+--------+--------+--------+
| attr 1 | attr 2 | attr 3 |
+--------+--------+--------+
| v1     | v2     | NULL   |
+--------+--------+--------+

mysql> SELECT
         mysql_query_attribute_string('n1') AS 'attr 1',
         mysql_query_attribute_string('n2') AS 'attr 2';
+--------+--------+
| attr 1 | attr 2 |
+--------+--------+
| NULL   | NULL   |
+--------+--------+
```

如第二个所示`选择`语句，在给定语句之前定义的属性仅对该语句可用，并在语句执行后清除。要跨多个语句使用属性值，请将其分配给变量。以下示例显示了如何执行此操作，并说明属性值可通过变量在后续语句中使用，但不能通过调用[`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string)：

```
mysql> query_attributes n1 v1 n2 v2;
mysql> SET
         @attr1 = mysql_query_attribute_string('n1'),
         @attr2 = mysql_query_attribute_string('n2');

mysql> SELECT
         @attr1, mysql_query_attribute_string('n1') AS 'attr 1',
         @attr2, mysql_query_attribute_string('n2') AS 'attr 2';
+--------+--------+--------+--------+
| @attr1 | attr 1 | @attr2 | attr 2 |
+--------+--------+--------+--------+
| v1     | NULL   | v2     | NULL   |
+--------+--------+--------+--------+
```

还可以通过将属性存储在表中来保存属性以供以后使用：

```
mysql> CREATE TABLE t1 (c1 CHAR(20), c2 CHAR(20));

mysql> query_attributes n1 v1 n2 v2;
mysql> INSERT INTO t1 (c1, c2) VALUES(
         mysql_query_attribute_string('n1'),
         mysql_query_attribute_string('n2')
       );

mysql> SELECT * FROM t1;
+------+------+
| c1   | c2   |
+------+------+
| v1   | v2   |
+------+------+
```

查询属性受以下限制和限制：

-   如果在将语句发送到服务器执行之前发生了多个属性定义操作，则最近的定义操作将应用并替换之前操作中定义的属性。

-   如果使用相同的名称定义了多个属性，则尝试检索属性值会产生未定义的结果。

-   用空名称定义的属性不能按名称检索。

-   属性不适用于用[`准备`](prepare.html).

-   这[`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string)函数不能在 DDL 语句中使用。

-   属性不会被复制。调用的语句[`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string)函数不会在所有服务器上获得相同的值。

### 使用查询属性的先决条件

要访问已定义属性的 SQL 语句中的查询属性，`查询属性`必须安装组件。使用以下语句执行此操作：

```
INSTALL COMPONENT "file://component_query_attributes";
```

组件安装是一次性操作，不需要每次服务器启动都完成。[`安装组件`](install-component.html)加载组件，并将其注册到`mysql.component`系统表，使其在随后的服务器启动期间被加载。

这`查询属性`组件访问查询属性以实现[`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string)功能。看[第 5.5.4 节，“查询属性组件”](query-attribute-components.html).

要卸载`查询属性`组件，请使用以下语句：

```
UNINSTALL COMPONENT "file://component_query_attributes";
```

[`卸载组件`](uninstall-component.html)卸载组件，并从`mysql.component`系统表，以使其在后续服务器启动期间不被加载。

因为安装和卸载`查询属性`组件安装和卸载[`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string)组件实现的功能，不需要使用`创建函数`要么`拖放功能`这样做。

### 查询属性可加载函数

-   [](<>) [`mysql_query_attribute_string(*`姓名`*)`](query-attributes.html#function_mysql-query-attribute-string)

    [](<>)

    应用程序可以定义应用于发送到服务器的下一个查询的属性。这[`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string)从 MySQL 8.0.23 开始可用的函数，在给定属性名称的情况下，将属性值作为字符串返回。此功能使查询能够访问和合并适用于它的属性的值。

    [`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string)通过安装`查询属性`零件。看[第 9.6 节，“查询属性”](query-attributes.html)，其中还讨论了查询属性的用途和用途。

    论据：

    -   *`姓名`*: 属性名称。

        返回值：

        将属性值作为成功的字符串返回，或`空值`如果属性不存在。

        例子：

        以下示例使用[**mysql**](mysql.html)客户`查询属性`命令定义可以通过以下方式检索的查询属性[`mysql_query_attribute_string()`](query-attributes.html#function_mysql-query-attribute-string).这`选择`表明检索一个不存在的属性 (`n3`) 返回`空值`.

    ```
    mysql> query_attributes n1 v1 n2 v2;
    mysql> SELECT
        ->   mysql_query_attribute_string('n1') AS 'attr 1',
        ->   mysql_query_attribute_string('n2') AS 'attr 2',
        ->   mysql_query_attribute_string('n3') AS 'attr 3';
    +--------+--------+--------+
    | attr 1 | attr 2 | attr 3 |
    +--------+--------+--------+
    | v1     | v2     | NULL   |
    +--------+--------+--------+
    ```
