
    Xf0                        d Z ddlZddlmZ ddlmZ ddlmZ ddlmZ ddl	m
Z
 ddlmZ dd	lmZ dd
lmZ ddlmZ ddlmZ ddlmZ ddddddZdddZd Zd Zd Zd Zd Zd Z G d de          Z G d de          ZdS ) zBio.SeqIO support for the "xdna" file format.

The Xdna binary format is generated by Christian Marck's DNA Strider program
and also used by Serial Cloner.
    N)match)pack)unpack)BiopythonWarning)Seq)ExactPosition)
SeqFeature)SimpleLocation)	SeqRecord   )SequenceIterator)SequenceWriterDNARNAprotein)r   r            linearcircular)r   r   c                 z    |                      |          }t          |          |k     rt          d|z            |S )z9Read the specified number of bytes from the given handle.z Cannot read %d bytes from handle)readlen
ValueError)handlelengthdatas      0lib/python3.11/site-packages/Bio/SeqIO/XdnaIO.py_readr   '   s=    ;;vD
4yy6;fDEEEK    c                     t          dt          | d                    d         }t          d|z  t          | |                    d                             d          S )zRead a Pascal string.

    A Pascal string comprises a single byte giving the length of the string
    followed by as many bytes.
    >Br   r   z%dsASCII)r   r   decode)r   r   s     r   _read_pstringr%   /   sS     D%**++A.F%&.%"7"788;BB7KKKr    c                 :    t          t          |                     S )N)intr%   )r   s    r   _read_pstring_as_integerr(   9   s    }V$$%%%r    c                 r    t          |           }|dk    r!t          | t          |                    }||fS dS )a  Read an overhang specification.

    An overhang is represented in a XDNA file as:
      - a Pascal string containing the text representation of the overhang
        length, which also indicates the nature of the overhang:
        - a length of zero means no overhang,
        - a negative length means a 3' overhang,
        - a positive length means a 5' overhang;
      - the actual overhang sequence.

    Examples:
      - 0x01 0x30: no overhang ("0", as a P-string)
      - 0x01 0x32 0x41 0x41: 5' AA overhang (P-string "2", then "AA")
      - 0x02 0x2D 0x31 0x43: 3' C overhang (P-string "-1", then "C")

    Returns a tuple (length, sequence).

    r   )NN)r(   r   abs)r   r   overhangs      r   _read_overhangr,   =   s?    & &f--F{{V--!!|r    c                     d |                      d          D             D ]<}t          d|          }|r|                                \  }}|g||<   2d|vr|g|d<   =dS )zParse the description field of a Xdna feature.

    The 'description' field of a feature sometimes contains several
    GenBank-like qualifiers, separated by carriage returns (CR, 0x0D).
    c                 8    g | ]}t          |          d k    |S )r   )r   ).0xs     r   
<listcomp>z._parse_feature_description.<locals>.<listcomp>_   s#    ===q#a&&1*****r    z^([^=]+)="([^"]+)"?$"noteN)splitr   groups)desc
qualifierslinemqualvalues         r   _parse_feature_descriptionr=   X   s     >=DJJv..=== 	( 	(($// 	(((**KD% %wJt__"&Jv	( 	(r    c                    t          |           }t          |           }t          |           pd}t          |           }t          |           }t          dt          | d                    \  }}}	|rd}
nd}
||}}t          |            t	          |dz
  ||
          }i }|r|g|d<   t          ||           t          |||          }|j                            |           d	S )
zRead a single sequence feature.misc_featurez>BBxBr   r   )strandlabel)typer8   N)	r%   r(   r   r   r
   r=   r	   featuresappend)r   recordnamer7   rC   startendforwarddisplayarrowrA   locationr8   features                 r   _read_featurerO   k   s
     D  D  2ND$V,,E
"6
*
*C !'wfa0@0@ A AWgu  %s &
 eaiV<<<HJ %#f
7tZ000DDDG
O7#####r    c                   .     e Zd ZdZ fdZd Zd Z xZS )XdnaIteratorzParser for Xdna files.c                 P    t                                          |dd           dS )a   Parse a Xdna file and return a SeqRecord object.

        Argument source is a file-like object in binary mode or a path to a file.

        Note that this is an "iterator" in name only since an Xdna file always
        contain a single sequence.

        bXdna)modefmtNsuper__init__)selfsource	__class__s     r   rY   zXdnaIterator.__init__   s*     	cv66666r    c                     |                     d          }|st          d          t          |          dk     rt          d          |                     ||          }|S )z9Start parsing the file, and return a SeqRecord generator.p   zEmpty file.z2Improper header, cannot read 112 bytes from handle)r   r   r   iterate)rZ   r   headerrecordss       r   parsezXdnaIterator.parse   sc     S!! 	,]+++v;;QRRR,,vv..r    c              #   .  K   t          d|          \  }}}}}}|dk    rt          d          |t          vrt          d          t          ||                              d          }	t          ||                              d          }
|
                    d          d         }t          t          |	          |
||          }t          |         rt          |         |j        d<   |t          v rt          |         |j        d	<   t          |                    d
                    d
k    rct          |           t          |           t          dt          |d
                    d         }|dk    rt          ||           |d
