当您需要访问存储在Hologres中的数据时,MaxCompute支持使用外部表访问Hologres数据源数据,无需导入数据至MaxCompute中,实现快速查询Hologres数据。本文为您介绍如何在外部表建表语句中指定Hologres数据源、STS认证信息或打开双签名开关、映射目标表、JDBC驱动信息,来创建Hologres外部表。
背景信息
Hologres是兼容PostgreSQL协议的实时交互式分析数据仓库,在底层与MaxCompute无缝连接。
您可以使用在MaxCompute上创建Hologres外部表的方式,基于PostgreSQL JDBC驱动及STS认证信息查询Hologres数据源的数据。该方式无冗余存储,无需导入导出数据,可实现快速获取查询结果。
前提条件
创建Hologres外部表前,请确认已经满足如下条件:
已准备好Hologres数据库及目标表。
创建Hologres数据库信息,请参见创建数据库。
创建Hologres表信息,请参见CREATE TABLE。
假设已准备好的Hologres实例信息如下:
Hologres数据库名称:
mc_test
。Hologres数据库的Schema:
public
。Hologres数据库经典网络连接地址:
hgprecn-cn-oew210ut****-cn-hangzhou-internal.hologres.aliyuncs.com:80
。Hologres表名称:
holo
。表数据如下:
已准备好待创建Hologres外部表的目标MaxCompute项目。
创建MaxCompute项目信息,请参见创建MaxCompute项目。
已安装MaxCompute客户端。
更多安装MaxCompute客户端操作,请参见安装并配置MaxCompute客户端。
使用限制
Hologres外部表的使用限制如下:
MaxCompute不支持对创建的Hologres外部表执行更新(UPDATE)、删除(DELETE)操作。
Hologres的分区表和MaxCompute的分区表没有对应关系。Hologres外部表不支持分区。
当您需要向Hologres外部表写入大量数据时,采用并行多进程写入方式,会小概率出现某个写入进程数据重写情况,导致数据重复。
MaxCompute里建的Hologres外部表,其中DECIMAL数据类型默认小数18位,不能修改,只能建成
decimal(38,18)
。如果小数位数比较少,可以在MaxCompute中建外部表时数据类型选择String,使用的时候再使用cast
函数强制转换后使用。MaxCompute创建的Hologres外部表,不支持Array,Map,Struct复杂数据类型。
在MaxCompute创建Hologres外部表时,Hologres中有的JSON、JSONB、MONEY等数据类型,目前在MaxCompute没有对应的数据类型,暂时不支持。
Hologres外部表不支持cluster属性。
注意事项
Hologres外部表使用过程中需要注意:
如果Hologres开启了IP白名单功能,用户需要采用双签名模式创建Hologres外部表。如果用STS模式创建Hologres外部表,MaxCompute访问Hologres时会被IP白名单拦截。
对于Hologres的父、子表,Hologres外部表中会指定表名,并执行SQL语句。父、子表都可以映射至Hologres外部表,但是父表只能读不能写。
向Hologres外部表写入数据时,暂不支持Hologres的INSERT ON CONFLICT(UPSERT)机制。如果Hologres源表有主键,请避免写入的数据与Hologres源表中的数据产生主键唯一性冲突。
建表时,表名和字段名大小写不敏感。在查询表或字段时,无需区分大小写,且不支持强制转换大小写。
创建Hologres外部表语法
在创建外部表时,您需要在建表DDL语句中指定StorageHandler,并配置STS认证信息(或打开双签名开关)、JDBC连接地址实现访问Hologres数据源。建表语句定义如下。
STS模式创建Hologres外部表。
CREATE EXTERNAL TABLE [IF NOT EXISTS] <table_name>( <col1_name> <data_type>, <col2_name> <data_type>, ...... ) stored BY '<com.aliyun.odps.jdbc.JdbcStorageHandler>' WITH serdeproperties ( 'odps.properties.rolearn'='<ram_arn>') location '<jdbc:postgresql://<endpoint>:<port>/<database>?ApplicationName=MaxCompute&[currentSchema=<schema>&][useSSL={true|false}&]table=<holo_table_name>/>' tblproperties ( 'mcfed.mapreduce.jdbc.driver.class'='org.postgresql.Driver', 'odps.federation.jdbc.target.db.type'='holo', ['odps.federation.jdbc.colmapping'='<col1:column1,col2:column2,col3:column3,...>'] );
双签名模式创建Hologres外部表。
双签名Hologres外部表支持相同RAM用户可以访问MaxCompute和Hologres对应有权限的表,不需要再手工授权。同时支持HologresIP白名单能力,方便您使用。
--打开双签名开关 SET odps.sql.common.table.planner.ext.hive.bridge=true; --创建外部表 CREATE EXTERNAL TABLE [IF NOT EXISTS] <table_name>( <col1_name> <data_type>, <col2_name> <data_type>, ...... ) stored BY '<com.aliyun.odps.jdbc.JdbcStorageHandler>' location'<jdbc:postgresql://<endpoint>:<port>/<database>?ApplicationName=MaxCompute&[currentSchema=<schema>&][useSSL={true|false}&]table=<holo_table_name>/>' tblproperties ( 'mcfed.mapreduce.jdbc.driver.class'='org.postgresql.Driver', 'odps.federation.jdbc.target.db.type'='holo', ['odps.federation.jdbc.colmapping'='<col1:column1,col2:column2,col3:column3,...>'] );
odps.sql.common.table.planner.ext.hive.bridge:通过双签名模式创建Hologres外部表必填;通过STS模式创建Hologres外部表不填。双签名开关,值设置为
true
,表示打开双签名开关,通过双签名模式创建Hologres外部表。if not exists:可选。如果不指定if not exists选项而存在同名表,会报错。如果指定if not exists,无论是否存在同名表,即使原表结构与要创建的目标表结构不一致,均返回成功。已存在的同名表的元数据信息不会被改动。
table_name:必填。在MaxCompute上创建的Hologres外部表的名称。
col_name:必填。Hologres外部表的列名称。
data_type:必填。Hologres外部表的列的数据类型。
stored by:必填。指定StorageHandler,定义了如何查询Hologres外部表。固定取值为
com.aliyun.odps.jdbc.JdbcStorageHandler
,使用JdbcStorageHandler连接方式。ram_arn:通过STS模式创建Hologres外部表必填;通过双签名模式创建Hologres外部表不填。指定RAM角色的ARN信息,用于创建外部表时STS认证信息的填写。您可以在RAM访问控制页面,单击目标RAM角色名称后,在基本信息区域获取。
location:必填。Hologres实例的JDBC连接地址。其中:
endpoint:必填。Hologres实例的经典网络域名。获取方式,请参见实例配置。
port:必填。Hologres实例的网络端口。获取方式,请参见实例配置。
database:必填。连接的Hologres数据库名称。更多Hologres数据库信息,请参见CREATE DATABASE。
ApplicationName:必填。默认为MaxCompute,无需修改。
schema:可选。如果表名在Hologres数据库内是唯一的,或源表是默认Schema中的表,可以不配置该属性。更多Schema信息,请参见CREATE SCHEMA。
holo_table_name:必填。Hologres源表名称。更多Hologres源表信息,请参见CREATE TABLE。
tblproperties:
mcfed.mapreduce.jdbc.driver.class:必填。指定连接Hologres数据库的驱动程序。固定取值为
org.postgresql.Driver
。odps.federation.jdbc.target.db.type:必填。指定连接的数据库类型。固定取值为
holo
。odps.federation.jdbc.colmapping:可选。如果需要将指定数据源的部分列映射至Hologres外部表,需要配置该参数,指定Hologres源表的字段和Hologres外部表字段的映射关系。
若未配置该参数,按照源表字段名映射至Hologres外部表同名列。
若配置该参数,但是只指定MaxCompute外部表部分列的映射关系,则按照源表字段名映射至Hologres外部表同名列,其他未指定的列,列名或类型不匹配会报错。
若配置该参数,Hologres里的字段名称存在大写的情形,需要为Hologres字段名称添加双引号(
""
)。格式为:MaxCompute字段1 : "Hologres字段1"[ ,MaxCompute字段2 : "Hologres字段2" ,...]
。说明Hologres源表字段是
c bool, map_B string, a bigint
。MaxCompute外部表字段是a bigint, x string, c bool
。colmapping
配置的内容是'x: "map_B"'
,则可以成功映射并查询Hologres数据。
mcfed.mapreduce.jdbc.input.query:可选。读取Hologres数据源表数据。外部表的列、列名与直接查询的Hologres数据源表的列、列名及数据类型保持一致。如果使用了别名,则与别名保持一致。
select_sentence
格式为SELECT xxx FROM <holo_database_name>.<holo_schema_name>.<holo_table_name>
。
创建Hologres外部表(STS模式)
通过STS模式创建Hologres外部表的步骤如下:
创建RAM角色
创建RAM角色获取ARN信息,用于创建外部表时填写STS认证信息。
登录RAM访问控制创建RAM角色。
创建RAM角色的可信实体类型根据实际需求选择阿里云账号或者身份提供商。
阿里云账号:
阿里云账号下的RAM用户可以通过扮演RAM角色来访问云资源,详情请参见创建可信实体为阿里云账号的RAM角色。
身份提供商:
通过设置SSO实现从企业本地账号系统登录至阿里云控制台,帮您解决企业的统一用户登录认证要求。详情请参见创建可信实体为身份提供商的RAM角色。
修改信任策略配置内容。
在角色页面,单击已创建完成的RAM角色名称。
单击信任策略页签。
在信任策略页签,单击编辑信任策略。
参照如下内容修改信任策略配置。
修改信任策略配置内容与选择的可信实体类型相关。
可信实体类型为阿里云账号:
{ "Statement": [ { "Action": "sts:AssumeRole", "Effect": "Allow", "Principal": { "RAM": [ "acs:ram::<UID>:root" ] } }, { "Action": "sts:AssumeRole", "Effect": "Allow", "Principal": { "Service": [ "<UID>@odps.aliyuncs.com" ] } } ], "Version": "1" }
可信实体类型为身份提供商:
{ "Statement": [ { "Action": "sts:AssumeRole", "Condition": { "StringEquals": { "saml:recipient": "https://signin.aliyun.com/saml-role/sso" } }, "Effect": "Allow", "Principal": { "Federated": [ "acs:ram::<UID>:saml-provider/IDP" ] } }, { "Action": "sts:AssumeRole", "Effect": "Allow", "Principal": { "Service": [ "<UID>@odps.aliyuncs.com" ] } } ], "Version": "1" }
说明<UID>即阿里云账号ID,可在用户信息页面获取。
单击确定。
添加RAM角色至Hologres实例并授权
RAM角色需要有Hologres实例的开发权限,才能在权限范围内使用Hologres。由于RAM角色默认没有Hologres管理控制台的查看和操作实例的权限,因此需要阿里云账号完成RAM相关权限授予才能进行后续操作。添加RAM角色至Hologres实例,您可以通过如下方式进行授权。
通过Hologres管理控制台授权。
在左侧导航栏单击实例列表,单击需要授权的Hologres实例名称。
在实例详情页面,单击账号管理。
在用户管理页面单击新增用户添加RAM角色至Hologres实例。
在DB授权页签,为该RAM角色授予实例的开发权限。
说明若数据库的权限策略设置为专家模式,则需在用户管理页面将角色类型修改为SuperUser,后续将不再需要进行数据库授权操作。
通过SQL方式授权。
您可以通过SQL方式进行授权,授权SQL请参见Hologres权限模型概述。
若是通过RAM用户扮演RAM角色,RAM用户默认没有Hologres管理控制台的权限,需要阿里云账号给RAM用户在访问控制页面授予AliyunRAMReadOnlyAccess权限,否则RAM用户无法在Hologres管理控制台进行任何操作。详情请参见文档授予RAM用户权限。
创建Hologres外部表
完成上述步骤后,基于已准备好的数据信息,您即可登录MaxCompute客户端,结合创建Hologres外部表语法创建Hologres外部表。
安装并登录MaxCompute本地客户端,进入目标MaxCompute项目。
进入目标项目命令信息,请参见项目空间操作。
执行如下命令创建Hologres外部表。
命令示例如下。
CREATE EXTERNAL TABLE [IF NOT EXISTS] my_table_holo_jdbc ( id bigint, name string ) stored BY 'com.aliyun.odps.jdbc.JdbcStorageHandler' WITH serdeproperties ( 'odps.properties.rolearn'='acs:ram::139699392458****:role/aliyunodpsholorole') location 'jdbc:postgresql://hgprecn-cn-oew210ut****-cn-hangzhou-internal.hologres.aliyuncs.com:80/mc_test?ApplicationName=MaxCompute¤tSchema=public&useSSL=false&table=holo/' tblproperties ( 'mcfed.mapreduce.jdbc.driver.class'='org.postgresql.Driver', 'odps.federation.jdbc.target.db.type'='holo', 'odps.federation.jdbc.colmapping'='id:id,name:name' );
执行如下命令基于新建的Hologres外部表查询Hologres源表信息。
命令示例如下。
--访问Hologres外部表需要添加如下属性。 SET odps.sql.split.hive.bridge=true; SET odps.sql.hive.compatible=true; --查询Hologres外部表数据。 SELECT * FROM my_table_holo_jdbc limit 10;
返回结果如下。
+------------+------------+ | id | name | +------------+------------+ | 1 | kate | | 2 | mary | | 3 | bob | | 4 | tom | | 5 | lulu | | 6 | mark | | 7 | haward | | 8 | lilei | | 9 | hanmeimei | | 10 | lily | +------------+------------+
可选:基于Hologres外部表与Hologres进行数据交换、联合分析。
例如,将MaxCompute加工后的数据利用Hologres外部表,写入Hologres实现加速分析、在线服务。命令示例如下。
--访问Hologres外部表需要添加如下属性。 SET odps.sql.split.hive.bridge=true; SET odps.sql.hive.compatible=true; --向Hologres外部表插入数据。 INSERT INTO my_table_holo_jdbc VALUES (12,'alice'); --查询Hologres外部表数据。 SELECT * FROM my_table_holo_jdbc;
返回结果如下。
+------------+------------+ | id | name | +------------+------------+ | 12 | alice | | 1 | kate | | 2 | mary | | 3 | bob | | 4 | tom | | 5 | lulu | | 6 | mark | | 7 | haward | | 8 | lilei | | 9 | hanmeimei | | 10 | lily | | 11 | lucy | +------------+------------+
频繁更新的维度表保存在Hologres,满足实时动态更新需要。MaxCompute通过外部表方式访问维度表与MaxCompute中事实表进行关联分析,命令示例如下。
--访问Hologres外部表需要添加如下属性。 SET odps.sql.split.hive.bridge=true; SET odps.sql.hive.compatible=true; --创建MaxCompute内部表。 CREATE TABLE holo_test AS SELECT * FROM my_table_holo_jdbc; --MaxCompute内部表与Hologres外部表进行关联分析。 SELECT * FROM my_table_holo_jdbc t1 INNER JOIN holo_test t2 ON t1.id=t2.id;
返回结果如下。
+------------+------------+------------+------------+ | id | name | id2 | name2 | +------------+------------+------------+------------+ | 1 | kate | 1 | kate | | 2 | mary | 2 | mary | | 3 | bob | 3 | bob | | 4 | tom | 4 | tom | | 5 | lulu | 5 | lulu | | 6 | mark | 6 | mark | | 7 | harward | 7 | harward | | 8 | lilei | 8 | lilei | | 9 | hanmeimei | 9 | hanmeimei | | 10 | lily | 10 | lily | | 11 | lucy | 11 | lucy | | 12 | alice | 12 | alice | +------------+------------+------------+------------+
创建Hologres外部表(双签名模式)
双签名是MaxCompute和Hologres共同研发的认证及鉴权协议,在MaxCompute侧使用账号登录信息加签名后,把认证数据传递给Hologres侧,Hologres根据MaxCompute底层达成的协议,进行同名认证及鉴权。这样只需要在MaxCompute和Hologres有相同的账号,就可以直接进行外部表访问,不需要额外设置认证信息。
前提条件。
Hologres中存在跟MaxCompute相同名称的账号,并且该账号具有Hologres中对应表的读写权限。
使用限制。
仅Hologres V1.3及以上版本支持MaxCompute使用双签名模式创建Hologres外部表,目前双签名模式只支持从Hologres外部表中读取数据,不支持写入数据至Hologres外部表。
命令示例。
您可直接登录MaxCompute客户端,结合创建Hologres外部表语法通过双签名模式创建Hologres外部表。
--创建外部表 CREATE EXTERNAL TABLE IF NOT EXISTS holo_mc_external_dbl ( id int, name string, ds string ) STORED BY 'com.aliyun.odps.jdbc.JdbcStorageHandler' location 'jdbc:postgresql://hgprecn-cn-zvp2o6aq****-cn-beijing-internal.hologres.aliyuncs.com:80/mc_test?ApplicationName=MaxCompute¤tSchema=public&preferQueryMode=simple&useSSL=false&table=mf_holo_mc_up/' TBLPROPERTIES ( 'mcfed.mapreduce.jdbc.driver.class'='org.postgresql.Driver', 'odps.federation.jdbc.target.db.type'='holo', 'odps.federation.jdbc.colmapping'='id:id,name:name,ds:ds' ); --查询外部表(必须与打开双签名开关命令一起执行) SET odps.sql.common.table.planner.ext.hive.bridge=true; SELECT * FROM holo_mc_external_dbl;
开启Hologres外部表存储直读功能
背景介绍
MaxCompute对Hologres外部表的读是通过走JDBC模式,目前版本支持MaxCompute直读Hologres存储层,能够带来以下优势:
可以大幅降低读表的延迟,大幅度提高查询数据的速度。
可以大幅度减少Hologres FE的连接数,大多数Query仅需要一个连接数即可。
使用限制
当开启Hologres直读模式时,使用限制如下,在条件不满足时会回退到JDBC模式。
依赖Hologres实例版本 : V1.3.34及以上版本。
Hologres版本低于V1.3.34不支持直读功能。
由于网络连通性,只支持同Region的MaxCompute访问Hologres实例。
目前不支持跨Region访问,跨Region访问会报错:
FAILED: ODPS-0010000:System internal error - fuxi job failed, caused by: Pangu request failed with error code 3
。不支持直读Hologres冷存表。
目前直读功能不支持Hologres行存表。
当Hologres配置为主从架构,仅支持配置连接URL为主实例,不支持配置为从实例。
直读功能会对MaxCompute与Hologres之间的列进行类型校验,当出现不匹配的类型时会自动回退为JDBC模式执行。MaxCompute创建Hologres外部表时,数据类型的限制如下:
JDBC模式与MaxCompute直读模式都不支持的数据类型:
不支持Array、Map、Struct复杂数据类型。
不支持JSON、MONEY等数据类型。
JDBC模式支持,而MaxCompute直读模式不支持的数据类型:
BINARY类型。
MaxCompute直读模式支持,而JDBC模式不支持的数据类型:
JSONB数据类型
MaxCompute直读模式使用Timestamp类型映射Hologres中的Timestamp With Time Zone类型会存在细微的时间误差,具体差异如下:
Hologres中Timestamp With Time Zone类型列的时间在
1900-12-31 15:54:15
之前,MaxCompute查询出来的时间会多5分44秒。Hologres中Timestamp With Time Zone类型列的时间在
1900-12-31 15:54:16
和1969-12-31 23:59:58
之间,MaxCompute查询出来的时间会多1秒。Hologres中Timestamp With Time Zone类型列的时间在
1969-12-31 23:59:59
之后,MaxCompute查询出来的时间与Hologres中的无区别。说明MaxCompute直读模式使用Timestamp类型映射Hologres中的Timestamp With Time Zone类型不仅会存在细微的时间误差,还会存在时区偏移,例如:
以MaxCompute的时区为东八区为例,Hologres中Timestamp With Time Zone类型列的时间为
2000-01-01 00:00:00
,MaxCompute查询出来的时间为2000-01-01 08:00:00
。以MaxCompute的时区为东八区为例,Hologres中Timestamp With Time Zone类型列的时间为
1969-01-01 00:00:00
,MaxCompute查询出来的时间为1969-01-01 08:00:01
。
其他数据类型映射如下:
Hologres数据类型
MaxCompute数据类型
说明
TEXT
STRING
VARCHAR
不涉及
SMALLINT
SMALLINT
不涉及
INT
INT4
INTEGER
INT
不涉及
INT8
BIGINT
BIGINT
不涉及
FLOAT4
REAL
FLOAT
不涉及
FLOAT
FLOAT8
DOUBLE
不涉及
BOOL
BOOLEAN
BOOLEAN
不涉及
TIMESTAMP
TIMESTAMP
存储精度为微秒,存在时区的时间误差。
TIMESTAMP WITH TIME ZONE
TIMESTAMP
MaxCompute与Hologres在底层已经进行了精度转换。MaxCompute输出不包含时区格式。
NUMERIC
DECIMAL
MaxCompute的DECIMAL如果未指定精度,则默认为
(38,18)
,使用IMPORT FOREIGN SCHEMA
语句创建表时系统会自动转换精度。CHAR(n)
CHAR(n)
MaxCompute的
CHAR(n)
为固定长度字符类型,n
为长度。最大取值为255。长度不足则使用空格填充。VARCHAR(n)
VARCHAR(n)
MaxCompute的
VARCHAR(n)
为可变长度字符类型,n
为长度。取值范围为1~65535。DATE
DATE
不涉及
Foreign Server模式存在的额外限制:MaxCompute Project需要开启三层模型。
开启方式
在MaxCompute中查询Hologres外部表时SQL前加上如下参数。
SET odps.table.api.enable.holo.table=true;
直读验证
可以在Logview里查看日志,判断查询是否走了直读模式,Logview使用详情请参见使用Logview 2.0查看作业运行信息。
在Logview的Summary页签下,查找external holo tables
字段查看属性,属性格式如下:
<project_name>.<table_name>:<访问方式>[<(回退原因)>]
参数说明:
参数 | 说明 |
project_name | 项目名称。 |
table_name | 表名称。 |
访问方式 | 外部表的访问方式,取值如下:
|
回退原因 | 如果访问方式为
|