

 从补丁 198 开始，Amazon Redshift 将不再支持创建新的 Python UDF。现有的 Python UDF 将继续正常运行至 2026 年 6 月 30 日。有关更多信息，请参阅[博客文章](https://aws.amazon.com/blogs/big-data/amazon-redshift-python-user-defined-functions-will-reach-end-of-support-after-june-30-2026/)。

# SQL 命令
<a name="iceberg-writes-sql-syntax"></a>

Amazon Redshift 中的 Apache Iceberg 表提供了一种强大的方法用于管理数据湖中的大型分析数据集。这些表支持 ACID 事务、架构发展和时间旅行功能，同时保持了高性能的分析工作负载。使用 Apache Iceberg 表，您可以高效地组织和分区数据，控制文件格式和文件压缩，并与其他 AWS 服务无缝集成。

您可以使用 `CREATE TABLE ... USING ICEBERG` 和 `CREATE TABLE ... USING ICEBERG AS SELECT` 命令创建分区和未分区的 Iceberg 表。您可以使用外部架构表示法 (`external_schema.table_name`) 或三部分表示法 (`"catalog_name".database_name.table_name`) 引用 Iceberg 表。本部分中的示例将演示这两种方法。

创建表之后，您可以使用标准 `INSERT` 命令添加数据。请记住，虽然 Amazon Redshift 可处理许多 Iceberg 数据类型，但在插入信息时，您可能需要转换某些数据格式。

您可以使用 `SHOW TABLES` 命令查看 Iceberg 表。如果要从 AWS Glue Data Catalog 中移除表，您可以使用 `DROP TABLE` 命令。请注意，这只会移除表注册信息。实际数据仍保留在存储中，直到您单独将其删除。

Iceberg 表目前尚不支持所有其他 SQL 语句，例如 `DELETE`、`UPDATE`、`MERGE` 和 `ALTER TABLE`。

以下部分演示了在 Amazon Redshift 中创建、插入和管理 Iceberg 表的语法。

**Contents**
+ [CREATE TABLE](#iceberg-writes-create-table)
+ [CREATE TABLE AS SELECT](#iceberg-writes-create-table-as-select)
+ [SHOW TABLE](#iceberg-writes-show-table)
+ [INSERT INTO](#iceberg-writes-insert-into)
+ [DROP TABLE](#iceberg-writes-drop-table)

## CREATE TABLE
<a name="iceberg-writes-create-table"></a>

```
CREATE TABLE [IF NOT EXISTS] <external_schema>.<table_name> (
  column_name data_type [, ...]
)
USING ICEBERG
[LOCATION 's3://your-bucket-name/prefix/']
[PARTITIONED BY [[column_name | transform_function]], ...]
[TABLE PROPERTIES ('compression_type'='<compression_value>')]
```

对于 S3 表存储桶，您也可以使用三部分表示法。

```
CREATE TABLE "<table_bucket_name>@s3tablescatalog".<database_name>.<table_name> (
  column_name data_type [, ...]
)
USING ICEBERG
[PARTITIONED BY [[column_name | transform_function]], ...]
[TABLE PROPERTIES ('compression_type'='<compression_value>')]
```

请注意，`<external_schema>` 必须是创建外部表时使用的现有外部架构名称。有关如何创建和管理外部架构的更多信息，请参阅 Amazon Redshift 文档中的 [CREATE EXTERNAL SCHEMA](https://docs.aws.amazon.com/redshift/latest/dg/r_CREATE_EXTERNAL_SCHEMA.html)。

`LOCATION` 子句定义此新创建的 Iceberg 表的表位置。对于 Amazon S3 表，无法指定 `LOCATION`，因为表的位置由 Amazon S3 表目录 (`s3tablescatalog`) 确定。

在所有其他情况下，`LOCATION` 均必填，并且应为空位置，也就是说没有现有的 Amazon S3 对象共享了这个相同的存储桶和前缀。请注意，Amazon S3 存储桶必须与 Amazon Redshift 集群位于同一区域。

但是，AWS 提供了一种方法，用于将存储在一个 AWS 区域的 AWS Glue Data Catalog 中的 Iceberg 表的数据复制到不同 AWS 区域，这样您就可以将写入操作复制到不同的区域。有关更多信息，请参阅[跨 AWS 区域复制数据](https://docs.aws.amazon.com/prescriptive-guidance/latest/apache-iceberg-on-aws/best-practices-workloads.html#workloads-replication)。

`PARTITIONED BY` 定义 Iceberg 表分区。Amazon Redshift 支持所有 Iceberg v2 分区转换，但 `void` 除外。以下是当前支持的转换列表：
+ **身份**
+ **bucket[N]**
+ **truncate[W]**
+ **年**
+ **个月**
+ **day**
+ **小时**

有关这些转换的完整定义以及兼容的数据类型，请参阅 Apache Iceberg 文档中的 [Partition Transforms](https://iceberg.apache.org/spec/#partition-transforms)。

`PARTITIONED BY` 支持多个级别的分区。例如，您可以运行以下命令：

```
CREATE TABLE ...
USING ICEBERG
LOCATION ...
PARTITIONED BY (bucket(16, id), year(ship_date));
```

但是，Amazon Redshift 不支持在多个转换中使用单列。例如，不支持以下语法。

```
CREATE TABLE ...
USING ICEBERG
LOCATION ...
PARTITIONED BY (bucket(16, ship_date), year(ship_date));
```

`TABLE PROPERTIES` 子句定义此 Iceberg 表的额外表属性。唯一支持的表属性是 `compression_type`，该属性定义默认的 Parquet 数据文件压缩。如果未指定该项，则使用 `snappy` 作为压缩编解码器。`compression_type` 的可能值包括 `zstd`、`brotli`、`gzip`、`snappy` 和 `uncompressed`。

**注意**  
Iceberg 表不支持 `CREATE TABLE ... LIKE ...`。此外，Iceberg 表不支持列约束和列属性，这与 RMS 表不同。

或者，您可以使用 `CREATE TABLE AS SELECT` 在单个操作中创建和填充 Iceberg 表：

## CREATE TABLE AS SELECT
<a name="iceberg-writes-create-table-as-select"></a>

```
CREATE TABLE <external_schema>.<table_name> [(
  column_name[, ...]
)]
USING ICEBERG
[LOCATION 's3://your-bucket-name/prefix/']
[PARTITIONED BY [[column_name | transform_function]], ...]
[TABLE PROPERTIES ('compression_type'='<compression-value>')]
AS
SELECT query
```

您也可以使用三部分表示法在自动挂载目录中创建表：

```
CREATE TABLE "<catalog_name>".<database_name>.<table_name> [(
  column_name[, ...]
)]
USING ICEBERG
[LOCATION 's3://your-bucket-name/prefix/']
[PARTITIONED BY [[column_name | transform_function]], ...]
[TABLE PROPERTIES ('compression_type'='<compression-value>')]
AS
SELECT query
```

这与 `CREATE TABLE` 语句类似，不同之处在于 `CREATE` 后跟 `SELECT` 语句，用于在表中填充 `SELECT` 查询结果。

此处的 `CREATE TABLE` 子句不再允许您指定数据类型，因为列的数据类型将由 `SELECT` 查询决定。

如果 `SELECT` 查询因任何原因失败，则此查询将失败，并且不会创建 Iceberg 表。

您可以使用 `SHOW TABLE` 查看 Iceberg 表的结构：

## SHOW TABLE
<a name="iceberg-writes-show-table"></a>

```
SHOW TABLE <external_schema>.<table_name>
```

您还可以对自动挂载目录使用三部分表示法：

```
SHOW TABLE "<catalog_name>".<database_name>.<table_name>
```

`SHOW TABLE` 显示 Iceberg 表的 `CREATE TABLE` 语句。该命令将根据表的类型显示相应的结果。以下是 Iceberg 表的 `SHOW TABLE` 输出示例：

```
CREATE TABLE my_schema.items (id int, price decimal(5, 2))
USING ICEBERG
LOCATION 's3://my_s3_bucket/items/'
PARTITIONED BY (bucket(16, id))
TABLE PROPERTIES ('compression_type'='snappy')
```

**注意**  
对于 Amazon S3 表，由于表位置由 Amazon S3 表目录管理，因此 `SHOW TABLE` 结果中将省略 `LOCATION` 子句。

创建表后，您可以使用 `INSERT INTO` 添加数据：

## INSERT INTO
<a name="iceberg-writes-insert-into"></a>

```
INSERT INTO <external_schema>.<table_name> [(column_name [, ...])] VALUES (...)
INSERT INTO <external_schema>.<table_name> [(column_name [, ...])] (SELECT query)

-- Using three-part notation for S3 table buckets:
INSERT INTO "<table_bucket_name>@s3tablescatalog".<database_name>.<table_name> [(column_name [, ...])] VALUES (...)
INSERT INTO "<table_bucket_name>@s3tablescatalog".<database_name>.<table_name> [(column_name [, ...])] (SELECT query)
```

您可以使用上述语法对现有 Iceberg 表执行 `INSERT INTO`。如果使用 `VALUES` 子句，则按 `column_name` 列出您为列提供的值，如果省略了 `column_name` 部分，则提供所有列的值。

将数据插入分区表时，将根据预定义的分区规范分布新行。如果 `SELECT` 查询由于任何原因失败，则查询将失败，并且不向 Iceberg 表中插入任何数据。

您可以对并非由 Amazon Redshift 创建的 Iceberg 表执行 `INSERT INTO` 操作。但是，这里有一些限制：
+ 该表必须是 Iceberg v2 表。
+ 该表必须使用 Parquet 作为默认数据格式。
+ 该表不可将元数据压缩设置为 True。
+ 该表不可启用写入-审计-发布（WAP）。

要从目录中删除 Iceberg 表，请使用 `DROP TABLE` 命令：

## DROP TABLE
<a name="iceberg-writes-drop-table"></a>

```
DROP TABLE <external_schema>.<table_name>
```

您还可以对自动挂载目录使用三部分表示法：

```
DROP TABLE "<catalog_name>.<database_name>.<table_name>
```

使用 DROP 命令删除 Iceberg 表是仅对元数据执行的操作。如果表是 Amazon S3 表，则它会从 AWS Glue Data Catalog 和 Amazon S3 表目录中删除该表条目。Amazon Redshift 不会清理或删除表位置下的任何现有数据文件或元数据文件。您可以使用 AWS Glue 和 Amazon S3 表中的功能来移除孤立文件。对于 AWS Glue，请参阅[删除孤立文件](https://docs.aws.amazon.com/glue/latest/dg/orphan-file-deletion.html)。对于 Amazon S3 表，请参阅[表维护](https://docs.aws.amazon.com/AmazonS3/latest/userguide/s3-tables-maintenance.html)。