阿里雲holo交互式分析的jdbc連接及常見問題

阿里雲交互式分析(Holo),可用於數倉查詢加速。底層採用的是postgreSQL協議。其jdbc配置方式與PG完全一致,可參考《JDBC連接PostgreSQL》

下面列舉常見問題。

下列問題整理於2020年2月前。考慮官方會陸續優化,建議先按官方文檔嘗試,再通過本文解決問題。

語法

Holo不支持`字符和COMMENT關鍵字

`字符直接去掉即可,Holo的保留字限定範圍很小,幾乎不會重複。
COMMENT去掉。

賬號權限

下列權限問題,在2020年2月前尚未支持。官方有優化計劃,具體見阿里雲通知。

賬號不存在

Caused by: org.postgresql.util.PSQLException: FATAL: role "[email protected]:xx_user" does not exist
	at org.postgresql.core.v3.QueryExecutorImpl.receiveErrorResponse(QueryExecutorImpl.java:2497)
	at org.postgresql.core.v3.QueryExecutorImpl.readStartupMessages(QueryExecutorImpl.java:2618)
	at org.postgresql.core.v3.QueryExecutorImpl.<init>(QueryExecutorImpl.java:135)
	at org.postgresql.core.v3.ConnectionFactoryImpl.openConnectionImpl(ConnectionFactoryImpl.java:250)
	at org.postgresql.core.ConnectionFactory.openConnection(ConnectionFactory.java:49)
	at org.postgresql.jdbc.PgConnection.<init>(PgConnection.java:195)
	at org.postgresql.Driver.makeConnection(Driver.java:458)
	at org.postgresql.Driver.connect(Driver.java:260)
	at org.apache.commons.dbcp2.DriverConnectionFactory.createConnection(DriverConnectionFactory.java:39)
	at org.apache.commons.dbcp2.PoolableConnectionFactory.makeObject(PoolableConnectionFactory.java:256)
	at org.apache.commons.dbcp2.BasicDataSource.validateConnectionFactory(BasicDataSource.java:2301)
	at org.apache.commons.dbcp2.BasicDataSource.createPoolableConnectionFactory(BasicDataSource.java:2287)

上面這個問題,表示沒有用戶和角色(用戶和角色的區別到底是啥呢?都是create user,是按能否登陸區別user和role?但權限的部分完全一樣?)。
實際上已經用官方文檔說明的create user "p4_賬號uid(RAM頁面獲取的xx_user的uid)";方式添加過用戶;看到這個提醒,懷疑上面這個無效,用CREATE USER "[email protected]:xx_user"的方式再添加了一遍,就不提示無用戶了。

沒有表權限

上面問題解決後,又遇到了java.sql.SQLException: ERROR: permission denied for foreign table xxx錯誤。

先檢查holostudio權限的配置:
我是通過GRANT SELECT,INSERT,UPDATE ON ALL TABLES IN SCHEMA public to PUBLIC;的方式給所有用戶授權了,在HoloStudio運行SQL查詢是正常的。

  • to PUBLIC是指授給所有用戶;
  • holo目前還不支持create schema,默認的schema是public。這個schema與mysql的schema不是一個概念:MySQL schema等同於database,holo的schema與其他對象的關係如下:
    在這裏插入圖片描述

在jdbc中還是會報錯。最終在url中添加preferQueryMode=simple&tcpKeepAlive=true參數後,權限正常。

庫表和數據類型

Holo外部表與ODPS表列無需完全對應

無需對應的部分是指:

  • 外部表的字段可以比ODPS表少
  • 外部表名稱與ODPS表無需保持一致

需要嚴格對應的部分有:

  • 外部表與ODPS表的分區列一定要一致
  • 外部表中列的類型與ODPS表的列要保持一致

HoloStudio的pg管理支持一鍵映射外部表,但容易出錯

一旦有類型映射不同,pg管理中會直接報錯。

  • 這裏支持的類型與實際支持類型會有出入。
  • 會映射全部字段,如果odps表存在holo不支持的類型、但其實Holo本身也不需要的字段,會導致映射失敗。

因爲上述問題帶來的不變,暫時建議還是使用數據開發手工組織ddl腳本。如果有一天該功能支持了自動更新schema,可以再用起來。

數據類型

ODPS2開始,已經新增了較多的數據類型,如tinyint、date、decimal等。但Holo對ODPS的支持並未完全同步,有如下問題:

不支持tinyint、smallint類型

holo完全不支持這三種類型:
tinyint和smallint,需要在odps表中的列類型改爲int或bigint,才能通過holo訪問表。

官方文檔說smallint可以轉化爲int2,親測尚未支持。

