ExcelAlchemy 2.2.8__tar.gz → 2.4.0__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 (86) hide show
  1. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/PKG-INFO +65 -4
  2. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/README-pypi.md +64 -3
  3. excelalchemy-2.4.0/src/excelalchemy/README.md +477 -0
  4. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/__init__.py +13 -2
  5. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/boolean.py +1 -0
  6. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/date.py +1 -0
  7. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/date_range.py +1 -0
  8. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/multi_checkbox.py +1 -0
  9. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/number.py +1 -0
  10. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/organization.py +6 -1
  11. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/radio.py +1 -0
  12. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/staff.py +8 -1
  13. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/string.py +1 -0
  14. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/tree.py +6 -1
  15. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/abstract.py +13 -3
  16. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/alchemy.py +34 -4
  17. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/import_session.py +125 -49
  18. excelalchemy-2.4.0/src/excelalchemy/core/preflight.py +97 -0
  19. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/storage_minio.py +6 -2
  20. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/exceptions.py +7 -0
  21. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/i18n/messages.py +3 -0
  22. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/metadata.py +27 -0
  23. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/results.py +301 -0
  24. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/LICENSE +0 -0
  25. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/pyproject.toml +0 -0
  26. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/_primitives/__init__.py +0 -0
  27. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/_primitives/constants.py +0 -0
  28. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/_primitives/deprecation.py +0 -0
  29. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/_primitives/diagnostics.py +0 -0
  30. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/_primitives/header_models.py +0 -0
  31. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/_primitives/identity.py +0 -0
  32. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/_primitives/payloads.py +0 -0
  33. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/artifacts.py +0 -0
  34. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/__init__.py +0 -0
  35. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/base.py +0 -0
  36. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/email.py +0 -0
  37. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/money.py +0 -0
  38. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/number_range.py +0 -0
  39. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/phone_number.py +0 -0
  40. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/codecs/url.py +0 -0
  41. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/config.py +0 -0
  42. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/const.py +0 -0
  43. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/__init__.py +0 -0
  44. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/executor.py +0 -0
  45. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/headers.py +0 -0
  46. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/rendering.py +0 -0
  47. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/rows.py +0 -0
  48. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/schema.py +0 -0
  49. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/storage.py +0 -0
  50. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/storage_protocol.py +0 -0
  51. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/table.py +0 -0
  52. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/core/writer.py +0 -0
  53. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/exc.py +0 -0
  54. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/header_models.py +0 -0
  55. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/helper/__init__.py +0 -0
  56. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/helper/pydantic.py +0 -0
  57. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/i18n/__init__.py +0 -0
  58. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/identity.py +0 -0
  59. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/py.typed +0 -0
  60. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/__init__.py +0 -0
  61. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/abstract.py +0 -0
  62. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/alchemy.py +0 -0
  63. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/field.py +0 -0
  64. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/header.py +0 -0
  65. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/identity.py +0 -0
  66. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/result.py +0 -0
  67. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/__init__.py +0 -0
  68. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/boolean.py +0 -0
  69. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/date.py +0 -0
  70. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/date_range.py +0 -0
  71. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/email.py +0 -0
  72. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/money.py +0 -0
  73. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/multi_checkbox.py +0 -0
  74. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/number.py +0 -0
  75. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/number_range.py +0 -0
  76. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/organization.py +0 -0
  77. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/phone_number.py +0 -0
  78. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/radio.py +0 -0
  79. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/staff.py +0 -0
  80. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/string.py +0 -0
  81. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/tree.py +0 -0
  82. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/types/value/url.py +0 -0
  83. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/util/__init__.py +0 -0
  84. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/util/converter.py +0 -0
  85. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/util/convertor.py +0 -0
  86. {excelalchemy-2.2.8 → excelalchemy-2.4.0}/src/excelalchemy/util/file.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: ExcelAlchemy
3
- Version: 2.2.8
3
+ Version: 2.4.0
4
4
  Summary: Schema-driven Python library for typed Excel import/export workflows with Pydantic and locale-aware workbooks.
5
5
  Keywords: excel,openpyxl,pydantic,minio,schema
6
6
  Author: Ray
@@ -49,9 +49,20 @@ ExcelAlchemy turns Pydantic models into typed workbook contracts:
49
49
  - render workbook-facing output in `zh-CN` or `en`
