1
0
mirror of https://github.com/kellyjonbrazil/jc.git synced 2025-06-17 00:07:37 +02:00

add working sfdisk parser

This commit is contained in:
Kelly Brazil
2021-06-30 12:38:36 -07:00
parent d48abf312c
commit db47f35783
15 changed files with 610 additions and 3 deletions

View File

@ -1,5 +1,8 @@
jc changelog
20210630 v1.15.7
- Add sfdisk command parser tested on linux
20210628 v1.15.6
- Fix issue to only load local plugin parsers that have filenames that end in .py

View File

@ -169,6 +169,7 @@ The JSON output can be compact (default) or pretty formatted with the `-p` optio
- `--ps` enables the `ps` command parser ([documentation](https://kellyjonbrazil.github.io/jc/docs/parsers/ps))
- `--route` enables the `route` command parser ([documentation](https://kellyjonbrazil.github.io/jc/docs/parsers/route))
- `--rpm-qi` enables the `rpm -qi` command parser ([documentation](https://kellyjonbrazil.github.io/jc/docs/parsers/rpm_qi))
- `--sfdisk` enables the `sfdisk` command parser ([documentation](https://kellyjonbrazil.github.io/jc/docs/parsers/sfdisk))
- `--shadow` enables the `/etc/shadow` file parser ([documentation](https://kellyjonbrazil.github.io/jc/docs/parsers/shadow))
- `--ss` enables the `ss` command parser ([documentation](https://kellyjonbrazil.github.io/jc/docs/parsers/ss))
- `--stat` enables the `stat` command parser ([documentation](https://kellyjonbrazil.github.io/jc/docs/parsers/stat))

213
docs/parsers/sfdisk.md Normal file
View File

@ -0,0 +1,213 @@
[Home](https://kellyjonbrazil.github.io/jc/)
# jc.parsers.sfdisk
jc - JSON CLI output utility `sfdisk` command output parser
Supports the following `sfdisk` options:
- `-l`
- `-d`
- `-uM`
- `-uC`
- `-uS`
- `-uB`
Usage (cli):
# sfdisk -l | jc --sfdisk
or
# jc sfdisk -l
Usage (module):
import jc.parsers.sfdisk
result = jc.parsers.sfdisk.parse(sfdisk_command_output)
Schema:
[
{
"disk": string,
"cylinders": integer,
"heads": integer,
"sectors_per_track": integer,
"units": string,
"partitions": [
{
"device": string,
"boot": boolean,
"start": integer,
"end": integer,
"size": integer,
"cyls": integer,
"mib": integer,
"blocks": integer,
"sectors": integer,
"id": string,
"system": string
}
]
}
]
Examples:
$ sfdisk -l | jc --sfdisk -p
[
{
"disk": "/dev/sda",
"cylinders": 2610,
"heads": 255,
"sectors_per_track": 63,
"units": "cylinders of 8225280 bytes, blocks of 1024 bytes, counting from 0",
"partitions": [
{
"device": "/dev/sda1",
"boot": true,
"start": 0,
"end": null,
"cyls": null,
"blocks": 1048576,
"id": "83",
"system": "Linux"
},
{
"device": "/dev/sda2",
"boot": false,
"start": 130,
"end": null,
"cyls": null,
"blocks": 19921920,
"id": "8e",
"system": "Linux LVM"
},
{
"device": "/dev/sda3",
"boot": false,
"start": 0,
"end": null,
"cyls": 0,
"blocks": 0,
"id": "0",
"system": "Empty"
},
{
"device": "/dev/sda4",
"boot": false,
"start": 0,
"end": null,
"cyls": 0,
"blocks": 0,
"id": "0",
"system": "Empty"
}
]
},
{
"disk": "/dev/mapper/centos-root",
"cylinders": 2218,
"heads": 255,
"sectors_per_track": 63
},
{
"disk": "/dev/mapper/centos-swap",
"cylinders": 261,
"heads": 255,
"sectors_per_track": 63
}
]
$ sfdisk | jc --sfdisk -p -r
[
{
"disk": "/dev/sda",
"cylinders": "2610",
"heads": "255",
"sectors_per_track": "63",
"units": "cylinders of 8225280 bytes, blocks of 1024 bytes, counting from 0",
"partitions": [
{
"device": "/dev/sda1",
"boot": "*",
"start": "0+",
"end": "130-",
"cyls": "131-",
"blocks": "1048576",
"id": "83",
"system": "Linux"
},
{
"device": "/dev/sda2",
"boot": null,
"start": "130+",
"end": "2610-",
"cyls": "2481-",
"blocks": "19921920",
"id": "8e",
"system": "Linux LVM"
},
{
"device": "/dev/sda3",
"boot": null,
"start": "0",
"end": "-",
"cyls": "0",
"blocks": "0",
"id": "0",
"system": "Empty"
},
{
"device": "/dev/sda4",
"boot": null,
"start": "0",
"end": "-",
"cyls": "0",
"blocks": "0",
"id": "0",
"system": "Empty"
}
]
},
{
"disk": "/dev/mapper/centos-root",
"cylinders": "2218",
"heads": "255",
"sectors_per_track": "63"
},
{
"disk": "/dev/mapper/centos-swap",
"cylinders": "261",
"heads": "255",
"sectors_per_track": "63"
}
]
## info
```python
info()
```
Provides parser metadata (version, author, etc.)
## parse
```python
parse(data, raw=False, quiet=False)
```
Main text parsing function
Parameters:
data: (string) text data to parse
raw: (boolean) output preprocessed JSON if True
quiet: (boolean) suppress warning messages if True
Returns:
List of Dictionaries. Raw or processed structured data.
## Parser Information
Compatibility: linux
Version 1.0 by Kelly Brazil (kellyjonbrazil@gmail.com)

View File

@ -86,4 +86,4 @@ Module Example:
"""
name = 'jc'
__version__ = '1.15.6'
__version__ = '1.15.7'

View File

@ -94,6 +94,7 @@ parsers = [
'ps',
'route',
'rpm-qi',
'sfdisk',
'shadow',
'ss',
'stat',

Binary file not shown.

325
jc/parsers/sfdisk.py Normal file
View File

@ -0,0 +1,325 @@
"""jc - JSON CLI output utility `sfdisk` command output parser
Supports the following `sfdisk` options:
- `-l`
- `-d`
- `-uM`
- `-uC`
- `-uS`
- `-uB`
Usage (cli):
# sfdisk -l | jc --sfdisk
or
# jc sfdisk -l
Usage (module):
import jc.parsers.sfdisk
result = jc.parsers.sfdisk.parse(sfdisk_command_output)
Schema:
[
{
"disk": string,
"cylinders": integer,
"heads": integer,
"sectors_per_track": integer,
"units": string,
"partitions": [
{
"device": string,
"boot": boolean,
"start": integer,
"end": integer,
"size": integer,
"cyls": integer,
"mib": integer,
"blocks": integer,
"sectors": integer,
"id": string,
"system": string
}
]
}
]
Examples:
$ sfdisk -l | jc --sfdisk -p
[
{
"disk": "/dev/sda",
"cylinders": 2610,
"heads": 255,
"sectors_per_track": 63,
"units": "cylinders of 8225280 bytes, blocks of 1024 bytes, counting from 0",
"partitions": [
{
"device": "/dev/sda1",
"boot": true,
"start": 0,
"end": null,
"cyls": null,
"blocks": 1048576,
"id": "83",
"system": "Linux"
},
{
"device": "/dev/sda2",
"boot": false,
"start": 130,
"end": null,
"cyls": null,
"blocks": 19921920,
"id": "8e",
"system": "Linux LVM"
},
{
"device": "/dev/sda3",
"boot": false,
"start": 0,
"end": null,
"cyls": 0,
"blocks": 0,
"id": "0",
"system": "Empty"
},
{
"device": "/dev/sda4",
"boot": false,
"start": 0,
"end": null,
"cyls": 0,
"blocks": 0,
"id": "0",
"system": "Empty"
}
]
},
{
"disk": "/dev/mapper/centos-root",
"cylinders": 2218,
"heads": 255,
"sectors_per_track": 63
},
{
"disk": "/dev/mapper/centos-swap",
"cylinders": 261,
"heads": 255,
"sectors_per_track": 63
}
]
$ sfdisk | jc --sfdisk -p -r
[
{
"disk": "/dev/sda",
"cylinders": "2610",
"heads": "255",
"sectors_per_track": "63",
"units": "cylinders of 8225280 bytes, blocks of 1024 bytes, counting from 0",
"partitions": [
{
"device": "/dev/sda1",
"boot": "*",
"start": "0+",
"end": "130-",
"cyls": "131-",
"blocks": "1048576",
"id": "83",
"system": "Linux"
},
{
"device": "/dev/sda2",
"boot": null,
"start": "130+",
"end": "2610-",
"cyls": "2481-",
"blocks": "19921920",
"id": "8e",
"system": "Linux LVM"
},
{
"device": "/dev/sda3",
"boot": null,
"start": "0",
"end": "-",
"cyls": "0",
"blocks": "0",
"id": "0",
"system": "Empty"
},
{
"device": "/dev/sda4",
"boot": null,
"start": "0",
"end": "-",
"cyls": "0",
"blocks": "0",
"id": "0",
"system": "Empty"
}
]
},
{
"disk": "/dev/mapper/centos-root",
"cylinders": "2218",
"heads": "255",
"sectors_per_track": "63"
},
{
"disk": "/dev/mapper/centos-swap",
"cylinders": "261",
"heads": "255",
"sectors_per_track": "63"
}
]
"""
import jc.utils
import jc.parsers.universal
class info():
"""Provides parser metadata (version, author, etc.)"""
version = '1.0'
description = '`sfdisk` command parser'
author = 'Kelly Brazil'
author_email = 'kellyjonbrazil@gmail.com'
compatible = ['linux']
magic_commands = ['sfdisk']
__version__ = info.version
def _process(proc_data):
"""
Final processing to conform to the schema.
Parameters:
proc_data: (List of Dictionaries) raw structured data to process
Returns:
List of Dictionaries. Structured to conform to the schema.
"""
int_list = ['cylinders', 'heads', 'sectors_per_track', 'start', 'end', 'size', 'cyls', 'mib',
'blocks', 'sectors']
bool_list = ['boot']
for entry in proc_data:
for key in entry:
if key in int_list:
entry[key] = jc.utils.convert_to_int(entry[key])
if 'partitions' in entry:
for tp in entry['partitions']:
for key in tp:
if key in int_list:
tp[key] = jc.utils.convert_to_int(tp[key])
if key in bool_list:
tp[key] = jc.utils.convert_to_bool(tp[key])
return proc_data
def parse(data, raw=False, quiet=False):
"""
Main text parsing function
Parameters:
data: (string) text data to parse
raw: (boolean) output preprocessed JSON if True
quiet: (boolean) suppress warning messages if True
Returns:
List of Dictionaries. Raw or processed structured data.
"""
if not quiet:
jc.utils.compatibility(__name__, info.compatible)
raw_output = []
item = {}
partitions = []
option = ''
section = ''
if jc.utils.has_data(data):
for line in data.splitlines():
if line.startswith('# partition table of'):
if item:
raw_output.append(item)
item = {}
partitions = []
option = 'd'
item['disk'] = line.split()[4]
continue
if option == 'd':
if line.startswith('unit: '):
item['units'] = line.split()[1]
section = 'partitions'
continue
if section == 'partitions' and line:
part = {}
part['device'] = line.split()[0]
line = line.replace(',', ' ').replace('=', ' ')
part['start'] = line.split()[3]
part['size'] = line.split()[5]
part['id'] = line.split()[7]
part['boot'] = '*' if 'bootable' in line else None
partitions.append(part)
item['partitions'] = partitions
continue
else:
if line.startswith('Disk '):
if item:
raw_output.append(item)
item = {}
partitions = []
line = line.replace(':', '').replace(',', '')
item['disk'] = line.split()[1]
item['cylinders'] = line.split()[2]
item['heads'] = line.split()[4]
item['sectors_per_track'] = line.split()[6]
continue
if line.startswith('Units: '):
item['units'] = line.split(':')[1].strip()
continue
if 'Device' in line and 'Boot' in line and 'Start' in line and 'End' in line:
section = 'partitions'
partitions.append(line.lower().replace('#', ' '))
continue
if section == 'partitions' and line:
partitions.append(line)
continue
if section == 'partitions' and line == '':
item['partitions'] = jc.parsers.universal.sparse_table_parse(partitions)
section = ''
partitions = []
continue
if item:
raw_output.append(item)
if raw:
return raw_output
else:
return _process(raw_output)

View File

@ -154,7 +154,7 @@ def convert_to_bool(value):
# if float converts, then bool the result
# if float does not convert then look for truthy string and bool True
# else False
truthy = ['y', 'yes', 'true']
truthy = ['y', 'yes', 'true', '*']
if isinstance(value, (int, float)):
return bool(value)

Binary file not shown.

View File

@ -5,7 +5,7 @@ with open('README.md', 'r') as f:
setuptools.setup(
name='jc',
version='1.15.6',
version='1.15.7',
author='Kelly Brazil',
author_email='kellyjonbrazil@gmail.com',
description='Converts the output of popular command-line tools and file-types to JSON.',

View File

@ -0,0 +1,8 @@
# partition table of /dev/sda
unit: sectors
/dev/sda1 : start= 2048, size= 2097152, Id=83, bootable
/dev/sda2 : start= 2099200, size= 39843840, Id=8e
/dev/sda3 : start= 0, size= 0, Id= 0
/dev/sda4 : start= 0, size= 0, Id= 0

14
tests/fixtures/centos-7.7/sfdisk-l.out vendored Normal file
View File

@ -0,0 +1,14 @@
Disk /dev/sda: 2610 cylinders, 255 heads, 63 sectors/track
Units: cylinders of 8225280 bytes, blocks of 1024 bytes, counting from 0
Device Boot Start End #cyls #blocks Id System
/dev/sda1 * 0+ 130- 131- 1048576 83 Linux
/dev/sda2 130+ 2610- 2481- 19921920 8e Linux LVM
/dev/sda3 0 - 0 0 0 Empty
/dev/sda4 0 - 0 0 0 Empty
Disk /dev/mapper/centos-root: 2218 cylinders, 255 heads, 63 sectors/track
Disk /dev/mapper/centos-swap: 261 cylinders, 255 heads, 63 sectors/track

View File

@ -0,0 +1,14 @@
Disk /dev/sda: 2610 cylinders, 255 heads, 63 sectors/track
Units: blocks of 1024 bytes, counting from 0
Device Boot Start End #blocks Id System
/dev/sda1 * 1024 1049599 1048576 83 Linux
/dev/sda2 1049600 20971519 19921920 8e Linux LVM
/dev/sda3 0 - 0 0 Empty
/dev/sda4 0 - 0 0 Empty
Disk /dev/mapper/centos-root: 2218 cylinders, 255 heads, 63 sectors/track
Disk /dev/mapper/centos-swap: 261 cylinders, 255 heads, 63 sectors/track

View File

@ -0,0 +1,14 @@
Disk /dev/sda: 2610 cylinders, 255 heads, 63 sectors/track
Units: 1MiB = 1024*1024 bytes, blocks of 1024 bytes, counting from 0
Device Boot Start End MiB #blocks Id System
/dev/sda1 * 1 1024 1024 1048576 83 Linux
/dev/sda2 1025 20479 19455 19921920 8e Linux LVM
/dev/sda3 0 - 0 0 0 Empty
/dev/sda4 0 - 0 0 0 Empty
Disk /dev/mapper/centos-root: 2218 cylinders, 255 heads, 63 sectors/track
Disk /dev/mapper/centos-swap: 261 cylinders, 255 heads, 63 sectors/track

View File

@ -0,0 +1,14 @@
Disk /dev/sda: 2610 cylinders, 255 heads, 63 sectors/track
Units: sectors of 512 bytes, counting from 0
Device Boot Start End #sectors Id System
/dev/sda1 * 2048 2099199 2097152 83 Linux
/dev/sda2 2099200 41943039 39843840 8e Linux LVM
/dev/sda3 0 - 0 0 Empty
/dev/sda4 0 - 0 0 Empty
Disk /dev/mapper/centos-root: 2218 cylinders, 255 heads, 63 sectors/track
Disk /dev/mapper/centos-swap: 261 cylinders, 255 heads, 63 sectors/track