# human errors
humans do make some errors, so we should show it to them, so that it can be fixed
## usage:
### json/orjson
```py
from human_errors import json_dump
import orjson
try:
with open("config.json", "r") as file:
config = orjson.loads(file.read())
except orjson.JSONDecodeError as exc:
json_dump(exc, "config.json")
```
Output (error):
```
--> C:\Users\<user>\absolute\path\to\config.json:19:5
17 │ "path": "$DESKTOP"
18 │ }
╭╴19 │ {
│ │ ↑
│ 20 │ "name": "Pictures",
│ 21 │ "path": "$PICTURES"
╰────❯ unexpected character
```
### tomllib (>=3.14) or toml
if you want to use tomllib, python >= 3.14 must be used so that the message and line + column numbers can be extracted.
```py
from human_errors import toml_dump
import toml
try:
with open("pyproject.toml", "r") as file:
config = toml.loads(file.read())
except toml.TomlDecodeError as exc:
toml_dump(exc, "pyproject.toml")
```
Output (error):
```
--> C:\Users\<user>\path\to\pyproject.toml:9:26
7 │ { name = "<name>", email = "<email>" }
8 │ ]
╭╴ 9 │ requires-python = ">=3.12
│ │ ↑
│ 10 │ dependencies = [
│ 11 │ "rich>=14.2.0",
╰────❯ Unbalanced quotes
```
### Base Renderer (Custom Errors)
For custom error handling or any file-based errors not covered by the built-in renderers:
```py
from human_errors.base_renderer import dump
def validate_config(file_path: str):
with open(file_path, "r") as f:
for line_num, line in enumerate(f, start=1):
if "TODO" in line:
col = line.index("TODO") + 1
dump(
doc_path=file_path,
cause="TODO found in production config",
line_number=line_num,
column_number=col,
context=3,
extra=[
"Production configs should not contain TODO items",
"Please replace with actual values or remove this entry"
]
)
exit(1)
```
Output (error):
```
--> C:\Users\<user>\absolute\path\to\config.py:15:9
12 │ DATABASE_HOST = "localhost"
13 │ DATABASE_PORT = 5432
14 │
╭╴15 │ API_KEY = "TODO: add production key"
│ │ ↑
│ 16 │
│ 17 │ CACHE_ENABLED = True
│ 18 │ CACHE_TTL = 3600
╰─────❯ TODO found in production config
╭───────────────────────────────────────────────────────────╮
│ Production configs should not contain TODO items │
├───────────────────────────────────────────────────────────┤
│ Please replace with actual values or remove this entry │
╰───────────────────────────────────────────────────────────╯
```
more soon i guess
## contributing
any extra data format must be in an extra, and also available in the `all` group
any contributions must pre-lint with `ruff` and `ty`
```sh
uv run ruff check --unsafe-fixes --fix
uv run ty check
```
adding support for pytest is also fine
<div align="center">
<h1>( ̄︶ ̄)↗ give a star</h1>
</div>
Raw data
{
"_id": null,
"home_page": null,
"name": "human-errors",
"maintainer": null,
"docs_url": null,
"requires_python": ">=3.12",
"maintainer_email": null,
"keywords": "exception, config, json, yaml, toml",
"author": "NSPC911",
"author_email": null,
"download_url": "https://files.pythonhosted.org/packages/3e/5b/547d64dab7efa6bb14815fc8ee0a4ab7869bf9f37a0880fa3298259c6add/human_errors-0.0.2.post1.tar.gz",
"platform": null,
"description": "# human errors\r\n\r\nhumans do make some errors, so we should show it to them, so that it can be fixed\r\n\r\n## usage:\r\n\r\n### json/orjson\r\n\r\n```py\r\nfrom human_errors import json_dump\r\nimport orjson\r\n\r\ntry:\r\n with open(\"config.json\", \"r\") as file:\r\n config = orjson.loads(file.read())\r\nexcept orjson.JSONDecodeError as exc:\r\n json_dump(exc, \"config.json\")\r\n```\r\n\r\nOutput (error):\r\n```\r\n --> C:\\Users\\<user>\\absolute\\path\\to\\config.json:19:5\r\n 17 \u2502 \"path\": \"$DESKTOP\"\r\n 18 \u2502 }\r\n\u256d\u257419 \u2502 {\r\n\u2502 \u2502 \u2191\r\n\u2502 20 \u2502 \"name\": \"Pictures\",\r\n\u2502 21 \u2502 \"path\": \"$PICTURES\"\r\n\u2570\u2500\u2500\u2500\u2500\u276f unexpected character\r\n```\r\n\r\n### tomllib (>=3.14) or toml\r\nif you want to use tomllib, python >= 3.14 must be used so that the message and line + column numbers can be extracted.\r\n```py\r\nfrom human_errors import toml_dump\r\nimport toml\r\ntry:\r\n with open(\"pyproject.toml\", \"r\") as file:\r\n config = toml.loads(file.read())\r\nexcept toml.TomlDecodeError as exc:\r\n toml_dump(exc, \"pyproject.toml\")\r\n```\r\n\r\nOutput (error):\r\n```\r\n --> C:\\Users\\<user>\\path\\to\\pyproject.toml:9:26\r\n 7 \u2502 { name = \"<name>\", email = \"<email>\" }\r\n 8 \u2502 ]\r\n\u256d\u2574 9 \u2502 requires-python = \">=3.12\r\n\u2502 \u2502 \u2191\r\n\u2502 10 \u2502 dependencies = [\r\n\u2502 11 \u2502 \"rich>=14.2.0\",\r\n\u2570\u2500\u2500\u2500\u2500\u276f Unbalanced quotes\r\n```\r\n\r\n### Base Renderer (Custom Errors)\r\n\r\nFor custom error handling or any file-based errors not covered by the built-in renderers:\r\n\r\n```py\r\nfrom human_errors.base_renderer import dump\r\n\r\ndef validate_config(file_path: str):\r\n with open(file_path, \"r\") as f:\r\n for line_num, line in enumerate(f, start=1):\r\n if \"TODO\" in line:\r\n col = line.index(\"TODO\") + 1\r\n dump(\r\n doc_path=file_path,\r\n cause=\"TODO found in production config\",\r\n line_number=line_num,\r\n column_number=col,\r\n context=3,\r\n extra=[\r\n \"Production configs should not contain TODO items\",\r\n \"Please replace with actual values or remove this entry\"\r\n ]\r\n )\r\n exit(1)\r\n```\r\n\r\nOutput (error):\r\n```\r\n --> C:\\Users\\<user>\\absolute\\path\\to\\config.py:15:9\r\n 12 \u2502 DATABASE_HOST = \"localhost\"\r\n 13 \u2502 DATABASE_PORT = 5432\r\n 14 \u2502\r\n\u256d\u257415 \u2502 API_KEY = \"TODO: add production key\"\r\n\u2502 \u2502 \u2191\r\n\u2502 16 \u2502\r\n\u2502 17 \u2502 CACHE_ENABLED = True\r\n\u2502 18 \u2502 CACHE_TTL = 3600\r\n\u2570\u2500\u2500\u2500\u2500\u2500\u276f TODO found in production config\r\n \u256d\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u256e\r\n \u2502 Production configs should not contain TODO items \u2502\r\n \u251c\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2524\r\n \u2502 Please replace with actual values or remove this entry \u2502\r\n \u2570\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u256f\r\n```\r\n\r\nmore soon i guess\r\n\r\n## contributing\r\n\r\nany extra data format must be in an extra, and also available in the `all` group\r\n\r\nany contributions must pre-lint with `ruff` and `ty`\r\n\r\n```sh\r\nuv run ruff check --unsafe-fixes --fix\r\nuv run ty check\r\n```\r\n\r\nadding support for pytest is also fine\r\n\r\n<div align=\"center\">\r\n <h1>\uff08\uffe3\ufe36\uffe3\uff09\u2197 give a star</h1>\r\n</div>\r\n",
"bugtrack_url": null,
"license": "MIT",
"summary": "everyone makes mistakes, show the errors to them ",
"version": "0.0.2.post1",
"project_urls": {
"Issues": "https://github.com/NSPC911/human-errors/issues",
"Source": "https://github.com/NSPC911/human-errors"
},
"split_keywords": [
"exception",
" config",
" json",
" yaml",
" toml"
],
"urls": [
{
"comment_text": null,
"digests": {
"blake2b_256": "f6ce11730457d84bd2ad432bfc4c4607c76eb9206d1f74356ec2fd0c3a778f5a",
"md5": "5f988298079ad9f5c7d031ebfb75ce1e",
"sha256": "cc2719a0d4de78a8446066c18acbb9c9a4757020e32ba99d2253af865dd62c90"
},
"downloads": -1,
"filename": "human_errors-0.0.2.post1-py3-none-any.whl",
"has_sig": false,
"md5_digest": "5f988298079ad9f5c7d031ebfb75ce1e",
"packagetype": "bdist_wheel",
"python_version": "py3",
"requires_python": ">=3.12",
"size": 8171,
"upload_time": "2025-11-02T18:46:43",
"upload_time_iso_8601": "2025-11-02T18:46:43.534290Z",
"url": "https://files.pythonhosted.org/packages/f6/ce/11730457d84bd2ad432bfc4c4607c76eb9206d1f74356ec2fd0c3a778f5a/human_errors-0.0.2.post1-py3-none-any.whl",
"yanked": false,
"yanked_reason": null
},
{
"comment_text": null,
"digests": {
"blake2b_256": "3e5b547d64dab7efa6bb14815fc8ee0a4ab7869bf9f37a0880fa3298259c6add",
"md5": "db985b4349883ae15544362fc2622287",
"sha256": "d75f71569f875c574a94f1d7721748817bac64c895db22904e1177346793c23d"
},
"downloads": -1,
"filename": "human_errors-0.0.2.post1.tar.gz",
"has_sig": false,
"md5_digest": "db985b4349883ae15544362fc2622287",
"packagetype": "sdist",
"python_version": "source",
"requires_python": ">=3.12",
"size": 5919,
"upload_time": "2025-11-02T18:46:44",
"upload_time_iso_8601": "2025-11-02T18:46:44.622560Z",
"url": "https://files.pythonhosted.org/packages/3e/5b/547d64dab7efa6bb14815fc8ee0a4ab7869bf9f37a0880fa3298259c6add/human_errors-0.0.2.post1.tar.gz",
"yanked": false,
"yanked_reason": null
}
],
"upload_time": "2025-11-02 18:46:44",
"github": true,
"gitlab": false,
"bitbucket": false,
"codeberg": false,
"github_user": "NSPC911",
"github_project": "human-errors",
"travis_ci": false,
"coveralls": false,
"github_actions": false,
"lcname": "human-errors"
}