Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[EventGrid] Fix lint errors #13640

Merged
merged 2 commits into from
Sep 8, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion eng/tox/allowed_pylint_failures.py
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,6 @@
"azure-common",
"azure-nspkg",
"azure-servicemanagement-legacy",
"azure-eventgrid",
"azure-graphrbac",
"azure-loganalytics",
"azure-servicefabric",
Expand Down
2 changes: 1 addition & 1 deletion sdk/eventgrid/azure-eventgrid/azure/__init__.py
Original file line number Diff line number Diff line change
@@ -1 +1 @@
__path__ = __import__('pkgutil').extend_path(__path__, __name__)
__path__ = __import__('pkgutil').extend_path(__path__, __name__)
6 changes: 3 additions & 3 deletions sdk/eventgrid/azure-eventgrid/azure/eventgrid/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,11 @@
from ._publisher_client import EventGridPublisherClient
from ._consumer import EventGridConsumer
from ._helpers import generate_shared_access_signature
from ._models import CloudEvent, CustomEvent, EventGridEvent, StorageBlobCreatedEventData
from ._models import CloudEvent, CustomEvent, EventGridEvent
from ._shared_access_signature_credential import EventGridSharedAccessSignatureCredential
from ._version import VERSION

__all__ = ['EventGridPublisherClient', 'EventGridConsumer',
'CloudEvent', 'CustomEvent', 'EventGridEvent', 'StorageBlobCreatedEventData',
'generate_shared_access_signature', 'EventGridSharedAccessSignatureCredential']
'CloudEvent', 'CustomEvent', 'EventGridEvent', 'generate_shared_access_signature',
'EventGridSharedAccessSignatureCredential']
__version__ = VERSION
43 changes: 21 additions & 22 deletions sdk/eventgrid/azure-eventgrid/azure/eventgrid/_consumer.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,26 +7,21 @@
# --------------------------------------------------------------------------

from typing import TYPE_CHECKING
import json
import six
import logging

from azure.core import PipelineClient
from msrest import Deserializer, Serializer
from ._models import CloudEvent, EventGridEvent

if TYPE_CHECKING:
# pylint: disable=unused-import,ungrouped-imports
from typing import Any

_LOGGER = logging.getLogger(__name__)

from ._models import CloudEvent, EventGridEvent

class EventGridConsumer(object):
"""
A consumer responsible for deserializing event handler messages, to allow for access to strongly typed Event objects.
A consumer responsible for deserializing event handler messages, to allow for
access to strongly typed Event objects.
"""
def decode_cloud_event(self, cloud_event, **kwargs):
def decode_cloud_event(self, cloud_event, **kwargs): # pylint: disable=no-self-use
# type: (Union[str, dict, bytes], Any) -> CloudEvent
"""Single event following CloudEvent schema will be parsed and returned as Deserialized Event.
:param cloud_event: The event to be deserialized.
Expand All @@ -37,17 +32,19 @@ def decode_cloud_event(self, cloud_event, **kwargs):
"""
encode = kwargs.pop('encoding', 'utf-8')
try:
cloud_event = CloudEvent._from_json(cloud_event, encode)
deserialized_event = CloudEvent._from_generated(cloud_event)
CloudEvent._deserialize_data(deserialized_event, deserialized_event.type)
return deserialized_event
cloud_event = CloudEvent._from_json(cloud_event, encode) # pylint: disable=protected-access
deserialized_event = CloudEvent._from_generated(cloud_event) # pylint: disable=protected-access
CloudEvent._deserialize_data(deserialized_event, deserialized_event.type) # pylint: disable=protected-access
return deserialized_event
except Exception as err:
_LOGGER.error('Error: cannot deserialize event. Event does not have a valid format. Event must be a string, dict, or bytes following the CloudEvent schema.')
_LOGGER.error('Your event: {}'.format(cloud_event))
_LOGGER.error('Error: cannot deserialize event. Event does not have a valid format. \
Event must be a string, dict, or bytes following the CloudEvent schema.')
_LOGGER.error('Your event: %s', cloud_event)
_LOGGER.error(err)
raise ValueError('Error: cannot deserialize event. Event does not have a valid format. Event must be a string, dict, or bytes following the CloudEvent schema.')
raise ValueError('Error: cannot deserialize event. Event does not have a valid format. \
Event must be a string, dict, or bytes following the CloudEvent schema.')

