选择 Python 库

您可以根据自己的应用场景在 BigQuery 的三个 Python 库中进行选择。

使用场景 维护方式 说明
BigQuery DataFrame 通过服务器端处理(例如使用槽)进行基于 Python 的数据处理和机器学习操作 Google 通过服务器端下推实现了 Pandas 和 Scikit learn API。如需了解详情,请参阅 BigQuery DataFrames 简介
pandas-gbq 使用客户端数据复制进行基于 Python 的数据处理 这是由 PyData 和志愿贡献者维护的开放源代码库 可让您在客户端将数据移入和移出 Python DataFrame。如需了解详情,请参阅相关文档源代码
google-cloud-bigquery BigQuery 部署、管理和基于 SQL 的查询 由 Google 维护的开放源代码库 封装所有 BigQuery API 的 Python 软件包。如需了解详情,请参阅相关文档源代码

使用 pandas-gbq 和 google-cloud-bigquery

pandas-gbq 库提供了一个用于运行查询以及将 pandas DataFrame 上传到 BigQuery 的简单接口。它是 BigQuery 客户端库 google-cloud-bigquery 的瘦封装容器。这两个库都专注于帮助您使用 SQL 执行数据分析。

安装库

要使用本指南中的代码示例,请安装 pandas-gbq 软件包和 BigQuery Python 客户端库。

安装 pandas-gbqgoogle-cloud-bigquery 软件包。

pip install --upgrade pandas-gbq 'google-cloud-bigquery[bqstorage,pandas]'

运行查询

两个库都支持查询 BigQuery 中存储的数据。二者的主要区别如下所示:

pandas-gbq google-cloud-bigquery
默认 SQL 语法 GoogleSQL(可使用 pandas_gbq.context.dialect 配置) GoogleSQL
查询配置 按照查询请求的格式以字典形式发送。 使用 QueryJobConfig 类,其中包含各种 API 配置选项的属性。

使用 GoogleSQL 语法查询数据

以下示例演示了如何在明确指定项目和未明确指定项目的情况下运行 GoogleSQL 查询。对于这两个库,如果未指定项目,则系统将根据默认凭据确定项目。

pandas-gbq

import pandas

sql = """
    SELECT name
    FROM `bigquery-public-data.usa_names.usa_1910_current`
    WHERE state = 'TX'
    LIMIT 100
"""

# Run a Standard SQL query using the environment's default project
df = pandas.read_gbq(sql, dialect="standard")

# Run a Standard SQL query with the project set explicitly
project_id = "your-project-id"
df = pandas.read_gbq(sql, project_id=project_id, dialect="standard")

google-cloud-bigquery

from google.cloud import bigquery

client = bigquery.Client()
sql = """
    SELECT name
    FROM `bigquery-public-data.usa_names.usa_1910_current`
    WHERE state = 'TX'
    LIMIT 100
"""

# Run a Standard SQL query using the environment's default project
df = client.query(sql).to_dataframe()

# Run a Standard SQL query with the project set explicitly
project_id = "your-project-id"
df = client.query(sql, project=project_id).to_dataframe()

使用旧版 SQL 语法查询数据

以下示例演示了如何使用旧版 SQL 语法运行查询。如需了解如何将查询更新为采用 GoogleSQL,请参阅 GoogleSQL 迁移指南

pandas-gbq

import pandas

sql = """
    SELECT name
    FROM [bigquery-public-data:usa_names.usa_1910_current]
    WHERE state = 'TX'
    LIMIT 100
"""

df = pandas.read_gbq(sql, dialect="legacy")

google-cloud-bigquery

from google.cloud import bigquery

client = bigquery.Client()
sql = """
    SELECT name
    FROM [bigquery-public-data:usa_names.usa_1910_current]
    WHERE state = 'TX'
    LIMIT 100
"""
query_config = bigquery.QueryJobConfig(use_legacy_sql=True)

df = client.query(sql, job_config=query_config).to_dataframe()

使用 BigQuery Storage API 下载大型结果

使用 BigQuery Storage API 将大型结果的下载速度提高 15 至 31 倍

pandas-gbq

import pandas

sql = "SELECT * FROM `bigquery-public-data.irs_990.irs_990_2012`"

# Use the BigQuery Storage API to download results more quickly.
df = pandas.read_gbq(sql, dialect="standard", use_bqstorage_api=True)

google-cloud-bigquery

from google.cloud import bigquery

client = bigquery.Client()
sql = "SELECT * FROM `bigquery-public-data.irs_990.irs_990_2012`"

# The client library uses the BigQuery Storage API to download results to a
# pandas dataframe if the API is enabled on the project, the
# `google-cloud-bigquery-storage` package is installed, and the `pyarrow`
# package is installed.
df = client.query(sql).to_dataframe()

通过配置运行查询

