Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Migrate to using pathlib in most of the SDK #5435

Merged
merged 1 commit into from
Dec 8, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,8 @@ from online detectors & interactors) (<https://github.com/opencv/cvat/pull/4543>
- Allowed trailing slashes in the SDK host address (<https://github.com/opencv/cvat/pull/5057>)
- Adjusted initial camera position, enabled 'Reset zoom' option for 3D canvas (<https://github.com/opencv/cvat/pull/5395>)
- Enabled authentication via email (<https://github.com/opencv/cvat/pull/5037>)
- In the SDK, functions taking paths as strings now also accept path-like objects
(<https://github.com/opencv/cvat/pull/5435>)

### Deprecated
- TDB
Expand Down
8 changes: 4 additions & 4 deletions cvat-sdk/cvat_sdk/core/downloading.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@

from __future__ import annotations

import os.path as osp
from contextlib import closing
from pathlib import Path
from typing import TYPE_CHECKING, Any, Dict, Optional

from cvat_sdk.api_client.api_client import Endpoint
Expand All @@ -28,7 +28,7 @@ def __init__(self, client: Client):
def download_file(
self,
url: str,
output_path: str,
output_path: Path,
*,
timeout: int = 60,
pbar: Optional[ProgressReporter] = None,
Expand All @@ -39,7 +39,7 @@ def download_file(

CHUNK_SIZE = 10 * 2**20

assert not osp.exists(output_path)
assert not output_path.exists()

response = self._client.api_client.rest_client.GET(
url,
Expand Down Expand Up @@ -70,7 +70,7 @@ def download_file(
def prepare_and_download_file_from_endpoint(
self,
endpoint: Endpoint,
filename: str,
filename: Path,
*,
url_params: Optional[Dict[str, Any]] = None,
query_params: Optional[Dict[str, Any]] = None,
Expand Down
25 changes: 17 additions & 8 deletions cvat-sdk/cvat_sdk/core/proxies/jobs.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,8 @@

import io
import mimetypes
import os
import os.path as osp
from typing import List, Optional, Sequence
from pathlib import Path
from typing import TYPE_CHECKING, List, Optional, Sequence

from PIL import Image

Expand All @@ -26,6 +25,9 @@
)
from cvat_sdk.core.uploading import AnnotationUploader

if TYPE_CHECKING:
from _typeshed import StrPath

_JobEntityBase, _JobRepoBase = build_model_bases(
models.JobRead, apis.JobsApi, api_member_name="jobs_api"
)
Expand All @@ -43,7 +45,7 @@ class Job(
def import_annotations(
self,
format_name: str,
filename: str,
filename: StrPath,
*,
status_check_period: Optional[int] = None,
pbar: Optional[ProgressReporter] = None,
Expand All @@ -52,6 +54,8 @@ def import_annotations(
Upload annotations for a job in the specified format (e.g. 'YOLO ZIP 1.0').
"""

filename = Path(filename)

AnnotationUploader(self._client).upload_file_and_wait(
self.api.create_annotations_endpoint,
filename,
Expand All @@ -66,7 +70,7 @@ def import_annotations(
def export_dataset(
self,
format_name: str,
filename: str,
filename: StrPath,
*,
pbar: Optional[ProgressReporter] = None,
status_check_period: Optional[int] = None,
Expand All @@ -75,6 +79,9 @@ def export_dataset(
"""
Download annotations for a job in the specified format (e.g. 'YOLO ZIP 1.0').
"""

filename = Path(filename)

if include_images:
endpoint = self.api.retrieve_dataset_endpoint
else:
Expand Down Expand Up @@ -112,15 +119,17 @@ def download_frames(
self,
frame_ids: Sequence[int],
*,
outdir: str = "",
outdir: StrPath = ".",
quality: str = "original",
filename_pattern: str = "frame_{frame_id:06d}{frame_ext}",
) -> Optional[List[Image.Image]]:
"""
Download the requested frame numbers for a job and save images as outdir/filename_pattern
"""
# TODO: add arg descriptions in schema
os.makedirs(outdir, exist_ok=True)

outdir = Path(outdir)
outdir.mkdir(parents=True, exist_ok=True)

for frame_id in frame_ids:
frame_bytes = self.get_frame(frame_id, quality=quality)
Expand All @@ -136,7 +145,7 @@ def download_frames(
im_ext = ".jpg"

outfile = filename_pattern.format(frame_id=frame_id, frame_ext=im_ext)
im.save(osp.join(outdir, outfile))
im.save(outdir / outfile)

def get_meta(self) -> models.IDataMetaRead:
(meta, _) = self.api.retrieve_data_meta(self.id)
Expand Down
27 changes: 20 additions & 7 deletions cvat-sdk/cvat_sdk/core/proxies/projects.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@
from __future__ import annotations

import json
import os.path as osp
from typing import Optional
from pathlib import Path
from typing import TYPE_CHECKING, Optional

from cvat_sdk.api_client import apis, models
from cvat_sdk.core.downloading import Downloader
Expand All @@ -21,6 +21,9 @@
)
from cvat_sdk.core.uploading import DatasetUploader, Uploader

if TYPE_CHECKING:
from _typeshed import StrPath

_ProjectEntityBase, _ProjectRepoBase = build_model_bases(
models.ProjectRead, apis.ProjectsApi, api_member_name="projects_api"
)
Expand All @@ -34,7 +37,7 @@ class Project(
def import_dataset(
self,
format_name: str,
filename: str,
filename: StrPath,
*,
status_check_period: Optional[int] = None,
pbar: Optional[ProgressReporter] = None,
Expand All @@ -43,6 +46,8 @@ def import_dataset(
Import dataset for a project in the specified format (e.g. 'YOLO ZIP 1.0').
"""

filename = Path(filename)

DatasetUploader(self._client).upload_file_and_wait(
self.api.create_dataset_endpoint,
filename,
Expand All @@ -57,7 +62,7 @@ def import_dataset(
def export_dataset(
self,
format_name: str,
filename: str,
filename: StrPath,
*,
pbar: Optional[ProgressReporter] = None,
status_check_period: Optional[int] = None,
Expand All @@ -66,6 +71,9 @@ def export_dataset(
"""
Download annotations for a project in the specified format (e.g. 'YOLO ZIP 1.0').
"""

filename = Path(filename)

if include_images:
endpoint = self.api.retrieve_dataset_endpoint
else:
Expand All @@ -84,7 +92,7 @@ def export_dataset(

def download_backup(
self,
filename: str,
filename: StrPath,
*,
status_check_period: int = None,
pbar: Optional[ProgressReporter] = None,
Expand All @@ -93,6 +101,8 @@ def download_backup(
Download a project backup
"""

filename = Path(filename)

Downloader(self._client).prepare_and_download_file_from_endpoint(
self.api.retrieve_backup_endpoint,
filename=filename,
Expand Down Expand Up @@ -148,18 +158,21 @@ def create_from_dataset(

def create_from_backup(
self,
filename: str,
filename: StrPath,
*,
status_check_period: int = None,
pbar: Optional[ProgressReporter] = None,
) -> Project:
"""
Import a project from a backup file
"""

filename = Path(filename)

if status_check_period is None:
status_check_period = self.config.status_check_period

params = {"filename": osp.basename(filename)}
params = {"filename": filename.name}
url = self.api_map.make_endpoint_url(self.api.create_backup_endpoint.path)

uploader = Uploader(self)
Expand Down
Loading