> ## Documentation Index
> Fetch the complete documentation index at: https://private-7c7dfe99-detect-table-modification.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# analyzer_compatibility_* 会话设置

> ClickHouse 在 analyzer_compatibility_* 自动生成分组中的会话设置。

export const VersionHistory = ({rows = []}) => {
  if (rows.length === 0) {
    return null;
  }
  const headers = ["版本", "默认值", "注释"];
  const border = "1px solid rgba(128, 128, 128, 0.3)";
  const cell = {
    border,
    padding: "0.25rem 0.5rem",
    textAlign: "start",
    verticalAlign: "top"
  };
  return <details className="not-prose" style={{
    border,
    borderRadius: "0.5rem",
    margin: "0.5rem 0",
    padding: "0.5rem 0.75rem",
    fontSize: "0.8125rem",
    lineHeight: "1.125rem"
  }}>
      <summary style={{
    cursor: "pointer",
    fontWeight: 600,
    opacity: 0.72
  }}>
        版本历史
      </summary>
      <table style={{
    borderCollapse: "collapse",
    width: "100%",
    margin: "0.5rem 0 0"
  }}>
        <thead>
          <tr>
            {headers.map(header => <th key={header} style={{
    ...cell,
    fontWeight: 600,
    opacity: 0.72
  }}>
                {header}
              </th>)}
          </tr>
        </thead>
        <tbody>
          {rows.map((row, row_index) => <tr key={row.id ?? row_index}>
              {(row.items ?? []).map((item, item_index) => <td key={item_index} style={{
    ...cell,
    overflowWrap: "anywhere"
  }}>
                  {item?.label}
                </td>)}
            </tr>)}
        </tbody>
      </table>
    </details>;
};

export const SettingsInfoBlock = ({type, default_value, changeable_without_restart}) => {
  return <div className="not-prose" style={{
    display: "flex",
    flexWrap: "wrap",
    alignItems: "baseline",
    columnGap: "0.5rem",
    rowGap: "0.125rem",
    margin: "0.375rem 0",
    fontSize: "0.8125rem",
    lineHeight: "1.125rem"
  }}>
      <div style={{
    fontWeight: 600,
    opacity: 0.72
  }}>类型</div>
      <div style={{
    overflowWrap: "anywhere"
  }}>{type}</div>
      <div style={{
    fontWeight: 600,
    opacity: 0.72,
    marginInlineStart: "0.5rem"
  }}>默认值</div>
      <div style={{
    overflowWrap: "anywhere"
  }}>{default_value}</div>
      {changeable_without_restart && <div style={{
    fontWeight: 600,
    opacity: 0.72,
    marginInlineStart: "0.5rem"
  }}>
          无需重启即可更改
        </div>}
      {changeable_without_restart && <div style={{
    overflowWrap: "anywhere"
  }}>
          {changeable_without_restart}
        </div>}
    </div>;
};

