athena-python-docx 0.40.0__tar.gz → 0.41.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 (498) hide show
  1. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/AGENTS.md +37 -19
  2. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/PKG-INFO +1 -1
  3. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/__init__.py +1 -1
  4. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/comments.py +62 -1
  5. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/text/paragraph.py +41 -11
  6. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/pyproject.toml +1 -1
  7. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/live/fixture_scripts.py +318 -0
  8. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/intentional_deviations.json +1 -9
  9. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_comments.py +132 -0
  10. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_hyperlink_coalescing.py +43 -0
  11. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_rendered_page_breaks.py +24 -0
  12. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/uv.lock +1 -1
  13. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/.gitignore +0 -0
  14. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/CLAUDE.md +0 -0
  15. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/DOCX_EXEC_LAB.md +0 -0
  16. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/README.md +0 -0
  17. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_athena_extension.py +0 -0
  18. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_batching.py +0 -0
  19. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_buffer.py +0 -0
  20. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_capabilities.py +0 -0
  21. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_citations.py +0 -0
  22. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_execution.py +0 -0
  23. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_http.py +0 -0
  24. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_http_doc.py +0 -0
  25. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_image_utils.py +0 -0
  26. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_postproc.py +0 -0
  27. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_proxy.py +0 -0
  28. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_ptc.py +0 -0
  29. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_references.py +0 -0
  30. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_run_order.py +0 -0
  31. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_table_styles.py +0 -0
  32. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_timeouts.py +0 -0
  33. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_tracked.py +0 -0
  34. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/_xml_text.py +0 -0
  35. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/api.py +0 -0
  36. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/blkcntnr.py +0 -0
  37. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/bookmarks.py +0 -0
  38. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/charts.py +0 -0
  39. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/client.py +0 -0
  40. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/commands.py +0 -0
  41. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/document.py +0 -0
  42. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/drawing/__init__.py +0 -0
  43. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/enum/__init__.py +0 -0
  44. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/enum/base.py +0 -0
  45. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/enum/dml.py +0 -0
  46. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/enum/section.py +0 -0
  47. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/enum/shape.py +0 -0
  48. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/enum/style.py +0 -0
  49. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/enum/table.py +0 -0
  50. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/enum/text.py +0 -0
  51. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/errors.py +0 -0
  52. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/exceptions.py +0 -0
  53. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/fields.py +0 -0
  54. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/footnotes.py +0 -0
  55. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/image/__init__.py +0 -0
  56. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/image/exceptions.py +0 -0
  57. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/image/image.py +0 -0
  58. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/math.py +0 -0
  59. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/opc/__init__.py +0 -0
  60. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/opc/coreprops.py +0 -0
  61. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/oxml/__init__.py +0 -0
  62. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/revisions.py +0 -0
  63. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/sdt.py +0 -0
  64. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/section.py +0 -0
  65. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/session.py +0 -0
  66. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/settings.py +0 -0
  67. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/shape.py +0 -0
  68. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/shared.py +0 -0
  69. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/styles/__init__.py +0 -0
  70. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/styles/_table.py +0 -0
  71. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/styles/latent.py +0 -0
  72. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/styles/style.py +0 -0
  73. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/styles/styles.py +0 -0
  74. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/table.py +0 -0
  75. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/text/__init__.py +0 -0
  76. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/text/font.py +0 -0
  77. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/text/hyperlink.py +0 -0
  78. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/text/pagebreak.py +0 -0
  79. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/text/parfmt.py +0 -0
  80. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/text/run.py +0 -0
  81. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/text/tabstops.py +0 -0
  82. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/toc.py +0 -0
  83. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/docx/typing.py +0 -0
  84. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/scripts/docx_exec_lab.py +0 -0
  85. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/scripts/docx_exec_lab_examples/fast_table_fill.py +0 -0
  86. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/scripts/docx_exec_lab_examples/find_replace_literal.py +0 -0
  87. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/scripts/docx_exec_lab_server.py +0 -0
  88. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/scripts/dump_wire_fixtures.py +0 -0
  89. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/scripts/release.sh +0 -0
  90. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/scripts/round_trip_smoke.py +0 -0
  91. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/scripts/smoke_test_block_not_found.py +0 -0
  92. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/scripts/validate_find_replace_asset.py +0 -0
  93. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/__init__.py +0 -0
  94. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/conftest.py +0 -0
  95. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/METHODOLOGY.md +0 -0
  96. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/README.md +0 -0
  97. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/__init__.py +0 -0
  98. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/__init__.py +0 -0
  99. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/agent_documents.py +0 -0
  100. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/default_style_run_formatting.py +0 -0
  101. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/header_footer_pictures.py +0 -0
  102. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/less_used_writes.py +0 -0
  103. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/merged_cell_identity.py +0 -0
  104. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/paragraph_text_setter.py +0 -0
  105. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/picture_runs.py +0 -0
  106. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/proxy_equality.py +0 -0
  107. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/return_types.py +0 -0
  108. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/xml_incompatible_text.py +0 -0
  109. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe/zero_and_negative_indents.py +0 -0
  110. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe_cases.py +0 -0
  111. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ab_probe_runner.py +0 -0
  112. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/auto_gen_cases.py +0 -0
  113. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/binary_round_trip.py +0 -0
  114. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/cases.py +0 -0
  115. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/complex_cases.py +0 -0
  116. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/coverage_report.py +0 -0
  117. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/extract.py +0 -0
  118. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/extreme_cases.py +0 -0
  119. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/fake_session.py +0 -0
  120. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/firm_templates/README.md +0 -0
  121. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/firm_templates/__init__.py +0 -0
  122. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/firm_templates/_runner.py +0 -0
  123. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/firm_templates/extractor.py +0 -0
  124. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/firm_templates/test_pw_corpus.py +0 -0
  125. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/firm_templates/test_pw_research_digest.py +0 -0
  126. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/local_runner.py +0 -0
  127. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/mega_cases.py +0 -0
  128. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshot.py +0 -0
  129. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/01_basic_paragraph.json +0 -0
  130. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/02_multiple_headings.json +0 -0
  131. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/03_runs_with_formatting.json +0 -0
  132. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/04_font_name_and_size.json +0 -0
  133. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/05_font_color_rgb.json +0 -0
  134. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/06_font_character_properties.json +0 -0
  135. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/07_font_subscript_superscript.json +0 -0
  136. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/08_font_highlight.json +0 -0
  137. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/09_paragraph_alignment.json +0 -0
  138. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/100_table_negative_indexing.json +0 -0
  139. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/101_table_cells_flat_iteration.json +0 -0
  140. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/102_text_with_embedded_special_chars.json +0 -0
  141. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/104_core_properties_datetime.json +0 -0
  142. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/105_default_one_section.json +0 -0
  143. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/106_heading_paragraph_format.json +0 -0
  144. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/107_varying_row_heights.json +0 -0
  145. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/10_paragraph_indents.json +0 -0
  146. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/11_paragraph_spacing.json +0 -0
  147. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/12_paragraph_keep_options.json +0 -0
  148. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/13_paragraph_tab_stops.json +0 -0
  149. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/14_run_add_tab_and_break.json +0 -0
  150. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/15_run_add_break_page.json +0 -0
  151. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/16_paragraph_clear_and_insert_before.json +0 -0
  152. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/17_table_basic.json +0 -0
  153. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/18_table_cell_text.json +0 -0
  154. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/19_table_row_column_sizing.json +0 -0
  155. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/20_table_cell_vertical_alignment.json +0 -0
  156. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/21_table_alignment_and_autofit.json +0 -0
  157. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/22_table_cell_paragraphs_iteration.json +0 -0
  158. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/24_table_add_row_column.json +0 -0
  159. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/25_table_merge_cells.json +0 -0
  160. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/26_section_page_setup.json +0 -0
  161. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/27_section_margins.json +0 -0
  162. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/28_section_add_new.json +0 -0
  163. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/29_section_headers_linked.json +0 -0
  164. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/30_styles_iteration.json +0 -0
  165. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/31_styles_lookup_and_default.json +0 -0
  166. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/32_styles_add_paragraph_style.json +0 -0
  167. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/33_core_properties_set_and_get.json +0 -0
  168. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/34_inline_shapes_iterate_empty.json +0 -0
  169. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/35_full_report.json +0 -0
  170. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/36_replace_text_in_paragraph.json +0 -0
  171. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/37_iterate_runs_and_format_all_bold.json +0 -0
  172. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/38_font_all_properties.json +0 -0
  173. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/39_large_body_100_paragraphs.json +0 -0
  174. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/40_large_table_10x10.json +0 -0
  175. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/41_unicode_and_emoji.json +0 -0
  176. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/42_very_long_paragraph.json +0 -0
  177. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/43_paragraph_text_round_trip.json +0 -0
  178. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/44_paragraph_alignment_round_trip.json +0 -0
  179. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/45_cell_text_round_trip.json +0 -0
  180. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/46_run_text_setter_round_trip.json +0 -0
  181. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/47_font_size_round_trip.json +0 -0
  182. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/48_font_color_round_trip.json +0 -0
  183. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/49_resume_layout.json +0 -0
  184. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/50_multi_section_doc.json +0 -0
  185. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/52_iterate_everything.json +0 -0
  186. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/53_apply_style_to_paragraphs.json +0 -0
  187. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/54_empty_everything.json +0 -0
  188. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/55_single_character_runs.json +0 -0
  189. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/56_everything_in_one.json +0 -0
  190. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/57_runs_after_multiple_text_appends.json +0 -0
  191. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/58_modify_runs_in_place.json +0 -0
  192. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/59_indent_round_trip.json +0 -0
  193. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/60_space_round_trip.json +0 -0
  194. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/61_cell_paragraph_with_runs.json +0 -0
  195. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/62_many_cell_paragraphs.json +0 -0
  196. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/63_table_style_round_trip.json +0 -0
  197. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/64_many_sections.json +0 -0
  198. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/65_20x20_table_formatted.json +0 -0
  199. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/66_toc_like_structure.json +0 -0
  200. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/67_paragraph_insert_before_chain.json +0 -0
  201. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/68_invoice.json +0 -0
  202. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/69_newsletter.json +0 -0
  203. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/70_add_and_iterate_back.json +0 -0
  204. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/71_academic_paper.json +0 -0
  205. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/72_legal_contract.json +0 -0
  206. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/73_form_with_many_tables.json +0 -0
  207. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/74_paragraph_with_10_runs.json +0 -0
  208. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/75_paragraph_negative_first_line_indent.json +0 -0
  209. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/76_rgbcolor_from_string.json +0 -0
  210. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/77_length_unit_conversions.json +0 -0
  211. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/78_paragraph_copy_style.json +0 -0
  212. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/79_bulk_cell_formatting.json +0 -0
  213. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/80_apply_style_after_add_run.json +0 -0
  214. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/81_multi_page_with_breaks.json +0 -0
  215. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/82_add_text_on_existing_run.json +0 -0
  216. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/83_clear_then_repopulate_paragraph.json +0 -0
  217. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/84_table_reread_row_count.json +0 -0
  218. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/85_header_footer_access.json +0 -0
  219. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/86_font_read_unset_returns_none.json +0 -0
  220. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/87_500_paragraph_doc.json +0 -0
  221. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/88_mixed_content_iteration.json +0 -0
  222. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/89_alignment_clear_via_none.json +0 -0
  223. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/90_cell_add_paragraph_styled.json +0 -0
  224. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/91_many_small_tables.json +0 -0
  225. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/92_margins_every_section.json +0 -0
  226. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/93_font_bool_reads_after_set.json +0 -0
  227. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/94_page_break_before_paragraph.json +0 -0
  228. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/95_paragraph_hyperlinks_empty.json +0 -0
  229. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/96_paragraph_contains_page_break.json +0 -0
  230. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/97_document_styles_by_key.json +0 -0
  231. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/98_style_contains_check.json +0 -0
  232. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/99_run_add_picture_from_bytes.json +0 -0
  233. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex02_unicode_everywhere.json +0 -0
  234. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex03_1000_paragraphs.json +0 -0
  235. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex04_50x50_table.json +0 -0
  236. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex05_long_text_in_cell.json +0 -0
  237. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex06_hundred_tiny_runs.json +0 -0
  238. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex07_every_font_boolean.json +0 -0
  239. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex08_many_continuous_sections.json +0 -0
  240. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex09_many_tab_stops.json +0 -0
  241. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex10_complex_bom.json +0 -0
  242. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex11_banded_rows_formatting.json +0 -0
  243. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex12_section_reconfigure.json +0 -0
  244. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex13_cell_with_10_paragraphs.json +0 -0
  245. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex14_styled_report_table.json +0 -0
  246. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex15_paragraph_all_format_props.json +0 -0
  247. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex16_runs_interleaved_with_breaks.json +0 -0
  248. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex17_all_break_kinds.json +0 -0
  249. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex18_read_back_large_doc.json +0 -0
  250. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex19_mutate_all_runs.json +0 -0
  251. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/ex20_kitchen_sink_v2.json +0 -0
  252. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega01_book_chapter.json +0 -0
  253. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega02_research_proposal.json +0 -0
  254. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega03_financial_statement.json +0 -0
  255. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega04_recipe_card.json +0 -0
  256. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega05_user_manual.json +0 -0
  257. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega06_complex_newsletter.json +0 -0
  258. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega07_budget_spreadsheet.json +0 -0
  259. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega08_product_catalog.json +0 -0
  260. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega09_signed_contract.json +0 -0
  261. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/mega10_api_documentation.json +0 -0
  262. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw01_official_quickstart.json +0 -0
  263. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw02_paragraph_style_list.json +0 -0
  264. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw03_character_formatting.json +0 -0
  265. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw04_section_page_setup.json +0 -0
  266. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw05_toc_pattern.json +0 -0
  267. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw06_meeting_minutes.json +0 -0
  268. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw07_dense_formatting_demo.json +0 -0
  269. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw08_table_merged_header.json +0 -0
  270. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw09_bulk_run_iteration.json +0 -0
  271. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw10_colored_grid_table.json +0 -0
  272. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw11_header_text.json +0 -0
  273. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw12_first_page_footer.json +0 -0
  274. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw13_even_page_header.json +0 -0
  275. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw15_paragraph_style_instance.json +0 -0
  276. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw16_header_footer_tables.json +0 -0
  277. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw17_header_letterhead_filled.json +0 -0
  278. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw18_header_table_properties.json +0 -0
  279. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw19_header_table_rows_columns.json +0 -0
  280. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/op_snapshots/rw20_header_table_merges.json +0 -0
  281. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/ours_spec.json +0 -0
  282. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/parity_crawl.py +0 -0
  283. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/parity_diff.json +0 -0
  284. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/real_world_cases.py +0 -0
  285. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/round_trip_tests.py +0 -0
  286. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/stock_spec.json +0 -0
  287. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fidelity/test_e2e_against_staging.py +0 -0
  288. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fixtures/field_reads.json +0 -0
  289. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fixtures/note_reference_reads.json +0 -0
  290. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fixtures/ruby_reads.json +0 -0
  291. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/fixtures/symbol_reads.json +0 -0
  292. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/live/__init__.py +0 -0
  293. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/live/baseline.json +0 -0
  294. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/live/reader.py +0 -0
  295. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/live/runner.py +0 -0
  296. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/live/sdk_driver.py +0 -0
  297. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/live/stock_driver.py +0 -0
  298. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/live/test_live_runner.py +0 -0
  299. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/README.md +0 -0
  300. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/__init__.py +0 -0
  301. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/baseline_gaps.json +0 -0
  302. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/compare.py +0 -0
  303. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/introspect.py +0 -0
  304. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/reports/GAP_ANALYSIS.md +0 -0
  305. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/reports/gap_report.json +0 -0
  306. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/run_parity.py +0 -0
  307. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/snapshots/athena_latest.json +0 -0
  308. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/snapshots/upstream_python_docx_1.2.0.json +0 -0
  309. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/parity/test_parity_gap.py +0 -0
  310. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_add_section.py +0 -0
  311. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_add_section_extract_items.py +0 -0
  312. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_alignment_values.py +0 -0
  313. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_athena_extension_creates_session_open.py +0 -0
  314. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_athena_extensions_contract.py +0 -0
  315. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_athena_extensions_registry.py +0 -0
  316. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_batch_chunking.py +0 -0
  317. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_batching_perf.py +0 -0
  318. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_battery_cases.py +0 -0
  319. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_block_not_found_error.py +0 -0
  320. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_buffer.py +0 -0
  321. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_add_paragraph_wire_shape.py +0 -0
  322. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_add_table_not_supported.py +0 -0
  323. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_borders_spec.py +0 -0
  324. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_fastpath_runs.py +0 -0
  325. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_inner_add_hyperlink_stash.py +0 -0
  326. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_inner_add_run_via_cell_insert.py +0 -0
  327. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_inner_format_stash.py +0 -0
  328. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_inner_run_format_stash.py +0 -0
  329. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_inner_run_guard.py +0 -0
  330. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_merge.py +0 -0
  331. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_nested_tables.py +0 -0
  332. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_paragraphs_listed.py +0 -0
  333. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_text_plain_fastpath.py +0 -0
  334. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_cell_text_replace_semantics.py +0 -0
  335. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_citations.py +0 -0
  336. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_collapsed_range_format.py +0 -0
  337. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_color_format_theme.py +0 -0
  338. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_command_dataclasses.py +0 -0
  339. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_commands.py +0 -0
  340. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_comment_paragraphs.py +0 -0
  341. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_comments_first_read.py +0 -0
  342. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_content_control_value.py +0 -0
  343. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_core_properties.py +0 -0
  344. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_document_asset_id_property.py +0 -0
  345. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_document_clear.py +0 -0
  346. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_document_create.py +0 -0
  347. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_document_create_from_template.py +0 -0
  348. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_document_factory_validation.py +0 -0
  349. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_document_settings_session_open.py +0 -0
  350. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_docx_exec_lab.py +0 -0
  351. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_docx_exec_lab_server.py +0 -0
  352. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_drawing_image.py +0 -0
  353. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_e2e_partial_failure_cascade.py +0 -0
  354. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_empty_hyperlinks.py +0 -0
  355. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_enum_parity.py +0 -0
  356. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_execution_scope.py +0 -0
  357. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_export_docx_clean.py +0 -0
  358. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_export_rescue_anchors.py +0 -0
  359. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_field_reads_python_docx_parity.py +0 -0
  360. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_field_refresh.py +0 -0
  361. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_field_runs.py +0 -0
  362. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_find_replace_session_open.py +0 -0
  363. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_flushed_write_failures.py +0 -0
  364. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_http_transport.py +0 -0
  365. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_image_url_data_uri.py +0 -0
  366. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_inline_page_break.py +0 -0
  367. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_inline_shape_alt_text.py +0 -0
  368. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_inline_shape_size.py +0 -0
  369. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_inline_shape_type.py +0 -0
  370. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_inline_shapes_floating.py +0 -0
  371. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_insert_deferred.py +0 -0
  372. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_iter_inner_content.py +0 -0
  373. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_latent_style_writes.py +0 -0
  374. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_line_clear_break.py +0 -0
  375. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_list_styles.py +0 -0
  376. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_listed_paragraph_reads.py +0 -0
  377. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_literal_no_break_hyphens.py +0 -0
  378. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_literal_soft_hyphens.py +0 -0
  379. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_merged_cell_identity.py +0 -0
  380. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_merged_cell_secondary_slot.py +0 -0
  381. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_merged_cells.py +0 -0
  382. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_missing_modules.py +0 -0
  383. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_nested_table_refused.py +0 -0
  384. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_note_reference_reads_python_docx_parity.py +0 -0
  385. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_oxml_shim.py +0 -0
  386. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_page_break.py +0 -0
  387. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_paragraph_delete.py +0 -0
  388. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_paragraph_indent_reads.py +0 -0
  389. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_paragraph_runs_hyperlinks.py +0 -0
  390. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_paragraph_text_empty_run.py +0 -0
  391. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_paragraph_text_len_cache.py +0 -0
  392. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_parfmt_clears.py +0 -0
  393. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_parity_misc.py +0 -0
  394. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_parity_round2.py +0 -0
  395. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_partial_failure_cascade.py +0 -0
  396. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_pdf_export_and_page_renders.py +0 -0
  397. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_phase_a_behavior.py +0 -0
  398. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_phase_b_headers_footers.py +0 -0
  399. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_phase_c_tables.py +0 -0
  400. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_positional_cell_id.py +0 -0
  401. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_postproc_cell_format_rewrite.py +0 -0
  402. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_postproc_cell_run_format_rewrite.py +0 -0
  403. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_postproc_ref_restore.py +0 -0
  404. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_pr19766_review_fixes.py +0 -0
  405. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_proxy_equality.py +0 -0
  406. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_ptc.py +0 -0
  407. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_python_docx_api_parity.py +0 -0
  408. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_read_run_ranges.py +0 -0
  409. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_repeated_node_read.py +0 -0
  410. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_restart_numbering.py +0 -0
  411. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_revisions.py +0 -0
  412. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_round_trip_smoke_script.py +0 -0
  413. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_ruby_reads_python_docx_parity.py +0 -0
  414. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_add_picture_anchor.py +0 -0
  415. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_break_inner_content.py +0 -0
  416. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_edges.py +0 -0
  417. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_formatting_wire.py +0 -0
  418. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_identity.py +0 -0
  419. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_later_runs.py +0 -0
  420. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_mark_inheritance.py +0 -0
  421. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_page_number_blocks.py +0 -0
  422. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_table_style_objects.py +0 -0
  423. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_text_python_docx.py +0 -0
  424. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_text_refreshes_paragraph.py +0 -0
  425. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_run_unmodeled_toggles.py +0 -0
  426. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_sdk_reads_served.py +0 -0
  427. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_section_read_lengths.py +0 -0
  428. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_sections_empty_list.py +0 -0
  429. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_add_paragraph_style.py +0 -0
  430. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_add_picture.py +0 -0
  431. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_add_run.py +0 -0
  432. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_cell_add_paragraph.py +0 -0
  433. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_comments_add_comment.py +0 -0
  434. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_comments_get.py +0 -0
  435. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_document_audit.py +0 -0
  436. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_document_element.py +0 -0
  437. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_enum_section.py +0 -0
  438. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_font_audit.py +0 -0
  439. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_header_footer.py +0 -0
  440. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_hyperlink.py +0 -0
  441. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_inline_shape.py +0 -0
  442. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_insert_paragraph_before.py +0 -0
  443. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_misc.py +0 -0
  444. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_paragraph_strict.py +0 -0
  445. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_paragraph_style.py +0 -0
  446. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_paragraph_style_strict.py +0 -0
  447. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_parfmt.py +0 -0
  448. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_row_col_cell.py +0 -0
  449. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_run_add_break.py +0 -0
  450. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_run_bool_setters.py +0 -0
  451. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_run_style.py +0 -0
  452. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_run_style_strict.py +0 -0
  453. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_run_text.py +0 -0
  454. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_run_underline.py +0 -0
  455. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_section_audit.py +0 -0
  456. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_section_dimensions.py +0 -0
  457. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_section_onoff.py +0 -0
  458. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_settings.py +0 -0
  459. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_shared_audit.py +0 -0
  460. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_style.py +0 -0
  461. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_styles.py +0 -0
  462. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_table_audit.py +0 -0
  463. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_table_cell.py +0 -0
  464. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_table_dimensions.py +0 -0
  465. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_silent_stub_table_layout.py +0 -0
  466. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_smoke_integration.py +0 -0
  467. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_acceptance.py +0 -0
  468. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_delete.py +0 -0
  469. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_font.py +0 -0
  470. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_formatting_writes.py +0 -0
  471. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_metadata_writes.py +0 -0
  472. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_names.py +0 -0
  473. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_resolution.py +0 -0
  474. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_setters_contract.py +0 -0
  475. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_tab_stops.py +0 -0
  476. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_style_tab_stops_read.py +0 -0
  477. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_symbol_reads_python_docx_parity.py +0 -0
  478. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_tab_stop_writes.py +0 -0
  479. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_table_add_row_grid_row.py +0 -0
  480. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_table_anchors.py +0 -0
  481. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_table_clears.py +0 -0
  482. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_table_direction.py +0 -0
  483. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_table_length_reads.py +0 -0
  484. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_table_listing_reads.py +0 -0
  485. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_table_read_reuse.py +0 -0
  486. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_table_set_cell_perf.py +0 -0
  487. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_table_style_id_resolution.py +0 -0
  488. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_temporarily_unavailable.py +0 -0
  489. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_text_control_characters.py +0 -0
  490. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_tracked_revisions_offsets.py +0 -0
  491. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_unmapped_alignment_reads.py +0 -0
  492. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_uv_lock_version.py +0 -0
  493. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_validate_find_replace_asset_script.py +0 -0
  494. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_versioned_read_reuse.py +0 -0
  495. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_wire_contract.py +0 -0
  496. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_xml_attr_guard.py +0 -0
  497. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_xml_incompatible_text.py +0 -0
  498. {athena_python_docx-0.40.0 → athena_python_docx-0.41.0}/tests/test_zod_wire_contract.py +0 -0
