Skip to content

Commit 9ad39f5

Browse files
committed
Refactor server context
1 parent cee9142 commit 9ad39f5

File tree

7 files changed

+117
-55
lines changed

7 files changed

+117
-55
lines changed

ansys/dpf/core/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,7 @@
8181
from ansys.dpf.core import path_utilities
8282
from ansys.dpf.core import settings
8383
from ansys.dpf.core.server_factory import ServerConfig, AvailableServerConfigs
84-
from ansys.dpf.core.server_context import apply_server_context, AvailableServerContexts
84+
from ansys.dpf.core.server_context import set_default_server_context, AvailableServerContexts
8585

8686
# for matplotlib
8787
# solves "QApplication: invalid style override passed, ignoring it."

ansys/dpf/core/core.py

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -439,12 +439,12 @@ def apply_context(self, context):
439439
if not self._server().meet_version("6.0"):
440440
raise errors.DpfVersionNotSupported("6.0")
441441
if self._server().has_client():
442-
error = self._api.data_processing_apply_context_on_client(
443-
self._server().client, context.context_type.value, context.xml_path
442+
self._api.data_processing_apply_context_on_client(
443+
self._server().client, int(context.licensing_context_type), context.xml_path
444444
)
445445
else:
446-
error = self._api.data_processing_apply_context(
447-
context.context_type.value, context.xml_path
446+
self._api.data_processing_apply_context(
447+
int(context.licensing_context_type), context.xml_path
448448
)
449449

450450
def initialize_with_context(self, context):
@@ -464,14 +464,14 @@ def initialize_with_context(self, context):
464464
if self._server().has_client():
465465
if not self._server().meet_version("6.0"):
466466
raise errors.DpfVersionNotSupported("6.0")
467-
error = self._api.data_processing_initialize_with_context_on_client(
468-
self._server().client, context.context_type.value, context.xml_path
467+
self._api.data_processing_initialize_with_context_on_client(
468+
self._server().client, int(context.licensing_context_type), context.xml_path
469469
)
470470
else:
471471
if not self._server().meet_version("4.0"):
472472
raise errors.DpfVersionNotSupported("4.0")
473-
error = self._api.data_processing_initialize_with_context(
474-
context.context_type.value, context.xml_path
473+
self._api.data_processing_initialize_with_context(
474+
int(context.licensing_context_type), context.xml_path
475475
)
476476

477477
@version_requires("6.0")

ansys/dpf/core/server_context.py

Lines changed: 56 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -5,21 +5,28 @@
55
Gives the ability to choose the context with which the server should be started.
66
The context allows to choose which capabilities are available.
77
"""
8+
import os.path
89
from enum import Enum
910

1011

11-
class EContextType(Enum):
12-
pre_defined_environment = 0
13-
"""DataProcessingCore.xml that is next to DataProcessingCore.dll/libDataProcessingCore.so will
14-
be taken"""
12+
class LicensingContextType(Enum):
1513
premium = 1
16-
"""Gets the Specific premium DataProcessingCore.xml."""
17-
user_defined = 2
18-
"""Load a user defined xml using its path."""
19-
custom_defined = 3
20-
"""Loads the xml named "DpfCustomDefined.xml" that the user can modify."""
14+
"""Allows capabilities requiring Licenses check out."""
2115
entry = 4
22-
"""Loads the minimum number of plugins for a basic usage."""
16+
"""Loads minimum capabilities without requiring any Licenses check out."""
17+
18+
def __int__(self):
19+
return self.value
20+
21+
@staticmethod
22+
def same_licensing_context(first, second):
23+
if int(first) == int(LicensingContextType.entry) and int(second) != int(
24+
LicensingContextType.entry):
25+
return False
26+
elif int(second) == int(LicensingContextType.entry) and int(first) != int(
27+
LicensingContextType.entry):
28+
return False
29+
return True
2330

2431

2532
class ServerContext:
@@ -32,45 +39,66 @@ class ServerContext:
3239
xml_path : str, optional
3340
Path to the xml to load.
3441
"""
35-
def __init__(self, context_type=EContextType.user_defined, xml_path=""):
42+
43+
def __init__(self, context_type=LicensingContextType.premium, xml_path=""):
3644
self._context_type = context_type
3745
self._xml_path = xml_path
3846

3947
@property
40-
def context_type(self):
48+
def licensing_context_type(self):
49+
"""Whether capabilities requiring Licenses check out should be allowed.
50+
51+
Returns
52+
-------
53+
LicensingContextType
54+
"""
4155
return self._context_type
4256

4357
@property
4458
def xml_path(self):
59+
"""Path to the xml listing the capabilities to load on the server.
60+
61+
Returns
62+
-------
63+
str
64+
"""
4565
return self._xml_path
4666

4767
def __str__(self):
48-
return f"Server Context of type {self.context_type}" \
49-
f" with {'no' if len(self.xml_path)==0 else ''} xml path" \
50-
f"{'' if len(self.xml_path)==0 else ': ' + self.xml_path}"
68+
return f"Server Context of type {self.licensing_context_type}" \
69+
f" with {'no' if len(self.xml_path) == 0 else ''} xml path" \
70+
f"{'' if len(self.xml_path) == 0 else ': ' + self.xml_path}"
71+
72+
def __eq__(self, other):
73+
if not isinstance(other, ServerContext):
74+
return False
75+
return os.path.normpath(self.xml_path) == os.path.normpath(other.xml_path) \
76+
and LicensingContextType.same_licensing_context(self.licensing_context_type,
77+
other.licensing_context_type)
78+
79+
def __ne__(self, other):
80+
return not self == other
5181

5282

5383
class AvailableServerContexts:
54-
pre_defined_environment = ServerContext(EContextType.pre_defined_environment)
84+
pre_defined_environment = ServerContext(0)
5585
"""DataProcessingCore.xml that is next to DataProcessingCore.dll/libDataProcessingCore.so will
5686
be taken"""
57-
premium = ServerContext(EContextType.premium)
87+
premium = ServerContext(LicensingContextType.premium)
5888
"""Gets the Specific premium DataProcessingCore.xml to load most plugins with their
5989
environments."""
60-
custom_defined = ServerContext(EContextType.custom_defined)
90+
custom_defined = ServerContext(3)
6191
"""Loads the xml named "DpfCustomDefined.xml" that the user can modify."""
62-
entry = ServerContext(EContextType.entry)
92+
entry = ServerContext(LicensingContextType.entry)
6393
"""Loads the minimum number of plugins for a basic usage. Is the default."""
6494

6595

6696
SERVER_CONTEXT = AvailableServerContexts.entry
6797

6898

69-
def apply_server_context(context=AvailableServerContexts.entry, server=None) -> None:
70-
"""Allows to apply a context globally (if no server is specified) or to a
71-
given server.
72-
When called before any server is started, the context will be applied by default to any
73-
new server.
99+
def set_default_server_context(context=AvailableServerContexts.entry) -> None:
100+
"""This context will be applied by default to any new server as well as
101+
the global server, if it's running.
74102
75103
The context allows to choose which capabilities are available server side.
76104
@@ -79,20 +107,13 @@ def apply_server_context(context=AvailableServerContexts.entry, server=None) ->
79107
context : ServerContext
80108
Context to apply to the given server or to the newly started servers (when no server
81109
is given).
82-
server : server.DPFServer, optional
83-
Server with channel connected to the remote or local instance. When
84-
``None``, attempts to use the global server.
85110
86111
Notes
87112
-----
88113
Available with server's version starting at 6.0 (Ansys 2023R2).
89114
"""
90115
from ansys.dpf.core import SERVER
91-
if server is None:
92-
server = SERVER
93-
global SERVER_CONTEXT
94-
SERVER_CONTEXT = context
95-
if server is not None:
96-
from ansys.dpf.core.core import BaseService
97-
base = BaseService(server, load_operators=False)
98-
base.apply_context(context)
116+
global SERVER_CONTEXT
117+
SERVER_CONTEXT = context
118+
if SERVER is not None:
119+
SERVER.apply_context(context)

ansys/dpf/core/server_types.py

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -342,6 +342,7 @@ def __init__(self):
342342
self._server_id = None
343343
self._session_instance = None
344344
self._base_service_instance = None
345+
self._context = None
345346
self._docker_config = server_factory.RunningDockerConfig()
346347

347348
def set_as_global(self, as_global=True):
@@ -468,6 +469,19 @@ def apply_context(self, context):
468469
Available with server's version starting at 6.0 (Ansys 2023R2).
469470
"""
470471
self._base_service.apply_context(context)
472+
self._context = context
473+
474+
@property
475+
def context(self):
476+
"""Returns the settings used to load DPF's plugins.
477+
To update the context server side, use
478+
:func:`ansys.dpf.core.BaseServer.server_types.apply_context`
479+
480+
Returns
481+
-------
482+
ServerContext
483+
"""
484+
return self._context
471485

472486
def check_version(self, required_version, msg=None):
473487
"""Check if the server version matches with a required version.
@@ -639,7 +653,7 @@ def __init__(self,
639653
self._check_first_call(num_connection_tryouts)
640654
self.set_as_global(as_global=as_global)
641655
try:
642-
self._base_service.initialize_with_context(server_context.SERVER_CONTEXT)
656+
self.apply_context(server_context.SERVER_CONTEXT)
643657
except errors.DpfVersionNotSupported:
644658
pass
645659

@@ -804,11 +818,12 @@ def __init__(self,
804818
raise e
805819
self.set_as_global(as_global=as_global)
806820
try:
807-
self._base_service.apply_context(server_context.SERVER_CONTEXT)
821+
self.apply_context(server_context.SERVER_CONTEXT)
808822
except errors.DpfVersionNotSupported:
809823
self._base_service.initialize_with_context(
810824
server_context.AvailableServerContexts.premium
811825
)
826+
self._context = server_context.AvailableServerContexts.premium
812827
pass
813828

814829
@property
@@ -950,7 +965,7 @@ def __init__(
950965
check_ansys_grpc_dpf_version(self, timeout)
951966
self.set_as_global(as_global=as_global)
952967
try:
953-
self._base_service.initialize_with_context(server_context.SERVER_CONTEXT)
968+
self.apply_context(server_context.SERVER_CONTEXT)
954969
except errors.DpfVersionNotSupported:
955970
pass
956971

tests/conftest.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -446,6 +446,6 @@ def count_servers():
446446
if SERVERS_VERSION_GREATER_THAN_OR_EQUAL_TO_6_0:
447447
core.server.shutdown_all_session_servers()
448448
try:
449-
core.apply_server_context(core.AvailableServerContexts.premium)
449+
core.set_default_server_context(core.AvailableServerContexts.premium)
450450
except core.errors.DpfVersionNotSupported:
451451
pass

tests/test_multi_server.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
from ansys.dpf.core.server_factory import ServerConfig, CommunicationProtocols
99

1010
if conftest.SERVERS_VERSION_GREATER_THAN_OR_EQUAL_TO_6_0:
11-
dpf.apply_server_context(dpf.AvailableServerContexts.entry)
11+
dpf.set_default_server_context(dpf.AvailableServerContexts.entry)
1212

1313

1414
@pytest.fixture(scope="module", params=[
@@ -32,7 +32,7 @@ def other_remote_server(request):
3232

3333
if conftest.SERVERS_VERSION_GREATER_THAN_OR_EQUAL_TO_6_0:
3434
dpf.server.shutdown_all_session_servers()
35-
dpf.apply_server_context(dpf.AvailableServerContexts.premium)
35+
dpf.set_default_server_context(dpf.AvailableServerContexts.premium)
3636

3737

3838
@pytest.fixture()

tests/test_service.py

Lines changed: 31 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -446,15 +446,15 @@ def set_context_back_to_premium(request):
446446

447447
dpf.core.server.shutdown_all_session_servers()
448448
try:
449-
dpf.core.apply_server_context(dpf.core.AvailableServerContexts.entry)
449+
dpf.core.set_default_server_context(dpf.core.AvailableServerContexts.entry)
450450
except dpf.core.errors.DpfVersionNotSupported:
451451
pass
452452

453453
def revert():
454454
dpf.core.SERVER_CONFIGURATION = None
455455
dpf.core.server.shutdown_all_session_servers()
456456
try:
457-
dpf.core.apply_server_context(dpf.core.AvailableServerContexts.premium)
457+
dpf.core.set_default_server_context(dpf.core.AvailableServerContexts.premium)
458458
except dpf.core.errors.DpfVersionNotSupported:
459459
pass
460460

@@ -474,11 +474,23 @@ def test_apply_context(set_context_back_to_premium):
474474
if conftest.SERVERS_VERSION_GREATER_THAN_OR_EQUAL_TO_6_0:
475475
with pytest.raises(KeyError):
476476
dpf.core.Operator("core::field::high_pass")
477+
with pytest.raises(dpf.core.errors.DPFServerException):
478+
if dpf.core.SERVER.os == "nt":
479+
dpf.core.load_library("Ans.Dpf.Math.dll", "math_operators")
480+
else:
481+
dpf.core.load_library("libAns.Dpf.Math.so", "math_operators")
482+
assert dpf.core.SERVER.context == dpf.core.AvailableServerContexts.entry
477483
else:
478484
dpf.core.start_local_server()
479485

480-
dpf.core.apply_server_context(dpf.core.AvailableServerContexts.premium, dpf.core.SERVER)
486+
dpf.core.set_default_server_context(dpf.core.AvailableServerContexts.premium)
487+
assert dpf.core.SERVER.context == dpf.core.AvailableServerContexts.premium
481488
dpf.core.Operator("core::field::high_pass")
489+
with pytest.raises(dpf.core.errors.DPFServerException):
490+
dpf.core.set_default_server_context(dpf.core.AvailableServerContexts.entry)
491+
with pytest.raises(dpf.core.errors.DPFServerException):
492+
dpf.core.SERVER.apply_context(dpf.core.AvailableServerContexts.entry)
493+
assert dpf.core.SERVER.context == dpf.core.AvailableServerContexts.premium
482494

483495

484496
@pytest.mark.order(2)
@@ -491,17 +503,31 @@ def test_apply_context_remote(remote_config_server_type, set_context_back_to_pre
491503
if conftest.SERVERS_VERSION_GREATER_THAN_OR_EQUAL_TO_6_0:
492504
with pytest.raises(dpf.core.errors.DPFServerException):
493505
dpf.core.Operator("core::field::high_pass")
506+
with pytest.raises(dpf.core.errors.DPFServerException):
507+
if dpf.core.SERVER.os == "nt":
508+
dpf.core.load_library("Ans.Dpf.Math.dll", "math_operators")
509+
else:
510+
dpf.core.load_library("libAns.Dpf.Math.so", "math_operators")
511+
512+
assert dpf.core.SERVER.context == dpf.core.AvailableServerContexts.entry
494513
else:
495514
dpf.core.start_local_server()
496515

497-
dpf.core.apply_server_context(dpf.core.AvailableServerContexts.premium, dpf.core.SERVER)
516+
dpf.core.SERVER.apply_context(dpf.core.AvailableServerContexts.premium)
498517
dpf.core.Operator("core::field::high_pass")
518+
assert dpf.core.SERVER.context == dpf.core.AvailableServerContexts.premium
499519

500520
dpf.core.server.shutdown_all_session_servers()
501521
with pytest.raises(dpf.core.errors.DPFServerException):
502522
dpf.core.Operator("core::field::high_pass")
503-
dpf.core.apply_server_context(dpf.core.AvailableServerContexts.premium)
523+
dpf.core.set_default_server_context(dpf.core.AvailableServerContexts.premium)
504524
dpf.core.Operator("core::field::high_pass")
525+
with pytest.raises(dpf.core.errors.DPFServerException):
526+
dpf.core.set_default_server_context(dpf.core.AvailableServerContexts.entry)
527+
with pytest.raises(dpf.core.errors.DPFServerException):
528+
dpf.core.SERVER.apply_context(dpf.core.AvailableServerContexts.entry)
529+
530+
assert dpf.core.SERVER.context == dpf.core.AvailableServerContexts.premium
505531

506532

507533
@pytest.mark.order("last")

0 commit comments

Comments
 (0)