rucio 37.2.0__py3-none-any.whl → 37.4.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of rucio might be problematic. Click here for more details.
- rucio/cli/rule.py +1 -1
- rucio/client/accountclient.py +205 -60
- rucio/client/accountlimitclient.py +84 -25
- rucio/client/baseclient.py +85 -48
- rucio/client/client.py +49 -41
- rucio/client/configclient.py +36 -13
- rucio/client/credentialclient.py +16 -6
- rucio/client/didclient.py +321 -133
- rucio/client/diracclient.py +13 -6
- rucio/client/downloadclient.py +435 -165
- rucio/client/exportclient.py +8 -2
- rucio/client/fileclient.py +10 -3
- rucio/client/importclient.py +4 -1
- rucio/client/lifetimeclient.py +48 -31
- rucio/client/lockclient.py +22 -7
- rucio/client/metaconventionsclient.py +59 -21
- rucio/client/pingclient.py +3 -1
- rucio/client/replicaclient.py +213 -96
- rucio/client/requestclient.py +123 -16
- rucio/client/rseclient.py +385 -160
- rucio/client/ruleclient.py +147 -51
- rucio/client/scopeclient.py +35 -10
- rucio/client/subscriptionclient.py +60 -27
- rucio/client/touchclient.py +16 -7
- rucio/common/plugins.py +1 -1
- rucio/core/did.py +2 -3
- rucio/core/permission/generic.py +37 -1
- rucio/core/replica.py +6 -6
- rucio/core/rule.py +5 -3
- rucio/daemons/judge/evaluator.py +1 -1
- rucio/db/sqla/util.py +1 -1
- rucio/gateway/authentication.py +58 -88
- rucio/gateway/config.py +63 -75
- rucio/gateway/did.py +245 -329
- rucio/gateway/dirac.py +33 -34
- rucio/gateway/exporter.py +27 -30
- rucio/gateway/importer.py +12 -14
- rucio/gateway/lifetime_exception.py +16 -24
- rucio/gateway/lock.py +27 -40
- rucio/gateway/replica.py +334 -249
- rucio/gateway/request.py +176 -103
- rucio/gateway/rse.py +191 -218
- rucio/gateway/rule.py +115 -146
- rucio/gateway/scope.py +18 -25
- rucio/gateway/subscription.py +90 -108
- rucio/gateway/trace.py +48 -0
- rucio/vcsversion.py +3 -3
- rucio/web/rest/flaskapi/v1/accounts.py +2 -2
- rucio/web/rest/flaskapi/v1/auth.py +15 -0
- rucio/web/rest/flaskapi/v1/common.py +3 -0
- rucio/web/rest/flaskapi/v1/config.py +7 -7
- rucio/web/rest/flaskapi/v1/dids.py +55 -55
- rucio/web/rest/flaskapi/v1/dirac.py +2 -2
- rucio/web/rest/flaskapi/v1/export.py +1 -1
- rucio/web/rest/flaskapi/v1/import.py +1 -1
- rucio/web/rest/flaskapi/v1/lifetime_exceptions.py +5 -5
- rucio/web/rest/flaskapi/v1/locks.py +4 -4
- rucio/web/rest/flaskapi/v1/main.py +17 -10
- rucio/web/rest/flaskapi/v1/redirect.py +1 -1
- rucio/web/rest/flaskapi/v1/replicas.py +30 -29
- rucio/web/rest/flaskapi/v1/requests.py +211 -20
- rucio/web/rest/flaskapi/v1/rses.py +37 -37
- rucio/web/rest/flaskapi/v1/rules.py +15 -15
- rucio/web/rest/flaskapi/v1/scopes.py +3 -3
- rucio/web/rest/flaskapi/v1/subscriptions.py +9 -9
- rucio/web/rest/flaskapi/v1/traces.py +75 -77
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/rucio.cfg.template +0 -1
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/rucio_multi_vo.cfg.template +0 -1
- {rucio-37.2.0.dist-info → rucio-37.4.0.dist-info}/METADATA +1 -1
- {rucio-37.2.0.dist-info → rucio-37.4.0.dist-info}/RECORD +127 -126
- {rucio-37.2.0.dist-info → rucio-37.4.0.dist-info}/WHEEL +1 -1
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/alembic.ini.template +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/alembic_offline.ini.template +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/globus-config.yml.template +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/ldap.cfg.template +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/mail_templates/rule_approval_request.tmpl +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/mail_templates/rule_approved_admin.tmpl +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/mail_templates/rule_approved_user.tmpl +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/mail_templates/rule_denied_admin.tmpl +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/mail_templates/rule_denied_user.tmpl +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/mail_templates/rule_ok_notification.tmpl +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/rse-accounts.cfg.template +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/etc/rucio.cfg.atlas.client.template +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/requirements.server.txt +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/tools/bootstrap.py +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/tools/merge_rucio_configs.py +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/data/rucio/tools/reset_database.py +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-abacus-account +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-abacus-collection-replica +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-abacus-rse +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-admin +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-atropos +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-auditor +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-automatix +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-bb8 +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-cache-client +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-cache-consumer +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-conveyor-finisher +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-conveyor-poller +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-conveyor-preparer +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-conveyor-receiver +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-conveyor-stager +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-conveyor-submitter +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-conveyor-throttler +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-dark-reaper +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-dumper +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-follower +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-hermes +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-judge-cleaner +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-judge-evaluator +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-judge-injector +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-judge-repairer +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-kronos +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-minos +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-minos-temporary-expiration +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-necromancer +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-oauth-manager +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-reaper +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-replica-recoverer +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-rse-decommissioner +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-storage-consistency-actions +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-transmogrifier +0 -0
- {rucio-37.2.0.data → rucio-37.4.0.data}/scripts/rucio-undertaker +0 -0
- {rucio-37.2.0.dist-info → rucio-37.4.0.dist-info}/licenses/AUTHORS.rst +0 -0
- {rucio-37.2.0.dist-info → rucio-37.4.0.dist-info}/licenses/LICENSE +0 -0
- {rucio-37.2.0.dist-info → rucio-37.4.0.dist-info}/top_level.txt +0 -0
rucio/gateway/rule.py
CHANGED
|
@@ -20,7 +20,8 @@ from rucio.common.schema import validate_schema
|
|
|
20
20
|
from rucio.common.types import InternalAccount, InternalScope
|
|
21
21
|
from rucio.common.utils import gateway_update_return_dict
|
|
22
22
|
from rucio.core import rule
|
|
23
|
-
from rucio.db.sqla.
|
|
23
|
+
from rucio.db.sqla.constants import DatabaseOperationType
|
|
24
|
+
from rucio.db.sqla.session import db_session
|
|
24
25
|
from rucio.gateway.permission import has_permission
|
|
25
26
|
|
|
26
27
|
if TYPE_CHECKING:
|
|
@@ -29,8 +30,7 @@ if TYPE_CHECKING:
|
|
|
29
30
|
from sqlalchemy.orm import Session
|
|
30
31
|
|
|
31
32
|
|
|
32
|
-
|
|
33
|
-
def is_multi_vo(*, session: "Session") -> bool:
|
|
33
|
+
def is_multi_vo(session: "Session") -> bool:
|
|
34
34
|
"""
|
|
35
35
|
Check whether this instance is configured for multi-VO
|
|
36
36
|
returns: Boolean True if running in multi-VO
|
|
@@ -38,7 +38,6 @@ def is_multi_vo(*, session: "Session") -> bool:
|
|
|
38
38
|
return config_get_bool('common', 'multi_vo', raise_exception=False, default=False, session=session)
|
|
39
39
|
|
|
40
40
|
|
|
41
|
-
@transactional_session
|
|
42
41
|
def add_replication_rule(
|
|
43
42
|
dids: "Sequence[dict[str, str]]",
|
|
44
43
|
copies: int,
|
|
@@ -63,8 +62,6 @@ def add_replication_rule(
|
|
|
63
62
|
meta: Optional[dict[str, Any]],
|
|
64
63
|
issuer: str,
|
|
65
64
|
vo: str = 'def',
|
|
66
|
-
*,
|
|
67
|
-
session: "Session"
|
|
68
65
|
) -> list[str]:
|
|
69
66
|
"""
|
|
70
67
|
Adds a replication rule.
|
|
@@ -93,7 +90,6 @@ def add_replication_rule(
|
|
|
93
90
|
:param meta: WFMS metadata as a dictionary.
|
|
94
91
|
:param issuer: The issuing account of this operation.
|
|
95
92
|
:param vo: The VO to act on.
|
|
96
|
-
:param session: The database session in use.
|
|
97
93
|
:returns: List of created replication rules.
|
|
98
94
|
"""
|
|
99
95
|
if account is None:
|
|
@@ -111,69 +107,65 @@ def add_replication_rule(
|
|
|
111
107
|
|
|
112
108
|
validate_schema(name='rule', obj=kwargs, vo=vo)
|
|
113
109
|
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
def get_replication_rule(rule_id: str, issuer: str, vo: str = 'def'
|
|
110
|
+
with db_session(DatabaseOperationType.WRITE) as session:
|
|
111
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='add_rule', kwargs=kwargs, session=session)
|
|
112
|
+
if not auth_result.allowed:
|
|
113
|
+
raise AccessDenied('Account %s can not add replication rule. %s' % (issuer, auth_result.message))
|
|
114
|
+
|
|
115
|
+
account_internal = InternalAccount(account, vo=vo)
|
|
116
|
+
dids_with_internal_scope = [{'name': d['name'], 'scope': InternalScope(d['scope'], vo=vo)} for d in dids]
|
|
117
|
+
|
|
118
|
+
return rule.add_rule(account=account_internal,
|
|
119
|
+
dids=dids_with_internal_scope,
|
|
120
|
+
copies=copies,
|
|
121
|
+
rse_expression=rse_expression,
|
|
122
|
+
grouping=grouping,
|
|
123
|
+
weight=weight,
|
|
124
|
+
lifetime=lifetime,
|
|
125
|
+
locked=locked,
|
|
126
|
+
subscription_id=subscription_id,
|
|
127
|
+
source_replica_expression=source_replica_expression,
|
|
128
|
+
activity=activity,
|
|
129
|
+
notify=notify,
|
|
130
|
+
purge_replicas=purge_replicas,
|
|
131
|
+
ignore_availability=ignore_availability,
|
|
132
|
+
comment=comment,
|
|
133
|
+
ask_approval=ask_approval,
|
|
134
|
+
asynchronous=asynchronous,
|
|
135
|
+
delay_injection=delay_injection,
|
|
136
|
+
priority=priority,
|
|
137
|
+
split_container=split_container,
|
|
138
|
+
meta=meta,
|
|
139
|
+
session=session)
|
|
140
|
+
|
|
141
|
+
|
|
142
|
+
def get_replication_rule(rule_id: str, issuer: str, vo: str = 'def') -> dict[str, Any]:
|
|
147
143
|
"""
|
|
148
144
|
Get replication rule by it's id.
|
|
149
145
|
|
|
150
146
|
:param rule_id: The rule_id to get.
|
|
151
147
|
:param issuer: The issuing account of this operation.
|
|
152
148
|
:param vo: The VO of the issuer.
|
|
153
|
-
:param session: The database session in use.
|
|
154
149
|
"""
|
|
155
150
|
kwargs = {'rule_id': rule_id}
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
151
|
+
with db_session(DatabaseOperationType.READ) as session:
|
|
152
|
+
if is_multi_vo(session=session):
|
|
153
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='access_rule_vo', kwargs=kwargs, session=session)
|
|
154
|
+
if not auth_result.allowed:
|
|
155
|
+
raise AccessDenied('Account %s can not access rules at other VOs. %s' % (issuer, auth_result.message))
|
|
156
|
+
result = rule.get_rule(rule_id, session=session)
|
|
157
|
+
return gateway_update_return_dict(result, session=session)
|
|
162
158
|
|
|
163
159
|
|
|
164
|
-
@stream_session
|
|
165
160
|
def list_replication_rules(
|
|
166
161
|
filters: Optional[dict[str, Any]] = None,
|
|
167
162
|
vo: str = 'def',
|
|
168
|
-
*,
|
|
169
|
-
session: "Session"
|
|
170
163
|
) -> "Iterator[dict[str, Any]]":
|
|
171
164
|
"""
|
|
172
165
|
Lists replication rules based on a filter.
|
|
173
166
|
|
|
174
167
|
:param filters: dictionary of attributes by which the results should be filtered.
|
|
175
168
|
:param vo: The VO to act on.
|
|
176
|
-
:param session: The database session in use.
|
|
177
169
|
"""
|
|
178
170
|
# If filters is empty, create a new dict to avoid overwriting the function's default
|
|
179
171
|
filters = filters or {}
|
|
@@ -190,18 +182,16 @@ def list_replication_rules(
|
|
|
190
182
|
account = '*'
|
|
191
183
|
filters['account'] = InternalAccount(account=account, vo=vo)
|
|
192
184
|
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
185
|
+
with db_session(DatabaseOperationType.READ) as session:
|
|
186
|
+
rules = rule.list_rules(filters, session=session)
|
|
187
|
+
for r in rules:
|
|
188
|
+
yield gateway_update_return_dict(r, session=session)
|
|
196
189
|
|
|
197
190
|
|
|
198
|
-
@read_session
|
|
199
191
|
def list_replication_rule_history(
|
|
200
192
|
rule_id: str,
|
|
201
193
|
issuer: str,
|
|
202
194
|
vo: str = 'def',
|
|
203
|
-
*,
|
|
204
|
-
session: "Session"
|
|
205
195
|
) -> "Iterator[dict[str, Any]]":
|
|
206
196
|
"""
|
|
207
197
|
Lists replication rule history..
|
|
@@ -209,23 +199,20 @@ def list_replication_rule_history(
|
|
|
209
199
|
:param rule_id: The rule_id to list.
|
|
210
200
|
:param issuer: The issuing account of this operation.
|
|
211
201
|
:param vo: The VO of the issuer.
|
|
212
|
-
:param session: The database session in use.
|
|
213
202
|
"""
|
|
214
203
|
kwargs = {'rule_id': rule_id}
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
204
|
+
with db_session(DatabaseOperationType.READ) as session:
|
|
205
|
+
if is_multi_vo(session=session):
|
|
206
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='access_rule_vo', kwargs=kwargs, session=session)
|
|
207
|
+
if not auth_result.allowed:
|
|
208
|
+
raise AccessDenied('Account %s can not access rules at other VOs. %s' % (issuer, auth_result.message))
|
|
209
|
+
return rule.list_rule_history(rule_id, session=session)
|
|
220
210
|
|
|
221
211
|
|
|
222
|
-
@stream_session
|
|
223
212
|
def list_replication_rule_full_history(
|
|
224
213
|
scope: str,
|
|
225
214
|
name: str,
|
|
226
215
|
vo: str = 'def',
|
|
227
|
-
*,
|
|
228
|
-
session: "Session"
|
|
229
216
|
) -> "Iterator[dict[str, Any]]":
|
|
230
217
|
"""
|
|
231
218
|
List the rule history of a DID.
|
|
@@ -233,21 +220,18 @@ def list_replication_rule_full_history(
|
|
|
233
220
|
:param scope: The scope of the DID.
|
|
234
221
|
:param name: The name of the DID.
|
|
235
222
|
:param vo: The VO to act on.
|
|
236
|
-
:param session: The database session in use.
|
|
237
223
|
"""
|
|
238
224
|
scope_internal = InternalScope(scope, vo=vo)
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
225
|
+
with db_session(DatabaseOperationType.READ) as session:
|
|
226
|
+
rules = rule.list_rule_full_history(scope_internal, name, session=session)
|
|
227
|
+
for r in rules:
|
|
228
|
+
yield gateway_update_return_dict(r, session=session)
|
|
242
229
|
|
|
243
230
|
|
|
244
|
-
@stream_session
|
|
245
231
|
def list_associated_replication_rules_for_file(
|
|
246
232
|
scope: str,
|
|
247
233
|
name: str,
|
|
248
234
|
vo: str = 'def',
|
|
249
|
-
*,
|
|
250
|
-
session: "Session"
|
|
251
235
|
) -> "Iterator[dict[str, Any]]":
|
|
252
236
|
"""
|
|
253
237
|
Lists associated replication rules by file.
|
|
@@ -255,22 +239,19 @@ def list_associated_replication_rules_for_file(
|
|
|
255
239
|
:param scope: Scope of the file..
|
|
256
240
|
:param name: Name of the file.
|
|
257
241
|
:param vo: The VO to act on.
|
|
258
|
-
:param session: The database session in use.
|
|
259
242
|
"""
|
|
260
243
|
scope_internal = InternalScope(scope, vo=vo)
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
244
|
+
with db_session(DatabaseOperationType.READ) as session:
|
|
245
|
+
rules = rule.list_associated_rules_for_file(scope=scope_internal, name=name, session=session)
|
|
246
|
+
for r in rules:
|
|
247
|
+
yield gateway_update_return_dict(r, session=session)
|
|
264
248
|
|
|
265
249
|
|
|
266
|
-
@transactional_session
|
|
267
250
|
def delete_replication_rule(
|
|
268
251
|
rule_id: str,
|
|
269
252
|
purge_replicas: Optional[bool],
|
|
270
253
|
issuer: str,
|
|
271
254
|
vo: str = 'def',
|
|
272
|
-
*,
|
|
273
|
-
session: "Session"
|
|
274
255
|
) -> None:
|
|
275
256
|
"""
|
|
276
257
|
Deletes a replication rule and all associated locks.
|
|
@@ -279,28 +260,25 @@ def delete_replication_rule(
|
|
|
279
260
|
:param purge_replicas: Purge the replicas immediately
|
|
280
261
|
:param issuer: The issuing account of this operation
|
|
281
262
|
:param vo: The VO to act on.
|
|
282
|
-
:param session: The database session in use.
|
|
283
263
|
:raises: RuleNotFound, AccessDenied
|
|
284
264
|
"""
|
|
285
265
|
kwargs = {'rule_id': rule_id, 'purge_replicas': purge_replicas}
|
|
286
|
-
|
|
287
|
-
|
|
266
|
+
with db_session(DatabaseOperationType.WRITE) as session:
|
|
267
|
+
if is_multi_vo(session=session):
|
|
268
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='access_rule_vo', kwargs=kwargs, session=session)
|
|
269
|
+
if not auth_result.allowed:
|
|
270
|
+
raise AccessDenied('Account %s can not access rules at other VOs. %s' % (issuer, auth_result.message))
|
|
271
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='del_rule', kwargs=kwargs)
|
|
288
272
|
if not auth_result.allowed:
|
|
289
|
-
raise AccessDenied('Account %s can not
|
|
290
|
-
|
|
291
|
-
if not auth_result.allowed:
|
|
292
|
-
raise AccessDenied('Account %s can not remove this replication rule. %s' % (issuer, auth_result.message))
|
|
293
|
-
rule.delete_rule(rule_id=rule_id, purge_replicas=purge_replicas, soft=True, session=session)
|
|
273
|
+
raise AccessDenied('Account %s can not remove this replication rule. %s' % (issuer, auth_result.message))
|
|
274
|
+
rule.delete_rule(rule_id=rule_id, purge_replicas=purge_replicas, soft=True, session=session)
|
|
294
275
|
|
|
295
276
|
|
|
296
|
-
@transactional_session
|
|
297
277
|
def update_replication_rule(
|
|
298
278
|
rule_id: str,
|
|
299
279
|
options: dict[str, Any],
|
|
300
280
|
issuer: str,
|
|
301
281
|
vo: str = 'def',
|
|
302
|
-
*,
|
|
303
|
-
session: "Session"
|
|
304
282
|
) -> None:
|
|
305
283
|
"""
|
|
306
284
|
Update lock state of a replication rule.
|
|
@@ -309,42 +287,39 @@ def update_replication_rule(
|
|
|
309
287
|
:param options: Options dictionary.
|
|
310
288
|
:param issuer: The issuing account of this operation
|
|
311
289
|
:param vo: The VO to act on.
|
|
312
|
-
:param session: The database session in use.
|
|
313
290
|
:raises: RuleNotFound if no Rule can be found.
|
|
314
291
|
"""
|
|
315
292
|
kwargs = {'rule_id': rule_id, 'options': options}
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
293
|
+
with db_session(DatabaseOperationType.WRITE) as session:
|
|
294
|
+
if is_multi_vo(session=session):
|
|
295
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='access_rule_vo', kwargs=kwargs, session=session)
|
|
296
|
+
if not auth_result.allowed:
|
|
297
|
+
raise AccessDenied('Account %s can not access rules at other VOs. %s' % (issuer, auth_result.message))
|
|
298
|
+
if 'approve' in options:
|
|
299
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='approve_rule', kwargs=kwargs, session=session)
|
|
300
|
+
if not auth_result.allowed:
|
|
301
|
+
raise AccessDenied('Account %s can not approve/deny this replication rule. %s' % (issuer, auth_result.message))
|
|
302
|
+
|
|
303
|
+
issuer_ia = InternalAccount(issuer, vo=vo)
|
|
304
|
+
if options['approve']:
|
|
305
|
+
rule.approve_rule(rule_id=rule_id, approver=issuer_ia, session=session)
|
|
306
|
+
else:
|
|
307
|
+
rule.deny_rule(rule_id=rule_id, approver=issuer_ia, reason=options.get('comment', None), session=session)
|
|
328
308
|
else:
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
options['account'] = InternalAccount(options['account'], vo=vo)
|
|
336
|
-
rule.update_rule(rule_id=rule_id, options=options, session=session)
|
|
309
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='update_rule', kwargs=kwargs, session=session)
|
|
310
|
+
if not auth_result.allowed:
|
|
311
|
+
raise AccessDenied('Account %s can not update this replication rule. %s' % (issuer, auth_result.message))
|
|
312
|
+
if 'account' in options:
|
|
313
|
+
options['account'] = InternalAccount(options['account'], vo=vo)
|
|
314
|
+
rule.update_rule(rule_id=rule_id, options=options, session=session)
|
|
337
315
|
|
|
338
316
|
|
|
339
|
-
@transactional_session
|
|
340
317
|
def reduce_replication_rule(
|
|
341
318
|
rule_id: str,
|
|
342
319
|
copies: int,
|
|
343
320
|
exclude_expression: Optional[str],
|
|
344
321
|
issuer: str,
|
|
345
322
|
vo: str = 'def',
|
|
346
|
-
*,
|
|
347
|
-
session: "Session"
|
|
348
323
|
) -> str:
|
|
349
324
|
"""
|
|
350
325
|
Reduce the number of copies for a rule by atomically replacing the rule.
|
|
@@ -354,28 +329,25 @@ def reduce_replication_rule(
|
|
|
354
329
|
:param exclude_expression: RSE Expression of RSEs to exclude.
|
|
355
330
|
:param issuer: The issuing account of this operation
|
|
356
331
|
:param vo: The VO to act on.
|
|
357
|
-
:param session: The database session in use.
|
|
358
332
|
:raises: RuleReplaceFailed, RuleNotFound
|
|
359
333
|
"""
|
|
360
334
|
kwargs = {'rule_id': rule_id, 'copies': copies, 'exclude_expression': exclude_expression}
|
|
361
|
-
|
|
362
|
-
|
|
335
|
+
with db_session(DatabaseOperationType.WRITE) as session:
|
|
336
|
+
if is_multi_vo(session=session):
|
|
337
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='access_rule_vo', kwargs=kwargs, session=session)
|
|
338
|
+
if not auth_result.allowed:
|
|
339
|
+
raise AccessDenied('Account %s can not access rules at other VOs. %s' % (issuer, auth_result.message))
|
|
340
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='reduce_rule', kwargs=kwargs, session=session)
|
|
363
341
|
if not auth_result.allowed:
|
|
364
|
-
raise AccessDenied('Account %s can not
|
|
365
|
-
auth_result = has_permission(issuer=issuer, vo=vo, action='reduce_rule', kwargs=kwargs, session=session)
|
|
366
|
-
if not auth_result.allowed:
|
|
367
|
-
raise AccessDenied('Account %s can not reduce this replication rule. %s' % (issuer, auth_result.message))
|
|
342
|
+
raise AccessDenied('Account %s can not reduce this replication rule. %s' % (issuer, auth_result.message))
|
|
368
343
|
|
|
369
|
-
|
|
344
|
+
return rule.reduce_rule(rule_id=rule_id, copies=copies, exclude_expression=exclude_expression, session=session)
|
|
370
345
|
|
|
371
346
|
|
|
372
|
-
@read_session
|
|
373
347
|
def examine_replication_rule(
|
|
374
348
|
rule_id: str,
|
|
375
349
|
issuer: str,
|
|
376
350
|
vo: str = 'def',
|
|
377
|
-
*,
|
|
378
|
-
session: "Session"
|
|
379
351
|
) -> dict[str, Any]:
|
|
380
352
|
"""
|
|
381
353
|
Examine a replication rule.
|
|
@@ -383,29 +355,26 @@ def examine_replication_rule(
|
|
|
383
355
|
:param rule_id: The rule_id to get.
|
|
384
356
|
:param issuer: The issuing account of this operation.
|
|
385
357
|
:param vo: The VO of the issuer.
|
|
386
|
-
:param session: The database session in use.
|
|
387
358
|
"""
|
|
388
359
|
kwargs = {'rule_id': rule_id}
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
360
|
+
with db_session(DatabaseOperationType.READ) as session:
|
|
361
|
+
if is_multi_vo(session=session):
|
|
362
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='access_rule_vo', kwargs=kwargs, session=session)
|
|
363
|
+
if not auth_result.allowed:
|
|
364
|
+
raise AccessDenied('Account %s can not access rules at other VOs. %s' % (issuer, auth_result.message))
|
|
365
|
+
result = rule.examine_rule(rule_id, session=session)
|
|
366
|
+
result = gateway_update_return_dict(result, session=session)
|
|
367
|
+
if 'transfers' in result:
|
|
368
|
+
result['transfers'] = [gateway_update_return_dict(t, session=session) for t in result['transfers']]
|
|
397
369
|
return result
|
|
398
370
|
|
|
399
371
|
|
|
400
|
-
@transactional_session
|
|
401
372
|
def move_replication_rule(
|
|
402
373
|
rule_id: str,
|
|
403
374
|
rse_expression: str,
|
|
404
375
|
override: dict[str, Any],
|
|
405
376
|
issuer: str,
|
|
406
377
|
vo: str = 'def',
|
|
407
|
-
*,
|
|
408
|
-
session: "Session"
|
|
409
378
|
) -> str:
|
|
410
379
|
"""
|
|
411
380
|
Move a replication rule to another RSE and, once done, delete the original one.
|
|
@@ -413,7 +382,6 @@ def move_replication_rule(
|
|
|
413
382
|
:param rule_id: Rule to be moved.
|
|
414
383
|
:param rse_expression: RSE expression of the new rule.
|
|
415
384
|
:param override: Configurations to update for the new rule.
|
|
416
|
-
:param session: The DB Session.
|
|
417
385
|
:param vo: The VO to act on.
|
|
418
386
|
:raises: RuleNotFound, RuleReplaceFailed, InvalidRSEExpression, AccessDenied
|
|
419
387
|
"""
|
|
@@ -426,12 +394,13 @@ def move_replication_rule(
|
|
|
426
394
|
'override': override,
|
|
427
395
|
}
|
|
428
396
|
|
|
429
|
-
|
|
430
|
-
|
|
397
|
+
with db_session(DatabaseOperationType.WRITE) as session:
|
|
398
|
+
if is_multi_vo(session=session):
|
|
399
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='access_rule_vo', kwargs=kwargs, session=session)
|
|
400
|
+
if not auth_result.allowed:
|
|
401
|
+
raise AccessDenied('Account %s can not access rules at other VOs. %s' % (issuer, auth_result.message))
|
|
402
|
+
auth_result = has_permission(issuer=issuer, vo=vo, action='move_rule', kwargs=kwargs, session=session)
|
|
431
403
|
if not auth_result.allowed:
|
|
432
|
-
raise AccessDenied('Account %s can not
|
|
433
|
-
auth_result = has_permission(issuer=issuer, vo=vo, action='move_rule', kwargs=kwargs, session=session)
|
|
434
|
-
if not auth_result.allowed:
|
|
435
|
-
raise AccessDenied('Account %s can not move this replication rule. %s' % (issuer, auth_result.message))
|
|
404
|
+
raise AccessDenied('Account %s can not move this replication rule. %s' % (issuer, auth_result.message))
|
|
436
405
|
|
|
437
|
-
|
|
406
|
+
return rule.move_rule(**kwargs, session=session)
|
rucio/gateway/scope.py
CHANGED
|
@@ -12,27 +12,23 @@
|
|
|
12
12
|
# See the License for the specific language governing permissions and
|
|
13
13
|
# limitations under the License.
|
|
14
14
|
|
|
15
|
-
from typing import
|
|
15
|
+
from typing import Any, Optional
|
|
16
16
|
|
|
17
|
-
import rucio.common.exception
|
|
18
17
|
import rucio.gateway.permission
|
|
18
|
+
from rucio.common.exception import AccessDenied
|
|
19
19
|
from rucio.common.schema import validate_schema
|
|
20
20
|
from rucio.common.types import InternalAccount, InternalScope
|
|
21
21
|
from rucio.core import scope as core_scope
|
|
22
|
-
from rucio.db.sqla.
|
|
22
|
+
from rucio.db.sqla.constants import DatabaseOperationType
|
|
23
|
+
from rucio.db.sqla.session import db_session
|
|
23
24
|
|
|
24
|
-
if TYPE_CHECKING:
|
|
25
|
-
from sqlalchemy.orm import Session
|
|
26
25
|
|
|
27
|
-
|
|
28
|
-
@read_session
|
|
29
|
-
def list_scopes(filter_: Optional[dict[str, Any]] = None, vo: str = 'def', *, session: "Session") -> list[str]:
|
|
26
|
+
def list_scopes(filter_: Optional[dict[str, Any]] = None, vo: str = 'def') -> list[str]:
|
|
30
27
|
"""
|
|
31
28
|
Lists all scopes.
|
|
32
29
|
|
|
33
30
|
:param filter_: Dictionary of attributes by which the input data should be filtered
|
|
34
31
|
:param vo: The VO to act on.
|
|
35
|
-
:param session: The database session in use.
|
|
36
32
|
|
|
37
33
|
:returns: A list containing all scopes.
|
|
38
34
|
"""
|
|
@@ -43,17 +39,16 @@ def list_scopes(filter_: Optional[dict[str, Any]] = None, vo: str = 'def', *, se
|
|
|
43
39
|
filter_['scope'] = InternalScope(scope=filter_['scope'], vo=vo)
|
|
44
40
|
else:
|
|
45
41
|
filter_['scope'] = InternalScope(scope='*', vo=vo)
|
|
46
|
-
|
|
42
|
+
|
|
43
|
+
with db_session(DatabaseOperationType.READ) as session:
|
|
44
|
+
return [scope.external for scope in core_scope.list_scopes(filter_=filter_, session=session)]
|
|
47
45
|
|
|
48
46
|
|
|
49
|
-
@transactional_session
|
|
50
47
|
def add_scope(
|
|
51
48
|
scope: str,
|
|
52
49
|
account: str,
|
|
53
50
|
issuer: str,
|
|
54
51
|
vo: str = 'def',
|
|
55
|
-
*,
|
|
56
|
-
session: "Session"
|
|
57
52
|
) -> None:
|
|
58
53
|
"""
|
|
59
54
|
Creates a scope for an account.
|
|
@@ -62,39 +57,37 @@ def add_scope(
|
|
|
62
57
|
:param scope: The scope identifier.
|
|
63
58
|
:param issuer: The issuer account.
|
|
64
59
|
:param vo: The VO to act on.
|
|
65
|
-
:param session: The database session in use.
|
|
66
60
|
"""
|
|
67
61
|
|
|
68
62
|
validate_schema(name='scope', obj=scope, vo=vo)
|
|
69
63
|
|
|
70
64
|
kwargs = {'scope': scope, 'account': account}
|
|
71
|
-
auth_result = rucio.gateway.permission.has_permission(issuer=issuer, vo=vo, action='add_scope', kwargs=kwargs, session=session)
|
|
72
|
-
if not auth_result.allowed:
|
|
73
|
-
raise rucio.common.exception.AccessDenied('Account %s can not add scope. %s' % (issuer, auth_result.message))
|
|
74
65
|
|
|
75
|
-
|
|
76
|
-
|
|
66
|
+
with db_session(DatabaseOperationType.WRITE) as session:
|
|
67
|
+
auth_result = rucio.gateway.permission.has_permission(issuer=issuer, vo=vo, action='add_scope', kwargs=kwargs, session=session)
|
|
68
|
+
if not auth_result.allowed:
|
|
69
|
+
raise AccessDenied('Account %s can not add scope. %s' % (issuer, auth_result.message))
|
|
70
|
+
|
|
71
|
+
internal_scope = InternalScope(scope, vo=vo)
|
|
72
|
+
internal_account = InternalAccount(account, vo=vo)
|
|
77
73
|
|
|
78
|
-
|
|
74
|
+
core_scope.add_scope(internal_scope, internal_account, session=session)
|
|
79
75
|
|
|
80
76
|
|
|
81
|
-
@read_session
|
|
82
77
|
def get_scopes(
|
|
83
78
|
account: str,
|
|
84
79
|
vo: str = 'def',
|
|
85
|
-
*,
|
|
86
|
-
session: "Session"
|
|
87
80
|
) -> list[str]:
|
|
88
81
|
"""
|
|
89
82
|
Gets a list of all scopes for an account.
|
|
90
83
|
|
|
91
84
|
:param account: The account name.
|
|
92
85
|
:param vo: The VO to act on.
|
|
93
|
-
:param session: The database session in use.
|
|
94
86
|
|
|
95
87
|
:returns: A list containing the names of all scopes for this account.
|
|
96
88
|
"""
|
|
97
89
|
|
|
98
90
|
internal_account = InternalAccount(account, vo=vo)
|
|
99
91
|
|
|
100
|
-
|
|
92
|
+
with db_session(DatabaseOperationType.READ) as session:
|
|
93
|
+
return [scope.external for scope in core_scope.get_scopes(internal_account, session=session)]
|