@@ -1223,7 +1223,9 @@ architecture or a DOCX Studio constraint:
1223
1223
  offsets in a run's text (`literalCharacters`), which `_word_text` reads as
1224
1224
  written; a docx-studio that sends none reads each as the element, as before.
1225
1225
  The export writes them back in a `w:t`, and text a script writes holds them
1226
- as upstream writes it, in a `w:t`.
1226
+ as upstream writes it, in a `w:t`. `Document.find_replace` keeps each hyphen
1227
+ the replacement shares with the match as the match held it, and writes any
1228
+ other in a `w:t`, as upstream writes text.
1227
1229
 
1228
1230
  - **`CoreProperties.modified` is the time of the last save.** The asset is a
1229
1231
  live Word document, and docx-studio stamps `dcterms:modified` when it saves
@@ -1292,24 +1294,19 @@ architecture or a DOCX Studio constraint:
1292
1294
  which the editor draws it with, where upstream reads the default table
1293
1295
  style; reading the default would change how such tables draw. The export
1294
1296
  leaves the style undefined, as the source has it: an unedited download of
1295
- a document imported since is the source's bytes (owner, 2026-10-23). The read is kept until Word can be
1296
- checked, as no Word probe can be made on the machine that recorded it
1297
- (`tables-undefined-style`).
1297
+ a document imported since is the source's bytes (owner, 2026-10-23). The read is kept
1298
+ (`tables-undefined-style`): checked on 2026-10-24 against the one sample
1299
+ document's Word PDF, whose tables draw alike under either style (empty
1300
+ paragraph defaults, the tables' own borders and margins) and match the
1301
+ editor's Table Grid layout, so no corpus document yet tells the two apart.
1298
1302
  - A package with no styles part (1 document) reads Word's built-in styles,
1299
1303
  which the editor gives it, where upstream reads its own default template's
1300
1304
  (`styles-part-absent`). Confirmed by the owner, 2026-10-23.
1301
1305
 
1302
- - **Two more reads follow the model where python-docx reads the source**
1303
- (2026-10-22 SDK live parity run over 398 customer documents, round 3). Each is
1306
+ - **One more read follows the model where python-docx reads the source**
1307
+ (2026-10-22 SDK live parity run over 398 customer documents, round 3). It is
1304
1308
  recorded in `tests/parity/intentional_deviations.json` (`live_deviations`)
1305
1309
  with a synthetic fixture:
1306
- - A comment whose range ends between paragraphs (`w:commentRangeEnd` a
1307
- child of `w:body`; 1 document, 11 of 6,826 uploads) reads its reference
1308
- run at the end of the last paragraph its mark covers, where the export
1309
- writes it from the model, where upstream reads it in the paragraph after
1310
- the range end: the model holds a range as a mark on its text and no range
1311
- end between paragraphs (`comments-range-end-between-paragraphs`).
1312
- Confirmed by the owner, 2026-10-23.
1313
1310
  - A comment's annotation reference run that names no character style
1314
1311
  (1 document, 13 of 6,826 uploads) reads in the CommentReference style, in