要执行某些复杂操作(例如运行参数化查询或指定目标表来存储查询结果),需要通过 BigQuery API 请求发送配置。在 pandas-gbq 中,必须按照查询请求的格式以字典形式发送配置。google-cloud-bigquery 提供了作业配置类(例如 QueryJobConfig),其中包含用于配置复杂作业的必要属性。

以下示例演示了如何使用指定参数运行查询。

pandas-gbq

import pandas

sql = """
    SELECT name
    FROM `bigquery-public-data.usa_names.usa_1910_current`
    WHERE state = @state
    LIMIT @limit
"""
query_config = {
    "query": {
        "parameterMode": "NAMED",
        "queryParameters": [
            {
                "name": "state",
                "parameterType": {"type": "STRING"},
                "parameterValue": {"value": "TX"},
            },
            {
                "name": "limit",
                "parameterType": {"type": "INTEGER"},
                "parameterValue": {"value": 100},
            },
        ],
    }
}

df = pandas.read_gbq(sql, configuration=query_config)

google-cloud-bigquery

from google.cloud import bigquery

client = bigquery.Client()
sql = """
    SELECT name
    FROM `bigquery-public-data.usa_names.usa_1910_current`
    WHERE state = @state
    LIMIT @limit
"""
query_config = bigquery.QueryJobConfig(
    query_parameters=[
        bigquery.ScalarQueryParameter("state", "STRING", "TX"),
        bigquery.ScalarQueryParameter("limit", "INTEGER", 100),
    ]
)

df = client.query(sql, job_config=query_config).to_dataframe()

将 pandas DataFrame 数据加载到 BigQuery 表中

两个库都支持将 pandas DataFrame 中的数据上传到 BigQuery 中的新表。二者的主要区别如下所示:

pandas-gbq google-cloud-bigquery
类型支持 将要发送到 API 的 DataFrame 数据转换为 CSV 格式,该格式不支持嵌套值或数组值。 将要发送到 API 的 DataFrame 数据转换为 Parquet 或 CSV 格式,该格式支持嵌套值和数组值。可选择 Parquet 以用于结构体和数组值,选择 CSV 以实现日期和时间序列化灵活性。Parquet 是默认选项。请注意,pyarrow 是用于将 DataFrame 数据发送到 BigQuery API 的 parquet 引擎,因此必须安装该引擎才能将 DataFrame 数据加载到表中。
加载配置 您可以视需要指定表架构 使用 LoadJobConfig 类,其中包含各种 API 配置选项的属性。

pandas-gbq

import pandas

df = pandas.DataFrame(
    {
        "my_string": ["a", "b", "c"],
        "my_int64": [1, 2, 3],
        "my_float64": [4.0, 5.0, 6.0],
        "my_timestamp": [
            pandas.Timestamp("1998-09-04T16:03:14"),
            pandas.Timestamp("2010-09-13T12:03:45"),
            pandas.Timestamp("2015-10-02T16:00:00"),
        ],
    }
)
table_id = "my_dataset.new_table"

df.to_gbq(table_id)

google-cloud-bigquery

google-cloud-bigquery 软件包要求 pyarrow 库将 pandas DataFrame 序列化为 Parquet 文件。

安装 pyarrow 软件包。

 pip install pyarrow

from google.cloud import bigquery
import pandas

df = pandas.DataFrame(
    {
        "my_string": ["a", "b", "c"],
        "my_int64": [1, 2, 3],
        "my_float64": [4.0, 5.0, 6.0],
        "my_timestamp": [
            pandas.Timestamp("1998-09-04T16:03:14"),
            pandas.Timestamp("2010-09-13T12:03:45"),
            pandas.Timestamp("2015-10-02T16:00:00"),
        ],
    }
)
client = bigquery.Client()
table_id = "my_dataset.new_table"
# Since string columns use the "object" dtype, pass in a (partial) schema
# to ensure the correct BigQuery data type.
job_config = bigquery.LoadJobConfig(
    schema=[
        bigquery.SchemaField("my_string", "STRING"),
    ]
)

job = client.load_table_from_dataframe(df, table_id, job_config=job_config)

# Wait for the load job to complete.
job.result()

pandas-gbq 不支持的功能

虽然 pandas-gbq 库提供了一个可以查询数据并将数据写入表中的实用接口,但它并不具备 BigQuery API 的众多功能,包括但不限于:

排查连接池错误

错误字符串:Connection pool is full, discarding connection: bigquery.googleapis.com. Connection pool size: 10

如果在 Python 中使用默认的 BigQuery 客户端对象,则您最多只能使用 10 个线程,因为 Python HTTPAdapter 的默认池大小为 10。如需使用 10 个以上的连接,请创建自定义 requests.adapters.HTTPAdapter 对象。例如:

client = bigquery.Client()
adapter = requests.adapters.HTTPAdapter(pool_connections=128,
pool_maxsize=128,max_retries=3)
client._http.mount("https://",adapter)
client._http._auth_request.session.mount("https://",adapter)
query_job = client.query(QUERY)