Skip to content

Commit aaeb59e

Browse files
authored
[ml] Address azure sdk review comments (Azure#30294)
* Address azure sdk review comments * Fix
1 parent de47b3d commit aaeb59e

File tree

8 files changed

+594
-473
lines changed

8 files changed

+594
-473
lines changed

sdk/ml/azure-ai-ml/azure/ai/ml/_schema/_feature_set/featureset_spec_properties_schema.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,11 +31,17 @@ class FeaturePropertiesSchema(metaclass=PatchedSchemaMeta):
3131
tags = fields.Dict(keys=fields.Str(), values=fields.Str(), data_key="Tags")
3232

3333

34+
class ColumnPropertiesSchema(metaclass=PatchedSchemaMeta):
35+
name = fields.Str(data_key="ColumnName")
36+
type = fields.Str(data_key="DataType")
37+
38+
3439
class FeaturesetSpecPropertiesSchema(YamlFileSchema):
3540
source = fields.Nested(SourceMetadataSchema, data_key="source")
3641
feature_transformation_code = fields.Nested(
3742
FeatureTransformationCodePropertiesSchema, data_key="featureTransformationCode"
3843
)
3944
features = fields.List(NestedField(FeaturePropertiesSchema), data_key="features")
45+
index_columns = fields.List(NestedField(ColumnPropertiesSchema), data_key="indexColumns")
4046
source_lookback = fields.Nested(DelayMetadataPropertiesSchema, data_key="sourceLookback")
4147
temporal_join_lookback = fields.Nested(DelayMetadataPropertiesSchema, data_key="temporalJoinLookback")

sdk/ml/azure-ai-ml/azure/ai/ml/_utils/_feature_store_utils.py

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
# ---------------------------------------------------------
44

55
# pylint: disable=protected-access
6-
6+
from datetime import datetime
77
from pathlib import Path
88
from tempfile import TemporaryDirectory
99
from typing import TYPE_CHECKING, Dict, Union
@@ -101,3 +101,7 @@ def _archive_or_restore(
101101
body=version_resource,
102102
**kwargs,
103103
)
104+
105+
106+
def _datetime_to_str(datetime_obj: Union[str, datetime]):
107+
return datetime_obj if isinstance(datetime_obj, str) else datetime_obj.isoformat()

sdk/ml/azure-ai-ml/azure/ai/ml/operations/_feature_set_operations.py

Lines changed: 29 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
import json
99
from pathlib import Path
1010
from datetime import datetime
11-
from typing import Dict, Optional
11+
from typing import Dict, Optional, Union
1212

1313
from marshmallow.exceptions import ValidationError as SchemaValidationError
1414

@@ -26,11 +26,12 @@
2626
from azure.ai.ml._artifacts._artifact_utilities import _check_and_upload_path
2727
from azure.ai.ml.operations._datastore_operations import DatastoreOperations
2828

29-
# from azure.ai.ml._telemetry import ActivityType, monitor_with_activity
29+
from azure.ai.ml._telemetry import ActivityType, monitor_with_activity
3030
from azure.ai.ml._utils._feature_store_utils import (
3131
_archive_or_restore,
3232
read_feature_set_metadata_contents,
3333
read_remote_feature_set_spec_metadata_contents,
34+
_datetime_to_str,
3435
)
3536
from azure.ai.ml._utils._logger_utils import OpsLogger
3637
from azure.ai.ml.entities._assets._artifacts.feature_set import FeatureSet
@@ -41,9 +42,10 @@
4142
from azure.ai.ml.entities._feature_set.feature import Feature
4243
from azure.core.polling import LROPoller
4344
from azure.core.paging import ItemPaged
45+
from azure.core.tracing.decorator import distributed_trace
4446

4547
ops_logger = OpsLogger(__name__)
46-
module_logger = ops_logger.module_logger
48+
logger, module_logger = ops_logger.package_logger, ops_logger.module_logger
4749

4850

4951
class FeatureSetOperations(_ScopeDependentOperations):
@@ -71,7 +73,8 @@ def __init__(
7173
self._datastore_operation = datastore_operations
7274
self._init_kwargs = kwargs
7375

74-
# @monitor_with_activity(logger, "FeatureSet.List", ActivityType.PUBLICAPI)
76+
@distributed_trace
77+
@monitor_with_activity(logger, "FeatureSet.List", ActivityType.PUBLICAPI)
7578
def list(
7679
self,
7780
name: Optional[str] = None,
@@ -116,7 +119,8 @@ def _get(self, name: str, version: str = None, **kwargs: Dict) -> FeaturesetVers
116119
**kwargs,
117120
)
118121

119-
# @monitor_with_activity(logger, "FeatureSet.Get", ActivityType.PUBLICAPI)
122+
@distributed_trace
123+
@monitor_with_activity(logger, "FeatureSet.Get", ActivityType.PUBLICAPI)
120124
def get(self, name: str, version: str, **kwargs: Dict) -> FeatureSet:
121125
"""Get the specified FeatureSet asset.
122126
@@ -135,7 +139,8 @@ def get(self, name: str, version: str, **kwargs: Dict) -> FeatureSet:
135139
except (ValidationException, SchemaValidationError) as ex:
136140
log_and_raise_error(ex)
137141

138-
# @monitor_with_activity(logger, "FeatureSet.BeginCreateOrUpdate", ActivityType.PUBLICAPI)
142+
@distributed_trace
143+
@monitor_with_activity(logger, "FeatureSet.BeginCreateOrUpdate", ActivityType.PUBLICAPI)
139144
def begin_create_or_update(self, featureset: FeatureSet, **kwargs: Dict) -> LROPoller[FeatureSet]:
140145
"""Create or update FeatureSet
141146
@@ -166,7 +171,8 @@ def begin_create_or_update(self, featureset: FeatureSet, **kwargs: Dict) -> LROP
166171
cls=lambda response, deserialized, headers: FeatureSet._from_rest_object(deserialized),
167172
)
168173

169-
# @monitor_with_activity(logger, "FeatureSet.BeginBackFill", ActivityType.PUBLICAPI)
174+
@distributed_trace
175+
@monitor_with_activity(logger, "FeatureSet.BeginBackFill", ActivityType.PUBLICAPI)
170176
def begin_backfill(
171177
self,
172178
*,
@@ -224,14 +230,15 @@ def begin_backfill(
224230
cls=lambda response, deserialized, headers: FeatureSetBackfillMetadata._from_rest_object(deserialized),
225231
)
226232

227-
# @monitor_with_activity(logger, "FeatureSet.ListMaterializationOperation", ActivityType.PUBLICAPI)
233+
@distributed_trace
234+
@monitor_with_activity(logger, "FeatureSet.ListMaterializationOperation", ActivityType.PUBLICAPI)
228235
def list_materialization_operations(
229236
self,
230237
name: str,
231238
version: str,
232239
*,
233-
feature_window_start_time: Optional[str] = None,
234-
feature_window_end_time: Optional[str] = None,
240+
feature_window_start_time: Optional[Union[str, datetime]] = None,
241+
feature_window_end_time: Optional[Union[str, datetime]] = None,
235242
filters: Optional[str] = None,
236243
**kwargs: Dict,
237244
) -> ItemPaged[FeatureSetMaterializationMetadata]:
@@ -242,15 +249,16 @@ def list_materialization_operations(
242249
:param version: Feature set version.
243250
:type version: str
244251
:param feature_window_start_time: Start time of the feature window to filter materialization jobs.
245-
:type feature_window_start_time: str
252+
:type feature_window_start_time: Union[str, datetime]
246253
:param feature_window_end_time: End time of the feature window to filter materialization jobs.
247-
:type feature_window_end_time: str
254+
:type feature_window_end_time: Union[str, datetime]
248255
:param filters: Comma-separated list of tag names (and optionally values). Example: tag1,tag2=value2.
249256
:type filters: str
250257
:return: An iterator like instance of ~azure.ai.ml.entities.FeatureSetMaterializationMetadata objects
251258
:rtype: ~azure.core.paging.ItemPaged[FeatureSetMaterializationMetadata]
252259
"""
253-
260+
feature_window_start_time = _datetime_to_str(feature_window_start_time) if feature_window_start_time else None
261+
feature_window_end_time = _datetime_to_str(feature_window_end_time) if feature_window_end_time else None
254262
materialization_jobs = self._operation.list_materialization_jobs(
255263
resource_group_name=self._resource_group_name,
256264
workspace_name=self._workspace_name,
@@ -264,7 +272,8 @@ def list_materialization_operations(
264272
)
265273
return materialization_jobs
266274

267-
# @monitor_with_activity(logger, "FeatureSet.ListFeatures", ActivityType.INTERNALCALL)
275+
@distributed_trace
276+
@monitor_with_activity(logger, "FeatureSet.ListFeatures", ActivityType.PUBLICAPI)
268277
def list_features(
269278
self,
270279
feature_set_name: str,
@@ -303,7 +312,8 @@ def list_features(
303312
)
304313
return features
305314

306-
# @monitor_with_activity(logger, "FeatureSet.GetFeature", ActivityType.INTERNALCALL)
315+
@distributed_trace
316+
@monitor_with_activity(logger, "FeatureSet.GetFeature", ActivityType.PUBLICAPI)
307317
def get_feature(self, feature_set_name: str, version: str, *, feature_name: str, **kwargs: Dict) -> "Feature":
308318
"""Get Feature
309319
@@ -329,7 +339,8 @@ def get_feature(self, feature_set_name: str, version: str, *, feature_name: str,
329339

330340
return Feature._from_rest_object(feature)
331341

332-
# @monitor_with_activity(logger, "FeatureSet.Archive", ActivityType.PUBLICAPI)
342+
@distributed_trace
343+
@monitor_with_activity(logger, "FeatureSet.Archive", ActivityType.PUBLICAPI)
333344
def archive(
334345
self,
335346
name: str,
@@ -354,7 +365,8 @@ def archive(
354365
**kwargs,
355366
)
356367

357-
# @monitor_with_activity(logger, "FeatureSet.Restore", ActivityType.PUBLICAPI)
368+
@distributed_trace
369+
@monitor_with_activity(logger, "FeatureSet.Restore", ActivityType.PUBLICAPI)
358370
def restore(
359371
self,
360372
name: str,

sdk/ml/azure-ai-ml/azure/ai/ml/operations/_feature_store_entity_operations.py

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -15,17 +15,18 @@
1515
from azure.ai.ml.exceptions import ValidationException
1616

1717

18-
# from azure.ai.ml._telemetry import ActivityType, monitor_with_activity
18+
from azure.ai.ml._telemetry import ActivityType, monitor_with_activity
1919
from azure.ai.ml._utils._feature_store_utils import (
2020
_archive_or_restore,
2121
)
2222
from azure.ai.ml._utils._logger_utils import OpsLogger
2323
from azure.ai.ml.entities._feature_store_entity.feature_store_entity import FeatureStoreEntity
2424
from azure.core.polling import LROPoller
2525
from azure.core.paging import ItemPaged
26+
from azure.core.tracing.decorator import distributed_trace
2627

2728
ops_logger = OpsLogger(__name__)
28-
module_logger = ops_logger.module_logger
29+
logger, module_logger = ops_logger.package_logger, ops_logger.module_logger
2930

3031

3132
class FeatureStoreEntityOperations(_ScopeDependentOperations):
@@ -50,7 +51,8 @@ def __init__(
5051
self._service_client = service_client
5152
self._init_kwargs = kwargs
5253

53-
# @monitor_with_activity(logger, "FeatureStoreEntity.List", ActivityType.PUBLICAPI)
54+
@distributed_trace
55+
@monitor_with_activity(logger, "FeatureStoreEntity.List", ActivityType.PUBLICAPI)
5456
def list(
5557
self,
5658
name: Optional[str] = None,
@@ -95,7 +97,8 @@ def _get(self, name: str, version: str = None, **kwargs: Dict) -> FeaturestoreEn
9597
**kwargs,
9698
)
9799

98-
# @monitor_with_activity(logger, "FeatureStoreEntity.Get", ActivityType.PUBLICAPI)
100+
@distributed_trace
101+
@monitor_with_activity(logger, "FeatureStoreEntity.Get", ActivityType.PUBLICAPI)
99102
def get(self, name: str, version: str, **kwargs: Dict) -> FeatureStoreEntity:
100103
"""Get the specified FeatureStoreEntity asset.
101104
@@ -114,7 +117,8 @@ def get(self, name: str, version: str, **kwargs: Dict) -> FeatureStoreEntity:
114117
except (ValidationException, SchemaValidationError) as ex:
115118
log_and_raise_error(ex)
116119

117-
# @monitor_with_activity(logger, "FeatureStoreEntity.BeginCreateOrUpdate", ActivityType.PUBLICAPI)
120+
@distributed_trace
121+
@monitor_with_activity(logger, "FeatureStoreEntity.BeginCreateOrUpdate", ActivityType.PUBLICAPI)
118122
def begin_create_or_update(
119123
self, feature_store_entity: FeatureStoreEntity, **kwargs: Dict
120124
) -> LROPoller[FeatureStoreEntity]:
@@ -137,7 +141,8 @@ def begin_create_or_update(
137141
**kwargs,
138142
)
139143

140-
# @monitor_with_activity(logger, "FeatureStoreEntity.Archive", ActivityType.PUBLICAPI)
144+
@distributed_trace
145+
@monitor_with_activity(logger, "FeatureStoreEntity.Archive", ActivityType.PUBLICAPI)
141146
def archive(
142147
self,
143148
name: str,
@@ -162,7 +167,8 @@ def archive(
162167
**kwargs,
163168
)
164169

165-
# @monitor_with_activity(logger, "FeatureStoreEntity.Restore", ActivityType.PUBLICAPI)
170+
@distributed_trace
171+
@monitor_with_activity(logger, "FeatureStoreEntity.Restore", ActivityType.PUBLICAPI)
166172
def restore(
167173
self,
168174
name: str,

sdk/ml/azure-ai-ml/azure/ai/ml/operations/_feature_store_operations.py

Lines changed: 11 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
from azure.ai.ml._restclient.v2023_04_01_preview import AzureMachineLearningWorkspaces as ServiceClient042023Preview
1212
from azure.ai.ml._scope_dependent_operations import OperationsContainer, OperationScope
1313

14-
# from azure.ai.ml._telemetry import ActivityType, monitor_with_activity
14+
from azure.ai.ml._telemetry import ActivityType, monitor_with_activity
1515
from azure.core.credentials import TokenCredential
1616
from azure.core.polling import LROPoller
1717
from azure.core.tracing.decorator import distributed_trace
@@ -40,7 +40,7 @@
4040
from ._workspace_operations_base import WorkspaceOperationsBase
4141

4242
ops_logger = OpsLogger(__name__)
43-
module_logger = ops_logger.module_logger
43+
logger, module_logger = ops_logger.package_logger, ops_logger.module_logger
4444

4545

4646
class FeatureStoreOperations(WorkspaceOperationsBase):
@@ -69,7 +69,9 @@ def __init__(
6969
)
7070
self._workspace_connection_operation = service_client.workspace_connections
7171

72-
# @monitor_with_activity(logger, "FeatureStore.List", ActivityType.PUBLICAPI)
72+
@distributed_trace
73+
@monitor_with_activity(logger, "FeatureStore.List", ActivityType.PUBLICAPI)
74+
# pylint: disable=unused-argument
7375
def list(self, *, scope: str = Scope.RESOURCE_GROUP, **kwargs: Dict) -> Iterable[FeatureStore]:
7476
"""List all feature stores that the user has access to in the current
7577
resource group or subscription.
@@ -82,23 +84,21 @@ def list(self, *, scope: str = Scope.RESOURCE_GROUP, **kwargs: Dict) -> Iterable
8284

8385
if scope == Scope.SUBSCRIPTION:
8486
return self._operation.list_by_subscription(
85-
**kwargs,
8687
cls=lambda objs: [
8788
FeatureStore._from_rest_object(filterObj)
8889
for filterObj in filter(lambda ws: ws.kind.lower() == FEATURE_STORE_KIND, objs)
8990
],
9091
)
9192
return self._operation.list_by_resource_group(
9293
self._resource_group_name,
93-
**kwargs,
9494
cls=lambda objs: [
9595
FeatureStore._from_rest_object(filterObj)
9696
for filterObj in filter(lambda ws: ws.kind.lower() == FEATURE_STORE_KIND, objs)
9797
],
9898
)
9999

100-
# @monitor_with_activity(logger, "FeatureStore.Get", ActivityType.PUBLICAPI)
101100
@distributed_trace
101+
@monitor_with_activity(logger, "FeatureStore.Get", ActivityType.PUBLICAPI)
102102
# pylint: disable=arguments-renamed
103103
def get(self, name: str, **kwargs: Dict) -> FeatureStore:
104104
"""Get a feature store by name.
@@ -111,7 +111,7 @@ def get(self, name: str, **kwargs: Dict) -> FeatureStore:
111111

112112
feature_store = None
113113
resource_group = kwargs.get("resource_group") or self._resource_group_name
114-
rest_workspace_obj = self._operation.get(resource_group, name, **kwargs)
114+
rest_workspace_obj = self._operation.get(resource_group, name)
115115
if rest_workspace_obj and rest_workspace_obj.kind and rest_workspace_obj.kind.lower() == FEATURE_STORE_KIND:
116116
feature_store = FeatureStore._from_rest_object(rest_workspace_obj)
117117

@@ -171,8 +171,8 @@ def get(self, name: str, **kwargs: Dict) -> FeatureStore:
171171

172172
return feature_store
173173

174-
# @monitor_with_activity(logger, "FeatureStore.BeginCreate", ActivityType.PUBLICAPI)
175174
@distributed_trace
175+
@monitor_with_activity(logger, "FeatureStore.BeginCreate", ActivityType.PUBLICAPI)
176176
# pylint: disable=arguments-differ
177177
def begin_create(
178178
self,
@@ -214,8 +214,8 @@ def get_callback():
214214
**kwargs,
215215
)
216216

217-
# @monitor_with_activity(logger, "FeatureStore.BeginUpdate", ActivityType.PUBLICAPI)
218217
@distributed_trace
218+
@monitor_with_activity(logger, "FeatureStore.BeginUpdate", ActivityType.PUBLICAPI)
219219
# pylint: disable=arguments-renamed
220220
def begin_update(
221221
self,
@@ -364,9 +364,9 @@ def deserialize_callback(rest_obj):
364364
**kwargs,
365365
)
366366

367-
# @monitor_with_activity(logger, "FeatureStore.BeginDelete", ActivityType.PUBLICAPI)
368367
@distributed_trace
369-
def begin_delete(self, name: str, *, delete_dependent_resources: bool, **kwargs: Dict) -> LROPoller[None]:
368+
@monitor_with_activity(logger, "FeatureStore.BeginDelete", ActivityType.PUBLICAPI)
369+
def begin_delete(self, name: str, *, delete_dependent_resources: bool = False, **kwargs: Dict) -> LROPoller[None]:
370370
"""Delete a FeatureStore.
371371
372372
:param name: Name of the FeatureStore

sdk/ml/azure-ai-ml/tests/feature_store/unittests/test_feature_store_operations.py

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -66,10 +66,10 @@ def test_update(self, mock_feature_store_operation: FeatureStoreOperations) -> N
6666
description="description",
6767
)
6868

69-
def outgoing_get_call(rg, name, **kwargs):
69+
def outgoing_get_call(rg, name):
7070
return Workspace(name=name, kind="featurestore")._to_rest_object()
7171

72-
def outgoing_call(rg, name, params, polling, cls, **kwargs):
72+
def outgoing_call(rg, name, params, polling, cls):
7373
assert rg == "test_resource_group"
7474
assert name == "name"
7575
assert params.description == "description"
@@ -83,7 +83,7 @@ def outgoing_call(rg, name, params, polling, cls, **kwargs):
8383
mock_feature_store_operation._operation.begin_update.assert_called()
8484

8585
def test_delete(self, mock_feature_store_operation: FeatureStoreOperations, mocker: MockFixture) -> None:
86-
def outgoing_call(rg, name, **kwargs):
86+
def outgoing_call(rg, name):
8787
return Workspace(name=name, kind="featurestore")._to_rest_object()
8888

8989
mock_feature_store_operation._operation.get.side_effect = outgoing_call
@@ -94,7 +94,7 @@ def outgoing_call(rg, name, **kwargs):
9494
def test_delete_non_feature_store_kind(
9595
self, mock_feature_store_operation: FeatureStoreOperations, mocker: MockFixture
9696
) -> None:
97-
def outgoing_call(rg, name, **kwargs):
97+
def outgoing_call(rg, name):
9898
return Workspace(name=name)._to_rest_object()
9999

100100
mock_feature_store_operation._operation.get.side_effect = outgoing_call

0 commit comments

Comments
 (0)