AnalyticDB for MySQL支援通過外表匯入外部資料。本文介紹如何通過外表將OSS的資料匯入AnalyticDB for MySQL叢集。
前提條件
AnalyticDB for MySQL叢集與OSS儲存空間位於同一地區。具體操作,請參見開通OSS服務。
已將資料檔案上傳至OSS目錄中。
AnalyticDB for MySQL數倉版已開啟ENI訪問。
重要登入雲原生資料倉儲AnalyticDB MySQL控制台,在叢集資訊頁面的網路資訊地區,開啟ENI網路開關。
開啟和關閉ENI網路會導致資料庫連接中斷大約2分鐘,無法讀寫。請謹慎評估影響後再開啟或關閉ENI網路。
資料準備
本文樣本將資料檔案person.csv上傳至OSS中的testBucketName/adb/dt=2023-06-15目錄,資料行分隔字元為分行符號,資料行分隔符號為英文逗號(,)。person.csv中的樣本資料如下:
1,james,10,2023-06-15
2,bond,20,2023-06-15
3,jack,30,2023-06-15
4,lucy,40,2023-06-15 操作步驟
企業版、基礎版及湖倉版
進入SQL開發編輯器。
登入雲原生資料倉儲AnalyticDB MySQL控制台,在左上方選擇叢集所在地區。在左側導覽列,單擊集群清單,然後單擊目的地組群ID。
在左側導覽列,單擊。
匯入資料。
資料匯入方式分為常規匯入(預設)和彈性匯入。常規匯入在計算節點中讀取來源資料,然後在儲存節點中構建索引,消耗計算資源和儲存資源。彈性匯入在Serverless Spark Job中讀取來源資料和構建索引,消耗Job型資源群組的資源。僅核心版本3.1.10.0及以上且已建立Job型資源群組的企業版、基礎版及湖倉版叢集支援彈性匯入資料。更多內容,請參見資料匯入方式介紹。
常規匯入
建立外部資料庫。
CREATE EXTERNAL DATABASE adb_external_db;建立外表。使用CREATE EXTERNAL TABLE語句在外部資料庫
adb_external_db中建立OSS外表。本文以adb_external_db.person為例。查詢資料。
資料表建立成功後,您可以在AnalyticDB for MySQL中通過SELECT語句查詢OSS的資料。
SELECT * FROM adb_external_db.person;返回結果如下:
+------+-------+------+-----------+ | id | name | age | dt | +------+-------+------+-----------+ | 1 | james | 10 |2023-06-15 | | 2 | bond | 20 |2023-06-15 | | 3 | jack | 30 |2023-06-15 | | 4 | lucy | 40 |2023-06-15 | +------+-------+------+-----------+在AnalyticDB for MySQL中建立資料庫。如果有已建立的資料庫,可以忽略本步驟。樣本如下:
CREATE DATABASE adb_demo;在AnalyticDB for MySQL中建立表用於儲存從OSS中匯入的資料。樣本如下:
說明建立的內表和步驟b中建立的外表的欄位名稱、欄位數量、欄位順序、欄位類型必須相同。
CREATE TABLE IF NOT EXISTS adb_demo.adb_import_test( id INT, name VARCHAR(1023), age INT, dt VARCHAR(1023) ) DISTRIBUTED BY HASH(id);向表中匯入資料。
方法一:使用
INSERT INTO語句匯入資料,當主鍵重複時會自動忽略當前寫入資料,資料不做更新,作用等同於INSERT IGNORE INTO,更多資訊,請參見INSERT INTO。樣本如下:INSERT INTO adb_demo.adb_import_test SELECT * FROM adb_external_db.person;方法二:使用
INSERT OVERWRITE INTO語句同步匯入資料,會覆蓋表中原有的資料。樣本如下:INSERT OVERWRITE INTO adb_demo.adb_import_test SELECT * FROM adb_external_db.person;方法三:使用
INSERT OVERWRITE INTO語句非同步匯入資料,更多資訊,請參見非同步寫入。樣本如下:SUBMIT JOB INSERT OVERWRITE adb_demo.adb_import_test SELECT * FROM adb_external_db.person;
彈性匯入
建立資料庫。如果有已建立的資料庫,可以忽略本步驟。樣本如下:
CREATE DATABASE adb_demo;建立外表。
說明AnalyticDB for MySQL外表的欄位名稱、欄位數量、欄位順序、欄位類型需要與和OSS檔案相同。
彈性匯入僅支援
CREATE TABLE語句建立外表。
CREATE TABLE oss_import_test_external_table ( id INT(1023), name VARCHAR(1023), age INT, dt VARCHAR(1023) ) ENGINE='OSS' TABLE_PROPERTIES='{ "endpoint":"oss-cn-hangzhou-internal.aliyuncs.com", "url":"oss://testBucketName/adb/dt=2023-06-15/person.csv", "accessid":"accesskey_id", "accesskey":"accesskey_secret", "delimiter":"," }';重要建立外表時,CSV、Parquet、ORC格式的外表支援設定的TABLE_PROPERTIES參數不同:
CSV格式:僅支援設定
endpoint、url、accessid、accesskey、format、delimiter、null_value和partition_column參數。Parquet格式:僅支援設定
endpoint、url、accessid、accesskey、format和partition_column參數。ORC格式:僅支援設定
endpoint、url、accessid、accesskey、format和partition_column參數。
查詢資料。
資料表建立成功後,您可以在AnalyticDB for MySQL中通過SELECT語句查詢OSS的資料。
SELECT * FROM oss_import_test_external_table;返回結果如下:
+------+-------+------+-----------+ | id | name | age | dt | +------+-------+------+-----------+ | 1 | james | 10 |2023-06-15 | | 2 | bond | 20 |2023-06-15 | | 3 | jack | 30 |2023-06-15 | | 4 | lucy | 40 |2023-06-15 | +------+-------+------+-----------+ 4 rows in set (0.35 sec)在AnalyticDB for MySQL中建立表用於儲存從OSS中匯入的資料。樣本如下:
說明建立的內表和步驟b中建立的外表的欄位名稱、欄位數量、欄位順序、欄位類型必須相同。
CREATE TABLE adb_import_test ( id INT, name VARCHAR(1023), age INT, dt VARCHAR(1023) ) DISTRIBUTED BY HASH(id);匯入資料。
重要彈性匯入僅支援通過
INSERT OVERWRITE INTO語句匯入資料。方法一:執行INSERT OVERWRITE INTO彈性匯入資料,會覆蓋表中原有的資料。樣本如下:
/+*elastic_load=true, elastic_load_configs=[adb.load.resource.group.name=resource_group]*/ INSERT OVERWRITE INTO adb_demo.adb_import_test SELECT * FROM adb_demo.oss_import_test_external_table;
方法二:非同步執行INSERT OVERWRITE INTO彈性匯入資料。通常使用
SUBMIT JOB提交非同步任務,由後台調度。/*+elastic_load=true, elastic_load_configs=[adb.load.resource.group.name=resource_group]*/ SUBMIT JOB INSERT OVERWRITE INTO adb_demo.adb_import_test SELECT * FROM adb_demo.oss_import_test_external_table;重要非同步提交彈性匯入任務時,不支援設定優先權隊列。
返回結果如下:
+---------------------------------------+ | job_id | +---------------------------------------+ | 202308151719510210170190********** |
使用
SUBMIT JOB提交非同步任務後,返回結果僅表示非同步任務提交成功。您可以通過job_id終止非同步任務或查詢非同步任務狀態,判斷任務是否執行成功。具體操作,請參見非同步提交匯入任務。Hint參數說明:
elastic_load:是否使用彈性匯入方式。取值:true或false(預設值)。
elastic_load_configs:彈性匯入方式支援配置的參數。參數需使用方括弧([ ])括起來,且多個參數之間以豎線(|)分隔,支援配置的參數如下表所示:
參數
是否必填
說明
adb.load.resource.group.name
是
執行彈性匯入任務的Job資源群組名稱。
adb.load.job.max.acu
否
單個彈性匯入任務最多使用的資源。單位為ACU,最小值為5 ACU。預設值為叢集Shard個數+1。
執行如下語句可查詢叢集Shard個數:
SELECT count(1) FROM information_schema.kepler_meta_shards;spark.driver.resourceSpec
否
Spark driver的資源規格。預設值為small。取值範圍,請參見Spark應用配置參數說明的型號列。
spark.executor.resourceSpec
否
Spark executor的資源規格。預設值為large。取值範圍,請參見Spark應用配置參數說明的型號列。
spark.adb.executorDiskSize
否
Spark executor的磁碟容量,取值範圍為(0,100],單位為GiB,預設值為10 Gi。更多資訊,請參見指定Driver和Executor資源。
(可選)查看已提交的匯入任務是否為彈性匯入任務。
SELECT job_name, (job_type = 3) AS is_elastic_load FROM INFORMATION_SCHEMA.kepler_meta_async_jobs where job_name = "2023081818010602101701907303151******";返回結果如下:
+---------------------------------------+------------------+ | job_name | is_elastic_load | +---------------------------------------+------------------+ | 20230815171951021017019072*********** | 1 | +---------------------------------------+------------------+is_elastic_load的傳回值為1,表示已提交的匯入任務是彈性匯入任務;若為0,則表示已提交的匯入任務是常規匯入任務。
數倉版
串連叢集,建立資料庫。
CREATE DATABASE adb_demo;建立外表。使用CREATE TABLE文法建立CSV、Parquet或ORC格式的OSS外表。具體文法,請參見OSS外表文法。
本文樣本以CSV格式非分區外表為例。
CREATE TABLE IF NOT EXISTS oss_import_test_external_table ( id INT, name VARCHAR(1023), age INT, dt VARCHAR(1023) ) ENGINE='OSS' TABLE_PROPERTIES='{ "endpoint":"oss-cn-hangzhou-internal.aliyuncs.com", "url":"oss://testBucketname/adb/dt=2023-06-15/person.csv", "accessid":"accesskey_id", "accesskey":"accesskey_secret", "delimiter":",", "skip_header_line_count":0, "charset":"utf-8" }';查詢
oss_import_test_external_table外表資料。說明對於CSV格式、Parquet和ORC格式資料檔案,資料量越大,通過外表查詢的效能損耗越大。如果您需要進一步提升查詢效率,建議您按照後續步驟(4~5)將OSS外表資料匯入AnalyticDB for MySQL後再做查詢。
SELECT * FROM oss_import_test_external_table;在AnalyticDB for MySQL中建立表,用於儲存從OSS外表匯入的資料。
CREATE TABLE IF NOT EXISTS adb_oss_import_test ( id INT, name VARCHAR(1023), age INT, dt VARCHAR(1023) ) DISTRIBUTED BY HASH(id);執行INSERT語句將OSS外表資料匯入AnalyticDB for MySQL。
重要使用
INSERT INTO或INSERT OVERWRITE SELECT匯入資料時,預設是同步執行流程。如果資料量較大,達到幾百GB,用戶端到AnalyticDB for MySQL服務端的串連需要保持較長時間。在此期間,可能會因為網路因素導致串連中斷,進而導致資料匯入失敗。因此,如果您的資料量較大時,推薦使用SUBMIT JOB INSERT OVERWRITE SELECT非同步執行匯入。方式一:執行
INSERT INTO匯入資料,當主鍵重複時會自動忽略當前寫入資料,不進行更新覆蓋,作用等同於INSERT IGNORE INTO,詳情請參見INSERT INTO。樣本如下:INSERT INTO adb_oss_import_test SELECT * FROM oss_import_test_external_table;方式二:執行INSERT OVERWRITE匯入資料,會覆蓋表中原有的資料。樣本如下:
INSERT OVERWRITE adb_oss_import_test SELECT * FROM oss_import_test_external_table;方式三:非同步執行
INSERT OVERWRITE匯入資料。 通常使用SUBMIT JOB提交非同步任務,由後台調度,可以在寫入任務前增加Hint(/*+ direct_batch_load=true*/)加速寫入任務。詳情請參見非同步寫入。樣本如下:SUBMIT JOB INSERT OVERWRITE adb_oss_import_test SELECT * FROM oss_import_test_external_table;返回結果如下:
+---------------------------------------+ | job_id | +---------------------------------------+ | 2020112122202917203100908203303****** |關於非同步提交任務詳情,請參見非同步提交匯入任務。
OSS外表文法
企業版、基礎版及湖倉版
企業版、基礎版及湖倉版OSS外表的文法及相關說明,請參見OSS外表。
數倉版
OSS非分區外表
CREATE TABLE [IF NOT EXISTS] table_name
(column_name column_type[, …])
ENGINE='OSS'
TABLE_PROPERTIES='{
"endpoint":"endpoint",
"url":"OSS_LOCATION",
"accessid":"accesskey_id",
"accesskey":"accesskey_secret",
"format":"csv|orc|parquet|text
"delimiter|field_delimiter":";",
"skip_header_line_count":1,
"charset":"utf-8"
}';外表類型 | 參數 | 是否必填 | 說明 |
CSV格式、Parquet格式和ORC格式外表 | ENGINE='OSS' | 是 | 表引擎,固定填寫為OSS。 |
endpoint | OSS的EndPoint(地區節點)。 目前僅支援AnalyticDB for MySQL通過VPC網路訪問OSS。 說明 您可登入OSS控制台,單擊目標Bucket,在Bucket概覽頁面查看EndPoint(地區節點)。 | ||
url | 指定OSS檔案或目錄所在的路徑。
| ||
accessid | 阿里雲帳號或者具備OSS系統管理權限的RAM使用者的AccessKey ID。 如何擷取AccessKey ID,請參見帳號與許可權。 | ||
accesskey | 阿里雲帳號或者具備OSS系統管理權限的RAM使用者的AccessKey Secret。 如何擷取AccessKey Secret,請參見帳號與許可權。 | ||
format | 條件必填 | 資料檔案的格式。
| |
CSV格式和Text格式外表 | delimiter|field_delimiter | 是 | 定義資料檔案的資料行分隔符號。
|
CSV格式外表 | null_value | 否 | 定義CSV資料檔案的 重要 僅核心版本為3.1.4.2及以上的叢集支援配置該參數。 |
ossnull | 選擇CSV資料檔案中
說明 上述各樣本的前提為 | ||
skip_header_line_count | 定義匯入資料時需要在開頭跳過的行數。CSV檔案第一行為表頭,若設定該參數為1,匯入資料時可自動跳過第一行的表頭。 預設取值為0,即不跳過。 | ||
oss_ignore_quote_and_escape | 是否忽略欄位值中的引號和轉義。預設取值為false,即不忽略欄位值中的引號和轉義。 重要 僅核心版本為3.1.4.2及以上的叢集支援配置該參數。 | ||
charset | OSS外表字元集,取值說明:
重要 僅核心版本為3.1.10.4及以上的叢集支援配置該參數。 |
外表建立語句中的列名需與Parquet或ORC檔案中該列的名稱完全相同(可忽略大小寫),且列的順序需要一致。
建立外表時,可以僅選擇Parquet或ORC檔案中的部分列作為外表中的列,未被選擇的列不會被匯入。
如果建立外表建立語句中出現了Parquet或ORC檔案中不存在的列,針對該列的查詢結果均會返回NULL。
AnalyticDB for MySQL支援通過OSS的CSV格式的外表讀寫Hive TEXT檔案。建表語句如下:
CREATE TABLE adb_csv_hive_format_oss (
a tinyint,
b smallint,
c int,
d bigint,
e boolean,
f float,
g double,
h varchar,
i varchar, -- binary
j timestamp,
k DECIMAL(10, 4),
l varchar, -- char(10)
m varchar, -- varchar(100)
n date
) ENGINE = 'OSS' TABLE_PROPERTIES='{
"format": "csv",
"endpoint":"oss-cn-hangzhou-internal.aliyuncs.com",
"accessid":"accesskey_id",
"accesskey":"accesskey_secret",
"url":"oss://testBucketname/adb_data/",
"delimiter": "\\1",
"null_value": "\\\\N",
"oss_ignore_quote_and_escape": "true",
"ossnull": 2
}';在建立OSS的CSV格式的外表來讀取Hive TEXT檔案時,需注意如下幾點:
Hive TEXT檔案的預設資料行分隔符號為
\1。若您需要通過OSS的CSV格式的外表讀寫Hive TEXT檔案,您可以在配置delimiter參數時將其轉義為\\1。Hive TEXT檔案的預設
NULL值為\N。若您需要通過OSS的CSV格式的外表讀寫Hive TEXT檔案,您可以在配置null_value參數時將其轉義為\\\\N。Hive的其他基礎資料型別 (Elementary Data Type)(如
BOOLEAN)與AnalyticDB for MySQL的資料類型一一對應,但BINARY、CHAR(n)和VARCHAR(n)類型均對應AnalyticDB for MySQL中的VARCHAR類型。
附錄:資料類型映射關係
建表指定的資料類型必須遵循以下表格中的對應關係。特別是
DECIMAL類型,其精度也需保持一致。Parquet格式外表暫不支援
STRUCT類型,會導致建表失敗。ORC格式外表暫不支援
LIST、STRUCT和UNION等複合類型,會導致建表失敗。ORC格式外表的列使用MAP類型可以建表,但ORC的查詢會失敗。
Parquet檔案與AnalyticDB for MySQL的資料類型映射關係
Parquet基本類型 | Parquet的logicalType類型 | AnalyticDB for MySQL的資料類型 |
BOOLEAN | 無 | BOOLEAN |
INT32 | INT_8 | TINYINT |
INT32 | INT_16 | SMALLINT |
INT32 | 無 | INT或INTEGER |
INT64 | 無 | BIGINT |
FLOAT | 無 | FLOAT |
DOUBLE | 無 | DOUBLE |
| DECIMAL | DECIMAL |
BINARY | UTF-8 |
|
INT32 | DATE | DATE |
INT64 | TIMESTAMP_MILLIS | TIMESTAMP或DATETIME |
INT96 | 無 | TIMESTAMP或DATETIME |
ORC檔案與AnalyticDB for MySQL的資料類型映射關係
ORC檔案中的資料類型 | AnalyticDB for MySQL中的資料類型 |
BOOLEAN | BOOLEAN |
BYTE | TINYINT |
SHORT | SMALLINT |
INT | INT或INTEGER |
LONG | BIGINT |
DECIMAL | DECIMAL |
FLOAT | FLOAT |
DOUBLE | DOUBLE |
|
|
TIMESTAMP | TIMESTAMP或DATETIME |
DATE | DATE |
Paimon檔案與AnalyticDB for MySQL的資料類型映射關係
Paimon檔案中的資料類型 | AnalyticDB for MySQL中的資料類型 |
CHAR | VARCHAR |
VARCHAR | VARCHAR |
BOOLEAN | BOOLEAN |
BINARY | VARBINARY |
VARBINARY | VARBINARY |
DECIMAL | DECIMAL |
TINYINT | TINYINT |
SMALLINT | SMALLINT |
INT | INTEGER |
BIGINT | BIGINT |
FLOAT | REAL |
DOUBLE | DOUBLE |
DATE | DATE |
TIME | 不支援 |
TIMESTAMP | TIMESTAMP |
LocalZonedTIMESTAMP | TIMESTAMP(忽略本地時區資訊) |
ARRAR | ARRAR |
MAP | MAP |
ROW | ROW |