exstruct 0.7.0__tar.gz → 0.7.1__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. {exstruct-0.7.0 → exstruct-0.7.1}/PKG-INFO +4 -4
  2. {exstruct-0.7.0 → exstruct-0.7.1}/README.md +3 -3
  3. {exstruct-0.7.0 → exstruct-0.7.1}/pyproject.toml +1 -1
  4. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/__init__.py +181 -45
  5. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/cli/availability.py +1 -1
  6. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/cli/edit.py +525 -411
  7. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/cli/main.py +108 -27
  8. exstruct-0.7.1/src/exstruct/edit/__init__.py +281 -0
  9. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/engine.py +914 -725
  10. exstruct-0.7.0/src/exstruct/edit/__init__.py +0 -128
  11. {exstruct-0.7.0 → exstruct-0.7.1}/LICENSE +0 -0
  12. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/constraints.py +0 -0
  13. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/__init__.py +0 -0
  14. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/_libreoffice_bridge.py +0 -0
  15. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/backends/__init__.py +0 -0
  16. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/backends/base.py +0 -0
  17. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/backends/com_backend.py +0 -0
  18. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/backends/libreoffice_backend.py +0 -0
  19. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/backends/openpyxl_backend.py +0 -0
  20. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/cells.py +0 -0
  21. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/charts.py +0 -0
  22. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/integrate.py +0 -0
  23. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/libreoffice.py +0 -0
  24. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/logging_utils.py +0 -0
  25. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/modeling.py +0 -0
  26. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/ooxml_drawing.py +0 -0
  27. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/pipeline.py +0 -0
  28. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/ranges.py +0 -0
  29. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/shapes.py +0 -0
  30. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/core/workbook.py +0 -0
  31. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/a1.py +0 -0
  32. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/api.py +0 -0
  33. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/chart_types.py +0 -0
  34. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/engine/__init__.py +0 -0
  35. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/engine/openpyxl_engine.py +0 -0
  36. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/engine/xlwings_engine.py +0 -0
  37. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/errors.py +0 -0
  38. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/internal.py +0 -0
  39. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/models.py +0 -0
  40. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/normalize.py +0 -0
  41. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/op_schema.py +0 -0
  42. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/output_path.py +0 -0
  43. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/runtime.py +0 -0
  44. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/service.py +0 -0
  45. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/specs.py +0 -0
  46. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/edit/types.py +0 -0
  47. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/errors.py +0 -0
  48. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/io/__init__.py +0 -0
  49. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/io/serialize.py +0 -0
  50. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/__init__.py +0 -0
  51. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/chunk_reader.py +0 -0
  52. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/extract_runner.py +0 -0
  53. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/io.py +0 -0
  54. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/op_schema.py +0 -0
  55. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/__init__.py +0 -0
  56. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/chart_types.py +0 -0
  57. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/engine/__init__.py +0 -0
  58. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/engine/base.py +0 -0
  59. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/engine/openpyxl_engine.py +0 -0
  60. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/engine/xlwings_engine.py +0 -0
  61. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/internal.py +0 -0
  62. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/models.py +0 -0
  63. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/normalize.py +0 -0
  64. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/ops/__init__.py +0 -0
  65. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/ops/common.py +0 -0
  66. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/ops/openpyxl_ops.py +0 -0
  67. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/ops/xlwings_ops.py +0 -0
  68. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/runtime.py +0 -0
  69. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/service.py +0 -0
  70. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/specs.py +0 -0
  71. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch/types.py +0 -0
  72. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/patch_runner.py +0 -0
  73. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/render_runner.py +0 -0
  74. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/server.py +0 -0
  75. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/shared/__init__.py +0 -0
  76. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/shared/a1.py +0 -0
  77. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/shared/output_path.py +0 -0
  78. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/sheet_reader.py +0 -0
  79. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/tools.py +0 -0
  80. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/mcp/validate_input.py +0 -0
  81. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/models/__init__.py +0 -0
  82. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/models/maps.py +0 -0
  83. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/models/types.py +0 -0
  84. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/py.typed +0 -0
  85. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/render/__init__.py +0 -0
  86. {exstruct-0.7.0 → exstruct-0.7.1}/src/exstruct/render/subprocess_worker.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.3
2
2
  Name: exstruct
3
- Version: 0.7.0
3
+ Version: 0.7.1
4
4
  Summary: Excel to structured JSON (tables, shapes, charts) for LLM/RAG pipelines
