如何在BigQuery中通过SQL加载GCS上动态命名的CSV文件?
问题:BigQuery调度每日LOAD DATA任务加载动态命名的GCS CSV文件
需要在BigQuery中调度每日查询任务,使用LOAD DATA语句加载GCS存储桶中每日生成的CSV文件,文件名格式为随机哈希_YYYY-MM-DD.csv(示例:7c4615_2024-08-28.csv)。
尝试以下SQL后无法正常运行:
DECLARE URI array<string> default ['gs://my_bucket/*_' || format_date('%Y-%m-%d', current_date) || '.csv']; load data overwrite `<PROJECT>.<DATASET>.<TABLE_NAME>`(name string) FROM FILES ( format = 'CSV', uris = URI);
报错信息:
Query error: Unable to determine if URI is a string or expression. If a string is intended, please enclose it with quotation marks. If an expression is intended, please enclose it with parentheses.
核心问题是LOAD DATA语句的uris参数不支持直接引用变量,以下是两种可行的解决方案:
解决方案1:使用EXECUTE IMMEDIATE动态生成SQL
通过动态拼接完整的LOAD DATA语句,将生成的目标URI直接嵌入SQL字符串后执行,这是最简洁的实现方式:
DECLARE sql_query STRING; DECLARE target_uri STRING; -- 生成当日目标文件的通配符URI SET target_uri = 'gs://my_bucket/*_' || FORMAT_DATE('%Y-%m-%d', CURRENT_DATE()) || '.csv'; -- 拼接LOAD DATA语句 SET sql_query = """ LOAD DATA OVERWRITE `<PROJECT>.<DATASET>.<TABLE_NAME>`(name string) FROM FILES ( format = 'CSV', uris = ['""" || target_uri || """'] ); """; -- 执行动态生成的SQL EXECUTE IMMEDIATE sql_query;
解决方案2:先查询GCS文件列表再加载
如果需要精确匹配当日文件(避免通配符误匹配),可以先通过EXTERNAL_QUERY获取GCS中符合日期条件的文件URI列表,再动态执行LOAD DATA:
DECLARE uris_array ARRAY<STRING>; -- 获取当日目标文件的URI列表(需先创建GCS外部连接) SET uris_array = ( SELECT ARRAY_AGG(CONCAT('gs://my_bucket/', name)) FROM EXTERNAL_QUERY( '<PROJECT>.<DATASET>.gcs_connection', -- 替换为你的GCS外部连接名称 "SELECT name FROM `my_bucket` WHERE name LIKE '%_" || FORMAT_DATE('%Y-%m-%d', CURRENT_DATE()) || ".csv'" ) ); -- 动态执行LOAD DATA,传入URI数组 EXECUTE IMMEDIATE """ LOAD DATA OVERWRITE `<PROJECT>.<DATASET>.<TABLE_NAME>`(name string) FROM FILES ( format = 'CSV', uris = @uris ) """ USING uris_array AS uris;
说明:方案2需要提前创建GCS与BigQuery的外部连接,适合对文件匹配精度要求较高的场景;方案1无需额外配置,适合按通配符批量加载的场景。
内容的提问来源于stack exchange,提问作者o_yeah
相关产品推荐
相关产品推荐

