Add udev sync before lsblk that follows formatting (#2412)
This commit is contained in:
parent
613bec6562
commit
df2884085d
|
|
@ -2,7 +2,6 @@ from __future__ import annotations
|
||||||
|
|
||||||
import json
|
import json
|
||||||
import os
|
import os
|
||||||
import time
|
|
||||||
import logging
|
import logging
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import List, Dict, Any, Optional, TYPE_CHECKING
|
from typing import List, Dict, Any, Optional, TYPE_CHECKING
|
||||||
|
|
@ -316,6 +315,9 @@ class DeviceHandler(object):
|
||||||
else:
|
else:
|
||||||
self._perform_formatting(part_mod.safe_fs_type, part_mod.safe_dev_path)
|
self._perform_formatting(part_mod.safe_fs_type, part_mod.safe_dev_path)
|
||||||
|
|
||||||
|
# synchronize with udev before using lsblk
|
||||||
|
SysCommand('udevadm settle')
|
||||||
|
|
||||||
lsblk_info = self._fetch_part_info(part_mod.safe_dev_path)
|
lsblk_info = self._fetch_part_info(part_mod.safe_dev_path)
|
||||||
|
|
||||||
part_mod.partn = lsblk_info.partn
|
part_mod.partn = lsblk_info.partn
|
||||||
|
|
@ -384,19 +386,7 @@ class DeviceHandler(object):
|
||||||
part_mod.dev_path = Path(partition.path)
|
part_mod.dev_path = Path(partition.path)
|
||||||
|
|
||||||
def _fetch_part_info(self, path: Path) -> LsblkInfo:
|
def _fetch_part_info(self, path: Path) -> LsblkInfo:
|
||||||
attempts = 3
|
lsblk_info = get_lsblk_info(path)
|
||||||
lsblk_info: Optional[LsblkInfo] = None
|
|
||||||
|
|
||||||
for attempt_nr in range(attempts):
|
|
||||||
time.sleep(attempt_nr + 1)
|
|
||||||
lsblk_info = get_lsblk_info(path)
|
|
||||||
|
|
||||||
if lsblk_info.partn and lsblk_info.partuuid and lsblk_info.uuid:
|
|
||||||
break
|
|
||||||
|
|
||||||
if not lsblk_info:
|
|
||||||
debug(f'Unable to get partition information: {path}')
|
|
||||||
raise DiskError(f'Unable to get partition information: {path}')
|
|
||||||
|
|
||||||
if not lsblk_info.partn:
|
if not lsblk_info.partn:
|
||||||
debug(f'Unable to determine new partition number: {path}\n{lsblk_info}')
|
debug(f'Unable to determine new partition number: {path}\n{lsblk_info}')
|
||||||
|
|
|
||||||
|
|
@ -3,7 +3,6 @@ from __future__ import annotations
|
||||||
import dataclasses
|
import dataclasses
|
||||||
import json
|
import json
|
||||||
import math
|
import math
|
||||||
import time
|
|
||||||
import uuid
|
import uuid
|
||||||
from dataclasses import dataclass, field
|
from dataclasses import dataclass, field
|
||||||
from enum import Enum
|
from enum import Enum
|
||||||
|
|
@ -1103,39 +1102,34 @@ def _clean_field(name: str, clean_type: CleanType) -> str:
|
||||||
return name.replace('_percentage', '%').replace('_', '-')
|
return name.replace('_percentage', '%').replace('_', '-')
|
||||||
|
|
||||||
|
|
||||||
def _fetch_lsblk_info(dev_path: Optional[Union[Path, str]] = None, retry: int = 3) -> List[LsblkInfo]:
|
def _fetch_lsblk_info(dev_path: Optional[Union[Path, str]] = None) -> List[LsblkInfo]:
|
||||||
fields = [_clean_field(f, CleanType.Lsblk) for f in LsblkInfo.fields()]
|
fields = [_clean_field(f, CleanType.Lsblk) for f in LsblkInfo.fields()]
|
||||||
lsblk_fields = ','.join(fields)
|
cmd = ['lsblk', '--json', '--bytes', '--output', '+' + ','.join(fields)]
|
||||||
|
|
||||||
if not dev_path:
|
if dev_path:
|
||||||
dev_path = ''
|
cmd.append(str(dev_path))
|
||||||
|
|
||||||
for retry_attempt in range(retry + 1):
|
try:
|
||||||
try:
|
result = SysCommand(cmd).decode()
|
||||||
result = SysCommand(f'lsblk --json -b -o+{lsblk_fields} {dev_path}').decode()
|
except SysCallError as err:
|
||||||
break
|
# Get the output minus the message/info from lsblk if it returns a non-zero exit code.
|
||||||
except SysCallError as err:
|
if err.worker:
|
||||||
# Get the output minus the message/info from lsblk if it returns a non-zero exit code.
|
err_str = err.worker.decode()
|
||||||
if err.worker:
|
debug(f'Error calling lsblk: {err_str}')
|
||||||
err_str = err.worker.decode()
|
|
||||||
debug(f'Error calling lsblk: {err_str}')
|
|
||||||
else:
|
|
||||||
raise err
|
|
||||||
|
|
||||||
if retry_attempt == retry:
|
if dev_path:
|
||||||
raise err
|
raise DiskError(f'Failed to read disk "{dev_path}" with lsblk')
|
||||||
|
|
||||||
time.sleep(1)
|
raise err
|
||||||
|
|
||||||
try:
|
try:
|
||||||
block_devices = json.loads(result)
|
block_devices = json.loads(result)
|
||||||
blockdevices = block_devices['blockdevices']
|
|
||||||
return [LsblkInfo.from_json(device) for device in blockdevices]
|
|
||||||
except json.decoder.JSONDecodeError as err:
|
except json.decoder.JSONDecodeError as err:
|
||||||
error(f"Could not decode lsblk JSON: {result}")
|
error(f"Could not decode lsblk JSON: {result}")
|
||||||
raise err
|
raise err
|
||||||
|
|
||||||
raise DiskError(f'Failed to read disk "{dev_path}" with lsblk')
|
blockdevices = block_devices['blockdevices']
|
||||||
|
return [LsblkInfo.from_json(device) for device in blockdevices]
|
||||||
|
|
||||||
|
|
||||||
def get_lsblk_info(dev_path: Union[Path, str]) -> LsblkInfo:
|
def get_lsblk_info(dev_path: Union[Path, str]) -> LsblkInfo:
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue