Skip to content

Commit 6a5067f

Browse files
authored
Merge pull request #8157 from chrisburr/TheImpersonator-perf
[9.0] Improve performance of TheImpersonator
2 parents 656920b + 54c529c commit 6a5067f

File tree

1 file changed

+18
-7
lines changed

1 file changed

+18
-7
lines changed

src/DIRAC/FrameworkSystem/Utilities/diracx.py

Lines changed: 18 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,14 @@
11
import requests
22

3-
from cachetools import TTLCache, cached
3+
from cachetools import TTLCache, LRUCache, cached
44
from cachetools.keys import hashkey
55
from pathlib import Path
66
from tempfile import NamedTemporaryFile
77
from typing import Any
8+
from collections.abc import Generator
89
from DIRAC import gConfig
910
from DIRAC.ConfigurationSystem.Client.Helpers import Registry
10-
11+
from contextlib import contextmanager
1112

1213
from diracx.core.preferences import DiracxPreferences
1314

@@ -25,6 +26,8 @@
2526
DEFAULT_TOKEN_CACHE_TTL = 5 * 60
2627
DEFAULT_TOKEN_CACHE_SIZE = 1024
2728

29+
legacy_exchange_session = requests.Session()
30+
2831

2932
def get_token(
3033
username: str, group: str, dirac_properties: set[str], *, expires_minutes: int | None = None, source: str = ""
@@ -42,7 +45,7 @@ def get_token(
4245
vo = Registry.getVOForGroup(group)
4346
scopes = [f"vo:{vo}", f"group:{group}"] + [f"property:{prop}" for prop in dirac_properties]
4447

45-
r = requests.get(
48+
r = legacy_exchange_session.get(
4649
f"{diracxUrl}/api/auth/legacy-exchange",
4750
params={
4851
"preferred_username": username,
@@ -71,7 +74,11 @@ def _get_token_file(username: str, group: str, dirac_properties: set[str], *, so
7174
return token_location
7275

7376

74-
def TheImpersonator(credDict: dict[str, Any], *, source: str = "") -> SyncDiracClient:
77+
diracx_client_cache = LRUCache(maxsize=64)
78+
79+
80+
@contextmanager
81+
def TheImpersonator(credDict: dict[str, Any], *, source: str = "") -> Generator[SyncDiracClient, None, None]:
7582
"""
7683
Client to be used by DIRAC server needing to impersonate
7784
a user for diracx.
@@ -90,6 +97,10 @@ def TheImpersonator(credDict: dict[str, Any], *, source: str = "") -> SyncDiracC
9097
set(credDict.get("groupProperties", []) + credDict.get("properties", [])),
9198
source=source,
9299
)
93-
pref = DiracxPreferences(url=diracxUrl, credentials_path=token_location)
94-
95-
return SyncDiracClient(diracx_preferences=pref)
100+
client = diracx_client_cache.get(token_location)
101+
if client is None:
102+
pref = DiracxPreferences(url=diracxUrl, credentials_path=token_location)
103+
client = SyncDiracClient(diracx_preferences=pref)
104+
client.__enter__()
105+
diracx_client_cache[token_location] = client
106+
yield client

0 commit comments

Comments
 (0)