5
5
  Keywords: excel,structure,data,exstruct
6
6
  Author: harumiWeb
@@ -159,7 +159,7 @@ exstruct input.xlsx -o out.json --pretty # write pretty JSON to a file
159
159
  exstruct input.xlsx --format yaml # YAML (requires pyyaml)
160
160
  exstruct input.xlsx --format toon # TOON (requires python-toon)
161
161
  exstruct input.xlsx --sheets-dir sheets/ # write one file per sheet
162
- exstruct input.xlsx --auto-page-breaks-dir auto_areas/ # COM only; shown only when available
162
+ exstruct input.xlsx --auto-page-breaks-dir auto_areas/ # always shown; execution requires standard/verbose + Excel COM
163
163
  exstruct input.xlsx --alpha-col # output column keys as A, B, ..., AA
164
164
  exstruct input.xlsx --include-backend-metadata # include shape/chart backend metadata
165
165
  exstruct input.xlsx --mode light # cells + table candidates only
@@ -167,8 +167,8 @@ exstruct input.xlsx --mode libreoffice # best-effort extraction of shapes/co
167
167
  exstruct input.xlsx --pdf --image # PDF and PNGs (Excel COM required)
168
168
  ```
169
169
 
170
- Auto page-break export is available from both the API and the CLI when Excel/COM is available. The CLI exposes `--auto-page-breaks-dir` only in COM-capable environments.
171
- `mode=libreoffice` rejects `--pdf`, `--image`, and `--auto-page-breaks-dir` early. Use `standard` or `verbose` with Excel COM for those features.
170
+ Auto page-break export is available from both the API and the CLI when Excel/COM is available. The CLI always exposes `--auto-page-breaks-dir`, but validates it at execution time.
171
+ `mode=libreoffice` rejects `--pdf`, `--image`, and `--auto-page-breaks-dir` early, and `mode=light` also rejects `--auto-page-breaks-dir`. Use `standard` or `verbose` with Excel COM for those features.
172
172
  By default, the CLI keeps legacy 0-based numeric string column keys (`"0"`, `"1"`, ...). Use `--alpha-col` when you need Excel-style keys (`"A"`, `"B"`, ...).
173
173
  By default, serialized shape/chart output omits backend metadata (`provenance`, `approximation_level`, `confidence`) to reduce token usage. Use `--include-backend-metadata` or the corresponding Python/MCP option when you need it.
174
174
  Note: MCP `exstruct_extract` defaults to `options.alpha_col=true`, which differs from the CLI default (`false`).
@@ -93,7 +93,7 @@ exstruct input.xlsx -o out.json --pretty # write pretty JSON to a file
93
93
  exstruct input.xlsx --format yaml # YAML (requires pyyaml)
94
94
  exstruct input.xlsx --format toon # TOON (requires python-toon)
95
95
  exstruct input.xlsx --sheets-dir sheets/ # write one file per sheet
96
- exstruct input.xlsx --auto-page-breaks-dir auto_areas/ # COM only; shown only when available
96
+ exstruct input.xlsx --auto-page-breaks-dir auto_areas/ # always shown; execution requires standard/verbose + Excel COM
97
97
  exstruct input.xlsx --alpha-col # output column keys as A, B, ..., AA
98
98
  exstruct input.xlsx --include-backend-metadata # include shape/chart backend metadata
99
99
  exstruct input.xlsx --mode light # cells + table candidates only
@@ -101,8 +101,8 @@ exstruct input.xlsx --mode libreoffice # best-effort extraction of shapes/co
101
101
  exstruct input.xlsx --pdf --image # PDF and PNGs (Excel COM required)
102
102
  ```
103
103
 
104
- Auto page-break export is available from both the API and the CLI when Excel/COM is available. The CLI exposes `--auto-page-breaks-dir` only in COM-capable environments.
105
- `mode=libreoffice` rejects `--pdf`, `--image`, and `--auto-page-breaks-dir` early. Use `standard` or `verbose` with Excel COM for those features.
104
+ Auto page-break export is available from both the API and the CLI when Excel/COM is available. The CLI always exposes `--auto-page-breaks-dir`, but validates it at execution time.
105
+ `mode=libreoffice` rejects `--pdf`, `--image`, and `--auto-page-breaks-dir` early, and `mode=light` also rejects `--auto-page-breaks-dir`. Use `standard` or `verbose` with Excel COM for those features.
106
106
  By default, the CLI keeps legacy 0-based numeric string column keys (`"0"`, `"1"`, ...). Use `--alpha-col` when you need Excel-style keys (`"A"`, `"B"`, ...).
