
    Mi                    @   % S SK Jr  S SKrS SKrS SKrS SKrS SKrS SKrS SKJ	r	  S SK
JrJrJrJrJr  S SKrS SKJr  S SKJr  S SKJr  S SKJr  S S	KJrJrJr  S S
KJr  S SKJ r J!r!  S SK"J#r#  S SK$J%r%  S SK&J'r'  S SK(J)r)  S SK*J+r+  S SK,J-r-  S SK.J/r/  S SK0J1r1  S SK2J3r3J4r4J5r5J6r6J7r7J8r8J9r9J:r:J;r;J<r<J=r=JrJ>r>J?r?  S SK@JArA  S SKBJCrCJDrD  S SKEJFrFJGrGJHrHJIrI  S SKJJKrK  S SKLJMrM  0 S\>_S\?_S\?_S\?_S\?_S\?_S \?_S!\?_S"\?_S#\?_S$\>_S%\;_S&\;_S'\;_S(\;_S)\;_S*\;_\;\;\;\;\;\;\;\>\>\>\?\?\?S+.ErNS,rOS-\PS.'   S/rQS0\PS1'   S2rRS0\PS3'   SAS5 jrS " S6 S4\5      rT\C" \AR                  5      \- SBSS7S7S8SS9.               SCS: jjj5       5       rV " S; S<5      rW " S= S>5      rX " S? S@5      rYg)D    )annotationsN)cached_property)IOAnyIteratorProtocolType)Document)WD_SECTION_START)CT_Tbl)CT_P)Section_Footer_Header)Table)_Cell_Row)	Hyperlink)RenderedPageBreak)	Paragraph)Run)	TypeAlias)add_chunking_strategy)clean_bullets)htmlify_matrix_of_cell_texts)AddressElementElementMetadataEmailAddressFooterHeaderImageLinkListItemNarrativeText	PageBreakr   TextTitle)FileType)apply_metadataget_last_modified_date)is_bulleted_textis_email_addressis_possible_narrative_textis_us_city_state_zip)PartitionStrategy)is_temp_file_pathCaptionz	Heading 1z	Heading 2z	Heading 3z	Heading 4z	Heading 5z	Heading 6z	Heading 7z	Heading 8z	Heading 9zIntense QuoteListzList 2zList 3List BulletzList Bullet 2zList Bullet 3)List ContinuezList Continue 2zList Continue 3List NumberzList Number 2zList Number 3zList Paragraphz
Macro Textz
No SpacingQuoteSubtitle
TOCHeadingr(   docxstrDETECTION_ORIGINzCT_P | CT_Tblr   BlockElementzParagraph | DocxTable	BlockItemPicturePartitionerTc                .    [         R                  U 5        g)zLSpecify a pluggable sub-partitioner to be used for partitioning DOCX images.N)DocxPartitionerOptionsregister_picture_partitioner)picture_partitioners    u/var/www/eduai.edurigo.com/storigo/production/storigo_env/lib/python3.13/site-packages/unstructured/partition/docx.pyrB   rB   a   s    778KL    c                  ,    \ rS rSrSr\SS j5       rSrg)r?   k   a  Defines the interface for a pluggable sub-partitioner for DOCX Picture objects.

In Microsoft Word parlance, an image is a "picture". We use that term here for an image in a
DOCX file both for domain consistency and because it conveniently avoids confusion with an
`unstructured` `Image` element.

A picture can be either *inline* or *floating*. An inline picture is treated like a big
character in the text of a paragraph, moving with the text. A floating picture can be moved
freely and text flows around it.

Both inline and floating pictures are defined inside a paragraph in the DOCX file. A paragraph
can have zero or more pictures. A DOCX picture partitioner takes a `docx` `Paragraph` object
and generates an `Image` element for each picture found in that paragraph.
c                    g)z<Generate an `Image` element for each picture in `paragraph`.N cls	paragraphoptss      rD   iter_elements!PicturePartitionerT.iter_elements{   s     	rE   rI   NrL   r   rM   rA   returnIterator[Image]__name__
__module____qualname____firstlineno____doc__classmethodrN   __static_attributes__rI   rE   rD   r?   r?   k   s      rE   T   )fileinclude_page_breaksinfer_table_structurestarting_page_numberstrategyc          	     r    [         R                  UU UUUUS9n[        R                  U5      n[	        U5      $ )a  Partitions Microsoft Word Documents in .docx format into its document elements.

Parameters
----------
filename
    A string defining the target filename path.
file
    A file-like object using "rb" mode --> open(filename, "rb").
include_page_breaks
    When True, add a `PageBreak` element to the element-stream when a page-break is detected in
    the document. Note that not all DOCX files include page-break information.
infer_table_structure
    If True, any Table elements that are extracted will also have a metadata field
    named "text_as_html" where the table's text content is rendered into an html string.
    I.e., rows and cells are preserved.
    Whether True or False, the "text" field is always present in any Table element
    and is the text content of the table (no structure).
metadata_filename
    The filename to use for the metadata. Relevant because partition_doc converts the document
    to .docx before partition. We want the original source filename in the metadata.
metadata_last_modified
    The last modified date for the document.
starting_page_number
    Assign this number to the first page of this document and increment the page number from
    there.
)r\   	file_pathr]   r^   r_   r`   )rA   load_DocxPartitioneriter_document_elementslist)	filenamer\   r]   r^   r_   r`   kwargsrM   elementss	            rD   partition_docxrj      sH    L "&&/31 ' D  66t<H>rE   c                  `   \ rS rSrSrSr SSS.           SS jjr\SS j5       r\SS j5       r	\
SS	 j5       r\
SS
 j5       rSS jr\
