annofabcli 1.111.2__py3-none-any.whl → 1.113.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.
- annofabcli/__main__.py +1 -2
- annofabcli/annotation/annotation_query.py +10 -10
- annofabcli/annotation/change_annotation_attributes.py +10 -10
- annofabcli/annotation/change_annotation_attributes_per_annotation.py +4 -5
- annofabcli/annotation/change_annotation_properties.py +14 -14
- annofabcli/annotation/copy_annotation.py +6 -6
- annofabcli/annotation/create_classification_annotation.py +7 -7
- annofabcli/annotation/delete_annotation.py +9 -9
- annofabcli/annotation/download_annotation_zip.py +1 -3
- annofabcli/annotation/dump_annotation.py +8 -8
- annofabcli/annotation/import_annotation.py +13 -13
- annofabcli/annotation/list_annotation.py +9 -9
- annofabcli/annotation/list_annotation_count.py +2 -3
- annofabcli/annotation/merge_segmentation.py +6 -6
- annofabcli/annotation/remove_segmentation_overlap.py +5 -5
- annofabcli/annotation/restore_annotation.py +7 -7
- annofabcli/annotation/subcommand_annotation.py +1 -2
- annofabcli/annotation_specs/add_attribute_restriction.py +4 -5
- annofabcli/annotation_specs/attribute_restriction.py +8 -8
- annofabcli/annotation_specs/export_annotation_specs.py +4 -5
- annofabcli/annotation_specs/get_annotation_specs_with_attribute_id_replaced.py +3 -4
- annofabcli/annotation_specs/get_annotation_specs_with_choice_id_replaced.py +3 -4
- annofabcli/annotation_specs/get_annotation_specs_with_label_id_replaced.py +3 -4
- annofabcli/annotation_specs/list_annotation_specs_attribute.py +9 -10
- annofabcli/annotation_specs/list_annotation_specs_choice.py +9 -10
- annofabcli/annotation_specs/list_annotation_specs_history.py +3 -3
- annofabcli/annotation_specs/list_annotation_specs_label.py +8 -9
- annofabcli/annotation_specs/list_annotation_specs_label_attribute.py +10 -11
- annofabcli/annotation_specs/list_attribute_restriction.py +2 -4
- annofabcli/annotation_specs/list_label_color.py +2 -3
- annofabcli/annotation_specs/put_label_color.py +3 -4
- annofabcli/annotation_specs/subcommand_annotation_specs.py +1 -3
- annofabcli/annotation_zip/list_annotation_3d_bounding_box.py +365 -0
- annofabcli/annotation_zip/list_annotation_bounding_box_2d.py +37 -38
- annofabcli/annotation_zip/list_polygon_annotation.py +390 -0
- annofabcli/annotation_zip/list_polyline_annotation.py +402 -0
- annofabcli/annotation_zip/list_range_annotation.py +25 -15
- annofabcli/annotation_zip/list_single_point_annotation.py +25 -34
- annofabcli/annotation_zip/subcommand_annotation_zip.py +7 -2
- annofabcli/annotation_zip/validate_annotation.py +8 -7
- annofabcli/comment/delete_comment.py +4 -6
- annofabcli/comment/download_comment_json.py +4 -6
- annofabcli/comment/list_all_comment.py +5 -6
- annofabcli/comment/list_comment.py +3 -4
- annofabcli/comment/put_comment.py +9 -10
- annofabcli/comment/put_comment_simply.py +5 -6
- annofabcli/comment/put_inspection_comment.py +1 -3
- annofabcli/comment/put_inspection_comment_simply.py +1 -3
- annofabcli/comment/put_onhold_comment.py +1 -3
- annofabcli/comment/put_onhold_comment_simply.py +1 -3
- annofabcli/comment/subcommand_comment.py +1 -3
- annofabcli/common/bokeh.py +4 -4
- annofabcli/common/cli.py +18 -17
- annofabcli/common/download.py +28 -29
- annofabcli/common/facade.py +37 -38
- annofabcli/common/image.py +14 -14
- annofabcli/common/utils.py +8 -8
- annofabcli/common/visualize.py +13 -13
- annofabcli/experimental/list_out_of_range_annotation_for_movie.py +3 -4
- annofabcli/experimental/subcommand_experimental.py +1 -3
- annofabcli/filesystem/draw_annotation.py +27 -27
- annofabcli/filesystem/filter_annotation.py +9 -10
- annofabcli/filesystem/mask_user_info.py +15 -15
- annofabcli/filesystem/merge_annotation.py +9 -9
- annofabcli/filesystem/subcommand_filesystem.py +1 -3
- annofabcli/input_data/copy_input_data.py +8 -9
- annofabcli/input_data/delete_input_data.py +3 -3
- annofabcli/input_data/delete_metadata_key_of_input_data.py +3 -5
- annofabcli/input_data/download_input_data_json.py +4 -6
- annofabcli/input_data/list_all_input_data.py +9 -9
- annofabcli/input_data/list_all_input_data_merged_task.py +5 -5
- annofabcli/input_data/list_input_data.py +5 -5
- annofabcli/input_data/put_input_data.py +6 -6
- annofabcli/input_data/put_input_data_with_zip.py +3 -4
- annofabcli/input_data/subcommand_input_data.py +1 -3
- annofabcli/input_data/update_input_data.py +6 -8
- annofabcli/input_data/update_metadata_of_input_data.py +3 -5
- annofabcli/instruction/copy_instruction.py +5 -6
- annofabcli/instruction/download_instruction.py +5 -6
- annofabcli/instruction/list_instruction_history.py +3 -3
- annofabcli/instruction/subcommand_instruction.py +1 -3
- annofabcli/instruction/upload_instruction.py +3 -4
- annofabcli/job/delete_job.py +2 -3
- annofabcli/job/list_job.py +5 -5
- annofabcli/job/list_last_job.py +4 -4
- annofabcli/job/subcommand_job.py +1 -3
- annofabcli/job/wait_job.py +4 -5
- annofabcli/my_account/get_my_account.py +2 -3
- annofabcli/my_account/subcommand_my_account.py +1 -3
- annofabcli/organization/list_organization.py +2 -3
- annofabcli/organization/subcommand_organization.py +1 -3
- annofabcli/organization_member/change_organization_member.py +3 -4
- annofabcli/organization_member/delete_organization_member.py +3 -4
- annofabcli/organization_member/invite_organization_member.py +1 -3
- annofabcli/organization_member/list_organization_member.py +3 -3
- annofabcli/organization_member/subcommand_organization_member.py +1 -3
- annofabcli/project/change_organization_of_project.py +4 -4
- annofabcli/project/change_project_status.py +4 -4
- annofabcli/project/copy_project.py +5 -5
- annofabcli/project/create_project.py +8 -8
- annofabcli/project/diff_projects.py +4 -5
- annofabcli/project/list_project.py +5 -5
- annofabcli/project/put_project.py +2 -3
- annofabcli/project/subcommand_project.py +1 -2
- annofabcli/project/update_configuration.py +4 -4
- annofabcli/project/update_project.py +6 -8
- annofabcli/project_member/change_project_members.py +8 -8
- annofabcli/project_member/copy_project_members.py +4 -4
- annofabcli/project_member/drop_project_members.py +2 -3
- annofabcli/project_member/invite_project_members.py +1 -3
- annofabcli/project_member/list_users.py +2 -3
- annofabcli/project_member/put_project_members.py +6 -6
- annofabcli/project_member/subcommand_project_member.py +1 -3
- annofabcli/stat_visualization/mask_visualization_dir.py +8 -9
- annofabcli/stat_visualization/merge_visualization_dir.py +6 -7
- annofabcli/stat_visualization/subcommand_stat_visualization.py +1 -2
- annofabcli/stat_visualization/summarize_whole_performance_csv.py +1 -2
- annofabcli/stat_visualization/write_graph.py +2 -3
- annofabcli/stat_visualization/write_performance_rating_csv.py +20 -27
- annofabcli/statistics/histogram.py +5 -6
- annofabcli/statistics/linegraph.py +13 -14
- annofabcli/statistics/list_annotation_area.py +38 -13
- annofabcli/statistics/list_annotation_attribute.py +9 -10
- annofabcli/statistics/list_annotation_attribute_filled_count.py +30 -31
- annofabcli/statistics/list_annotation_count.py +57 -58
- annofabcli/statistics/list_annotation_duration.py +33 -34
- annofabcli/statistics/list_video_duration.py +4 -5
- annofabcli/statistics/list_worktime.py +4 -4
- annofabcli/statistics/scatter.py +9 -8
- annofabcli/statistics/subcommand_statistics.py +1 -4
- annofabcli/statistics/summarize_task_count.py +4 -6
- annofabcli/statistics/summarize_task_count_by_task_id_group.py +2 -4
- annofabcli/statistics/summarize_task_count_by_user.py +1 -3
- annofabcli/statistics/visualization/dataframe/annotation_count.py +5 -4
- annofabcli/statistics/visualization/dataframe/annotation_duration.py +2 -3
- annofabcli/statistics/visualization/dataframe/cumulative_productivity.py +15 -17
- annofabcli/statistics/visualization/dataframe/productivity_per_date.py +17 -19
- annofabcli/statistics/visualization/dataframe/project_performance.py +3 -12
- annofabcli/statistics/visualization/dataframe/task.py +11 -12
- annofabcli/statistics/visualization/dataframe/task_worktime_by_phase_user.py +9 -10
- annofabcli/statistics/visualization/dataframe/user_performance.py +21 -19
- annofabcli/statistics/visualization/dataframe/whole_performance.py +3 -4
- annofabcli/statistics/visualization/dataframe/whole_productivity_per_date.py +12 -14
- annofabcli/statistics/visualization/dataframe/worktime_per_date.py +11 -13
- annofabcli/statistics/visualization/filtering_query.py +7 -7
- annofabcli/statistics/visualization/project_dir.py +27 -14
- annofabcli/statistics/visualize_annotation_count.py +22 -23
- annofabcli/statistics/visualize_annotation_duration.py +21 -22
- annofabcli/statistics/visualize_statistics.py +36 -33
- annofabcli/statistics/visualize_video_duration.py +18 -20
- annofabcli/supplementary/delete_supplementary_data.py +5 -5
- annofabcli/supplementary/list_supplementary_data.py +4 -4
- annofabcli/supplementary/put_supplementary_data.py +9 -9
- annofabcli/supplementary/subcommand_supplementary.py +1 -3
- annofabcli/task/cancel_acceptance.py +16 -17
- annofabcli/task/change_operator.py +10 -12
- annofabcli/task/change_status_to_break.py +7 -9
- annofabcli/task/change_status_to_on_hold.py +10 -12
- annofabcli/task/complete_tasks.py +17 -18
- annofabcli/task/copy_tasks.py +3 -5
- annofabcli/task/delete_metadata_key_of_task.py +4 -6
- annofabcli/task/delete_tasks.py +7 -7
- annofabcli/task/download_task_json.py +4 -6
- annofabcli/task/list_all_tasks.py +8 -8
- annofabcli/task/list_all_tasks_added_task_history.py +14 -13
- annofabcli/task/list_tasks.py +7 -7
- annofabcli/task/list_tasks_added_task_history.py +10 -10
- annofabcli/task/put_tasks.py +5 -6
- annofabcli/task/put_tasks_by_count.py +2 -3
- annofabcli/task/reject_tasks.py +18 -20
- annofabcli/task/subcommand_task.py +1 -3
- annofabcli/task/update_metadata_of_task.py +5 -6
- annofabcli/task_history/download_task_history_json.py +4 -6
- annofabcli/task_history/list_all_task_history.py +6 -7
- annofabcli/task_history/list_task_history.py +4 -5
- annofabcli/task_history/subcommand_task_history.py +1 -3
- annofabcli/task_history_event/download_task_history_event_json.py +4 -6
- annofabcli/task_history_event/list_all_task_history_event.py +7 -7
- annofabcli/task_history_event/list_worktime.py +17 -16
- annofabcli/task_history_event/subcommand_task_history_event.py +1 -2
- {annofabcli-1.111.2.dist-info → annofabcli-1.113.0.dist-info}/METADATA +9 -15
- annofabcli-1.113.0.dist-info/RECORD +231 -0
- {annofabcli-1.111.2.dist-info → annofabcli-1.113.0.dist-info}/WHEEL +1 -1
- annofabcli-1.111.2.dist-info/RECORD +0 -228
- {annofabcli-1.111.2.dist-info → annofabcli-1.113.0.dist-info}/entry_points.txt +0 -0
- {annofabcli-1.111.2.dist-info → annofabcli-1.113.0.dist-info}/licenses/LICENSE +0 -0
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
"""サブコマンド annotation_zip"""
|
|
2
2
|
|
|
3
3
|
import argparse
|
|
4
|
-
from typing import Optional
|
|
5
4
|
|
|
6
5
|
import annofabcli
|
|
6
|
+
from annofabcli.annotation_zip.list_annotation_3d_bounding_box import add_parser as add_parser_list_annotation_3d_bounding_box
|
|
7
7
|
from annofabcli.annotation_zip.list_annotation_bounding_box_2d import add_parser as add_parser_list_annotation_bounding_box_2d
|
|
8
|
+
from annofabcli.annotation_zip.list_polygon_annotation import add_parser as add_parser_list_polygon_annotation
|
|
9
|
+
from annofabcli.annotation_zip.list_polyline_annotation import add_parser as add_parser_list_polyline_annotation
|
|
8
10
|
from annofabcli.annotation_zip.list_range_annotation import add_parser as add_parser_list_range_annotation
|
|
9
11
|
from annofabcli.annotation_zip.list_single_point_annotation import add_parser as add_parser_list_single_point_annotation
|
|
10
12
|
|
|
@@ -18,14 +20,17 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
18
20
|
subparsers = parser.add_subparsers(dest="subcommand_name")
|
|
19
21
|
|
|
20
22
|
# サブコマンドの定義
|
|
23
|
+
add_parser_list_annotation_3d_bounding_box(subparsers)
|
|
21
24
|
add_parser_list_annotation_bounding_box_2d(subparsers)
|
|
25
|
+
add_parser_list_polygon_annotation(subparsers)
|
|
26
|
+
add_parser_list_polyline_annotation(subparsers)
|
|
22
27
|
add_parser_list_range_annotation(subparsers)
|
|
23
28
|
add_parser_list_single_point_annotation(subparsers)
|
|
24
29
|
# 作成中のためコメントアウト
|
|
25
30
|
# add_parser_validate_annotation(subparsers)
|
|
26
31
|
|
|
27
32
|
|
|
28
|
-
def add_parser(subparsers:
|
|
33
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
29
34
|
"""
|
|
30
35
|
annotation_zipサブコマンドを追加する。
|
|
31
36
|
Args:
|
|
@@ -6,9 +6,10 @@ import json
|
|
|
6
6
|
import logging
|
|
7
7
|
import sys
|
|
8
8
|
import tempfile
|
|
9
|
+
from collections.abc import Callable
|
|
9
10
|
from dataclasses import dataclass
|
|
10
11
|
from pathlib import Path
|
|
11
|
-
from typing import Any
|
|
12
|
+
from typing import Any
|
|
12
13
|
|
|
13
14
|
import annofabapi
|
|
14
15
|
import pandas
|
|
@@ -37,8 +38,8 @@ class ValidationResult:
|
|
|
37
38
|
label_name: str
|
|
38
39
|
function_name: str
|
|
39
40
|
is_valid: bool
|
|
40
|
-
error_message:
|
|
41
|
-
detail_data:
|
|
41
|
+
error_message: str | None = None
|
|
42
|
+
detail_data: dict[str, Any] | None = None
|
|
42
43
|
|
|
43
44
|
|
|
44
45
|
class ValidationFunctionLoader:
|
|
@@ -101,7 +102,7 @@ class AnnotationValidator:
|
|
|
101
102
|
service: annofabapi.Resource,
|
|
102
103
|
project_id: str,
|
|
103
104
|
validation_functions: dict[str, Callable[[dict[str, Any]], bool]],
|
|
104
|
-
task_query:
|
|
105
|
+
task_query: TaskQuery | None = None,
|
|
105
106
|
) -> None:
|
|
106
107
|
self.service = service
|
|
107
108
|
self.project_id = project_id
|
|
@@ -233,7 +234,7 @@ class ValidateAnnotation(CommandLine):
|
|
|
233
234
|
logger.info(f"読み込んだバリデーション関数: {list(validation_functions.keys())}")
|
|
234
235
|
|
|
235
236
|
# タスク検索クエリ
|
|
236
|
-
task_query:
|
|
237
|
+
task_query: TaskQuery | None = None
|
|
237
238
|
if args.task_query is not None:
|
|
238
239
|
dict_task_query = annofabcli.common.cli.get_json_from_args(args.task_query)
|
|
239
240
|
task_query = TaskQuery.from_dict(dict_task_query)
|
|
@@ -277,7 +278,7 @@ class ValidateAnnotation(CommandLine):
|
|
|
277
278
|
# サマリー表示
|
|
278
279
|
self._print_summary(results)
|
|
279
280
|
|
|
280
|
-
def _output_results(self, results: list[ValidationResult], format_type: str, output_file:
|
|
281
|
+
def _output_results(self, results: list[ValidationResult], format_type: str, output_file: Path | None) -> None:
|
|
281
282
|
"""バリデーション結果を出力する"""
|
|
282
283
|
if not results:
|
|
283
284
|
logger.info("バリデーション結果はありません。")
|
|
@@ -382,7 +383,7 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
382
383
|
parser.set_defaults(subcommand_func=main)
|
|
383
384
|
|
|
384
385
|
|
|
385
|
-
def add_parser(subparsers:
|
|
386
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
386
387
|
subcommand_name = "validate"
|
|
387
388
|
subcommand_help = "ユーザー定義のバリデーション関数でアノテーションZIPを検証します。"
|
|
388
389
|
description = "ユーザー定義のバリデーション関数でアノテーションZIPを検証します。\nバリデーション関数は 'validate_' から始まる関数名で定義してください。"
|
|
@@ -3,14 +3,12 @@ import json
|
|
|
3
3
|
import logging
|
|
4
4
|
import multiprocessing
|
|
5
5
|
import sys
|
|
6
|
-
from typing import Any
|
|
6
|
+
from typing import Any
|
|
7
7
|
|
|
8
8
|
import annofabapi
|
|
9
|
-
import annofabapi.utils
|
|
10
9
|
import requests
|
|
11
10
|
from annofabapi.models import ProjectMemberRole, TaskStatus
|
|
12
11
|
|
|
13
|
-
import annofabcli
|
|
14
12
|
import annofabcli.common.cli
|
|
15
13
|
from annofabcli.common.cli import (
|
|
16
14
|
COMMAND_LINE_ERROR_STATUS_CODE,
|
|
@@ -106,7 +104,7 @@ class DeleteCommentMain(CommandLineWithConfirm):
|
|
|
106
104
|
self,
|
|
107
105
|
task_id: str,
|
|
108
106
|
comment_ids_for_task: DeletedCommentsForTask,
|
|
109
|
-
task_index:
|
|
107
|
+
task_index: int | None = None,
|
|
110
108
|
) -> int:
|
|
111
109
|
"""
|
|
112
110
|
タスクに対してコメントを削除します。
|
|
@@ -172,7 +170,7 @@ class DeleteCommentMain(CommandLineWithConfirm):
|
|
|
172
170
|
def delete_comments_for_task_list(
|
|
173
171
|
self,
|
|
174
172
|
comment_ids_for_task_list: DeletedComments,
|
|
175
|
-
parallelism:
|
|
173
|
+
parallelism: int | None = None,
|
|
176
174
|
) -> None:
|
|
177
175
|
comments_count = sum(len(e) for e in comment_ids_for_task_list.values())
|
|
178
176
|
logger.info(f"削除対象のコメントを含むタスクの個数: {len(comment_ids_for_task_list)}, 削除対象のコメントを含む入力データ数: {comments_count}")
|
|
@@ -260,7 +258,7 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
260
258
|
parser.set_defaults(subcommand_func=main)
|
|
261
259
|
|
|
262
260
|
|
|
263
|
-
def add_parser(subparsers:
|
|
261
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
264
262
|
subcommand_name = "delete"
|
|
265
263
|
subcommand_help = "コメントを削除します。"
|
|
266
264
|
description = "コメントを削除します。\n【注意】他人の付けたコメントも削除できてしまいます。"
|
|
@@ -1,11 +1,9 @@
|
|
|
1
1
|
import argparse
|
|
2
2
|
import logging
|
|
3
3
|
from pathlib import Path
|
|
4
|
-
from typing import Optional
|
|
5
4
|
|
|
6
5
|
from annofabapi.models import ProjectMemberRole
|
|
7
6
|
|
|
8
|
-
import annofabcli
|
|
9
7
|
import annofabcli.common.cli
|
|
10
8
|
from annofabcli.common.cli import CommandLine, build_annofabapi_resource_and_login
|
|
11
9
|
from annofabcli.common.download import DownloadingFile
|
|
@@ -15,17 +13,17 @@ logger = logging.getLogger(__name__)
|
|
|
15
13
|
|
|
16
14
|
|
|
17
15
|
class DownloadingComment(CommandLine):
|
|
18
|
-
def download_comment_json(self, project_id: str, output_file: Path)
|
|
16
|
+
def download_comment_json(self, project_id: str, output_file: Path) -> None:
|
|
19
17
|
super().validate_project(project_id, [ProjectMemberRole.OWNER, ProjectMemberRole.TRAINING_DATA_USER])
|
|
20
18
|
project_title = self.facade.get_project_title(project_id)
|
|
21
|
-
logger.info(f"{project_title}
|
|
19
|
+
logger.info(f"project_id='{project_id}'のコメント全件ファイルをダウンロードします。 :: project_title='{project_title}'")
|
|
22
20
|
|
|
23
21
|
obj = DownloadingFile(self.service)
|
|
24
22
|
obj.download_comment_json(
|
|
25
23
|
project_id,
|
|
26
24
|
str(output_file),
|
|
27
25
|
)
|
|
28
|
-
logger.info(f"
|
|
26
|
+
logger.info(f"project_id='{project_id}'のコメント全件ファイルをダウンロードしました。 :: output='{output_file}', project_title='{project_title}'")
|
|
29
27
|
|
|
30
28
|
def main(self) -> None:
|
|
31
29
|
args = self.args
|
|
@@ -50,7 +48,7 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
50
48
|
parser.set_defaults(subcommand_func=main)
|
|
51
49
|
|
|
52
50
|
|
|
53
|
-
def add_parser(subparsers:
|
|
51
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
54
52
|
subcommand_name = "download"
|
|
55
53
|
subcommand_help = "コメント全件ファイルをダウンロードします。"
|
|
56
54
|
epilog = "オーナロールまたはアノテーションユーザロールを持つユーザで実行してください。"
|
|
@@ -10,13 +10,12 @@ import logging
|
|
|
10
10
|
import tempfile
|
|
11
11
|
from collections.abc import Collection
|
|
12
12
|
from pathlib import Path
|
|
13
|
-
from typing import Any
|
|
13
|
+
from typing import Any
|
|
14
14
|
|
|
15
15
|
import annofabapi
|
|
16
16
|
import pandas
|
|
17
17
|
from annofabapi.models import CommentType
|
|
18
18
|
|
|
19
|
-
import annofabcli
|
|
20
19
|
import annofabcli.common.cli
|
|
21
20
|
from annofabcli.comment.list_comment import create_empty_df_comment, create_reply_counter
|
|
22
21
|
from annofabcli.common.cli import ArgumentParser, CommandLine, build_annofabapi_resource_and_login
|
|
@@ -36,9 +35,9 @@ class ListAllCommentMain:
|
|
|
36
35
|
def get_all_comment(
|
|
37
36
|
self,
|
|
38
37
|
project_id: str,
|
|
39
|
-
comment_json:
|
|
40
|
-
task_ids:
|
|
41
|
-
comment_type:
|
|
38
|
+
comment_json: Path | None,
|
|
39
|
+
task_ids: Collection[str] | None,
|
|
40
|
+
comment_type: CommentType | None,
|
|
42
41
|
exclude_reply: bool, # noqa: FBT001
|
|
43
42
|
) -> list[dict[str, Any]]:
|
|
44
43
|
if comment_json is None:
|
|
@@ -154,7 +153,7 @@ def main(args: argparse.Namespace) -> None:
|
|
|
154
153
|
ListAllComment(service, facade, args).main()
|
|
155
154
|
|
|
156
155
|
|
|
157
|
-
def add_parser(subparsers:
|
|
156
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
158
157
|
subcommand_name = "list_all"
|
|
159
158
|
subcommand_help = "すべてのコメントの一覧を出力します。"
|
|
160
159
|
description = (
|
|
@@ -3,13 +3,12 @@ from __future__ import annotations
|
|
|
3
3
|
import argparse
|
|
4
4
|
import logging
|
|
5
5
|
from collections import Counter
|
|
6
|
-
from typing import Any
|
|
6
|
+
from typing import Any
|
|
7
7
|
|
|
8
8
|
import pandas
|
|
9
9
|
import requests
|
|
10
10
|
from annofabapi.models import Comment, CommentType
|
|
11
11
|
|
|
12
|
-
import annofabcli
|
|
13
12
|
import annofabcli.common.cli
|
|
14
13
|
from annofabcli.common.cli import ArgumentParser, CommandLine, build_annofabapi_resource_and_login
|
|
15
14
|
from annofabcli.common.enums import FormatArgument
|
|
@@ -61,7 +60,7 @@ class ListingComments(CommandLine):
|
|
|
61
60
|
c["reply_count"] = reply_counter.get(key, 0)
|
|
62
61
|
return comments
|
|
63
62
|
|
|
64
|
-
def get_comment_list(self, project_id: str, task_id_list: list[str], *, comment_type:
|
|
63
|
+
def get_comment_list(self, project_id: str, task_id_list: list[str], *, comment_type: CommentType | None, exclude_reply: bool) -> list[dict[str, Any]]:
|
|
65
64
|
all_comments: list[Comment] = []
|
|
66
65
|
|
|
67
66
|
for task_id in task_id_list:
|
|
@@ -151,7 +150,7 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
151
150
|
parser.set_defaults(subcommand_func=main)
|
|
152
151
|
|
|
153
152
|
|
|
154
|
-
def add_parser(subparsers:
|
|
153
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
155
154
|
subcommand_name = "list"
|
|
156
155
|
subcommand_help = "コメント一覧を出力します。"
|
|
157
156
|
|
|
@@ -4,10 +4,9 @@ import logging
|
|
|
4
4
|
import multiprocessing
|
|
5
5
|
import uuid
|
|
6
6
|
from dataclasses import dataclass
|
|
7
|
-
from typing import Any
|
|
7
|
+
from typing import Any
|
|
8
8
|
|
|
9
9
|
import annofabapi
|
|
10
|
-
import annofabapi.utils
|
|
11
10
|
import requests
|
|
12
11
|
from annofabapi.models import CommentType, TaskPhase, TaskStatus
|
|
13
12
|
from dataclasses_json import DataClassJsonMixin
|
|
@@ -29,13 +28,13 @@ class AddedComment(DataClassJsonMixin):
|
|
|
29
28
|
comment: str
|
|
30
29
|
"""コメントの中身"""
|
|
31
30
|
|
|
32
|
-
data:
|
|
31
|
+
data: dict[str, Any] | None
|
|
33
32
|
"""コメントを付与する位置や区間"""
|
|
34
33
|
|
|
35
|
-
annotation_id:
|
|
34
|
+
annotation_id: str | None
|
|
36
35
|
"""コメントに紐付けるアノテーションID"""
|
|
37
36
|
|
|
38
|
-
phrases:
|
|
37
|
+
phrases: list[str] | None
|
|
39
38
|
"""参照している定型指摘ID"""
|
|
40
39
|
|
|
41
40
|
|
|
@@ -139,7 +138,7 @@ class PutCommentMain(CommandLineWithConfirm):
|
|
|
139
138
|
self,
|
|
140
139
|
task_id: str,
|
|
141
140
|
comments_for_task: AddedCommentsForTask,
|
|
142
|
-
task_index:
|
|
141
|
+
task_index: int | None = None,
|
|
143
142
|
) -> int:
|
|
144
143
|
"""
|
|
145
144
|
タスクにコメントを付与します。
|
|
@@ -207,7 +206,7 @@ class PutCommentMain(CommandLineWithConfirm):
|
|
|
207
206
|
def add_comments_for_task_list(
|
|
208
207
|
self,
|
|
209
208
|
comments_for_task_list: AddedComments,
|
|
210
|
-
parallelism:
|
|
209
|
+
parallelism: int | None = None,
|
|
211
210
|
) -> None:
|
|
212
211
|
comments_count = sum(len(e) for e in comments_for_task_list.values())
|
|
213
212
|
logger.info(f"{self.comment_type_name}を付与するタスク数: {len(comments_for_task_list)}, {self.comment_type_name}を付与する入力データ数: {comments_count}")
|
|
@@ -252,10 +251,10 @@ def convert_cli_comments(dict_comments: dict[str, Any], *, comment_type: Comment
|
|
|
252
251
|
data: dict[str, Any]
|
|
253
252
|
"""コメントを付与する位置や区間"""
|
|
254
253
|
|
|
255
|
-
annotation_id:
|
|
254
|
+
annotation_id: str | None = None
|
|
256
255
|
"""コメントに紐付けるアノテーションID"""
|
|
257
256
|
|
|
258
|
-
phrases:
|
|
257
|
+
phrases: list[str] | None = None
|
|
259
258
|
"""参照している定型指摘ID"""
|
|
260
259
|
|
|
261
260
|
@dataclass
|
|
@@ -267,7 +266,7 @@ def convert_cli_comments(dict_comments: dict[str, Any], *, comment_type: Comment
|
|
|
267
266
|
comment: str
|
|
268
267
|
"""コメントの中身"""
|
|
269
268
|
|
|
270
|
-
annotation_id:
|
|
269
|
+
annotation_id: str | None = None
|
|
271
270
|
"""コメントに紐付けるアノテーションID"""
|
|
272
271
|
|
|
273
272
|
def convert_inspection_comment(comment: dict[str, Any]) -> AddedComment:
|
|
@@ -4,10 +4,9 @@ import uuid
|
|
|
4
4
|
from collections.abc import Collection
|
|
5
5
|
from dataclasses import dataclass
|
|
6
6
|
from functools import partial
|
|
7
|
-
from typing import Any
|
|
7
|
+
from typing import Any
|
|
8
8
|
|
|
9
9
|
import annofabapi
|
|
10
|
-
import annofabapi.utils
|
|
11
10
|
from annofabapi.models import CommentType, TaskPhase, TaskStatus
|
|
12
11
|
|
|
13
12
|
from annofabcli.comment.utils import get_comment_type_name
|
|
@@ -26,10 +25,10 @@ class AddedSimpleComment:
|
|
|
26
25
|
comment: str
|
|
27
26
|
"""コメントの中身"""
|
|
28
27
|
|
|
29
|
-
data:
|
|
28
|
+
data: dict[str, Any] | None
|
|
30
29
|
"""コメントを付与する位置や区間"""
|
|
31
30
|
|
|
32
|
-
phrases:
|
|
31
|
+
phrases: list[str] | None = None
|
|
33
32
|
"""参照している定型指摘ID"""
|
|
34
33
|
|
|
35
34
|
|
|
@@ -103,7 +102,7 @@ class PutCommentSimplyMain(CommandLineWithConfirm):
|
|
|
103
102
|
self,
|
|
104
103
|
task_id: str,
|
|
105
104
|
comment_info: AddedSimpleComment,
|
|
106
|
-
task_index:
|
|
105
|
+
task_index: int | None = None,
|
|
107
106
|
) -> bool:
|
|
108
107
|
"""
|
|
109
108
|
タスクにコメントを付与します。
|
|
@@ -166,7 +165,7 @@ class PutCommentSimplyMain(CommandLineWithConfirm):
|
|
|
166
165
|
self,
|
|
167
166
|
task_ids: Collection[str],
|
|
168
167
|
comment_info: AddedSimpleComment,
|
|
169
|
-
parallelism:
|
|
168
|
+
parallelism: int | None = None,
|
|
170
169
|
) -> None:
|
|
171
170
|
logger.info(f"{len(task_ids)} 件のタスクに{self.comment_type_name}を付与します。")
|
|
172
171
|
|
|
@@ -4,11 +4,9 @@ import argparse
|
|
|
4
4
|
import json
|
|
5
5
|
import logging
|
|
6
6
|
import sys
|
|
7
|
-
from typing import Optional
|
|
8
7
|
|
|
9
8
|
from annofabapi.models import CommentType, ProjectMemberRole
|
|
10
9
|
|
|
11
|
-
import annofabcli
|
|
12
10
|
import annofabcli.common.cli
|
|
13
11
|
from annofabcli.comment.put_comment import PutCommentMain, convert_cli_comments
|
|
14
12
|
from annofabcli.common.cli import (
|
|
@@ -83,7 +81,7 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
83
81
|
parser.set_defaults(subcommand_func=main)
|
|
84
82
|
|
|
85
83
|
|
|
86
|
-
def add_parser(subparsers:
|
|
84
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
87
85
|
subcommand_name = "put_inspection"
|
|
88
86
|
subcommand_help = "検査コメントを付与します"
|
|
89
87
|
description = "検査コメントを付与します。"
|
|
@@ -1,12 +1,10 @@
|
|
|
1
1
|
import argparse
|
|
2
2
|
import logging
|
|
3
3
|
import sys
|
|
4
|
-
from typing import Optional
|
|
5
4
|
|
|
6
5
|
from annofabapi.models import CommentType, InputDataType, ProjectMemberRole
|
|
7
6
|
from annofabapi.plugin import EditorPluginId
|
|
8
7
|
|
|
9
|
-
import annofabcli
|
|
10
8
|
import annofabcli.common.cli
|
|
11
9
|
from annofabcli.comment.put_comment_simply import AddedSimpleComment, PutCommentSimplyMain
|
|
12
10
|
from annofabcli.common.cli import (
|
|
@@ -135,7 +133,7 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
135
133
|
parser.set_defaults(subcommand_func=main)
|
|
136
134
|
|
|
137
135
|
|
|
138
|
-
def add_parser(subparsers:
|
|
136
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
139
137
|
subcommand_name = "put_inspection_simply"
|
|
140
138
|
subcommand_help = "``comment put_inspection`` コマンドよりも、簡単に検査コメントを付与します。"
|
|
141
139
|
epilog = "チェッカーロールまたはオーナロールを持つユーザで実行してください。"
|
|
@@ -2,11 +2,9 @@ import argparse
|
|
|
2
2
|
import json
|
|
3
3
|
import logging
|
|
4
4
|
import sys
|
|
5
|
-
from typing import Optional
|
|
6
5
|
|
|
7
6
|
from annofabapi.models import CommentType
|
|
8
7
|
|
|
9
|
-
import annofabcli
|
|
10
8
|
import annofabcli.common.cli
|
|
11
9
|
from annofabcli.comment.put_comment import PutCommentMain, convert_cli_comments
|
|
12
10
|
from annofabcli.common.cli import (
|
|
@@ -84,7 +82,7 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
84
82
|
parser.set_defaults(subcommand_func=main)
|
|
85
83
|
|
|
86
84
|
|
|
87
|
-
def add_parser(subparsers:
|
|
85
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
88
86
|
subcommand_name = "put_onhold"
|
|
89
87
|
subcommand_help = "保留コメントを付与します"
|
|
90
88
|
|
|
@@ -1,11 +1,9 @@
|
|
|
1
1
|
import argparse
|
|
2
2
|
import logging
|
|
3
3
|
import sys
|
|
4
|
-
from typing import Optional
|
|
5
4
|
|
|
6
5
|
from annofabapi.models import CommentType
|
|
7
6
|
|
|
8
|
-
import annofabcli
|
|
9
7
|
import annofabcli.common.cli
|
|
10
8
|
from annofabcli.comment.put_comment_simply import AddedSimpleComment, PutCommentSimplyMain
|
|
11
9
|
from annofabcli.common.cli import (
|
|
@@ -87,7 +85,7 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
87
85
|
parser.set_defaults(subcommand_func=main)
|
|
88
86
|
|
|
89
87
|
|
|
90
|
-
def add_parser(subparsers:
|
|
88
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
91
89
|
subcommand_name = "put_onhold_simply"
|
|
92
90
|
subcommand_help = "``comment put_onhold`` コマンドよりも、簡単に保留コメントを付与します。"
|
|
93
91
|
|
|
@@ -1,7 +1,5 @@
|
|
|
1
1
|
import argparse
|
|
2
|
-
from typing import Optional
|
|
3
2
|
|
|
4
|
-
import annofabcli
|
|
5
3
|
import annofabcli.comment.delete_comment
|
|
6
4
|
import annofabcli.comment.download_comment_json
|
|
7
5
|
import annofabcli.comment.list_all_comment
|
|
@@ -27,7 +25,7 @@ def parse_args(parser: argparse.ArgumentParser) -> None:
|
|
|
27
25
|
annofabcli.comment.put_onhold_comment_simply.add_parser(subparsers)
|
|
28
26
|
|
|
29
27
|
|
|
30
|
-
def add_parser(subparsers:
|
|
28
|
+
def add_parser(subparsers: argparse._SubParsersAction | None = None) -> argparse.ArgumentParser:
|
|
31
29
|
subcommand_name = "comment"
|
|
32
30
|
subcommand_help = "コメント関係のサブコマンド"
|
|
33
31
|
|
annofabcli/common/bokeh.py
CHANGED
|
@@ -2,7 +2,7 @@ from __future__ import annotations
|
|
|
2
2
|
|
|
3
3
|
import json
|
|
4
4
|
import math
|
|
5
|
-
from typing import Any
|
|
5
|
+
from typing import Any
|
|
6
6
|
|
|
7
7
|
from bokeh.models import LayoutDOM
|
|
8
8
|
from bokeh.models.widgets.markups import PreText
|
|
@@ -15,16 +15,16 @@ def create_pretext_from_metadata(metadata: dict[str, Any]) -> PreText:
|
|
|
15
15
|
return PreText(text=text)
|
|
16
16
|
|
|
17
17
|
|
|
18
|
-
def convert_1d_figure_list_to_2d(figure_list: list[figure], *, ncols: int = 4) -> list[list[
|
|
18
|
+
def convert_1d_figure_list_to_2d(figure_list: list[figure], *, ncols: int = 4) -> list[list[LayoutDOM | None]]:
|
|
19
19
|
"""
|
|
20
20
|
1次元のfigure_listを、grid layout用に2次元のfigureリストに変換する。
|
|
21
21
|
"""
|
|
22
|
-
row_list: list[list[
|
|
22
|
+
row_list: list[list[LayoutDOM | None]] = []
|
|
23
23
|
|
|
24
24
|
for i in range(math.ceil(len(figure_list) / ncols)):
|
|
25
25
|
start = i * ncols
|
|
26
26
|
end = (i + 1) * ncols
|
|
27
|
-
row: list[
|
|
27
|
+
row: list[LayoutDOM | None] = []
|
|
28
28
|
row.extend(figure_list[start:end])
|
|
29
29
|
if len(row) < ncols:
|
|
30
30
|
row.extend([None] * (ncols - len(row)))
|
annofabcli/common/cli.py
CHANGED
|
@@ -6,10 +6,11 @@ import argparse
|
|
|
6
6
|
import getpass
|
|
7
7
|
import json
|
|
8
8
|
import logging
|
|
9
|
+
import logging.config
|
|
9
10
|
import os
|
|
10
11
|
import pkgutil
|
|
11
12
|
from pathlib import Path
|
|
12
|
-
from typing import Any
|
|
13
|
+
from typing import Any
|
|
13
14
|
|
|
14
15
|
import annofabapi
|
|
15
16
|
import pandas
|
|
@@ -81,12 +82,12 @@ def build_annofabapi_resource_and_login(args: argparse.Namespace) -> annofabapi.
|
|
|
81
82
|
|
|
82
83
|
|
|
83
84
|
def add_parser(
|
|
84
|
-
subparsers:
|
|
85
|
+
subparsers: argparse._SubParsersAction | None,
|
|
85
86
|
command_name: str,
|
|
86
87
|
command_help: str,
|
|
87
|
-
description:
|
|
88
|
+
description: str | None = None,
|
|
88
89
|
is_subcommand: bool = True, # noqa: FBT001, FBT002
|
|
89
|
-
epilog:
|
|
90
|
+
epilog: str | None = None,
|
|
90
91
|
) -> argparse.ArgumentParser:
|
|
91
92
|
"""
|
|
92
93
|
サブコマンド用にparserを追加する
|
|
@@ -159,7 +160,7 @@ def add_parser(
|
|
|
159
160
|
return parser
|
|
160
161
|
|
|
161
162
|
|
|
162
|
-
def get_list_from_args(str_list:
|
|
163
|
+
def get_list_from_args(str_list: list[str] | None = None) -> list[str]:
|
|
163
164
|
"""
|
|
164
165
|
文字列のListのサイズが1で、プレフィックスが`file://`ならば、ファイルパスとしてファイルを読み込み、行をListとして返す。
|
|
165
166
|
そうでなければ、引数の値をそのまま返す。
|
|
@@ -185,7 +186,7 @@ def get_list_from_args(str_list: Optional[list[str]] = None) -> list[str]:
|
|
|
185
186
|
return str_list
|
|
186
187
|
|
|
187
188
|
|
|
188
|
-
def get_json_from_args(target:
|
|
189
|
+
def get_json_from_args(target: str | None = None) -> Any: # noqa: ANN401
|
|
189
190
|
"""
|
|
190
191
|
JSON形式をPythonオブジェクトに変換する。
|
|
191
192
|
プレフィックスが`file://`ならば、ファイルパスとしてファイルを読み込み、Pythonオブジェクトを返す。
|
|
@@ -202,7 +203,7 @@ def get_json_from_args(target: Optional[str] = None) -> Any: # noqa: ANN401
|
|
|
202
203
|
return json.loads(target)
|
|
203
204
|
|
|
204
205
|
|
|
205
|
-
def get_input_data_size(str_input_data_size: str) ->
|
|
206
|
+
def get_input_data_size(str_input_data_size: str) -> InputDataSize | None:
|
|
206
207
|
"""400x300を(400,300)に変換する"""
|
|
207
208
|
splitted_list = str_input_data_size.split("x")
|
|
208
209
|
if len(splitted_list) < 2:
|
|
@@ -380,7 +381,7 @@ class ArgumentParser:
|
|
|
380
381
|
def __init__(self, parser: argparse.ArgumentParser) -> None:
|
|
381
382
|
self.parser = parser
|
|
382
383
|
|
|
383
|
-
def add_project_id(self, help_message:
|
|
384
|
+
def add_project_id(self, help_message: str | None = None) -> None:
|
|
384
385
|
"""
|
|
385
386
|
'--project_id` 引数を追加
|
|
386
387
|
"""
|
|
@@ -389,7 +390,7 @@ class ArgumentParser:
|
|
|
389
390
|
|
|
390
391
|
self.parser.add_argument("-p", "--project_id", type=str, required=True, help=help_message)
|
|
391
392
|
|
|
392
|
-
def add_task_id(self, *, required: bool = True, help_message:
|
|
393
|
+
def add_task_id(self, *, required: bool = True, help_message: str | None = None) -> None:
|
|
393
394
|
"""
|
|
394
395
|
'--task_id` 引数を追加
|
|
395
396
|
"""
|
|
@@ -398,7 +399,7 @@ class ArgumentParser:
|
|
|
398
399
|
|
|
399
400
|
self.parser.add_argument("-t", "--task_id", type=str, required=required, nargs="+", help=help_message)
|
|
400
401
|
|
|
401
|
-
def add_input_data_id(self, *, required: bool = True, help_message:
|
|
402
|
+
def add_input_data_id(self, *, required: bool = True, help_message: str | None = None) -> None:
|
|
402
403
|
"""
|
|
403
404
|
'--input_data_id` 引数を追加
|
|
404
405
|
"""
|
|
@@ -407,7 +408,7 @@ class ArgumentParser:
|
|
|
407
408
|
|
|
408
409
|
self.parser.add_argument("-i", "--input_data_id", type=str, required=required, nargs="+", help=help_message)
|
|
409
410
|
|
|
410
|
-
def add_format(self, choices: list[FormatArgument], default: FormatArgument, help_message:
|
|
411
|
+
def add_format(self, choices: list[FormatArgument], default: FormatArgument, help_message: str | None = None) -> None:
|
|
411
412
|
"""
|
|
412
413
|
'--format` 引数を追加
|
|
413
414
|
"""
|
|
@@ -416,7 +417,7 @@ class ArgumentParser:
|
|
|
416
417
|
|
|
417
418
|
self.parser.add_argument("-f", "--format", type=str, choices=[e.value for e in choices], default=default.value, help=help_message)
|
|
418
419
|
|
|
419
|
-
def add_output(self, *, required: bool = False, help_message:
|
|
420
|
+
def add_output(self, *, required: bool = False, help_message: str | None = None) -> None:
|
|
420
421
|
"""
|
|
421
422
|
'--output` 引数を追加
|
|
422
423
|
"""
|
|
@@ -425,7 +426,7 @@ class ArgumentParser:
|
|
|
425
426
|
|
|
426
427
|
self.parser.add_argument("-o", "--output", type=str, required=required, help=help_message)
|
|
427
428
|
|
|
428
|
-
def add_task_query(self, *, required: bool = False, help_message:
|
|
429
|
+
def add_task_query(self, *, required: bool = False, help_message: str | None = None) -> None:
|
|
429
430
|
if help_message is None:
|
|
430
431
|
help_message = (
|
|
431
432
|
"タスクを絞り込むためのクエリ条件をJSON形式で指定します。"
|
|
@@ -476,10 +477,10 @@ class CommandLineWithoutWebapi:
|
|
|
476
477
|
all_yes: bool = False
|
|
477
478
|
|
|
478
479
|
#: 出力先
|
|
479
|
-
output:
|
|
480
|
+
output: str | None = None
|
|
480
481
|
|
|
481
482
|
#: 出力フォーマット
|
|
482
|
-
str_format:
|
|
483
|
+
str_format: str | None = None
|
|
483
484
|
|
|
484
485
|
def __init__(self, args: argparse.Namespace) -> None:
|
|
485
486
|
self.args = args
|
|
@@ -575,8 +576,8 @@ class CommandLine(CommandLineWithoutWebapi):
|
|
|
575
576
|
def validate_project(
|
|
576
577
|
self,
|
|
577
578
|
project_id: str,
|
|
578
|
-
project_member_roles:
|
|
579
|
-
organization_member_roles:
|
|
579
|
+
project_member_roles: list[ProjectMemberRole] | None = None,
|
|
580
|
+
organization_member_roles: list[OrganizationMemberRole] | None = None,
|
|
580
581
|
) -> None:
|
|
581
582
|
"""
|
|
582
583
|
プロジェクト or 組織に対して、必要な権限が付与されているかを確認する。
|