speedy-utils 1.1.43__tar.gz → 1.1.45__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (147) hide show
  1. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/PKG-INFO +158 -8
  2. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/README.md +157 -7
  3. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/pyproject.toml +1 -1
  4. speedy_utils-1.1.45/scripts/bug.py +12 -0
  5. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/test_locals.py +1 -2
  6. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/test_ray_locals.py +1 -2
  7. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/llm.py +3 -0
  8. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/__init__.py +6 -0
  9. speedy_utils-1.1.45/src/speedy_utils/common/utils_error.py +261 -0
  10. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/multi_worker/process.py +25 -18
  11. speedy_utils-1.1.43/scripts/bug.py +0 -34
  12. speedy_utils-1.1.43/test_s3.py +0 -34
  13. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.githooks/pre-push +0 -0
  14. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/copilot-instructions.md +0 -0
  15. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/prompts/improveParallelErrorHandling.prompt.md +0 -0
  16. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/caching-utilities/SKILL.md +0 -0
  17. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/caching-utilities/examples/caching_example.py +0 -0
  18. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/io-utilities/SKILL.md +0 -0
  19. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/io-utilities/examples/io_example.py +0 -0
  20. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/llm-integration/SKILL.md +0 -0
  21. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/llm-integration/examples/llm_example.py +0 -0
  22. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/multi-threading-processing/SKILL.md +0 -0
  23. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/ray-distributed-computing/SKILL.md +0 -0
  24. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/skill-creation/SKILL.md +0 -0
  25. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/vision-utilities/SKILL.md +0 -0
  26. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/skills/vision-utilities/examples/vision_example.py +0 -0
  27. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.github/workflows/publish.yml +0 -0
  28. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.gitignore +0 -0
  29. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/.pre-commit-config.yaml +0 -0
  30. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/AGENTS.md +0 -0
  31. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/bumpversion.sh +0 -0
  32. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/debug/debug_generate_response.py +0 -0
  33. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/debug/debug_n_param.py +0 -0
  34. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/debug/debug_n_structure.py +0 -0
  35. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/debug/integration_test.py +0 -0
  36. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/debug/test_decode_api.py +0 -0
  37. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/debug/test_endpoints.py +0 -0
  38. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/debug/test_generate.py +0 -0
  39. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/debug/test_generate_endpoint.py +0 -0
  40. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/docs/GENERATE_QUICKREF.md +0 -0
  41. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/docs/IMPLEMENTATION.md +0 -0
  42. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/docs/QUICKSTART.md +0 -0
  43. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/docs/TOKENIZATION.md +0 -0
  44. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/docs/TOKENIZATION_IMPLEMENTATION.md +0 -0
  45. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/docs/zero_copy_sharing.md +0 -0
  46. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/examples/generate_example.py +0 -0
  47. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/examples/llm_ray_example.py +0 -0
  48. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/examples/pytorch_large_model.py +0 -0
  49. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/examples/shared_kwargs_example.py +0 -0
  50. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/examples/temperature_range_example.py +0 -0
  51. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/examples/test_parallel_gpu.py +0 -0
  52. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/examples/test_share_ray.py +0 -0
  53. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/examples/tokenization_example.py +0 -0
  54. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/examples/vision_utils_example.py +0 -0
  55. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/experiments/exp1/dockerfile +0 -0
  56. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/experiments/exp1/run_in_docker.sh +0 -0
  57. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/experiments/exp1/test.png +0 -0
  58. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/experiments/test_read_image.py +0 -0
  59. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/notebooks/README.ipynb +0 -0
  60. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/notebooks/llm_utils/llm_as_a_judge.ipynb +0 -0
  61. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/notebooks/parallel_gpu_pool.ipynb +0 -0
  62. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/notebooks/ray_tutorial.ipynb +0 -0
  63. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/notebooks/test_multi_thread.ipynb +0 -0
  64. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/ruff.toml +0 -0
  65. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/bug_simple.py +0 -0
  66. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/debug_import_time.py +0 -0
  67. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/deploy.sh +0 -0
  68. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/imports.sh +0 -0
  69. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/test.py +0 -0
  70. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/test_both_backends.py +0 -0
  71. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/test_error_handling.py +0 -0
  72. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/test_import_time_vision.py +0 -0
  73. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/scripts/test_ray_mp.py +0 -0
  74. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/setup.cfg +0 -0
  75. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/datasets_utils/convert_to_arrow.py +0 -0
  76. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/__init__.py +0 -0
  77. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/chat_format/__init__.py +0 -0
  78. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/chat_format/display.py +0 -0
  79. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/chat_format/transform.py +0 -0
  80. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/chat_format/utils.py +0 -0
  81. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/group_messages.py +0 -0
  82. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/llm_ray.py +0 -0
  83. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/__init__.py +0 -0
  84. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/async_lm/__init__.py +0 -0
  85. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/async_lm/_utils.py +0 -0
  86. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/async_lm/async_llm_task.py +0 -0
  87. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/async_lm/async_lm.py +0 -0
  88. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/async_lm/async_lm_base.py +0 -0
  89. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/async_lm/lm_specific.py +0 -0
  90. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/base_prompt_builder.py +0 -0
  91. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/llm_signature.py +0 -0
  92. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/lm_base.py +0 -0
  93. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/mixins.py +0 -0
  94. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/openai_memoize.py +0 -0
  95. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/signature.py +0 -0
  96. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/lm/utils.py +0 -0
  97. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/scripts/README.md +0 -0
  98. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/scripts/fast_vllm.py +0 -0
  99. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/scripts/vllm_load_balancer.py +0 -0
  100. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/scripts/vllm_serve.py +0 -0
  101. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/vector_cache/__init__.py +0 -0
  102. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/vector_cache/cli.py +0 -0
  103. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/vector_cache/core.py +0 -0
  104. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/vector_cache/types.py +0 -0
  105. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/llm_utils/vector_cache/utils.py +0 -0
  106. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/__imports.py +0 -0
  107. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/__init__.py +0 -0
  108. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/clock.py +0 -0
  109. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/function_decorator.py +0 -0
  110. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/logger.py +0 -0
  111. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/notebook_utils.py +0 -0
  112. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/patcher.py +0 -0
  113. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/report_manager.py +0 -0
  114. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/utils_cache.py +0 -0
  115. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/utils_io.py +0 -0
  116. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/utils_misc.py +0 -0
  117. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/common/utils_print.py +0 -0
  118. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/multi_worker/__init__.py +0 -0
  119. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/multi_worker/dataset_ray.py +0 -0
  120. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/multi_worker/parallel_gpu_pool.py +0 -0
  121. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/multi_worker/progress.py +0 -0
  122. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/multi_worker/thread.py +0 -0
  123. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/scripts/__init__.py +0 -0
  124. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/scripts/mpython.py +0 -0
  125. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/speedy_utils/scripts/openapi_client_codegen.py +0 -0
  126. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/vision_utils/README.md +0 -0
  127. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/vision_utils/__init__.py +0 -0
  128. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/vision_utils/io_utils.py +0 -0
  129. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/src/vision_utils/plot.py +0 -0
  130. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/import_all.py +0 -0
  131. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/import_time_report.py +0 -0
  132. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/integration_test.py +0 -0
  133. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/llm_utils/test_llm_mixins.py +0 -0
  134. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/sample_objects.py +0 -0
  135. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test.py +0 -0
  136. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_logger.py +0 -0
  137. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_logger_format.py +0 -0
  138. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_memoize_typing.py +0 -0
  139. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_mpython.py +0 -0
  140. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_multithread_error_trace.py +0 -0
  141. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_process.py +0 -0
  142. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_process_update.py +0 -0
  143. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_pytorch_sharing.py +0 -0
  144. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_shared_kwargs.py +0 -0
  145. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_thread.py +0 -0
  146. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/tests/test_tokenization.py +0 -0
  147. {speedy_utils-1.1.43 → speedy_utils-1.1.45}/uv.lock +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: speedy-utils
3
- Version: 1.1.43
3
+ Version: 1.1.45
4
4
  Summary: Fast and easy-to-use package for data science
5
5
  Project-URL: Homepage, https://github.com/anhvth/speedy
6
6
  Project-URL: Repository, https://github.com/anhvth/speedy
@@ -58,13 +58,49 @@ Description-Content-Type: text/markdown
58
58
 
59
59
  **Speedy Utils** is a Python utility library designed to streamline common programming tasks such as caching, parallel processing, file I/O, and data manipulation. It provides a collection of decorators, functions, and classes to enhance productivity and performance in your Python projects.
60
60
 
61
+ ## 🚀 Recent Updates (January 27, 2026)
62
+
63
+ **Enhanced Error Handling in Parallel Processing:**
64
+
65
+ - Rich-formatted error tracebacks with code context and syntax highlighting
66
+ - Three error handling modes: 'raise', 'ignore', and 'log'
67
+ - Filtered tracebacks focusing on user code (hiding infrastructure)
68
+ - Real-time progress reporting with error/success statistics
69
+ - Automatic error logging to timestamped files
70
+ - Caller frame information showing where parallel functions were invoked
71
+
72
+ ## Quick Start
73
+
74
+ ### Parallel Processing with Error Handling
75
+
76
+ ```python
77
+ from speedy_utils import multi_thread, multi_process
78
+
79
+ # Simple parallel processing
80
+ results = multi_thread(lambda x: x * 2, [1, 2, 3, 4, 5])
81
+ # Results: [2, 4, 6, 8, 10]
82
+
83
+ # Robust processing with error handling
84
+ def process_item(item):
85
+ if item == 3:
86
+ raise ValueError(f"Cannot process item {item}")
87
+ return item * 2
88
+
89
+ # Continue processing despite errors
90
+ results = multi_thread(process_item, [1, 2, 3, 4, 5], error_handler='log')
91
+ # Results: [2, 4, None, 8, 10] - errors logged automatically
92
+ ```
93
+
61
94
  ## Table of Contents
