本文为您介绍使用Hologres对接MaxCompute时的常见报错及解决方法。
基本概念
Hologres与MaxCompute的对比。
对比项
MaxCompute
Hologres
使用场景
ETL(Extract-Transform-Load)加工,面向数据明细层(DWD,Data Warehouse Detail)和数据服务层(DWS,Data WareHouse Service)。
交互式查询、在线数据服务,面向应用的数据服务(ADS)。
用户使用
异步的执行作业。
同步的Query。
集群资源
共享大集群,SaaS模式。
独享集群,PaaS模式。
计算引擎
基于Job Execution模型,将作业转化为Stage,每个Stage按需申请计算资源,执行过程中通过File持久化。
基于MPP模型,精细化内存资源管理,执行引擎常驻内存,用户态细粒度SQL算子调度,计算不落盘。
调度方式
进程级别,运行时按需申请、分配。
轻量级线程,资源启动时预留。
扩展性
几乎不受限制。
复杂查询尽量避免跨多节点数据Shuffle。
存储格式
列式。
行式、列式、行列共存。
存储成本
基于Pangu,成本低。
基于Pangu,利用SSD做缓存加速,成本相对高。
接口标准
MaxCompute SQL,类Hive。
PostgreSQL。
Hologres外部表和内部表的适用场景
新建外部表直接加速查询
外部表不存储数据,数据存储在MaxCompute中,且外部表没有索引,全靠CPU资源进行计算,因此外部表比较适用于小数据量,低QPS(Queries-per-second)的查询。
导入数据至Hologres内部表进行加速查询
内部表的数据存储在Hologres中,当有数据更新、复杂查询、高QPS的查询时,建议导入内部表,能充分发挥Hologres底层的性能优势。
性能调优
性能退化:MaxCompute外部表发生Schema Evolution之后,查询性能大幅下降
下降原因:Hologres加速查询MaxCompute外部表默认走HQE直读链路,当MaxCompute外部表结构发生变更后,会回退到SQE链路,访问链路更长,导致查询性能下降。
解决方法:通过hologres.hg_query_log来查询慢Query。如果engine_type为SQE,可以确认MaxCompute Schema Evolution链路切换为SQE导致性能下降。可以尝试重新构建需要进行表结构变更的MaxCompute外部表来解决该问题。
常见报错
MaxCompute权限相关:
其他报错:
报错:SERVER_INTERNAL_ERROR message: GetRecordBatch() is not implemented.
报错:Build desc failed: Exceeds the scan limitation of 200 GB, current scan xxx GB.
报错:query next from foreign table executor failed, Not implemented.
报错:Build desc failed: failed to check permission: Currently not supported table type "view".
报错:failed to import foreign schema:Failed to get MaxCompute table:Not enable schema evolution.
报错:failed to import foreign schema:Failed to get MaxCompute table:Not enable acid table.
导入数据报错:Query executor exceeded total memory limitation xxxxx: yyyy bytes used.
报错:Timestamp overflow detected while converting timestampfrom orc VectorBatch to arrow.
报错:The sensitive label of column 'xxx' is 2, but your effective label is 0.
报错:query next from foreign table executor failed validate userinfao
报错:SERVER_INTERNAL_ERROR message: GetRecordBatch() is not implemented.
查询MaxCompute外表时报错:query next from foreign table executor failed, GetRecordBatch() is not implemented
。
报错原因:当前MaxCompute的表类型不是Cfile类型的表,Hologres暂不支持该类型的表。
解决方法:在查询数据SQL前添加如下GUC。
set hg_experimental_enable_access_odps_with_table_api =on;
报错:ERROR: not an ORC file
查询外部表时报错:ERROR: status { code: SERVER_INTERNAL_ERROR message: "hos_exception: Invalid argument: ../../../src/OrcFileMetaHelper.cc(234)-<operator()>: not an ORC file
。
报错原因:MaxCompute的表是Stream表,数据是通过Tunnel等流式写入,当前Hologres直读MaxCompute外部表时暂不支持查询该状态的表。
解决方法:在查询数据SQL前添加如下GUC。
set hg_experimental_enable_access_odps_with_table_api=on; set hg_experimental_enable_access_odps_orc_via_holo =off;
报错:specified partitions count in MaxCompute table: exceeds the limitation of 512, please add stricter partition filter or set axf_MaxCompute_partition_limit.或者Build desc failed: Exceeds the partition limitation of 512, current match xxx partitions.
报错原因:
当前Hologres支持查询最多分区数为512个,查询超过此限制。
解决方法:
请添加分区过滤条件,使一次查询不超过512个分区。
请将数据导入Hologres内部表,则没有分区限制,详情请参见使用SQL导入MaxCompute的数据至Hologres。
使用如下命令调整每次Query命中的分区数,默认为512,最大为1024,不建议调整太大,否则会影响查询性能。
-- V1.1及以上版本 set hg_foreign_table_max_partition_limit = 128; -- V0.10版本 set hg_experimental_foreign_table_max_partition_limit = xxx ;
说明如果MaxCompute配置了多级分区,会按照最细粒度分区单位进行分区命中计数。
报错:Build desc failed: Exceeds the scan limitation of 200 GB, current scan xxx GB.
报错原因:
Hologres中默认最大的底层数据扫描量为200GB,此数据量是命中MaxCompute分区之后的扫描数据量,和MaxCompute自身存储数据量无关,查询超出此限制导致报错。
解决方法:
增加过滤条件,命中更少的分区,使一次Query的扫描数据量在200GB以内。
请将MaxCompute表数据导入至Hologres中,再进行查询,详情请参见使用SQL导入MaxCompute的数据至Hologres。
(不推荐)使用
set hg_experimental_foreign_table_max_scan_size = xxx;
命令设置参数调大数据量限制(其中xxx可以替换为业务的数据量,如400,单位为GB)。但是过分调大外部表数据量限制,可能无法得到预期的性能,也可能造成实例OOM(Out Of Memory),影响正常使用。
报错:query next from foreign table executor failed, Not implemented.
报错原因:MaxCompute表数据写入时使用Streaming Tunnel的方式写入,写入命令为
tunnel.createStreamUploadSession
。Hologres读取数据时需要开启两个GUC。解决方法:
添加如下两个配置项。
说明仅Hologres V1.3及以上版本支持该GUC。
set hg_experimental_enable_access_odps_with_table_api=on; set hg_experimental_enable_access_odps_orc_via_holo =off;
如果实例版本低于V1.3版本,建议在MaxCompute侧停止streaming写入,然后通过以下语句对数据进行Merge:
set odps.merge.task.mode=sql; set odps.merge.lock.expire.time=0; ALTER TABLE tablename [PARTITION] MERGE SMALLFILES;
报错:Build desc failed: failed to check permission: Currently not supported table type "view".
报错原因:目前暂时不支持MaxCompute的View。
报错:Build desc failed: failed to get foreign table split:MaxCompute-0010000: System internal error - get input pangu dir meta fai.
报错原因:
Hologres读取MaxCompute的配置未及时更新。
解决方法:
请过几分钟重试,若是重试好几次都未成功,请联系技术支持处理。
报错:ERROR: Query:[xxx] Build desc failed: failed to get foreign table split:ERPC_ERROR_CONNECTION_CLOSED.
报错原因:
MaxCompute小文件过多,导致请求的META超过远程过程调用协议(RPC,Remote Procedure Call Protocol)1GB的最大限制。
解决方法:
请执行以下命令进行小文件合并。
set MaxCompute.merge.task.mode=sql; set MaxCompute.merge.lock.expire.time=0; ALTER TABLE <tablename> [PARTITION] MERGE SMALLFILES;
HologresV0.10.21及以上版本已优化,请升级Hologres实例,详情请参见实例升级。
请联系MaxCompute技术支持从源头解决,如果数据量不大可直接将数据写入Hologres。
报错:ERROR: status { code: SERVER_INTERNAL_ERROR message: "hos_exception: IO error: Failed to execute pangu open normal file, err: PanguParameterInvalidException" }.
报错原因:
Hologres HQE不支持直读MaxCompute Pangu加密数据。
解决方法:
请执行
ALTER DATABASE <dbname> SET hg_experimental_enable_access_odps_orc_via_holo = false;
命令将外部表的执行引擎修改为SQE,使用SQE访问MaxCompute加密数据,该配置是数据库级别配置,需要重新创建连接才能生效;您也可执行Session级别设置:SET hg_experimental_enable_access_odps_orc_via_holo = false;
。
报错:failed to import foreign schema:Failed to get MaxCompute table:Not enable schema evolution.
报错原因:
对MaxCompute表的元数据做了修改。
解决方法:
请升级Hologres实例版本至V1.3及以上版本,通过加入实时数仓Hologres交流群申请升级实例或自助升级,加群方式请参见如何获取更多的在线支持?。
更新了MaxCompute外部表Schema之后(例如增加列、删除列操作),请执行IMPORT FOREIGN SCHEMA来做刷新。
如果执行了
IMPORT FOREIGN SCHEMA
还报错的话,请重新建一次MaxCompute的表,再建外部表,因为MaxCompute修改Schema之后进入到schema evolution
状态,Hologres无法读取这种状态的表。
报错:Open ORC file failed for schema mismatch. Reader schema:
报错原因:
MaxCompute的表为ORC格式,表的DECIMAL类型存储方式改变(一般是MaxCompute新加了DECIMAL字段或者MaxCompute做了灰度配置变更),导致Hologres读MaxCompute的DECIMAL类型出错。
解决方法:
请执行
set MaxCompute.storage.orc.enable.binary.decimal=false
命令,重新导下MaxCompute数据。请将MaxCompute的表的DECIMAL类型改为DOUBLE类型,再重新刷新一遍数据。
报错:failed to import foreign schema:Failed to get MaxCompute table:Not enable acid table.
报错原因:
MaxCompute表是事务(Transactional)表。
解决方法:
当前不支持MaxCompute的Transactional表,建议改为普通表。
报错:Request denied, may caused by server busy.
报错原因:
外部表资源占满,CPU用量严重超出。
解决方法:
请优化SQL,使SQL更加充分合理地使用资源,详情请参见优化MaxCompute外部表的查询性能。
降低并发度。
使用
show hg_foreign_table_executor_max_dop;
命令查看当前配置。使用如下命令降低并发度,推荐调整为当前配置的一半。
-- 语法示例 set hg_foreign_table_executor_max_dop = <并发数>; -- 使用示例 set hg_foreign_table_executor_max_dop = 18;
并发数:外部表单个执行节点读取外部表数据的并发度,默认值为256,取值范围为0-1024。修改后的风险: 并发度太大可能造成实例OOM,导致导入、查询失败,甚至实例重启,以至于服务不可用。并发度太小会导致外表查询、外表导入内表性能较差。
请导入数据至Hologres内部表,内部表可以设置索引,使查询性能更好,详情请参见使用SQL导入MaxCompute的数据至Hologres。
导入数据报错:Query executor exceeded total memory limitation xxxxx: yyyy bytes used.
报错原因:
数据量太大或者导入逻辑太复杂,导致超出了内存限制。(实例由多个节点组成,一个节点标准的内存上限是64GB,节点内存会分为三部分,三分之一用于计算,三分之一用于缓存,三分之一用于元数据。这里的报错是计算内存超出了限制。)
解决方法:
查看执行计划
可以执行
explain analyze sql;
命令查看执行计划中具体的数据行数。当导入Query包含查询,但部分表没有analyze
,或者analyze
过,但数据又有更新导致不准确,导致查询优化器决策连接顺序有误,会引起内存开销过高。对所有参与的内表、外表执行
analyze tablename;
命令,更新表的统计元信息,可以帮助查询优化器生成更优的执行计划。设置单行导入条数
当表的列数较多,单行数据量较大时,单次读取的数据量会更大,通过在SQL前加以下参数来控制单次读取数据的行数,可以有效减少OOM情况。
set hg_experimental_query_batch_size = 1024; -- 默认值为8192 insert into holo_table select * from mc_table;
降低导入的并发度。
降低导入并发度,也会有效减少导入过程中的内存开销,并发度通过参数
hg_foreign_table_executor_max_dop
控制,默认为实例的Core数,可以在导入时设置更小的参数,降低导入的内存使用。set hg_foreign_table_executor_max_dop = 8; insert into holo_table select * from mc_table;
排查外表重复数据是否过多。
如果以上操作都做完了,还是导入不了,如果使用的是
insert on conflict
命令,请排查是否外表重复数据太多,重复数据太多也会导致导入性能不好,可以在MaxCompute做重复数据去重,再进行导入,详情请参见多行数据合并为一行数据。升级新版本动态调整内存。
Hologres从V1.1.24版本开始,会对内存进行动态调整,后台会实时刷新当前内存水位,若是有空闲,则会分配更多内存给计算使用,请升级Hologres至最新版本,具体操作请参见实例升级。
扩容。
如果以上操作都做完了,导入数据还是不成功,请对Hologres扩容,详情请参见升配。
报错:Timestamp overflow detected while converting timestampfrom orc VectorBatch to arrow.
报错原因:
在MaxCompute表中有TIMESTAMP类型,使用Tunnel写入后TIMESTAMP精度会变成纳秒,目前Hologres暂不支持精度为纳秒的TIMESTAMP。
解决方法:
在MaxCompute中将TIMESTAMP类型转换为DateTime类型。
Hologres实例升级版本到 V1.1.70及以上版本。
报错:You have NO privilege 'MaxCompute:Select' on xxx.
报错原因:
当前账号不具备MaxCompute表的查询(Select)权限。
解决方法:
请联系MaxCompute管理员在MaxCompute中授予当前账号查询表(Select)的权限,具体操作请参见MaxCompute权限。
报错:The sensitive label of column 'xxx' is 2, but your effective label is 0.
报错原因:
当前账号只有MaxCompute表的部分字段权限。
解决方法:
核对有权限的账号和报错的账号是否为同一个账号,若确实没有权限,可以去申请MaxCompute的权限,或者只过滤有权限的字段查询。获取MaxCompute表全部字段的权限,具体操作请参见授权。
若是有权限,并且也只查询了有权限的字段,在实例比较老的版本可能存在缺陷,您可以在执行的Query前增加如下命令解决报错问题。
set hg_experimental_enable_MaxCompute_executor=on; set hg_experimental_enable_query_master=on;
报错:query next from foreign table executor failed validate userinfao
报错原因:
未正确对Hologres的AliyunHologresEncryptionDefaultRole进行授权,或者因为缓存的原因,授权未超过3小时也可能偶发出现此报错。
解决方法:
对账号授权AliyunHologresEncryptionDefaultRolePolicy角色,详情请参见查询MaxCompute加密数据(BYOK模式)。
查询外部表速度慢如何解决?
建议优化SQL,详情请参见优化MaxCompute外部表的查询性能。
查询外部表报错:You have NO privilege 'odps:Select' on xxx
问题现象
当您在Hologres管理控制台创建外部表之后,查询外部表时报错提示“You have NO privilege 'odps:Select' on xxx”。
问题原因
当前账号不具备MaxCompute表的查询(Select)权限。
解决方法
需要MaxCompute管理员在MaxCompute中授予当前账号查询表(Select)的权限,具体操作请参见MaxCompute权限。
查询外部表报错:The sensitive label of column 'xxx' is 2, but your effective label is 0
问题现象
当您在Hologres管理控制台创建外部表之后,查询外部表时报错提示“The sensitive label of column 'xxx' is 2, but your effective label is 0”。
问题原因
当前账号只有MaxCompute表的部分字段权限。
解决方法
您可以选择如下三种方法中的一种来解决该问题:
(推荐)建议您搜索加入实时数仓Hologres交流群申请将当前实例版本升级至V0.8,详情请参见如何获取更多的在线支持?。
您可以在执行的Query前增加如下参数解决报错问题。
set hg_experimental_enable_odps_executor=on; set hg_experimental_enable_query_master=on;
获取MaxCompute表全部字段的权限,具体操作请参见MaxCompute权限。
跨project访问MaxCompute表报错:You have NO privilege 'odps:Select' on xxx
问题现象
当前账号已经具备MaxCompute表查询权限,但是跨project访问MaxCompute表报错”You have NO privilege 'odps:Select' on xxx“。
问题原因
若是当前账号已经具备MaxCompute已经有表的查询权限,跨project访问MaxCompute表还是报错,则MaxCompute当前可能采用的是package授权,您需要添加SQL语句解决该问题。
解决方法
当前如果MaxCompute是project授权方式,在Hologres中,您可以在SQL前添加如下参数解决。
// V0.7版本的实例请执行以下语句授权 set seahawks.seahawks_internal_current_odps_project='holoprojectname'; //V0.8版本的实例请执行以下语句授权 set hg_experimental_odps_current_project_name = 'holoprojectname';
创建外部表报错:You have NO privilege 'odps:List' on xxx
问题现象
当您在Hologres管理控制台使用HoloWeb或DataStudio可视化创建外部表时报错提示“You have NO privilege 'odps:List' on xxx”。
问题原因
当前账号在MaxCompute中不具备查看所有表(List)的权限。
解决方法
需要MaxCompute管理员在MaxCompute中授予当前账号查看所有表(List)的权限,具体操作请参见MaxCompute权限。
使用SQL语句创建外部表查询数据,具体操作请参见通过创建外部表加速查询MaxCompute数据。
创建外部表时报错:Access denied by project ip white list: sourceIP:'xxxx' is not in white list. project: xxxx
问题现象
当您在Hologres管理控制台使用HoloWeb创建外部表时报错提示“Access denied by project ip white list: sourceIP:'xxxx' is not in white list. project: xxxx”。
问题原因
当前MaxCompute集群设置了白名单访问,Holoweb不在白名单内。
解决方法
当MaxCompute项目开启白名单功能时,仅允许白名单内的设备访问项目空间;非白名单内的设备访问项目空间时,即使拥有正确的AccessKey ID及AccessKey Secret,也无法通过鉴权。因此需要将报错信息中的IP设置为白名单才可以创建外表,具体操作请参见管理IP白名单。
创建外部表时报错:You don't exist in project xxx
问题现象
当您在创建外部表时报错提示“You don't exist in project xxx”。
问题原因
执行创建外部表的账号不具有访问对应MaxCompute Project的权限。
解决方法
请先确认需要访问的MaxCompute Project名称,如果Project名称错误请先换成正确的Project名。如果Project名称正确仍然报同样的错误,需要前往MaxCompute中给报错的账号授权,详情请参见权限概述。