1315
1312
  which the export writes every comment's annotation run when it writes the
@@ -1317,6 +1314,25 @@ architecture or a DOCX Studio constraint:
1317
1314
  run as an empty run nothing tells from another
1318
1315
  (`comments-annotation-ref-unstyled`). Confirmed by the owner, 2026-10-23.
1319
1316
 
1317
+ A comment whose range ends between paragraphs (`w:commentRangeEnd` a child
1318
+ of `w:body`; 1 document, 11 of 6,826 uploads) is no longer a deviation, with
1319
+ the other comments whose reference run stands apart from the text their
1320
+ range marks: one over links alone in several paragraphs or over a picture or
1321
+ an object alone, which the model holds no range for, one that ends in a
1322
+ paragraph holding none of its text, and one whose run follows a field's end
1323
+ run. The import records where the source body holds each reference run and
1324
+ range end (`commentReferenceRunPlaces`: the paragraph and how many of its
1325
+ runs come before it), the paragraphs whose text it marks for the comment,
1326
+ and the fingerprint of each body block that holds them. While those blocks
1327
+ are as imported and the comment marks the same paragraphs, the run reads
1328
+ where the source holds it, where the export keeps the blocks' source XML,
1329
+ and a reply added since reads beside the comment's range end, where the
1330
+ export writes it (`comments-range-end-between-paragraphs`,
1331
+ `comments-range-over-links`, `comments-range-end-without-text`,
1332
+ `comments-range-over-object`). A block an edit changed, a comment moved to
1333
+ new text, and a room imported before the record read where the model places
1334
+ the run, as before.
1335
+
1320
1336
  A third, runs of one formatting read and exported joined after a run write