50
50
  - keep storage pluggable through `ExcelStorage`
51
51
 
52
- The current stable release is `2.2.8`, which continues the 2.x line with a clearer integration roadmap, stronger import-failure payload smoke verification, and more direct install-time validation of the FastAPI reference app.
52
+ The current stable release is `2.4.0`, which continues the 2.x line with a
53
+ more complete import workflow: clearer template guidance before upload,
54
+ lightweight structural preflight before execution, synchronous lifecycle
55
+ visibility during import, and remediation-oriented payloads after failures.
53
56
 
54
- [GitHub Repository](https://github.com/RayCarterLab/ExcelAlchemy) · [Full README](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/README.md) · [Getting Started](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/getting-started.md) · [Integration Roadmap](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-roadmap.md) · [Result Objects](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/result-objects.md) · [API Response Cookbook](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/api-response-cookbook.md) · [Examples Showcase](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/examples-showcase.md) · [Architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/architecture.md) · [Migration Notes](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/MIGRATIONS.md)
57
+ At the top level, that import workflow is:
58
+
59
+ - template authoring
60
+ - preflight gate
61
+ - import runtime
62
+ - result intelligence
63
+ - artifact and delivery
64
+
65
+ [GitHub Repository](https://github.com/RayCarterLab/ExcelAlchemy) · [Full README](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/README.md) · [Getting Started](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/getting-started.md) · [Integration Roadmap](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-roadmap.md) · [Platform Architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/platform-architecture.md) · [Runtime Model](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/runtime-model.md) · [Integration Blueprints](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-blueprints.md) · [Result Objects](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/result-objects.md) · [API Response Cookbook](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/api-response-cookbook.md) · [Examples Showcase](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/examples-showcase.md) · [Architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/architecture.md) · [Migration Notes](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/MIGRATIONS.md)
55
66
 
56
67
  ## Screenshots
57
68
 
@@ -108,7 +119,12 @@ class Importer(BaseModel):
108
119
  email: Annotated[
109
120
  Email,
110
121
  Field(min_length=10),
111
- ExcelMeta(label='Email', order=1, hint='Use your work email'),
122
+ ExcelMeta(
123
+ label='Email',
124
+ order=1,
125
+ hint='Use your work email',
126
+ example_value='alice@company.com',
127
+ ),
112
128
  ]
113
129
 
114
130
 
@@ -116,6 +132,48 @@ alchemy = ExcelAlchemy(ImporterConfig(Importer, locale='en'))
116
132
  template = alchemy.download_template_artifact(filename='people-template.xlsx')
117
133
  ```
118
134
 
135
+ This template metadata is additive: it leaves the worksheet layout alone and
136
+ improves the generated header comment with both guidance text and a concrete
137
+ example value.
138
+
139
+ ## Import Workflow Overview
140
+
141
+ The shortest path through the import workflow is:
142
+
143
+ ```text
144
+ template -> preflight -> import -> remediation -> delivery
145
+ ```
146
+
147
+ Minimal example:
148
+
149
+ ```python
150
+ from excelalchemy.results import build_frontend_remediation_payload
151
+
152
+
153
+ events: list[dict[str, object]] = []
154
+
155
+ preflight = alchemy.preflight_import('employees.xlsx')
156
+ if preflight.is_valid:
157
+ result = await alchemy.import_data(
158
+ 'employees.xlsx',
159
+ 'employees-result.xlsx',
160
+ on_event=events.append,
161
+ )
162
+ payload = build_frontend_remediation_payload(
163
+ result=result,
164
+ cell_error_map=alchemy.cell_error_map,
165
+ row_error_map=alchemy.row_error_map,
166
+ )
167
+ ```
168
+
169
+ See also:
170
+
171
+ - [Platform Architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/platform-architecture.md)
172
+ - [Runtime Model](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/runtime-model.md)
173
+ - [Integration Blueprints](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-blueprints.md)
174
+ - [Result Objects](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/result-objects.md)
175
+ - [API Response Cookbook](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/api-response-cookbook.md)
176
+
119
177
  ## Example Outputs
120
178
 
121
179
  These fixed outputs are generated from the repository examples by
@@ -193,6 +251,9 @@ for configured selection fields.
193
251
  ## Learn More
194
252
 
195
253
  - [Full project README](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/README.md)
254
+ - [Platform architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/platform-architecture.md)
255
+ - [Runtime model](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/runtime-model.md)
256
+ - [Integration blueprints](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-blueprints.md)
196
257
  - [Architecture notes](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/architecture.md)
197
258
  - [Locale policy](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/locale.md)
198
259
  - [Migration notes](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/MIGRATIONS.md)
@@ -10,9 +10,20 @@ ExcelAlchemy turns Pydantic models into typed workbook contracts:
10
10
  - render workbook-facing output in `zh-CN` or `en`
11
11
  - keep storage pluggable through `ExcelStorage`
12
12
 
13
- The current stable release is `2.2.8`, which continues the 2.x line with a clearer integration roadmap, stronger import-failure payload smoke verification, and more direct install-time validation of the FastAPI reference app.
13
+ The current stable release is `2.4.0`, which continues the 2.x line with a
14
+ more complete import workflow: clearer template guidance before upload,
15
+ lightweight structural preflight before execution, synchronous lifecycle
16
+ visibility during import, and remediation-oriented payloads after failures.
14
17
 
15
- [GitHub Repository](https://github.com/RayCarterLab/ExcelAlchemy) · [Full README](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/README.md) · [Getting Started](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/getting-started.md) · [Integration Roadmap](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-roadmap.md) · [Result Objects](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/result-objects.md) · [API Response Cookbook](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/api-response-cookbook.md) · [Examples Showcase](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/examples-showcase.md) · [Architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/architecture.md) · [Migration Notes](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/MIGRATIONS.md)
18
+ At the top level, that import workflow is:
19
+
20
+ - template authoring
21
+ - preflight gate
22
+ - import runtime
23
+ - result intelligence
24
+ - artifact and delivery
25
+
26
+ [GitHub Repository](https://github.com/RayCarterLab/ExcelAlchemy) · [Full README](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/README.md) · [Getting Started](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/getting-started.md) · [Integration Roadmap](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-roadmap.md) · [Platform Architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/platform-architecture.md) · [Runtime Model](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/runtime-model.md) · [Integration Blueprints](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-blueprints.md) · [Result Objects](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/result-objects.md) · [API Response Cookbook](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/api-response-cookbook.md) · [Examples Showcase](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/examples-showcase.md) · [Architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/architecture.md) · [Migration Notes](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/MIGRATIONS.md)
16
27
 
17
28
  ## Screenshots
18
29
 
@@ -69,7 +80,12 @@ class Importer(BaseModel):
69
80
  email: Annotated[
70
81
  Email,
71
82
  Field(min_length=10),
72
- ExcelMeta(label='Email', order=1, hint='Use your work email'),
83
+ ExcelMeta(
84
+ label='Email',
85
+ order=1,
86
+ hint='Use your work email',
87
+ example_value='alice@company.com',
88
+ ),
73
89
  ]
74
90
 
75
91
 
@@ -77,6 +93,48 @@ alchemy = ExcelAlchemy(ImporterConfig(Importer, locale='en'))
77
93
  template = alchemy.download_template_artifact(filename='people-template.xlsx')
78
94
  ```
79
95
 
96
+ This template metadata is additive: it leaves the worksheet layout alone and
97
+ improves the generated header comment with both guidance text and a concrete
98
+ example value.
99
+
100
+ ## Import Workflow Overview
101
+
102
+ The shortest path through the import workflow is:
103
+
104
+ ```text
105
+ template -> preflight -> import -> remediation -> delivery
106
+ ```
107
+
108
+ Minimal example:
109
+
110
+ ```python
111
+ from excelalchemy.results import build_frontend_remediation_payload
112
+
113
+
114
+ events: list[dict[str, object]] = []
115
+
116
+ preflight = alchemy.preflight_import('employees.xlsx')
117
+ if preflight.is_valid:
118
+ result = await alchemy.import_data(
119
+ 'employees.xlsx',
120
+ 'employees-result.xlsx',
121
+ on_event=events.append,
122
+ )
123
+ payload = build_frontend_remediation_payload(
124
+ result=result,
125
+ cell_error_map=alchemy.cell_error_map,
126
+ row_error_map=alchemy.row_error_map,
127
+ )
128
+ ```
129
+
130
+ See also:
131
+
132
+ - [Platform Architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/platform-architecture.md)
133
+ - [Runtime Model](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/runtime-model.md)
134
+ - [Integration Blueprints](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-blueprints.md)
135
+ - [Result Objects](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/result-objects.md)
136
+ - [API Response Cookbook](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/api-response-cookbook.md)
137
+
80
138
  ## Example Outputs
81
139
 
82
140
  These fixed outputs are generated from the repository examples by
@@ -154,6 +212,9 @@ for configured selection fields.
154
212
  ## Learn More
155
213
 
156
214
  - [Full project README](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/README.md)
215
+ - [Platform architecture](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/platform-architecture.md)
216
+ - [Runtime model](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/runtime-model.md)
217
+ - [Integration blueprints](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/integration-blueprints.md)
157
218
  - [Architecture notes](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/architecture.md)
158
219
  - [Locale policy](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/docs/locale.md)
159
220
  - [Migration notes](https://github.com/RayCarterLab/ExcelAlchemy/blob/main/MIGRATIONS.md)
@@ -0,0 +1,477 @@
1
+ # `src/excelalchemy/` Package Guide
2
+
3
+ This file explains the internal structure of the main package directory.
4
+ It is meant for developers and AI agents who need to change implementation details without confusing public API, compatibility layers, and internal collaborators.
5
+
6
+ ## Related docs
7
+
8
+ - [../../README.md](../../README.md) for the public-facing overview.
9
+ - [../../AGENTS.md](../../AGENTS.md) for repository-local editing guidance.
10
+ - [../../docs/repo-map.md](../../docs/repo-map.md) for top-level repository navigation.
11
+ - [../../docs/domain-model.md](../../docs/domain-model.md) for the main concepts implemented here.
12
+ - [../../docs/invariants.md](../../docs/invariants.md) for important behavioral constraints.
13
+ - [../../tests/README.md](../../tests/README.md) for where this package's behavior is protected.
14
+
15
+ ## Role of This Package
16
+
17
+ - `src/excelalchemy/` is the main library package.
18
+ - It contains:
19
+ - the stable public surface used by application code
20
+ - the internal orchestration that implements import, export, template generation, rendering, and storage integration
21
+ - compatibility modules retained for the 2.x line
22
+ - The package is organized around a small public facade and a set of focused internal collaborators.
23
+ - In the v2.4 docs, those collaborators are also described through a higher-level
24
+ import platform model:
25
+ - template authoring
26
+ - preflight gate
27
+ - import runtime
28
+ - result intelligence
29
+ - artifact and delivery
30
+
31
+ ## High-Level Package Structure
32
+
33
+ - `__init__.py`
34
+ - Main public re-export surface.
35
+ - If application-facing imports change, start here.
36
+ - `config.py`
37
+ - Public workflow configuration types.
38
+ - `metadata.py`
39
+ - Public metadata declarations plus the internal layered field-metadata model.
40
+ - `results.py`
41
+ - Public result models and API-friendly error maps.
42
+ - `exceptions.py`
43
+ - Public exception types.
44
+ - `artifacts.py`
45
+ - Public workbook artifact wrapper.
46
+ - `codecs/`
47
+ - Public field codecs and codec base classes.
48
+ - `core/`
49
+ - Internal workflow orchestration and execution.
50
+ - `helper/`
51
+ - Internal adapter layer, currently centered on Pydantic integration.
52
+ - `i18n/`
53
+ - Internal message and locale handling.
54
+ - `_primitives/`
55
+ - Internal low-level types, constants, payload aliases, diagnostics, and deprecation helpers.
56
+ - `types/`, `exc.py`, `identity.py`, `header_models.py`, `const.py`, `util/convertor.py`
57
+ - Compatibility-oriented modules retained in the 2.x line.
58
+
59
+ ## Public Surface vs Internal Implementation
60
+
61
+ ### Public surface
62
+
63
+ These modules are the stable public entry points documented in `docs/public-api.md`:
64
+
65
+ - `src/excelalchemy/__init__.py`
66
+ - `src/excelalchemy/config.py`
67
+ - `src/excelalchemy/metadata.py`
68
+ - `src/excelalchemy/results.py`
69
+ - `src/excelalchemy/exceptions.py`
70
+ - `src/excelalchemy/codecs/`
71
+ - `src/excelalchemy/artifacts.py`
72
+
73
+ ### Internal implementation
74
+
75
+ These modules implement behavior but are not the recommended import paths for application code:
76
+
77
+ - `src/excelalchemy/core/`
78
+ - `src/excelalchemy/helper/`
79
+ - `src/excelalchemy/i18n/`
80
+ - `src/excelalchemy/_primitives/`
81
+
82
+ ### Compatibility-only surface
83
+
84
+ These exist to support the 2.x line and should not be treated as preferred implementation entry points for new work:
85
+
86
+ - `src/excelalchemy/types/`
87
+ - `src/excelalchemy/exc.py`
88
+ - `src/excelalchemy/identity.py`
89
+ - `src/excelalchemy/header_models.py`
90
+ - `src/excelalchemy/const.py`
91
+ - `src/excelalchemy/util/convertor.py`
92
+
93
+ ## Major Modules and Responsibilities
94
+
95
+ ### Public-facing root modules
96
+
97
+ - `src/excelalchemy/__init__.py`
98
+ - Re-exports `ExcelAlchemy`, configs, codecs, result types, exception types, and common identity/value types.
99
+ - Changes here affect top-level user imports directly.
100
+
101
+ - `src/excelalchemy/config.py`
102
+ - Defines:
103
+ - `ExcelMode`
104
+ - `ImportMode`
105
+ - `ImporterConfig`
106
+ - `ExporterConfig`
107
+ - normalized schema/behavior/storage option groupings
108
+ - Also contains legacy Minio compatibility handling and deprecation warnings.
109
+
110
+ - `src/excelalchemy/metadata.py`
111
+ - Defines public declaration helpers:
112
+ - `FieldMeta(...)`
113
+ - `ExcelMeta(...)`
114
+ - Also defines the internal metadata layers behind `FieldMetaInfo`:
115
+ - `DeclaredFieldMeta`
116
+ - `RuntimeFieldBinding`
117
+ - `WorkbookPresentationMeta`
118
+ - `ImportConstraints`
119
+ - This file is central when changing field declaration behavior, workbook comments, formatting hints, or constraint overlay rules.
120
+
121
+ - `src/excelalchemy/results.py`
122
+ - Defines public result objects:
123
+ - `ImportResult`
124
+ - `ValidateHeaderResult`
125
+ - `ValidateResult`
126
+ - `ValidateRowResult`
127
+ - `CellErrorMap`
128
+ - `RowIssueMap`
129
+ - This is the main file for API payload shape and structured error access.
130
+
131
+ - `src/excelalchemy/exceptions.py`
132
+ - Defines the public exception model:
133
+ - `ExcelAlchemyError`
134
+ - `ExcelCellError`
135
+ - `ExcelRowError`
136
+ - `ProgrammaticError`
137
+ - `ConfigError`
138
+
139
+ - `src/excelalchemy/artifacts.py`
140
+ - Defines `ExcelArtifact`, which wraps rendered workbook content as bytes, base64, or a data URL.
141
+
142
+ ### `core/` internal orchestration
143
+
144
+ - `src/excelalchemy/core/alchemy.py`
145
+ - Main facade implementation.
146
+ - Builds layout and storage, exposes the top-level workflow methods, and surfaces inspection properties like `worksheet_table` and `cell_error_map`.
147
+ - This is the first internal file to inspect when changing how the facade behaves.
148
+
149
+ - `src/excelalchemy/core/import_session.py`
150
+ - Owns one import run’s runtime state.
151
+ - Tracks:
152
+ - workbook load state
153
+ - header table
154
+ - worksheet table
155
+ - issue maps
156
+ - execution counts
157
+ - result rendering state
158
+ - `ImportSessionSnapshot`
159
+ - This is the main import lifecycle owner.
160
+
161
+ - `src/excelalchemy/core/schema.py`
162
+ - Converts extracted field metadata into `ExcelSchemaLayout`.
163
+ - Responsible for:
164
+ - layout ordering
165
+ - unique label/key indexing
166
+ - composite field expansion
167
+ - merged-header detection for selected output keys
168
+
169
+ - `src/excelalchemy/core/headers.py`
170
+ - Header parsing and header validation.
171
+ - Responsible for:
172
+ - detecting simple vs merged headers
173
+ - normalizing parsed headers into `ExcelHeader` objects
174
+ - comparing workbook headers against schema layout
175
+
176
+ - `src/excelalchemy/core/rows.py`
177
+ - Row reconstruction and issue tracking.
178
+ - `RowAggregator` groups flattened worksheet data back into model-shaped payloads.
179
+ - `ImportIssueTracker` maps row/cell failures back to workbook coordinates and prepends result columns.
180
+
181
+ - `src/excelalchemy/core/executor.py`
182
+ - Dispatches the actual import execution path.
183
+ - Responsible for:
184
+ - choosing create/update/create-or-update behavior
185
+ - validating reconstructed payloads
186
+ - invoking configured callbacks
187
+ - mapping failures into row/cell issues
188
+
189
+ - `src/excelalchemy/core/rendering.py`
190
+ - High-level rendering entry points for templates, exports, and import result workbooks.
191
+
192
+ - `src/excelalchemy/core/writer.py`
193
+ - Lower-level workbook writing details:
194
+ - comments
195
+ - fills/colors
196
+ - workbook rows/cells
197
+ - result/reason columns
198
+
199
+ - `src/excelalchemy/core/storage_protocol.py`
200
+ - Defines the `ExcelStorage` protocol.
201
+ - This is the main storage extension boundary.
202
+
203
+ - `src/excelalchemy/core/storage.py`
204
+ - Resolves configured storage into a concrete gateway.
205
+ - Also defines the missing-storage fallback path.
206
+
207
+ - `src/excelalchemy/core/storage_minio.py`
208
+ - Built-in Minio-backed storage implementation.
209
+
210
+ - `src/excelalchemy/core/table.py`
211
+ - Defines `WorksheetTable`, `WorksheetRow`, and related helpers.
212
+ - This is the internal table abstraction used instead of pandas.
213
+
214
+ ### `codecs/` field behavior
215
+
216
+ - `src/excelalchemy/codecs/base.py`
217
+ - Defines:
218
+ - `ExcelFieldCodec`
219
+ - `CompositeExcelFieldCodec`
220
+ - fallback logging helpers
221
+ - Start here when changing the codec contract itself.
222
+
223
+ - `src/excelalchemy/codecs/*.py`
224
+ - Built-in concrete field codecs such as:
225
+ - `string.py`
226
+ - `number.py`
227
+ - `date.py`
228
+ - `date_range.py`
229
+ - `email.py`
230
+ - `phone_number.py`
231
+ - `money.py`
232
+ - `radio.py`
233
+ - `multi_checkbox.py`
234
+ - `organization.py`
235
+ - `staff.py`
236
+ - `tree.py`
237
+ - `url.py`
238
+
239
+ ### Adapter, i18n, and primitive helpers
240
+
241
+ - `src/excelalchemy/helper/pydantic.py`
242
+ - Isolates the Pydantic boundary.
243
+ - Responsible for:
244
+ - extracting model metadata
245
+ - resolving codec types
246
+ - normalizing validation messages
247
+ - mapping Pydantic validation output to `ExcelCellError` and `ExcelRowError`
248
+
249
+ - `src/excelalchemy/i18n/messages.py`
250
+ - Central message lookup and locale handling.
251
+ - Important when changing workbook-facing text, runtime error text, or locale policy.
252
+
253
+ - `src/excelalchemy/_primitives/constants.py`
254
+ - Internal constants and enum-like definitions used across the package.
255
+
256
+ - `src/excelalchemy/_primitives/identity.py`
257
+ - Internal typed wrappers for labels, keys, row indexes, column indexes, URLs, and related string-like identifiers.
258
+
259
+ - `src/excelalchemy/_primitives/payloads.py`
260
+ - Shared payload type aliases for import/export/data-converter/callback paths.
261
+
262
+ - `src/excelalchemy/_primitives/diagnostics.py`
263
+ - Developer-facing diagnostic logging helpers.
264
+
265
+ - `src/excelalchemy/_primitives/deprecation.py`
266
+ - Deprecation warning helpers used by compatibility modules.
267
+
268
+ - `src/excelalchemy/_primitives/header_models.py`
269
+ - Internal parsed-header model objects.
270
+
271
+ ## Major Internal Flows
272
+
273
+ The package guide keeps the internal ownership view.
274
+ If you want the capability-oriented platform view above these flows, start with:
275
+
276
+ - [`../../docs/platform-architecture.md`](../../docs/platform-architecture.md)
277
+ - [`../../docs/runtime-model.md`](../../docs/runtime-model.md)
278
+ - [`../../docs/platform-code-mapping.md`](../../docs/platform-code-mapping.md)
279
+
280
+ ### Import validation flow
281
+
282
+ The import path is implemented roughly in this order:
283
+
284
+ 1. `src/excelalchemy/core/alchemy.py`
285
+ - `ExcelAlchemy.import_data(...)` creates a new import session.
286
+ 2. `src/excelalchemy/core/import_session.py`
287
+ - loads workbook data through storage
288
+ - builds header and worksheet state
289
+ 3. `src/excelalchemy/core/headers.py`
290
+ - parses headers
291
+ - validates headers against the schema layout
292
+ 4. `src/excelalchemy/core/rows.py`
293
+ - reconstructs model-shaped row payloads
294
+ 5. `src/excelalchemy/core/executor.py`
295
+ - validates and dispatches create/update/upsert logic
296
+ 6. `src/excelalchemy/helper/pydantic.py`
297
+ - adapts Pydantic validation into ExcelAlchemy issues
298
+ 7. `src/excelalchemy/core/rows.py`
299
+ - records row/cell failures in workbook coordinates
300
+ 8. `src/excelalchemy/core/rendering.py` and `src/excelalchemy/core/writer.py`
301
+ - render the import result workbook when rows fail
302
+ 9. `src/excelalchemy/results.py`
303
+ - exposes the final result through `ImportResult`, `CellErrorMap`, and `RowIssueMap`
304
+
305
+ ### Template generation flow
306
+
307
+ The template path is implemented roughly in this order:
308
+
309
+ 1. `src/excelalchemy/core/alchemy.py`
310
+ - selects output keys and header shape
311
+ 2. `src/excelalchemy/core/schema.py`
312
+ - provides ordered layout and merged-header decisions
313
+ 3. `src/excelalchemy/codecs/`
314
+ - provide comments, display formatting, and field-specific workbook semantics
315
+ 4. `src/excelalchemy/core/rendering.py`
316
+ 5. `src/excelalchemy/core/writer.py`
317
+ - produce the workbook output
318
+ 6. `src/excelalchemy/artifacts.py`
319
+ - wraps the output when the artifact API is used
320
+
321
+ ### Export flow
322
+
323
+ The export path is implemented roughly in this order:
324
+
325
+ 1. `src/excelalchemy/core/alchemy.py`
326
+ - accepts export rows and selected keys
327
+ 2. `src/excelalchemy/core/schema.py`
328
+ - resolves output layout and merged-header needs
329
+ 3. `src/excelalchemy/codecs/`
330
+ - format workbook-facing values
331
+ 4. `src/excelalchemy/core/rendering.py`
332
+ 5. `src/excelalchemy/core/writer.py`
333
+ 6. `src/excelalchemy/core/storage_protocol.py` and `src/excelalchemy/core/storage.py`
334
+ - are used only when the upload path is chosen
335
+
336
+ ### Storage integration flow
337
+
338
+ Storage-related behavior is split into three concerns:
339
+
340
+ - contract:
341
+ - `src/excelalchemy/core/storage_protocol.py`
342
+ - resolution:
343
+ - `src/excelalchemy/core/storage.py`
344
+ - built-in Minio backend:
345
+ - `src/excelalchemy/core/storage_minio.py`
346
+
347
+ The recommended 2.x design is:
348
+
349
+ - config holds `storage=...`
350
+ - `build_storage_gateway(...)` resolves it
351
+ - import reads workbook data as `WorksheetTable`
352
+ - export/import-result uploads return a URL through the storage implementation
353
+ - custom storage readers currently use `src/excelalchemy/core/table.py` for that `WorksheetTable` contract
354
+
355
+ ## Where To Look When Changing Specific Behavior
356
+
357
+ ### Changing public API behavior
358
+
359
+ Start here:
360
+
361
+ - `src/excelalchemy/__init__.py`
362
+ - `src/excelalchemy/config.py`
363
+ - `src/excelalchemy/metadata.py`
364
+ - `src/excelalchemy/results.py`
365
+ - `src/excelalchemy/exceptions.py`
366
+ - `docs/public-api.md`
367
+ - `MIGRATIONS.md`
368
+ - `tests/contracts/`
369
+
370
+ Use extra caution when changing:
371
+
372
+ - exported names
373
+ - config constructor behavior
374
+ - result payload shape
375
+ - exception wording or exception type mapping
376
+ - compatibility aliases
377
+
378
+ ### Changing import validation behavior
379
+
380
+ Start here:
381
+
382
+ - `src/excelalchemy/core/import_session.py`
383
+ - `src/excelalchemy/core/headers.py`
384
+ - `src/excelalchemy/core/rows.py`
385
+ - `src/excelalchemy/core/executor.py`
386
+ - `src/excelalchemy/helper/pydantic.py`
387
+ - `src/excelalchemy/results.py`
388
+ - `tests/contracts/test_import_contract.py`
389
+ - `tests/contracts/test_core_components_contract.py`
390
+ - `tests/contracts/test_pydantic_contract.py`
391
+
392
+ Typical examples:
393
+
394
+ - header validation rules
395
+ - row reconstruction
396
+ - Pydantic error mapping
397
+ - create/update/upsert behavior
398
+ - result-workbook error placement
399
+
400
+ ### Changing export or template generation behavior
401
+
402
+ Start here:
403
+
404
+ - `src/excelalchemy/core/alchemy.py`
405
+ - `src/excelalchemy/core/schema.py`
406
+ - `src/excelalchemy/core/rendering.py`
407
+ - `src/excelalchemy/core/writer.py`
408
+ - `src/excelalchemy/codecs/`
409
+ - `tests/contracts/test_template_contract.py`
410
+ - `tests/contracts/test_export_contract.py`
411
+
412
+ Typical examples:
413
+
414
+ - workbook comments
415
+ - merged headers
416
+ - selected output keys
417
+ - workbook-facing display formatting
418
+ - artifact generation
419
+
420
+ ### Changing storage integration behavior
421
+
422
+ Start here:
423
+
424
+ - `src/excelalchemy/core/storage_protocol.py`
425
+ - `src/excelalchemy/core/storage.py`
426
+ - `src/excelalchemy/core/storage_minio.py`
427
+ - `src/excelalchemy/config.py`
428
+ - `examples/custom_storage.py`
429
+ - `tests/contracts/test_storage_contract.py`
430
+ - `tests/unit/test_config_options.py`
431
+
432
+ Typical examples:
433
+
434
+ - storage contract shape
435
+ - default gateway selection
436
+ - missing-storage behavior
437
+ - Minio compatibility behavior
438
+ - upload payload expectations
439
+
440
+ ### Changing locale-aware output behavior
441
+
442
+ Start here:
443
+
444
+ - `src/excelalchemy/i18n/messages.py`
445
+ - `src/excelalchemy/metadata.py`
446
+ - `src/excelalchemy/core/alchemy.py`
447
+ - `src/excelalchemy/core/writer.py`
448
+ - `docs/locale.md`
449
+ - `tests/contracts/test_template_contract.py`
450
+ - `tests/contracts/test_import_contract.py`
451
+
452
+ Typical examples:
453
+
454
+ - workbook instruction text
455
+ - header comments
456
+ - result/reason column labels
457
+ - row status text
458
+ - fallback locale behavior
459
+
460
+ ## Implementation Cautions
461
+
462
+ - Do not treat compatibility modules under `src/excelalchemy/types/` and the root compatibility shims as preferred edit points for new behavior.
463
+ - Do not reintroduce pandas-style assumptions into the runtime path; this package now uses `WorksheetTable`.
464
+ - Do not hard-wire Minio into core workflow logic; storage is intentionally abstracted behind `ExcelStorage`.
465
+ - Treat `src/excelalchemy/core/table.py` as a narrow extension seam for current 2.x storage integrations, not as a general application import surface.
466
+ - If you change result payload shape, inspect:
467
+ - `src/excelalchemy/results.py`
468
+ - `docs/result-objects.md`
469
+ - `docs/api-response-cookbook.md`
470
+ - `scripts/smoke_api_payload_snapshot.py`
471
+ - `files/example-outputs/import-failure-api-payload.json`
472
+ - If you change docs-visible example behavior, inspect:
473
+ - `examples/`
474
+ - `files/example-outputs/`
475
+ - `scripts/generate_example_output_assets.py`
476
+ - `scripts/smoke_examples.py`
477
+ - `scripts/smoke_docs_assets.py`