def decode_eventgrid_event(self, eventgrid_event, **kwargs):
def decode_eventgrid_event(self, eventgrid_event, **kwargs): # pylint: disable=no-self-use
# type: (Union[str, dict, bytes], Any) -> EventGridEvent
"""Single event following EventGridEvent schema will be parsed and returned as Deserialized Event.
:param eventgrid_event: The event to be deserialized.
Expand All @@ -58,12 +55,14 @@ def decode_eventgrid_event(self, eventgrid_event, **kwargs):
"""
encode = kwargs.pop('encoding', 'utf-8')
try:
eventgrid_event = EventGridEvent._from_json(eventgrid_event, encode)
eventgrid_event = EventGridEvent._from_json(eventgrid_event, encode) # pylint: disable=protected-access
deserialized_event = EventGridEvent.deserialize(eventgrid_event)
EventGridEvent._deserialize_data(deserialized_event, deserialized_event.event_type)
EventGridEvent._deserialize_data(deserialized_event, deserialized_event.event_type) # pylint: disable=protected-access
return deserialized_event
except Exception as err:
_LOGGER.error('Error: cannot deserialize event. Event does not have a valid format. Event must be a string, dict, or bytes following the CloudEvent schema.')
_LOGGER.error('Your event: {}'.format(eventgrid_event))
_LOGGER.error('Error: cannot deserialize event. Event does not have a valid format. \
Event must be a string, dict, or bytes following the CloudEvent schema.')
_LOGGER.error('Your event: %s', eventgrid_event)
_LOGGER.error(err)
raise ValueError('Error: cannot deserialize event. Event does not have a valid format. Event must be a string, dict, or bytes following the CloudEvent schema.')
raise ValueError('Error: cannot deserialize event. Event does not have a valid format. \
Event must be a string, dict, or bytes following the CloudEvent schema.')
14 changes: 9 additions & 5 deletions sdk/eventgrid/azure-eventgrid/azure/eventgrid/_event_mappings.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,8 @@
"Microsoft.EventGrid.SubscriptionValidationEvent": models.SubscriptionValidationEventData,
"Microsoft.EventGrid.SubscriptionDeletedEvent": models.SubscriptionDeletedEventData,
"Microsoft.EventHub.CaptureFileCreated": models.EventHubCaptureFileCreatedEventData,
"Microsoft.MachineLearningServices.DatasetDriftDetected": models.MachineLearningServicesDatasetDriftDetectedEventData,
"Microsoft.MachineLearningServices.DatasetDriftDetected":
models.MachineLearningServicesDatasetDriftDetectedEventData,
"Microsoft.MachineLearningServices.ModelDeployed": models.MachineLearningServicesModelDeployedEventData,
"Microsoft.MachineLearningServices.ModelRegistered": models.MachineLearningServicesModelRegisteredEventData,
"Microsoft.MachineLearningServices.RunCompleted": models.MachineLearningServicesRunCompletedEventData,
Expand Down Expand Up @@ -47,7 +48,8 @@
"Microsoft.Media.LiveEventEncoderDisconnected": models.MediaLiveEventEncoderDisconnectedEventData,
"Microsoft.Media.LiveEventIncomingStreamReceived": models.MediaLiveEventIncomingStreamReceivedEventData,
"Microsoft.Media.LiveEventIncomingStreamsOutOfSync": models.MediaLiveEventIncomingStreamsOutOfSyncEventData,
"Microsoft.Media.LiveEventIncomingVideoStreamsOutOfSync": models.MediaLiveEventIncomingVideoStreamsOutOfSyncEventData,
"Microsoft.Media.LiveEventIncomingVideoStreamsOutOfSync":
models.MediaLiveEventIncomingVideoStreamsOutOfSyncEventData,
"Microsoft.Media.LiveEventIncomingDataChunkDropped": models.MediaLiveEventIncomingDataChunkDroppedEventData,
"Microsoft.Media.LiveEventIngestHeartbeat": models.MediaLiveEventIngestHeartbeatEventData,
"Microsoft.Media.LiveEventTrackDiscontinuityDetected": models.MediaLiveEventTrackDiscontinuityDetectedEventData,
Expand All @@ -60,8 +62,10 @@
"Microsoft.Resources.ResourceActionSuccess": models.ResourceActionSuccessData,
"Microsoft.Resources.ResourceActionFailure": models.ResourceActionFailureData,
"Microsoft.Resources.ResourceActionCancel": models.ResourceActionCancelData,
"Microsoft.ServiceBus.ActiveMessagesAvailableWithNoListeners": models.ServiceBusActiveMessagesAvailableWithNoListenersEventData,
"Microsoft.ServiceBus.DeadletterMessagesAvailableWithNoListener": models.ServiceBusDeadletterMessagesAvailableWithNoListenersEventData,
"Microsoft.ServiceBus.ActiveMessagesAvailableWithNoListeners":
models.ServiceBusActiveMessagesAvailableWithNoListenersEventData,
"Microsoft.ServiceBus.DeadletterMessagesAvailableWithNoListener":
models.ServiceBusDeadletterMessagesAvailableWithNoListenersEventData,
"Microsoft.Storage.BlobCreated": models.StorageBlobCreatedEventData,
"Microsoft.Storage.BlobDeleted": models.StorageBlobDeletedEventData,
"Microsoft.Storage.BlobRenamed": models.StorageBlobRenamedEventData,
Expand All @@ -82,4 +86,4 @@
"Microsoft.Web.SlotSwapWithPreviewStarted": models.WebSlotSwapWithPreviewStartedEventData,
"Microsoft.Web.SlotSwapWithPreviewCancelled": models.WebSlotSwapWithPreviewCancelledEventData,
"Microsoft.Web.AppServicePlanUpdated": models.WebAppServicePlanUpdatedEventData,
}
}
23 changes: 16 additions & 7 deletions sdk/eventgrid/azure-eventgrid/azure/eventgrid/_helpers.py
Original file line number Diff line number Diff line change
@@ -1,18 +1,20 @@
# --------------------------------------------------------------------------------------------
# Copyright (c) Microsoft Corporation. All rights reserved.
# Licensed under the MIT License. See License.txt in the project root for license information.
# --------------------------------------------------------------------------------------------
import hashlib
import hmac
import base64
try:
from urllib.parse import quote
except ImportError:
from urllib2 import quote # type: ignore
import datetime

