Skip to content

Commit 2ad4eb0

Browse files
authored
Merge pull request #261 from superannotateai/fix-logs
Fix logs
2 parents 9a99b3f + ff79aa4 commit 2ad4eb0

File tree

4 files changed

+92
-52
lines changed

4 files changed

+92
-52
lines changed

src/superannotate/lib/app/interface/sdk_interface.py

Lines changed: 13 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -2447,22 +2447,23 @@ def upload_annotations_from_folder_to_project(
24472447
project_name, folder_name = extract_project_folder(project)
24482448
project_folder_name = project_name + (f"/{folder_name}" if folder_name else "")
24492449

2450-
24512450
if recursive_subfolders:
24522451
logger.info(
24532452
"When using recursive subfolder parsing same name annotations in different "
24542453
"subfolders will overwrite each other.",
24552454
)
2456-
logger.info("The JSON files should follow a specific naming convention, matching file names already present "
2457-
"on the platform. Existing annotations will be overwritten")
2455+
logger.info(
2456+
"The JSON files should follow a specific naming convention, matching file names already present "
2457+
"on the platform. Existing annotations will be overwritten"
2458+
)
24582459

24592460
annotation_paths = get_annotation_paths(
24602461
folder_path, from_s3_bucket, recursive_subfolders
24612462
)
2462-
if not annotation_paths:
2463-
raise AppException("Could not find annotations matching existing items on the platform.")
24642463

2465-
logger.info(f"Uploading {len(annotation_paths)} annotations from {folder_path} to the project {project_folder_name}.")
2464+
logger.info(
2465+
f"Uploading {len(annotation_paths)} annotations from {folder_path} to the project {project_folder_name}."
2466+
)
24662467
response = controller.upload_annotations_from_folder(
24672468
project_name=project_name,
24682469
folder_name=folder_name,
@@ -2518,16 +2519,17 @@ def upload_preannotations_from_folder_to_project(
25182519
"When using recursive subfolder parsing same name annotations in different "
25192520
"subfolders will overwrite each other.",
25202521
)
2521-
logger.info("The JSON files should follow a specific naming convention, matching file names already present "
2522-
"on the platform. Existing annotations will be overwritten")
2522+
logger.info(
2523+
"The JSON files should follow a specific naming convention, matching file names already present "
2524+
"on the platform. Existing annotations will be overwritten"
2525+
)
25232526
logger.info("Existing annotations will be overwritten.",)
25242527
annotation_paths = get_annotation_paths(
25252528
folder_path, from_s3_bucket, recursive_subfolders
25262529
)
2527-
if not annotation_paths:
2528-
raise AppException("Could not find annotations matching existing items on the platform.")
25292530
logger.info(
2530-
f"Uploading {len(annotation_paths)} annotations from {folder_path} to the project {project_folder_name}.")
2531+
f"Uploading {len(annotation_paths)} annotations from {folder_path} to the project {project_folder_name}."
2532+
)
25312533
response = controller.upload_annotations_from_folder(
25322534
project_name=project_name,
25332535
folder_name=folder_name,

src/superannotate/lib/core/helpers.py

Lines changed: 41 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,7 @@
88
def map_annotation_classes_name(annotation_classes, reporter: Reporter) -> dict:
99
classes_data = defaultdict(dict)
1010
for annotation_class in annotation_classes:
11-
class_info = {
12-
"id": annotation_class.uuid,
13-
"attribute_groups": {}
14-
}
11+
class_info = {"id": annotation_class.uuid, "attribute_groups": {}}
1512
if annotation_class.attribute_groups:
1613
for attribute_group in annotation_class.attribute_groups:
1714
attribute_group_data = defaultdict(dict)
@@ -46,14 +43,13 @@ def map_annotation_classes_name(annotation_classes, reporter: Reporter) -> dict:
4643

4744

4845
def fill_document_tags(
49-
annotations: dict,
50-
annotation_classes: dict,
46+
annotations: dict, annotation_classes: dict,
5147
):
5248
new_tags = []
53-
for tag in annotations['tags']:
49+
for tag in annotations["tags"]:
5450
if annotation_classes.get(tag):
55-
new_tags.append(annotation_classes[tag]['id'])
56-
annotations['tags'] = new_tags
51+
new_tags.append(annotation_classes[tag]["id"])
52+
annotations["tags"] = new_tags
5753

5854

5955
def fill_annotation_ids(
@@ -108,7 +104,10 @@ def fill_annotation_ids(
108104
reporter.log_warning(
109105
f"Couldn't find annotation group {attribute['groupName']}."
110106
)
111-
reporter.store_message("missing_attribute_groups", f"{annotation['className']}.{attribute['groupName']}")
107+
reporter.store_message(
108+
"missing_attribute_groups",
109+
f"{annotation['className']}.{attribute['groupName']}",
110+
)
112111
continue
113112
attribute["groupId"] = annotation_classes_name_maps[annotation_class_name][
114113
"attribute_groups"
@@ -131,7 +130,9 @@ def fill_annotation_ids(
131130
][attribute["groupName"]]["attributes"][attribute["name"]]
132131

133132

134-
def convert_to_video_editor_json(data: dict, class_name_mapper: dict, reporter: Reporter):
133+
def convert_to_video_editor_json(
134+
data: dict, class_name_mapper: dict, reporter: Reporter
135+
):
135136
id_generator = ClassIdGenerator()
136137

137138
def safe_time(timestamp):
@@ -161,7 +162,9 @@ def convert_timestamp(timestamp):
161162
"locked": True,
162163
}
163164
if class_name:
164-
editor_instance["classId"] = class_name_mapper.get(class_name, {}).get("id", id_generator.send(class_name))
165+
editor_instance["classId"] = class_name_mapper.get(class_name, {}).get(
166+
"id", id_generator.send(class_name)
167+
)
165168
else:
166169
editor_instance["classId"] = id_generator.send("unknown_class")
167170
if meta.get("pointLabels", None):
@@ -194,13 +197,33 @@ def convert_timestamp(timestamp):
194197

195198
existing_attributes_in_current_instance = set()
196199
for attribute in timestamp_data["attributes"]:
197-
group_name, attr_name = attribute.get("groupName"), attribute.get("name")
198-
if not class_name_mapper[class_name].get("attribute_groups", {}).get(group_name):
199-
reporter.store_message("missing_attribute_groups", f"{class_name}.{group_name}")
200-
elif not class_name_mapper[class_name]["attribute_groups"][group_name].get("attributes", {}).get(attr_name):
201-
reporter.store_message("missing_attributes", f"{class_name}.{group_name}.{attr_name}")
200+
group_name, attr_name = (
201+
attribute.get("groupName"),
202+
attribute.get("name"),
203+
)
204+
if (
205+
not class_name_mapper[class_name]
206+
.get("attribute_groups", {})
207+
.get(group_name)
208+
):
209+
reporter.store_message(
210+
"missing_attribute_groups", f"{class_name}.{group_name}"
211+
)
212+
elif (
213+
not class_name_mapper[class_name]["attribute_groups"][
214+
group_name
215+
]
216+
.get("attributes", {})
217+
.get(attr_name)
218+
):
219+
reporter.store_message(
220+
"missing_attributes",
221+
f"{class_name}.{group_name}.{attr_name}",
222+
)
202223
else:
203-
existing_attributes_in_current_instance.add((group_name, attr_name))
224+
existing_attributes_in_current_instance.add(
225+
(group_name, attr_name)
226+
)
204227
attributes_to_add = (
205228
existing_attributes_in_current_instance - active_attributes
206229
)

src/superannotate/lib/core/types.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ class Metadata(BaseModel):
4848

4949

5050
class PointLabels(BaseModel):
51-
__root__: Dict[constr(regex=r'^[0-9]*$'), str]
51+
__root__: Dict[constr(regex=r"^[0-9]*$"), str]
5252

5353

5454
class BaseInstance(BaseModel):

src/superannotate/lib/core/usecases/annotations.py

Lines changed: 37 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,6 @@
1212
from lib.core.entities import FolderEntity
1313
from lib.core.entities import ImageEntity
1414
from lib.core.entities import ProjectEntity
15-
from lib.core.exceptions import AppException
1615
from lib.core.helpers import convert_to_video_editor_json
1716
from lib.core.helpers import fill_annotation_ids
1817
from lib.core.helpers import fill_document_tags
@@ -111,6 +110,7 @@ def annotations_to_upload(self):
111110
for idx, detail in enumerate(images_detail):
112111
if detail.name == image_data.name:
113112
images_detail[idx] = detail._replace(id=image_data.uuid)
113+
break
114114

115115
missing_annotations = list(
116116
filter(lambda image_detail: image_detail.id is None, images_detail)
@@ -119,13 +119,8 @@ def annotations_to_upload(self):
119119
filter(lambda image_detail: image_detail.id is not None, images_detail)
120120
)
121121
if missing_annotations:
122-
for missing in missing_annotations:
123-
logger.warning(
124-
f"Couldn't find image {missing.path} for annotation upload."
125-
)
126-
if not annotations_to_upload:
127-
raise AppException(
128-
"No item to attach annotations."
122+
logger.warning(
123+
f"Couldn't find {len(missing_annotations)}/{len(annotations_to_upload + missing_annotations)} items on the platform that match the annotations you want to upload."
129124
)
130125
self._missing_annotations = missing_annotations
131126
self._annotations_to_upload = annotations_to_upload
@@ -199,9 +194,7 @@ def _log_report(self):
199194
template = "Could not find attribute groups matching existing attribute groups on the platform: [{}]"
200195
elif key == "missing_attributes":
201196
template = "Could not find attributes matching existing attributes on the platform: [{}]"
202-
logger.warning(
203-
template.format("', '".join(values))
204-
)
197+
logger.warning(template.format("', '".join(values)))
205198

206199
def execute(self):
207200
uploaded_annotations = []
@@ -210,19 +203,27 @@ def execute(self):
210203
iterations_range = range(
211204
0, len(self.annotations_to_upload), self.AUTH_DATA_CHUNK_SIZE
212205
)
213-
self.reporter.start_progress(len(self.annotations_to_upload), description="Uploading Annotations")
206+
self.reporter.start_progress(
207+
len(self.annotations_to_upload), description="Uploading Annotations"
208+
)
214209
for step in iterations_range:
215-
annotations_to_upload = self.annotations_to_upload[step : step + self.AUTH_DATA_CHUNK_SIZE] # noqa: E203
210+
annotations_to_upload = self.annotations_to_upload[
211+
step : step + self.AUTH_DATA_CHUNK_SIZE
212+
] # noqa: E203
216213
upload_data = self.get_annotation_upload_data(
217214
[int(image.id) for image in annotations_to_upload]
218215
)
219-
bucket = self.get_bucket_to_upload([int(image.id) for image in annotations_to_upload])
216+
bucket = self.get_bucket_to_upload(
217+
[int(image.id) for image in annotations_to_upload]
218+
)
220219
if bucket:
221220
image_id_name_map = {
222221
image.id: image for image in self.annotations_to_upload
223222
}
224223
# dummy progress
225-
for _ in range(len(annotations_to_upload) - len(upload_data.images)):
224+
for _ in range(
225+
len(annotations_to_upload) - len(upload_data.images)
226+
):
226227
self.reporter.update_progress()
227228
with concurrent.futures.ThreadPoolExecutor(
228229
max_workers=self.MAX_WORKERS
@@ -252,8 +253,6 @@ def execute(self):
252253
[annotation.path for annotation in self._missing_annotations],
253254
)
254255
self._log_report()
255-
else:
256-
self._response.errors = "Could not find annotations matching existing items on the platform."
257256
return self._response
258257

259258

@@ -338,13 +337,26 @@ def from_s3(self):
338337
def set_annotation_json(self):
339338
if not self._annotation_json:
340339
if self._client_s3_bucket:
341-
self._annotation_json = json.load(self.get_s3_file(self.from_s3, self._annotation_path))
340+
self._annotation_json = json.load(
341+
self.get_s3_file(self.from_s3, self._annotation_path)
342+
)
342343
if self._project.project_type == constances.ProjectType.PIXEL.value:
343-
self._mask = self.get_s3_file(self.from_s3, self._annotation_path.replace(constances.PIXEL_ANNOTATION_POSTFIX, constances.ANNOTATION_MASK_POSTFIX))
344+
self._mask = self.get_s3_file(
345+
self.from_s3,
346+
self._annotation_path.replace(
347+
constances.PIXEL_ANNOTATION_POSTFIX,
348+
constances.ANNOTATION_MASK_POSTFIX,
349+
),
350+
)
344351
else:
345352
self._annotation_json = json.load(open(self._annotation_path))
346353
if self._project.project_type == constances.ProjectType.PIXEL.value:
347-
self._mask = open(self._annotation_path.replace(constances.PIXEL_ANNOTATION_POSTFIX, constances.ANNOTATION_MASK_POSTFIX))
354+
self._mask = open(
355+
self._annotation_path.replace(
356+
constances.PIXEL_ANNOTATION_POSTFIX,
357+
constances.ANNOTATION_MASK_POSTFIX,
358+
)
359+
)
348360

349361
def _is_valid_json(self, json_data: dict):
350362
use_case = ValidateAnnotationUseCase(
@@ -368,7 +380,7 @@ def prepare_annotations(
368380
if project_type in (
369381
constances.ProjectType.VECTOR.value,
370382
constances.ProjectType.PIXEL.value,
371-
constances.ProjectType.DOCUMENT.value
383+
constances.ProjectType.DOCUMENT.value,
372384
):
373385
fill_annotation_ids(
374386
annotations=annotations,
@@ -415,7 +427,10 @@ def execute(self):
415427
],
416428
Body=json.dumps(annotation_json),
417429
)
418-
if self._project.project_type == constances.ProjectType.PIXEL.value and self._mask:
430+
if (
431+
self._project.project_type == constances.ProjectType.PIXEL.value
432+
and self._mask
433+
):
419434
bucket.put_object(
420435
Key=self.annotation_upload_data.images[self._image.uuid][
421436
"annotation_bluemap_path"

0 commit comments

Comments
 (0)