62
95
 
96
+ - [🚀 Recent Updates](#-recent-updates-january-27-2026)
97
+ - [Quick Start](#quick-start)
63
98
  - [Features](#features)
64
99
  - [Installation](#installation)
65
100
  - [Usage](#usage)
66
- - [Caching](#caching)
67
101
  - [Parallel Processing](#parallel-processing)
102
+ - [Enhanced Error Handling](#enhanced-error-handling)
103
+ - [Caching](#caching)
68
104
  - [File I/O](#file-io)
69
105
  - [Data Manipulation](#data-manipulation)
70
106
  - [Utility Functions](#utility-functions)
@@ -73,11 +109,12 @@ Description-Content-Type: text/markdown
73
109
  ## Features
74
110
 
75
111
  - **Caching Mechanisms**: Disk-based and in-memory caching to optimize function calls.
76
- - **Parallel Processing**: Multi-threading, multi-processing, and asynchronous multi-threading utilities.
112
+ - **Parallel Processing**: Multi-threading, multi-processing, and asynchronous multi-threading utilities with enhanced error handling.
77
113
  - **File I/O**: Simplified JSON, JSONL, and pickle file handling with support for various file extensions.
78
114
  - **Data Manipulation**: Utilities for flattening lists and dictionaries, converting data types, and more.
79
115
  - **Timing Utilities**: Tools to measure and log execution time of functions and processes.
80
116
  - **Pretty Printing**: Enhanced printing functions for structured data, including HTML tables for Jupyter notebooks.
117
+ - **Enhanced Error Handling**: Rich error tracebacks with code context, configurable error handling modes ('raise', 'ignore', 'log'), and detailed progress reporting.
81
118
 
82
119
  ## Installation
83
120
 
@@ -162,20 +199,133 @@ result = compute_sum(5, 7) # Retrieved from in-memory cache
162
199
 
163
200
  ### Parallel Processing
164
201
 
165
- #### Multi-threading
202
+ #### Multi-threading with Enhanced Error Handling
166
203
 
167
- Execute functions concurrently using multiple threads. This approach is straightforward and automatically handles both notebook and Python script executions. In a notebook environment, it delegates the running thread to a separate process. If interrupted, it immediately stops this process, avoiding thread dependency issues where threads continue running until all tasks are completed.
204
+ Execute functions concurrently using multiple threads with comprehensive error handling. The enhanced error handling provides three modes: 'raise' (default), 'ignore', and 'log'. When errors occur, you'll see rich-formatted tracebacks with code context and caller information.
168
205
 
169
206
  ```python
170
207
  from speedy_utils import multi_thread
171
208
 
172
209
  def process_item(item):
173
- # Your processing logic
210
+ # Simulate processing that might fail
211
+ if item == 3:
212
+ raise ValueError(f"Invalid item: {item}")
174
213
  return item * 2
175
214
 
176
215
  items = [1, 2, 3, 4, 5]
177
- results = multi_thread(process_item, items, workers=3)
178
- print(results) # [2, 4, 6, 8, 10]
216
+
217
+ # Default behavior: raise on first error with rich traceback
218
+ try:
219
+ results = multi_thread(process_item, items, workers=3)
220
+ except SystemExit:
221
+ print("Error occurred and was displayed with rich formatting")
222
+
223
+ # Continue processing on errors, return None for failed items
224
+ results = multi_thread(process_item, items, workers=3, error_handler='ignore')
225
+ print(results) # [2, 4, None, 8, 10]
226
+
227
+ # Log errors to files and continue processing
228
+ results = multi_thread(process_item, items, workers=3, error_handler='log', max_error_files=10)
229
+ print(results) # [2, 4, None, 8, 10] - errors logged to .cache/speedy_utils/error_logs/
230
+ ```
231
+
232
+ #### Multi-processing with Error Handling
233
+
234
+ Process items across multiple processes with the same enhanced error handling capabilities.
235
+
236
+ ```python
237
+ from speedy_utils import multi_process
238
+
239
+ def risky_computation(x):
240
+ """Computation that might fail for certain inputs."""
241
+ if x % 5 == 0:
242
+ raise RuntimeError(f"Cannot process multiples of 5: {x}")
243
+ return x ** 2
244
+
245
+ data = list(range(12))
246
+
247
+ # Process with error logging (continues on errors)
248
+ results = multi_process(
249
+ risky_computation,
250
+ data,
251
+ backend='mp',
252
+ error_handler='log',
253
+ max_error_files=5
254
+ )
255
+ print(results) # [0, 1, 4, 9, 16, None, 36, 49, 64, 81, None, 121]
256
+ ```
257
+
258
+ ### Enhanced Error Handling
259
+
260
+ **Speedy Utils** now provides comprehensive error handling for parallel processing with rich formatting and detailed diagnostics.
261
+
262
+ #### Rich Error Tracebacks
263
+
264
+ When errors occur, you'll see beautifully formatted tracebacks with:
265
+
266
+ - **Code context**: Lines of code around the error location
267
+ - **Caller information**: Shows where the parallel function was invoked
268
+ - **Filtered frames**: Focuses on user code, hiding infrastructure details
269
+ - **Color coding**: Easy-to-read formatting with syntax highlighting
270
+
271
+ #### Error Handling Modes
272
+
273
+ Choose how to handle errors in parallel processing:
274
+
275
+ - **`'raise'` (default)**: Stop on first error with detailed traceback
276
+ - **`'ignore'`**: Continue processing, return `None` for failed items
277
+ - **`'log'`**: Log errors to files and continue processing
278
+
279
+ #### Error Logging
280
+
281
+ When using `error_handler='log'`, errors are automatically saved to timestamped files in `.cache/speedy_utils/error_logs/` with full context and stack traces.
282
+
283
+ #### Progress Reporting with Error Statistics
284
+
285
+ Progress bars now show real-time error and success counts:
286
+
287
+ ```bash
288
+ Multi-thread [8/10] [00:02<00:00, 3.45it/s, success=8, errors=2, pending=0]
289
+ ```
290
+
291
+ This makes it easy to monitor processing health at a glance.
292
+
293
+ #### Example: Robust Data Processing
294
+
295
+ ```python
296
+ from speedy_utils import multi_thread
297
+
298
+ def process_data_record(record):
299
+ """Process a data record that might have issues."""
300
+ try:
301
+ # Your processing logic here
302
+ value = record['value'] / record['divisor']
303
+ return {'result': value, 'status': 'success'}
304
+ except KeyError as e:
305
+ raise ValueError(f"Missing required field in record: {e}")
306
+ except ZeroDivisionError:
307
+ raise ValueError("Division by zero in record")
308
+
309
+ # Sample data with some problematic records
310
+ data = [
311
+ {'value': 10, 'divisor': 2}, # OK
312
+ {'value': 15, 'divisor': 0}, # Will error
313
+ {'value': 20, 'divisor': 4}, # OK
314
+ {'value': 25}, # Missing divisor - will error
315
+ ]
316
+
317
+ # Process with error logging - continues despite errors
318
+ results = multi_thread(
319
+ process_data_record,
320
+ data,
321
+ workers=4,
322
+ error_handler='log',
323
+ max_error_files=10
324
+ )
325
+
326
+ print("Results:", results)
327
+ # Output: Results: [{'result': 5.0, 'status': 'success'}, None, {'result': 5.0, 'status': 'success'}, None]
328
+ # Errors are logged to files for later analysis
179
329
  ```
180
330
 
181
331
  ### File I/O
@@ -6,13 +6,49 @@
6
6
 
7
7
  **Speedy Utils** is a Python utility library designed to streamline common programming tasks such as caching, parallel processing, file I/O, and data manipulation. It provides a collection of decorators, functions, and classes to enhance productivity and performance in your Python projects.
8
8
 
9
+ ## 🚀 Recent Updates (January 27, 2026)
10
+
11
+ **Enhanced Error Handling in Parallel Processing:**
12
+
13
+ - Rich-formatted error tracebacks with code context and syntax highlighting
14
+ - Three error handling modes: 'raise', 'ignore', and 'log'
15
+ - Filtered tracebacks focusing on user code (hiding infrastructure)
16
+ - Real-time progress reporting with error/success statistics
17
+ - Automatic error logging to timestamped files
18
+ - Caller frame information showing where parallel functions were invoked
19
+
20
+ ## Quick Start
21
+
22
+ ### Parallel Processing with Error Handling
23
+
24
+ ```python
25
+ from speedy_utils import multi_thread, multi_process
26
+
27
+ # Simple parallel processing
28
+ results = multi_thread(lambda x: x * 2, [1, 2, 3, 4, 5])
29
+ # Results: [2, 4, 6, 8, 10]
30
+
31
+ # Robust processing with error handling
32
+ def process_item(item):
33
+ if item == 3:
34
+ raise ValueError(f"Cannot process item {item}")
35
+ return item * 2
36
+
37
+ # Continue processing despite errors
38
+ results = multi_thread(process_item, [1, 2, 3, 4, 5], error_handler='log')
39
+ # Results: [2, 4, None, 8, 10] - errors logged automatically
40
+ ```
41
+
9
42
  ## Table of Contents
10
43
 
44
+ - [🚀 Recent Updates](#-recent-updates-january-27-2026)
45
+ - [Quick Start](#quick-start)
11
46
  - [Features](#features)
12
47
  - [Installation](#installation)
13
48
  - [Usage](#usage)
14
- - [Caching](#caching)
15
49
  - [Parallel Processing](#parallel-processing)
50
+ - [Enhanced Error Handling](#enhanced-error-handling)
51
+ - [Caching](#caching)
16
52
  - [File I/O](#file-io)
17
53
  - [Data Manipulation](#data-manipulation)
18
54
  - [Utility Functions](#utility-functions)
@@ -21,11 +57,12 @@
21
57
  ## Features
22
58
 
23
59
  - **Caching Mechanisms**: Disk-based and in-memory caching to optimize function calls.
24
- - **Parallel Processing**: Multi-threading, multi-processing, and asynchronous multi-threading utilities.
60
+ - **Parallel Processing**: Multi-threading, multi-processing, and asynchronous multi-threading utilities with enhanced error handling.
25
61
  - **File I/O**: Simplified JSON, JSONL, and pickle file handling with support for various file extensions.
26
62
  - **Data Manipulation**: Utilities for flattening lists and dictionaries, converting data types, and more.
27
63
  - **Timing Utilities**: Tools to measure and log execution time of functions and processes.
28
64
  - **Pretty Printing**: Enhanced printing functions for structured data, including HTML tables for Jupyter notebooks.
65
+ - **Enhanced Error Handling**: Rich error tracebacks with code context, configurable error handling modes ('raise', 'ignore', 'log'), and detailed progress reporting.
29
66
 
30
67
  ## Installation
31
68
 
@@ -110,20 +147,133 @@ result = compute_sum(5, 7) # Retrieved from in-memory cache
110
147
 
111
148
  ### Parallel Processing
112
149
 
113
- #### Multi-threading
150
+ #### Multi-threading with Enhanced Error Handling
114
151
 
115
- Execute functions concurrently using multiple threads. This approach is straightforward and automatically handles both notebook and Python script executions. In a notebook environment, it delegates the running thread to a separate process. If interrupted, it immediately stops this process, avoiding thread dependency issues where threads continue running until all tasks are completed.
152
+ Execute functions concurrently using multiple threads with comprehensive error handling. The enhanced error handling provides three modes: 'raise' (default), 'ignore', and 'log'. When errors occur, you'll see rich-formatted tracebacks with code context and caller information.
116
153
 
117
154
  ```python
118
155
  from speedy_utils import multi_thread
119
156
 
120
157
  def process_item(item):
121
- # Your processing logic
158
+ # Simulate processing that might fail
159
+ if item == 3:
160
+ raise ValueError(f"Invalid item: {item}")
122
161
  return item * 2
123
162
 
124
163
  items = [1, 2, 3, 4, 5]
125
- results = multi_thread(process_item, items, workers=3)
126
- print(results) # [2, 4, 6, 8, 10]
164
+
165
+ # Default behavior: raise on first error with rich traceback
166
+ try:
167
+ results = multi_thread(process_item, items, workers=3)
168
+ except SystemExit:
169
+ print("Error occurred and was displayed with rich formatting")
170
+
171
+ # Continue processing on errors, return None for failed items
172
+ results = multi_thread(process_item, items, workers=3, error_handler='ignore')
173
+ print(results) # [2, 4, None, 8, 10]
174
+
175
+ # Log errors to files and continue processing
176
+ results = multi_thread(process_item, items, workers=3, error_handler='log', max_error_files=10)
177
+ print(results) # [2, 4, None, 8, 10] - errors logged to .cache/speedy_utils/error_logs/
178
+ ```
179
+
180
+ #### Multi-processing with Error Handling
181
+
182
+ Process items across multiple processes with the same enhanced error handling capabilities.
183
+
184
+ ```python
185
+ from speedy_utils import multi_process
186
+
187
+ def risky_computation(x):
188
+ """Computation that might fail for certain inputs."""
189
+ if x % 5 == 0:
190
+ raise RuntimeError(f"Cannot process multiples of 5: {x}")
191
+ return x ** 2
192
+
193
+ data = list(range(12))
194
+
195
+ # Process with error logging (continues on errors)
196
+ results = multi_process(
197
+ risky_computation,
198
+ data,
199
+ backend='mp',
200
+ error_handler='log',
201
+ max_error_files=5
202
+ )
203
+ print(results) # [0, 1, 4, 9, 16, None, 36, 49, 64, 81, None, 121]
204
+ ```
205
+
206
+ ### Enhanced Error Handling
207
+
208
+ **Speedy Utils** now provides comprehensive error handling for parallel processing with rich formatting and detailed diagnostics.
209
+
210
+ #### Rich Error Tracebacks
211
+
212
+ When errors occur, you'll see beautifully formatted tracebacks with:
213
+
214
+ - **Code context**: Lines of code around the error location
215
+ - **Caller information**: Shows where the parallel function was invoked
216
+ - **Filtered frames**: Focuses on user code, hiding infrastructure details
217
+ - **Color coding**: Easy-to-read formatting with syntax highlighting
218
+
219
+ #### Error Handling Modes
220
+
221
+ Choose how to handle errors in parallel processing:
222
+
223
+ - **`'raise'` (default)**: Stop on first error with detailed traceback
224
+ - **`'ignore'`**: Continue processing, return `None` for failed items
225
+ - **`'log'`**: Log errors to files and continue processing
226
+
227
+ #### Error Logging
228
+
229
+ When using `error_handler='log'`, errors are automatically saved to timestamped files in `.cache/speedy_utils/error_logs/` with full context and stack traces.
230
+
231
+ #### Progress Reporting with Error Statistics
232
+
233
+ Progress bars now show real-time error and success counts:
234
+
235
+ ```bash
236
+ Multi-thread [8/10] [00:02<00:00, 3.45it/s, success=8, errors=2, pending=0]
237
+ ```
238
+
239
+ This makes it easy to monitor processing health at a glance.
240
+
241
+ #### Example: Robust Data Processing
242
+
243
+ ```python
244
+ from speedy_utils import multi_thread
245
+
246
+ def process_data_record(record):
247
+ """Process a data record that might have issues."""
248
+ try:
249
+ # Your processing logic here
250
+ value = record['value'] / record['divisor']
251
+ return {'result': value, 'status': 'success'}
252
+ except KeyError as e:
253
+ raise ValueError(f"Missing required field in record: {e}")
254
+ except ZeroDivisionError:
255
+ raise ValueError("Division by zero in record")
256
+
257
+ # Sample data with some problematic records
258
+ data = [
259
+ {'value': 10, 'divisor': 2}, # OK
260
+ {'value': 15, 'divisor': 0}, # Will error
261
+ {'value': 20, 'divisor': 4}, # OK
262
+ {'value': 25}, # Missing divisor - will error
263
+ ]
264
+
265
+ # Process with error logging - continues despite errors
266
+ results = multi_thread(
267
+ process_data_record,
268
+ data,
269
+ workers=4,
270
+ error_handler='log',
271
+ max_error_files=10
272
+ )
273
+
274
+ print("Results:", results)
275
+ # Output: Results: [{'result': 5.0, 'status': 'success'}, None, {'result': 5.0, 'status': 'success'}, None]
276
+ # Errors are logged to files for later analysis
127
277
  ```
128
278
 
129
279
  ### File I/O
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "speedy-utils"
3
- version = "1.1.43"
3
+ version = "1.1.45"
4
4
  description = "Fast and easy-to-use package for data science"
5
5
  authors = [{ name = "AnhVTH", email = "anhvth.226@gmail.com" }]
6
6
  readme = "README.md"
@@ -0,0 +1,12 @@
1
+ import llm_utils
2
+ from speedy_utils import multi_process
3
+
4
+ llm = llm_utils.LLM(client=8666, timeout=3)
5
+
6
+ def f(x):
7
+ return llm('hello world')
8
+
9
+
10
+ # multi_process(f, range(10), backend='mp', error_handler='ignore')
11
+
12
+ f(0)
@@ -15,5 +15,4 @@ def process_data(item):
15
15
 
16
16
  if __name__ == '__main__':
17
17
  inputs = range(5)
18
- ret = multi_process(process_data, inputs, backend='mp', error_handler='log')
19
- print(ret)
18
+ multi_process(process_data, inputs, backend='mp')
@@ -3,8 +3,7 @@ from speedy_utils import *
3
3
  def do_something(x):
4
4
  x = 10
5
5
  y = 0
6
- # Intentionally cause division by zero error for testing
7
- _ = x/y
6
+ x/y
8
7
 
9
8
  if __name__ == '__main__':
10
9
  inputs = range(10)
@@ -16,6 +16,7 @@ from openai.types.chat import ChatCompletionMessageParam
16
16
  from pydantic import BaseModel
17
17
 
18
18
  from speedy_utils.common.utils_io import jdumps
19
+ from speedy_utils import clean_traceback
19
20
 
20
21
  from .base_prompt_builder import BasePromptBuilder
21
22
  from .mixins import (
@@ -159,6 +160,7 @@ class LLM(
159
160
  messages.append({'role': 'user', 'content': user_content})
160
161
  return cast(Messages, messages)
161
162
 
163
+ @clean_traceback
162
164
  def text_completion(
163
165
  self, input_data: str | BaseModel | list[dict], **runtime_kwargs
164
166
  ) -> list[dict[str, Any]]:
@@ -214,6 +216,7 @@ class LLM(
214
216
  results.append(result_dict)
215
217
  return results
216
218
 
219
+ @clean_traceback
217
220
  def pydantic_parse(
218
221
  self,
219
222
  input_data: str | BaseModel | list[dict],
@@ -58,6 +58,9 @@ from .common.utils_print import (
58
58
  fprint,
59
59
  )
60
60
 
61
+ # Error handling utilities
62
+ from .common.utils_error import clean_traceback, handle_exceptions_with_clean_traceback
63
+
61
64
  # Multi-worker processing
62
65
  from .multi_worker.process import multi_process
63
66
  from .multi_worker.thread import kill_all_thread, multi_thread
@@ -156,6 +159,9 @@ __all__ = [
156
159
  'print_table',
157
160
  'setup_logger',
158
161
  'log',
162
+ # Error handling utilities
163
+ 'clean_traceback',
164
+ 'handle_exceptions_with_clean_traceback',
159
165
  # Multi-worker processing
160
166
  'multi_process',
161
167
  'multi_thread',