nlbone 0.11.0__tar.gz → 0.11.1__tar.gz
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.
- {nlbone-0.11.0 → nlbone-0.11.1}/PKG-INFO +1 -1
- {nlbone-0.11.0 → nlbone-0.11.1}/pyproject.toml +1 -1
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/postgres/query_builder.py +52 -1
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/additional_filed/assembler.py +50 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/additional_filed/field_registry.py +2 -1
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/additional_filed/resolver.py +79 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/dependencies/async_auth.py +1 -1
- {nlbone-0.11.0 → nlbone-0.11.1}/.gitignore +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/LICENSE +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/README.md +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/auth/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/auth/async_auth_service.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/auth/async_token_provider.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/auth/auth_service.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/auth/keycloak.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/auth/token_provider.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/cache/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/cache/async_redis.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/cache/memory.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/cache/pubsub_listener.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/cache/redis.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/postgres/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/postgres/audit.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/postgres/base.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/postgres/engine.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/postgres/repository.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/postgres/schema.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/postgres/types.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/postgres/uow.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/redis/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/db/redis/client.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/http_clients/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/http_clients/pricing/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/http_clients/pricing/async_pricing_service.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/http_clients/pricing/pricing_service.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/http_clients/uploadchi/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/http_clients/uploadchi/uploadchi.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/http_clients/uploadchi/uploadchi_async.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/i18n/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/i18n/engine.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/i18n/loaders.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/i18n/locales/fa-IR.json +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/messaging/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/messaging/event_bus.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/messaging/rabbitmq.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/outbox/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/outbox/outbox_consumer.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/outbox/outbox_repo.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/percolation/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/percolation/connection.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/repositories/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/snowflake.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/ticketing/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/ticketing/client.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/config/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/config/logging.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/config/settings.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/container.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/application/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/application/base_worker.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/application/bus.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/application/di.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/application/registry.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/application/services/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/application/use_case.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/domain/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/domain/base.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/domain/models.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/ports/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/ports/auth.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/ports/cache.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/ports/event_bus.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/ports/files.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/ports/outbox.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/ports/repository.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/ports/translation.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/core/ports/uow.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/additional_filed/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/additional_filed/default_field_rules/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/additional_filed/default_field_rules/image_field_rules.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/dependencies/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/dependencies/auth.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/dependencies/client_credential.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/dependencies/db.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/dependencies/uow.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/exception_handlers.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/exceptions.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/middleware/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/middleware/access_log.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/middleware/add_request_context.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/middleware/authentication.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/pagination/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/pagination/offset_base.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/routers.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/schema/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/schema/adaptive_schema.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/schema/base_response_model.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/schemas.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/cli/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/cli/crypto.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/cli/init_db.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/cli/main.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/cli/ticket.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/jobs/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/jobs/dispatch_outbox.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/jobs/sync_tokens.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/types.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/__init__.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/cache.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/cache_keys.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/cache_registry.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/context.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/crypto.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/flatten_dict.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/flatten_sqlalchemy_result.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/http.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/normalize_mobile.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/read_files.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/redactor.py +0 -0
- {nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/utils/time.py +0 -0
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
from typing import Any, Callable, List, Optional, Sequence, Type, Union
|
|
2
2
|
|
|
3
|
-
from sqlalchemy import and_, asc, case, desc, literal, or_
|
|
3
|
+
from sqlalchemy import Select, and_, asc, case, desc, func, literal, or_, select
|
|
4
4
|
from sqlalchemy.dialects.postgresql import ENUM as PGEnum
|
|
5
|
+
from sqlalchemy.ext.asyncio import AsyncSession
|
|
5
6
|
from sqlalchemy.orm import Query, Session, aliased
|
|
6
7
|
from sqlalchemy.orm.attributes import InstrumentedAttribute
|
|
7
8
|
from sqlalchemy.orm.interfaces import LoaderOption
|
|
@@ -384,6 +385,19 @@ def _apply_order(pagination: PaginateRequest, entity, query):
|
|
|
384
385
|
return query
|
|
385
386
|
|
|
386
387
|
|
|
388
|
+
def apply_pagination_async(pagination: PaginateRequest, entity, stmt: Select = None, limit: bool = True) -> Select:
|
|
389
|
+
if stmt is None:
|
|
390
|
+
stmt = select(entity)
|
|
391
|
+
|
|
392
|
+
stmt = _apply_filters(pagination, entity, stmt)
|
|
393
|
+
stmt = _apply_order(pagination, entity, stmt)
|
|
394
|
+
|
|
395
|
+
if limit:
|
|
396
|
+
stmt = stmt.limit(pagination.limit).offset(pagination.offset)
|
|
397
|
+
|
|
398
|
+
return stmt
|
|
399
|
+
|
|
400
|
+
|
|
387
401
|
def apply_pagination(pagination: PaginateRequest, entity, session: Session, limit=True, query=None) -> Query:
|
|
388
402
|
if not query:
|
|
389
403
|
query = session.query(entity)
|
|
@@ -437,6 +451,43 @@ def _serialize_item(item: Any, output_cls: OutputType) -> Any:
|
|
|
437
451
|
return item
|
|
438
452
|
|
|
439
453
|
|
|
454
|
+
async def get_paginated_response_async(
|
|
455
|
+
pagination,
|
|
456
|
+
entity,
|
|
457
|
+
session: AsyncSession,
|
|
458
|
+
*,
|
|
459
|
+
with_count: bool = True,
|
|
460
|
+
output_cls: Optional[Type] = None,
|
|
461
|
+
eager_options: Optional[Sequence[LoaderOption]] = None,
|
|
462
|
+
query: Optional[Select] = None,
|
|
463
|
+
) -> dict:
|
|
464
|
+
stmt = query if query is not None else select(entity)
|
|
465
|
+
|
|
466
|
+
if eager_options:
|
|
467
|
+
stmt = stmt.options(*eager_options)
|
|
468
|
+
|
|
469
|
+
filtered_stmt = apply_pagination_async(pagination, entity, stmt=stmt, limit=False)
|
|
470
|
+
|
|
471
|
+
total_count = None
|
|
472
|
+
if with_count:
|
|
473
|
+
subquery = filtered_stmt.subquery()
|
|
474
|
+
count_stmt = select(func.count()).select_from(subquery)
|
|
475
|
+
total_count = await session.scalar(count_stmt)
|
|
476
|
+
|
|
477
|
+
final_stmt = filtered_stmt.limit(pagination.limit).offset(pagination.offset)
|
|
478
|
+
result = await session.execute(final_stmt)
|
|
479
|
+
rows = result.scalars().all()
|
|
480
|
+
|
|
481
|
+
if output_cls is not None:
|
|
482
|
+
data = [output_cls.model_validate(r, from_attributes=True).model_dump() for r in rows]
|
|
483
|
+
else:
|
|
484
|
+
data = rows
|
|
485
|
+
|
|
486
|
+
return PaginateResponse(
|
|
487
|
+
total_count=total_count, data=data, limit=pagination.limit, offset=pagination.offset
|
|
488
|
+
).to_dict()
|
|
489
|
+
|
|
490
|
+
|
|
440
491
|
def get_paginated_response(
|
|
441
492
|
pagination,
|
|
442
493
|
entity,
|
|
@@ -2,11 +2,61 @@ import inspect
|
|
|
2
2
|
from typing import Any, Dict
|
|
3
3
|
|
|
4
4
|
from pydantic import BaseModel
|
|
5
|
+
from sqlalchemy.ext.asyncio import AsyncSession
|
|
5
6
|
|
|
6
7
|
from nlbone.container import Container
|
|
7
8
|
from nlbone.interfaces.api.additional_filed.field_registry import FieldRule, ResourceRegistry
|
|
8
9
|
|
|
9
10
|
|
|
11
|
+
async def assemble_response_async(
|
|
12
|
+
obj: Any,
|
|
13
|
+
reg: ResourceRegistry,
|
|
14
|
+
selected_rules: Dict[str, FieldRule],
|
|
15
|
+
session: AsyncSession,
|
|
16
|
+
base_schema: type[BaseModel] | None,
|
|
17
|
+
scope_map: dict[str, set[str]] = None,
|
|
18
|
+
**kwargs,
|
|
19
|
+
) -> Dict[str, Any]:
|
|
20
|
+
"""
|
|
21
|
+
Async version of assemble_response.
|
|
22
|
+
Awaits loaders if they are coroutines.
|
|
23
|
+
"""
|
|
24
|
+
base = {f: getattr(obj, f, None) for f in reg.default_fields - set(reg.rules.keys())}
|
|
25
|
+
if base_schema:
|
|
26
|
+
base = base_schema.model_validate(base).model_dump()
|
|
27
|
+
|
|
28
|
+
ctx = {
|
|
29
|
+
"file_service": Container.afiles_service(),
|
|
30
|
+
"entity": obj,
|
|
31
|
+
"db": session,
|
|
32
|
+
"pricing_service": Container.async_pricing_service(),
|
|
33
|
+
**kwargs,
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
roots = {name.split(".", 1)[0] for name in selected_rules.keys()}
|
|
37
|
+
|
|
38
|
+
for root in roots:
|
|
39
|
+
rule = reg.rules.get(root)
|
|
40
|
+
if not rule:
|
|
41
|
+
continue
|
|
42
|
+
|
|
43
|
+
if rule.loader:
|
|
44
|
+
dependencies = ctx | {"scope": scope_map.get(root, {""})} if scope_map else ctx
|
|
45
|
+
|
|
46
|
+
result = inject_dependencies(rule.loader, dependencies=dependencies)
|
|
47
|
+
|
|
48
|
+
if inspect.iscoroutine(result):
|
|
49
|
+
value = await result
|
|
50
|
+
else:
|
|
51
|
+
value = result
|
|
52
|
+
else:
|
|
53
|
+
value = _get_nested_attr(obj, root)
|
|
54
|
+
|
|
55
|
+
_put_nested_key(base, root, value)
|
|
56
|
+
|
|
57
|
+
return base
|
|
58
|
+
|
|
59
|
+
|
|
10
60
|
def assemble_response(
|
|
11
61
|
obj: Any,
|
|
12
62
|
reg: ResourceRegistry,
|
{nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/interfaces/api/additional_filed/field_registry.py
RENAMED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
from dataclasses import dataclass, field
|
|
2
2
|
from enum import Enum
|
|
3
|
-
from typing import Any, Callable, Dict, Iterable, Optional, Set, Tuple, Type
|
|
3
|
+
from typing import Any, Awaitable, Callable, Dict, Iterable, Optional, Set, Tuple, Type
|
|
4
4
|
|
|
5
5
|
from pydantic import BaseModel
|
|
6
6
|
|
|
7
7
|
PermissionChecker = Callable[[Any, str], bool]
|
|
8
|
+
AsyncPermissionChecker = Callable[[str], Awaitable[bool]]
|
|
8
9
|
Loader = Callable
|
|
9
10
|
|
|
10
11
|
|
|
@@ -2,11 +2,15 @@ from collections import defaultdict
|
|
|
2
2
|
from typing import Dict, List, Set, Tuple
|
|
3
3
|
|
|
4
4
|
from nlbone.interfaces.api.additional_filed.field_registry import (
|
|
5
|
+
AsyncPermissionChecker,
|
|
5
6
|
DefaultsMergeMode,
|
|
6
7
|
FieldRule,
|
|
7
8
|
PermissionChecker,
|
|
8
9
|
ResourceRegistry,
|
|
9
10
|
)
|
|
11
|
+
from nlbone.interfaces.api.dependencies.async_auth import (
|
|
12
|
+
client_or_user_has_access_func as async_client_or_user_has_access_func,
|
|
13
|
+
)
|
|
10
14
|
from nlbone.interfaces.api.dependencies.auth import client_or_user_has_access_func
|
|
11
15
|
from nlbone.interfaces.api.exceptions import BadRequestException, InternalServerException
|
|
12
16
|
|
|
@@ -36,6 +40,81 @@ class AdditionalFieldsRequest:
|
|
|
36
40
|
return [x.strip() for x in s.split(",") if x.strip()]
|
|
37
41
|
|
|
38
42
|
|
|
43
|
+
async def resolve_requested_fields_async(
|
|
44
|
+
reg: ResourceRegistry,
|
|
45
|
+
additional_fields: AdditionalFieldsRequest = None,
|
|
46
|
+
can: AsyncPermissionChecker = None,
|
|
47
|
+
mode: DefaultsMergeMode = DefaultsMergeMode.UNION,
|
|
48
|
+
) -> Tuple[Set[str], Dict[str, FieldRule]]:
|
|
49
|
+
if not additional_fields:
|
|
50
|
+
additional_fields = AdditionalFieldsRequest()
|
|
51
|
+
if not can:
|
|
52
|
+
can = async_client_or_user_has_access_func
|
|
53
|
+
|
|
54
|
+
reg.finalize_defaults(mode=mode)
|
|
55
|
+
|
|
56
|
+
expanded_bundles = _expand_bundles(reg, set(additional_fields.bundles))
|
|
57
|
+
requested = set(reg.default_fields) | set(additional_fields.fields) | expanded_bundles
|
|
58
|
+
|
|
59
|
+
# Validation
|
|
60
|
+
unknown = {f for f in requested if (f not in reg.default_fields and f not in reg.rules)}
|
|
61
|
+
if unknown:
|
|
62
|
+
raise BadRequestException(f"unknown_fields: {sorted(unknown)}")
|
|
63
|
+
|
|
64
|
+
selected_rules: Dict[str, FieldRule] = {}
|
|
65
|
+
|
|
66
|
+
for f in requested:
|
|
67
|
+
rule = reg.rules.get(f)
|
|
68
|
+
|
|
69
|
+
if f in reg.default_fields and f not in reg.rules:
|
|
70
|
+
continue
|
|
71
|
+
|
|
72
|
+
if not rule:
|
|
73
|
+
continue
|
|
74
|
+
|
|
75
|
+
# Check Permission
|
|
76
|
+
if rule.permission:
|
|
77
|
+
try:
|
|
78
|
+
if not await can(rule.permission):
|
|
79
|
+
continue
|
|
80
|
+
except Exception:
|
|
81
|
+
continue
|
|
82
|
+
|
|
83
|
+
is_explicit = f in additional_fields.fields
|
|
84
|
+
if not rule.default and not is_explicit:
|
|
85
|
+
continue
|
|
86
|
+
|
|
87
|
+
selected_rules[f] = rule
|
|
88
|
+
|
|
89
|
+
# Dependencies
|
|
90
|
+
final_set = set(requested)
|
|
91
|
+
|
|
92
|
+
def add_deps_recursive(name: str):
|
|
93
|
+
_rule = reg.rules.get(name)
|
|
94
|
+
if not _rule or not _rule.deps:
|
|
95
|
+
return
|
|
96
|
+
for d in _rule.deps:
|
|
97
|
+
if d not in final_set:
|
|
98
|
+
final_set.add(d)
|
|
99
|
+
add_deps_recursive(d)
|
|
100
|
+
|
|
101
|
+
for field_with_rule in list(selected_rules.keys()):
|
|
102
|
+
add_deps_recursive(field_with_rule)
|
|
103
|
+
|
|
104
|
+
parents = {f.split(".", 1)[0] for f in final_set if "." in f}
|
|
105
|
+
for p in parents:
|
|
106
|
+
if p in reg.rules:
|
|
107
|
+
final_set.add(p)
|
|
108
|
+
if p not in selected_rules:
|
|
109
|
+
selected_rules[p] = reg.rules[p]
|
|
110
|
+
|
|
111
|
+
missing_deps = (final_set - set(reg.default_fields)) - set(reg.rules.keys())
|
|
112
|
+
if missing_deps:
|
|
113
|
+
raise InternalServerException(f"registry_missing_rules_for: {sorted(missing_deps)}")
|
|
114
|
+
|
|
115
|
+
return final_set, selected_rules
|
|
116
|
+
|
|
117
|
+
|
|
39
118
|
def resolve_requested_fields(
|
|
40
119
|
reg: ResourceRegistry,
|
|
41
120
|
additional_fields: AdditionalFieldsRequest = None,
|
|
@@ -92,7 +92,7 @@ def client_or_user_has_access(*, permissions=None, client_permissions=None):
|
|
|
92
92
|
return decorator
|
|
93
93
|
|
|
94
94
|
|
|
95
|
-
|
|
95
|
+
def is_permitted_user(permissions=None):
|
|
96
96
|
async def check_permissions():
|
|
97
97
|
try:
|
|
98
98
|
if bypass_authz():
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/http_clients/pricing/async_pricing_service.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{nlbone-0.11.0 → nlbone-0.11.1}/src/nlbone/adapters/http_clients/uploadchi/uploadchi_async.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|