1321
1337
  in a paragraph with a link, an inline content control, an equation or a
1322
1338
  field beside a picture, is no longer a deviation (the owner asked for it to
@@ -1324,14 +1340,16 @@ architecture or a DOCX Studio constraint:
1324
1340
  `add_run`, `add_text`) carries the records the read takes of such a
1325
1341
  paragraph's runs (`_writtenRunRecords`), each `w:r` kept with the written
1326
1342
  run changed as python-docx changes it, and the export writes the paragraph
1327
- from them. A write the records cannot describe (a format of a field's runs,
1328
- a write across a field, a run the offsets cannot tell from an empty one
1329
- beside it) leaves the paragraph as before: a link paragraph's kept content,
1330
- else the runs its marks make. Fixture scripts
1343
+ from them. A format of one of a field's own runs is carried too, into the
1344
+ field's record (2026-10-24, #46477). A write the records cannot describe (a
1345
+ write across a field, a field's result written, a run the offsets cannot
1346
+ tell from an empty one beside it) leaves the paragraph as before: a link
1347
+ paragraph's kept content, else the runs its marks make. Fixture scripts
1331
1348
  `fixture-links-run-write-keeps-runs`, `fixture-links-run-writes`,
1332
1349
  `fixture-content-controls-inline-run-writes`,