from azure.core.pipeline.policies import AzureKeyCredentialPolicy
from azure.core.credentials import AzureKeyCredential
from ._shared_access_signature_credential import EventGridSharedAccessSignatureCredential
from ._signature_credential_policy import EventGridSharedAccessSignatureCredentialPolicy
from . import _constants as constants
from ._event_mappings import _event_mappings

def generate_shared_access_signature(topic_hostname, shared_access_key, expiration_date_utc, **kwargs):
# type: (str, str, datetime.Datetime, Any) -> str
Expand All @@ -21,13 +23,17 @@ def generate_shared_access_signature(topic_hostname, shared_access_key, expirati
Similar to <YOUR-TOPIC-NAME>.<YOUR-REGION-NAME>-1.eventgrid.azure.net
:param str shared_access_key: The shared access key to be used for generating the token
:param datetime.datetime expiration_date_utc: The expiration datetime in UTC for the signature.
:param str api_version: The API Version to include in the signature. If not provided, the default API version will be used.
:param str api_version: The API Version to include in the signature.
If not provided, the default API version will be used.
:rtype: str
"""

full_topic_hostname = _get_full_topic_hostname(topic_hostname)

full_topic_hostname = "{}?apiVersion={}".format(full_topic_hostname, kwargs.get('api_version', None) or constants.DEFAULT_API_VERSION)
full_topic_hostname = "{}?apiVersion={}".format(
full_topic_hostname,
kwargs.get('api_version', None) or constants.DEFAULT_API_VERSION
)
encoded_resource = quote(full_topic_hostname, safe=constants.SAFE_ENCODE)
encoded_expiration_utc = quote(str(expiration_date_utc), safe=constants.SAFE_ENCODE)

Expand All @@ -43,7 +49,7 @@ def _get_topic_hostname_only_fqdn(topic_hostname):
topic_hostname = topic_hostname.replace("https://", "")
if topic_hostname.endswith("/api/events"):
topic_hostname = topic_hostname.replace("/api/events", "")

return topic_hostname

def _get_full_topic_hostname(topic_hostname):
Expand All @@ -53,7 +59,7 @@ def _get_full_topic_hostname(topic_hostname):
topic_hostname = "https://{}".format(topic_hostname)
if not topic_hostname.endswith("/api/events"):
topic_hostname = "{}/api/events".format(topic_hostname)

return topic_hostname

def _generate_hmac(key, message):
Expand All @@ -69,7 +75,10 @@ def _get_authentication_policy(credential):
if isinstance(credential, AzureKeyCredential):
authentication_policy = AzureKeyCredentialPolicy(credential=credential, name=constants.EVENTGRID_KEY_HEADER)
if isinstance(credential, EventGridSharedAccessSignatureCredential):
authentication_policy = EventGridSharedAccessSignatureCredentialPolicy(credential=credential, name=constants.EVENTGRID_TOKEN_HEADER)
authentication_policy = EventGridSharedAccessSignatureCredentialPolicy(
credential=credential,
name=constants.EVENTGRID_TOKEN_HEADER
)
return authentication_policy

def _is_cloud_event(event):
Expand Down
21 changes: 9 additions & 12 deletions sdk/eventgrid/azure-eventgrid/azure/eventgrid/_models.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,16 +3,12 @@
# Licensed under the MIT License. See License.txt in the project root for license information.
# --------------------------------------------------------------------------------------------
# pylint:disable=protected-access
from typing import Optional
from msrest.serialization import UTC
import datetime as dt
import uuid
import json
import six
from ._generated import models
from ._generated.models import StorageBlobCreatedEventData, \
EventGridEvent as InternalEventGridEvent, \
CloudEvent as InternalCloudEvent
from msrest.serialization import UTC
from ._generated.models import EventGridEvent as InternalEventGridEvent, CloudEvent as InternalCloudEvent
from ._shared.mixins import DictMixin
lmazuel marked this conversation as resolved.
Show resolved Hide resolved
from ._event_mappings import _event_mappings

Expand Down Expand Up @@ -55,8 +51,8 @@ class CloudEvent(EventMixin): #pylint:disable=too-many-instance-attributes

All required parameters must be populated in order to send to Azure.

:param source: Required. Identifies the context in which an event happened. The combination of id and source must be
unique for each distinct event. If publishing to a domain topic, source must be the domain name.
:param source: Required. Identifies the context in which an event happened. The combination of id and source must
be unique for each distinct event. If publishing to a domain topic, source must be the domain name.
:type source: str
:param data: Event data specific to the event type.
:type data: object
Expand All @@ -75,7 +71,7 @@ class CloudEvent(EventMixin): #pylint:disable=too-many-instance-attributes
unique for each distinct event.
:type id: Optional[str]
"""
def __init__(self, source, type, **kwargs):
def __init__(self, source, type, **kwargs): # pylint: disable=redefined-builtin
lmazuel marked this conversation as resolved.
Show resolved Hide resolved
# type: (str, str, Any) -> None
self.source = source
self.type = type
Expand All @@ -87,13 +83,13 @@ def __init__(self, source, type, **kwargs):
self.dataschema = kwargs.pop("dataschema", None)
self.subject = kwargs.pop("subject", None)
self.extensions = {}
self.extensions.update({k:v for k, v in kwargs.pop('extensions', {}).items()})
self.extensions.update(dict(kwargs.pop('extensions', {})))

@classmethod
def _from_generated(cls, cloud_event, **kwargs):
generated = InternalCloudEvent.deserialize(cloud_event)
if generated.additional_properties:
extensions = {k:v for k, v in generated.additional_properties.items()}
extensions = dict(generated.additional_properties)
kwargs.setdefault('extensions', extensions)
return cls(
id=generated.id,
Expand Down Expand Up @@ -154,7 +150,8 @@ class EventGridEvent(InternalEventGridEvent, EventMixin):
:param id: Optional. An identifier for the event. The combination of id and source must be
unique for each distinct event.
:type id: Optional[str]
:param event_time: Optional.The time (in UTC) of the event. If not provided, it will be the time (in UTC) the event was generated.
:param event_time: Optional.The time (in UTC) of the event. If not provided,
it will be the time (in UTC) the event was generated.
:type event_time: Optional[~datetime.datetime]
"""

Expand Down
23 changes: 10 additions & 13 deletions sdk/eventgrid/azure-eventgrid/azure/eventgrid/_publisher_client.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,11 @@
# license information.
# --------------------------------------------------------------------------

from typing import TYPE_CHECKING, Sequence
import json
from typing import TYPE_CHECKING

from azure.core import PipelineClient
from msrest import Deserializer, Serializer
from ._models import CloudEvent, EventGridEvent, CustomEvent
from ._helpers import _get_topic_hostname_only_fqdn, _get_authentication_policy, _is_cloud_event
from ._generated._event_grid_publisher_client import EventGridPublisherClient as EventGridPublisherClientImpl

if TYPE_CHECKING:
# pylint: disable=unused-import,ungrouped-imports
Expand All @@ -25,18 +25,14 @@
List[Dict]
]

from ._models import CloudEvent, EventGridEvent, CustomEvent
from ._helpers import _get_topic_hostname_only_fqdn, _get_authentication_policy, _is_cloud_event
from ._generated._event_grid_publisher_client import EventGridPublisherClient as EventGridPublisherClientImpl
from . import _constants as constants


class EventGridPublisherClient(object):
"""EventGrid Python Publisher Client.

:param str topic_hostname: The topic endpoint to send the events to.
:param credential: The credential object used for authentication which implements SAS key authentication or SAS token authentication.
:type credential: Union[~azure.core.credentials.AzureKeyCredential, azure.eventgrid.EventGridSharedAccessSignatureCredential]
:param credential: The credential object used for authentication which
implements SAS key authentication or SAS token authentication.
:type credential: ~azure.core.credentials.AzureKeyCredential or EventGridSharedAccessSignatureCredential
"""

def __init__(self, topic_hostname, credential, **kwargs):
Expand All @@ -54,7 +50,8 @@ def send(self, events, **kwargs):
:param events: A list or an instance of CloudEvent/EventGridEvent/CustomEvent to be sent.
:type events: SendType
:keyword str content_type: The type of content to be used to send the events.
Has default value "application/json; charset=utf-8" for EventGridEvents, with "cloudevents-batch+json" for CloudEvents
Has default value "application/json; charset=utf-8" for EventGridEvents,
with "cloudevents-batch+json" for CloudEvents
:rtype: None
:raises: :class:`ValueError`, when events do not follow specified SendType.
"""
Expand All @@ -63,7 +60,7 @@ def send(self, events, **kwargs):

if all(isinstance(e, CloudEvent) for e in events) or all(_is_cloud_event(e) for e in events):
try:
events = [e._to_generated(**kwargs) for e in events]
events = [e._to_generated(**kwargs) for e in events] # pylint: disable=protected-access
except AttributeError:
pass # means it's a dictionary
kwargs.setdefault("content_type", "application/cloudevents-batch+json; charset=utf-8")
Expand Down
10 changes: 5 additions & 5 deletions sdk/eventgrid/azure-eventgrid/azure/eventgrid/_shared/mixins.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,22 +37,22 @@ def __ne__(self, other):
def __str__(self):
return str({k: v for k, v in self.__dict__.items() if not k.startswith('_')})

def has_key(self, k, **kwargs):
def has_key(self, k):
return k in self.__dict__

def update(self, *args, **kwargs):
return self.__dict__.update(*args, **kwargs)

def keys(self, **kwargs):
def keys(self):
return [k for k in self.__dict__ if not k.startswith('_')]

def values(self, **kwargs):
def values(self):
return [v for k, v in self.__dict__.items() if not k.startswith('_')]

def items(self, **kwargs):
def items(self):
return [(k, v) for k, v in self.__dict__.items() if not k.startswith('_')]

def get(self, key, default=None, **kwargs):
def get(self, key, default=None):
if key in self.__dict__:
return self.__dict__[key]
return default
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ def signature(self):
:rtype: str
"""
return self._signature

def update(self, signature):
# type: (str) -> None
"""
Expand Down
Loading