讀取

本頁面說明可傳送至 Bigtable 的讀取要求類型、效能影響,並針對特定類型的查詢提供一些建議。閱讀本頁面前,請先熟悉 Bigtable 總覽。

總覽

對 Bigtable 的讀取要求會依索引鍵順序,串流傳回所要求資料列的內容,也就是依儲存順序傳回。您可以讀取任何已傳回回應的寫入作業。

資料表支援的查詢應有助於判斷最適合您用途的讀取類型。Bigtable 讀取要求大致分為兩類:

  • 讀取單一資料列
  • 掃描或讀取多個資料列

如要查看讀取流量在查詢類型 (例如點讀取、短掃描、反向掃描、稀疏讀取和大量讀取) 的分布情形,請參閱「分析存取模式」。

讀取作業在資料列層級是不可部分完成的。也就是說,當您傳送資料列讀取要求時,Bigtable 會傳回整個資料列,或在要求失敗時不傳回任何資料列。除非您明確要求,否則系統不會傳回部分資料列。

強烈建議您使用 Cloud Bigtable 用戶端程式庫讀取資料表中的資料,而非直接呼叫 API。我們提供多種語言的程式碼範例,示範如何傳送讀取要求。所有讀取要求都會發出 ReadRows API 呼叫。

使用 Data Boost 無伺服器運算讀取資料

Bigtable Data Boost 可讓您執行高處理量讀取工作,不會影響服務路徑應用程式流量。Data Boost 是一項無伺服器運算服務,可讓您讀取 Bigtable 資料,同時核心應用程式會使用叢集的節點進行運算。Enterprise Plus 擴充 Data Boost 查詢功能,支援 SQL 並可存取 HDD 和分級式儲存空間資料。

Data Boost 非常適合用於掃描,但不建議用於單一資料列讀取。Data Boost 無法用於反向掃描。如要瞭解詳情和資格條件,請參閱「Data Boost 總覽」。

單一資料列讀取

您可以根據資料列索引鍵要求單一資料列。單列讀取 (也稱為點讀取) 與 Data Boost 不相容。下列變化版本提供程式碼範例:

掃描檔

掃描是最常見的 Bigtable 資料讀取方式。您可以指定資料列索引鍵前置字元,或指定起始和結束資料列索引鍵,從 Bigtable 讀取一系列連續資料列或多個資料列範圍。我們提供下列變化版本的程式碼範例:

反向掃描

反向掃描可讓您指定資料列索引鍵前置字串或資料列範圍,反向讀取資料列範圍。資料列索引鍵前置字串會做為掃描的起始點,向後讀取。如果指定資料列範圍,系統會以結束資料列索引鍵做為掃描的起始點。

反向掃描適用於下列情況:

反向掃描的效率低於正向掃描。一般來說,請設計資料列索引鍵,讓大多數掃描作業向前進行。如要進行短時間掃描 (例如 50 列以下),請使用反向掃描,以維持低延遲回應時間。

如要反向掃描,請將 ReadRowsRequest 欄位 reversed 的值設為 true。預設值為 false。

使用下列用戶端程式庫時,可進行反向掃描:

  • C++ 專用 Bigtable 用戶端程式庫 2.18.0 以上版本
  • Go 專用 Bigtable 用戶端程式庫 1.21.0 以上版本
  • Java 適用的 Bigtable 用戶端程式庫 2.24.1 以上版本
  • Java 版 Bigtable HBase 用戶端 2.10.0 以上版本

如需示範如何使用反向掃描的程式碼範例,請參閱「反向掃描」。

應用實例範例

以下範例說明如何使用反向掃描,找出客戶上次變更密碼的時間,以及某項產品在特定日期前後的價格波動。

重設密碼

假設您的資料列索引鍵都包含客戶 ID 和日期,格式為 123ABC#2022-05-02,其中一個資料欄為 password_reset,用於儲存密碼重設的時間。Bigtable 會自動依字典順序儲存資料,如下所示。請注意,如果密碼未重設,則該資料列 (日期) 不會顯示這個資料欄。

`123ABC#2022-02-12,password_reset:03`
`123ABC#2022-04-02,password_reset:11`
`123ABC#2022-04-14`
`123ABC#2022-05-02`
`223ABC#2022-05-22`

