python-hwpx-automation 6.7.1__tar.gz → 7.0.2__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.
- {python_hwpx_automation-6.7.1/src/python_hwpx_automation.egg-info → python_hwpx_automation-7.0.2}/PKG-INFO +8 -11
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/README.md +6 -9
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/pyproject.toml +30 -4
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/content.py +14 -12
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/formatting.py +3 -3
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/errors.py +3 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/form_fill.py +52 -13
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/content_edit.py +28 -4
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/layout_style.py +36 -14
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/tracked_changes.py +12 -6
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/identity.json +20 -9
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/mixed_form.py +1 -1
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/blueprint/dump.py +2 -2
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/blueprint/mapping.py +4 -1
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/blueprint/native.py +3 -3
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/commands.py +3 -3
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/document.py +2 -2
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/__init__.py +47 -19
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/builder/core.py +50 -15
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/harvest.py +2 -2
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/presets/proposal.py +10 -10
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/evalplan/runtime.py +36 -1
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/exam/profile.py +1 -1
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/fit/seal.py +1 -1
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/template_formfit.py +1 -1
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/house_style/org_chart.py +3 -3
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/content_layout.py +39 -17
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/form_fields.py +108 -10
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/media.py +36 -6
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/memo_style.py +18 -6
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/package_validation.py +3 -3
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/read_query.py +3 -3
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/save_policy.py +15 -3
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/tables.py +4 -7
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/transactions.py +1 -1
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/quality_generation.py +14 -8
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/runtime.py +6 -1
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/tool_contract.py +4 -4
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/upstream.py +11 -11
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workspace.py +13 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2/src/python_hwpx_automation.egg-info}/PKG-INFO +8 -11
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/python_hwpx_automation.egg-info/requires.txt +1 -1
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/LICENSE +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/MANIFEST.in +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/NOTICE +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/setup.cfg +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/__init__.pyi +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/__main__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/agent_document.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/api.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/blind_eval.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/capabilities.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/compat.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/configuration.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/context.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/diff.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/document.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/handles.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/locations.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/locator.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/plan.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/resources.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/search.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/transactions.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/txn.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/document_state.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/execution_lock.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/fastmcp_adapter.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/form_output_models.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/_shared.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/agent_document.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/authoring.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/form_fill.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/quality_render.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/read_export.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/specialized.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/handlers/workflow.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/hwp_converter.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/hwp_support.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/hwpx_ops.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/identity.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ingest_adapters.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/markdown_plan.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/mcp_cli.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/metadata/tools_meta.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/mutation_models.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/network_policy.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/_batch_verification.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/blueprint/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/blueprint/bundle.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/blueprint/catalog.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/blueprint/model.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/blueprint/replay.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/catalog.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/cli.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/form_plan.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/model.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/path.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/query.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/agent/story.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/advanced_generators.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/builder/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/builder/report.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/_support.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/composer.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/plan.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profile.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/application_form/fragments/body.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/application_form/fragments/heading.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/application_form/fragments/info_table.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/application_form/fragments/title.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/application_form/profile.json +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/application_form/template.hwpx +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/home_notice/fragments/body.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/home_notice/fragments/heading.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/home_notice/fragments/title.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/home_notice/profile.json +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/home_notice/template.hwpx +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/official_notice/fragments/body.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/official_notice/fragments/heading.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/official_notice/fragments/info_table.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/official_notice/fragments/title.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/official_notice/profile.json +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/official_notice/template.hwpx +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/report/fragments/body.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/report/fragments/heading.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/report/fragments/info_table.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/report/fragments/title.xml +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/report/profile.json +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/profiles/report/template.hwpx +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/design/validator.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/presets/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/report_parser.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/style_profile.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/authoring/template_analyzer.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/charting/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/compliance/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/compliance/official_lint.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/compliance/pii.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/document_ops/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/document_ops/comparison.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/document_ops/mail_merge.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/document_ops/redline.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/evalplan/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/exam/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/exam/compose.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/exam/ir.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/exam/measure.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/exam/parser.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/classification.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/fill_residue.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/fit/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/fit/apply.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/fit/engine.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/fit/measure.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/fit/policy.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/fit/report.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/fit/wordbox.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/guidance.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/quality.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/form_fill/split_run.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/house_style/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/house_style/composition.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/house_style/data/bank.json +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/house_style/data/genres.json +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/house_style/gianmun.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/quality/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/quality/page_guard.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/_hancom_open_rate.ps1 +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/_refresh_hwpx_mac.applescript +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/_render_hwpx.ps1 +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/_render_hwpx_mac.applescript +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/block_splits.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/detectors.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/diff.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/fixture_corpus.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/oracle.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/page_qa.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/qa_contracts.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/qa_metrics.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/rendering/worker.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/utilities/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/office/utilities/table_compute.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/_border_fill.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/composition.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/context.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/planning.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/ops_services/preview_export.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/preview_output_models.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/public-modules.json +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/py.typed +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/quality.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/resources.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/runtime_services.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/server.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/storage.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/tool_bindings.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/utils/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/utils/helpers.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/visual_qa.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/__init__.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/adapters.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/dispatcher.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/models.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/policy.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/render_contracts.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/render_metrics.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/render_queue.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/render_security.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/render_transport.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/rendering.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/service.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/state_machine.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/workflow/store.py +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/python_hwpx_automation.egg-info/SOURCES.txt +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/python_hwpx_automation.egg-info/dependency_links.txt +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/python_hwpx_automation.egg-info/entry_points.txt +0 -0
- {python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/python_hwpx_automation.egg-info/top_level.txt +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: python-hwpx-automation
|
|
3
|
-
Version:
|
|
3
|
+
Version: 7.0.2
|
|
4
4
|
Summary: Task-oriented HWPX document automation for Python, with an optional MCP adapter.
|
|
5
5
|
Author: Kohkyuhyun
|
|
6
6
|
License-Expression: Apache-2.0
|
|
@@ -20,7 +20,7 @@ Requires-Python: >=3.10
|
|
|
20
20
|
Description-Content-Type: text/markdown
|
|
21
21
|
License-File: LICENSE
|
|
22
22
|
License-File: NOTICE
|
|
23
|
-
Requires-Dist: python-hwpx<6
|
|
23
|
+
Requires-Dist: python-hwpx<7,>=6.0.2
|
|
24
24
|
Requires-Dist: pydantic<3,>=2.11
|
|
25
25
|
Requires-Dist: cryptography>=42.0
|
|
26
26
|
Requires-Dist: anyio>=4.0
|
|
@@ -74,15 +74,12 @@ Dynamic: license-file
|
|
|
74
74
|
|
|
75
75
|
<!-- release-state: release-approved -->
|
|
76
76
|
> [!NOTE]
|
|
77
|
-
>
|
|
78
|
-
>
|
|
79
|
-
>
|
|
80
|
-
>
|
|
81
|
-
>
|
|
82
|
-
>
|
|
83
|
-
> Release·marketplace·실제 marketplace 설치까지 확인한 뒤에만 승격하며, 기존
|
|
84
|
-
> 5.x 설치는 별도 발행된 `hwpx-mcp-server 5.1.1`이 보호합니다. 절차와 상태
|
|
85
|
-
> 머신: [릴리스 runbook](docs/release-runbook.md)
|
|
77
|
+
> 공개 트레인: `python-hwpx 6.1.0 → python-hwpx-automation 7.0.1 →
|
|
78
|
+
> hwpx-plugin 2.0.0`. automation 7.0.2 패치(Windows 저장 수리 #98,
|
|
79
|
+
> 업로드 경로 안내 #75)가 release-approved 상태이며, 원격
|
|
80
|
+
> 진실(core·automation PyPI와 plugin GitHub
|
|
81
|
+
> Release·marketplace·실제 marketplace 설치) 관찰 전까지 공개 좌표를
|
|
82
|
+
> 승격하지 않습니다 — [릴리스 runbook](docs/release-runbook.md)
|
|
86
83
|
|
|
87
84
|
[python-hwpx](https://github.com/airmang/python-hwpx) 엔진 위에서 문서 저작·
|
|
88
85
|
양식 채움·시험지 조판·안전한 에이전트 워크플로를 제공하는 응용 계층입니다.
|
|
@@ -14,15 +14,12 @@
|
|
|
14
14
|
|
|
15
15
|
<!-- release-state: release-approved -->
|
|
16
16
|
> [!NOTE]
|
|
17
|
-
>
|
|
18
|
-
>
|
|
19
|
-
>
|
|
20
|
-
>
|
|
21
|
-
>
|
|
22
|
-
>
|
|
23
|
-
> Release·marketplace·실제 marketplace 설치까지 확인한 뒤에만 승격하며, 기존
|
|
24
|
-
> 5.x 설치는 별도 발행된 `hwpx-mcp-server 5.1.1`이 보호합니다. 절차와 상태
|
|
25
|
-
> 머신: [릴리스 runbook](docs/release-runbook.md)
|
|
17
|
+
> 공개 트레인: `python-hwpx 6.1.0 → python-hwpx-automation 7.0.1 →
|
|
18
|
+
> hwpx-plugin 2.0.0`. automation 7.0.2 패치(Windows 저장 수리 #98,
|
|
19
|
+
> 업로드 경로 안내 #75)가 release-approved 상태이며, 원격
|
|
20
|
+
> 진실(core·automation PyPI와 plugin GitHub
|
|
21
|
+
> Release·marketplace·실제 marketplace 설치) 관찰 전까지 공개 좌표를
|
|
22
|
+
> 승격하지 않습니다 — [릴리스 runbook](docs/release-runbook.md)
|
|
26
23
|
|
|
27
24
|
[python-hwpx](https://github.com/airmang/python-hwpx) 엔진 위에서 문서 저작·
|
|
28
25
|
양식 채움·시험지 조판·안전한 에이전트 워크플로를 제공하는 응용 계층입니다.
|
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "python-hwpx-automation"
|
|
7
|
-
version = "
|
|
7
|
+
version = "7.0.2"
|
|
8
8
|
description = "Task-oriented HWPX document automation for Python, with an optional MCP adapter."
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
authors = [{ name = "Kohkyuhyun" }]
|
|
@@ -24,12 +24,14 @@ classifiers = [
|
|
|
24
24
|
"Typing :: Typed",
|
|
25
25
|
]
|
|
26
26
|
dependencies = [
|
|
27
|
-
#
|
|
27
|
+
# 6.0 is the floor, not a preference: this package declares the `hwpx` console
|
|
28
28
|
# name that core used to own, and core only stops declaring it at 5.0. Pinning
|
|
29
29
|
# the bounded major here is what makes "no valid install has two declarers"
|
|
30
30
|
# true rather than hopeful, and prevents the next core major from silently
|
|
31
|
-
# breaking an already-published automation line.
|
|
32
|
-
|
|
31
|
+
# breaking an already-published automation line. WP-F (engine surface 6.0):
|
|
32
|
+
# this line adapted to the new namespace surface (design §9 WP-F) — the dev0
|
|
33
|
+
# pre-release qualifier tracks core's own not-yet-tagged 6.0 identity.
|
|
34
|
+
"python-hwpx>=6.0.2,<7", # HWPX object model, OXML/OPC, format-native primitives
|
|
33
35
|
|
|
34
36
|
"pydantic>=2.11,<3",
|
|
35
37
|
"cryptography>=42.0",
|
|
@@ -124,6 +126,30 @@ include = ["hwpx_automation*"]
|
|
|
124
126
|
# exercise, and their tests import them by bare name.
|
|
125
127
|
pythonpath = ["src", "scripts"]
|
|
126
128
|
addopts = "-q"
|
|
129
|
+
# WP-F (core 6.0 namespace adaptation, design §9): any DeprecationWarning this
|
|
130
|
+
# package's own code triggers by calling core's pre-7.0 legacy shim surface is
|
|
131
|
+
# a real regression -- error by default, and name each known non-automation
|
|
132
|
+
# source precisely rather than silencing DeprecationWarning wholesale.
|
|
133
|
+
filterwarnings = [
|
|
134
|
+
"error::DeprecationWarning",
|
|
135
|
+
# hwpx-core's own internal modules still call its pre-6.0 facade
|
|
136
|
+
# internally (core's own migration debt, not automation's -- out of this
|
|
137
|
+
# package's control/scope).
|
|
138
|
+
"ignore::DeprecationWarning:hwpx\\._document\\._legacy",
|
|
139
|
+
"ignore::DeprecationWarning:hwpx\\.form_fit\\.measure",
|
|
140
|
+
"ignore::DeprecationWarning:hwpx\\.ingest\\.hwpx_converter",
|
|
141
|
+
"ignore::DeprecationWarning:hwpx\\.tools\\.mail_merge",
|
|
142
|
+
"ignore::DeprecationWarning:hwpx\\.tools\\.redline",
|
|
143
|
+
# test_fuzz_harness_wired dynamically imports whichever co-located
|
|
144
|
+
# python-hwpx* sibling checkout happens to carry scripts/fuzz (by design
|
|
145
|
+
# it does not pin to PYTHON_HWPX_REPO -- see that test's own docstring);
|
|
146
|
+
# that checkout's migration state is outside this package's control.
|
|
147
|
+
"ignore::DeprecationWarning:fuzz\\.runner",
|
|
148
|
+
# SWIG-generated C-extension types (from a rendering/test dependency)
|
|
149
|
+
# lack __module__ on some builtin types under newer CPython -- a
|
|
150
|
+
# third-party artifact, never an hwpx-sourced warning.
|
|
151
|
+
"ignore:builtin type \\w+ has no __module__ attribute:DeprecationWarning",
|
|
152
|
+
]
|
|
127
153
|
|
|
128
154
|
[tool.mypy]
|
|
129
155
|
python_version = "3.10"
|
{python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/content.py
RENAMED
|
@@ -274,7 +274,9 @@ def delete_paragraph_from_doc(doc: HwpxDocument, paragraph_index: int) -> int:
|
|
|
274
274
|
return total
|
|
275
275
|
|
|
276
276
|
try:
|
|
277
|
-
|
|
277
|
+
# remove_paragraph is demoted in 6.0 with no namespace replacement
|
|
278
|
+
# (design table row 101) — the paragraph object owns .remove() now.
|
|
279
|
+
paragraphs[paragraph_index].remove()
|
|
278
280
|
except (ValueError, IndexError) as exc:
|
|
279
281
|
raise RuntimeError("삭제할 문단 요소를 섹션에서 찾을 수 없습니다.") from exc
|
|
280
282
|
return total - 1
|
|
@@ -317,19 +319,19 @@ def get_table_data(doc: HwpxDocument, table_index: int) -> dict:
|
|
|
317
319
|
|
|
318
320
|
def get_table_map_in_doc(doc: HwpxDocument) -> dict:
|
|
319
321
|
"""문서의 표 메타데이터를 LLM 친화적인 JSON 형태로 반환한다."""
|
|
320
|
-
result = doc.
|
|
322
|
+
result = doc.tables.map()
|
|
321
323
|
tables = list(result.get("tables", []))
|
|
322
324
|
return {"tables": tables, "count": len(tables)}
|
|
323
325
|
|
|
324
326
|
|
|
325
327
|
def find_cell_by_label_in_doc(doc: HwpxDocument, label_text: str, direction: str = "right") -> dict:
|
|
326
328
|
"""라벨 셀 기준으로 대상 셀을 찾는다."""
|
|
327
|
-
return doc.find_cell_by_label(label_text, direction=direction)
|
|
329
|
+
return doc.tables.find_cell_by_label(label_text, direction=direction)
|
|
328
330
|
|
|
329
331
|
|
|
330
332
|
def fill_by_path_in_doc(doc: HwpxDocument, mappings: dict[str, str]) -> dict:
|
|
331
333
|
"""라벨 기반 경로 구문으로 표 셀을 채운다."""
|
|
332
|
-
return doc.fill_by_path(mappings)
|
|
334
|
+
return doc.tables.fill_by_path(mappings)
|
|
333
335
|
|
|
334
336
|
|
|
335
337
|
def set_cell_text(
|
|
@@ -429,7 +431,7 @@ def _apply_table_border_fill(
|
|
|
429
431
|
col: int = None,
|
|
430
432
|
) -> str:
|
|
431
433
|
"""테두리/음영 borderFill을 만들어 표 전체 또는 한 셀에 적용한다."""
|
|
432
|
-
border_fill_id = doc.ensure_border_fill(
|
|
434
|
+
border_fill_id = doc.styles.ensure_border_fill(
|
|
433
435
|
border_type=border_type or "SOLID",
|
|
434
436
|
border_color=border_color or "#000000",
|
|
435
437
|
border_width=border_width or "0.12 mm",
|
|
@@ -736,20 +738,20 @@ def add_memo_to_doc(
|
|
|
736
738
|
create=True,
|
|
737
739
|
)
|
|
738
740
|
paragraph = resolved.paragraph
|
|
739
|
-
memo_count_before = len(doc.memos)
|
|
741
|
+
memo_count_before = len(doc.notes.memos)
|
|
740
742
|
try:
|
|
741
|
-
doc.
|
|
743
|
+
doc.notes.add_memo(text or "", anchor=paragraph)
|
|
742
744
|
except Exception as exc: # noqa: BLE001
|
|
743
745
|
if not _looks_like_mixed_xml_type_error(exc):
|
|
744
746
|
raise
|
|
745
747
|
# Clean up any partially-created memo from the failed native call
|
|
746
|
-
current_memos = doc.memos
|
|
748
|
+
current_memos = doc.notes.memos
|
|
747
749
|
while len(current_memos) > memo_count_before:
|
|
748
750
|
try:
|
|
749
|
-
doc.remove_memo(current_memos[-1])
|
|
751
|
+
doc.notes.remove_memo(current_memos[-1])
|
|
750
752
|
except Exception: # noqa: BLE001
|
|
751
753
|
break
|
|
752
|
-
current_memos = doc.memos
|
|
754
|
+
current_memos = doc.notes.memos
|
|
753
755
|
logger.warning("메모 추가 중 혼합 XML 타입 충돌 감지, fallback 경로 사용: %s", exc)
|
|
754
756
|
_add_memo_with_anchor_fallback(paragraph, text or "")
|
|
755
757
|
return {"memo_added": True, "location": resolved.location}
|
|
@@ -775,9 +777,9 @@ def remove_memo_from_doc(
|
|
|
775
777
|
if memo_id:
|
|
776
778
|
memo_ids.add(memo_id)
|
|
777
779
|
|
|
778
|
-
for memo in list(doc.memos):
|
|
780
|
+
for memo in list(doc.notes.memos):
|
|
779
781
|
if memo.id in memo_ids:
|
|
780
|
-
doc.remove_memo(memo)
|
|
782
|
+
doc.notes.remove_memo(memo)
|
|
781
783
|
|
|
782
784
|
removed_anchor = False
|
|
783
785
|
for run_element in _memo_anchor_runs(paragraph, memo_ids):
|
{python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/core/formatting.py
RENAMED
|
@@ -406,10 +406,10 @@ def create_style_in_doc(
|
|
|
406
406
|
name = (style_name or "").strip()
|
|
407
407
|
if not name:
|
|
408
408
|
raise ValueError("style_name cannot be empty")
|
|
409
|
-
if not doc.headers:
|
|
409
|
+
if not doc.parts.headers:
|
|
410
410
|
raise RuntimeError("document does not contain any headers to host styles")
|
|
411
411
|
|
|
412
|
-
header = doc.headers[0]
|
|
412
|
+
header = doc.parts.headers[0]
|
|
413
413
|
styles_element = document_styles_element(doc)
|
|
414
414
|
|
|
415
415
|
for style in _iter_unique_styles(doc):
|
|
@@ -427,7 +427,7 @@ def create_style_in_doc(
|
|
|
427
427
|
}
|
|
428
428
|
|
|
429
429
|
base_style_id = _default_base_style_id(doc)
|
|
430
|
-
base_style = doc.
|
|
430
|
+
base_style = doc.styles.get(base_style_id)
|
|
431
431
|
if base_style is None:
|
|
432
432
|
raise RuntimeError(f"failed to resolve base style id: {base_style_id}")
|
|
433
433
|
|
|
@@ -36,6 +36,7 @@ class CommonErrorModel(BaseModel):
|
|
|
36
36
|
|
|
37
37
|
|
|
38
38
|
ERROR_CODE_TO_MCP_CODE: dict[str, int] = {
|
|
39
|
+
"CLIENT_UPLOAD_PATH_UNAVAILABLE": -32602,
|
|
39
40
|
"DOCUMENT_NOT_FOUND": -32044,
|
|
40
41
|
"PERMISSION_DENIED": -32043,
|
|
41
42
|
"TABLE_INDEX_OUT_OF_RANGE": -32042,
|
|
@@ -57,6 +58,7 @@ DEFAULT_ERROR_SUGGESTIONS: dict[str, str] = {
|
|
|
57
58
|
"AMBIGUOUS_TARGET": "검색 조건을 더 구체화하거나 limit=1로 미리보기를 다시 생성하세요.",
|
|
58
59
|
"BYTE_PATCH_OPEN_SAFETY_FAILED": "반환된 openSafety 진단을 확인하고 일반 저장/복구 경로로 다시 생성하세요.",
|
|
59
60
|
"CAPABILITY_SKEW": "core/automation/plugin ToolSpec 계약 불일치로 쓰기가 차단되었습니다. mcp_server_health의 최소 버전과 contract hash에 맞춰 다시 설치한 뒤 호스트를 재시작하세요.",
|
|
61
|
+
"CLIENT_UPLOAD_PATH_UNAVAILABLE": "대화에 업로드된 파일의 내부 경로는 로컬 MCP 서버에서 읽을 수 없습니다. 파일을 PC에 저장한 뒤 실제 로컬 경로를 전달하세요.",
|
|
60
62
|
"FIELD_OVERFLOW": "값이 칸에 넘칩니다. fitPolicy(mode=wrap_then_shrink/shrink/truncate_with_report) 또는 overflow=warn으로 다시 채우거나 값을 줄이세요. details.visualComplete.suggestedRetry 참고.",
|
|
61
63
|
"STALE_LINESEG_DETECTED": "오래된 lineseg 레이아웃 캐시가 남았습니다. 해당 문단을 다시 편집해 캐시를 무효화한 뒤 저장하세요.",
|
|
62
64
|
"VISUAL_COMPLETE_FAILED": "한컴 렌더에서 겹침/넘침 등 시각 결함이 감지되었습니다. details.visualComplete를 확인하고 수정 후 다시 저장하세요.",
|
|
@@ -120,6 +122,7 @@ def category_for_error(error_code: str) -> ErrorCategory:
|
|
|
120
122
|
if error_code.startswith("NETWORK_"):
|
|
121
123
|
return "network"
|
|
122
124
|
if error_code in {
|
|
125
|
+
"CLIENT_UPLOAD_PATH_UNAVAILABLE",
|
|
123
126
|
"INVALID_ARGUMENT",
|
|
124
127
|
"WORKSPACE_PATH_INVALID",
|
|
125
128
|
"DOCUMENT_LOCATOR_REQUIRED",
|
{python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/form_fill.py
RENAMED
|
@@ -311,7 +311,10 @@ def apply_form_fill_workflow(
|
|
|
311
311
|
if mapping.get("kind") == "form-field":
|
|
312
312
|
before_fields = _document_form_fields(doc)
|
|
313
313
|
before_field = _find_form_field_by_mapping(before_fields, mapping)
|
|
314
|
-
|
|
314
|
+
# fields.fill now returns a frozen FieldFillResult rather
|
|
315
|
+
# than a dict (design §2.3) — read its attributes directly
|
|
316
|
+
# instead of the old after_value/style_before/... dict keys.
|
|
317
|
+
fill_result = doc.fields.fill(
|
|
315
318
|
str(mapping.get("value", "")),
|
|
316
319
|
field_index=int(mapping["field_index"]),
|
|
317
320
|
)
|
|
@@ -320,10 +323,10 @@ def apply_form_fill_workflow(
|
|
|
320
323
|
{
|
|
321
324
|
**mapping,
|
|
322
325
|
"before_text": mask_pii(_before_ff, DEFAULT_POLICY) if mask else _before_ff,
|
|
323
|
-
"after_text": fill_result
|
|
324
|
-
"style_before": fill_result.
|
|
325
|
-
"style_after": fill_result.
|
|
326
|
-
"style_preserved": bool(fill_result.
|
|
326
|
+
"after_text": fill_result.after,
|
|
327
|
+
"style_before": list(fill_result.style_before),
|
|
328
|
+
"style_after": list(fill_result.style_after),
|
|
329
|
+
"style_preserved": bool(fill_result.style_preserved),
|
|
327
330
|
}
|
|
328
331
|
)
|
|
329
332
|
elif mapping.get("kind") == "cell":
|
|
@@ -589,7 +592,7 @@ def _build_mapping_analysis(doc: Any, canonical_input: dict[str, Any]) -> dict[s
|
|
|
589
592
|
if native_mapping is not None:
|
|
590
593
|
resolved.append(native_mapping)
|
|
591
594
|
continue
|
|
592
|
-
matches = doc.find_cell_by_label(label, direction=direction).get("matches", [])
|
|
595
|
+
matches = doc.tables.find_cell_by_label(label, direction=direction).get("matches", [])
|
|
593
596
|
if len(matches) == 1:
|
|
594
597
|
match = matches[0]
|
|
595
598
|
cell = match["target_cell"]
|
|
@@ -681,14 +684,50 @@ def _build_mapping_analysis(doc: Any, canonical_input: dict[str, Any]) -> dict[s
|
|
|
681
684
|
return {"resolved": resolved, "unresolved": unresolved, "formFields": form_field_strategy}
|
|
682
685
|
|
|
683
686
|
|
|
687
|
+
def _form_field_to_legacy_dict(field: Any, *, index: int) -> dict[str, Any]:
|
|
688
|
+
"""Rebuild the 5.x form-field dict shape from a 6.0 ``FormField`` view.
|
|
689
|
+
|
|
690
|
+
Mirrors ``ops_services.form_fields._form_field_to_legacy_dict`` — kept
|
|
691
|
+
local (not imported) since this lower-level workflow module sits below
|
|
692
|
+
the service layer and importing from it would invert that dependency
|
|
693
|
+
direction. ``index`` is load-bearing here: downstream mapping resolution
|
|
694
|
+
(``_resolved_explicit_form_field_mapping``/``_find_form_field_by_mapping``)
|
|
695
|
+
matches on ``field["index"]`` to build ``field_index=`` fill targets.
|
|
696
|
+
"""
|
|
697
|
+
|
|
698
|
+
location = field.location
|
|
699
|
+
return {
|
|
700
|
+
"index": index,
|
|
701
|
+
"field_id": field.field_id,
|
|
702
|
+
"id": field.field_id,
|
|
703
|
+
"fieldid": field.field_id,
|
|
704
|
+
"name": field.name,
|
|
705
|
+
"prompt": field.prompt,
|
|
706
|
+
"instruction": field.prompt,
|
|
707
|
+
"memo": field.memo,
|
|
708
|
+
"dirty": field.element.get("dirty", ""),
|
|
709
|
+
"is_placeholder": field.is_placeholder,
|
|
710
|
+
"current_value": field.value,
|
|
711
|
+
"field_type": field.field_type,
|
|
712
|
+
"control_type": field.field_type,
|
|
713
|
+
"section_index": location.section_index,
|
|
714
|
+
"paragraph_index": location.paragraph_index,
|
|
715
|
+
"paragraph_index_in_section": location.paragraph_index_in_section,
|
|
716
|
+
"run_index": location.run_index,
|
|
717
|
+
"child_index": location.child_index,
|
|
718
|
+
"has_end": field.has_end,
|
|
719
|
+
"parameters": [parameter.to_dict() for parameter in field.parameters],
|
|
720
|
+
}
|
|
721
|
+
|
|
722
|
+
|
|
684
723
|
def _document_form_fields(doc: Any) -> list[dict[str, Any]]:
|
|
685
|
-
|
|
686
|
-
|
|
687
|
-
|
|
688
|
-
|
|
689
|
-
|
|
690
|
-
|
|
691
|
-
|
|
724
|
+
# fields.all now returns tuple[FormField, ...] rather than list[dict]
|
|
725
|
+
# (design §2.3/§2.5) — reconstruct the established dict shape since
|
|
726
|
+
# FormField has no to_dict() of its own.
|
|
727
|
+
return [
|
|
728
|
+
_form_field_to_legacy_dict(field, index=index)
|
|
729
|
+
for index, field in enumerate(doc.fields.all)
|
|
730
|
+
]
|
|
692
731
|
|
|
693
732
|
|
|
694
733
|
def _normalize_match_text(value: Any) -> str:
|
|
@@ -787,7 +787,10 @@ def insert_picture(
|
|
|
787
787
|
section_index=section_index,
|
|
788
788
|
align=align,
|
|
789
789
|
)
|
|
790
|
-
|
|
790
|
+
# media.picture_references now returns tuple[PictureRef, ...] rather
|
|
791
|
+
# than list[dict] (design §2.5) — .to_dict() per entry keeps this
|
|
792
|
+
# handler's own dict-shaped response unchanged.
|
|
793
|
+
picture_refs = [ref.to_dict() for ref in doc.media.picture_references()]
|
|
791
794
|
result = {
|
|
792
795
|
"ok": True,
|
|
793
796
|
"filename": filename,
|
|
@@ -821,19 +824,40 @@ def replace_picture(
|
|
|
821
824
|
target_path = resolve_path(output) if output else path
|
|
822
825
|
doc = open_doc(path)
|
|
823
826
|
image_data = _decode_image_base64(image_base64)
|
|
824
|
-
|
|
827
|
+
# media.replace_picture now returns a frozen PictureReplacement (design
|
|
828
|
+
# §2.4) whose own .to_dict() uses different field names than this op's
|
|
829
|
+
# established response contract (old_binaryItemIDRef/new_binaryItemIDRef/
|
|
830
|
+
# removedOldImage/geometryPreserved/picture_index/section_index), which
|
|
831
|
+
# existing callers/tests depend on — rebuild that exact shape instead.
|
|
832
|
+
replacement = doc.media.replace_picture(
|
|
825
833
|
image_data,
|
|
826
834
|
image_format,
|
|
827
835
|
picture_index=picture_index,
|
|
828
836
|
binary_item_id_ref=binary_item_id_ref,
|
|
829
837
|
remove_orphaned=remove_orphaned,
|
|
830
838
|
)
|
|
839
|
+
replaced_section_index = next(
|
|
840
|
+
(
|
|
841
|
+
index
|
|
842
|
+
for index, section in enumerate(doc.sections)
|
|
843
|
+
if section.element is replacement.picture.paragraph.section.element
|
|
844
|
+
),
|
|
845
|
+
None,
|
|
846
|
+
)
|
|
847
|
+
replacement_payload = {
|
|
848
|
+
"picture_index": picture_index,
|
|
849
|
+
"section_index": replaced_section_index,
|
|
850
|
+
"old_binaryItemIDRef": replacement.previous_item_id,
|
|
851
|
+
"new_binaryItemIDRef": replacement.item_id,
|
|
852
|
+
"removedOldImage": bool(replacement.removed_orphans),
|
|
853
|
+
"geometryPreserved": True,
|
|
854
|
+
}
|
|
831
855
|
result = {
|
|
832
856
|
"ok": True,
|
|
833
857
|
"filename": filename,
|
|
834
858
|
"outputPath": target_path,
|
|
835
|
-
"replacement":
|
|
836
|
-
"pictureReferences": doc.picture_references(),
|
|
859
|
+
"replacement": replacement_payload,
|
|
860
|
+
"pictureReferences": [ref.to_dict() for ref in doc.media.picture_references()],
|
|
837
861
|
"idIntegrity": _id_integrity_payload(doc),
|
|
838
862
|
}
|
|
839
863
|
if dry_run:
|
|
@@ -294,7 +294,10 @@ def set_paragraph_format(
|
|
|
294
294
|
if guard is not None:
|
|
295
295
|
return guard
|
|
296
296
|
doc = open_doc(path)
|
|
297
|
-
|
|
297
|
+
# apply_paragraph_format now returns a frozen ParagraphFormatResult
|
|
298
|
+
# (design §2.4) rather than a dict — .to_dict() keeps this handler's own
|
|
299
|
+
# dict-shaped response (filename merged below) unchanged.
|
|
300
|
+
result = doc.styles.apply_paragraph_format(
|
|
298
301
|
paragraph_index=paragraph_index,
|
|
299
302
|
paragraph_indexes=paragraph_indexes,
|
|
300
303
|
alignment=alignment,
|
|
@@ -308,7 +311,7 @@ def set_paragraph_format(
|
|
|
308
311
|
keep_with_next=keep_with_next,
|
|
309
312
|
keep_lines=keep_lines,
|
|
310
313
|
page_break_before=page_break_before,
|
|
311
|
-
)
|
|
314
|
+
).to_dict()
|
|
312
315
|
result["filename"] = filename
|
|
313
316
|
if dry_run:
|
|
314
317
|
return _with_dry_run_verification(result, doc, path)
|
|
@@ -342,7 +345,10 @@ def set_page_setup(
|
|
|
342
345
|
if guard is not None:
|
|
343
346
|
return guard
|
|
344
347
|
doc = open_doc(path)
|
|
345
|
-
|
|
348
|
+
# page.setup now returns a frozen PageSetup (design §2.4) rather than a
|
|
349
|
+
# dict — .to_dict() keeps this handler's own dict-shaped response
|
|
350
|
+
# (filename merged below) unchanged.
|
|
351
|
+
result = doc.page.setup(
|
|
346
352
|
paper_size=paper_size,
|
|
347
353
|
width_mm=width_mm,
|
|
348
354
|
height_mm=height_mm,
|
|
@@ -358,7 +364,7 @@ def set_page_setup(
|
|
|
358
364
|
columns=columns,
|
|
359
365
|
column_gap_mm=column_gap_mm,
|
|
360
366
|
section_index=section_index,
|
|
361
|
-
)
|
|
367
|
+
).to_dict()
|
|
362
368
|
result["filename"] = filename
|
|
363
369
|
if dry_run:
|
|
364
370
|
return _with_dry_run_verification(result, doc, path)
|
|
@@ -398,13 +404,26 @@ def set_header_footer(
|
|
|
398
404
|
if guard is not None:
|
|
399
405
|
return guard
|
|
400
406
|
doc = open_doc(path)
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
407
|
+
# set_header_footer is demoted in 6.0 with no namespace replacement
|
|
408
|
+
# (design table row 102, kind= dispatch removed) — dispatch here
|
|
409
|
+
# instead, replicating the normalization the removed method used to do.
|
|
410
|
+
normalized_kind = kind.strip().lower() if isinstance(kind, str) else kind
|
|
411
|
+
if normalized_kind == "header":
|
|
412
|
+
wrapper = doc.page.set_header(
|
|
413
|
+
text=text,
|
|
414
|
+
content=content,
|
|
415
|
+
section_index=section_index,
|
|
416
|
+
page_type=page_type,
|
|
417
|
+
)
|
|
418
|
+
elif normalized_kind == "footer":
|
|
419
|
+
wrapper = doc.page.set_footer(
|
|
420
|
+
text=text,
|
|
421
|
+
content=content,
|
|
422
|
+
section_index=section_index,
|
|
423
|
+
page_type=page_type,
|
|
424
|
+
)
|
|
425
|
+
else:
|
|
426
|
+
raise ValueError("kind must be 'header' or 'footer'")
|
|
408
427
|
result = {
|
|
409
428
|
"filename": filename,
|
|
410
429
|
"headerFooter": _header_footer_payload(wrapper, kind=kind, page_type=page_type),
|
|
@@ -435,7 +454,7 @@ def set_page_number(
|
|
|
435
454
|
if guard is not None:
|
|
436
455
|
return guard
|
|
437
456
|
doc = open_doc(path)
|
|
438
|
-
wrapper = doc.set_page_number(
|
|
457
|
+
wrapper = doc.page.set_page_number(
|
|
439
458
|
target=target,
|
|
440
459
|
page_type=page_type,
|
|
441
460
|
format=format,
|
|
@@ -478,7 +497,10 @@ def set_list_format(
|
|
|
478
497
|
if guard is not None:
|
|
479
498
|
return guard
|
|
480
499
|
doc = open_doc(path)
|
|
481
|
-
|
|
500
|
+
# apply_list_format now returns a frozen ListFormatResult (design §2.4)
|
|
501
|
+
# rather than a dict — .to_dict() keeps this handler's own dict-shaped
|
|
502
|
+
# response (filename merged below) unchanged.
|
|
503
|
+
result = doc.styles.apply_list_format(
|
|
482
504
|
paragraph_index=paragraph_index,
|
|
483
505
|
paragraph_indexes=paragraph_indexes,
|
|
484
506
|
kind=kind,
|
|
@@ -486,7 +508,7 @@ def set_list_format(
|
|
|
486
508
|
bullet_char=bullet_char,
|
|
487
509
|
number_format=number_format,
|
|
488
510
|
start=start,
|
|
489
|
-
)
|
|
511
|
+
).to_dict()
|
|
490
512
|
result["filename"] = filename
|
|
491
513
|
if dry_run:
|
|
492
514
|
return _with_dry_run_verification(result, doc, path)
|
|
@@ -483,30 +483,36 @@ def add_tracked_edit(
|
|
|
483
483
|
paragraph = doc.paragraphs[paragraph_index]
|
|
484
484
|
before_text = _tracked_paragraph_text(paragraph)
|
|
485
485
|
if edit_type == "insert":
|
|
486
|
-
|
|
486
|
+
# tracking.insert/delete/replace now return TrackedChange /
|
|
487
|
+
# TrackedReplacement objects rather than bare int/tuple
|
|
488
|
+
# (design §2.6) — .change_id (and .delete/.insert for the
|
|
489
|
+
# replace case, in the same delete-then-insert order 5.x
|
|
490
|
+
# returned) keeps this handler's own int-list response shape
|
|
491
|
+
# unchanged.
|
|
492
|
+
change = doc.tracking.insert(
|
|
487
493
|
paragraph,
|
|
488
494
|
edit["text"],
|
|
489
495
|
author=author,
|
|
490
496
|
date=normalized_date,
|
|
491
497
|
)
|
|
492
|
-
change_ids = [change_id]
|
|
498
|
+
change_ids = [change.change_id]
|
|
493
499
|
elif edit_type == "delete":
|
|
494
|
-
|
|
500
|
+
change = doc.tracking.delete(
|
|
495
501
|
paragraph,
|
|
496
502
|
match=edit.get("match"),
|
|
497
503
|
author=author,
|
|
498
504
|
date=normalized_date,
|
|
499
505
|
)
|
|
500
|
-
change_ids = [change_id]
|
|
506
|
+
change_ids = [change.change_id]
|
|
501
507
|
elif edit_type == "replace":
|
|
502
|
-
|
|
508
|
+
replacement = doc.tracking.replace(
|
|
503
509
|
paragraph,
|
|
504
510
|
edit["old"],
|
|
505
511
|
edit["new"],
|
|
506
512
|
author=author,
|
|
507
513
|
date=normalized_date,
|
|
508
514
|
)
|
|
509
|
-
change_ids =
|
|
515
|
+
change_ids = [replacement.delete.change_id, replacement.insert.change_id]
|
|
510
516
|
else: # pragma: no cover - validation prevents this branch
|
|
511
517
|
raise ValueError(f"unsupported tracked edit type: {edit_type}")
|
|
512
518
|
edit_results.append(
|
{python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/identity.json
RENAMED
|
@@ -5,23 +5,34 @@
|
|
|
5
5
|
"releaseState": {
|
|
6
6
|
"status": "release-approved",
|
|
7
7
|
"candidate": {
|
|
8
|
-
"pythonHwpx": "
|
|
8
|
+
"pythonHwpx": "6.1.0",
|
|
9
9
|
"canonicalDistribution": "python-hwpx-automation",
|
|
10
|
-
"canonicalAutomation": "
|
|
10
|
+
"canonicalAutomation": "7.0.2",
|
|
11
11
|
"compatibilityDistribution": "hwpx-mcp-server",
|
|
12
|
-
"compatibility": "
|
|
13
|
-
"plugin": "
|
|
14
|
-
"contractHash": "
|
|
12
|
+
"compatibility": "7.0.2",
|
|
13
|
+
"plugin": "2.0.0",
|
|
14
|
+
"contractHash": "34a91560759dc47a"
|
|
15
15
|
},
|
|
16
16
|
"currentPublic": {
|
|
17
|
-
"pythonHwpx": "
|
|
17
|
+
"pythonHwpx": "6.1.0",
|
|
18
18
|
"primaryDistribution": "python-hwpx-automation",
|
|
19
|
-
"primaryApplication": "
|
|
20
|
-
"plugin": "
|
|
21
|
-
"contractHash": "
|
|
19
|
+
"primaryApplication": "7.0.1",
|
|
20
|
+
"plugin": "2.0.0",
|
|
21
|
+
"contractHash": "34a91560759dc47a"
|
|
22
22
|
},
|
|
23
23
|
"promotionGate": "Three states are mandatory: unreleased-candidate while auditing; release-approved only after separate owner approval and while currentPublic still names the previously observed coherent stack; released only in a follow-up commit after remote truth is observed for core, canonical automation, the compatibility distribution, the plugin GitHub release, the marketplace entry, and a real marketplace install. The automation tag workflow publishes only release-approved, leaves currentPublic unchanged, and hands an attached receipt to plugin publication."
|
|
24
24
|
},
|
|
25
|
+
"releaseFloors": {
|
|
26
|
+
"description": "Frozen historical coordinates. Unlike releaseState these do not advance train by train; they pin the pre-6.0 legacy compatibility cap that every core 5 resolution must be observed against. They live here so the release path has no version literal that is not declared data.",
|
|
27
|
+
"legacyCompatibilityDistribution": "hwpx-mcp-server",
|
|
28
|
+
"legacyCompatibilityVersion": "5.1.1",
|
|
29
|
+
"legacyCoreVersion": "4.2.0",
|
|
30
|
+
"legacyCoreSpecifiers": [
|
|
31
|
+
">=4.2.0",
|
|
32
|
+
"<5"
|
|
33
|
+
],
|
|
34
|
+
"legacyCoreRequirementCount": 3
|
|
35
|
+
},
|
|
25
36
|
"identifiers": [
|
|
26
37
|
{
|
|
27
38
|
"surface": "repository",
|
{python_hwpx_automation-6.7.1 → python_hwpx_automation-7.0.2}/src/hwpx_automation/mixed_form.py
RENAMED
|
@@ -2393,7 +2393,7 @@ def _specialized_allowed_members(source_bytes: bytes) -> set[str]:
|
|
|
2393
2393
|
members = {str(section.part_name) for section in document.document.sections}
|
|
2394
2394
|
members.update(
|
|
2395
2395
|
str(header.part_name)
|
|
2396
|
-
for header in getattr(document.document, "headers", ())
|
|
2396
|
+
for header in getattr(document.document.parts, "headers", ())
|
|
2397
2397
|
)
|
|
2398
2398
|
if not members:
|
|
2399
2399
|
raise ValueError("specialized form operation has no editable document members")
|
|
@@ -115,7 +115,7 @@ def _numbering_properties(agent: HwpxAgentDocument, record: NodeRecord) -> dict[
|
|
|
115
115
|
if record.kind != "paragraph":
|
|
116
116
|
return None
|
|
117
117
|
paragraph = record.native
|
|
118
|
-
para_pr = agent.document.paragraph_property(paragraph.element.get("paraPrIDRef"))
|
|
118
|
+
para_pr = agent.document.styles.paragraph_property(paragraph.element.get("paraPrIDRef"))
|
|
119
119
|
heading = para_pr.heading if para_pr is not None else None
|
|
120
120
|
if heading is None or not heading.type or str(heading.type).upper() == "NONE":
|
|
121
121
|
return None
|
|
@@ -143,7 +143,7 @@ def _numbering_properties(agent: HwpxAgentDocument, record: NodeRecord) -> dict[
|
|
|
143
143
|
def _style_dependency(agent: HwpxAgentDocument, record: NodeRecord) -> dict[str, Any] | None:
|
|
144
144
|
if record.kind == "paragraph":
|
|
145
145
|
paragraph = record.native
|
|
146
|
-
style = agent.document.
|
|
146
|
+
style = agent.document.styles.get(paragraph.element.get("styleIDRef"))
|
|
147
147
|
properties = {
|
|
148
148
|
"category": "paragraph",
|
|
149
149
|
"name": record.summary.get("style"),
|
|
@@ -299,8 +299,11 @@ def materialize_dependencies(
|
|
|
299
299
|
elif family == "resource":
|
|
300
300
|
asset_path = str(properties["assetPath"])
|
|
301
301
|
suffix = asset_path.rsplit(".", 1)[-1]
|
|
302
|
+
# media.add_image now returns a BinaryItem rather than a bare
|
|
303
|
+
# str (design §2.6) — str(...) is the documented migration
|
|
304
|
+
# buffer (item_id), keeping this identity payload a plain string.
|
|
302
305
|
item["identity"] = {
|
|
303
|
-
"binaryItemIDRef": document.add_image(assets[asset_path], suffix),
|
|
306
|
+
"binaryItemIDRef": str(document.media.add_image(assets[asset_path], suffix)),
|
|
304
307
|
"mediaType": properties["mediaType"],
|
|
305
308
|
}
|
|
306
309
|
else: # pragma: no cover - validated dependency family exhaustiveness
|