Skip to content

Commit ae79df1

Browse files
authored
Merge branch 'master' into fastapi-inprocess
2 parents 009a90e + 8fb08aa commit ae79df1

File tree

12 files changed

+185
-31
lines changed

12 files changed

+185
-31
lines changed

CHANGELOG.md

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,36 @@
11
# Changelog
22

3+
## v2.229.0 (2024-08-15)
4+
5+
### Features
6+
7+
* Support for ModelBuilder In_Process Mode (1/2)
8+
* Pulling in dependencies (in_process mode) using conda environment
9+
* Add optional CodeArtifact login to FrameworkProcessing job script
10+
* implemented security-monitoring to send metrics to CW #1510
11+
12+
### Bug Fixes and Other Changes
13+
14+
* alt configs model deployment and training issues
15+
* fix keras extension in integ test
16+
* update image_uri_configs 08-13-2024 07:17:54 PST
17+
* trn1 instance family does not support volume size
18+
* Update model.py
19+
* removed log statement
20+
* update image_uri_configs 08-09-2024 07:18:00 PST
21+
* Added torchrun compatibility for distributet training across multiple GPUs in a single node (single instance)
22+
* BiasConfig type hint
23+
* add model monitor image accounts for ap-southeast-5 and eu-central-2
24+
* aligned UTC times with PST
25+
* ensure hpt jobs inherit tags from config
26+
* add JumpStart PDT and OSU regions
27+
* chore(deps): bump certifi in /src/sagemaker/serve/utils
28+
* Updates for DJL 0.29.0 release
29+
* chore(deps): bump apache-airflow from 2.9.2 to 2.9.3 in /requirements/extras
30+
* chore(deps): bump torch from 2.0.1 to 2.2.0 in /tests/data/serve_resources/mlflow/pytorch
31+
* avoided printing stack trace and escaped input
32+
* removing kwargs as this is breaking predictor_cls param for mode…
33+
334
## v2.228.0 (2024-08-06)
435

536
### Features

VERSION

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
2.228.1.dev0
1+
2.229.1.dev0

src/sagemaker/image_uri_config/tensorflow.json

Lines changed: 43 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2465,7 +2465,8 @@
24652465
"2.11": "2.11.0",
24662466
"2.12": "2.12.0",
24672467
"2.13": "2.13.0",
2468-
"2.14": "2.14.1"
2468+
"2.14": "2.14.1",
2469+
"2.16": "2.16.2"
24692470
},
24702471
"versions": {
24712472
"1.4.1": {
@@ -4407,6 +4408,47 @@
44074408
"us-west-2": "763104351884"
44084409
},
44094410
"repository": "tensorflow-training"
4411+
},
4412+
"2.16.2": {
4413+
"py_versions": [
4414+
"py310"
4415+
],
4416+
"registries": {
4417+
"af-south-1": "626614931356",
4418+
"ap-east-1": "871362719292",
4419+
"ap-northeast-1": "763104351884",
4420+
"ap-northeast-2": "763104351884",
4421+
"ap-northeast-3": "364406365360",
4422+
"ap-south-1": "763104351884",
4423+
"ap-south-2": "772153158452",
4424+
"ap-southeast-1": "763104351884",
4425+
"ap-southeast-2": "763104351884",
4426+
"ap-southeast-3": "907027046896",
4427+
"ap-southeast-4": "457447274322",
4428+
"ca-central-1": "763104351884",
4429+
"ca-west-1": "204538143572",
4430+
"cn-north-1": "727897471807",
4431+
"cn-northwest-1": "727897471807",
4432+
"eu-central-1": "763104351884",
4433+
"eu-central-2": "380420809688",
4434+
"eu-north-1": "763104351884",
4435+
"eu-south-1": "692866216735",
4436+
"eu-south-2": "503227376785",
4437+
"eu-west-1": "763104351884",
4438+
"eu-west-2": "763104351884",
4439+
"eu-west-3": "763104351884",
4440+
"il-central-1": "780543022126",
4441+
"me-central-1": "914824155844",
4442+
"me-south-1": "217643126080",
4443+
"sa-east-1": "763104351884",
4444+
"us-east-1": "763104351884",
4445+
"us-east-2": "763104351884",
4446+
"us-gov-east-1": "446045086412",
4447+
"us-gov-west-1": "442386744353",
4448+
"us-west-1": "763104351884",
4449+
"us-west-2": "763104351884"
4450+
},
4451+
"repository": "tensorflow-training"
44104452
}
44114453
}
44124454
}