1333
- `fixture-equations-beside-runs-run-writes` and
1334
- `fixture-fields-beside-pictures-run-writes`.
1350
+ `fixture-equations-beside-runs-run-writes`,
1351
+ `fixture-fields-beside-pictures-run-writes` and
1352
+ `fixture-fields-beside-pictures-field-run-formats`.
1335
1353
 
1336
1354
  - **A citation link Athena added reads as its text, as the export writes it**
1337
1355
  (owner decision #40122). Athena's citation flow stamps the links it writes
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.5
2
2
  Name: athena-python-docx
3
- Version: 0.40.0
3
+ Version: 0.41.0
4
4
  Summary: Drop-in replacement for python-docx that connects to Athena's DOCX Studio collaborative document stack
5
5
  Project-URL: Homepage, https://athenaintelligence.ai
6
6
  Author-email: Athena Intelligence <engineering@athenaintelligence.ai>
@@ -6,7 +6,7 @@ See CLAUDE.md for the API parity contract.
6
6
 
7
7
  from __future__ import annotations
8
8
 
9
- __version__ = "0.40.0"
9
+ __version__ = "0.41.0"
10
10
 
11
11
  from docx.api import Document
12
12
  from docx._buffer import discard_all, flush_all
@@ -40,6 +40,7 @@ from docx._batching import run_sync
40
40
  from docx._buffer import writes_unapplied
41
41
  from docx.blkcntnr import BlockItemContainer
42
42
  from docx.errors import DocxError, NotFoundError
43
+ from docx.text.paragraph import _buffer_writes
43
44
 
44
45
  if TYPE_CHECKING:
45
46
  from collections.abc import Iterator, Sequence
@@ -186,6 +187,35 @@ def _coerce_timestamp(raw: object) -> datetime | None:
186
187
  return None
187
188
 
188
189
 
190
+ def _word_date(raw: object) -> datetime | None:
191
+ """A comment's ``w:date`` as python-docx 1.2.0's ``Comment.timestamp``
192
+ reads it (``ST_DateTime.convert_from_xml``): with a trailing ``Z``, a time
193
+ in UTC; with an offset, a time in that zone; without either, a time in no
194
+ zone, as Word writes the author's local time; one it cannot parse, the
195
+ epoch in UTC. ``None`` for a comment with no ``w:date``."""
196
+ if not isinstance(raw, str):
197
+ return None
198
+
199
+ def parse(text: str) -> datetime:
200
+ if text.endswith("Z"):
201
+ try:
202
+ return datetime.strptime(text, "%Y-%m-%dT%H:%M:%S.%fZ").replace(tzinfo=timezone.utc)
203
+ except ValueError:
204
+ return datetime.strptime(text, "%Y-%m-%dT%H:%M:%SZ").replace(tzinfo=timezone.utc)
205
+ try:
206
+ return datetime.fromisoformat(text)
207
+ except ValueError:
208
+ try:
209
+ return datetime.strptime(text, "%Y-%m-%dT%H:%M:%S.%f")
210
+ except ValueError:
211
+ return datetime.strptime(text, "%Y-%m-%dT%H:%M:%S")
212
+
213
+ try:
214
+ return parse(raw)
215
+ except Exception:
216
+ return datetime(1970, 1, 1, tzinfo=timezone.utc)
217
+
218
+
189
219
  # docx-studio's caps (``MAX_COMMENT_AUTHOR_LENGTH`` /
190
220
  # ``MAX_COMMENT_INITIALS_LENGTH`` in apps/api/src/commands/types.ts), in
191
221
  # UTF-16 code units as the server counts them.
@@ -274,7 +304,7 @@ def _created_comment_info(
274
304
  }
275
305
  stored = result.get("comment") if isinstance(result, dict) else None
276
306
  if isinstance(stored, dict):
277
- for key in ("creatorName", "initials", "createdTime"):
307
+ for key in ("creatorName", "initials", "createdTime", "wordDate"):
278
308
  if key in stored:
279
309
  info[key] = stored[key]
280
310
  return info
@@ -291,6 +321,10 @@ class Comment(BlockItemContainer):
291
321
  ) -> None:
292
322
  self._session: "Session" = session
293
323
  self._info: dict = dict(info or {})
324
+ # The command buffer's ``writes`` count the info was read at: a later
325
+ # write (to the comment's paragraphs or runs, its replies' root, or
326
+ # anything the export writes it anew for) may change its ``w:date``.
327
+ self._dated_at: int | None = _buffer_writes(session)
294
328
 
295
329
  # ---- identity / metadata ----
296
330
  @property
@@ -336,6 +370,29 @@ class Comment(BlockItemContainer):
336
370
 
337
371
  @property
338
372
  def timestamp(self) -> datetime | None:
373
+ """The ``w:date`` docx-studio says the export writes for the comment
374
+ (``wordDate``), read as python-docx reads it: the source's own for a
375
+ comment no write changed, which Word writes in the author's local time
376
+ with no zone. A docx-studio that does not say gives the comment's
377
+ time in UTC (``createdTime``). After a write since the comment was
378
+ read (its text, a paragraph added to it, an edit of its paragraphs or
379
+ runs, or any other, which may make the export write it anew), it reads
380
+ the comment again; a read that fails is tried again at the next."""
381
+ if self._info.get("_wordDateStale") or _buffer_writes(self._session) != self._dated_at:
382
+ try:
383
+ fresh: object = run_sync(self._session.doc.comments.get({"id": self._id}))
384
+ except NotFoundError as exc:
385
+ if writes_unapplied(exc):
386
+ raise
387
+ fresh = None
388
+ if isinstance(fresh, dict):
389
+ for key in ("wordDate", "createdTime"):
390
+ if key in fresh:
391
+ self._info[key] = fresh[key]
392
+ self._info.pop("_wordDateStale", None)
393
+ self._dated_at = _buffer_writes(self._session)
394
+ if "wordDate" in self._info:
395
+ return _word_date(self._info.get("wordDate"))
339
396
  return _coerce_timestamp(self._info.get("createdTime"))
340
397
 
341
398
  # ---- body ----
@@ -363,6 +420,8 @@ class Comment(BlockItemContainer):
363
420
 
364
421
  run_sync(self._session.doc.comments.patch({"id": self._id, "text": value}))
365
422
  self._info["text"] = value
423
+ # The export writes the comment anew, with the date its record holds.
424
+ self._info["_wordDateStale"] = True
366
425
  # CommentsPatch is a Command type — referenced for clarity / parity
367
426
  # with the bus dispatch path.
368
427
  del CommentsPatch
@@ -459,6 +518,8 @@ class Comment(BlockItemContainer):
459
518
  node_id = result.get("nodeId") if isinstance(result, dict) else None
460
519
  if not isinstance(node_id, str) or not node_id:
461
520
  raise CommentsNotImplementedError("Paragraphs added to comments")
521
+ # The export writes the comment anew, with the date its record holds.
522
+ self._info["_wordDateStale"] = True
462
523
  paragraph = Paragraph(session=self._session, node_id=node_id, node_type="paragraph", text_len=len(text))
463
524
  if style is not None:
464
525
  paragraph.style = style
@@ -347,10 +347,24 @@ def _keep_link_address(run_data: dict, inline: dict) -> None:
347
347
  """Give a picture's run the address of the link it is in where its read
348
348
  sends one apart (``hyperlinkAddress``, for a target that holds a ``#`` of
349
349
  its own), as a text run's read holds it: :attr:`Hyperlink.address` reads
350
- the whole target then, as python-docx does."""
350
+ the whole target then, as python-docx does; that it opens a link of its
351
+ own (``newLink``, :func:`_opens_link`); and that the link has no target
352
+ (``linkWithoutTarget``)."""
351
353
  address: object = inline.get("hyperlinkAddress")
352
354
  if isinstance(address, str):
353
355
  run_data["hyperlinkAddress"] = address
356
+ if inline.get("newLink") is True:
357
+ run_data["newLink"] = True
358
+ if inline.get("linkWithoutTarget") is True:
359
+ run_data["linkWithoutTarget"] = True
360
+
361
+
362
+ def _opens_link(run_data: dict) -> bool:
363
+ """True for the first run of a link that follows another link to the same
364
+ target with nothing between them (``newLink``): two ``w:hyperlink``
365
+ elements side by side, which python-docx reads as two links. Without it,
366
+ runs of one target side by side are one link."""
367
+ return run_data.get("newLink") is True
354
368
 
355
369
 
356
370
  def _picture_run_data(inline: dict, drawing: dict) -> dict:
@@ -372,8 +386,9 @@ def _picture_run_data(inline: dict, drawing: dict) -> dict:
372
386
 
373
387
  def _rendered_page_break_reads(info: object) -> "list[tuple[dict, int]]":
374
388
  """Each rendered page break docx-studio reads in the runs of the paragraph
