Parametr konfiguracji use_proto_plus
pozwala określić, czy biblioteka ma zwracać wiadomości proto-plus czy wiadomości protobuf. Szczegółowe informacje o tym, jak ustawić ten parametr, znajdziesz w dokumentacji dotyczącej konfiguracji.
Z tej sekcji dowiesz się, jak wybór typu wiadomości wpływa na skuteczność. Dlatego zalecamy zapoznanie się z dostępnymi opcjami, aby podjąć świadomą decyzję.
Porównanie wiadomości proto-plus i protobuf
Przepływ generowania kodu integruje proto-plus, aby poprawić ergonomię interfejsu wiadomości protobuf, sprawiając, że będą one zachowywać się bardziej jak natywne obiekty Pythona. Oznacza to jednak, że korzystanie z proto-plus powoduje wzrost obciążenia wydajności.
Skuteczność proto-plus
Jedną z głównych zalet proto-plus jest to, że konwertuje wiadomości proto-plus i znane typy na natywne typy Pythona za pomocą procesu zwanego typem marshaling.
Marshalowanie występuje, gdy uzyskuje się dostęp do pola w przypadku wystąpienia wiadomości proto-plus, a w szczególności gdy pole jest odczytywane lub ustawiane, na przykład w definicji protobuf:
syntax = "proto3";
message Dog {
string name = 1;
}
Gdy ta definicja zostanie przekonwertowana na klasę proto-plus, będzie wyglądać tak:
import proto
class Dog(proto.Message):
name = proto.Field(proto.STRING, number=1)
Następnie możesz zainicjować klasę Dog
i uzyskać dostęp do jej pola name
tak jak do dowolnego innego obiektu Pythona:
dog = Dog()
dog.name = "Scruffy"
print(dog.name)
Podczas odczytywania i ustawiania pola name
wartość jest konwertowana z natywnego typu str
w Pythonie na typ string
, aby była zgodna ze środowiskiem wykonawczym protobuf.
Na podstawie analizy wydajności stwierdziliśmy, że czas potrzebny na przeprowadzenie tego typu konwersji ma na tyle duży wpływ na wydajność, że użytkownicy powinni sami decydować, czy chcą używać wiadomości protobuf.
Przypadki użycia wiadomości protokołu protoplus i protobuf
- Przypadki użycia wiadomości proto-plus
- Protoplus oferuje wiele udoskonaleń w stosunku do wiadomości protobuf, dzięki czemu idealnie nadaje się do pisania łatwego w utrzymaniu i czytelnego kodu. Udostępniają natywne obiekty Pythona, więc są łatwiejsze w użyciu i zrozumieniu.
- Zastosowania wiadomości Protobuf
- Używaj protokołów protobuf w przypadkach, w których liczy się wydajność, zwłaszcza w aplikacjach, które muszą szybko przetwarzać duże raporty lub które tworzą zapytania o zmianę z dużą liczbą operacji, np.
BatchJobService
lubOfflineUserDataJobService
.
Dynamiczna zmiana typów wiadomości
Po wybraniu odpowiedniego typu wiadomości dla aplikacji może się okazać, że w przypadku określonego procesu roboczego musisz użyć innego typu. W tym przypadku można łatwo przełączać się między tymi dwoma typami dynamicznie, korzystając z narzędzi oferowanych przez bibliotekę klienta. Przy użyciu tej samej klasy wiadomości Dog
z powyższego przykładu:
from google.ads.googleads import util
# Proto-plus message type
dog = Dog()
# Protobuf message type
dog = util.convert_proto_plus_to_protobuf(dog)
# Back to proto-plus message type
dog = util.convert_protobuf_to_proto_plus(dog)
Różnice w interfejsie wiadomości Protobuf
Interfejs proto-plus jest szczegółowo opisany, ale tutaj wyróżniliśmy kilka kluczowych różnic, które mają wpływ na typowe zastosowania biblioteki klienta Google Ads.
Serializacja bajtów
- Komunikaty proto-plus
serialized = type(campaign).serialize(campaign) deserialized = type(campaign).deserialize(serialized)
- komunikaty Protobuf;
serialized = campaign.SerializeToString() deserialized = campaign.FromString(serialized)
Serializacja JSON
- Wiadomości Proto Plus
serialized = type(campaign).to_json(campaign) deserialized = type(campaign).from_json(serialized)
- Komunikaty Protobuf
from google.protobuf.json_format import MessageToJson, Parse serialized = MessageToJson(campaign) deserialized = Parse(serialized, campaign)
Maski pól
Metoda pomocnicza maski pola udostępniana przez api-core jest przeznaczona do używania instancji wiadomości protobuf. Jeśli więc używasz wiadomości protobuf, przekonwertuj je na wiadomości protobuf, aby użyć funkcji pomocniczej:
- Komunikaty proto-plus
from google.api_core.protobuf_helpers import field_mask campaign = client.get_type("Campaign") protobuf_campaign = util.convert_proto_plus_to_protobuf(campaign) mask = field_mask(None, protobuf_campaign)
- komunikaty Protobuf;
from google.api_core.protobuf_helpers import field_mask campaign = client.get_type("Campaign") mask = field_mask(None, campaign)
Wartości w polu enum
Enumy udostępniane przez wiadomości proto-plus są instancjami natywnego typu Pythona enum
, a zatem dziedziczą wiele metod ułatwiających pracę.
Pobieranie typu wyliczeniowego
Gdy używasz metody GoogleAdsClient.get_type
do pobierania typów enumeracji, zwracane komunikaty różnią się nieco w zależności od tego, czy używasz proto-plus czy komunikatów protobuf. Na przykład:
- Wiadomości Proto Plus
val = client.get_type("CampaignStatusEnum").CampaignStatus.PAUSED
- komunikaty Protobuf;
val = client.get_type("CampaignStatusEnum").PAUSED
Aby ułatwić pobieranie typów, w przypadku instancji GoogleAdsClient
jest dostępny atrybuty ułatwiający, który ma spójny interfejs niezależnie od tego, którego typu wiadomości używasz:
val = client.enums.CampaignStatusEnum.PAUSED
Pobieranie wartości typu wyliczeniowego
Czasami przydatna jest wartość lub identyfikator pola danego wyliczenia. Na przykład PAUSED
w polu CampaignStatusEnum
odpowiada 3
:
- Wiadomości Proto Plus
campaign = client.get_type("Campaign") campaign.status = client.enums.CampaignStatusEnum.PAUSED # To read the value of campaign status print(campaign.status.value)
- Komunikaty Protobuf
campaign = client.get_type("Campaign") status_enum = client.enums.CampaignStatusEnum campaign.status = status_enum.PAUSED # To read the value of campaign status print(status_enum.CampaignStatus.Value(campaign.status))
Pobieranie nazwy typu wyliczeniowego
Czasami warto znać nazwę pola typu enum. Na przykład podczas odczytywania obiektów z interfejsu API możesz chcieć wiedzieć, któremu stanowi kampanii odpowiada wartość int 3
:
- Komunikaty proto-plus
campaign = client.get_type("Campaign") campaign.status = client.enums.CampaignStatusEnum.PAUSED # To read the name of campaign status print(campaign.status.name)
- Komunikaty Protobuf
campaign = client.get_type("Campaign") status_enum = client.enums.CampaignStatusEnum # Sets the campaign status to the int value for PAUSED campaign.status = status_enum.PAUSED # To read the name of campaign status status_enum.CampaignStatus.Name(campaign.status)
Pola powtarzane
Zgodnie z opisem w dokumentach Proto-plus pola powtarzane są zasadniczo równoważne z listami typowymi, co oznacza, że działają prawie tak samo jak list
.
Dołączanie wartości do powtarzających się pól skalarnych
Podczas dodawania wartości do powtarzanych pól skalowania, np. pól string
lub int64
, interfejs jest taki sam niezależnie od typu wiadomości:
- Komunikaty proto-plus
ad.final_urls.append("https://www.example.com")
- Komunikaty Protobuf
ad.final_urls.append("https://www.example.com")
Obejmuje to również wszystkie inne popularne metody list
, np. extend
:
- Komunikaty proto-plus
ad.final_urls.extend(["https://www.example.com", "https://www.example.com/2"])
- komunikaty Protobuf;
ad.final_urls.extend(["https://www.example.com", "https://www.example.com/2"])
Dołączanie typów wiadomości do pól powtarzalnych
Jeśli powtarzane pole nie jest polem typu skalarnego, jego dodawanie do powtarzanych pól działa nieco inaczej:
- Komunikaty proto-plus
frequency_cap = client.get_type("FrequencyCapEntry") frequency_cap.cap = 100 campaign.frequency_caps.append(frequency_cap)
- komunikaty Protobuf;
# The add method initializes a message and adds it to the repeated field frequency_cap = campaign.frequency_caps.add() frequency_cap.cap = 100
Przypisywanie pól powtarzalnych
W przypadku zarówno skalarnych, jak i nieskalarnych pól powtarzalnych możesz przypisywać do nich listy na różne sposoby:
- Wiadomości Proto Plus
# In proto-plus it's possible to use assignment. urls = ["https://www.example.com"] ad.final_urls = urls
- Komunikaty Protobuf
# Protobuf messages do not allow assignment, but you can replace the # existing list using slice syntax. urls = ["https://www.example.com"] ad.final_urls[:] = urls
puste wiadomości;
Czasami przydaje się wiedzieć, czy instancja wiadomości zawiera jakieś informacje lub czy ma ustawione jakieś pola.
- Komunikaty proto-plus
# When using proto-plus messages you can simply check the message for # truthiness. is_empty = bool(campaign) is_empty = not campaign
- komunikaty protokołu protobuf;
is_empty = campaign.ByteSize() == 0
Treść wiadomości
W przypadku wiadomości proto-plus i protobuf zalecamy użycie metody pomocniczej copy_from
w GoogleAdsClient
:
client.copy_from(campaign, other_campaign)
Puste pola wiadomości
Proces ustawiania pustych pól wiadomości jest taki sam niezależnie od używanego typu wiadomości. Wystarczy skopiować pustą wiadomość w odpowiednim polu. Zobacz sekcję Kopia wiadomości oraz przewodnik Puste pola wiadomości. Oto przykład ustawienia pustego pola wiadomości:
client.copy_from(campaign.manual_cpm, client.get_type("ManualCpm"))
nazwy pól, które są zastrzeżonymi słowami;
W przypadku wiadomości proto-plus nazwy pól są automatycznie wyświetlane z podkreśleniem, jeśli są one również zarezerwowanymi słowami w Pythonie. Oto przykład pracy z instancją Asset
:
asset = client.get_type("Asset")
asset.type_ = client.enums.AssetTypeEnum.IMAGE
Pełna lista nazw zastrzeżonych jest tworzona w module gapicgenerator. Dostęp do niego można uzyskać automatycznie.
Najpierw zainstaluj moduł:
python -m pip install gapic-generator
Następnie w replu lub skrypcie Pythona:
import gapic.utils
print(gapic.utils.reserved_names.RESERVED_NAMES)
Obecność w polu
Ponieważ pola instancji wiadomości buforów protokołu mają wartości domyślne, ustalenie, czy pole zostało ustawione, czy nie zawsze jest intuicyjne.
- Komunikaty proto-plus
# Use the "in" operator. has_field = "name" in campaign
- komunikaty protokołu protobuf;
campaign = client.get_type("Campaign") # Determines whether "name" is set and not just an empty string. campaign.HasField("name")
Interfejs klasy protobufMessage
ma metodę HasField
, która określa, czy pole w wiadomości zostało ustawione, nawet jeśli ma wartość domyślną.
Metody komunikatów buforów protokołu
Interfejs wiadomości protobuf zawiera pewne wygodne metody, które nie są częścią interfejsu protobuf. Można je jednak łatwo uzyskać, konwertując wiadomość proto-plus na jej odpowiednik w formacie protobuf:
# Accessing the ListFields method
protobuf_campaign = util.convert_protobuf_to_proto_plus(campaign)
print(campaign.ListFields())
# Accessing the Clear method
protobuf_campaign = util.convert_protobuf_to_proto_plus(campaign)
print(campaign.Clear())
Śledzenie problemów
Jeśli masz pytania dotyczące tych zmian lub problemy z przeniesieniem do najnowszej wersji biblioteki, zgłoś problem w naszym systemie śledzenia błędów.