107
107
  By default, serialized shape/chart output omits backend metadata (`provenance`, `approximation_level`, `confidence`) to reduce token usage. Use `--include-backend-metadata` or the corresponding Python/MCP option when you need it.
108
108
  Note: MCP `exstruct_extract` defaults to `options.alpha_col=true`, which differs from the CLI default (`false`).
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "exstruct"
3
- version = "0.7.0"
3
+ version = "0.7.1"
4
4
  description = "Excel to structured JSON (tables, shapes, charts) for LLM/RAG pipelines"
5
5
  readme = "README.md"
6
6
  license = { file = "LICENSE" }
@@ -2,53 +2,47 @@
2
2
 
3
3
  from __future__ import annotations
4
4
 
5
+ from collections.abc import Callable
5
6
  import logging
6
7
  from pathlib import Path
7
- from typing import Literal, TextIO
8
-
9
- from .core.cells import set_table_detection_params
10
- from .core.integrate import extract_workbook
11
- from .engine import (
12
- ColorsOptions,
13
- DestinationOptions,
14
- ExStructEngine,
15
- FilterOptions,
16
- FormatOptions,
17
- OutputOptions,
18
- StructOptions,
19
- )
20
- from .errors import (
21
- ConfigError,
22
- ExstructError,
23
- MissingDependencyError,
24
- PrintAreaError,
25
- RenderError,
26
- SerializationError,
27
- )
28
- from .io import (
29
- save_as_json,
30
- save_as_toon,
31
- save_as_yaml,
32
- save_auto_page_break_views,
33
- save_print_area_views,
34
- save_sheets,
35
- serialize_workbook,
36
- )
37
- from .models import (
38
- CellRow,
39
- Chart,
40
- ChartSeries,
41
- PrintArea,
42
- PrintAreaView,
43
- Shape,
44
- SheetData,
45
- WorkbookData,
46
- col_index_to_alpha,
47
- convert_row_keys_to_alpha,
48
- convert_sheet_keys_to_alpha,
49
- convert_workbook_keys_to_alpha,
50
- )
51
- from .render import export_pdf, export_sheet_images
8
+ from typing import TYPE_CHECKING, Literal, TextIO
9
+
10
+ if TYPE_CHECKING:
11
+ from .core.cells import set_table_detection_params
12
+ from .core.integrate import extract_workbook
13
+ from .engine import (
14
+ ColorsOptions,
15
+ DestinationOptions,
16
+ ExStructEngine,
17
+ FilterOptions,
18
+ FormatOptions,
19
+ OutputOptions,
20
+ StructOptions,
21
+ )
22
+ from .errors import (
23
+ ConfigError,
24
+ ExstructError,
25
+ MissingDependencyError,
26
+ PrintAreaError,
27
+ RenderError,
28
+ SerializationError,
29
+ )
30
+ from .io import serialize_workbook
31
+ from .models import (
32
+ CellRow,
33
+ Chart,
34
+ ChartSeries,
35
+ PrintArea,
36
+ PrintAreaView,
37
+ Shape,
38
+ SheetData,
39
+ WorkbookData,
40
+ col_index_to_alpha,
41
+ convert_row_keys_to_alpha,
42
+ convert_sheet_keys_to_alpha,
43
+ convert_workbook_keys_to_alpha,
44
+ )
45
+ from .render import export_pdf, export_sheet_images
52
46
 
53
47
  logger = logging.getLogger(__name__)
54
48
 
