Skip to content

Commit e361f79

Browse files
committed
Adding helper to parse a Bigtable column family protobuf.
1 parent 9e08e57 commit e361f79

2 files changed

Lines changed: 98 additions & 0 deletions

File tree

gcloud/bigtable/row.py

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919

2020
import six
2121

22+
from gcloud._helpers import _datetime_from_microseconds
2223
from gcloud._helpers import _microseconds_from_datetime
2324
from gcloud._helpers import _to_bytes
2425
from gcloud.bigtable._generated import bigtable_data_pb2 as data_pb2
@@ -1192,3 +1193,41 @@ def to_pb(self):
11921193
condition_kwargs['false_filter'] = self.false_filter.to_pb()
11931194
condition = data_pb2.RowFilter.Condition(**condition_kwargs)
11941195
return data_pb2.RowFilter(condition=condition)
1196+
1197+
1198+
def _parse_family_pb(family_pb):
1199+
"""Parses a Family protobuf into a dictionary.
1200+
1201+
:type family_pb: :class:`._generated.bigtable_data_pb2.Family`
1202+
:param family_pb: A protobuf
1203+
1204+
:rtype: tuple
1205+
:returns: A string and dictionary. The string is the name of the
1206+
column family and the dictionary has column names (within the
1207+
family) as keys and cell lists as values. Each cell is
1208+
represented with a two-tuple with the value (in bytes) and the
1209+
timestamp for the cell. For example:
1210+
1211+
.. code:: python
1212+
1213+
{
1214+
b'col-name1': [
1215+
(b'cell-val', datetime.datetime(...)),
1216+
(b'cell-val-newer', datetime.datetime(...)),
1217+
],
1218+
b'col-name2': [
1219+
(b'altcol-cell-val', datetime.datetime(...)),
1220+
],
1221+
}
1222+
"""
1223+
result = {}
1224+
for column in family_pb.columns:
1225+
result[column.qualifier] = cells = []
1226+
for cell in column.cells:
1227+
val_pair = (
1228+
cell.value,
1229+
_datetime_from_microseconds(cell.timestamp_micros),
1230+
)
1231+
cells.append(val_pair)
1232+
1233+
return family_pb.name, result

gcloud/bigtable/test_row.py

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1535,6 +1535,65 @@ def test_to_pb_false_only(self):
15351535
self.assertEqual(filter_pb, expected_pb)
15361536

15371537

1538+
class Test__parse_family_pb(unittest2.TestCase):
1539+
1540+
def _callFUT(self, family_pb):
1541+
from gcloud.bigtable.row import _parse_family_pb
1542+
return _parse_family_pb(family_pb)
1543+
1544+
def test_it(self):
1545+
from gcloud._helpers import _datetime_from_microseconds
1546+
from gcloud.bigtable._generated import bigtable_data_pb2 as data_pb2
1547+
1548+
col_fam1 = u'col-fam-id'
1549+
col_name1 = b'col-name1'
1550+
col_name2 = b'col-name2'
1551+
cell_val1 = b'cell-val'
1552+
cell_val2 = b'cell-val-newer'
1553+
cell_val3 = b'altcol-cell-val'
1554+
1555+
microseconds = 5554441037
1556+
timestamp = _datetime_from_microseconds(microseconds)
1557+
expected_dict = {
1558+
col_name1: [
1559+
(cell_val1, timestamp),
1560+
(cell_val2, timestamp),
1561+
],
1562+
col_name2: [
1563+
(cell_val3, timestamp),
1564+
],
1565+
}
1566+
expected_output = (col_fam1, expected_dict)
1567+
sample_input = data_pb2.Family(
1568+
name=col_fam1,
1569+
columns=[
1570+
data_pb2.Column(
1571+
qualifier=col_name1,
1572+
cells=[
1573+
data_pb2.Cell(
1574+
value=cell_val1,
1575+
timestamp_micros=microseconds,
1576+
),
1577+
data_pb2.Cell(
1578+
value=cell_val2,
1579+
timestamp_micros=microseconds,
1580+
),
1581+
],
1582+
),
1583+
data_pb2.Column(
1584+
qualifier=col_name2,
1585+
cells=[
1586+
data_pb2.Cell(
1587+
value=cell_val3,
1588+
timestamp_micros=microseconds,
1589+
),
1590+
],
1591+
),
1592+
],
1593+
)
1594+
self.assertEqual(expected_output, self._callFUT(sample_input))
1595+
1596+
15381597
class _Client(object):
15391598

15401599
data_stub = None

0 commit comments

Comments
 (0)