z  }|dk    |V  dS )z.Parse the file and generate SeqRecord objects.z>BBB25xII60xI12xr   zUnsupported XDNA versionzUnknown sequence typer#    )descriptionrG   idmolecule_typetopologyr   r"   N)r   r   
_seq_typesr   r$   r5   r   r   annotations_seq_topologiesr   r   r,   rO   )rZ   r   r`   versionseq_typerh   r   
neg_length
com_lengthsequencecommentrG   rF   num_featuress                 r   r_   zXdnaIterator.iterate   s     HNI
 I
E(Hfj* a<<7888:%%4555((//88
++227;; }}S!!!$ 3x==gDTRRRh 	G2<X2FF/&&-<X-FFz*v{{1~~!##
 6"""6""" "$fa(8(899!<L""ff---! "" r    )__name__
__module____qualname____doc__rY   rb   r_   __classcell__r\   s   @r   rQ   rQ      s\          	7 	7 	7 	7 	7  $& & & & & & &r    rQ   c                   .     e Zd ZdZ fdZd Zd Z xZS )
XdnaWriterzWrite files in the Xdna format.c                 N    t                                          |d           dS )zInitialize an Xdna writer object.

        Arguments:
         - target - Output stream opened in binary mode, or a path to a file.

        wb)rU   NrW   )rZ   targetr\   s     r   rY   zXdnaWriter.__init__   s(     	d+++++r    c                    t          |          }	 t          |          }n# t          $ r t          d          dw xY w	 t          |           t          d          # t          $ r Y nw xY wd| _        |j                            d          }|d}nd|v rd}nd	|v rd
}n	d|v rd}nd}|j                            dd          dk    rd}nd}|j                            |j	                  r|j        }n|j	         d|j         }| j
                            t          dd||t          |          dt          |          d                     | j
                            t          |j                             | j
                            |                    d                     | j
                            t          dd                     |                     d           |                     d           d |j        D             }t          |j                  t          |          z
  }|dk    rt'          j        d| dt*                     t          |          dk    r9t          |          dz
  }t'          j        d| t*                     |dd         }| j
                            t          dt          |                               |D ]|}	|                     |	j                            ddg          d                    d}
|	j        D ]:}|dv r|	j        |         D ]%}t          |
          dk    r|
dz   }
|
| d| dz   }
&;|                     |
           |                     |	j                   t1          |	j        j                  dz   }t1          |	j        j                  }d}|	j        j        d k    r||}}d}|                     t;          |                     |                     t;          |                     | j
                            t          d!|ddd                     |                     d"           ~| j        rt'          j        d#t*                     dS )$a  Write the specified record to a Xdna file.

        Note that the function expects a list (or iterable) of records
        as per the SequenceWriter interface, but the list should contain
        only one record as the Xdna format is a mono-record format.
        zMust have one sequenceNzMore than one sequence foundFrg   r   r   r   r   r   r   r   rh   r   r   rd   z>BBB25xII60xI11xB   r#   r"   0c                     g | ]B}t          |j        j        t                    !t          |j        j        t                    @|CS  )
isinstancerM   rH   r   rI   )r/   fs     r   r1   z)XdnaWriter.write_file.<locals>.<listcomp>.  sU     
 
 
!**M::
 1:>=99	

 
 
r    z	Dropping z features with fuzzy locationsz%Too many features, dropping the last rB    )rB   translationr2   z="r3   r@   z>BBBBz127,127,127z1Some annotations were truncated to 255 characters)iternextStopIterationr   _has_truncated_stringsrj   getre   
startswithrf   r   writer   r   bytesseqencode_write_pstringrD   warningswarnr   r8   rC   r'   rM   rH   rI   rA   str)rZ   ra   rF   rg   seqtyperh   rq   rD   droprN   re   qnamevalrH   rI   rA   s                   r   
write_filezXdnaWriter.write_file   s    w--	A']]FF 	A 	A 	A566D@	A	MMM;<<< 	 	 	D	 ',#*..?? GGm##GGm##GG-''GGG!!*h77:EEHHH
 ((33 	:(GG99V%799G 	#FG	 		
 	
 	
 	%
++,,,'..11222$tQ--(((C   C   

 
_
 
 
 6?##c(mm3!88M@D@@@BR   x==3x==3&DM>>>@P    ~H$tS]]33444 	/ 	/G 2 6 6w E Ea HIIIK + C C444"-e4 C CC;''!++&1F&:"-50B0BC0B0B0B"BKKC ,,,---(.//!3Eg&*++CF&",, %sE

+++C)))Kd7FAq!<<===....& 	MCEU   qs   ! < A 
A+*A+c                    t          |          dk    rd| _        |dd         }| j                            t	          dt          |                               | j                            |                    d                     dS )z*Write the given string as a Pascal string.r   TNr"   r#   )r   r   r   r   r   r   )rZ   ss     r   r   zXdnaWriter._write_pstringg  st    q66C<<*.D'$3$A$tSVV,,---!((7++,,,,,r    )rs   rt   ru   rv   rY   r   r   rw   rx   s   @r   rz   rz      s`        )), , , , ,  B- - - - - - -r    rz   )rv   r   rer   structr   r   Bior   Bio.Seqr   Bio.SeqFeaturer   r	   r
   Bio.SeqRecordr   
Interfacesr   r   ri   rk   r   r%   r(   r,   r=   rO   rQ   rz   r   r    r   <module>r      s                                         ( ( ( ( ( ( % % % % % % ) ) ) ) ) ) # # # # # # ( ( ( ( ( ( & & & & & &  
 :..  L L L& & &  6( ( (&#$ #$ #$LF F F F F# F F FRS- S- S- S- S- S- S- S- S- S-r    