src/sagemaker/jumpstart/artifacts/metric_definitions.py

Lines changed: 11 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -96,16 +96,17 @@ def _retrieve_default_training_metric_definitions(
9696
else []
9797
)
9898

99-
instance_specific_metric_name: str
100-
for instance_specific_metric_definition in instance_specific_metric_definitions:
101-
instance_specific_metric_name = instance_specific_metric_definition["Name"]
102-
default_metric_definitions = list(
103-
filter(
104-
lambda metric_definition: metric_definition["Name"]
105-
!= instance_specific_metric_name,
106-
default_metric_definitions,
99+
if instance_specific_metric_definitions:
100+
instance_specific_metric_name: str
101+
for instance_specific_metric_definition in instance_specific_metric_definitions:
102+
instance_specific_metric_name = instance_specific_metric_definition["Name"]
103+
default_metric_definitions = list(
104+
filter(
105+
lambda metric_definition: metric_definition["Name"]
106+
!= instance_specific_metric_name,
107+
default_metric_definitions,
108+
)
107109
)
108-
)
109-
default_metric_definitions.append(instance_specific_metric_definition)
110+
default_metric_definitions.append(instance_specific_metric_definition)
110111

111112
return default_metric_definitions

src/sagemaker/jumpstart/factory/model.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -259,6 +259,7 @@ def _add_instance_type_to_kwargs(
259259
sagemaker_session=kwargs.sagemaker_session,
260260
model_type=kwargs.model_type,
261261
config_name=kwargs.config_name,
262+
hub_arn=kwargs.hub_arn,
262263
)
263264

264265
if specs.inference_configs and kwargs.config_name not in specs.inference_configs.configs:
@@ -780,6 +781,7 @@ def _add_config_name_to_deploy_kwargs(
780781
sagemaker_session=temp_session,
781782
model_type=kwargs.model_type,
782783
config_name=kwargs.config_name,
784+
hub_arn=kwargs.hub_arn,
783785
)
784786
default_config_name = _select_inference_config_from_training_config(
785787
specs=specs, training_config_name=training_config_name

src/sagemaker/jumpstart/hub/parser_utils.py

Lines changed: 25 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -10,16 +10,20 @@
1010
# distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF
1111
# ANY KIND, either express or implied. See the License for the specific
1212
# language governing permissions and limitations under the License.
13+
# pylint: skip-file
1314
"""This module contains utilities related to SageMaker JumpStart Hub."""
1415
from __future__ import absolute_import
1516

1617
import re
17-
from typing import Any, Dict
18+
from typing import Any, Dict, List, Optional
1819

1920

2021
def camel_to_snake(camel_case_string: str) -> str:
2122
"""Converts camelCaseString or UpperCamelCaseString to snake_case_string."""
2223
snake_case_string = re.sub("(.)([A-Z][a-z]+)", r"\1_\2", camel_case_string)
24+
if "-" in snake_case_string:
25+
# remove any hyphen from the string for accurate conversion.
26+
snake_case_string = snake_case_string.replace("-", "")
2327
return re.sub("([a-z0-9])([A-Z])", r"\1_\2", snake_case_string).lower()
2428

2529

@@ -29,20 +33,29 @@ def snake_to_upper_camel(snake_case_string: str) -> str:
2933
return upper_camel_case_string
3034

3135

32-
def walk_and_apply_json(json_obj: Dict[Any, Any], apply) -> Dict[Any, Any]:
33-
"""Recursively walks a json object and applies a given function to the keys."""
36+
def walk_and_apply_json(
37+
json_obj: Dict[Any, Any], apply, stop_keys: Optional[List[str]] = ["metrics"]
38+
) -> Dict[Any, Any]:
39+
"""Recursively walks a json object and applies a given function to the keys.
40+
41+
stop_keys (Optional[list[str]]): List of field keys that should stop the application function.
42+
Any children of these keys will not have the application function applied to them.
43+
"""
3444

3545
def _walk_and_apply_json(json_obj, new):
3646
if isinstance(json_obj, dict) and isinstance(new, dict):
3747
for key, value in json_obj.items():
3848
new_key = apply(key)
39-
if isinstance(value, dict):
40-
new[new_key] = {}
41-
_walk_and_apply_json(value, new=new[new_key])
42-
elif isinstance(value, list):
43-
new[new_key] = []
44-
for item in value:
45-
_walk_and_apply_json(item, new=new[new_key])
49+
if (stop_keys and new_key not in stop_keys) or stop_keys is None:
50+
if isinstance(value, dict):
51+
new[new_key] = {}
52+
_walk_and_apply_json(value, new=new[new_key])
53+
elif isinstance(value, list):
54+
new[new_key] = []
55+
for item in value:
56+
_walk_and_apply_json(item, new=new[new_key])
57+
else:
58+
new[new_key] = value
4659
else:
4760
new[new_key] = value
4861
elif isinstance(json_obj, dict) and isinstance(new, list):
@@ -51,6 +64,8 @@ def _walk_and_apply_json(json_obj, new):
5164
new.update(json_obj)
5265
elif isinstance(json_obj, list) and isinstance(new, list):
5366
new.append(json_obj)
67+
elif isinstance(json_obj, str) and isinstance(new, list):
68+
new.append(json_obj)
5469
return new
5570

5671
return _walk_and_apply_json(json_obj, new={})

src/sagemaker/jumpstart/types.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1174,7 +1174,7 @@ def __init__(self, spec: Optional[Dict[str, Any]], is_hub_content=False):
11741174
spec (Dict[str, Any]): Dictionary representation of training config ranking.
11751175
"""
11761176
if is_hub_content:
1177-
spec = {camel_to_snake(key): val for key, val in spec.items()}
1177+
spec = walk_and_apply_json(spec, camel_to_snake)
11781178
self.from_json(spec)
11791179

11801180
def from_json(self, json_obj: Dict[str, Any]) -> None:
@@ -1400,7 +1400,7 @@ def from_json(self, json_obj: Dict[str, Any]) -> None:
14001400

14011401
if self.training_supported:
14021402
if self._is_hub_content:
1403-
self.training_ecr_uri: Optional[str] = json_obj["training_ecr_uri"]
1403+
self.training_ecr_uri: Optional[str] = json_obj.get("training_ecr_uri")
14041404
self._non_serializable_slots.append("training_ecr_specs")
14051405
else:
14061406
self.training_ecr_specs: Optional[JumpStartECRSpecs] = (

src/sagemaker/jumpstart/utils.py

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@
3333

3434
from sagemaker.jumpstart import constants, enums
3535
from sagemaker.jumpstart import accessors
36+
from sagemaker.jumpstart.hub.parser_utils import camel_to_snake, snake_to_upper_camel
3637
from sagemaker.s3 import parse_s3_url
3738
from sagemaker.jumpstart.exceptions import (
3839
DeprecatedJumpStartModelError,
@@ -1103,6 +1104,17 @@ def get_jumpstart_configs(
11031104
metadata_configs.config_rankings.get("overall").rankings if metadata_configs else []
11041105
)
11051106

1107+
if hub_arn:
1108+
return (
1109+
{
1110+
config_name: metadata_configs.configs[
1111+
camel_to_snake(snake_to_upper_camel(config_name))
1112+
]
1113+
for config_name in config_names
1114+
}
1115+
if metadata_configs
1116+
else {}
1117+
)
11061118
return (
11071119
{config_name: metadata_configs.configs[config_name] for config_name in config_names}
11081120
if metadata_configs

src/sagemaker/utils.py

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1457,11 +1457,11 @@ def volume_size_supported(instance_type: str) -> bool:
14571457
# Any instance type with a "d" in the instance family (i.e. c5d, p4d, etc)
14581458
# + g5 or g6 or p5 does not support attaching an EBS volume.
14591459
family = parts[0]
1460-
return (
1461-
"d" not in family
1462-
and not family.startswith("g5")
1463-
and not family.startswith("g6")
1464-
and not family.startswith("p5")
1460+
1461+
unsupported_families = ["g5", "g6", "p5", "trn1"]
1462+
1463+
return "d" not in family and not any(
1464+
family.startswith(prefix) for prefix in unsupported_families
14651465
)
14661466
except Exception as e:
14671467
raise ValueError(f"Failed to parse instance type '{instance_type}': {str(e)}")

tests/data/tensorflow_mnist/mnist_v2.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -198,7 +198,7 @@ def main(args):
198198

199199
if args.current_host == args.hosts[0]:
200200
ckpt_manager.save()
201-
net.save("/opt/ml/model/1")
201+
net.save("/opt/ml/model/1.keras")
202202

203203

204204
if __name__ == "__main__":

0 commit comments

Comments
 (0)