227 lines
8.7 KiB
Python
Executable File
227 lines
8.7 KiB
Python
Executable File
from window import Window
|
|
from windowstringreader import WindowStringReader
|
|
from partitionpane import PartitionPane
|
|
from readmultext import ReadMulText
|
|
from confirmwindow import ConfirmWindow
|
|
from actionresult import ActionResult
|
|
from device import Device
|
|
|
|
class CustomPartition(object):
|
|
def __init__(self, maxy, maxx, install_config):
|
|
self.maxx = maxx
|
|
self.maxy = maxy
|
|
self.win_width = maxx - 4
|
|
self.win_height = maxy - 4
|
|
self.install_config = install_config
|
|
self.path_checker = []
|
|
|
|
self.win_starty = (self.maxy - self.win_height) // 2
|
|
self.win_startx = (self.maxx - self.win_width) // 2
|
|
|
|
self.text_starty = self.win_starty + 4
|
|
self.text_height = self.win_height - 6
|
|
self.text_width = self.win_width - 6
|
|
self.cp_config = {}
|
|
self.cp_config['partitionsnumber'] = 0
|
|
self.devices = Device.refresh_devices_bytes()
|
|
self.has_slash = False
|
|
self.has_remain = False
|
|
self.has_empty = False
|
|
|
|
self.disk_size = []
|
|
self.disk_to_index = {}
|
|
for index, device in enumerate(self.devices):
|
|
self.disk_size.append((device.path, int(device.size) / 1048576))
|
|
self.disk_to_index[device.path] = index
|
|
|
|
self.window = Window(self.win_height, self.win_width, self.maxy, self.maxx,
|
|
'Welcome to the Photon installer', False, can_go_next=False)
|
|
Device.refresh_devices()
|
|
|
|
def display(self):
|
|
if 'autopartition' in self.install_config and self.install_config['autopartition'] == True:
|
|
return ActionResult(True, None)
|
|
|
|
self.device_index = self.disk_to_index[self.install_config['disk']]
|
|
|
|
self.disk_buttom_items = []
|
|
self.disk_buttom_items.append(('<Next>', self.next))
|
|
self.disk_buttom_items.append(('<Create New>', self.create_function))
|
|
self.disk_buttom_items.append(('<Delete All>', self.delete_function))
|
|
self.disk_buttom_items.append(('<Go Back>', self.go_back))
|
|
|
|
self.text_items = []
|
|
self.text_items.append(('Disk', 20))
|
|
self.text_items.append(('Size', 5))
|
|
self.text_items.append(('Type', 5))
|
|
self.text_items.append(('Mountpoint', 20))
|
|
self.table_space = 5
|
|
|
|
title = 'Current partitions:\n'
|
|
self.window.addstr(0, (self.win_width - len(title)) // 2, title)
|
|
|
|
info = ("Unpartitioned space: " +
|
|
str(self.disk_size[self.device_index][1])+
|
|
" MB, Total size: "+
|
|
str(int(self.devices[self.device_index].size)/ 1048576) + " MB")
|
|
|
|
self.partition_pane = PartitionPane(self.text_starty, self.maxx, self.text_width,
|
|
self.text_height, self.disk_buttom_items,
|
|
config=self.cp_config,
|
|
text_items=self.text_items, table_space=self.table_space,
|
|
info=info,
|
|
size_left=str(self.disk_size[self.device_index][1]))
|
|
|
|
self.window.set_action_panel(self.partition_pane)
|
|
|
|
return self.window.do_action()
|
|
|
|
def validate_partition(self, pstr):
|
|
if not pstr:
|
|
return ActionResult(False, None)
|
|
sizedata = pstr[0]
|
|
mtdata = pstr[2]
|
|
typedata = pstr[1]
|
|
devicedata = self.devices[self.device_index].path
|
|
|
|
#no empty fields unless swap
|
|
if (typedata == 'swap' and
|
|
(len(mtdata) != 0 or len(typedata) == 0 or len(devicedata) == 0)):
|
|
return False, "invalid swap data "
|
|
|
|
if (typedata != 'swap' and
|
|
(len(sizedata) == 0 or
|
|
len(mtdata) == 0 or
|
|
len(typedata) == 0 or
|
|
len(devicedata) == 0)):
|
|
if not self.has_empty and mtdata and typedata and devicedata:
|
|
self.has_empty = True
|
|
else:
|
|
return False, "Input cannot be empty"
|
|
|
|
if typedata != 'swap' and typedata != 'ext3' and typedata != 'ext4':
|
|
return False, "Invalid type"
|
|
|
|
if len(mtdata) != 0 and mtdata[0] != '/':
|
|
return False, "Invalid path"
|
|
|
|
if mtdata in self.path_checker:
|
|
return False, "Path already existed"
|
|
#validate disk: must be one of the existing disks
|
|
i = self.device_index
|
|
|
|
#valid size: must not exceed memory limit
|
|
curr_size = self.disk_size[i][1]
|
|
if len(sizedata) != 0:
|
|
try:
|
|
int(sizedata)
|
|
except ValueError:
|
|
return False, "invalid device size"
|
|
|
|
if int(curr_size) - int(sizedata) < 0:
|
|
return False, "invalid device size"
|
|
#if valid, update the size and return true
|
|
new_size = (self.disk_size[i][0], int(curr_size)- int(sizedata))
|
|
self.disk_size[i] = new_size
|
|
|
|
if mtdata == "/":
|
|
self.has_slash = True
|
|
|
|
self.path_checker.append(mtdata)
|
|
return True, None
|
|
|
|
def create_function(self):
|
|
self.window.hide_window()
|
|
|
|
self.cp_config['partition_disk'] = self.devices[self.device_index].path
|
|
self.partition_items = []
|
|
self.partition_items.append(('Size in MB: ' +
|
|
str(self.disk_size[self.device_index][1]) +
|
|
' available'))
|
|
self.partition_items.append(('Type: (ext3, ext4, swap)'))
|
|
self.partition_items.append(('Mountpoint:'))
|
|
self.create_window = ReadMulText(
|
|
self.maxy, self.maxx, 0,
|
|
self.cp_config,
|
|
str(self.cp_config['partitionsnumber']) + 'partition_info',
|
|
self.partition_items,
|
|
None,
|
|
None,
|
|
None,
|
|
self.validate_partition, #validation function of the input
|
|
None,
|
|
True,
|
|
)
|
|
result = self.create_window.do_action()
|
|
if result.success:
|
|
self.cp_config['partitionsnumber'] = self.cp_config['partitionsnumber'] + 1
|
|
|
|
#parse the input in install config
|
|
return self.display()
|
|
|
|
def delete_function(self):
|
|
self.delete()
|
|
return self.display()
|
|
|
|
def go_back(self):
|
|
self.delete()
|
|
self.window.hide_window()
|
|
self.partition_pane.hide()
|
|
return ActionResult(False, {'goBack':True})
|
|
|
|
def next(self):
|
|
if self.cp_config['partitionsnumber'] == 0:
|
|
window_height = 9
|
|
window_width = 40
|
|
window_starty = (self.maxy-window_height) // 2 + 5
|
|
confirm_window = ConfirmWindow(window_height, window_width, self.maxy,
|
|
self.maxx, window_starty,
|
|
'Partition information cannot be empty',
|
|
info=True)
|
|
confirm_window.do_action()
|
|
return self.display()
|
|
#must have /
|
|
if not self.has_slash:
|
|
window_height = 9
|
|
window_width = 40
|
|
window_starty = (self.maxy - window_height) // 2 + 5
|
|
confirm_window = ConfirmWindow(window_height, window_width, self.maxy,
|
|
self.maxx, window_starty, 'Missing /',
|
|
info=True)
|
|
confirm_window.do_action()
|
|
return self.display()
|
|
|
|
self.window.hide_window()
|
|
self.partition_pane.hide()
|
|
|
|
partitions = []
|
|
for i in range(int(self.cp_config['partitionsnumber'])):
|
|
if len(self.cp_config[str(i)+'partition_info'+str(0)]) == 0:
|
|
sizedata = 0
|
|
else:
|
|
sizedata = int(self.cp_config[str(i) + 'partition_info' + str(0)])
|
|
mtdata = self.cp_config[str(i) + 'partition_info' + str(2)]
|
|
typedata = self.cp_config[str(i) + 'partition_info'+str(1)]
|
|
|
|
partitions = partitions + [{"mountpoint": mtdata,
|
|
"size": sizedata,
|
|
"filesystem": typedata},]
|
|
self.install_config['partitions'] = partitions
|
|
|
|
return ActionResult(True, {'goNext':True})
|
|
|
|
def delete(self):
|
|
for i in range(int(self.cp_config['partitionsnumber'])):
|
|
self.cp_config[str(i)+'partition_info'+str(0)] = ''
|
|
self.cp_config[str(i)+'partition_info'+str(1)] = ''
|
|
self.cp_config[str(i)+'partition_info'+str(2)] = ''
|
|
self.cp_config[str(i)+'partition_info'+str(3)] = ''
|
|
del self.disk_size[:]
|
|
for index, device in enumerate(self.devices):
|
|
self.disk_size.append((device.path, int(device.size) / 1048576))
|
|
del self.path_checker[:]
|
|
self.has_slash = False
|
|
self.has_remain = False
|
|
self.has_empty = False
|
|
self.cp_config['partitionsnumber'] = 0
|