Skip to content

Commit a048eb2

Browse files
authored
Merge pull request #7444 from aldbr/v8.0_FIX_AREX-get-logging-info
[8.0] fix: AREX get pilot logging info with a token
2 parents 970cb7a + ca7a210 commit a048eb2

File tree

2 files changed

+119
-15
lines changed

2 files changed

+119
-15
lines changed

src/DIRAC/Resources/Computing/AREXComputingElement.py

Lines changed: 25 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -174,7 +174,7 @@ def _request(self, method, query, params=None, data=None, headers=None, timeout=
174174
except requests.RequestException as e:
175175
return S_ERROR(f"Request exception: {e}")
176176

177-
def _checkSession(self):
177+
def _checkSession(self, mandatoryProxy: bool = False):
178178
"""Check that the session exists and carries a valid proxy."""
179179
if not self.session:
180180
return S_ERROR("REST interface not initialised.")
@@ -183,23 +183,33 @@ def _checkSession(self):
183183
self.session.cert = None
184184
self.headers.pop("Authorization", None)
185185

186-
# Get a proxy: still mandatory, even if tokens are used to authenticate
187-
if not self.proxy:
188-
self.log.error("Proxy not set")
189-
return S_ERROR("Proxy not set")
186+
# We need a token or a proxy to interact with the REST interface
187+
if not (self.token or self.proxy):
188+
self.log.error("Proxy or token not set")
189+
return S_ERROR("Proxy or token not set")
190+
191+
# A proxy might be required: in this case, it should be present
192+
if mandatoryProxy and not self.proxy:
193+
self.log.error("Proxy is mandatory but not set")
194+
return S_ERROR("Proxy is mandatory but not set")
195+
196+
# If a proxy is required or if no token is set
197+
if mandatoryProxy or not self.token:
198+
# Prepare the proxy in X509_USER_PROXY
199+
if not (result := self._prepareProxy())["OK"]:
200+
self.log.error("Failed to set up proxy", result["Message"])
201+
return result
190202

191-
result = self._prepareProxy()
192-
if not result["OK"]:
193-
self.log.error("Failed to set up proxy", result["Message"])
194-
return result
203+
# Attach the proxy to the session
204+
self.session.cert = os.environ.get("X509_USER_PROXY")
205+
self.log.verbose("A proxy is attached to the session")
195206

207+
# If a token is set, we use it
196208
if self.token:
197209
# Attach the token to the headers if present
198-
self.headers["Authorization"] = "Bearer " + self.token["access_token"]
199-
return S_OK()
210+
self.headers["Authorization"] = f"Bearer {self.token['access_token']}"
211+
self.log.verbose("A token is attached to the header of the request(s)")
200212

201-
# Attach the proxy to the session, only if the token is unavailable
202-
self.session.cert = os.environ["X509_USER_PROXY"]
203213
return S_OK()
204214

205215
#############################################################################
@@ -413,7 +423,7 @@ def submitJob(self, executableFile, proxy, numberOfJobs=1, inputs=None, outputs=
413423
Assume that the ARC queues are always of the format nordugrid-<batchSystem>-<queue>
414424
And none of our supported batch systems have a "-" in their name
415425
"""
416-
result = self._checkSession()
426+
result = self._checkSession(mandatoryProxy=True)
417427
if not result["OK"]:
418428
self.log.error("Cannot submit jobs", result["Message"])
419429
return result
@@ -715,7 +725,7 @@ def getJobStatus(self, jobIDList):
715725
716726
:param list jobIDList: list of job references, followed by the DIRAC stamp.
717727
"""
718-
result = self._checkSession()
728+
result = self._checkSession(mandatoryProxy=True)
719729
if not result["OK"]:
720730
self.log.error("Cannot get status of the jobs", result["Message"])
721731
return result
Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,94 @@
1+
import os
2+
import requests
3+
from unittest.mock import MagicMock, patch
4+
5+
from DIRAC import S_ERROR, S_OK
6+
7+
8+
# Assuming 'arc' is imported at the module level of ARCComputingElement
9+
@patch.dict("sys.modules", {"arc": MagicMock()})
10+
def test__checkSession(mocker):
11+
"""Test checkSession"""
12+
from DIRAC.Resources.Computing.AREXComputingElement import AREXComputingElement
13+
14+
arex = AREXComputingElement("test")
15+
16+
# 1. The session has not been initialized: it shoud return an error
17+
result = arex._checkSession()
18+
19+
assert not result["OK"], result
20+
assert not arex.session
21+
assert "Authorization" not in arex.headers, arex.headers
22+
23+
# 2. This time the session is initialized but there is no proxy nor token
24+
# It should return an error
25+
arex.session = requests.Session()
26+
result = arex._checkSession()
27+
28+
assert not result["OK"], result
29+
assert arex.session
30+
assert not arex.session.cert
31+
assert "Authorization" not in arex.headers, arex.headers
32+
33+
# 3. We set a malformed proxy, but not a token: it should return an error
34+
arex.proxy = "fake proxy"
35+
mocker.patch(
36+
"DIRAC.Resources.Computing.AREXComputingElement.AREXComputingElement._prepareProxy", return_value=S_ERROR()
37+
)
38+
39+
result = arex._checkSession()
40+
assert not result["OK"], result
41+
assert arex.session
42+
assert not arex.session.cert
43+
assert "Authorization" not in arex.headers, arex.headers
44+
45+
# 4. We set a proxy, but not a token: the session should include the proxy, but not the token
46+
arex.proxy = "fake proxy"
47+
48+
def side_effect():
49+
os.environ["X509_USER_PROXY"] = arex.proxy
50+
return S_OK()
51+
52+
mocker.patch(
53+
"DIRAC.Resources.Computing.AREXComputingElement.AREXComputingElement._prepareProxy", side_effect=side_effect
54+
)
55+
56+
result = arex._checkSession()
57+
assert result["OK"], result
58+
assert arex.session
59+
assert arex.session.cert
60+
assert "Authorization" not in arex.headers, arex.headers
61+
62+
# 5. We set a proxy and a token: the session should just include
63+
# the token because the proxy is not mandatory
64+
arex.proxy = "fake proxy"
65+
arex.token = {"access_token": "fake token"}
66+
67+
result = arex._checkSession()
68+
assert result["OK"], result
69+
assert arex.session
70+
assert not arex.session.cert
71+
assert "Authorization" in arex.headers, arex.headers
72+
73+
# 6. We make the proxy mandatory: the session should include both the proxy and the token
74+
result = arex._checkSession(mandatoryProxy=True)
75+
assert result["OK"], result
76+
assert arex.session
77+
assert arex.session.cert
78+
assert "Authorization" in arex.headers, arex.headers
79+
80+
# 7. Now we just include the token, the proxy is not mandatory:
81+
# the session should only include the token
82+
arex.proxy = None
83+
result = arex._checkSession()
84+
assert result["OK"], result
85+
assert arex.session
86+
assert not arex.session.cert
87+
assert "Authorization" in arex.headers, arex.headers
88+
89+
# 8. Now we just include the token, but the proxy is mandatory: it should return an error
90+
result = arex._checkSession(mandatoryProxy=True)
91+
assert not result["OK"], result
92+
assert arex.session
93+
assert not arex.session.cert
94+
assert "Authorization" not in arex.headers, arex.headers

0 commit comments

Comments
 (0)