Add device selection menu
This commit is contained in:
parent
667223b3c2
commit
cfbd0ec8f2
1 changed files with 45 additions and 5 deletions
|
|
@ -5,6 +5,7 @@ import pathlib
|
||||||
import re
|
import re
|
||||||
|
|
||||||
from functions.common import *
|
from functions.common import *
|
||||||
|
from operator import itemgetter
|
||||||
|
|
||||||
# STATIC VARIABLES
|
# STATIC VARIABLES
|
||||||
USAGE=""" {script_name} clone [source [destination]]
|
USAGE=""" {script_name} clone [source [destination]]
|
||||||
|
|
@ -62,6 +63,7 @@ def setup_loopback_device(source_path):
|
||||||
try:
|
try:
|
||||||
out = run_program(cmd, check=True)
|
out = run_program(cmd, check=True)
|
||||||
dev_path = out.stdout.decode().strip()
|
dev_path = out.stdout.decode().strip()
|
||||||
|
sleep(1)
|
||||||
except CalledProcessError:
|
except CalledProcessError:
|
||||||
print_error('Failed to setup loopback device for source.')
|
print_error('Failed to setup loopback device for source.')
|
||||||
abort()
|
abort()
|
||||||
|
|
@ -76,9 +78,7 @@ def menu_clone(source_path, dest_path):
|
||||||
|
|
||||||
# Select source if not preselected
|
# Select source if not preselected
|
||||||
if not source_path:
|
if not source_path:
|
||||||
#TODO menu_select drive
|
source_path = select_device('Please select a source device')
|
||||||
print_warning('Select drive not implemented yet.')
|
|
||||||
source_path = ''
|
|
||||||
|
|
||||||
# Check source
|
# Check source
|
||||||
source_path = os.path.realpath(source_path)
|
source_path = os.path.realpath(source_path)
|
||||||
|
|
@ -101,11 +101,13 @@ def menu_clone(source_path, dest_path):
|
||||||
source_details = get_device_details(source_dev_path)
|
source_details = get_device_details(source_dev_path)
|
||||||
|
|
||||||
# Show selection details
|
# Show selection details
|
||||||
|
print_success('Source device')
|
||||||
if source_is_image:
|
if source_is_image:
|
||||||
print_success('Using image file: {}'.format(source_path))
|
print_standard('Using image file: {}'.format(source_path))
|
||||||
print_success(' (via loopback device: {})'.format(
|
print_standard(' (via loopback device: {})'.format(
|
||||||
source_dev_path))
|
source_dev_path))
|
||||||
show_device_details(source_dev_path)
|
show_device_details(source_dev_path)
|
||||||
|
print_standard(' ')
|
||||||
|
|
||||||
def menu_ddrescue(*args):
|
def menu_ddrescue(*args):
|
||||||
"""Main ddrescue loop/menu."""
|
"""Main ddrescue loop/menu."""
|
||||||
|
|
@ -140,6 +142,44 @@ def menu_image(source_path, dest_path):
|
||||||
print_success('GNU ddrescue: Imaging Menu')
|
print_success('GNU ddrescue: Imaging Menu')
|
||||||
pass
|
pass
|
||||||
|
|
||||||
|
def select_device(title='Which device?'):
|
||||||
|
"""Select block device via a menu, returns dev_path as str."""
|
||||||
|
try:
|
||||||
|
cmd = (
|
||||||
|
'lsblk',
|
||||||
|
'--json',
|
||||||
|
'--nodeps',
|
||||||
|
'--output-all',
|
||||||
|
'--paths')
|
||||||
|
result = run_program(cmd)
|
||||||
|
json_data = json.loads(result.stdout.decode())
|
||||||
|
except CalledProcessError:
|
||||||
|
print_error('Failed to get device details for {}'.format(dev_path))
|
||||||
|
abort()
|
||||||
|
|
||||||
|
# Build menu
|
||||||
|
dev_options = []
|
||||||
|
for dev in json_data['blockdevices']:
|
||||||
|
dev_options.append({
|
||||||
|
'Name': '{name:12} {tran:5} {size:6} {model} {serial}'.format(
|
||||||
|
name = dev['name'],
|
||||||
|
tran = dev['tran'] if dev['tran'] else '',
|
||||||
|
size = dev['size'] if dev['size'] else '',
|
||||||
|
model = dev['model'] if dev['model'] else '',
|
||||||
|
serial = dev['serial'] if dev['serial'] else ''),
|
||||||
|
'Path': dev['name']})
|
||||||
|
dev_options = sorted(dev_options, key=itemgetter('Name'))
|
||||||
|
actions = [{'Name': 'Quit', 'Letter': 'Q'}]
|
||||||
|
selection = menu_select(
|
||||||
|
title = title,
|
||||||
|
main_entries = dev_options,
|
||||||
|
action_entries = actions)
|
||||||
|
|
||||||
|
if selection.isnumeric():
|
||||||
|
return dev_options[int(selection)-1]['Path']
|
||||||
|
elif selection == 'Q':
|
||||||
|
abort()
|
||||||
|
|
||||||
def show_usage(script_name):
|
def show_usage(script_name):
|
||||||
print_info('Usage:')
|
print_info('Usage:')
|
||||||
print_standard(USAGE.format(script_name=script_name))
|
print_standard(USAGE.format(script_name=script_name))
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue