protobuf 데이터 쿼리
이 문서에서는 Bigtable에 저장된 프로토콜 버퍼 (protobuf) 데이터를 읽고 쿼리하는 일반적인 쿼리 패턴의 예를 제공합니다.
이 페이지를 읽기 전에 다음 내용을 숙지하세요.
예시 데이터
다음 예시에서는 앨범과 아티스트에 관한 정보를 저장하는 Music 테이블을 사용합니다. 데이터는 column qualifier album이 있는 album_details이라는 column family에 저장됩니다. 열 한정자에는 protobuf 메시지가 포함됩니다.
protobuf 스키마는 다음 proto 파일에 정의되어 있습니다.
artist.proto:syntax = "proto3"; package package_name; message Artist { string name = 1; }album.proto:syntax = "proto3"; package package_name; import "artist.proto"; message Album { string title = 1; Artist artist = 2; int32 release_year = 3; }
따라서 Bigtable은 이러한 protobuf 정의에 대해 다음 설명자 세트가 포함된 이 테이블의 스키마 번들을 만듭니다.
file {
name: "artist.proto"
package: "package_name"
message_type {
name: "Artist"
field {
name: "name"
number: 1
label: LABEL_OPTIONAL
type: TYPE_STRING
json_name: "name"
}
}
syntax: "proto3"
}
file {
name: "album.proto"
package: "package_name"
dependency: "artist.proto"
message_type {
name: "Album"
field {
name: "title"
number: 1
label: LABEL_OPTIONAL
type: TYPE_STRING
json_name: "title"
}
field {
name: "artist"
number: 2
label: LABEL_OPTIONAL
type: TYPE_MESSAGE
type_name: ".package_name.Artist"
json_name: "artist"
}
field {
name: "release_year"
number: 3
label: LABEL_OPTIONAL
type: TYPE_INT32
json_name: "releaseYear"
}
}
syntax: "proto3"
}
쿼리 예
다음 예에서는 Bigtable 및 BigQuery 외부 테이블에 GoogleSQL을 사용하여 protobuf 데이터를 쿼리하는 방법을 보여줍니다.
열을 protobuf 메시지로 변환
CAST 연산자를 사용하여 BYTES 값을 protobuf 메시지로 해석할 수 있습니다.
이렇게 하려면 protobuf 메시지의 전체 이름을 SCHEMA_BUNDLE_ID.FULLY_QUALIFIED_MESSAGE_NAME 형식으로 제공해야 합니다.
다음을 바꿉니다.
SCHEMA_BUNDLE_ID: 스키마 번들을 만들 때 할당한 고유 ID입니다.FULLY_QUALIFIED_MESSAGE_NAME: 메시지의 전체 이름입니다. 프로토 파일에 정의된 패키지 이름을 포함해야 합니다(예:package_name.message_name).
다음 샘플 쿼리는 album 열을 Album protobuf 메시지로 변환합니다. 이 메시지는 package_name 패키지에 정의되어 있으며 bundle_name이라는 스키마 번들의 일부입니다.
SELECT
CAST(album_details['album'] AS bundle_name.package_name.Album).title
FROM
Music;
중첩된 필드 액세스
점 표기법을 사용하여 protobuf 메시지 내의 중첩된 필드에 액세스할 수 있습니다.
다음 쿼리는 Album 메시지 내에 중첩된 Artist 메시지에서 아티스트 이름을 가져옵니다.
SELECT
CAST(album_details['album'] AS bundle_name.package_name.Album).artist.name
FROM
Music;
protobuf 필드를 기준으로 필터링
WHERE 절을 사용하여 protobuf 메시지 내 필드의 값을 기준으로 행을 필터링할 수 있습니다.
다음 쿼리는 아티스트 Dana A.의 모든 앨범을 선택합니다.
SELECT
*
FROM
Music
WHERE
CAST(album_details['album'] AS bundle_name.package_name.Album).artist.name = 'Dana A.';
protobuf 필드 집계
protobuf 메시지 내의 숫자 필드에 SUM, AVG, MIN, MAX, COUNT과 같은 집계 함수를 사용할 수 있습니다.
다음 쿼리는 테이블에 있는 모든 앨범의 평균 출시 연도를 계산합니다.
SELECT
AVG(CAST(album_details['album'] AS bundle_name.package_name.Album).release_year)
FROM
Music;
protobuf 필드를 기준으로 순서 지정
ORDER BY 절을 사용하여 protobuf 메시지의 필드를 기준으로 결과 집합을 정렬할 수 있습니다.
다음 쿼리는 모든 앨범을 검색하고 출시 연도를 기준으로 내림차순으로 정렬합니다.
SELECT
*
FROM
Music
ORDER BY
CAST(album_details['album'] AS bundle_name.package_name.Album).release_year DESC;
BigQuery 외부 테이블과 함께 사용
외부 테이블을 만들어 BigQuery에서 Bigtable에 저장된 protobuf 데이터를 쿼리할 수 있습니다. 외부 테이블을 만들 때 열 유형을 JSON로, 인코딩을 PROTO_BINARY로 지정하고 스키마 번들과 연결합니다. 이 프로세스는 protobuf 메시지 바이트를 상응하는 JSON 데이터로 변환하므로 필드를 직접 쿼리할 수 있습니다.
다음은 Music 테이블에 BigQuery 외부 테이블을 만드는 테이블 정의 파일의 예입니다.
{
"sourceFormat": "BIGTABLE",
"sourceUris": [
"https://googleapis.com/bigtable/projects/PROJECT_ID/instances/INSTANCE_ID/tables/Music"
],
"bigtableOptions": {
"columnFamilies" : [
{
"familyId": "album_details",
"columns": [
{
"qualifierString": "album",
"type": "JSON",
"encoding": "PROTO_BINARY",
"protoConfig": {
"schemaBundleId": "bundle_name",
"protoMessageName": "package_name.Album"
}
}
]
}
]
}
}
외부 테이블이 생성되면 BigQuery에서 protobuf 데이터를 JSON 열로 쿼리할 수 있습니다.
다음 쿼리는 BigQuery 외부 테이블에서 2022년에 출시된 모든 앨범의 제목을 가져옵니다.
SELECT JSON_VALUE(value, '$.title') AS title
FROM
`PROJECT_ID.DATASET.TABLE_NAME` AS t,
UNNEST(t.album_details.album.cell)
WHERE INT64(JSON_EXTRACT(value, '$.releaseYear')) = 2022;
다음 단계
- protobuf의 스키마 설계 권장사항에 대해 알아봅니다.