Skip to content

Commit 0332164

Browse files
committed
šŸ› Refactor pagination parameters to use optional types across multiple services and routes
1 parent 008b770 commit 0332164

File tree

8 files changed

+76
-62
lines changed

8 files changed

+76
-62
lines changed

ā€Žservices/api-server/src/simcore_service_api_server/_service_jobs.pyā€Ž

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,12 @@
22
from collections.abc import Callable
33
from dataclasses import dataclass
44

5+
from common_library.exclude import as_dict_exclude_none
56
from models_library.api_schemas_webserver.projects import ProjectCreateNew, ProjectGet
67
from models_library.products import ProductName
78
from models_library.projects import ProjectID
89
from models_library.projects_nodes_io import NodeID
910
from models_library.rest_pagination import (
10-
MAXIMUM_NUMBER_OF_ITEMS_PER_PAGE,
1111
PageMetaInfoLimitOffset,
1212
PageOffsetInt,
1313
)
@@ -43,19 +43,22 @@ async def list_jobs(
4343
job_parent_resource_name: str,
4444
*,
4545
filter_any_custom_metadata: list[NameValueTuple] | None = None,
46-
pagination_offset: PageOffsetInt = 0,
47-
pagination_limit: PageLimitInt = MAXIMUM_NUMBER_OF_ITEMS_PER_PAGE - 1,
46+
pagination_offset: PageOffsetInt | None = None,
47+
pagination_limit: PageLimitInt | None = None,
4848
) -> tuple[list[Job], PageMetaInfoLimitOffset]:
4949
"""Lists all jobs for a user with pagination based on resource name prefix"""
5050

51+
pagination_kwargs = as_dict_exclude_none(
52+
offset=pagination_offset, limit=pagination_limit
53+
)
54+
5155
# 1. List projects marked as jobs
5256
projects_page = await self._web_rpc_client.list_projects_marked_as_jobs(
5357
product_name=self.product_name,
5458
user_id=self.user_id,
55-
pagination_offset=pagination_offset,
56-
pagination_limit=pagination_limit,
5759
filter_by_job_parent_resource_name_prefix=job_parent_resource_name,
5860
filter_any_custom_metadata=filter_any_custom_metadata,
61+
**pagination_kwargs,
5962
)
6063

6164
# 2. Convert projects to jobs

ā€Žservices/api-server/src/simcore_service_api_server/_service_programs.pyā€Ž

Lines changed: 11 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,12 @@
22

33
from models_library.api_schemas_catalog.services import ServiceListFilters
44
from models_library.basic_types import VersionStr
5-
from models_library.rest_pagination import PageMetaInfoLimitOffset
5+
from models_library.rest_pagination import (
6+
PageLimitInt,
7+
PageMetaInfoLimitOffset,
8+
PageOffsetInt,
9+
)
610
from models_library.services_enums import ServiceType
7-
from pydantic import NonNegativeInt, PositiveInt
811

912
from .models.schemas.programs import Program, ProgramKeyId
1013
from .services_rpc.catalog import CatalogService
@@ -31,8 +34,8 @@ async def get_program(
3134
async def list_latest_programs(
3235
self,
3336
*,
34-
pagination_offset: NonNegativeInt,
35-
pagination_limit: PositiveInt,
37+
pagination_offset: PageOffsetInt | None = None,
38+
pagination_limit: PageLimitInt | None = None,
3639
) -> tuple[list[Program], PageMetaInfoLimitOffset]:
3740
page, page_meta = await self.catalog_service.list_latest_releases(
3841
pagination_offset=pagination_offset,
@@ -47,13 +50,13 @@ async def list_program_history(
4750
self,
4851
*,
4952
program_key: ProgramKeyId,
50-
offset: NonNegativeInt,
51-
limit: PositiveInt,
53+
pagination_offset: PageOffsetInt | None = None,
54+
pagination_limit: PageLimitInt | None = None,
5255
) -> tuple[list[Program], PageMetaInfoLimitOffset]:
5356
page, page_meta = await self.catalog_service.list_release_history_latest_first(
5457
filter_by_service_key=program_key,
55-
pagination_offset=offset,
56-
pagination_limit=limit,
58+
pagination_offset=pagination_offset,
59+
pagination_limit=pagination_limit,
5760
)
5861
if len(page) == 0:
5962
return [], page_meta

ā€Žservices/api-server/src/simcore_service_api_server/_service_solvers.pyā€Ž

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -90,11 +90,11 @@ async def get_latest_release(
9090
async def list_jobs(
9191
self,
9292
*,
93+
pagination_offset: PageOffsetInt | None = None,
94+
pagination_limit: PageLimitInt | None = None,
9395
filter_by_solver_key: SolverKeyId | None = None,
9496
filter_by_solver_version: VersionStr | None = None,
9597
filter_any_custom_metadata: list[NameValueTuple] | None = None,
96-
pagination_offset: PageOffsetInt = 0,
97-
pagination_limit: PageLimitInt = DEFAULT_PAGINATION_LIMIT,
9898
) -> tuple[list[Job], PageMetaInfoLimitOffset]:
9999
"""Lists all solver jobs for a user with pagination"""
100100

@@ -124,8 +124,8 @@ async def solver_release_history(
124124
self,
125125
*,
126126
solver_key: SolverKeyId,
127-
pagination_offset: PageOffsetInt,
128-
pagination_limit: PageLimitInt,
127+
pagination_offset: PageOffsetInt | None = None,
128+
pagination_limit: PageLimitInt | None = None,
129129
) -> tuple[list[Solver], PageMetaInfoLimitOffset]:
130130

131131
releases, page_meta = (
@@ -155,8 +155,8 @@ async def solver_release_history(
155155
async def list_all_solvers(
156156
self,
157157
*,
158-
pagination_offset: PageOffsetInt,
159-
pagination_limit: PageLimitInt,
158+
pagination_offset: PageOffsetInt | None = None,
159+
pagination_limit: PageLimitInt | None = None,
160160
filter_by_solver_key_pattern: str | None = None,
161161
filter_by_version_display_pattern: str | None = None,
162162
) -> tuple[list[Solver], PageMetaInfoLimitOffset]:
@@ -196,8 +196,8 @@ async def list_all_solvers(
196196
async def latest_solvers(
197197
self,
198198
*,
199-
pagination_offset: PageOffsetInt,
200-
pagination_limit: PageLimitInt,
199+
pagination_offset: PageOffsetInt | None = None,
200+
pagination_limit: PageLimitInt | None = None,
201201
filter_by_solver_key_pattern: str | None = None,
202202
filter_by_version_display_pattern: str | None = None,
203203
) -> tuple[list[Solver], PageMetaInfoLimitOffset]:

ā€Žservices/api-server/src/simcore_service_api_server/_service_studies.pyā€Ž

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -36,8 +36,8 @@ async def list_jobs(
3636
self,
3737
*,
3838
filter_by_study_id: StudyID | None = None,
39-
pagination_offset: PageOffsetInt = 0,
40-
pagination_limit: PageLimitInt = DEFAULT_PAGINATION_LIMIT,
39+
pagination_offset: PageOffsetInt | None = None,
40+
pagination_limit: PageLimitInt | None = None,
4141
) -> tuple[list[Job], PageMetaInfoLimitOffset]:
4242
"""Lists all solver jobs for a user with pagination"""
4343

ā€Žservices/api-server/src/simcore_service_api_server/api/routes/programs.pyā€Ž

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -90,8 +90,8 @@ async def list_program_history(
9090
):
9191
programs, page_meta = await program_service.list_program_history(
9292
program_key=program_key,
93-
offset=page_params.offset,
94-
limit=page_params.limit,
93+
pagination_offset=page_params.offset,
94+
pagination_limit=page_params.limit,
9595
)
9696
page_params.limit = page_meta.limit
9797
page_params.offset = page_meta.offset

ā€Žservices/api-server/src/simcore_service_api_server/services_http/storage.pyā€Ž

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,8 @@
2020
)
2121
from models_library.basic_types import SHA256Str
2222
from models_library.generics import Envelope
23-
from pydantic import AnyUrl, PositiveInt
23+
from models_library.rest_pagination import PageLimitInt, PageOffsetInt
24+
from pydantic import AnyUrl
2425
from settings_library.tracing import TracingSettings
2526
from starlette.datastructures import URL
2627

@@ -97,8 +98,8 @@ async def search_owned_files(
9798
user_id: int,
9899
file_id: UUID | None,
99100
sha256_checksum: SHA256Str | None = None,
100-
limit: PositiveInt | None = None,
101-
offset: PositiveInt | None = None,
101+
limit: PageLimitInt | None = None,
102+
offset: PageOffsetInt | None = None,
102103
) -> list[StorageFileMetaData]:
103104
# NOTE: can NOT use /locations/0/files/metadata with uuid_filter=api/ because
104105
# logic in storage 'wrongly' assumes that all data is associated to a project and

ā€Žservices/api-server/src/simcore_service_api_server/services_http/webserver.pyā€Ž

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@
3838
from models_library.generics import Envelope
3939
from models_library.projects import ProjectID
4040
from models_library.projects_nodes_io import NodeID
41-
from models_library.rest_pagination import Page
41+
from models_library.rest_pagination import Page, PageLimitInt, PageOffsetInt
4242
from models_library.utils.fastapi_encoders import jsonable_encoder
4343
from pydantic import PositiveInt
4444
from servicelib.aiohttp.long_running_tasks.server import TaskStatus
@@ -353,7 +353,7 @@ async def get_project(self, *, project_id: UUID) -> ProjectGet:
353353
return data
354354

355355
async def get_projects_w_solver_page(
356-
self, *, solver_name: str, limit: int, offset: int
356+
self, *, solver_name: str, limit: PageLimitInt, offset: PageOffsetInt
357357
) -> Page[ProjectGet]:
358358
assert not solver_name.endswith("/") # nosec
359359

@@ -364,7 +364,7 @@ async def get_projects_w_solver_page(
364364
search_by_project_name=solver_name,
365365
)
366366

367-
async def get_projects_page(self, *, limit: int, offset: int):
367+
async def get_projects_page(self, *, limit: PageLimitInt, offset: PageOffsetInt):
368368
return await self._page_projects(
369369
limit=limit,
370370
offset=offset,

ā€Žservices/api-server/src/simcore_service_api_server/services_rpc/catalog.pyā€Ž

Lines changed: 38 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
from dataclasses import dataclass
22
from functools import partial
3+
from typing import Any
34

5+
from common_library.exclude import as_dict_exclude_none
46
from models_library.api_schemas_catalog.services import (
57
LatestServiceGet,
68
ServiceGetV2,
@@ -10,7 +12,6 @@
1012
from models_library.api_schemas_catalog.services_ports import ServicePortGet
1113
from models_library.products import ProductName
1214
from models_library.rest_pagination import (
13-
DEFAULT_NUMBER_OF_ITEMS_PER_PAGE,
1415
PageLimitInt,
1516
PageMetaInfoLimitOffset,
1617
PageOffsetInt,
@@ -36,6 +37,16 @@
3637
_exception_mapper = partial(service_exception_mapper, service_name="CatalogService")
3738

3839

40+
def _create_page_meta_info(page: Any) -> PageMetaInfoLimitOffset:
41+
"""Creates a PageMetaInfoLimitOffset from an RPC response page."""
42+
return PageMetaInfoLimitOffset(
43+
limit=page.meta.limit,
44+
offset=page.meta.offset,
45+
total=page.meta.total,
46+
count=page.meta.count,
47+
)
48+
49+
3950
@dataclass(frozen=True, kw_only=True)
4051
class CatalogService:
4152
_rpc_client: RabbitMQRPCClient
@@ -45,56 +56,53 @@ class CatalogService:
4556
async def list_latest_releases(
4657
self,
4758
*,
48-
pagination_offset: PageOffsetInt = 0,
49-
pagination_limit: PageLimitInt = DEFAULT_NUMBER_OF_ITEMS_PER_PAGE,
59+
pagination_offset: PageOffsetInt | None = None,
60+
pagination_limit: PageLimitInt | None = None,
5061
filters: ServiceListFilters | None = None,
5162
) -> tuple[list[LatestServiceGet], PageMetaInfoLimitOffset]:
5263

64+
pagination_kwargs = as_dict_exclude_none(
65+
offset=pagination_offset, limit=pagination_limit
66+
)
67+
5368
page = await catalog_rpc.list_services_paginated(
5469
self._rpc_client,
5570
product_name=self.product_name,
5671
user_id=self.user_id,
57-
offset=pagination_offset,
58-
limit=pagination_limit,
5972
filters=filters,
73+
**pagination_kwargs,
6074
)
61-
meta = PageMetaInfoLimitOffset(
62-
limit=page.meta.limit,
63-
offset=page.meta.offset,
64-
total=page.meta.total,
65-
count=page.meta.count,
66-
)
75+
meta = _create_page_meta_info(page)
6776
return page.data, meta
6877

6978
async def list_release_history_latest_first(
7079
self,
7180
*,
7281
filter_by_service_key: ServiceKey,
73-
pagination_offset: PageOffsetInt = 0,
74-
pagination_limit: PageLimitInt = DEFAULT_NUMBER_OF_ITEMS_PER_PAGE,
82+
pagination_offset: PageOffsetInt | None = None,
83+
pagination_limit: PageLimitInt | None = None,
7584
) -> tuple[list[ServiceRelease], PageMetaInfoLimitOffset]:
7685

86+
pagination_kwargs = as_dict_exclude_none(
87+
offset=pagination_offset, limit=pagination_limit
88+
)
89+
7790
page = await catalog_rpc.list_my_service_history_latest_first(
7891
self._rpc_client,
7992
product_name=self.product_name,
8093
user_id=self.user_id,
8194
service_key=filter_by_service_key,
82-
offset=pagination_offset,
83-
limit=pagination_limit,
84-
)
85-
meta = PageMetaInfoLimitOffset(
86-
limit=page.meta.limit,
87-
offset=page.meta.offset,
88-
total=page.meta.total,
89-
count=page.meta.count,
95+
**pagination_kwargs,
9096
)
97+
98+
meta = _create_page_meta_info(page)
9199
return page.data, meta
92100

93101
async def list_all_services_summaries(
94102
self,
95103
*,
96-
pagination_offset: PageOffsetInt = 0,
97-
pagination_limit: PageLimitInt = DEFAULT_NUMBER_OF_ITEMS_PER_PAGE,
104+
pagination_offset: PageOffsetInt | None = None,
105+
pagination_limit: PageLimitInt | None = None,
98106
filters: ServiceListFilters | None = None,
99107
) -> tuple[list[ServiceSummary], PageMetaInfoLimitOffset]:
100108
"""Lists all services with pagination, including all versions of each service.
@@ -109,20 +117,19 @@ async def list_all_services_summaries(
109117
Returns:
110118
Tuple containing list of service summaries and pagination metadata
111119
"""
120+
121+
pagination_kwargs = as_dict_exclude_none(
122+
offset=pagination_offset, limit=pagination_limit
123+
)
124+
112125
page = await catalog_rpc.list_all_services_summaries_paginated(
113126
self._rpc_client,
114127
product_name=self.product_name,
115128
user_id=self.user_id,
116-
offset=pagination_offset,
117-
limit=pagination_limit,
118129
filters=filters,
130+
**pagination_kwargs,
119131
)
120-
meta = PageMetaInfoLimitOffset(
121-
limit=page.meta.limit,
122-
offset=page.meta.offset,
123-
total=page.meta.total,
124-
count=page.meta.count,
125-
)
132+
meta = _create_page_meta_info(page)
126133
return page.data, meta
127134

128135
@_exception_mapper(

0 commit comments

Comments
Ā (0)