forked from ArduPilot/ardupilot
-
Notifications
You must be signed in to change notification settings - Fork 18
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Tools: siyi image and video download script
- Loading branch information
Showing
1 changed file
with
142 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,142 @@ | ||
#!/usr/bin/env python3 | ||
|
||
""" | ||
Downloads files from a Siyi camera connected via ethernet | ||
""" | ||
|
||
# | ||
# utility to download files from a siyi camera | ||
# | ||
|
||
import os | ||
import json | ||
from argparse import ArgumentParser | ||
from urllib.request import urlopen, urlretrieve | ||
from urllib.parse import urlencode | ||
from enum import Enum | ||
|
||
# prefix string for text outout to user | ||
prefix_str = "siyi-download.py: " | ||
ip_address_default = "192.168.144.25" | ||
|
||
|
||
# media types | ||
class MediaTypes(Enum): | ||
IMAGE = 0 | ||
VIDEO = 1 | ||
|
||
|
||
# media type strings. used to display to user | ||
MEDIA_TYPE_STR = ["image", "video"] | ||
|
||
|
||
# get URL for list of directories | ||
def get_dirlist_url(ip_address, media_type): | ||
params = {'media_type': media_type} | ||
return f"http://{ip_address}:82/cgi-bin/media.cgi/api/v1/getdirectories?" + urlencode(params) | ||
|
||
|
||
# get URL for list of files in a directory | ||
def get_filelist_url(ip_address, media_type, dir_path): | ||
params = { | ||
'media_type': str(media_type), | ||
'path': dir_path, | ||
'start': 0, | ||
'count': 999 | ||
} | ||
return f"http://{ip_address}:82/cgi-bin/media.cgi/api/v1/getmedialist?" + urlencode(params) | ||
|
||
|
||
# download files from camera | ||
def download_files(ip_address, dest_dir): | ||
|
||
# repeat for images and videos | ||
for media_type in [mt.value for mt in MediaTypes]: | ||
|
||
# display output to user | ||
print(prefix_str + f"downloading {MEDIA_TYPE_STR[media_type]} files") | ||
|
||
# download list of directories in JSON format | ||
dir_list_url = get_dirlist_url(ip_address, media_type) | ||
with urlopen(dir_list_url) as get_dir_url: | ||
dir_dict = json.load(get_dir_url) | ||
|
||
# check that the request succeeded | ||
if (not dir_dict['success']): | ||
exit(prefix_str + "failed to get list of directories") | ||
|
||
# check response includes 'data' | ||
if ('data' not in dir_dict.keys()): | ||
exit(prefix_str + "could not get list of directories, no 'data' in response") | ||
dir_dict_data = dir_dict['data'] | ||
|
||
# check response includes 'directories' | ||
if ('directories' not in dir_dict_data.keys()): | ||
exit(prefix_str + "could not get list of directories, no 'directories' in response") | ||
dir_dict_data_directories = dir_dict_data['directories'] | ||
|
||
# create list of directories from 'path' values | ||
dir_list = [] | ||
for dir in dir_dict_data_directories: | ||
if ('path' in dir.keys()): | ||
dir_list.append(dir['path']) | ||
print(prefix_str + f"{len(dir_list)} directories") | ||
|
||
# get list of files in each directory | ||
for dir_path in dir_list: | ||
filenames_url = get_filelist_url(ip_address, media_type, dir_path) | ||
with urlopen(filenames_url) as get_filenames_url: | ||
filename_dict = json.load(get_filenames_url) | ||
|
||
# check that the request succeeded | ||
if (not filename_dict['success']): | ||
exit(prefix_str + "failed to get list of files") | ||
|
||
# check response includes 'data' | ||
if ('data' not in filename_dict.keys()): | ||
exit(prefix_str + "could not get list of files, no 'data' in response") | ||
filename_dict_data = filename_dict['data'] | ||
|
||
# check response includes 'list' | ||
if ('list' not in filename_dict_data.keys()): | ||
exit(prefix_str + "could not get list of files, no 'list' in response") | ||
filename_dict_data_list = filename_dict_data['list'] | ||
print(prefix_str + f"{len(filename_dict_data_list)} files") | ||
|
||
# download each image | ||
for fileinfo in filename_dict_data_list: | ||
if ('name' not in fileinfo.keys() or 'url' not in fileinfo.keys()): | ||
exit(prefix_str + "could not get list of files, no 'name' or 'url' in response") | ||
filename = fileinfo['name'] | ||
file_url = fileinfo['url'] | ||
|
||
# correct incorrect ip address in returned url | ||
file_url_fixed = file_url.replace(ip_address_default, ip_address) | ||
|
||
# download file | ||
print(prefix_str + f"downloading {filename} from {file_url_fixed}") | ||
dest_filename = os.path.join(dest_dir, filename) | ||
try: | ||
urlretrieve(file_url_fixed, dest_filename) | ||
except Exception as e: | ||
print(prefix_str + f"failed to download {filename}: {e}") | ||
|
||
|
||
# main function | ||
def main(): | ||
parser = ArgumentParser(description=__doc__) | ||
parser.add_argument("--ipaddr", default=ip_address_default, help="IP address of camera") | ||
parser.add_argument("--dest", default=".", help="destination directory where downloaded files will be saved") | ||
args = parser.parse_args() | ||
|
||
# check destination directory exists | ||
if not os.path.exists(args.dest): | ||
exit(prefix_str + "invalid destination directory") | ||
|
||
# download files | ||
download_files(args.ipaddr, args.dest) | ||
|
||
|
||
# main | ||
if __name__ == "__main__": | ||
main() |