11# SPDX-FileCopyrightText: 2023-2024 MTS (Mobile Telesystems)
22# SPDX-License-Identifier: Apache-2.0
33
4+ import asyncio
5+
46from fastapi import APIRouter , Depends , Query , status
57from kombu .exceptions import KombuError
68
@@ -81,9 +83,18 @@ async def create_transfer(
8183 if group_permission < Permission .WRITE :
8284 raise ActionNotAllowedError
8385
84- target_connection = await unit_of_work .connection .read_by_id (transfer_data .target_connection_id )
85- source_connection = await unit_of_work .connection .read_by_id (transfer_data .source_connection_id )
86- queue = await unit_of_work .queue .read_by_id (transfer_data .queue_id )
86+ async with asyncio .TaskGroup () as tasks :
87+ target_connection_task = tasks .create_task (
88+ unit_of_work .connection .read_by_id (transfer_data .target_connection_id )
89+ )
90+ source_connection_task = tasks .create_task (
91+ unit_of_work .connection .read_by_id (transfer_data .source_connection_id )
92+ )
93+ queue_task = tasks .create_task (unit_of_work .queue .read_by_id (transfer_data .queue_id ))
94+
95+ target_connection = target_connection_task .result ()
96+ source_connection = source_connection_task .result ()
97+ queue = queue_task .result ()
8798
8899 if (
89100 target_connection .group_id != source_connection .group_id
@@ -92,6 +103,9 @@ async def create_transfer(
92103 ):
93104 raise DifferentTransferAndConnectionsGroupsError
94105
106+ if transfer_data .group_id != queue .group_id :
107+ raise DifferentTransferAndQueueGroupError
108+
95109 if target_connection .data ["type" ] != transfer_data .target_params .type :
96110 raise DifferentTypeConnectionsAndParamsError (
97111 connection_type = target_connection .data ["type" ],
@@ -106,9 +120,6 @@ async def create_transfer(
106120 params_type = transfer_data .source_params .type ,
107121 )
108122
109- if transfer_data .group_id != queue .group_id :
110- raise DifferentTransferAndQueueGroupError
111-
112123 transfer_data = process_file_transfer_directory_path (transfer_data ) # type: ignore
113124
114125 async with unit_of_work :
@@ -152,46 +163,53 @@ async def copy_transfer(
152163 current_user : User = Depends (get_user (is_active = True )),
153164 unit_of_work : UnitOfWork = Depends (UnitOfWorkMarker ),
154165) -> StatusCopyTransferResponseSchema :
155- resource_role = await unit_of_work .transfer .get_resource_permission (
156- user = current_user ,
157- resource_id = transfer_id ,
158- )
159- if resource_role == Permission .NONE :
160- raise TransferNotFoundError
166+ async with asyncio .TaskGroup () as tasks :
167+ resource_role_task = tasks .create_task (
168+ unit_of_work .transfer .get_resource_permission (
169+ user = current_user ,
170+ resource_id = transfer_id ,
171+ )
172+ )
173+ target_group_role_task = tasks .create_task (
174+ unit_of_work .transfer .get_group_permission (
175+ user = current_user ,
176+ group_id = transfer_data .new_group_id ,
177+ )
178+ )
179+ transfer_task = tasks .create_task (unit_of_work .transfer .read_by_id (transfer_id ))
180+
181+ resource_role = resource_role_task .result ()
182+ target_group_role = target_group_role_task .result ()
183+ transfer = transfer_task .result ()
161184
162185 # Check: user can delete transfer
163186 if transfer_data .remove_source and resource_role < Permission .DELETE :
164187 raise ActionNotAllowedError
165188
166- target_group_role = await unit_of_work .transfer .get_group_permission (
167- user = current_user ,
168- group_id = transfer_data .new_group_id ,
169- )
170189 if target_group_role < Permission .WRITE :
171190 raise ActionNotAllowedError
172191
173- transfer = await unit_of_work .transfer .read_by_id (transfer_id = transfer_id )
174-
175192 # Check: user can copy connection
176- source_connection_role = await unit_of_work .connection .get_resource_permission (
177- user = current_user ,
178- resource_id = transfer .source_connection_id ,
179- )
180- if source_connection_role == Permission .NONE :
181- raise ConnectionNotFoundError
193+ async with asyncio .TaskGroup () as tasks :
194+ source_connection_role_task = tasks .create_task (
195+ unit_of_work .connection .get_resource_permission (
196+ user = current_user ,
197+ resource_id = transfer .source_connection_id ,
198+ )
199+ )
200+ target_connection_role_task = tasks .create_task (
201+ unit_of_work .connection .get_resource_permission (
202+ user = current_user ,
203+ resource_id = transfer .target_connection_id ,
204+ )
205+ )
206+ target_queue_task = tasks .create_task (unit_of_work .queue .read_by_id (transfer_data .new_queue_id ))
182207
183- target_connection_role = await unit_of_work .connection .get_resource_permission (
184- user = current_user ,
185- resource_id = transfer .target_connection_id ,
186- )
187- if target_connection_role == Permission .NONE :
208+ if Permission .NONE in [source_connection_role_task .result (), target_connection_role_task .result ()]:
188209 raise ConnectionNotFoundError
189210
190- # Check: new queue exists
191- new_queue = await unit_of_work .queue .read_by_id (queue_id = transfer_data .new_queue_id )
192-
193211 # Acheck: new_queue_id and new_group_id are similar
194- if new_queue .group_id != transfer_data .new_group_id :
212+ if target_queue_task . result () .group_id != transfer_data .new_group_id :
195213 raise DifferentTransferAndQueueGroupError
196214
197215 async with unit_of_work :
@@ -240,46 +258,38 @@ async def update_transfer(
240258 unit_of_work : UnitOfWork = Depends (UnitOfWorkMarker ),
241259) -> ReadTransferSchema :
242260 # Check: user can update transfer
243- resource_role = await unit_of_work .transfer .get_resource_permission (
244- user = current_user ,
245- resource_id = transfer_id ,
246- )
261+ async with asyncio .TaskGroup () as tasks :
262+ resource_role_task = tasks .create_task (
263+ unit_of_work .transfer .get_resource_permission (
264+ user = current_user ,
265+ resource_id = transfer_id ,
266+ )
267+ )
268+ transfer_task = tasks .create_task (unit_of_work .transfer .read_by_id (transfer_id ))
269+
270+ resource_role , transfer = resource_role_task .result (), transfer_task .result ()
247271
248272 if resource_role == Permission .NONE :
249273 raise TransferNotFoundError
250274
251275 if resource_role < Permission .WRITE :
252276 raise ActionNotAllowedError
253277
254- transfer = await unit_of_work .transfer .read_by_id (
255- transfer_id = transfer_id ,
256- )
257-
258- target_connection = await unit_of_work .connection .read_by_id (
259- connection_id = transfer_data .target_connection_id or transfer .target_connection_id ,
260- )
261- source_connection = await unit_of_work .connection .read_by_id (
262- connection_id = transfer_data .source_connection_id or transfer .source_connection_id ,
263- )
264-
265- queue = await unit_of_work .queue .read_by_id (
266- transfer_data .new_queue_id or transfer .queue_id ,
267- )
268-
269- # Check: user can read new connections
270- target_connection_resource_role = await unit_of_work .connection .get_resource_permission (
271- user = current_user ,
272- resource_id = target_connection .id ,
273- )
278+ async with asyncio .TaskGroup () as tasks :
279+ target_connection_task = tasks .create_task (
280+ unit_of_work .connection .read_by_id (transfer_data .target_connection_id or transfer .target_connection_id )
281+ )
282+ source_connection_task = tasks .create_task (
283+ unit_of_work .connection .read_by_id (transfer_data .source_connection_id or transfer .source_connection_id )
284+ )
285+ queue_task = tasks .create_task (unit_of_work .queue .read_by_id (transfer_data .new_queue_id or transfer .queue_id ))
274286
275- source_connection_resource_role = await unit_of_work .connection .get_resource_permission (
276- user = current_user ,
277- resource_id = source_connection .id ,
287+ target_connection , source_connection , queue = (
288+ target_connection_task .result (),
289+ source_connection_task .result (),
290+ queue_task .result (),
278291 )
279292
280- if source_connection_resource_role == Permission .NONE or target_connection_resource_role == Permission .NONE :
281- raise ConnectionNotFoundError
282-
283293 # Check: connections and transfer group
284294 if (
285295 target_connection .group_id != source_connection .group_id
@@ -420,6 +430,7 @@ async def start_run(
420430
421431 async with unit_of_work :
422432 run = await unit_of_work .run .create (transfer_id = create_run_data .transfer_id )
433+
423434 try :
424435 celery .send_task ("run_transfer_task" , kwargs = {"run_id" : run .id }, queue = transfer .queue .name )
425436 except KombuError as e :
@@ -429,6 +440,7 @@ async def start_run(
429440 status = Status .FAILED ,
430441 )
431442 raise CannotConnectToTaskQueueError (run_id = run .id ) from e
443+
432444 return ReadRunSchema .from_orm (run )
433445
434446
0 commit comments