簡體   English   中英

如果子消息沒有字段,如何在 protobuf 消息上分配 oneof 字段?

[英]How do I assign a oneof field on a protobuf message if the child message has no fields?

我想創建一個 BigTable DeleteFromRow突變。 MutationDeleteFromRow如下所示:

oneof mutation {
    // Set a cell's value.
    SetCell set_cell = 1;

    // Deletes cells from a column.
    DeleteFromColumn delete_from_column = 2;

    // Deletes cells from a column family.
    DeleteFromFamily delete_from_family = 3;

    // Deletes cells from the entire row.
    DeleteFromRow delete_from_row = 4;
  }
}

message DeleteFromRow {

}

在 Python 中,您不能直接實例化DeleteFromRow對象並將Mutationdelete_from_row字段設置為該對象。

所以這不起作用

request = bigtable_pb2.MutateRowRequest(table_name='tablename', row_key=row_key)
mutation = request.mutations.add()
mutation.delete_from_row = data_pb2.Mutation.DeleteFromRow()

正如其他 SO 用戶提出的那樣(請參閱此問題),這會導致

AttributeError: Assignment not allowed to composite field "delete_from_row" in protocol message object.

根據protobuf docs ,您應該通過設置子字段之一來設置 oneof 字段。 因此,應該以這種方式創建DeleteFromFamily突變:

mutation.delete_from_family.family_name = 'some_family'

但是,如何為沒有字段的DeleteFromRow消息執行此操作?

您可以使用Message.SetInParent

將此標記為存在於父級中。

這通常在您分配子消息的字段時自動發生,但有時您希望在保持子消息為空的同時顯示子消息。 如果您發現自己在使用它,您可能需要重新考慮您的設計。

例子:

message Msg {
  oneof kind {
    int64 int_field = 1;
    EmptyMsg msg_field = 1;
  }
}

message EmptyMsg {}
msg = Msg()
print(msg.WhichOneof('kind'))  # None

msg.msg_field  # No-op (return EmptyMsg but don't set oneof field)
print(msg.WhichOneof('kind'))  # None

msg.msg_field.SetInParent()
print(v.WhichOneof('kind'))  # msg_field

您可以啟動DeleteFromRow對象並使用關鍵字參數delete_from_row創建突變:

dfr = data_pb2.Mutation.DeleteFromRow()
mutation = data_pb2.Mutation(delete_from_row=dfr)

雖然您不能將此更改addappend到請求的重復突變字段(盡管在我看來這就是文檔在此處所說的內容),但您可以extend它:

request = bigtable_pb2.MutateRowRequest(table_name='tablename', row_key=row_key)
request.mutations.extend([mutation])

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM