Skip to content

Commit 0fb33dc

Browse files
authored
Merge pull request #1945 from kili-technology/feature/lab-3849-aa-sdk-user-when-i-request-assets-it-changes-default-field
feat: asset default fields depend on project workflow version
2 parents 144be55 + 28661ee commit 0fb33dc

File tree

9 files changed

+227
-173
lines changed

9 files changed

+227
-173
lines changed

src/kili/domain/asset/asset.py

Lines changed: 50 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
"""Asset domain."""
22

33
from dataclasses import dataclass
4-
from typing import TYPE_CHECKING, Literal, NewType, Optional
4+
from typing import TYPE_CHECKING, Literal, NewType, Optional, TypedDict
55

6+
from kili.domain.project import WorkflowVersion
67
from kili.domain.types import ListOrTuple
78

89
if TYPE_CHECKING:
@@ -63,3 +64,51 @@ class AssetFilters:
6364
status_in: Optional[ListOrTuple[AssetStatus]] = None
6465
step_id_in: Optional[ListOrTuple[str]] = None
6566
step_status_in: Optional[ListOrTuple[StatusInStep]] = None
67+
68+
69+
class AssetWorkflowFilters(TypedDict):
70+
"""Asset filters relative to worklow."""
71+
72+
skipped: Optional[bool]
73+
status_in: Optional[ListOrTuple[AssetStatus]]
74+
step_name_in: Optional[ListOrTuple[str]]
75+
step_status_in: Optional[ListOrTuple[StatusInStep]]
76+
77+
78+
def get_asset_default_fields(
79+
project_workflow_version: WorkflowVersion,
80+
) -> ListOrTuple[str]:
81+
"""Get asset default fields for depending on the project workflow version."""
82+
if project_workflow_version == "V1":
83+
return (
84+
"content",
85+
"createdAt",
86+
"externalId",
87+
"id",
88+
"isHoneypot",
89+
"jsonMetadata",
90+
"labels.author.id",
91+
"labels.author.email",
92+
"labels.createdAt",
93+
"labels.id",
94+
"labels.jsonResponse",
95+
"skipped",
96+
"status",
97+
)
98+
99+
return (
100+
"content",
101+
"createdAt",
102+
"externalId",
103+
"id",
104+
"isHoneypot",
105+
"jsonMetadata",
106+
"labels.author.id",
107+
"labels.author.email",
108+
"labels.createdAt",
109+
"labels.id",
110+
"labels.jsonResponse",
111+
"skipped",
112+
"currentStep.name",
113+
"currentStep.status",
114+
)

src/kili/domain/asset/helpers.py

Lines changed: 40 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,11 @@
11
"""Helpers for the asset domain."""
22

3+
import warnings
34
from typing import Optional
45

56
from kili.domain.asset import AssetExternalId, AssetId
6-
from kili.domain.project import ProjectId
7+
from kili.domain.asset.asset import AssetWorkflowFilters
8+
from kili.domain.project import ProjectId, WorkflowVersion
79
from kili.domain.types import ListOrTuple
810
from kili.exceptions import IncompatibleArgumentsError, MissingArgumentError
911

@@ -25,3 +27,40 @@ def check_asset_identifier_arguments(
2527
raise MissingArgumentError(
2628
"Either provide asset IDs or project ID with asset external IDs."
2729
)
30+
31+
32+
def check_asset_workflow_arguments(
33+
project_workflow_version: WorkflowVersion, asset_workflow_filters: AssetWorkflowFilters
34+
) -> None:
35+
"""Check asset workflow parameters relative to the project workflow version."""
36+
step_name_in = asset_workflow_filters.get("step_name_in")
37+
step_status_in = asset_workflow_filters.get("step_status_in")
38+
status_in = asset_workflow_filters.get("status_in")
39+
skipped = asset_workflow_filters.get("skipped")
40+
41+
if project_workflow_version == "V2":
42+
if step_status_in is not None and status_in is not None:
43+
raise ValueError(
44+
"Filters step_status_in and status_in both given : only use filter step_status_in for this project."
45+
)
46+
if step_name_in is not None and status_in is not None:
47+
raise ValueError(
48+
"Filters step_name_in and status_in both given : use filter step_status_in instead of status_in for this project." # pylint: disable=line-too-long
49+
)
50+
if status_in is not None:
51+
warnings.warn(
52+
"Filter status_in given : use filters step_status_in and step_name_in instead for this project.",
53+
stacklevel=1,
54+
)
55+
if skipped is not None:
56+
warnings.warn(
57+
"Filter skipped given : only use filter step_status_in with the SKIPPED step status instead for this project", # pylint: disable=line-too-long
58+
stacklevel=1,
59+
)
60+
return
61+
62+
# project workflow v1
63+
if step_name_in is not None or step_status_in is not None:
64+
raise ValueError(
65+
"Filters step_name_in and/or step_status_in given : use filter status_in for this project."
66+
)

src/kili/domain/project.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
InputType = Literal[
1616
"IMAGE", "GEOSPATIAL", "PDF", "TEXT", "VIDEO", "LLM_RLHF", "LLM_INSTR_FOLLOWING", "LLM_STATIC"
1717
]
18+
WorkflowVersion = Literal["V1", "V2"]
1819

1920

2021
@dataclass(frozen=True)

src/kili/llm/presentation/client/llm.py

Lines changed: 20 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -2,19 +2,14 @@
22

33
# pylint: disable=too-many-lines
44
import warnings
5-
from typing import (
6-
Dict,
7-
List,
8-
Optional,
9-
Union,
10-
cast,
11-
)
5+
from typing import Dict, List, Optional, Union, cast
126

137
from kili_formats.types import ChatItem, ChatItemRole, Conversation
148

159
from kili.adapters.kili_api_gateway.kili_api_gateway import KiliAPIGateway
1610
from kili.domain.asset import AssetExternalId, AssetFilters, AssetId, AssetStatus
1711
from kili.domain.asset.asset import StatusInStep
12+
from kili.domain.asset.helpers import check_asset_workflow_arguments
1813
from kili.domain.label import LabelType
1914
from kili.domain.llm import (
2015
AzureOpenAICredentials,
@@ -31,7 +26,9 @@
3126
)
3227
from kili.domain.project import ProjectId
3328
from kili.llm.services.export import export
34-
from kili.presentation.client.helpers.filter_conversion import convert_step_in_to_step_id_in_filter
29+
from kili.presentation.client.helpers.filter_conversion import (
30+
extract_step_ids_from_project_steps,
31+
)
3532
from kili.services.export.exceptions import NoCompatibleJobError
3633
from kili.use_cases.asset.utils import AssetUseCasesUtils
3734
from kili.use_cases.project.project import ProjectUseCases
@@ -128,15 +125,26 @@ def export(
128125

129126
if status_in is not None or step_name_in is not None or step_status_in is not None:
130127
project_use_cases = ProjectUseCases(self.kili_api_gateway)
131-
step_id_in = convert_step_in_to_step_id_in_filter(
132-
project_steps=project_use_cases.get_project_steps(project_id),
133-
asset_filter_kwargs={
128+
(
129+
project_steps,
130+
project_workflow_version,
131+
) = project_use_cases.get_project_steps_and_version(project_id)
132+
check_asset_workflow_arguments(
133+
project_workflow_version=project_workflow_version,
134+
asset_workflow_filters={
135+
"skipped": None,
136+
"status_in": status_in,
134137
"step_name_in": step_name_in,
135138
"step_status_in": step_status_in,
136-
"status_in": status_in,
137139
},
138140
)
139141

142+
if project_workflow_version == "V2" and step_name_in is not None:
143+
step_id_in = extract_step_ids_from_project_steps(
144+
project_steps=project_steps,
145+
step_name_in=step_name_in,
146+
)
147+
140148
asset_filter = AssetFilters(
141149
project_id=ProjectId(project_id),
142150
asset_id_in=resolved_asset_ids,

src/kili/presentation/client/asset.py

Lines changed: 50 additions & 67 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,9 @@
2323
AssetId,
2424
AssetStatus,
2525
StatusInStep,
26+
get_asset_default_fields,
2627
)
28+
from kili.domain.asset.helpers import check_asset_workflow_arguments
2729
from kili.domain.issue import IssueStatus, IssueType
2830
from kili.domain.label import LabelType
2931
from kili.domain.project import ProjectId
@@ -32,7 +34,7 @@
3234
disable_tqdm_if_as_generator,
3335
)
3436
from kili.presentation.client.helpers.filter_conversion import (
35-
convert_step_in_to_step_id_in_filter,
37+
extract_step_ids_from_project_steps,
3638
)
3739
from kili.use_cases.asset import AssetUseCases
3840
from kili.use_cases.project.project import ProjectUseCases
@@ -55,21 +57,7 @@ def assets(
5557
project_id: str,
5658
asset_id: Optional[str] = None,
5759
skip: int = 0,
58-
fields: ListOrTuple[str] = (
59-
"content",
60-
"createdAt",
61-
"externalId",
62-
"id",
63-
"isHoneypot",
64-
"jsonMetadata",
65-
"labels.author.id",
66-
"labels.author.email",
67-
"labels.createdAt",
68-
"labels.id",
69-
"labels.jsonResponse",
70-
"skipped",
71-
"status",
72-
),
60+
fields: Optional[ListOrTuple[str]] = None,
7361
asset_id_in: Optional[List[str]] = None,
7462
asset_id_not_in: Optional[List[str]] = None,
7563
consensus_mark_gt: Optional[float] = None,
@@ -135,21 +123,7 @@ def assets(
135123
project_id: str,
136124
asset_id: Optional[str] = None,
137125
skip: int = 0,
138-
fields: ListOrTuple[str] = (
139-
"content",
140-
"createdAt",
141-
"externalId",
142-
"id",
143-
"isHoneypot",
144-
"jsonMetadata",
145-
"labels.author.id",
146-
"labels.author.email",
147-
"labels.createdAt",
148-
"labels.id",
149-
"labels.jsonResponse",
150-
"skipped",
151-
"status",
152-
),
126+
fields: Optional[ListOrTuple[str]] = None,
153127
asset_id_in: Optional[List[str]] = None,
154128
asset_id_not_in: Optional[List[str]] = None,
155129
consensus_mark_gt: Optional[float] = None,
@@ -215,21 +189,7 @@ def assets(
215189
project_id: str,
216190
asset_id: Optional[str] = None,
217191
skip: int = 0,
218-
fields: ListOrTuple[str] = (
219-
"content",
220-
"createdAt",
221-
"externalId",
222-
"id",
223-
"isHoneypot",
224-
"jsonMetadata",
225-
"labels.author.id",
226-
"labels.author.email",
227-
"labels.createdAt",
228-
"labels.id",
229-
"labels.jsonResponse",
230-
"skipped",
231-
"status",
232-
),
192+
fields: Optional[ListOrTuple[str]] = None,
233193
asset_id_in: Optional[List[str]] = None,
234194
asset_id_not_in: Optional[List[str]] = None,
235195
consensus_mark_gt: Optional[float] = None,
@@ -453,31 +413,44 @@ def assets(
453413

454414
disable_tqdm = disable_tqdm_if_as_generator(as_generator, disable_tqdm)
455415

416+
project_use_cases = ProjectUseCases(self.kili_api_gateway)
417+
project_steps, project_workflow_version = project_use_cases.get_project_steps_and_version(
418+
project_id
419+
)
420+
if fields is None:
421+
fields = get_asset_default_fields(project_workflow_version=project_workflow_version)
422+
elif project_workflow_version == "V1":
423+
for invalid_field in filter(lambda f: f.startswith("currentStep."), fields):
424+
warnings.warn(
425+
f"Field {invalid_field} requested : request 'status' field instead for this project",
426+
stacklevel=1,
427+
)
428+
elif "status" in fields:
429+
warnings.warn(
430+
"Field status requested : request 'currentStep.name' and 'currentStep.status' fields instead for this project",
431+
stacklevel=1,
432+
)
433+
456434
step_id_in = None
457435
if (
458436
step_name_in is not None
459437
or step_status_in is not None
460438
or status_in is not None
461439
or skipped is not None
462440
):
463-
project_use_cases = ProjectUseCases(self.kili_api_gateway)
464-
project_steps = project_use_cases.get_project_steps(project_id)
465-
466-
if step_name_in is not None or step_status_in is not None or status_in is not None:
467-
step_id_in = convert_step_in_to_step_id_in_filter(
441+
check_asset_workflow_arguments(
442+
project_workflow_version=project_workflow_version,
443+
asset_workflow_filters={
444+
"skipped": skipped,
445+
"status_in": status_in,
446+
"step_name_in": step_name_in,
447+
"step_status_in": step_status_in,
448+
},
449+
)
450+
if project_workflow_version == "V2" and step_name_in is not None:
451+
step_id_in = extract_step_ids_from_project_steps(
468452
project_steps=project_steps,
469-
fields=fields,
470-
asset_filter_kwargs={
471-
"step_name_in": step_name_in,
472-
"step_status_in": step_status_in,
473-
"status_in": status_in,
474-
"skipped": skipped,
475-
},
476-
)
477-
elif skipped is not None and len(project_steps) != 0:
478-
warnings.warn(
479-
"Filter skipped given : only use filter step_status_in with the SKIPPED step status instead for this project",
480-
stacklevel=1,
453+
step_name_in=step_name_in,
481454
)
482455

483456
asset_use_cases = AssetUseCases(self.kili_api_gateway)
@@ -722,18 +695,28 @@ def count_assets(
722695
)
723696

724697
step_id_in = None
725-
726698
if status_in is not None or step_name_in is not None or step_status_in is not None:
727699
project_use_cases = ProjectUseCases(self.kili_api_gateway)
728-
step_id_in = convert_step_in_to_step_id_in_filter(
729-
project_steps=project_use_cases.get_project_steps(project_id),
730-
asset_filter_kwargs={
700+
(
701+
project_steps,
702+
project_workflow_version,
703+
) = project_use_cases.get_project_steps_and_version(project_id)
704+
check_asset_workflow_arguments(
705+
project_workflow_version=project_workflow_version,
706+
asset_workflow_filters={
707+
"skipped": skipped,
731708
"step_name_in": step_name_in,
732709
"step_status_in": step_status_in,
733710
"status_in": status_in,
734711
},
735712
)
736713

714+
if project_workflow_version == "V2" and step_name_in is not None:
715+
step_id_in = extract_step_ids_from_project_steps(
716+
project_steps=project_steps,
717+
step_name_in=step_name_in,
718+
)
719+
737720
filters = AssetFilters(
738721
project_id=ProjectId(project_id),
739722
asset_id=AssetId(asset_id) if asset_id else None,

0 commit comments

Comments
 (0)