Metadata-Version: 2.4
Name: hexconv
Version: 0.2.0
Summary: Pythonic conversion toolkit for bytes, hex, integers, arrays, binary strings, base64, and text.
Author: hexconv contributors
License-Expression: MIT
Keywords: hex,bytes,binary,base64,conversion,encoding,toolkit
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Developers
Classifier: Operating System :: OS Independent
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3 :: Only
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Programming Language :: Python :: 3.14
Classifier: Topic :: Software Development :: Libraries :: Python Modules
Classifier: Topic :: Utilities
Classifier: Typing :: Typed
Requires-Python: >=3.10
Description-Content-Type: text/markdown
License-File: LICENSE
Provides-Extra: dev
Requires-Dist: build; extra == "dev"
Requires-Dist: pytest; extra == "dev"
Requires-Dist: twine; extra == "dev"
Dynamic: license-file

# hexconv

`hexconv` is a small, dependency-free Python conversion toolkit for working with
bytes, byte arrays, hex strings, hex arrays, integers, integer arrays, bytes
literals, binary strings, base64, and raw text.

The main idea is: explicitly state what you have, then ask for what you want.

```python
import hexconv as hx

hx.from_hex("dead beef").to_bytes()
# b'\xde\xad\xbe\xef'

hx.from_hex("dead beef").bytes
# b'\xde\xad\xbe\xef'

hx.from_bytes_array([0xde, 0xad, 0xbe, 0xef]).to_hex()
# 'deadbeef'

hx.from_bytes_array([0xde, 0xad, 0xbe, 0xef]).hex
# 'deadbeef'

hx.from_text("data").to_hex_array(prefix=True)
# ['0x64', '0x61', '0x74', '0x61']

hx.from_int(0xdeadbeef).to_bytes()
# b'\xde\xad\xbe\xef'

hx.from_int_array([0x1234, 0x5678], width=2).to_hex_array(width=2)
# ['1234', '5678']
```

## Configurable formats

For reusable conversions, construct format specs with options:

```python
hx.convert("de ad be ef", from_=hx.Hex(), to=hx.Bytes())
# b'\xde\xad\xbe\xef'

hx.convert("data", from_=hx.Text(), to=hx.Hex(prefix=True))
# '0x64617461'

hx.convert("π", from_=hx.Text(encoding="utf-8"), to=hx.Hex())
# 'cf80'

hx.convert("-_8", from_=hx.Base64(urlsafe=True, padding=False), to=hx.Hex())
# 'fbff'
```

Old marker-style conversions still work:

```python
hx.convert("data", from_=hx.Text, to=hx.HexString)
# '64617461'
```

## Composable pipelines

Use `pipeline()` when you want a readable builder:

```python
conv = (
    hx.pipeline()
    .from_(hx.Hex())
    .chunk(2)
    .to(hx.IntArray(width=2))
)

conv("12345678")
# [4660, 22136]
```

Use `>>` when you want compact composition:

```python
conv = hx.Hex() >> hx.Chunk(2) >> hx.HexArray()

conv("12345678")
# ['1234', '5678']
```

Available transforms:

- `Chunk(width, strict=True)` / `Group(width, strict=True)` — set downstream grouping.
- `Pad.left(width=..., byte=0)` / `Pad.right(block_size=..., byte=0)` — pad bytes.
- `Reverse()` — reverse byte order.

Examples:

```python
(hx.Hex() >> hx.Pad.left(width=4) >> hx.Hex())("dead")
# '0000dead'

(hx.Hex() >> hx.Reverse() >> hx.Hex())("deadbeef")
# 'efbeadde'
```

## Why explicit source helpers?

Some inputs are impossible to infer safely:

```python
"face"
```

That could be ASCII text (`66 61 63 65`) or hex bytes (`fa ce`). So `hexconv`
keeps the safe path explicit:

```python
hx.from_text("face").to_hex()
# '66616365'

hx.from_hex("face").to_bytes()
# b'\xfa\xce'
```

If you do want convenience heuristics, use `from_auto`:

```python
hx.from_auto("0xdeadbeef").to_int()
# 3735928559
```

## Converter API

If you prefer a reusable converter object, use marker classes:

```python
conv = hx.Converter(hx.BytesArray, hx.HexArray)
conv([0xde, 0xad, 0xbe, 0xef])
# ['de', 'ad', 'be', 'ef']

hx.convert("data", from_=hx.Text, to=hx.HexString)
# '64617461'
```

For conversions with options, pass input and output option dictionaries:

```python
conv = hx.Converter(
    hx.DecimalIntArray,
    hx.HexArray,
    input_options={"width": 2},
    output_options={"width": 2, "prefix": True},
)

conv([4660, 22136])
# ['0x1234', '0x5678']
```

## Extra formats

Base encodings:

```python
hx.from_text("data").to(hx.Base32(padding=False))
# 'MRQXIYI'

hx.from_text("data").to(hx.Base85())
# 'WMOn+'

hx.from_text("data").to(hx.Ascii85())
# 'A79Rg'
```

Escaped byte strings:

```python
hx.from_escaped(r"\xde\xad").hex
# 'dead'

hx.from_hex("dead").to(hx.Escaped())
# '\\xde\\xad'
```

Hexdump:

```python
dump = hx.from_hex("deadbeef").to(hx.Hexdump(width=2))
hx.from_hexdump(dump).hex
# 'deadbeef'
```

Python `struct` packing/unpacking:

```python
hx.from_struct((0x1234, 0x5678), fmt=">HH").hex
# '12345678'

hx.from_hex("12345678").to(hx.Struct(">HH"))
# (4660, 22136)
```

Bits:

```python
hx.from_bits([1, 0, 1]).hex
# '05'

hx.from_hex("05").to(hx.Bits())
# [0, 0, 0, 0, 0, 1, 0, 1]
```

Automatic inference with explanations:

```python
result = hx.infer("0xdead")
result.format, result.confidence, result.value.hex
# (<class 'hexconv._core.HexString'>, 0.75, 'dead')
```

## Supported source helpers

- `from_bytes(value)`
- `from_bytes_array(values)`
- `from_bytes_string(value)` for strings like `"b'\\xde\\xad'"`
- `from_hex(value)`
- `from_hex_array(values)`
- `from_hex_int(value)`
- `from_int(value)`
- `from_int_array(values, width=...)`
- `from_text(value)`
- `from_binary(value)`
- `from_base64(value)`
- `from_base32(value)`
- `from_base85(value)`
- `from_ascii85(value)`
- `from_escaped(value)`
- `from_hexdump(value)`
- `from_struct(value, fmt=...)`
- `from_bits(value)`
- `from_auto(value)`
- `infer(value)`

## Common output methods

- `to_bytes()`
- `to_bytearray()`
- `to_bytes_array()`
- `to_bytes_string()`
- `to_hex(sep="", prefix=False, uppercase=False)`
- `to_hex_array(width=1, prefix=False, uppercase=False)`
- `to_hex_numbers(width=1)`
- `to_int(endian="big", signed=False)`
- `to_int_array(width=1, endian="big", signed=False)`
- `to_text(encoding="ascii", errors="strict")`
- `to_binary(sep="")`
- `to_base64()`
- `to_base32()`
- `to_base85()`
- `to_ascii85()`
- `to_escaped()`
- `to_hexdump()`
- `to_struct(fmt)`
- `to_bits()`
- `to(format_marker, **options)`
