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

feat: New API update_semiconductor_wearout_props() #488

Merged
merged 4 commits into from
Jan 22, 2025
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: 1 addition & 0 deletions doc/changelog.d/488.added.md
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
feat: New API update_semiconductor_wearout_props()
71 changes: 70 additions & 1 deletion src/ansys/sherlock/core/analysis.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# Copyright (C) 2023-2024 ANSYS, Inc. and/or its affiliates.
# Copyright (C) 2023-2025 ANSYS, Inc. and/or its affiliates.

"""Module containing all analysis capabilities."""
from typing import Optional
Expand All @@ -14,6 +14,7 @@
UpdatePcbModelingPropsRequestAnalysisType,
UpdatePcbModelingPropsRequestPcbMaterialModel,
UpdatePcbModelingPropsRequestPcbModelType,
UpdateSemiconductorWearoutAnalysisPropsRequest,
ansnfernand marked this conversation as resolved.
Show resolved Hide resolved
)

try:
Expand Down Expand Up @@ -2234,3 +2235,71 @@
for return_code in self.stub.updateComponentFailureMechanismProps(update_request):
responses.append(return_code)
return responses

@require_version(252)
def update_semiconductor_wearout_props(
self,
request: UpdateSemiconductorWearoutAnalysisPropsRequest,
) -> list[SherlockCommonService_pb2.ReturnCode]:
r"""Update properties for one or more Semiconductor Wearout Analysis.

Parameters
----------
request: UpdateSemiconductorWearoutAnalysisPropsRequest
Contains all the information needed to update the properties for one or more
semiconductor wearout analyses per project.

Returns
-------
list[SherlockCommonService_pb2.ReturnCode]
Return codes for each request.

Examples
--------
>>> from ansys.sherlock.core.launcher import launch_sherlock
>>> from ansys.sherlock.core.types.analysis_types import (
SemiconductorWearoutAnalysis,
UpdateSemiconductorWearoutAnalysisPropsRequest,
)
>>> sherlock = launch_sherlock()
>>> sherlock.project.import_project_zip_archive(
project="Assembly Tutorial",
category="category",
archive_file=\
"C:\\Program Files\\ANSYS Inc\\v252\\sherlock\\tutorial\\Assembly Tutorial.zip",
)
>>> update_request1 = SemiconductorWearoutAnalysis(
cca_name="Main Board",
max_feature_size=1.5,
max_feature_size_units="mm",
part_temp_rise=10.0,
part_temp_rise_units="C",
part_temp_rise_min_enabled=True,
part_validation_enabled=False,
)
>>> update_request2 = SemiconductorWearoutAnalysis(
cca_name="Memory Card 1",
max_feature_size=2.0,
max_feature_size_units="mm",
part_temp_rise=15.0,
part_temp_rise_units="C",
part_temp_rise_min_enabled=False,
part_validation_enabled=True,
)
>>> request = UpdateSemiconductorWearoutAnalysisPropsRequest(
project="Test",
semiconductor_wearout_analysis_properties=[
update_request1,
update_request2
]
)
>>> return_codes = sherlock.analysis.update_semiconductor_wearout_props(request)
>>> for return_code in return_codes:
print(f"Return code: value={return_code.value}, message={return_code.message}")
"""
update_request = request._convert_to_grpc()

Check warning on line 2300 in src/ansys/sherlock/core/analysis.py

View check run for this annotation

Codecov / codecov/patch

src/ansys/sherlock/core/analysis.py#L2300

Added line #L2300 was not covered by tests

responses = []
for return_code in self.stub.updateSemiconductorWearoutAnalysisProps(update_request):
responses.append(return_code)
return responses

Check warning on line 2305 in src/ansys/sherlock/core/analysis.py

View check run for this annotation

Codecov / codecov/patch

src/ansys/sherlock/core/analysis.py#L2302-L2305

Added lines #L2302 - L2305 were not covered by tests
71 changes: 70 additions & 1 deletion src/ansys/sherlock/core/types/analysis_types.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# © 2023-2024 ANSYS, Inc. All rights reserved.
# © 2023-2025 ANSYS, Inc. All rights reserved.

"""Module containing types for the Analysis Service."""

Expand Down Expand Up @@ -179,3 +179,72 @@
for properties in self.component_failure_mechanism_properties_per_cca:
request.componentFailureMechanismProperties.append(properties._convert_to_grpc())
return request

ansnfernand marked this conversation as resolved.
Show resolved Hide resolved

class SemiconductorWearoutAnalysis(BaseModel):
"""Contains the properties of a semiconductor wearout analysis update request."""

cca_name: str
"""Name of the CCA."""
max_feature_size: float
"""Maximum feature size."""
max_feature_size_units: str
"""Units of the maximum feature size."""
part_temp_rise: float
"""Part temperature rise."""
part_temp_rise_units: str
"""Units of the part temperature rise."""
part_temp_rise_min_enabled: bool
"""Whether part temperature rise value is applied to the minimum temperature defined in the
thermal cycle."""
part_validation_enabled: bool
"""Whether part validation should be performed."""

def _convert_to_grpc(
self,
) -> (
analysis_service.UpdateSemiconductorWearoutAnalysisPropsRequest.SemiconductorWearoutAnalysis
):

request_class = analysis_service.UpdateSemiconductorWearoutAnalysisPropsRequest
semiconductor_wearout_analysis = request_class.SemiconductorWearoutAnalysis
grpc_data = semiconductor_wearout_analysis()

Check warning on line 211 in src/ansys/sherlock/core/types/analysis_types.py

View check run for this annotation

Codecov / codecov/patch

src/ansys/sherlock/core/types/analysis_types.py#L209-L211

Added lines #L209 - L211 were not covered by tests

grpc_data.ccaName = self.cca_name
grpc_data.maxFeatureSize = self.max_feature_size
grpc_data.maxFeatureSizeUnits = self.max_feature_size_units
grpc_data.partTempRise = self.part_temp_rise
grpc_data.partTempRiseUnits = self.part_temp_rise_units
grpc_data.partTempRiseMinEnabled = self.part_temp_rise_min_enabled
grpc_data.partValidationEnabled = self.part_validation_enabled
return grpc_data

Check warning on line 220 in src/ansys/sherlock/core/types/analysis_types.py

View check run for this annotation

Codecov / codecov/patch

src/ansys/sherlock/core/types/analysis_types.py#L213-L220

Added lines #L213 - L220 were not covered by tests

@field_validator("cca_name", "max_feature_size_units", "part_temp_rise_units")
@classmethod
def str_validation(cls, value: str, info: ValidationInfo):
"""Validate string fields listed."""
return basic_str_validator(value, info.field_name)

Check warning on line 226 in src/ansys/sherlock/core/types/analysis_types.py

View check run for this annotation

Codecov / codecov/patch

src/ansys/sherlock/core/types/analysis_types.py#L226

Added line #L226 was not covered by tests


class UpdateSemiconductorWearoutAnalysisPropsRequest(BaseModel):
"""Contains the properties of a semiconductor wearout analysis update per project."""

project: str
"""Name of the Sherlock project."""
semiconductor_wearout_analysis_properties: list[SemiconductorWearoutAnalysis]
"""List of semiconductor wearout analysis properties to update."""

@field_validator("project")
@classmethod
def str_validation(cls, value: str, info: ValidationInfo):
"""Validate string fields listed."""
return basic_str_validator(value, info.field_name)

Check warning on line 241 in src/ansys/sherlock/core/types/analysis_types.py

View check run for this annotation

Codecov / codecov/patch

src/ansys/sherlock/core/types/analysis_types.py#L241

Added line #L241 was not covered by tests

def _convert_to_grpc(
self,
) -> analysis_service.UpdateSemiconductorWearoutAnalysisPropsRequest:
request = analysis_service.UpdateSemiconductorWearoutAnalysisPropsRequest()
request.project = self.project
for properties in self.semiconductor_wearout_analysis_properties:
request.semiconductorWearoutAnalysisProperties.append(properties._convert_to_grpc())
return request

Check warning on line 250 in src/ansys/sherlock/core/types/analysis_types.py

View check run for this annotation

Codecov / codecov/patch

src/ansys/sherlock/core/types/analysis_types.py#L246-L250

Added lines #L246 - L250 were not covered by tests
90 changes: 89 additions & 1 deletion tests/test_analysis.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
# Copyright (C) 2023-2024 ANSYS, Inc. and/or its affiliates.
# Copyright (C) 2023-2025 ANSYS, Inc. and/or its affiliates.

try:
import SherlockAnalysisService_pb2
Expand Down Expand Up @@ -32,10 +32,12 @@
ModelSource,
RunAnalysisRequestAnalysisType,
RunStrainMapAnalysisRequestAnalysisType,
SemiconductorWearoutAnalysis,
UpdateComponentFailureMechanismPropsRequest,
ansnfernand marked this conversation as resolved.
Show resolved Hide resolved
UpdatePcbModelingPropsRequestAnalysisType,
UpdatePcbModelingPropsRequestPcbMaterialModel,
UpdatePcbModelingPropsRequestPcbModelType,
UpdateSemiconductorWearoutAnalysisPropsRequest,
)
from ansys.sherlock.core.utils.version_check import SKIP_VERSION_CHECK

Expand Down Expand Up @@ -2026,5 +2028,91 @@ def helper_test_update_component_failure_mechanism_props(analysis: Analysis):
assert return_code.message == ""


def helper_test_update_semiconductor_wearout_props(analysis: Analysis):
"""Test update semiconductor wearout properties API."""
try:
SemiconductorWearoutAnalysis(
cca_name="",
max_feature_size=0.1,
max_feature_size_units="mm",
part_temp_rise=10.0,
part_temp_rise_units="C",
part_temp_rise_min_enabled=True,
part_validation_enabled=False,
)
pytest.fail("No exception raised when using an invalid parameter")
except Exception as e:
assert isinstance(e, pydantic.ValidationError)
assert (
e.errors()[0]["msg"] == "Value error, cca_name is invalid because it is None or empty."
)

try:
UpdateSemiconductorWearoutAnalysisPropsRequest(
project="",
)
pytest.fail("No exception raised when using an invalid parameter")
except Exception as e:
assert isinstance(e, pydantic.ValidationError)
assert (
e.errors()[0]["msg"] == "Value error, project is invalid because it is None or empty."
)

try:
UpdateSemiconductorWearoutAnalysisPropsRequest(
project="Test",
semiconductor_wearout_analysis_properties=["Not a SemiconductorWearoutAnalysis"],
)
pytest.fail("No exception raised when using an invalid parameter")
except Exception as e:
assert isinstance(e, pydantic.ValidationError)
assert (
e.errors()[0]["msg"]
== "Input should be a valid dictionary or instance of SemiconductorWearoutAnalysis"
)

semiconductor_wearout_analysis = SemiconductorWearoutAnalysis(
cca_name="Main Board",
max_feature_size=1.5,
max_feature_size_units="mm",
part_temp_rise=10.0,
part_temp_rise_units="C",
part_temp_rise_min_enabled=True,
part_validation_enabled=False,
)
semiconductor_wearout_analysis2 = SemiconductorWearoutAnalysis(
cca_name="Memory Card 1",
max_feature_size=2.0,
max_feature_size_units="mm",
part_temp_rise=15.0,
part_temp_rise_units="C",
part_temp_rise_min_enabled=False,
part_validation_enabled=True,
)
request = UpdateSemiconductorWearoutAnalysisPropsRequest(
project="Invalid project",
semiconductor_wearout_analysis_properties=[
semiconductor_wearout_analysis,
semiconductor_wearout_analysis2,
],
)

if analysis._is_connection_up():
responses = analysis.update_semiconductor_wearout_props(request)

assert len(responses) == 2
for return_code in responses:
assert return_code.value == -1
assert return_code.message == f"Cannot find project: {request.project}"

request.project = "AssemblyTutorial"
responses = analysis.update_semiconductor_wearout_props(request)

assert len(responses) == 2
for return_code in responses:
assert return_code.value == 0
assert return_code.message == ""


if __name__ == "__main__":
test_all()
Loading