这些设置可在 [system.settings](/zh/reference/system-tables/settings) 中找到，并根据 [源代码](https://github.com/ClickHouse/ClickHouse/blob/master/src/Core/Settings.cpp) 自动生成。

<div id="analyzer_compatibility_allow_compound_identifiers_in_unflatten_nested">
  ## analyzer\_compatibility\_allow\_compound\_identifiers\_in\_unflatten\_nested
</div>

<SettingsInfoBlock type="Bool" default_value="1" />

<VersionHistory rows={[{"id": "row-1","items": [{"label": "25.8"},{"label": "1"},{"label": "新设置。"}]}]} />

允许向 Nested 中添加复合标识符。这是一项兼容性设置，因为它会改变查询结果。禁用时，`SELECT a.b.c FROM table ARRAY JOIN a` 将无法工作，而 `SELECT a FROM table` 的 `Nested a` 结果中也不会包含 `a.b.c` 列。

<div id="analyzer_compatibility_allow_non_aggregate_in_having">
  ## analyzer\_compatibility\_allow\_non\_aggregate\_in\_having
</div>

<SettingsInfoBlock type="Bool" default_value="0" />

<VersionHistory rows={[{"id": "row-1","items": [{"label": "26.7"},{"label": "0"},{"label": "新的兼容性设置。启用后，analyzer 会模拟旧版将非聚合 AND 合取项从 `HAVING` 重写到 `WHERE` 的行为，而不是抛出 `NOT_AN_AGGREGATE`。"}]}]} />

启用后，analyzer 会模拟旧版行为：将非聚合 AND 合取项从 `HAVING` 移到 `WHERE`，而不是抛出 `NOT_AN_AGGREGATE`。默认行为是按标准进行拒绝；此设置可作为迁移辅助，用于处理那些曾被旧版 analyzer (`enable_analyzer = 0`) 静默接受的查询。包含聚合、`grouping` 或非确定性函数的合取项会保留在 `HAVING` 中。如果任一合取项包含窗口函数或有状态函数 (例如 `rowNumberInBlock`) ，则整个 `HAVING` 的此类重写都会被禁用，这与旧版 `PredicateExpressionsOptimizer` 的行为一致。当 `GROUP BY` 使用 `WITH CUBE`、`WITH ROLLUP`、`WITH TOTALS` 或 `GROUPING SETS` 时，该设置同样会被忽略。

<div id="analyzer_compatibility_apply_final_to_all_joined_tables">
  ## analyzer\_compatibility\_apply\_final\_to\_all\_joined\_tables
</div>

<SettingsInfoBlock type="Bool" default_value="0" />

<VersionHistory rows={[{"id": "row-1","items": [{"label": "26.8"},{"label": "0"},{"label": "master 上新增的设置（默认 false，即修复后的行为）。行为变更本身记录在 26.6；针对旧发布分支的回移引入（默认 true）记录在 26.4。"}]}, {"id": "row-2","items": [{"label": "26.6"},{"label": "0"},{"label": "修复了 analyzer 中的一个 bug：JOIN 最左侧表上的 FINAL 被错误地同时应用于其他参与 JOIN 的表。previous_value=true，因此使用早于 26.6 版本的 `compatibility` 时会恢复旧行为。"}]}, {"id": "row-3","items": [{"label": "26.4"},{"label": "1"},{"label": "新增兼容性设置，用于控制 JOIN 最左侧表上的 FINAL 是否应用于其他参与 JOIN 的表。为回移到早于 26.6 的版本而引入，默认值为 true（旧行为）。"}]}]} />

恢复 26.6 之前版本的行为：JOIN 最左侧表上指定的 `FINAL` 修饰符会被错误地同时应用于所有其他参与 JOIN 的表 (适用于支持 `FINAL` 的引擎，例如 `ReplacingMergeTree`) 。默认情况下，`FINAL` 仅应用于其所在的表。若查询依赖旧行为，可启用此设置以保持兼容；建议的修复方法是在每个需要的表上显式指定 `FINAL`。

可能的值：

* 0 - `FINAL` 仅应用于指定它的表。
* 1 - JOIN 最左侧表上的 `FINAL` 会应用于所有参与 JOIN 的表。

<div id="analyzer_compatibility_join_using_top_level_identifier">
  ## analyzer\_compatibility\_join\_using\_top\_level\_identifier
</div>

<SettingsInfoBlock type="Bool" default_value="0" />

<VersionHistory rows={[{"id": "row-1","items": [{"label": "24.3"},{"label": "0"},{"label": "强制从投影中解析 JOIN USING 里的标识符"}]}]} />

强制从投影中解析 JOIN USING 里的标识符 (例如，在 `SELECT a + 1 AS b FROM t1 JOIN t2 USING (b)` 中，JOIN 将根据 `t1.a + 1 = t2.b` 执行，而不是 `t1.b = t2.b`) 。还会考虑 SELECT 列表中子表达式上定义的别名 (例如，在 `SELECT uniqExact(a + 1 AS b) FROM t1 JOIN t2 USING (b)` 中，JOIN 将根据 `t1.a + 1 = t2.b` 执行)。当匹配的别名定义在 SELECT 列表中的子表达式上而非顶层别名时，将对此查询禁用并行副本。对于发送到远程服务器的查询 (`Distributed` 表、`remote` 表函数) ，仅当标识符在远程服务器上完全无法解析时，此类查询才会因异常被拒绝；如果该别名遮蔽了左表中的实际列，远程服务器会改为基于该列执行 JOIN，因此结果可能与本地执行不同。

<div id="analyzer_compatibility_multiple_joins_qualify_column_names">
  ## analyzer\_compatibility\_multiple\_joins\_qualify\_column\_names
</div>

<SettingsInfoBlock type="Bool" default_value="0" />

<VersionHistory rows={[{"id": "row-1","items": [{"label": "26.8"},{"label": "0"},{"label": "新增兼容性设置。启用后，对于 FROM 子句中包含两个或更多 JOIN 的查询，analyzer 会模拟旧版 analyzer 对结果列名的限定方式。"}]}]} />

启用后，如果查询的 `FROM` 子句包含两个或更多 `JOIN` (以逗号分隔的表也计入；`ARRAY JOIN` 不计入) ，analyzer 会按旧版 analyzer 重写多 JOIN 查询时的方式为结果列命名：

* 通过展开 `*`、`<table>.*` 或 `COLUMNS('<regexp>')` 生成的列，名称格式为 `<alias-or-table>.<column>` (限定符优先使用表表达式的别名；若无别名，则使用不含数据库名的表名；否则使用 CTE 名称；未设别名的已连接子查询中的列不加限定符) 。有两类列会保留不带限定符的名称，因为它们属于 JOIN 而非某个单独的表表达式：由 `ARRAY JOIN` 生成的列，以及由 `JOIN ... USING` 合并的键。因此，`SELECT ll.arr` 或 `SELECT ll.k` 等外部引用在这两种形态下无法解析；
* 标识符列表形式的 `COLUMNS(col1, col2)` 并非匹配器展开：每一列都严格保留标识符原有的写法，因此 `COLUMNS(x)` 生成 `x`，而 `COLUMNS(a.x)` 生成 `a.x`；
* `SELECT` 列表中未使用别名的列引用会严格保留原有写法 (例如，即使 `x` 不存在歧义，`SELECT a.x` 生成的列名仍为 `a.x`) 。

这样，外部查询便可通过限定名称引用此类列，例如：

```sql theme={null}
SELECT ll.Date FROM (SELECT * FROM t AS ll LEFT JOIN t1 ON ll.k = t1.k LEFT JOIN t2 ON ll.k = t2.k);
```

仅在启用 analyzer 时生效 (`enable_analyzer = 1`) 。

<div id="analyzer_compatibility_prefer_alias_over_subcolumn">
  ## analyzer\_compatibility\_prefer\_alias\_over\_subcolumn
</div>

<SettingsInfoBlock type="Bool" default_value="0" />

<VersionHistory rows={[{"id": "row-1","items": [{"label": "26.6"},{"label": "0"},{"label": "新增兼容性设置"}]}]} />

当像 `b.id` 这样的多部分标识符既可能表示别名为 `b` 的表中的列 `id`，也可能表示另一列的 Tuple 子列 `b.id` 时，优先按别名前缀来解析 (即 `b` 的列 `id`) 。默认情况下，analyzer 会优先解析为子列。启用此设置可与旧版 analyzer 的解析方式保持一致。