375
- whose node info is `info` (``renderedPageBreaks``), its links' included, in
376
- order, with its offset in the paragraph's text-address space."""
389
+ whose node info is `info` (``renderedPageBreaks``), its links' and its
390
+ fields' included, in order, with its offset in the paragraph's
391
+ text-address space."""
377
392
  if not isinstance(info, dict):
378
393
  return []
379
394
  node: object = info.get("node")
@@ -382,6 +397,16 @@ def _rendered_page_break_reads(info: object) -> "list[tuple[dict, int]]":
382
397
  reads: list[tuple[dict, int]] = []
383
398
  offset = 0
384
399
  for inline in inlines if isinstance(inlines, list) else []:
400
+ field_run: object = inline.get("fieldRun") if isinstance(inline, dict) else None
401
+ if isinstance(field_run, dict):
402
+ # A run of a field (its begin, code, separate, result or end run):
403
+ # it takes no room in the text-address space, and a break in it
404
+ # stands there.
405
+ field_breaks: object = field_run.get("renderedPageBreaks")
406
+ for brk in field_breaks if isinstance(field_breaks, list) else []:
407
+ if isinstance(brk, dict):
408
+ reads.append((brk, offset))
409
+ continue
385
410
  run: object = inline.get("run") if isinstance(inline, dict) else None
386
411
  if not isinstance(run, dict):
387
412
  # A picture's run: its breaks stand before its drawing, and it holds no text.
@@ -1015,7 +1040,7 @@ class Paragraph:
1015
1040
  if isinstance(drawing, dict):
1016
1041
  # A picture: python-docx's run holding a ``w:drawing``. It
1017
1042
  # takes no room in the text-address space.
1018
- if self._extract_hyperlink_target(inline):
1043
+ if self._extract_hyperlink_target(inline) is not None:
1019
1044
  continue
1020
1045
  run_obj = Run(
1021
1046
  session=self._session,
@@ -1037,7 +1062,7 @@ class Paragraph:
1037
1062
  start: int = offset
1038
1063
  end: int = offset + len(text)
1039
1064
  offset = end
1040
- if self._extract_hyperlink_target(run_data) or _deleted(run_data):
1065
+ if self._extract_hyperlink_target(run_data) is not None or _deleted(run_data):
1041
1066
  continue
1042
1067
  run_obj = Run(
1043
1068
  session=self._session,
@@ -1058,7 +1083,7 @@ class Paragraph:
1058
1083
  start = offset
1059
1084
  end = offset + len(text2)
1060
1085
  offset = end
1061
- if self._extract_hyperlink_target(inline):
1086
+ if self._extract_hyperlink_target(inline) is not None:
1062
1087
  continue
1063
1088
  runs.append(
1064
1089
  Run(
@@ -1248,6 +1273,11 @@ class Paragraph:
1248
1273
  maybe = hl.get("url") or hl.get("target")
1249
1274
  if isinstance(maybe, str) and maybe:
1250
1275
  return maybe
1276
+ # A link with no target (``<w:hyperlink w:history="1">`` holding runs,
1277
+ # with no ``r:id`` and no ``w:anchor``), which python-docx reads as a
1278
+ # link whose address is "" (``linkWithoutTarget``).
1279
+ if run_data.get("linkWithoutTarget") is True:
1280
+ return ""
1251
1281
  return None
1252
1282
 
1253
1283
  @property
@@ -1304,7 +1334,7 @@ class Paragraph:
1304
1334
  # room in the text-address space.
1305
1335
  run_data = _picture_run_data(inline, drawing)
1306
1336
  link = self._extract_hyperlink_target(inline)
1307
- if link:
1337
+ if link is not None:
1308
1338
  run_data["hyperlink"] = link
1309
1339
  _keep_link_address(run_data, inline)
1310
1340
  elif isinstance(maybe_run, dict):
@@ -1373,7 +1403,7 @@ class Paragraph:
1373
1403
 
1374
1404
  # Hyperlinked run. Extend the current span if it shares a
1375
1405
  # target, otherwise close it and start a new one.
1376
- if current is not None and current[0] == target:
1406
+ if current is not None and current[0] == target and not _opens_link(run_data):
1377
1407
  current[1].append((run_data, (start, end)))
1378
1408
  else:
1379
1409
  if current is not None:
@@ -1523,7 +1553,7 @@ class Paragraph:
1523
1553
  # link when it carries one.
1524
1554
  run_data = _picture_run_data(inline, drawing)
1525
1555
  link = self._extract_hyperlink_target(inline)
1526
- if link:
1556
+ if link is not None:
1527
1557
  run_data["hyperlink"] = link
1528
1558
  _keep_link_address(run_data, inline)
1529
1559
  text = ""
@@ -1549,11 +1579,11 @@ class Paragraph:
1549
1579
  offset += len(text)
1550
1580
  continue
1551
1581
  target = self._extract_hyperlink_target(run_data)
1552
- if target:
1582
+ if target is not None:
1553
1583
  start = offset
1554
1584
  offset += len(text)
1555
1585
  segment = (run_data, (start, start + len(text)))
1556
- if current is not None and current[0] == target:
1586
+ if current is not None and current[0] == target and not _opens_link(run_data):
1557
1587
  current[1].append(segment)
1558
1588
  else:
1559
1589
  flushed = _flush_current()
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
4
4
 
5
5
  [project]
6
6
  name = "athena-python-docx"
7
- version = "0.40.0"
7
+ version = "0.41.0"
8
8
  description = "Drop-in replacement for python-docx that connects to Athena's DOCX Studio collaborative document stack"
9
9
  readme = "README.md"
10
10
  license = "MIT"