如要找出客戶 123ABC 上次重設密碼的時間,可以使用今天或未來的日期,反向掃描 123ABC# 至 123ABC#<DATE> 的範圍,找出所有包含 password_reset 欄的資料列,並將資料列限制設為 1。

價格異動

在這個範例中,資料列索引鍵包含產品、型號和時間戳記的值,其中一個資料欄則包含產品和型號在特定時間的價格。

`productA#model2#1675604471,price:82.63`
`productA#model2#1676219411,price:82.97`
`productA#model2#1677681011,price:83.15`
`productA#model2#1680786011,price:83.99`
`productA#model2#1682452238,price:83.12`

如要找出 2023 年 2 月 14 日前後的價格波動,即使資料表中沒有該特定日期的資料列索引鍵,您也可以從資料列索引鍵 productA#model2#1676376000 開始向前掃描 N 個資料列,然後從同一個起始資料列向後掃描相同數量的資料列。這兩次掃描會提供指定時間前後的價格。

經過篩選的讀取

如果只需要包含特定值或部分資料列,可以在讀取要求中使用篩選器。篩選器可讓您精準挑選所需資料。

篩選器還能確保讀取作業符合資料表使用的垃圾收集政策。如果您經常將新的時間戳記儲存格寫入現有資料欄,這項功能就特別實用。由於垃圾收集最多可能需要一週才能移除過期資料,因此使用時間戳記範圍篩選器讀取資料,可確保不會讀取超過所需的資料。

篩選器總覽詳細說明瞭可用的篩選器類型。「使用篩選器」一節提供多種語言的範例。

讀取授權檢視表中的資料

如要從授權檢視表讀取資料,您必須使用下列其中一項:

  • gcloud CLI
  • Java 適用的 Bigtable 用戶端

其他 Bigtable 用戶端程式庫尚不支援檢視權限。

只要是呼叫 Bigtable Data API 的 ReadRows 或 SampleRowKeys 方法,都支援。建立用戶端時,除了資料表 ID 外,您還須提供授權檢視表 ID。

讀取持續性 materialized view 的資料

您可以使用 SQL 或 ReadRows Data API 呼叫,從連續 materialized view 讀取資料。持續性 materialized view 屬於唯讀內容。materialized view 中的資料會根據定義該檢視表的查詢來決定類型。

SQL

如要使用 SQL 讀取持續性 materialized view 的資料,可以使用 Bigtable Studio 查詢編輯器,或支援 SQL 查詢的用戶端程式庫。

SQL 會自動將查詢結果顯示為已指定類型和格式的欄,因此您不必在查詢中處理編碼。

建立連續 materialized view 時,Bigtable 會自動為資料表建立資料列索引鍵結構定義,定義 view 的結構化資料列索引鍵。如要進一步瞭解如何使用 SQL 查詢結構化資料列索引鍵,請參閱「結構化資料列索引鍵查詢」。

在初始填入期間讀取資料

在現有資料表建立連續 materialized view 時,Bigtable 會啟動初始填入程序,將現有資料表資料複製到檢視表。

根據預設,為確保資料正確性,Bigtable 會拒絕在建立檢視表時,嘗試從連續 materialized view 讀取資料的讀取要求。如果查詢仍在填入資料的檢視表,Bigtable 會傳回 Materialized view is still creating. 錯誤。錯誤的狀態碼為 FAILED_PRECONDITION。

如果應用程式可以容許不完整的資料,您可以在初始母體完成前,選擇加入從檢視表讀取資料。如要在初始母體期間從連續 materialized view 讀取資料,請在 SQL 查詢中加入 allow_incomplete_view=true 陳述式層級查詢提示:

SELECT key_part FROM `VIEW_ID` @{allow_incomplete_view=true}

將 VIEW_ID 替換為連續 materialized view 的專屬 ID。

詳情請參閱「在現有資料表上建立連續 materialized view」。

資料 API

如果您打算使用 Bigtable 的其中一個用戶端程式庫,透過 ReadRows 呼叫讀取持續增補的 materialized view,請查看用於定義 view 的 SQL 查詢。請留意檢視表是否已定義 _key 欄 (建議使用 ReadRows 讀取的檢視表),以及是否具有 _timestamp 欄。