@@ -97,6 +91,110 @@ __all__ = [
97
91
 
98
92
  ExtractionMode = Literal["light", "libreoffice", "standard", "verbose"]
99
93
 
94
+ LazyExportLoader = Callable[[], object]
95
+
96
+
97
+ def _load_engine_attr(name: str) -> object:
98
+ from . import engine as engine_module
99
+
100
+ return getattr(engine_module, name)
101
+
102
+
103
+ def _load_error_attr(name: str) -> object:
104
+ from . import errors as errors_module
105
+
106
+ return getattr(errors_module, name)
107
+
108
+
109
+ def _load_model_attr(name: str) -> object:
110
+ from . import models as models_module
111
+
112
+ return getattr(models_module, name)
113
+
114
+
115
+ def _load_render_attr(name: str) -> object:
116
+ from . import render as render_module
117
+
118
+ return getattr(render_module, name)
119
+
120
+
121
+ def _load_io_attr(name: str) -> object:
122
+ from . import io as io_module
123
+
124
+ return getattr(io_module, name)
125
+
126
+
127
+ def _load_core_cells_attr(name: str) -> object:
128
+ from .core import cells as cells_module
129
+
130
+ return getattr(cells_module, name)
131
+
132
+
133
+ def _load_core_integrate_attr(name: str) -> object:
134
+ from .core import integrate as integrate_module
135
+
136
+ return getattr(integrate_module, name)
137
+
138
+
139
+ _LAZY_EXPORTS: dict[str, LazyExportLoader] = {
140
+ "ColorsOptions": lambda: _load_engine_attr("ColorsOptions"),
141
+ "ConfigError": lambda: _load_error_attr("ConfigError"),
142
+ "DestinationOptions": lambda: _load_engine_attr("DestinationOptions"),
143
+ "ExStructEngine": lambda: _load_engine_attr("ExStructEngine"),
144
+ "ExstructError": lambda: _load_error_attr("ExstructError"),
145
+ "FilterOptions": lambda: _load_engine_attr("FilterOptions"),
146
+ "FormatOptions": lambda: _load_engine_attr("FormatOptions"),
147
+ "MissingDependencyError": lambda: _load_error_attr("MissingDependencyError"),
148
+ "OutputOptions": lambda: _load_engine_attr("OutputOptions"),
149
+ "PrintArea": lambda: _load_model_attr("PrintArea"),
150
+ "PrintAreaError": lambda: _load_error_attr("PrintAreaError"),
151
+ "PrintAreaView": lambda: _load_model_attr("PrintAreaView"),
152
+ "RenderError": lambda: _load_error_attr("RenderError"),
153
+ "SerializationError": lambda: _load_error_attr("SerializationError"),
154
+ "StructOptions": lambda: _load_engine_attr("StructOptions"),
155
+ "WorkbookData": lambda: _load_model_attr("WorkbookData"),
156
+ "CellRow": lambda: _load_model_attr("CellRow"),
157
+ "Chart": lambda: _load_model_attr("Chart"),
158
+ "ChartSeries": lambda: _load_model_attr("ChartSeries"),
159
+ "Shape": lambda: _load_model_attr("Shape"),
160
+ "SheetData": lambda: _load_model_attr("SheetData"),
161
+ "col_index_to_alpha": lambda: _load_model_attr("col_index_to_alpha"),
162
+ "convert_row_keys_to_alpha": lambda: _load_model_attr("convert_row_keys_to_alpha"),
163
+ "convert_sheet_keys_to_alpha": lambda: _load_model_attr(
164
+ "convert_sheet_keys_to_alpha"
165
+ ),
166
+ "convert_workbook_keys_to_alpha": lambda: _load_model_attr(
167
+ "convert_workbook_keys_to_alpha"
168
+ ),
169
+ "export_pdf": lambda: _load_render_attr("export_pdf"),
170
+ "export_sheet_images": lambda: _load_render_attr("export_sheet_images"),
171
+ "extract_workbook": lambda: _load_core_integrate_attr("extract_workbook"),
172
+ "serialize_workbook": lambda: _load_io_attr("serialize_workbook"),
173
+ "set_table_detection_params": lambda: _load_core_cells_attr(
174
+ "set_table_detection_params"
175
+ ),
176
+ }
177
+
178
+
179
+ def _resolve_lazy_export(name: str) -> object:
180
+ value = _LAZY_EXPORTS[name]()
181
+ globals()[name] = value
182
+ return value
183
+
184
+
185
+ def _lazy_type(name: str) -> object:
186
+ return _resolve_lazy_export(name)
187
+
188
+
189
+ def __getattr__(name: str) -> object:
190
+ if name not in _LAZY_EXPORTS:
191
+ raise AttributeError(f"module {__name__!r} has no attribute {name!r}")
192
+ return _resolve_lazy_export(name)
193
+
194
+
195
+ def __dir__() -> list[str]:
196
+ return sorted(set(globals()) | set(__all__))
197
+
100
198
 
101
199
  def extract(
102
200
  file_path: str | Path, mode: ExtractionMode = "standard", *, alpha_col: bool = False
@@ -112,6 +210,8 @@ def extract(
112
210
  Returns:
113
211
  WorkbookData: Parsed workbook representation containing sheets, rows, shapes, charts, and print areas.
114
212
  """
213
+ from .engine import ExStructEngine, StructOptions
214
+
115
215
  include_links = True if mode == "verbose" else False
116
216
  include_colors_map = True if mode == "verbose" else None
117
217
  include_formulas_map = True if mode == "verbose" else None
@@ -157,6 +257,8 @@ def export(
157
257
  >>> export(wb, "out.json", pretty=True)
158
258
  >>> export(wb, "out.yaml", fmt="yaml") # doctest: +SKIP
159
259
  """
260
+ from .io import save_as_json, save_as_toon, save_as_yaml
261
+
160
262
  dest = Path(path)
161
263
  format_hint = (fmt or dest.suffix.lstrip(".") or "json").lower()
162
264
  match format_hint:
@@ -202,6 +304,8 @@ def export_sheets(
202
304
  >>> "Sheet1" in paths
203
305
  True
204
306
  """
307
+ from .io import save_sheets
308
+
205
309
  return save_sheets(
206
310
  data,
207
311
  Path(dir_path),
@@ -242,6 +346,8 @@ def export_sheets_as(
242
346
  >>> wb = extract("input.xlsx")
243
347
  >>> _ = export_sheets_as(wb, "out_yaml", fmt="yaml") # doctest: +SKIP
244
348
  """
349
+ from .io import save_sheets
350
+
245
351
  return save_sheets(
246
352
  data,
247
353
  Path(dir_path),
@@ -285,6 +391,8 @@ def export_print_areas_as(
285
391
  >>> isinstance(paths, dict)
286
392
  True
287
393
  """
394
+ from .io import save_print_area_views
395
+
288
396
  return save_print_area_views(
289
397
  data,
290
398
  Path(dir_path),
@@ -331,6 +439,9 @@ def export_auto_page_breaks(
331
439
  ... except PrintAreaError:
332
440
  ... pass
333
441
  """
442
+ from .errors import PrintAreaError
443
+ from .io import save_auto_page_break_views
444
+
334
445
  if not any(sheet.auto_print_areas for sheet in data.sheets.values()):
335
446
  message = "No auto page-break areas found. Enable COM-based auto page breaks before exporting."
336
447
  logger.warning(message)
@@ -407,6 +518,15 @@ def process_excel(
407
518
 
408
519
  >>> process_excel(Path("input.xlsx"), output_path=Path("out.json"), pdf=True) # doctest: +SKIP
409
520
  """
521
+ from .engine import (
522
+ DestinationOptions,
523
+ ExStructEngine,
524
+ FilterOptions,
525
+ FormatOptions,
526
+ OutputOptions,
527
+ StructOptions,
528
+ )
529
+
410
530
  engine = ExStructEngine(
411
531
  options=StructOptions(mode=mode, alpha_col=alpha_col),
412
532
  output=OutputOptions(
@@ -440,3 +560,19 @@ def process_excel(
440
560
  auto_page_breaks_dir=auto_page_breaks_dir,
441
561
  stream=stream,
442
562
  )
563
+
564
+
565
+ def _patch_runtime_annotations() -> None:
566
+ annotations_map: dict[Callable[..., object], dict[str, str]] = {
567
+ extract: {"return": "_lazy_type('WorkbookData')"},
568
+ export: {"data": "_lazy_type('WorkbookData')"},
569
+ export_sheets: {"data": "_lazy_type('WorkbookData')"},
570
+ export_sheets_as: {"data": "_lazy_type('WorkbookData')"},
571
+ export_print_areas_as: {"data": "_lazy_type('WorkbookData')"},
572
+ export_auto_page_breaks: {"data": "_lazy_type('WorkbookData')"},
573
+ }
574
+ for function, function_annotations in annotations_map.items():
575
+ function.__annotations__.update(function_annotations)
576
+
577
+
578
+ _patch_runtime_annotations()
@@ -22,7 +22,7 @@ class ComAvailability(BaseModel):
22
22
 
23
23
 
24
24
  def get_com_availability() -> ComAvailability:
25
- """Detect whether Excel COM is available for CLI features.
25
+ """Detect whether Excel COM is available for runtime CLI features.
26
26
 
27
27
  Returns:
28
28
  ComAvailability describing whether COM features can be used.