SS j5       r\
SS j5       r\
SS j5       r\SS j5       r\SS j5       r\
S S j5       r\
S!S j5       r\
SS j5       r\
S"S j5       rS#S jrSrg)$rA      zVEncapsulates partitioning option validation, computation, and application of defaults.Nr[   )r_   r`   c               L    Xl         X l        X0l        X@l        X`l        XPl        g N)_file
_file_path_include_page_breaks_infer_table_structure	_strategy_page_counter)selfr\   rb   r]   r^   r_   r`   s          rD   __init__DocxPartitionerOptions.__init__   s%     
#$7!&;#!1rE   c                .    U " S0 UD6R                  5       $ )z#Construct and validate an instance.rI   )	_validate)rK   rh   s     rD   rc   DocxPartitionerOptions.load   s     }V}&&((rE   c                    Xl         g)zKSpecify a pluggable sub-partitioner to extract images from DOCX paragraphs.N)_PicturePartitionerCls)rK   rC   s     rD   rB   3DocxPartitionerOptions.register_picture_partitioner   s
     &9"rE   c                B    [         R                  " U R                  5      $ z?The python-docx `Document` object loaded from file or filename.)r:   r
   
_docx_fileru   s    rD   documentDocxPartitionerOptions.document   s     }}T__--rE   c                    U R                   $ )a'  When True, include `PageBreak` elements in element-stream.

Note that regardless of this setting, page-breaks are detected, and page-number is tracked
and included in element metadata. Only the presence of distinct `PageBreak` elements (which
contain no text) in the element stream is affected.
)rq   r   s    rD   r]   *DocxPartitionerOptions.include_page_breaks   s     (((rE   c              #  z   #    U =R                   S-  sl         U R                  (       a  [        S[        S9v   gg7f)zGIncrement page-number by 1 and generate a PageBreak element if enabled.r[    )detection_originN)rt   rq   r&   r<   r   s    rD   increment_page_number,DocxPartitionerOptions.increment_page_number   s2     a$$B1ABB %s   9;c                    U R                   $ )zRTrue when partitioner should compute and apply `text_as_html` metadata for tables.)rr   r   s    rD   r^   ,DocxPartitionerOptions.infer_table_structure   s     ***rE   c                    U R                   (       d  g[        U R                   5      (       a  S$ [        U R                   5      $ )zHThe best last-modified date available, None if no sources are available.N)rp   r1   r+   r   s    rD   last_modified$DocxPartitionerOptions.last_modified   s:      &doo66D	
<RSWSbSb<c	
rE   c                    U R                   $ )zHThe best available file-path for this document or `None` if unavailable.)rp   r   s    rD   metadata_file_path)DocxPartitionerOptions.metadata_file_path  s     rE   c                @    U R                   (       a  U R                  $ S$ )a  The current page number to report in metadata, or None if we can't really tell.

Page numbers are not added to element metadata if we can't find any page-breaks in the
document (which may be a common case).

In the DOCX format, determining page numbers is strictly a best-efforts attempt since
actual page-breaks are determined at rendering time (e.g. printing) based on the
font-metrics of the target device. Explicit (hard) page-breaks are always recorded in the
docx file but the rendered page-breaks are only added optionally.
N)_document_contains_pagebreaksrt   r   s    rD   metadata_page_number+DocxPartitionerOptions.metadata_page_number  s     &*%G%Gt!!QTQrE   c                    U R                   $ )a/  The current page number.

Note this value may not represent the actual rendered page number when rendered page-break
indicators are not present in the document (not uncommon). Use `.metadata_page_number` for
metadata purposes, which is `None` when rendered page-breaks are not present in this
document.
)rt   r   s    rD   page_number"DocxPartitionerOptions.page_number  s     !!!rE   c                4    U R                   =(       d    [        $ )z5The sub-partitioner to use for DOCX image extraction.)r|   _NullPicturePartitionerr   s    rD   rC   *DocxPartitionerOptions.picture_partitioner&  s     **E.EErE   c                T    U R                   c  [        R                  $ U R                   $ )zThe partitioning strategy for this document.

One of "hi_res", "fast", and a few others. These are available as class attributes on
`unstructured.partition.utils.constants.PartitionStrategy` but resolve to str values.
)rs   r0   HI_RESr   s    rD   r`   DocxPartitionerOptions.strategy0  s#     ,0>>+A ''Ut~~UrE   c                b    Sn[        U R                  R                  R                  U5      5      $ )a  True when there is at least one page-break detected in the document.