您也必須瞭解每個資料欄的類型,並在應用程式程式碼中解碼資料欄資料。

連續 materialized view 中的匯總值會根據檢視表定義中資料欄的輸出類型,使用下表所述的編碼方式儲存。

類型 編碼
BOOL 1 位元組值,1 = true,0 = false
BYTES 不編碼
INT64 (或 INT、SMALLINT、INTEGER、BIGINT、TINYINT、BYTEINT) 64 位元大端序
FLOAT64 64 位元 IEEE 754,不含 NaN 和 +/-inf
STRING UTF-8
TIME/TIMESTAMP 64 位元整數,代表自 Unix 紀元起算的微秒數 (與 GoogleSQL 一致)
詳情請參閱 Data API 參考資料中的編碼。

除了瞭解檢視表中每個資料欄的類型外,您還需要瞭解資料欄系列和資料欄限定詞。預設資料欄系列稱為 default,資料欄限定詞則是定義查詢中指定的別名。舉例來說,假設您使用以下查詢定義持續性 materialized view:

SELECT
  _key,
  SUM(clicks) AS sum_clicks
FROM
  mytable
GROUP BY
  sum_clicks

使用 ReadRows 查詢檢視表時,您需要提供資料欄系列 default 和資料欄限定詞 sum_clicks。

讀取和效能

使用篩選器的讀取作業比不使用篩選器的讀取作業慢,且會增加 CPU 使用率。另一方面,這些方法可以限制傳回的資料量,大幅減少網路頻寬用量。一般來說,篩選器應用於控制處理量效率,而非延遲時間。

如要最佳化讀取效能,請考慮下列策略:

  1. 盡可能限制資料列集。如要縮短 Time to First Byte 和整體查詢延遲時間,第一步是限制節點必須掃描的資料列數量。如果未限制資料列集,Bigtable 幾乎肯定會掃描整個資料表。因此,建議您設計結構定義,讓最常見的查詢能以這種方式運作。

  2. 限制資料列集後,如要進一步調整效能,請嘗試新增基本篩選器。限制傳回的資料欄組合或版本數量,通常不會增加延遲時間,有時還能協助 Bigtable 更有效率地略過各列中的不相關資料。

  3. 如果採用前兩種策略後,仍想進一步微調讀取效能,建議使用更複雜的篩選器。可能的原因包括:

    • 您還是會收到許多不想要的資料。
    • 您想將查詢推送至 Bigtable,簡化應用程式程式碼。

    不過請注意,如果篩選器需要條件、交錯或規則運算式比對大型值,且允許大部分掃描的資料通過,則可能弊大於利。這種損害會以叢集 CPU 使用率增加的形式出現,而用戶端不會大幅節省。

除了這些策略之外,請避免在單一讀取要求中讀取大量不連續的資料列索引鍵或資料列範圍。如果您在單一要求中要求數百個資料列索引鍵或資料列範圍,Bigtable 會掃描資料表,並依序讀取要求的資料列。這種缺乏平行處理的情況會影響「整體」延遲時間,而任何命中熱節點的讀取作業都可能增加「尾端」延遲時間。要求的資料列範圍越多,讀取作業所需的時間就越長。如果無法接受這種延遲時間,請改為同時傳送多個並行要求,每個要求擷取的資料列範圍較小。

一般來說,在單一要求中讀取更多資料列範圍,可提高處理量,但無法縮短延遲時間。在多個並行要求中讀取較少的資料列範圍,可縮短延遲時間,但無法提高處理量。如何取得延遲時間和處理量之間的平衡,取決於應用程式的需求,您可以調整並行讀取要求數量和單一要求中的資料列範圍數量,找出最佳平衡點。

大型資料列

Bigtable 會對大型資料列強制執行下列限制:

  • 資料列的大小上限為 256 MB。如需讀取超過限制的資料列,可以將要求分頁,並使用 cells per row limit 篩選器和 cells per row offset 篩選器。請注意,如果寫入作業在分頁讀取要求之間抵達資料列,讀取作業可能不具原子性。

  • ReadRows API 呼叫的大小上限為 512 KB。如果超過上限,Bigtable 會傳回 INVALID_ARGUMENT 錯誤。

後續步驟