注意:
odps表的類型一定要改掉。odps不改、只在holo ddl中修改,雖然Holo外部表可以建立,但執行時會報錯:ERROR: Query:[20051919746691163] Get result failed: expected column type Oid:23, however real type Oid:21 of data row whose column index:1

不支持date類型

date類型建議在odps表改爲STRING或DATETIME。

在holo ddl中直接聲明爲date不會報錯,但一旦使用該列作爲條件或結果,會報錯:
ERROR: Query:[20032452110981017] Get result failed: exec sql failed => status:7 msg:ERROR: AXF Exception: Open ORC file failed for schema mismatch. Reader schema: column_xxx1:VT_INTEGER,column_xxx2:VT_INTEGER,column_xxxn:VT_INTEGER
這個錯誤是看不出任何關係的,查了好久。

不支持DATETIME類型,但可以轉化爲TIMETAMPTZ

即帶時區的時間類型,timestamptz等價於timestamp with tz

不支持STRING類型,但可以轉化爲TEXT

語義和效果一樣,只是關鍵字的區別。

常見的類型聲明錯誤

  • 如果是HOLO不支持的類型,在holoStudio寫DDL時就會提示。
  • 如果是ODPS類型與HOLO類型映射錯誤,在SQL運行時纔會提示,錯誤日誌如下:
    ERROR: Query:[20051919746691163] Get result failed: expected column type Oid:23, however real type Oid:21 of data row whose column index:1

性能問題

不要使用默認數據庫postgres

holo實例默認會建一個postgres庫,但該庫分配資源少。
官方建議新增一個數據庫用來處理實際業務,可參考《在HoloStudio中新增數據庫》

如果在HoloStudio中看不到新增的庫,可能有兩個原因:

  • 沒有刷新HoloStudio頁面
  • 新增庫後,刪掉了postgres庫的關聯,可能會導致該問題

掃描分區數默認不超過50個

如果執行SQL時遇到下面的報錯:

ERROR: Query:[20011148508652324] Get result failed: 
	exec sql failed => status:7 msg:
		ERROR:  AXF Exception: specified partitions count in odps table: odps_workspace.table_xxx is: 89, 
		        exceeds the limitation of 50, please add stricter partition filter or set axf_odps_partition_limit.

這表示你掃描的分區超過了默認限定的50。
Holo出於檢索效率、內存資源的考慮,限制掃描分區數默認不超過50個,最大不能超過1024個。
對於這個限制有幾種解決方式:

  • 優化分區裁剪

  • 使用cluster table替代分區
    odps的cluster table,多bucket可以實現並行計算,只是不能像分區可以重建。按業務情況選用

  • 調大默認配置到1024,使用命令set seahawks.axf_odps_partition_limit = 512
    該命令對session有效,意味着每次查詢前都要執行。
    該命令在HoloStudio終端菜單中可執行、SQL開發中不能執行。JDBC在執行查詢語句前,先執行該句。

    MyBatis中在sql前加上這句是不行的,需要使用同個連接、在執行sql前單獨執行一次該語句。

    該方式的問題在於:掃描的分區多了,查詢時性能肯定會變差,這個要做好權衡。

  • 外部表改爲內部表
    按官方說法,內部表效率比外部表高十倍(應該是從資源分配比例來計算的)。
    但使用內部表,需要配置odps到holo的數據同步任務,並且需按分區指定增量同步。我的業務不適合這種情況,所以沒有使用內部表。

外部表查詢容易OOM

如果你遇到了如下錯誤,則表示holo內部出現了OOM異常:

### Cause: java.sql.SQLException: 
	ERROR: Query:[10001157026468764] Get result failed: exec sql failed => status:7 msg:
		ERROR:  Error dispatching to seg123 11-199-8-163.changba-102-hm.default.svc.cluster.local:22342 pid=55615: (dispatcher.c:1874)
				 SQL: [select xxx from table_xxx where xxx;]; 		
				 uncategorized SQLException for SQL []; SQL state [XX000]; error code [0]; 
				 	ERROR: Query:[10001157026468764] Get result failed: exec sql failed => status:7 msg:ERROR:  Error dispatching to seg123 11-199-8-163.changba-102-hm.default.svc.cluster.local:22342 pid=55615: (dispatcher.c:1874)
  • 後臺調整外部表分配比例
    要聯繫小二評估實際情況,決定是否給調整
  • 提高holo實例配置

HOLO服務端問題

遇到過一個Holo服務端在調整、導致holo查詢報錯的問題:

connect [xxx-in-shanghai-117-shkm.default.svc.cluster.local:22340] failed:could not translate host name "xxx-in-shanghai-117-shkm.default.svc.cluster.local" to address: Name or service not known

費用問題

通過HOLO查詢MaxCompute(ODPS)的數據,無需任何費用。


以上。感謝您的閱讀。

待更新:

  • 添加更多新問題和解決方案
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章