Only `w:lastRenderedPageBreak` elements reliably indicate a page-break. These are reliably
inserted by Microsoft Word, but probably don't appear in documents converted into .docx
format from for example .odt format.
z./w:body/w:p/w:r/w:lastRenderedPageBreak | ./w:body/w:p/w:hyperlink/w:r/w:lastRenderedPageBreak | ./w:body/w:tbl/w:tr/w:tc/w:p/w:r/w:lastRenderedPageBreak | ./w:body/w:tbl/w:tr/w:tc/w:p/w:hyperlink/w:r/w:lastRenderedPageBreak)boolr   elementxpath)ru   r   s     rD   r   4DocxPartitionerOptions._document_contains_pagebreaks9  s/    V 	 DMM))//677rE   c                V   U R                   (       a  U R                   $ [        U R                  [        R                  5      (       aI  U R                  R                  S5        [        R                  " U R                  R                  5       5      $ U R                  c   eU R                  $ )zThe Word 2007+ document file to be partitioned.

This is either a `str` path or a file-like object. `python-docx` accepts either for opening
a document file.
r   )	rp   
isinstancero   tempfileSpooledTemporaryFileseekioBytesIOreadr   s    rD   r   !DocxPartitionerOptions._docx_fileN  sr     ????"
 djj("?"?@@JJOOA::djjoo/00zz%%%zzrE   c                   U R                   (       a  [        R                  R                  U R                   5      (       d!  [	        S[        U R                   5       35      e[        R                  " U R                   5      (       d!  [        S[        U R                   5       35      e U $ U R                  (       aI  [        R                  " U R                  5      (       d!  [        S[        U R                  5       35      e U $ [        S5      e)z6Raise on first invalide option, return self otherwise.zno such file or directory: z(not a ZIP archive (so not a DOCX file): zQno DOCX document specified, either `filename` or `file` argument must be provided)
rp   ospathisfileFileNotFoundErrorreprzipfile
is_zipfile
ValueErrorro   r   s    rD   ry    DocxPartitionerOptions._validateb  s     ??77>>$//22'*Ed4??F[E\(]^^%%doo66 #KDQUQ`Q`LaKb!cdd 7  ZZ%%djj11 #KDQUQ[Q[L\K]!^__ 2 	 c rE   )ro   rp   rq   rr   rt   rs   )r\   IO[bytes] | Nonerb   
str | Noner]   r   r^   r   r_   intr`   r   )rh   r   rQ   rA   )rC   r?   rQ   r
   rQ   r   )rQ   Iterator[PageBreak])rQ   r   )rQ   z
int | NonerQ   r   )rQ   r?   )rQ   r;   )rQ   zstr | IO[bytes])rQ   rA   )rT   rU   rV   rW   rX   r|   rv   rY   rc   rB   r   r   r]   r   r^   r   r   propertyr   r   rC   r`   r   r   ry   rZ   rI   rE   rD   rA   rA      sn   `!  %&#2 2 	2
 "2  $2 "2 2$ ) ) 9 9 . . ) )C + + 
 
   R R " " F F V V 8 8(  &rE   rA   c                  N   \ rS rSrSrS!S jr\S"S j5       rS#S jrS#S jr	S$S jr
S%S jr\S&S	 j5       r\S'S
 j5       rS(S jrS)S jrS$S jrS*S jrS+S jrS,S jrS-S jrS.S jrS/S jrS0S jrS1S jrS2S jrS3S jrS4S jrS5S jrS6S jrS7S jrS8S jr S8S jr!S9S jr"Sr#g ):rd   iu  z8Provides `.partition()` for MS-Word 2007+ (.docx) files.c                    Xl         g rn   _opts)ru   rM   s     rD   rv   _DocxPartitioner.__init__x  s    
rE   c                t    U " U5      nUR                   (       a  UR                  5       $ UR                  5       $ )zFPartition MS Word documents (.docx format) into its document elements.)_document_contains_sections_iter_document_elements#_iter_sectionless_document_elements)rK   rM   ru   s      rD   re   '_DocxPartitioner.iter_document_elements{  s>     4y // ((*	
 99;	
rE   c              #    #    [        U R                  R                  5       H  u  pU R                  X5       Sh  vN   U R	                  U5       Sh  vN   UR                  5        Hc  n[        U[        5      (       a  U R                  U5       Sh  vN   M3  [        U[        5      (       d  MJ  U R                  U5       Sh  vN   Me     U R                  U5       Sh  vN   M     g N N N\ N, N7f)zFGenerate each document-element in (docx) `document` in document order.N)	enumerate	_documentsections_iter_section_page_breaks_iter_section_headersiter_inner_contentr   r   _iter_paragraph_elements	DocxTable_iter_table_element_iter_section_footers)ru   section_idxsection
block_items       rD   r   (_DocxPartitioner._iter_document_elements  s      %.dnn.E.E$F K55kKKK11':::%88:
 j)44#<<ZHHH	   $77
CCC ; 11'::: %GK: I D:s^   9C8C.C8C0A C8C2C83C8C4C8$C6%
C80C82C84C86C8c              #    #    U R                   R                  5        Hc  n[        U[        5      (       a  U R	                  U5       Sh  vN   M3  [        U[
        5      (       d  MJ  U R                  U5       Sh  vN   Me     g N; N7f)zGenerate each document-element in a docx `document` that has no sections.

A "section-less" DOCX must be iterated differently. Also it will have no headers or footers
(because those live in a section).
N)r   r   r   r   r   r   r   )ru   r   s     rD   r   4_DocxPartitioner._iter_sectionless_document_elements  si      ..;;=J*i0088DDDJ	2233J??? >D @s*   AB		B
B	'B	;B<
B	B	c              #    #    SR                  S UR                  R                  S5       5       5      nUR                  5       (       d  gU R	                  U5      nU R                  U5      (       a2  [        U5      R                  5       nU(       a  [        UU[        S9v   gU R                  U5      nU(       a  U" X#[        S9v   gU R                  U5      nU(       a  U" X#[        S9v   g[        X#[        S9v   g7f)zGenerate zero-or-one document element for `paragraph`.

In Word, an empty paragraph is commonly used for inter-paragraph spacing. An empty paragraph
does not contribute to the document-element stream and will not cause an element to be
emitted.
r   c              3  :   #    U  H  nUR                   v   M     g 7frn   )text).0es     rD   	<genexpr>B_DocxPartitioner._classify_paragraph_to_element.<locals>.<genexpr>  s      
 FFs   zJw:r | w:hyperlink | w:r/descendant::wp:inline[ancestor::w:drawing][1]//w:rN)r   metadatar   )r   r   )join_pr   strip_paragraph_metadata_is_list_itemr   r$   r<   _style_based_element_type&_parse_paragraph_text_for_element_typer'   )ru   rL   r   r   
clean_text
TextSubClss         rD   _classify_paragraph_to_element/_DocxPartitioner._classify_paragraph_to_element  s      ww 
\\''\
 
 zz||++I6 i((&t,224J#%%5 
  33I>
$L\]] @@K
$L\]] 4=MNNs   C>D c           
        ^^ SU4S jjmSU4S jjm[        UR                   Vs/ s H  n[        T" U5      5      PM     sn5      $ s  snf )aH  HTML string version of `table`.

Example:

    <table>
    <tbody>
    <tr><th>item  </th><th style="text-align: right;">  qty</th></tr>
    <tr><td>spam  </td><td style="text-align: right;">   42</td></tr>
    <tr><td>eggs  </td><td style="text-align: right;">  451</td></tr>
    <tr><td>bacon </td><td style="text-align: right;">    0</td></tr>
    </tbody>
    </table>

`is_nested` is used for recursive calls when a nested table is encountered. Certain
behaviors are different in that case, but the caller can safely ignore that parameter and
allow it to take its default value.
c              3    >#    U R                  5        Hf  n[        U=n[        5      (       a  UR                  v   M*  [        U=n[        5      (       d  MC  UR
                   H  nT" U5       Sh  vN   M     Mh     g N7f)zGenerate the text of each paragraph or table in `cell` as a separate string.

A table nested in `cell` is converted to the normalized text it contains.
N)r   r   r   r   r   rows)cellr   rL   tablerowiter_row_cells_as_texts        rD   iter_cell_block_itemsF_DocxPartitioner._convert_table_to_html.<locals>.iter_cell_block_items  sl     
 #557
:5iyAA $..( 3Y??$zz#9##>>>  * 8 ?s   ABB1A?2Bc              3    >#    [        U R                  5       H  nSv   M	      U R                   H;  nSR                  T" U5      5      nSR                  UR	                  5       5      v   M=     [        U R                  5       H  nSv   M	     g! [
         a'  n[        R                  " SU 35        Sv    SnANMSnAff = f7f)a  Generate the normalized text of each cell in `row` as a separate string.

The text of each paragraph within a cell is not separated. A table nested in a cell is
converted to a normalized string of its contents and combined with the text of the
cell that contains the table.
r    z1Skipping cell in _iter_row_cells_as_text due to: N)	rangegrid_cols_beforecellsr   split	Exceptionloggingwarninggrid_cols_after)r   _r   	cell_textr   r   s        rD   r   G_DocxPartitioner._convert_table_to_html.<locals>.iter_row_cells_as_text  s      3//0 1  IID #)>t)D EI((9??#455 & 3../ 0  "STUSV WXs/   !CAB 0!C
CB=8C=CCr   r   rQ   Iterator[str])r   r   rQ   r  )r   r   rf   )ru   r   rr   r   s      @@rD   _convert_table_to_html'_DocxPartitioner._convert_table_to_html  sA    &	?	4 ,V[V`V`,aV`QRT2H2K-LV`,abb,as   Ac                .    U R                   R                  $ r   )r   r   r   s    rD   r   _DocxPartitioner._document   s     zz"""rE   c                @    [        U R                  R                  5      $ )a  True when there is at least one section in the document.

This is always true for a document produced by Word, but may not always be the case when the
document results from conversion or export. In particular, a Microsoft Teams chat-transcript
export will have no sections.
)r   r   r   r   s    rD   r   ,_DocxPartitioner._document_contains_sections%  s     DNN++,,rE   c                P   ^  SU 4S jjnSR                  S U" U5       5       5      $ )am  The text enclosed in `hdrftr` as a single string.

        Each paragraph is included along with the text of each table cell. Empty text is omitted.
        Each paragraph text-item is separated by a newline ("
") although note that a paragraph
        that contains a line-break will also include a newline representing that line-break, so
        newlines do not necessarily distinguish separate paragraphs.

        The entire text of a table is included as a single string with a space separating the text
        of each cell.

        A header with no text or only whitespace returns the empty string ("").
        c              3    >#    U R                  5        Ho  n[        U[        5      (       a  UR                  R	                  5       v   M6  [        U[
        5      (       d  MM  SR                  TR                  U5      5      v   Mq     g7f)zGenerate each text item in `hdrftr` stripped of leading and trailing whitespace.

This includes paragraphs as well as table cell contents.
r   N)r   r   r   r   r   r   r   _iter_table_texts)hdrftrr   ru   s     rD   iter_hdrftr_texts?_DocxPartitioner._header_footer_text.<locals>.iter_hdrftr_texts=  si     
 %779
j)44$////11	  ((4#9#9*#EFF :s   AB!'B
c              3  6   #    U  H  o(       d  M  Uv   M     g 7frn   rI   r   r   s     rD   r   7_DocxPartitioner._header_footer_text.<locals>.<genexpr>K  s     L*C$t*C   
	)r  _Header | _FooterrQ   r  )r   )ru   r  r  s   `  rD   _header_footer_text$_DocxPartitioner._header_footer_text/  s&    	G yyL*;F*CLLLrE   c                j    [        UR                  5      (       a  gSUR                  R                  ;   $ )z7True when `paragraph` can be identified as a list-item.Tz	<w:numPr>)r,   r   r   xml)ru   rL   s     rD   r   _DocxPartitioner._is_list_itemM  s)    INN++ill....rE   c              #    ^#    SU4S jjmT" U5       Hn  n[        U[        5      (       a4  U R                  U5       Sh  vN   U R                  U5       Sh  vN   ML  U R                  R                  5        Sh  vN   Mp     g NF N/ N7f)zGenerate zero-or-more document elements for `paragraph`.

The generated elements can be both textual elements and PageBreak elements. An empty
paragraph produces no elements.
c              3     >#    U R                   (       d  U v   gU R                  S   nUR                  nU(       a  Uv   Uv   UR                  nU(       a  T" U5       Sh  vN   gg N7f)a  Generate Paragraph and RenderedPageBreak items from `paragraph`.

Each generated paragraph is the portion of the paragraph on the same page. When the
paragraph contains no page-breaks, it is iterated unchanged and iteration stops. When
there is a page-break, in general there one paragraph "fragment" before the page break,
the page break, and then the fragment after the page break. However many combinations
are possible. The first item can be either a page-break or a paragraph, but the type
always alternates throughout the sequence.
Nr   )contains_page_breakrendered_page_breakspreceding_paragraph_fragmentfollowing_paragraph_fragment)rL   
page_breakr"  r#  iter_paragraph_itemss       rD   r%  G_DocxPartitioner._iter_paragraph_elements.<locals>.iter_paragraph_items[  sp      00"77:J ,6+R+R(+22
 ,6+R+R( ,/0LMMM ,Ms   AA+"A)#A+N)rL   r   rQ   z'Iterator[Paragraph | RenderedPageBreak])r   r   r   _iter_paragraph_imagesr   r   )ru   rL   itemr%  s      @rD   r   )_DocxPartitioner._iter_paragraph_elementsT  sr     	NB )3D$	**>>tDDD66t<<<::;;=== 4D<=s5   =B BBB	#B=B>
B	BBc              #    #    UR                    Hk  nUR                  (       a  UR                  R                  5       OSnU(       d  M9  UR                  (       a  USS.v   UR                  (       d  Md  USS.v   Mm     g7f)zLGenerate e.g. {"text": "MUST", "tag": "b"} for each emphasis in `paragraph`.r   b)r   tagiN)runsr   r   bolditalic)ru   rL   runr   s       rD   _iter_paragraph_emphasis)_DocxPartitioner._iter_paragraph_emphasis  sW     >>C'*xx388>>#RDxx#C00zzz#C00 "s   A-A?3A?c              #     #    U R                   R                  nUR                  XR                   5       Sh  vN   g N7f)zRGenerate `Image` element for each picture shape in `paragraph` when so configured.N)r   rC   rN   )ru   rL   PicturePartitionerClss      rD   r'  '_DocxPartitioner._iter_paragraph_images  s/      !%

 > >(66y**MMMs   5?=?c              #  :  ^ #    SU 4S jjnU" UR                   S5       Sh  vN   UR                  (       a  U" UR                  S5       Sh  vN   T R                  R                  R
                  (       a  U" UR                  S5       Sh  vN   gg Nr NH N
7f)a  Generate any `Footer` elements defined for this section.

A Word document has up to three header and footer definition pairs for each document
section, a primary, first-page, and even-page header and footer. The first-page pair
applies only to the first page of the section (perhaps a title page or chapter start). The
even-page pair is used in book-bound documents where there are both recto and verso pages
(it is applied to verso (even-numbered) pages). A page where neither more specialized
footer applies uses the primary footer.
c           
   3     >#    U R                   (       a  gTR                  U 5      nU(       d  g[        U[        [	        TR
                  R                  USS9S9v   g7f)z2Generate zero-or-one Footer elements for `footer`.Nr   rg   header_footer_typecategory_depthr   r   r   )is_linked_to_previousr  r    r<   r   r   r   )footerr:  r   ru   s      rD   iter_footer;_DocxPartitioner._iter_section_footers.<locals>.iter_footer  V     ++++F3D!1(!ZZ::'9#$    AAprimaryN
first_page	even_page)r>  r   r:  r;   rQ   Iterator[Footer])r>  "different_first_page_header_footerfirst_page_footerr   settings odd_and_even_pages_header_footereven_page_footer)ru   r   r?  s   `  rD   r   &_DocxPartitioner._iter_section_footers  sz     	" w~~y99955"7#<#<lKKK>>""CC"7#;#;[III D 	:KI3   BB+BB?BBBBBc              #  :  ^ #    SU 4S jjnU" UR                   S5       Sh  vN   UR                  (       a  U" UR                  S5       Sh  vN   T R                  R                  R
                  (       a  U" UR                  S5       Sh  vN   gg Nr NH N
7f)zGenerate `Header` elements for this section if it has them.

See `._iter_section_footers()` docstring for more on docx headers and footers.
c           
   3     >#    U R                   (       a  gTR                  U 5      nU(       d  g[        U[        [	        TR
                  R                  USS9S9v   g7f)z2Generate zero-or-one Header elements for `header`.Nr   r9  r<  )r=  r  r!   r<   r   r   r   )headerr:  r   ru   s      rD   maybe_iter_headerA_DocxPartitioner._iter_section_headers.<locals>.maybe_iter_header  rA  rB  rC  NrD  rE  )rP  r   r:  r;   rQ   Iterator[Header])rP  rG  first_page_headerr   rI  rJ  even_page_header)ru   r   rQ  s   `  rD   r   &_DocxPartitioner._iter_section_headers  s{     	" %W^^Y???55()B)BLQQQ>>""CC()A)A;OOO D 	@QOrM  c              #  V  ^ #    SU 4S jjnUR                   nU[        R                  :X  a/  U" 5       (       d"  T R                  R	                  5        Sh  vN   gU[        R
                  :X  a5  US:X  a  gU" 5       (       a"  T R                  R	                  5        Sh  vN   g NO N7f)a  Generate zero-or-one `PageBreak` document elements for `section`.

A docx section has a "start" type which can be "continuous" (no page-break), "nextPage",
"evenPage", or "oddPage". For the next, even, and odd varieties, a `w:renderedPageBreak`
element signals one page break. Here we only need to handle the case where we need to add
another, for example to go from one odd page to another odd page and we need a total of
two page-breaks.
c                 <   > T R                   R                  S-  S:H  $ )N   r[   )r   r   r   s   rD   page_is_odd?_DocxPartitioner._iter_section_page_breaks.<locals>.page_is_odd  s    ::))A-22rE   Nr   r   )
start_typer   	EVEN_PAGEr   r   ODD_PAGE)ru   r   r   rZ  r\  s   `    rD   r   *_DocxPartitioner._iter_section_page_breaks  s     	3 ''
 )333 ==::;;=== 	 +444a}}::;;=== 	 > >s%   AB)B%A	B)B' B)'B)c              #    #    U R                   R                  (       a  U R                  U5      OSnSR                  U R	                  U5      5      nU R                  U5      u  pE[        U[        [        UU R                   R                  U R                   R                  U R                   R                  U=(       d    SU=(       d    SS9S9v   g7f)zBGenerate zero-or-one Table element for a DOCX `w:tbl` XML element.Nr   )text_as_htmlrg   r   r   emphasized_text_contentsemphasized_text_tags)r   r   )r   r^   r  r   r  _table_emphasisr   r<   r   r   r   r   )ru   r   
html_table
text_tablerb  rc  s         rD   r   $_DocxPartitioner._iter_table_element  s     
 37**2R2RD''.X\ 	 XXd44U;<
9=9M9Me9T6 -$'66 JJ;;"jj66)A)IT%9%AT
 	
s   CCc              #    #    UR                    HC  n UR                   H/  nUR                   H  nU R                  U5       Sh  vN   M     M1     ME     g N! [         a$  n[
        R                  " SU 35         SnAMs  SnAff = f7f)zHGenerate e.g. {"text": "word", "tag": "b"} for each emphasis in `table`.Nz-Skipping row in _iter_table_emphasis due to: )r   r   
paragraphsr2  r   r   r   )ru   r   r   r   rL   r   s         rD   _iter_table_emphasis%_DocxPartitioner._iter_table_emphasis  sw     ::C  IID%)__	#'#@#@#KKK &5 &	  L "OPQs STs@   B
2AA
AB
A
B#B<B
BB
c           	   #     ^ #    SU 4S jjnUR                    HT  nUR                  nUR                   H5  nUR                  S:X  a  M  S U" [	        XQ5      5       5        Sh  vN   M7     MV     g N7f)zGenerate text of each cell in `table` stripped of leading and trailing whitespace.

Nested tables are recursed into and their text contributes to the output in depth-first
pre-order. Empty strings due to empty or whitespace-only cells are dropped.
c              3    >#    U R                  5        Hf  n[        U[        5      (       a  UR                  R	                  5       v   M6  [        U[
        5      (       d  MM  TR                  U5       Sh  vN   Mh     g N	7f)zGenerate each text item in `cell` stripped of leading and trailing whitespace.

This includes paragraphs as well as table cell contents.
N)r   r   r   r   r   r   r  )r   r   ru   s     rD   iter_cell_texts;_DocxPartitioner._iter_table_texts.<locals>.iter_cell_texts%  si     
 #557
j)44$////11	   $55jAAA 8 Bs   AB!B5A?6
Bcontinuec              3  6   #    U  H  o(       d  M  Uv   M     g 7frn   rI   r  s     rD   r   5_DocxPartitioner._iter_table_texts.<locals>.<genexpr>:  s     W-NTRVDD-Nr  Nr  )r   _trtc_lstvMerger   )ru   r   rn  r   trtcs   `     rD   r  "_DocxPartitioner._iter_table_texts  s`     	B ::CBii99
*W_U2=M-NWWW    Xs   A A3#A1$A3c                    [         R                  " U R                  U5      5      u  p#U Vs/ s H  oDS   PM	     snU Vs/ s H  oDS   PM	     sn4$ s  snf s  snf )z@[contents, tags] pair describing emphasized text in `paragraph`.r   r,  )	itertoolsteer2  )ru   rL   iter_p_emphiter_p_emph_2r   s        rD   _paragraph_emphasis$_DocxPartitioner._paragraph_emphasis<  sR    %.]]43P3PQZ3[%\"$/0Kq6K0]2S]U8]2STT02S   A Ac                   ^ TR                   (       d  / / / 4$ SU4S jjn[        U" 5       5      nU Vs/ s H  oDS   =(       d    SPM     nnU Vs/ s H  oDS   PM	     nnXVU4$ s  snf s  snf )z,Describes hyperlinks in `paragraph`, if any.c               3  X  >#    Sn TR                  5        H  n[        U[        5      (       a  U [        UR                  5      -  n M2  [        U[
        5      (       d  MI  UR                  nUR                  nU nU [        U5      -  n U(       d  Mz  U(       d  M  [        X#US9v   M     g7f)zGenerate `Link` typed-dict for each external link in `paragraph`.

Word uses hyperlinks for internal "jumps" within the document, as well as for web and
other external locations. Only generate the external ones.
r   )r   urlstart_indexN)r   r   r   lenr   r   r  r#   )offsetr(  r   r  r  rL   s        rD   iter_paragraph_linksC_DocxPartitioner._paragraph_link_meta.<locals>.iter_paragraph_linksF  s      F!446dC((c$))n,Fi0099D((C"(Kc$i'F
     D{KK' 7s   AB*AB*r   r   r  )rQ   zIterator[Link])
hyperlinksrf   )ru   rL   r  linkslink
link_texts	link_urlss    `     rD   _paragraph_link_meta%_DocxPartitioner._paragraph_link_metaA  sw    ##r2:	L8 )+, 6;;UT6l(b(U
;-23UT%[U	3e++ <3s   A%A*c                x   U R                  U5      nU R                  U5      u  p4U R                  U5      u  pVn[        UU=(       d    SU=(       d    SU R                  R
                  U R                  R                  U=(       d    SU=(       d    SU=(       d    SU R                  R                  S9	nSUl        U$ )z.ElementMetadata object describing `paragraph`.N)	r;  rb  rc  rg   r   r  r  r  r   r:   )	_parse_category_depth_by_styler~  r  r   r   r   r   r   r   )	ru   rL   r;  rb  rc  r  r  r  element_metadatas	            rD   r   $_DocxPartitioner._paragraph_metadatai  s    <<YG9=9Q9QR[9\6 '+'@'@'K$
u*)%=%E!5!=ZZ22**22!)T'4-4

77

 -3)rE   c                *   UR                   R                  S5      nU(       a  [        [        US   5      5      $ UR                  =(       a    UR                  R
                  =(       d    SnU R                  U5      nUS:  a  U$ U R                  5       $ )z0Determine category depth from paragraph metadataz./w:pPr/w:numPr/w:ilvl/@w:valr   Normal)_elementr   roundfloatstylename#_parse_category_depth_by_style_name#_parse_category_depth_by_style_ilvl)ru   rL   r   
style_namedepths        rD   r  /_DocxPartitioner._parse_category_depth_by_style|  s}     ""(()HIuQx))  oo>)//*>*>K8
88D19L ;;==rE   c                    g)Nr   rI   r   s    rD   r  4_DocxPartitioner._parse_category_depth_by_style_ilvl  s    rE   c                    SS jnUR                  S5      (       a  U" U5      $ US:X  a  gSnUR                  U5      (       a  U" U5      $ g)zParse category-depth from the style-name of `paragraph`.

Category depth is 0-indexed and relative to the other element types in the document.
c                    U R                  5       nU(       a)  US   R                  5       (       a  [        US   5      S-
  $ S$ )Nr[   r   )r   isdigitr   )suffixpartss     rD   _extract_numberM_DocxPartitioner._parse_category_depth_by_style_name.<locals>._extract_number  s9    LLNE*/E"I4E4E4G4G3uRy>A%OaOrE   Headingr8   r[   )r3   r4   r5   r6   r   )r  r;   rQ   r   )
startswith)ru   r  r  list_prefixess       rD   r  4_DocxPartitioner._parse_category_depth_by_style_name  sZ    	P
   ++":..# P  //":.. rE   c                    UR                   R                  5       n[        U5      S:  a  g[        U5      (       a  [        $ [        U5      (       a  [        $ [        U5      (       a  [        $ g)zEAttempt to differentiate the element-type by inspecting the raw text.rY  N)	r   r   r  r/   r   r-   r   r.   r%   )ru   rL   r   s      rD   r   7_DocxPartitioner._parse_paragraph_text_for_element_type  sW    ~~##%t9q=%%ND!!%d++  rE   c                    UR                   =(       a    UR                   R                  =(       d    Sn[        R                  U5      $ )zElement-type for `paragraph` based on its paragraph-style.

Returns `None` when the style doesn't tell us anything useful, including when it
is the default "Normal" style.
r  )r  r  STYLE_TO_ELEMENT_MAPPINGget)ru   rL   r  s      rD   r   *_DocxPartitioner._style_based_element_type  s4      oo>)//*>*>K8
 (++J77rE   c                    [         R                  " U R                  U5      5      u  p#U Vs/ s H  oDS   PM	     snU Vs/ s H  oDS   PM	     sn4$ s  snf s  snf )z<[contents, tags] pair describing emphasized text in `table`.r   r,  )rz  r{  rj  )ru   r   iter_tbl_emphiter_tbl_emph_2r   s        rD   rd   _DocxPartitioner._table_emphasis  sR    )2t7P7PQV7W)X&$12Mq6M24W!uX4WXX24Wr  r   N)rM   rA   rQ   None)rM   rA   rQ   Iterator[Element])rQ   r  )rL   r   rQ   r  )r   r   rQ   r;   r   r   )r  r  rQ   r;   )rL   r   rQ   r   )rL   r   rQ   Iterator[dict[str, str]])rL   r   rQ   rR   )r   r   rQ   rF  )r   r   rQ   rS  )r   r   r   r   rQ   r   )r   r   rQ   zIterator[Table])r   r   rQ   r  )r   r   rQ   r  )rL   r   rQ   tuple[list[str], list[str]])rL   r   rQ   z'tuple[list[str], list[str], list[Link]])rL   r   rQ   r   )rL   r   rQ   r   r   )r  r;   rQ   r   )rL   r   rQ   zType[Text] | None)r   r   rQ   r  )$rT   rU   rV   rW   rX   rv   rY   re   r   r   r   r  r   r   r   r  r   r   r2  r'  r   r   r   r   rj  r  r~  r  r   r  r  r  r   r   rd  rZ   rI   rE   rD   rd   rd   u  s    B 
 
;:@.O`;cz # # - -M</->^	1N JDP:$L
.X<U
&,P &>$28$YrE   rd   c                  ,    \ rS rSrSr\SS j5       rSrg)r   i  zWDoes not parse the provided paragraph for pictures and generates zero `Image` elements.c              #     #    g7f)zNo-op picture partitioner.NrI   rJ   s      rD   rN   %_NullPicturePartitioner.iter_elements  s
      	s   rI   NrP   rS   rI   rE   rD   r   r     s    a rE   r   )rC   r?   rQ   r  rn   )rg   r   r\   r   r]   r   r^   r   r_   r   r`   r   rh   r   rQ   zlist[Element])Z
__future__r   r   rz  r   r   r   r   	functoolsr   typingr   r   r   r   r	   r:   docx.documentr
   docx.enum.sectionr   docx.oxml.tabler   docx.oxml.text.paragraphr   docx.sectionr   r   r   
docx.tabler   r   r   r   docx.text.hyperlinkr   docx.text.pagebreakr   docx.text.paragraphr   docx.text.runr   typing_extensionsr   unstructured.chunkingr   unstructured.cleaners.corer   unstructured.common.html_tabler   unstructured.documents.elementsr   r   r   r   r    r!   r"   r#   r$   r%   r&   r'   r(   unstructured.file_utils.modelr)   &unstructured.partition.common.metadatar*   r+    unstructured.partition.text_typer,   r-   r.   r/   &unstructured.partition.utils.constantsr0   unstructured.utilsr1   r  r<   __annotations__r=   r>   rB   r?   DOCXrj   rA   rd   r   rI   rE   rD   <module>r     sl   # 	   	   % 4 4  " . " ) 2 2 ) " ) 1 )  ' 7 4 G     3 Y  E 0t  	
       T H h h 8  X!" X#$ = B  # )i ).	9 .M( 6 / " $"& !// / 	/
  / / / / /  /dx xvZ	Y Z	YD rE   